Experimental Discord bot written in Python
Nelze vybrat více než 25 témat Téma musí začínat písmenem nebo číslem, může obsahovat pomlčky („-“) a může být dlouhé až 35 znaků.

storage.py 2.1KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667686970717273747576
  1. import json
  2. from os.path import exists
  3. from discord import Guild
  4. from config import CONFIG
  5. class Storage:
  6. """
  7. Static class for managing persisted bot state.
  8. """
  9. # discord.Guild.id -> dict
  10. __guild_id_to_state = {}
  11. def state_for_guild(guild: Guild) -> dict:
  12. """
  13. Returns the state for the given guild, loading from disk if necessary.
  14. Always returns a dict.
  15. """
  16. state: dict = __guild_id_to_state[guild.id]
  17. if state is not None:
  18. # Already in memory
  19. return state
  20. # Load from disk if possible
  21. __trace(f'No loaded state for guild {guild.id}. Attempting to load from disk.')
  22. state = __load_guild_state(guild)
  23. __guild_id_to_state[guild.id] = state
  24. return state
  25. def save_guild_state(guild: Guild) -> NoneType:
  26. """
  27. Saves state for the given guild to disk, if any exists.
  28. """
  29. state: dict = __guild_id_to_state[guild.id]
  30. if state is None:
  31. # Nothing to save
  32. return
  33. __save_guild_state(guild, state)
  34. def __save_guild_state(guild: Guild, state: dict) -> NoneType:
  35. """
  36. Saves state for a guild to a JSON file on disk.
  37. """
  38. path: str = __guild_path(guild)
  39. __trace('Saving state for guild {guild.id} to {path}')
  40. with open(path, 'w') as file:
  41. # Pretty printing to make more legible for debugging
  42. # Sorting keys to help with diffs
  43. json.dump(state, file, indent='\t', sort_keys=True)
  44. __trace('State saved')
  45. def __load_guild_state(guild: Guild) -> dict:
  46. """
  47. Loads state for a guild from a JSON file on disk.
  48. """
  49. path: str = __guild_path(guild)
  50. if not exists(path):
  51. __trace(f'No state on disk for guild {guild.id}. Returning {{}}.')
  52. return {}
  53. __trace('Loading state from disk for guild {guild.id}')
  54. with open(path, 'r') as file:
  55. state = json.load(file)
  56. __trace('State loaded')
  57. return state
  58. def __guild_path(guild: Guild) -> str:
  59. """
  60. Returns the JSON file path where guild state should be written.
  61. """
  62. config_value: str = CONFIG['statePath']
  63. path: str = config_value if config_value.endswith('/') else f'{config_value}/'
  64. return f'{path}guild_{guild.id}.json'
  65. def __trace(message: str) -> NoneType:
  66. print(f'{Storage.__name__}: {message}')