Atomic Operations

Atomic methods are for same-key read-modify-write operations across LSM-tree segments.

They are useful for:

  • counters,
  • compare-and-set logic,
  • appending to a value,
  • updating an aggregate,
  • initializing a value if absent and updating if present.

They are not the default write API. UseUpsertfor simple inserts and replacements.

Add Or Update

zoneTree.TryAtomicAddOrUpdate(
    key: 42,
    valueToAdd: 1,
    valueUpdater: (ref int value) =>
    {
        value++;
        return true;
    },
    result: (in int value, long opIndex, OperationResult result) =>
    {
        Console.WriteLine($"{result}: {value} at {opIndex}");
    });

The updater decides whether the existing value should change. Returningfalsecancels the update. ForTryAtomicGetAndUpdate, that means the key was found but no new value was written; for add-or-update APIs, cancellation is reported asOperationResult.Cancelled.

ValueUpdaterDelegate<TValue>receives a local value byref, and it is designed to update that value. For mutable reference types, in-place mutation is valid when the delegate commits by returningtrue. If the delegate may cancel, decide first, then mutate or assign.

zoneTree.TryAtomicGetAndUpdate(42, out var user, (ref User value) =>
{
    if (!ShouldRename(value))
        return false;

    value = value with { Name = "Bob" };
    return true;
});

See value mutability.

Why Atomic Methods Exist

ZoneTree is an LSM-tree. A key can exist in several layers before compaction removes older versions. Atomic methods synchronize the read-decision-write sequence so other atomic methods observe a consistent ordering.

Mixing Atomic And Regular Writes

You can use atomic methods for specific hot keys while the rest of the tree usesUpsert.

Example:

  • stats:user:123uses atomic increment,
  • profile:user:123uses normalUpsert,
  • index entries use normalUpsertorForceDelete.

Avoid mixing regular writes and atomic writes for the same invariant. If a value must be protected by atomic read-modify-write, keep all writes for that value on the atomic path.

When To Use Transactions Instead

Atomic methods coordinate one key. Use transactions when the correctness rule spans multiple keys.