Skip to main content

Create Compare-Exchange Items


Create item using a cluster-wide session

  • Create compare-exchange items using a cluster-wide session when you want the creation to be part of a transaction committed via SaveChanges(). This is suitable if you want to include compare-exchange item creation and document changes in the same transaction. Learn more about cluster-wide sessions in Cluster transactions - overview.

  • Use CreateCompareExchangeValue() to register the creation of a new compare-exchange item in the session.
    The item will be created as part of the cluster-wide transaction when SaveChanges() is called.

  • Exceptions:
    An InvalidOperationException is thrown if the session is not opened in cluster-wide mode.
    If the key already exists, SaveChanges() will throw a ClusterTransactionConcurrencyException.

  • Examples:

    Ex.1 - Create compare-exchange item - with string value

    // The session must be opened in cluster-wide mode
    using (var session = store.OpenSession(
    new SessionOptions { TransactionMode = TransactionMode.ClusterWide }))
    {
    // Call 'CreateCompareExchangeValue' to register the creation of a new compare-exchange item
    // as part of the cluster-wide transaction. Specify the item's KEY and VALUE.
    // The item will be created only when 'SaveChanges' is called.
    CompareExchangeValue<string> item =
    session.Advanced.ClusterTransaction.CreateCompareExchangeValue(
    key: "user1-name@example.com",
    value: "users/1"
    );

    // Commit the cluster-wide transaction.
    // This will create the compare-exchange item,
    // or throw a 'ClusterTransactionConcurrencyException' if the key already exists.
    session.SaveChanges();
    }

    Ex.2 - Create compare-exchange item - with custom object value

    // Define the object to be stored as the value
    var user1Info = new UserInfo()
    {
    UserDocumentId = "users/1",
    AdditionalInfo = "someInfo.."
    };

    // The session must be opened in cluster-wide mode
    using (var session = store.OpenSession(
    new SessionOptions { TransactionMode = TransactionMode.ClusterWide }))
    {
    // Call 'CreateCompareExchangeValue' to register the creation of a new compare-exchange item
    // as part of the cluster-wide transaction. Specify the item's KEY and VALUE.
    // The item will be created only when 'SaveChanges' is called.
    CompareExchangeValue<UserInfo> item =
    session.Advanced.ClusterTransaction.CreateCompareExchangeValue(
    key: "user1-name@example.com",
    value: user1Info // Pass the object instance
    );

    // Commit the cluster-wide transaction.
    // This will create the compare-exchange item,
    // or throw a 'ClusterTransactionConcurrencyException' if the key already exists.
    session.SaveChanges();
    }

    Ex.3 - Create compare-exchange item - with metadata

    // The session must be opened in cluster-wide mode
    using (var session = store.OpenSession(
    new SessionOptions { TransactionMode = TransactionMode.ClusterWide }))
    {
    // Call 'CreateCompareExchangeValue', specify the item's KEY and VALUE:
    CompareExchangeValue<string> item =
    session.Advanced.ClusterTransaction.CreateCompareExchangeValue(
    key: "user1-name@example.com",
    value: "users/1"
    );

    // Add METADATA fields to the item:
    item.Metadata["field-name"] = "some value";
    item.Metadata["email-type"] = "work email"; // e.g. describe the email type

    // Commit the cluster-wide transaction.
    // This will create the compare-exchange item,
    // or throw a 'ClusterTransactionConcurrencyException' if the key already exists.
    session.SaveChanges();
    }

    Ex.4 - Create multiple items

    You can create multiple compare-exchange items in the same cluster-wide transaction.

    // The session must be opened in cluster-wide mode
    using (var session = store.OpenSession(
    new SessionOptions { TransactionMode = TransactionMode.ClusterWide }))
    {
    // You can create multiple compare-exchange items before calling 'SaveChanges'.
    // Call 'CreateCompareExchangeValue' for each item you want to create in the transaction.
    session.Advanced.ClusterTransaction.CreateCompareExchangeValue(
    key: "user7-name@example.com", value: "users/7"
    );

    session.Advanced.ClusterTransaction.CreateCompareExchangeValue(
    key: "user8-name@example.com", value: "users/8"
    );

    session.Advanced.ClusterTransaction.CreateCompareExchangeValue(
    key: "user9-name@example.com", value: "users/9"
    );

    // All three items will be created atomically as part of the same transaction.
    // If any creation fails (e.g., due to an existing key), the entire transaction is rolled back
    // and none of the new items will be created.
    session.SaveChanges();
    }

