|
| 1 | +# 1. Storage layer |
| 2 | + |
| 3 | +Date: 2023-11-15 |
| 4 | +Last update: 2023-12-27 |
| 5 | + |
| 6 | +**DO NOT rely on any APIs introduced until we finish the work completely!** |
| 7 | + |
| 8 | +## Status |
| 9 | + |
| 10 | +Work in progress |
| 11 | + |
| 12 | +## Context |
| 13 | + |
| 14 | +Slimefun has been around for a very long time and due to that, the way we |
| 15 | +wrote persistence of data has also been around for a very long time. |
| 16 | +While Slimefun has grown, the storage layer has never been adapted. |
| 17 | +This means that even all these years later, it's using the same old saving/loading. |
| 18 | +This isn't necessarily always bad, however, as Slimefun has grown both in terms of content |
| 19 | +and the servers using it - we've seen some issues. |
| 20 | + |
| 21 | +Today, files are saved as YAML files (sometimes with just a JSON object per line), |
| 22 | +which is good for a config format but not good for a data store. It can create very large files |
| 23 | +that can get corrupted, the way we've been saving data often means loading it all at once as well |
| 24 | +rather than lazy-loading and generally isn't very performant. |
| 25 | + |
| 26 | +For a long time we've been talking about rewriting our data storage in multiple forms |
| 27 | +(you may have seen this referenced for "BlockStorage rewrite" or "SQL for PlayerProfiles", etc.). |
| 28 | +Now is the time we start to do this, this will be a very large change and will not be done quickly or rushed. |
| 29 | + |
| 30 | +This ADR talks about the future of our data persistence. |
| 31 | + |
| 32 | +## Decision |
| 33 | + |
| 34 | +We want to create a new storage layer abstraction and implementations |
| 35 | +which will be backwards-compatible but open up new ways of storing data |
| 36 | +within Slimefun. The end end goal is we can quickly and easily support |
| 37 | +new storage backends (such as binary storage, SQL, etc.) for things like |
| 38 | +[PlayerProfile](https://github.com/Slimefun/Slimefun4/blob/bbfb9734b9f549d7e82291eff041f9b666a61b63/src/main/java/io/github/thebusybiscuit/slimefun4/api/player/PlayerProfile.java), [BlockStorage](https://github.com/Slimefun/Slimefun4/blob/bbfb9734b9f549d7e82291eff041f9b666a61b63/src/main/java/me/mrCookieSlime/Slimefun/api/BlockStorage.java), etc. |
| 39 | + |
| 40 | +We also want to be generally more efficient in the way we save and load data. |
| 41 | +Today, we load way more than is required. |
| 42 | +We can improve memory usage by only loading what we need, when we need it. |
| 43 | + |
| 44 | +We will do this incrementally and at first, in an experimental context. |
| 45 | +In that regard, we should aim to minimise the blast radius and lift as much |
| 46 | +as possible. |
| 47 | + |
| 48 | +### Quick changes overview |
| 49 | + |
| 50 | +* New abstraction over storage to easily support multiple backends. |
| 51 | +* Work towards moving away from the legacy YAML based storage. |
| 52 | +* Lazy load and save data to more efficiently handle the data life cycle. |
| 53 | + |
| 54 | +### Implementation details |
| 55 | + |
| 56 | +There is a new interface called [`Storage`](TBD) which is what all storage |
| 57 | +backends will implement. |
| 58 | +This will have methods for loading and saving things like |
| 59 | +[`PlayerProfile`](https://github.com/Slimefun/Slimefun4/blob/bbfb9734b9f549d7e82291eff041f9b666a61b63/src/main/java/io/github/thebusybiscuit/slimefun4/api/player/PlayerProfile.java) and [`BlockStorage`](https://github.com/Slimefun/Slimefun4/blob/bbfb9734b9f549d7e82291eff041f9b666a61b63/src/main/java/me/mrCookieSlime/Slimefun/api/BlockStorage.java). |
| 60 | + |
| 61 | +Then, backends will implement these |
| 62 | +(e.g. [`LegacyStorageBackend`](TBD) (today's YAML situation)) |
| 63 | +in order to support these functions. |
| 64 | +Not all storage backends are required support each data type. |
| 65 | +e.g. SQL may not support [`BlockStorage`](https://github.com/Slimefun/Slimefun4/blob/bbfb9734b9f549d7e82291eff041f9b666a61b63/src/main/java/me/mrCookieSlime/Slimefun/api/BlockStorage.java). |
| 66 | + |
| 67 | + |
| 68 | +## Addons |
| 69 | + |
| 70 | +The goal is that Addons will be able to use and implement new storage backends |
| 71 | +if they wish and also be extended so they can load/save things as they wish. |
| 72 | + |
| 73 | +The first few iterations will not focus on Addon support. We want to ensure |
| 74 | +this new storage layer will work and supports what we need it to today. |
| 75 | + |
| 76 | +This ADR will be updated when we get to supporting Addons properly. |
| 77 | + |
| 78 | +## Considerations |
| 79 | + |
| 80 | +This will be a big change therefore we will be doing it as incrementally as |
| 81 | +possible. |
| 82 | +Changes will be tested while in the PR stage and merged into the Dev releases when possible. |
| 83 | +We may do an experimental release if required. |
| 84 | + |
| 85 | +Phases do not (and very likely will not) be done within a single PR. They will also not have any timeframe attached to them. |
| 86 | + |
| 87 | +The current plan looks like this: |
| 88 | + |
| 89 | +* Phase 1 - Implement legacy data backend for [`PlayerProfile`](https://github.com/Slimefun/Slimefun4/blob/bbfb9734b9f549d7e82291eff041f9b666a61b63/src/main/java/io/github/thebusybiscuit/slimefun4/api/player/PlayerProfile.java). |
| 90 | + * We want to load player data using the new storage layer with the current |
| 91 | + data system. |
| 92 | + * We'll want to monitor for any possible issues and generally refine |
| 93 | + how this system should look |
| 94 | +* Phase 2 - Implement new experimental binary backend for [`PlayerProfile`](https://github.com/Slimefun/Slimefun4/blob/bbfb9734b9f549d7e82291eff041f9b666a61b63/src/main/java/io/github/thebusybiscuit/slimefun4/api/player/PlayerProfile.java). |
| 95 | + * Create a new backend for binary storage |
| 96 | + * Implement in an experimental capacity and allow users to opt-in |
| 97 | + * Provide a warning that this is **experimental** and there will be bugs. |
| 98 | + * Implement new metric for storage backend being used |
| 99 | +* Phase 3 - Mark the new backend as stable for [`PlayerProfile`](https://github.com/Slimefun/Slimefun4/blob/bbfb9734b9f549d7e82291eff041f9b666a61b63/src/main/java/io/github/thebusybiscuit/slimefun4/api/player/PlayerProfile.java). |
| 100 | + * Mark it as stable and remove the warnings once we're sure things are |
| 101 | + working correctly |
| 102 | + * Create a migration path for users currently using "legacy". |
| 103 | + * Enable by default for new servers |
| 104 | +* Phase 4 - Move [`BlockStorage`](https://github.com/Slimefun/Slimefun4/blob/bbfb9734b9f549d7e82291eff041f9b666a61b63/src/main/java/me/mrCookieSlime/Slimefun/api/BlockStorage.java) to new storage layer. |
| 105 | + * The big one! We're gonna tackle adding this to BlockStorage. |
| 106 | + This will probably be a large change and we'll want to be as |
| 107 | + careful as possible here. |
| 108 | + * Implement `legacy` and `binary` as experimental storage backends |
| 109 | + for BlockStorage and allow users to opt-in |
| 110 | + * Provide a warning that this is **experimental** and there will be bugs. |
| 111 | +* Phase 5 - Mark the new storage layer as stable for [`BlockStorage`](https://github.com/Slimefun/Slimefun4/blob/bbfb9734b9f549d7e82291eff041f9b666a61b63/src/main/java/me/mrCookieSlime/Slimefun/api/BlockStorage.java). |
| 112 | + * Mark it as stable and remove the warnings once we're sure things are |
| 113 | + working correctly |
| 114 | + * Ensure migration path works here too. |
| 115 | + * Enable by default for new servers |
| 116 | +* Phase 6 - Finish up and move anything else we want over |
| 117 | + * Move over any other data stores we have to the new layer |
| 118 | + * We should probably still do experimental -> stable but it should have |
| 119 | + less of a lead time. |
| 120 | + |
| 121 | +## State of work |
| 122 | + |
| 123 | +* Phase 1: In progress |
| 124 | + * https://github.com/Slimefun/Slimefun4/pull/4065 |
| 125 | +* Phase 2: Not started |
| 126 | +* Phase 3: Not started |
| 127 | +* Phase 4: Not started |
| 128 | +* Phase 5: Not started |
| 129 | +* Phase 6: Not started |
0 commit comments