TerraScale.CqlDriver 1.0.0

TerraScale.CqlDriver

High-performance CQL driver for ScyllaDB/Cassandra with AOT support.

Features

  • Custom CQL binary protocol v4 implementation
  • Connection pooling with stream multiplexing
  • Prepared statement caching
  • Full type codec support (primitives + collections)
  • PLAIN SASL authentication
  • TLS/SSL support
  • System.Text.Json serialization (AOT-compatible)
  • FluentResults error handling

Installation

dotnet add package TerraScale.CqlDriver

Quick Start

using TerraScale.CqlDriver;
using TerraScale.CqlDriver.Client;
using TerraScale.CqlDriver.Configuration;

// Create client
var options = new CqlClientOptions
{
    ContactPoints = ["localhost"],
    Port = 9042,
    Keyspace = "my_keyspace",
    Authentication = new AuthenticationOptions
    {
        Username = "cassandra",
        Password = "cassandra"
    }
};

await using var client = new CqlClient(options);

// Execute a query
var result = await client.ExecuteAsync("SELECT * FROM users WHERE id = ?", [userId]);
if (result.IsSuccess)
{
    foreach (var row in result.Value)
    {
        Console.WriteLine($"User: {row.GetString("name")}");
    }
}

// Prepare and execute
var prepared = await client.PrepareAsync("INSERT INTO users (id, name) VALUES (?, ?)");
if (prepared.IsSuccess)
{
    var bound = prepared.Value.Bind(Guid.NewGuid(), "Alice");
    await client.ExecuteAsync(bound);
}

// Batch operations
var batch = new BatchBuilder()
    .Add("INSERT INTO users (id, name) VALUES (?, ?)", Guid.NewGuid(), "Bob")
    .Add("INSERT INTO users (id, name) VALUES (?, ?)", Guid.NewGuid(), "Charlie");

await client.ExecuteBatchAsync(batch);

Dependency Injection

// Program.cs
builder.Services.AddCqlClient(new CqlClientOptions
{
    ContactPoints = ["scylla-node1", "scylla-node2"],
    Port = 9042,
    Keyspace = "my_keyspace",
    DefaultConsistency = ConsistencyLevel.LocalQuorum
});

// Usage
public class UserService(ICqlClient cqlClient)
{
    public async Task<User?> GetUserAsync(Guid id)
    {
        var result = await cqlClient.ExecuteAsync(
            "SELECT * FROM users WHERE id = ?", [id]);

        if (result.IsFailed || result.Value.Count == 0)
            return null;

        var row = result.Value[0];
        return new User
        {
            Id = row.GetGuid("id"),
            Name = row.GetString("name")!
        };
    }
}

Configuration Options

Option Type Default Description
ContactPoints string[] Required Cluster contact points
Port int 9042 CQL native protocol port
Keyspace string? null Default keyspace
ProtocolVersion ProtocolVersion V4 Protocol version
DefaultConsistency ConsistencyLevel LocalQuorum Default consistency level
QueryTimeout TimeSpan 12s Query timeout
ConnectionTimeout TimeSpan 5s Connection timeout
MaxRetries int 3 Maximum retry attempts

Pooling Options

Option Type Default Description
MinConnectionsPerHost int 1 Minimum connections per host
MaxConnectionsPerHost int 2 Maximum connections per host
MaxRequestsPerConnection int 1024 Max concurrent requests per connection
HeartbeatInterval TimeSpan 30s Keep-alive interval
IdleTimeout TimeSpan 10m Idle connection timeout

Authentication Options

options.Authentication = new AuthenticationOptions
{
    Username = "cassandra",
    Password = "cassandra"
};

TLS Options

options.Tls = new TlsOptions
{
    ValidateCertificate = true,
    CaCertificatePath = "/path/to/ca.crt",
    ClientCertificatePath = "/path/to/client.crt",
    ClientKeyPath = "/path/to/client.key"
};

Type Mappings

CQL Type C# Type
text, varchar string
int int
bigint, counter long
smallint short
tinyint sbyte
float float
double double
decimal decimal
boolean bool
uuid, timeuuid Guid
timestamp DateTimeOffset
date DateOnly
time TimeOnly
blob byte[]
inet IPAddress
varint BigInteger
list<T> List<T>
set<T> HashSet<T>
map<K,V> Dictionary<K,V>

Consistency Levels

ConsistencyLevel.Any          // Response from any replica
ConsistencyLevel.One          // Response from one replica
ConsistencyLevel.Two          // Response from two replicas
ConsistencyLevel.Three        // Response from three replicas
ConsistencyLevel.Quorum       // Majority of replicas
ConsistencyLevel.All          // All replicas
ConsistencyLevel.LocalQuorum  // Majority in local datacenter (default)
ConsistencyLevel.EachQuorum   // Majority in each datacenter
ConsistencyLevel.LocalOne     // One replica in local datacenter

Error Handling

The driver uses FluentResults for error handling:

var result = await client.ExecuteAsync("SELECT * FROM users");

if (result.IsSuccess)
{
    // Process rows
    foreach (var row in result.Value)
    {
        // ...
    }
}
else
{
    // Handle error
    Console.WriteLine($"Error: {result.Errors[0].Message}");
}

For specific error types, catch the exceptions:

try
{
    await client.ExecuteAsync("INVALID QUERY");
}
catch (SyntaxException ex)
{
    Console.WriteLine($"Syntax error: {ex.Message}");
}
catch (UnavailableException ex)
{
    Console.WriteLine($"Not enough replicas: {ex.Required} required, {ex.Alive} alive");
}
catch (ReadTimeoutException ex)
{
    Console.WriteLine($"Read timeout: {ex.Received}/{ex.BlockFor} responses");
}

No packages depend on TerraScale.CqlDriver.

Version Downloads Last updated
1.0.0 0 01/08/2026