Create item using a store operation

  • Use the PutCompareExchangeValueOperation store operation to create a compare-exchange item independently,
    without opening a session. This is ideal for stand-alone tasks that don't require batching multiple commands into a single transactional session.

  • Note:
    PutCompareExchangeValueOperation is used for both creating and modifying compare-exchange items.
    The intent of the operation is determined by the index you pass:

    • An index of 0 indicates a create operation.
    • A non-zero index indicates a modify operation.
  • Creating a new compare-exchange item will succeed only if:

    • The passed index is 0, and
    • The specified key does not already exist in the database.
  • The operation will return a failed result (no exception is thrown) in the following cases:

    • A new key is provided, but the index is not 0.
    • The key already exists, even if the passed index is 0.
  • Examples:

    Ex.5 - Create compare-exchange item - with string value

    // Create a new compare-exchange item:
    // ===================================

    // Define the put compare-exchange operation. Pass:
    // * KEY: a new unique string identifier (e.g. a user's email)
    // * VALUE: an associated value (e.g. the user's document ID)
    // * INDEX: pass '0' to indicate that this is a new compare-exchange item
    var putCmpXchgOp = new PutCompareExchangeValueOperation<string>(
    "user1-name@example.com", "users/1", 0);

    // Execute the operation by passing it to Operations.Send
    CompareExchangeResult<string> putResult = store.Operations.Send(putCmpXchgOp);

    // Check results
    bool successful = putResult.Successful; // Has operation succeeded
    long indexForItem = putResult.Index; // The version number assigned to the new item

    // If 'successful' is true, then a new compare-exchange item has been created
    // with the unique email key and the associated value.

    Ex.6 - Create compare-exchange item - with custom object value

    // Create a new compare-exchange item:
    // ===================================

    // Define the object to be stored as the value
    var user1Info = new UserInfo()
    {
    UserDocumentId = "users/1",
    AdditionalInfo = "someInfo.."
    };

    // Define the put compare-exchange operation.
    // Pass the key, the object instance, and '0' to indicate that this is a new item.
    // Specify the object type in the generic <T> parameter.
    var putCmpXchgOp = new PutCompareExchangeValueOperation<UserInfo>(
    "user1-name@example.com", user1Info, 0);

    // Execute the operation by passing it to Operations.Send
    CompareExchangeResult<UserInfo> putResult = store.Operations.Send(putCmpXchgOp);

    // Check results
    bool successful = putResult.Successful; // Has operation succeeded
    long indexForItem = putResult.Index; // The version number assigned to the new item

    // If 'successful' is true, then a new compare-exchange item has been created
    // with the unique email key and the associated value.

    Ex.7 - Create compare-exchange item - with metadata

    // Create a new compare-exchange item with metadata:
    // =================================================

    // Define the metadata - must be a valid JSON object
    var metadata = new MetadataAsDictionary
    {
    { "email-type", "work email" }
    };

    // Define the put compare-exchange operation.
    // Pass a 4'th parameter with the metadata object.
    var putCmpXchgOp = new PutCompareExchangeValueOperation<string>(
    "user1-name@example.com", "users/1", 0, metadata);

    // Execute the operation by passing it to Operations.Send
    CompareExchangeResult<string> putResult = store.Operations.Send(putCmpXchgOp);

    // Check results
    bool successful = putResult.Successful; // Has operation succeeded
    long indexForItem = putResult.Index; // The version number assigned to the new item

    // If successful is true then a new compare-exchange item has been created
    // with the unique key, value, and metadata.

Create item using the Studio

To create compare-exchange items using the Studio, go to Documents > Compare Exchange.

The compare-exchange view

The compare-exchange view

  1. Key
    Enter a unique identifier for the compare-exchange item (up to 512 bytes).
    This key must be unique across the entire database.
  2. Value
    Enter the value to associate with the key.
    Can be a number, string, array, or any valid JSON object.
  3. Metadata (optional)
    Add any additional data you want to store with the item.
    Must be a valid JSON object.
    Can be used to set expiration time for the compare-exchange item.
  4. Save
    Click to create the compare-exchange item.
    If the key already exists, an error message will be shown.

Syntax


PutCompareExchangeValueOperation

Create compare-exchange item using a store operation:

public PutCompareExchangeValueOperation(
string key, T value, long index, IMetadataDictionary metadata = null)
ParameterTypeDescription
keystring
  • A unique identifier in the database scope.
  • Can be up to 512 bytes.
valueT
  • A value to be saved for the specified key.
  • Can be any value (number, string, array, or any valid JSON object).
indexlong
  • Pass 0 to create a new key.
  • When updating an existing key, pass the current number for concurrency control.
metadataIMetadataDictionary
  • Optional metadata to be saved for the specified key.
  • Must be a valid JSON object.

Returned object:

public class CompareExchangeResult<T>
{
public bool Successful;
public T Value;
public long Index;
}
Return ValueTypeDescription
Successfulbool
  • true if the put operation has completed successfully.
  • false if the put operation has failed.
ValueT
  • Upon success - the value of the compare-exchange item that was saved.
  • Upon failure - the existing value on the server.
Indexlong
  • The compare-exchange item's version.
  • This number increases with each successful modification of the value or metadata.
  • Upon success - the updated version of the compare-exchange item that was saved.
  • Upon failure - the existing version number on the server.

CreateCompareExchangeValue

Create compare-exchange item using cluster-wide session:

session.Advanced.ClusterTransaction.CreateCompareExchangeValue<T>(key, value);
ParameterTypeDescription
keystringThe compare-exchange item key. This string can be up to 512 bytes.
valueTThe associated value to store for the key.
Can be a number, string, array, or any valid JSON object.
CreateCompareExchangeValue returns:Description
CompareExchangeValue<T>The compare-exchange item that is added to the transaction.
It will be created when SaveChanges() is called.

The returned CompareExchangeValue contains:

PropertyTypeDescription
keystringThe compare-exchange item key. This string can be up to 512 bytes.
valueTThe value associated with the key.
indexlongThe index used for concurrency control.
Will be 0 when calling CreateCompareExchangeValue.