Class SessionDedupeLedger

java.lang.Object
com.ultikits.ultitools.utils.SessionDedupeLedger
All Implemented Interfaces:
DedupeLedger

final class SessionDedupeLedger extends Object implements DedupeLedger
The DedupeLedger every inbound handler of the framework shares (plan 22-21, D-17 as narrowed by S-52, S-59): the command-id set and the receipts live in the current session's CommandDedupeSet, and persistNow() writes them, with the outbox, to cloud-outbox.json through the session's CloudStateStore.

Lifetime. One instance lives as long as the plugin is enabled, so the monitor stays the same across reconnects and across the session replacements of a login or logout. Each call asks the SessionDedupeLedger.Target supplier for the state of the session that is current at that moment; with no adopted credential (no target, or one without a store) firstSeen(java.lang.String) reports every id as new, no receipt exists and persistNow() fails, which the callers already treat as "continue with what is in memory".

Locks. Callers hold this ledger's monitor around a mutation and its persistence. persistNow() then takes the store's JVM-wide write lock and, inside it, the dedupe set's leaf monitor; it never takes a session monitor, so it cannot invert the lock order of CloudSession (S-32, S-37). It is synchronous and runs on the thread that handles the request -- the agent thread or the player-link handler thread, never the server thread. A module may complete its player-link result on any thread, the server thread included; PlayerLinkChannel moves the persistence of that result onto the player-link handler thread first.

  • Field Details

  • Constructor Details

    • SessionDedupeLedger

      SessionDedupeLedger(Supplier<SessionDedupeLedger.Target> target)
      Parameters:
      target - supplies the current session's state, or null while no credential is adopted
  • Method Details

    • fixed

      static SessionDedupeLedger fixed(CommandDedupeSet dedupe, CloudStateStore store, String serverId)
      Parameters:
      dedupe - the id set
      store - the state file writer, or null for an in-memory ledger
      serverId - the linked server's id
      Returns:
      a ledger bound to exactly that state
    • firstSeen

      public boolean firstSeen(String id)
      Description copied from interface: DedupeLedger
      Records a previously unseen id in memory, subject to retention bounds.
      Specified by:
      firstSeen in interface DedupeLedger
      Parameters:
      id - the request envelope ULID
      Returns:
      true for a newly recorded id, false for an unexpired duplicate
    • persistNow

      public void persistNow() throws IOException
      Writes the ids, their receipts and the outbox now, under the store's write lock.
      Specified by:
      persistNow in interface DedupeLedger
      Throws:
      IOException - when no store is adopted or the write fails; the dirty flags then stay set, so the next periodic flush retries
    • receiptFor

      public com.google.gson.JsonObject receiptFor(String id)
      Description copied from interface: DedupeLedger
      Looks up a completion result for replay, without invoking its handler again.
      Specified by:
      receiptFor in interface DedupeLedger
      Parameters:
      id - the completed-message envelope ULID
      Returns:
      the recorded result payload, or null when absent; callers must not mutate it
    • recordReceipt

      public void recordReceipt(String id, com.google.gson.JsonObject receipt)
      Records the receipt with its id. A receipt larger than CommandDedupeSet.MAX_RECEIPT_BYTES is not recorded and logs one WARNING: the reply is still sent, and a redelivery of that id asks the module again.
      Specified by:
      recordReceipt in interface DedupeLedger
      Parameters:
      id - the completed-message envelope ULID
      receipt - the result payload; callers must not mutate it after recording