java.lang.Object
com.ultikits.ultitools.interfaces.impl.data.json.JsonStore
All Implemented Interfaces:
DataStore

public class JsonStore extends Object implements DataStore
Json Data store.

The operator cache is keyed by (requesting identity, entity class), not by entity class alone -- two callers resolving to two different identities (two plugins on the plugin path, or two data folders on the external File path) never share a DataOperator instance (SILENT-04). Not static: DataStoreManager registers exactly one JsonStore instance, and instance scoping is what stops the cache from outliving a /reload.

Version:
1.0.0
Author:
wisdomme
  • Field Details

  • Constructor Details

    • JsonStore

      public JsonStore(String storeLocation)
  • Method Details

    • initScheduler

      private void initScheduler()
      Initialize the flush scheduler. Called lazily when first JsonStore is created. This avoids static initializer issues in test environments.

      Only the first JsonStore instance in a JVM ever starts the periodic flush task (guarded by the static schedulerInitialized flag, matching pre-existing behavior); in production there is exactly one JsonStore instance, so this flushes that instance's own cache, not a shared static one.

    • flushAllCaches

      void flushAllCaches()
      Flush all cached data operators. This method is extracted from BukkitRunnable for testability.
    • getDataOperatorCount

      int getDataOperatorCount()
      Get the number of registered data operators. Used for testing.
    • resetSchedulerState

      void resetSchedulerState()
      Reset the scheduler state. Used for testing.
    • getOperator

      public <T extends BaseDataEntity<String>> DataOperator<T> getOperator(UltiToolsPlugin plugin, Class<T> dataEntity)
      Description copied from interface: DataStore
      Get data operation entity class.
      Specified by:
      getOperator in interface DataStore
      Type Parameters:
      T - Must inherit BaseDataEntity
      Parameters:
      plugin - Plugin
      dataEntity - Data entity class
      Returns:
      Data operation entity
    • getOperator

      public <T extends BaseDataEntity<String>> DataOperator<T> getOperator(File dataFolder, Class<T> dataEntity)
      Description copied from interface: DataStore
      Get data operator for an external plugin, scoped to the plugin's own data folder. Refuses outright (D-18) when dataFolder resolves to a registered external plugin's scope that does not own dataEntity, or when dataFolder matches no registered scope at all -- an unresolvable folder fails closed rather than proceeding unchecked (D-15). A DataStore that overrides this method directly (as every backend shipped by this framework does) does not inherit this check; see the @deprecated note.
      Specified by:
      getOperator in interface DataStore
      Type Parameters:
      T - entity type
      Parameters:
      dataFolder - the external plugin's data folder (e.g., plugins/MyPlugin/)
      dataEntity - data entity class
      Returns:
      data operator
    • getOperatorUnchecked

      public <T extends BaseDataEntity<String>> DataOperator<T> getOperatorUnchecked(DataScope scope, Class<T> dataEntity)
      Internal, unchecked construction path (CR-01/CR-03, 02-13): DataStore.getOperator(DataScope, Class)'s default body calls this only after its own scope.owns(...) check has already passed. Branches internal/external exactly like identityOf(DataScope) already does for transactionManagerFor(DataScope) -- an internal scope resolves to internalLocation(String, Class) keyed on the plugin's own name (never the framework's shared core folder, the collapse regression 02-07 guarded against and CR-01 found reopened as a bypass), an external scope to externalLocation(File, Class).
      Specified by:
      getOperatorUnchecked in interface DataStore
      Type Parameters:
      T - Must inherit BaseDataEntity
      Parameters:
      scope - the requesting scope, already verified to own dataEntity
      dataEntity - data entity class
      Returns:
      data operator for that entity
    • getOperatorForIdentity

      private <T extends BaseDataEntity<String>> DataOperator<T> getOperatorForIdentity(String identity, String location, Class<T> dataEntity)
      Shared operator-construction body for all three entry points above, once ownership and the @Table annotation have already been established by whichever one of them was called. Single-sourced so the operator cache (keyed by (identity, entity)) and the transactionManagerFor(...) wiring are each written in exactly one place.
    • ensureTableAnnotation

      private static void ensureTableAnnotation(Class<?> dataEntity)
    • internalLocation

      private String internalLocation(String identity, Class<?> dataEntity)
      The internal-plugin storage location shape: <store location>/<plugin name>/<@Table value>. Shared by getOperator(UltiToolsPlugin, Class) and getOperatorUnchecked(DataScope, Class)'s internal branch.
    • externalLocation

      private static String externalLocation(File dataFolder, Class<?> dataEntity)
      The external-plugin storage location shape: <plugin's own data folder>/data/<@Table value>. Shared by getOperator(File, Class) and getOperatorUnchecked(DataScope, Class)'s external branch.
    • isInternalScope

      private static boolean isInternalScope(DataScope scope)
      Whether scope is an internal plugin's own scope -- its dataFolder is exactly the core framework's own data folder (DataScope.forPlugin's construction). The same disambiguation identityOf(DataScope) already uses for transactionManagerFor(DataScope) (02-05), extracted so getOperatorUnchecked(DataScope, Class) can also pick the matching location-construction formula, not just the matching identity string.
    • transactionManagerFor

      public JsonTransactionManager transactionManagerFor(DataScope scope)
      Resolves (creating on first use) the JsonTransactionManager for scope, giving the JSON backend a real TransactionManager so @Transactional is no longer refused on datasource.type: json (02-05, D-03). Called by PluginManager.wireAop's JSON branch, a different package -- public for that reason, even though it is not part of the officially-extensible DataStore contract; the actual snapshot mechanics it drives stay package-private on SimpleJsonDataOperator, reached only from inside this class.

      Shares one instance with every SimpleJsonDataOperator getOperator(com.ultikits.ultitools.abstracts.UltiToolsPlugin, java.lang.Class<T>) hands out for the same identity, so a single @Transactional method's writes across several of that plugin's entities are governed by the same transaction.

      Parameters:
      scope - the identity token minted for the caller
      Returns:
      this store's manager for that caller's identity
    • transactionManagerFor

      private JsonTransactionManager transactionManagerFor(String identity)
    • identityOf

      private static String identityOf(DataScope scope)
      Derives the same identity getOperator(UltiToolsPlugin, Class) and getOperator(File, Class) each already resolve for JsonStore.OperatorKey, from a DataScope instead of a raw plugin or File.

      DataScope carries both a plugin name and a data folder but no explicit internal-vs-external discriminator, so this disambiguates the same way DataScope.forPlugin(com.ultikits.ultitools.abstracts.UltiToolsPlugin, java.util.Set<java.lang.Class<?>>) itself is built: an internal scope's data folder is always the core UltiTools plugin's own folder (shared by every internal plugin), which no external plugin's own folder can equal. When it matches, the plugin-path identity (DataScope.getPluginName()) is used; otherwise the external-path identity (canonicalPath(java.io.File)) is used.

    • canonicalPath

      private static String canonicalPath(File dataFolder)
    • destroyAllOperators

      public void destroyAllOperators()
      Description copied from interface: DataStore
      Save all possible caches and destroy all data operation classes.
      Specified by:
      destroyAllOperators in interface DataStore
    • getStoreType

      public String getStoreType()
      Description copied from interface: DataStore
      Get the type of data storage.
      Specified by:
      getStoreType in interface DataStore
      Returns:
      Data storage type