No description
Find a file
despiegk 36e0a393ec
All checks were successful
Build / build (darwin-amd64, true, x86_64-apple-darwin, true) (push) Successful in 1m46s
Build / build (darwin-arm64, true, aarch64-apple-darwin, true) (push) Successful in 1m48s
Build / build (linux-amd64, false, x86_64-unknown-linux-gnu) (push) Successful in 1m51s
Build / build (linux-arm64, true, aarch64-linux-gnu-gcc, aarch64-unknown-linux-gnu) (push) Successful in 2m1s
redis is working
2025-12-29 11:33:38 +01:00
.forgejo/workflows Hero Redis: optimized Redis server on redb 2025-12-25 10:08:48 +01:00
docs redis is working 2025-12-29 11:33:38 +01:00
rhai_examples basic redis server working 2025-12-28 16:51:23 +01:00
scripts Hero Redis: optimized Redis server on redb 2025-12-25 10:08:48 +01:00
specs basic redis server working 2025-12-28 16:51:23 +01:00
src redis is working 2025-12-29 11:33:38 +01:00
.gitignore Hero Redis: optimized Redis server on redb 2025-12-25 10:08:48 +01:00
build.sh basic redis server working 2025-12-28 16:51:23 +01:00
Cargo.lock redis refactor 2025-12-28 12:52:25 +01:00
Cargo.toml basic redis server working 2025-12-28 16:51:23 +01:00
COMPLIANCE_REPORT.md basic redis server working 2025-12-28 16:51:23 +01:00
install.sh fixing & docs 2025-12-28 07:56:42 +01:00
instructions_client.md redis refactor 2025-12-28 12:52:25 +01:00
instructions_unit_accounting.md redis refactor 2025-12-28 12:52:25 +01:00
LICENSE Hero Redis: optimized Redis server on redb 2025-12-25 10:08:48 +01:00
README.md redis refactor 2025-12-28 12:52:25 +01:00
run.sh fixing & docs 2025-12-28 07:56:42 +01:00

Hero Redis

A high-performance, Redis-compatible server built on redb with ChaCha20-Poly1305 encryption and Ed25519 signature-based authentication.

Features

  • Redis Protocol Compatible - Works with any Redis client
  • Ed25519 Authentication - Cryptographic signature-based login (no passwords)
  • Multi-Database with ACL - Per-database Read/Write/Admin permissions
  • Persistent Storage - Data stored in redb (pure Rust embedded database)
  • Encryption - All values encrypted with ChaCha20-Poly1305
  • Multiple Databases - Up to 1000 databases with lazy loading
  • Low Memory - ~3MB at startup, databases loaded on demand
  • Auto-cleanup - Idle databases automatically closed after 5 minutes
  • Unix Socket & TCP - Both connection methods supported
  • Cross-platform - Linux (x86_64, aarch64) and macOS (x86_64, aarch64)

Quick Start

Build from Source

git clone https://github.com/herocode/hero_redis.git
cd hero_redis
cargo build --release

Generate Admin Keypair

# Generate a new Ed25519 keypair
./target/release/hero_redis_login --generate

# Output:
# PUBLIC_KEY=a1b2c3d4...  (64 hex chars)
# PRIVATE_KEY=e5f6a7b8... (64 hex chars)

Start Server

# Start with admin public key (required)
./target/release/hero_redis \
  --encryption-key "your-encryption-key" \
  --admin-pubkey "a1b2c3d4..." \
  --data-dir ~/.hero_redis \
  --port 6379

Authenticate and Use

# Get a session token
./target/release/hero_redis_login \
  --private-key "e5f6a7b8..." \
  --port 6379

# Use the token with redis-cli
redis-cli -p 6379
> AUTH <token>
OK
> SET mykey myvalue
OK

Testing

Run the comprehensive test suite to validate the authentication and ACL system:

# Build and run tests (starts server automatically)
cargo run --release --bin hero_redis_tester

The tester:

  • Starts a Hero Redis server on port 16379
  • Tests CHALLENGE/TOKEN/AUTH authentication flow
  • Tests DATABASE.CREATE and user management
  • Tests Read/Write/Admin permission enforcement
  • Tests database isolation between users
  • Cleans up automatically when done

Sample output:

