Redis Transactions Tutorial

In this Redis tutorial we learn how to queue multiple commands for later execution with guaranteed transactions.

We will take a look at how to create transaction queues, execute the queued commands, how to clear the queue and how transaction errors are handled.

Here's a table of contents of what you'll learn in this lesson:
(click on a link to skip to its section)

Let's jump right in.

What is a Redis Transaction

A database transaction represents any change in a database that’s independent of other transactions.

Redis transactions allow us to queue more than one operation and then execute all of them with a single command.

Redis transactions are performed with two important guarantees:

  1. All the commands in a transaction are serialized and executed in sequence. A request from one client cannot be served when another is in the middle of execution.
  2. Redis transactions are atomic, which means that either all of the commands are processed, or none of them are.

How to create a transaction

The MULTI command allows us to add operations to a queue to be performed later when an execution command is called.

As an example, let’s consider that we want to get the value of a key, perform calculations on the value and then update the key with the new value. We don’t want any other operation to change the value until we’re done with our calculations.

The MULTI command doesn’t have any arguments and we simply execute it before any other commands we want to queue.

Syntax:
MULTI

Redis will respond with a confirmation that the following commands will be added to the transaction queue.

Output:
OK

Now we can add commands to the queue.

Example:
SET num-1 20

Redis will add the script to the queue and return a confirmation message again.

Output:
QUEUED

We can do this with multiple commands

Example:
INCR num-1

GET num-1

DECR num-1

GET num-1

Now all three commands are queued to be executed.

How to execute the transaction queue’s commands

To execute the stack of queued commands in a Redis transaction we use the EXEC command. This command doesn’t have any arguments.

Syntax:
EXEC

Redis will perform the operations in sequence and return an array with the result of each operation in the same order the commands were queued.

Output:
1) OK
2) (integer) 21
3) "21"
4) (integer) 20
5) "20"

How to clear the transaction queue

If we need to clear the transaction queue, we use the DISCARD command. This command doesn’t have any arguments.

Syntax:
DISCARD

Let’s create a transaction queue and then clear it before execution

Example:
MULTI

INCR num-1

GET num-1

DISCARD

If the queue was cleared successfully, Redis will send a confirmation message.

Output:
OK

If we try to EXEC the transaction, it will fail and raise an error.

Output:
(error) ERR EXEC without MULTI

If we return the value of ‘num-1’ now, we can see that nothing changed.

Output:
"20"

How errors are handled within a transaction

It’s possible for us to encounter two types of errors.

As an example, let’s consider that we try to perform the wrong type of operation.

Example:
MULTI

SET msg "Hello"

LPOP msg

APPEND msg " World"

EXEC

In the example above we try to remove an element from a list with LPOP , but the msg key isn’t a list so the operation will fail.

Output:
1) OK
2) (error) WRONGTYPE Operation against a key holding the wrong kind of value
3) (integer) 11

Even if one command fails, the rest will still execute. If we GET ‘msg’, we can see that the APPEND command still executed.

Output:
"Hello World"

Another type of error is when a command fails to be queued. There may be an error before exec is even called.

For example, a command could be syntactically incorrect.

Example:
MULTI

GET key value

In the example above, we pass the wrong number of arguments to the GET command.

Output:
(error) ERR wrong number of arguments for 'get' command

We can still add more items to the queue.

Example:
SET msg "Hello There"
Output:
QUEUED

But if we try to EXEC , Redis will raise an error because it remembers that there was one in the stack.

Output:
(error) EXECABORT Transaction discarded because of previous errors.

In this case, Redis will DISCARD the transaction automatically.