All Products
Search
Document Center

ApsaraDB for Redis:Transaction processing

Last Updated:Jul 12, 2024

ApsaraDB for Redis supports the transaction mechanism defined in Redis. You can run MULTI, EXEC, DISCARD, WATCH, and UNWATCH commands to perform atomic operations in transactions.

Transactions in Redis work differently than transactions in relational databases. If an operation in a transaction fails or the transaction is canceled by the DISCARD command, Redis does not perform transaction rollbacks.

Sample code

Example 1: Two clients process different keys

Sample code:

package transcation.kvstore.aliyun.com;
import java.util.List;
import redis.clients.jedis.Jedis;
import redis.clients.jedis.Transaction;

public class KVStoreTranscationTest {
    static final String host = "xxxxxx.m.cnhza.kvstore.aliyuncs.com";
    static final int port = 6379;
    static final String password = "password";
    // Note that these two keys have different content.
    static String client1_key = "KVStore-Transcation-1";
    static String client2_key = "KVStore-Transcation-2";
    public static void main(String[] args) {
        Jedis jedis = new Jedis(host, port);
        // The password of the ApsaraDB for Redis instance.
        String authString = jedis.auth(password);//password
        if (!authString.equals("OK")) {
            System.err.println("authentication failed: " + authString);
            jedis.close();
            return;
        }
        jedis.set(client1_key, "0");
        // Start another thread to simulate the other client.
        new KVStoreTranscationTest().new OtherKVStoreClient().start();
        Thread.sleep(500);
        Transaction tx = jedis.multi();// Start the transaction.
        //The following operations are submitted to the server as atomic operations.
        tx.incr(client1_key);
        tx.incr(client1_key);
        Thread.sleep(400);// The suspension of the thread does not affect the subsequent operations in the transaction. Other thread operations cannot be performed.
        tx.incr(client1_key);
        Thread.sleep(300);// The suspension of the thread does not affect the subsequent operations in the transaction. Other thread operations cannot be performed.
        tx.incr(client1_key);
        Thread.sleep(200);// The suspension of the thread does not affect the subsequent operations in the transaction. Other thread operations cannot be performed.
        tx.incr(client1_key);
        List<Object> result = tx.exec();// Execute the transaction.
        // Parse and display the results.
        for(Object rt : result){
            System.out.println("Client 1 > transaction in progress> "+rt.toString());
        }
        jedis.close();
    }
    class OtherKVStoreClient extends Thread{
        @Override
        public void run() {
            Jedis jedis = new Jedis(host, port);
            // The password of the ApsaraDB for Redis instance.
            String authString = jedis.auth(password);// password
            if (!authString.equals("OK")) {
                System.err.println("AUTH Failed: " + authString);
                jedis.close();
                return;
            }
            jedis.set(client2_key, "100");
            for (int i = 0; i < 10; i++) {
                try {
                    Thread.sleep(300);
                } catch (InterruptedException e) {
                    e.printStackTrace();
                }
                System.out.println("Client 2 > "+jedis.incr(client2_key));
            }
            jedis.close();
        }
    }
}

After you access the ApsaraDB for Redis instance with the correct endpoint and password and run the preceding Java code, the following output is displayed. The output demonstrates that client 1 and client 2 run in two different threads. The transaction operations submitted by client 1 are executed in a sequential order. Client 2 sends requests to perform an operation on another key during this period, but the operation is blocked. Client 2 must wait until all the transaction operations of client 1 are completed.

Expected output:

Client 2 > 101
Client 2 > 102
Client 2 > 103
Client 2 > 104
Client 1> transaction in progress> 1
Client 1> transaction in progress> 2
Client 1> transaction in progress> 3
Client 1> transaction in progress> 4
Client 1> transaction in progress> 5
Client 2 > 105
Client 2 > 106
Client 2 > 107
Client 2 > 108
Client 2 > 109
Client 2 > 110

Example 2: Two clients process the same key

The code in Example 1 is slightly modified so that two clients process the same key. The other parts of the code remain unchanged.

    ... ... 
// Note that the content of these two keys is now the same.
    static String client1_key = "KVStore-Transcation-1";
    static String client2_key = "KVStore-Transcation-1";
    ... ...

After the modified Java code is executed, the following output is displayed. The two clients run in different threads but process the same key. However, while client 1 uses the transaction mechanism to process this key, client 2 is blocked and must wait until all the transaction operations of client 1 are completed.

Client 2 > 101
Client 2 > 102
Client 2 > 103
Client 2 > 104
Client 1> transaction in progress> 105
Client 1> transaction in progress> 106
Client 1> transaction in progress> 107
Client 1> transaction in progress> 108
Client 1> transaction in progress> 109
Client 2 > 110
Client 2 > 111
Client 2 > 112
Client 2 > 113
Client 2 > 114
Client 2 > 115