╔════════════════════════════════════════════════════════════════╗
║       Hero Redis Comprehensive Auth & ACL Tester               ║
╚════════════════════════════════════════════════════════════════╝

┌────────────────────────────────────────────────────────────────┐
│ Basic Connectivity                                             │
└────────────────────────────────────────────────────────────────┘
  ✓ PING without auth
  ✓ GET without auth rejected

┌────────────────────────────────────────────────────────────────┐
│ Admin Authentication Flow                                      │
└────────────────────────────────────────────────────────────────┘
  ✓ CHALLENGE returns 64 hex chars
  ✓ TOKEN returns token
  ✓ AUTH with token
  ...

╔════════════════════════════════════════════════════════════════╗
║                         Test Summary                           ║
╠════════════════════════════════════════════════════════════════╣
║  Passed: 60                                                    ║
║  Failed: 0                                                     ║
║  Total:  60                                                    ║
╚════════════════════════════════════════════════════════════════╝

🎉 All tests passed!

Authentication Flow

Hero Redis uses Ed25519 signature-based authentication:

Client                              Server
  |                                   |
  |-------- CHALLENGE --------------->|
  |<------- <random_challenge> -------|
  |                                   |
  |-- TOKEN <pubkey> <signature> ---->|
  |<------- <session_token> ----------|
  |                                   |
  |-------- AUTH <token> ------------>|
  |<------- OK -----------------------|
  1. CHALLENGE - Request a random challenge (64 hex chars)
  2. TOKEN - Sign the challenge with your private key, submit with public key
  3. AUTH - Use the returned session token to authenticate

Command Line Options

Server (hero_redis)

Option Default Description
-d, --data-dir ~/.hero_redis Database directory
-s, --socket ~/.hero_redis/redis.sock Unix socket path
-p, --port 6379 TCP port (0 to disable)
--encryption-key required Encryption key for DB 0
--admin-pubkey required Admin public key (can specify multiple)
-v, --verbose false Enable debug logging

Login Tool (hero_redis_login)

Option Description
-k, --private-key Ed25519 private key (64 hex chars)
--private-key-file Path to private key file
-p, --port Server port (default: 6379)
-h, --host Server host (default: 127.0.0.1)
-l, --login Perform full AUTH after getting token
-d, --db Select database after login
--generate Generate new keypair
--format Output format: token, json, verbose

Permission Levels

Level Can Read Can Write Can FLUSHDB Can USER.GRANT Can DATABASE.CREATE
read
write
admin ✓ (same db)
server admin

Admin Commands

Server Admin Commands (require server admin)

Command Description
ADMIN.ADD <pubkey> Add server admin
ADMIN.REMOVE <pubkey> Remove server admin
ADMIN.LIST List server admins
DATABASE.CREATE <encryption_key> Create new database
DATABASE.STATUS [db|all] Show database info
USER.CREATE <pubkey> Register a user
USER.DELETE <pubkey> Delete a user

Database Admin Commands

Command Description
USER.GRANT <db> <pubkey> <read|write|admin> Grant permission
USER.REVOKE <db> <pubkey> Revoke permission
FLUSHDB Clear current database

Supported Redis Commands

String Commands

GET, SET, MGET, MSET, DEL, EXISTS, EXPIRE, TTL, KEYS, INCR, INCRBY, DECR, DECRBY, APPEND, STRLEN, GETRANGE, SETNX, SETEX, GETSET, TYPE

Hash Commands

HSET, HGET, HMSET, HMGET, HGETALL, HDEL, HEXISTS, HLEN, HKEYS, HVALS, HINCRBY, HSETNX

List Commands

LPUSH, RPUSH, LPOP, RPOP, LRANGE, LLEN, LINDEX, LSET, LREM

Set Commands

SADD, SREM, SMEMBERS, SISMEMBER, SCARD, SPOP, SUNION, SINTER, SDIFF

Stream Commands

XADD, XLEN, XRANGE, XREVRANGE, XREAD, XINFO, XTRIM, XGROUP, XREADGROUP, XACK, XPENDING

Connection Commands

PING, AUTH, SELECT, QUIT, COMMAND

Management Commands

COMPACT, SHUTDOWN, MEMORY USAGE, MEMORY STATS, DBSIZE, FLUSHDB, INFO

Using as a Library

Quick Start

