- Type Parameters:
T- The objects that this journal uses to record its state snapshots.
- Direct Known Subclasses:
CauldronWrapper, ComposterWrapper, ItemStackResourceHandler, PlayerInventoryWrapper.DroppedItems, RootCommitJournal, SimpleEnergyHandler.EnergyJournal, StacksResourceHandler.StackJournal, TransactionalRandom
T in case it needs to revert to a previous state.
How to use from subclasses
- Call
updateSnapshots(TransactionContext)right before the state of your subclass is modified in a transaction. - Override
createSnapshot(): it is called when necessary to create an object representing the state of your subclass. - Override
revertToSnapshot(T): it is called when necessary to revert to a previous state of your subclass. - You may optionally override
onRootCommit(T): it is called at the end of a transaction that modified the state. For example, it could contain a call tosetChanged(). - (Advanced!) You may optionally override
releaseSnapshot(T): it is called once a snapshot object will not be used, for example you may wish to pool expensive state objects.
More technical explanation
updateSnapshots(TransactionContext) should be called before any modification.
This will record the state in the journal using createSnapshot() if no state was already saved for that transaction.
When the transaction is aborted and changes need to be rolled back, revertToSnapshot(T) will be called
to signal that the current state should revert to that of the snapshot.
The snapshot object is then released, and can be cached for subsequent use, or discarded.
When the root transaction is committed, revertToSnapshot(T) will not be called so that the current state of the journal
is retained. onRootCommit(T) will be called after the transaction is closed
and then releaseSnapshot(T) will be called because the snapshot is not necessary anymore.
-
Field Summary
Fields -
Constructor Summary
Constructors -
Method Summary
Modifier and TypeMethodDescription(package private) voidprotected abstract TReturns a new object containing a copy of this journal's current state.final booleanReturns whenever this journal is part of any ongoing transaction.(package private) voidonClose(Transaction transaction, boolean wasAborted) Perform the required state management when a transaction is closed.protected voidonRootCommit(T originalState) Called after the root transaction was successfully committed, to perform irreversible actions such assetChanged()or neighbor updates.protected voidreleaseSnapshot(T snapshot) Signals that the snapshot will not be used anymore, and is safe to cache for future calls tocreateSnapshot(), or discard entirely.protected abstract voidrevertToSnapshot(T snapshot) Rolls back to a state previously created bycreateSnapshot().voidupdateSnapshots(TransactionContext transaction) Update the stored snapshots so that the changes happening as part of the passed transaction can be correctly committed or rolled back.
-
Field Details
-
NO_SNAPSHOT
-
snapshots
-
snapshotCount
private int snapshotCount -
originalState
-
-
Constructor Details
-
SnapshotJournal
public SnapshotJournal()
-
-
Method Details
-
createSnapshot
Returns a new object containing a copy of this journal's current state.
One may settle for a partial copy of this journal's state, as long as the returned snapshot will be sufficient to rollback (via
revertToSnapshot(T)) all changes made to this journal's state since the snapshot was created.isInTransaction()will returntrueinside this callback, and will continue to returntrueuntil all snapshots have either been reverted to or committed.- Returns:
- a new object containing a copy of this journal's current state
-
revertToSnapshot
Rolls back to a state previously created bycreateSnapshot(). -
releaseSnapshot
Signals that the snapshot will not be used anymore, and is safe to cache for future calls tocreateSnapshot(), or discard entirely. -
onRootCommit
Called after the root transaction was successfully committed, to perform irreversible actions such assetChanged()or neighbor updates.isInTransaction()will returnfalseinside this callback.When a root transaction is being closed, all journals for which
onRootCommitwill be called are stored in a global thread-local queue. The processing of this queue starts immediately after the root transaction is closed. As such, new root transactions can safely be opened from this method.When a root transaction is opened from
onRootCommit, any journal might be modified, leading to moreonRootCommitcallbacks being enqueued:- A journal that is already enqueued for
onRootCommitwill not be enqueued a second time. It will thus be notified a single time for changes that spanned multiple transactions. TheoriginalStatewill be the state at the beginning of the first of these transactions. - A journal whose
onRootCommitwas already processed will be enqueued again. The journal will be notified a second time, withoriginalStatethe state at the beginning of the second transaction. - In particular, a journal is removed from the queue immediately before
onRootCommitis called. Should the journal be modified again from its ownonRootCommit, it will be added to the queue, andonRootCommitwill be called again later.
Given the large amount of actions that can happen between the last modification and the call to
onRootCommit, journals should not depend ononRootCommitbeing called immediately for correctness, and implementations of this method should be careful (e.g. in case the journal got removed from the level). For example, skipping block change notifications because the block was removed from the level is preferable than crashing or silently overwriting the block.- Parameters:
originalState- state of this journal before the transactional operations. This corresponds to the firstsnapshotthat was created in the transactional operations.
- A journal that is already enqueued for
-
isInTransaction
public final boolean isInTransaction()Returns whenever this journal is part of any ongoing transaction.
Always returns
truewhen invoked from withincreateSnapshot()andrevertToSnapshot(T), and corresponding calls toreleaseSnapshot(T). Returnsfalsewhen performing root commit actions outside a transaction.- Returns:
- whenever this journal is part of any ongoing transaction
-
updateSnapshots
Update the stored snapshots so that the changes happening as part of the passed transaction can be correctly committed or rolled back. This function should be called every time the journal is about to change its internal state as part of a transaction. However, only the first snapshot taken of that depth will be taken. -
onClose
Perform the required state management when a transaction is closed. -
callOnRootCommit
void callOnRootCommit()
-