See all blog posts

Using the CDRS Rust Driver with ScyllaDB

Editor’s Note: We have since launched our own ScyllaDB Rust driver, and have updated the ScyllaDB University course. You can find the new lesson here.

CHECK OUT THE LATEST RUST DRIVER LESSON ON SCYLLA UNIVERSITY

 

As part of the Using ScyllaDB Drivers course in ScyllaDB University, we recently published a new lesson, Rust and ScyllaDB. The lesson uses CDRS, which is an open-source ScyllaDB driver for Rust.

Rust is a programming language focused on performance, reliability, and safety. In the last four years it was voted “most loved programming language” in the Stack Overflow Developer Survey. In the lesson, we go over a simple Rust application that allows us to connect to a ScyllaDB cluster, store, and select temperature measurements from sensors.

Below is a recap of the lesson.

Creating a sample Rust Application

Our application will be able to store and query temperature time-series data. Each measurement will contain the following information:

  • The sensor ID for the sensor that measured the temperature
  • The time the temperature was measured
  • The temperature value

We’ll use a keyspace called tutorial:

CREATE KEYSPACE IF NOT EXISTS tutorial
    WITH REPLICATION = {
        'class': 'SimpleStrategy',
        'replication_factor': 1
};

As this is just an example, we’ll use SimpleStrategy with a single datacenter. Our cluster has a single node, so we’ll set the Replication Factor to one.

Based on the desired query being the temperature reported by a specific device for a given time interval, we’ll create the following table:

CREATE TABLE IF NOT EXISTS tutorial.temperature (
    device UUID,
    time timestamp,
    temperature smallint,
    PRIMARY KEY(device, time)
);

You can learn more about Basic Data Modeling in ScyllaDB here.

The application we’re building will be able to query all temperatures measured by a given device within a selected time frame. That’s why we will use the following SELECT query:

SELECT * FROM tutorial.temperature
    WHERE device = ?
    AND time > ?
    AND time < ?;

where ? will be replaced with actual values – device ID, time-from, and time-to, respectively.

Rust and connection to the DB

Our application name is temperature, and the required dependencies are defined in the Cargo.toml file:

Where:

  • CDRS – Rust ScyllaDB/Casandra driver
  • cdrs_helpers_derive helper utilities, which will help us to implement marshaling and unmarshaling for our data types.
  • uuid – package that provides UUID.
  • time – package for working with time primitives.

Next, we’ll declare these external dependencies inside the /src/main.rs file:

The file /src/db.rs will hold the logic for working with the ScyllaDB instance. To create an authorised connection with the database server, CDRS needs the following information:

  • authenticator – any structure that implements an Authenticator for a given authentication strategy defined by the ScyllaDB Server. For this example, we won’t use authentication so NoneAuthenticator should be used:

  • cluster configuration – a list of connection configurations provided for each node in a cluster.

Having that provided, we can create a new CDRS session (still in the /src/db.rs file):

In this lesson, the SingleNode load balancing strategy is used. CDRS also provides Random, RoundRobin, and RoundRobinSync strategies. If none of these satisfy your requirements, you can create your own strategy by implementing LoadBalancingStrategy for your structure, see an example here.

Next, still in the file /src/db.rs, we define functions for creating the keyspace and table where we will store temperature measurements. We’ll use queries for creating the keyspace and a table:

Next, we’ll create a structure that will represent a single temperature measurement that will be stored in the tutorial.temperature table this is defined in the file /src/temperature_measurement.rs:

As part of standard Debug, we’ve derived one extra trait – TryFromRow, provided by CDRS. It will help us to convert a ScyllaDB row into a TemperatureMeasurement Rust structure. Derive during the compilation time auto-generates code according to associated procedural macros. Procedural macros and derive is an advanced topic that is out of the scope of this lesson.

Still, in the file /src/temperature_measurement.rs, the into_query_value method does the opposite; it converts our structure into values which can be read by the ScyllaDB server:

In the file /src/db.rs, we define the insert query. ScyllaDB will use each value as a replacement for ?:

query_with_values allows us to use query string templates with ? as a placeholder for dynamic values. The values themselves are provided as a second argument.

Reading Measurements

Now we can create the select-query logic in the /src/db.rs module:

The important steps are:

  • Make a select query with the specified parameters (device ID, start and end date);
  • Read the response and convert it into rows
  • Once the rows are obtained, convert each row via the previously generated method TemperatureMeasurement::try_from_row(row).

To recap, so far, we created two important modules:

  • The db module (./src/db.rs) which is responsible for providing DB-related helpers;
  • The temperature_measurement module (./src/temperature_measurement.rs) which contains a model of temperature measurement.

Now, it’s time to create the main function which will connect to ScyllaDB, add a couple of measurements to it, and read them back (defined in /src/main.rs):

The next step would be to run the example. You can check out the full lesson here, as well as other NoSQL and ScyllaDB related courses on ScyllaDB University. If you haven’t done so yet, register as a user and get started. It’s free!

About Guy Shtub

Head of Training: Guy is experienced in creating products that people love. Previously he co-founded two start-ups. Outside of the office, you can find him climbing, juggling and generally getting off the beaten path. Guy holds a B.SC. degree in Software Engineering from Ben Gurion University.

About Alex (Oleksandr) Pikalov

Alex is a Rust enthusiast and author of CDRS, an open-source Rust ScyllaDB and Cassandra driver. Alex is a principal Javascript engineer and he holds an M.SC. degree in Physics.

Virtual Workshop

Build Low-Latency Applications in Rust on ScyllaDB