use hero_redis::hero_redis_client::HeroRedisClient;

// Connect with your private key (simplest way)
let mut client = HeroRedisClient::new("127.0.0.1", 6379, "your_private_key_hex")?;
client.select(1)?;

// String operations
client.set("name", "Alice")?;
let name = client.get("name")?.unwrap();

// With expiration (seconds)
client.set_ex("session", "token123", 3600)?;

// Counters
let views = client.incr("page:views")?;
client.incr_by("page:views", 10)?;

// Hashes (like objects/dictionaries)
client.hset("user:1", "name", "Bob")?;
client.hset("user:1", "email", "bob@example.com")?;
let user = client.hgetall("user:1")?;
let email = client.hget("user:1", "email")?;

// Lists (queues)
client.rpush("queue", "job1")?;
client.rpush("queue", "job2")?;
while let Some(job) = client.lpop("queue")? {
    println!("Processing: {}", job);
}

// Sets (unique collections)
client.sadd("tags", "rust")?;
client.sadd("tags", "redis")?;
let is_member = client.sismember("tags", "rust")?;
let all_tags = client.smembers("tags")?;

// Batch operations
client.mset(&[("a", "1"), ("b", "2"), ("c", "3")])?;
let values = client.mget(&["a", "b", "c"])?;

// Streams
let id = client.xadd("events", &[("type", "login"), ("user", "alice")])?;
let entries = client.xrange("events", "-", "+")?;

Admin Operations

use hero_redis::hero_redis_client::{HeroRedisClient, Permission};

let mut client = HeroRedisClient::new("127.0.0.1", 6379, "admin_private_key")?;

// Create a new database
let db = client.admin().create_database("db_encryption_key")?;

// Create user and grant permissions
client.admin().create_user(&user_pubkey)?;
client.admin().grant_permission(db, &user_pubkey, Permission::Write)?;

// List admins
let admins = client.admin().list_admins()?;

// Server info
let info = client.admin().info()?;
println!("Version: {:?}", info.version);

Builder Pattern

use hero_redis::hero_redis_client::HeroRedisClient;

let mut client = HeroRedisClient::builder()
    .host("127.0.0.1")
    .port(6379)
    .private_key("your_private_key_hex")?
    .database(1)  // Auto-select database after connect
    .connect()?;

Raw Commands

// Execute any Redis command
let result: String = client.cmd(&["INFO", "server"])?;
let count: i64 = client.cmd_int(&["DBSIZE"])?;
let keys: Vec<String> = client.cmd_vec(&["KEYS", "*"])?;

Architecture

hero_redis/
├── src/
│   ├── main.rs                    # Server CLI entry point
│   ├── lib.rs                     # Library exports
│   ├── hero_redis_server/
│   │   ├── mod.rs                 # Module exports
│   │   ├── server.rs              # TCP/Unix server + auth
│   │   ├── auth.rs                # Ed25519 authentication
│   │   ├── backend.rs             # redb storage engine
│   │   ├── encrypted_backend.rs   # Encryption wrapper
│   │   ├── crypto.rs              # ChaCha20-Poly1305
│   │   └── protocol.rs            # RESP v2 parser
│   ├── hero_redis_client/
│   │   ├── mod.rs                 # Client module exports
│   │   ├── client.rs              # Main client implementation
│   │   ├── admin.rs               # Admin operations
│   │   ├── builder.rs             # Builder pattern
│   │   ├── commands.rs            # Command options & types
│   │   └── error.rs               # Error types
│   ├── hero_redis_login/
│   │   └── mod.rs                 # Low-level login client
│   ├── bin/
│   │   └── hero_login.rs          # Login CLI (hero_redis_login)
│   └── hero_redis_tester/
│       └── main.rs                # Comprehensive test suite
├── specs/
│   ├── hero_redis_server_multi_db.md  # Multi-DB auth spec
│   └── hero_login.md                   # Login protocol spec
└── docs/
    └── *.md                       # Documentation

Data Storage

  • Data directory: ~/.hero_redis/ (configurable)
  • Database files: db0.redb, db1.redb, ... db999.redb
  • DB 0 is reserved for admin metadata (admin registry, user permissions)
  • Each database has its own encryption key
  • Values are encrypted with ChaCha20-Poly1305 before storage

License

Apache 2.0