-
Notifications
You must be signed in to change notification settings - Fork 3
Data store/cache service improvements needed #21
Description
v0.0.38 added support for AWS being used for the data store/data cache. This means that Slackémon can now finally be used on a ephemeral filesystem service like Heroku.
However, there are issues inherent in this:
- AWS is an eventually consistent filesystem, which theoretically could cause some player and battle data to be lost, overridden, or to temporarily step back in time.
- Slackémon was originally written around using the filesystem as a data store, so it is quite liberal in its opening of and writing to files. While this doesn't seem to cause too much latency when the calls are coming from nearby (eg. Heroku is also on AWS), it can quickly add up AWS costs.
- There is no concept of file locking built in. This is already an issue that exists even when Slackémon is run with its own local data store: a player trying to perform certain actions simultaneously, across different Slack messages or button actions, could potentially find they lose some data or even worse, corrupt their player JSON file if it is read by a local system while it is being written to.
Slackémon currently has separate settings for an image cache and a data cache, they can both be set to either 'local' or 'aws' independently. However, we're utilising the data cache as both a data cache and a data store.
We likely could solve the above issues by:
- When 'aws' is set as the data cache, also using a secondary local cache to reduce reads from AWS for the life of the current filesystem.
- Implementing an additional option for the data store, allowing either 'local' or an alternative store such as Redis or Postgres.
- Slackémon currently uses JSON files to store player and battle data (one per player and one per battle) so it would be ideal, to avoid having to rewrite alot, to stick somewhat to this method if possible. However, perhaps each individual player's Pokémon could be separated into a separate file to prevent single JSON strings from ever getting too big.
- The method chosen would need to be easy to set up and support. Both Redis and Postgres are simple on Heroku; we would just need to look into Docker options too.
- Implementing some sort of file lock for the data store, whether 'local' or the above alternative option is in use.
In addition, while in-memory caching is already in use for most data cache reads (eg. Pokémon & species data, move data, item data) and data store reads (player data and battle data), we could also probably reduce writes by ensuring that there's one save to a player file per request (at the moment there are sometimes two especially due to the slackemon_add_xp() function being called while something else requiring a save is also happening, such as catching a Pokémon).