Skip to content

Latest commit

 

History

5 Commits

Folders and files

NameName
Last commit message
Last commit date
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 

Repository files navigation

Project Ouroboros (RustNexCore)

Ultra-High Throughput, Self-Contained Rust HTTP Engine with Built-in Real-Time Telemetry & Load Generator

Rust 2021 Axum 0.8 Tokio PostgreSQL 5.85M RPS 4.55 MB 19 Passed


📑 Table of Contents

  1. Executive Summary & Core Philosophy
  2. Technology Stack & Architectural Rationale
  3. System Architecture & Visual Diagrams
  4. Exhaustive API Reference & Usage Guide
  5. Local Setup & Getting Started (Step-by-Step)
  6. Benchmarking & Stress Testing Guide
  7. Verification, Quality Gates & Acceptance Matrix
  8. Render.com Deployment Guide (Free Tier)
  9. Performance Expectations: Local vs Render Free Tier
  10. Strict Repository Constraints

1. Executive Summary & Core Philosophy

Project Ouroboros is an enterprise-grade, bare-metal optimized HTTP service engineered in Rust. It delivers sustained low-latency request handling, real-time observability, and automated database persistence without requiring external monitoring sidecars, caches, or reverse proxies.

Core Tenets

  • Zero-Allocation Hot Path: /api/v1/ping returns static compile-time byte buffers with relaxed atomic counter increments, achieving >5.8 Million RPS in Direct Mode.
  • Single Self-Contained Binary: Builds to a compact 4.55 MB executable containing the HTTP server, SQL migrations, background metric aggregator, web dashboard, and load generator.
  • Zero External Runtime Dependencies: Operates without Docker, Redis, Prometheus, Grafana, or Kubernetes.
  • In-Memory Rolling Window: 60-slot circular ring buffer retaining per-second snapshots broadcasted via WebSockets (/ws/metrics) to an embedded HTML5 dashboard.
  • Resilient Relational Persistence: Asynchronous connection pool (sqlx) managing PostgreSQL with automatic startup schema migrations.

2. Technology Stack & Architectural Rationale

Component Technology Version Purpose & Architectural Justification
Language Rust 2021 Edition (1.78+) Zero-cost abstractions, memory safety without garbage collection pauses, and low-level thread control.
HTTP Engine Axum 0.8.x Modular routing built natively on Tower/Hyper; ergonomic state extraction with sub-router isolation.
Async Runtime Tokio 1.x (Multi-Thread) Work-stealing async scheduler utilizing all available physical CPU cores for non-blocking I/O.
HTTP Core Hyper / Tower 1.x / 0.5.x High-throughput asynchronous HTTP protocol implementation with composable middleware services.
Database Engine PostgreSQL & SQLx 16+ / 0.8.x Pure async, compile-time verified SQL queries with built-in connection pooling and automated migrations.
Concurrency Primitives std::sync::atomic & parking_lot 0.12.x AtomicU64/AtomicBool with Ordering::Relaxed for lock-free counters; non-poisoning RwLock for ring buffer safety.
Visualization Chart.js 4.4.x (Vendored Offline) Hardware-accelerated canvas charts for live telemetry; zero external CDN dependencies (Constraint C10).
Serialization Serde / serde_json 1.0.x High-speed zero-copy JSON parsing and serialization across all REST endpoints.
Error Handling thiserror / anyhow 1.0.x Strongly typed domain error mapping (AppError) converted to consistent RFC-compliant JSON responses.

3. System Architecture & Visual Diagrams

3.1 End-to-End System Topology

flowchart TB
    subgraph Clients["Traffic Sources"]
        Browser["Web Browser (Dashboard UI)"]
        K6Client["k6 / External Load Generator"]
        CurlClient["CLI / cURL / REST Client"]
    end

    subgraph Binary["Ouroboros Standalone Executable (ouroboros.exe)"]
        subgraph Listener["TCP Socket (0.0.0.0:8080)"]
            TokioListener["Tokio Async TCP Listener"]
        end

        subgraph Middleware["Global Middleware Pipeline"]
            ReqId["RequestId Layer (X-Request-Id UUID v4)"]
            BodyLim["BodyLimit Layer (1 MB Max)"]
            ReqCount["Counter Layer (Atomic Total & Active Conns)"]
        end

        subgraph Routers["Route Dispatcher"]
            HotPath["/api/v1/ping (Hot Path Sub-Router)"]
            StandardPath["Standard Sub-Router (/health, /users, /dashboard, /bench)"]
        end

        subgraph StdMiddleware["Standard Route Middleware"]
            TimeoutLayer["Timeout Layer (408 Fast Fail)"]
            TraceLayer["Tracing / Logging Layer"]
            CorsLayer["Permissive CORS Layer"]
        end

        subgraph CoreEngines["Core Systems & Shared State (AppState)"]
            AtomicCounters["Atomic Counters (ping, total, errors)"]
            RingBuf["60-Slot RingBuffer (parking_lot::RwLock)"]
            BroadcastTx["Metrics Broadcast Channel (tokio::sync::broadcast)"]
            BenchEng["Built-in BenchEngine (Direct & Loopback)"]
            PgPool["SQLx Connection Pool (max_connections: 100)"]
        end

        subgraph BackgroundTasks["Async Background Tasks"]
            TickReporter["1-Second Metrics Reporter Task"]
        end
    end

    subgraph Storage["External Storage"]
        Postgres[("PostgreSQL 16 Database (ouroboros)")]
    end

    Clients --> TokioListener
    TokioListener --> ReqId
    ReqId --> BodyLim
    BodyLim --> ReqCount
    ReqCount --> Routers

    Routers -->|Hot Path Bypass| HotPath
    Routers -->|Standard Routes| StdMiddleware
    StdMiddleware --> StandardPath

    HotPath -->|Relaxed Atomic Incr| AtomicCounters
    StandardPath --> CoreEngines
    BackgroundTasks -->|Reads Every 1s| AtomicCounters
    BackgroundTasks -->|Pushes Snapshot| RingBuf
    BackgroundTasks -->|Broadcasts Snapshot| BroadcastTx
    BroadcastTx -.->|Streaming WS| Browser
    CoreEngines -->|Async Pool| Storage
Loading

3.2 Hot-Path vs Standard Request Pipeline

A fundamental design requirement of Ouroboros is the architectural isolation between the hot-path (/api/v1/ping) and standard business endpoints:

sequenceDiagram
    autonumber
    actor Client as HTTP Client
    participant Router as Axum Dispatcher
    participant HotPath as /api/v1/ping Handler
    participant StdRouter as Standard Router (/health, /users)
    participant Middleware as Tracing, Timeout & CORS
    participant Counters as Atomic Counters
    participant DB as PostgreSQL 16

    rect rgb(6, 182, 212, 0.1)
        Note over Client,Counters: HOT PATH EXECUTION (Sub-microsecond latency)
        Client->>Router: GET /api/v1/ping
        Router->>HotPath: Direct Routing (Bypasses Tracing & DB)
        HotPath->>Counters: ping.fetch_add(1, Relaxed)
        HotPath-->>Client: 200 OK (Static b"{\"success\":true,\"message\":\"pong\"}")
    end

    rect rgb(16, 185, 129, 0.1)
        Note over Client,DB: STANDARD PATH EXECUTION (Full Middleware & DB)
        Client->>Router: POST /api/v1/users
        Router->>StdRouter: Route Match
        StdRouter->>Middleware: Execute Timeout, TraceLayer & CORS
        Middleware->>DB: INSERT INTO users ... RETURNING *
        DB-->>Middleware: User Row
        Middleware-->>Client: 201 Created (JSON Body + X-Request-Id)
    end
Loading

3.3 In-Memory Metrics Engine & WebSocket Dataflow

flowchart LR
    subgraph Traffic["Incoming Traffic"]
        Requests["HTTP Requests"]
    end

    subgraph State["AppState"]
        Counters["Atomic Counters: ping, total, errors"]
        RingBuffer["RingBuffer<MetricSnapshot, 60>"]
        Channel["broadcast::Sender<MetricSnapshot>"]
    end

    subgraph Background["1-Second Background Reporter"]
        Timer["tokio::time::interval(1s)"]
        Compute["Compute RPS = count.swap(0, Relaxed)"]
    end

    subgraph Consumers["Subscribers & Outputs"]
        Terminal["Stdout Logger (RPS window rps=... total_rps=...)"]
        WsClients["WebSocket Clients (/ws/metrics)"]
        RestMetrics["REST API (/api/v1/metrics)"]
    end

    Requests -->|Increment| Counters
    Timer --> Compute
    Compute -->|Swap & Read| Counters
    Compute -->|Store Snapshot| RingBuffer
    Compute -->|Send Snapshot| Channel
    Compute -->|Structured Log| Terminal
    Channel -->|Push 1s Frame| WsClients
    RingBuffer -->|Sliding History| RestMetrics
Loading

3.4 Database Schema (Entity-Relationship)

erDiagram
    users {
        uuid id PK "DEFAULT gen_random_uuid()"
        varchar_255 name "NOT NULL"
        varchar_255 email UK "NOT NULL, UNIQUE"
        timestamptz created_at "NOT NULL, DEFAULT NOW()"
        timestamptz updated_at "NOT NULL, DEFAULT NOW()"
    }

    request_logs {
        bigserial id PK
        varchar_100 endpoint "NOT NULL"
        smallint status_code "NOT NULL"
        integer latency_us "NOT NULL"
        timestamptz logged_at "NOT NULL, DEFAULT NOW(), INDEXED"
    }

    bench_sessions {
        uuid id PK "DEFAULT gen_random_uuid()"
        varchar_20 mode "NOT NULL ('direct' | 'loopback')"
        integer concurrency "NOT NULL"
        integer duration_secs "NOT NULL"
        bigint peak_rps
        bigint avg_rps
        float p99_ms
        float error_rate_pct
        timestamptz started_at "NOT NULL, INDEXED"
        timestamptz ended_at
    }
Loading

4. Exhaustive API Reference & Usage Guide

4.1 System & Hot-Path Endpoints

GET /health

Liveness check returning service status and system uptime.

  • Authentication: None
  • Latency SLA: < 5ms
  • Sample Request (cURL):
    curl -i http://localhost:8080/health
  • Sample Request (PowerShell):
    Invoke-RestMethod -Uri http://localhost:8080/health
  • Sample Response (HTTP 200 OK):
    {
      "status": "ok",
      "uptime_secs": 142
    }

GET /api/v1/ping [HOT PATH]

Ultra-optimized ping target for raw throughput benchmarking. Zero heap allocations, zero serde overhead, static bytes returned directly.

  • Headers Returned: content-type: application/json, x-request-id: <uuid>
  • Sample Request:
    curl -i http://localhost:8080/api/v1/ping
  • Sample Response (HTTP 200 OK):
    {"success":true,"message":"pong"}

4.2 Observability & Telemetry Endpoints

GET /api/v1/metrics

Retrieves sliding 60-second in-memory metric snapshots.

  • Sample Request:
    curl -s http://localhost:8080/api/v1/metrics
  • Sample Response (HTTP 200 OK):
    [
      {
        "timestamp_secs": 1726744360,
        "ping_rps": 3510468,
        "total_rps": 3510468,
        "error_rate_pct": 0.0,
        "active_conns": 0
      }
    ]

GET /dashboard

Serves the self-contained Executive Observatory HTML5/CSS telemetry dashboard.

  • Browser URL (Local): http://localhost:8080/dashboard
  • Browser URL (Render Cloud): https://<your-app>.onrender.com/dashboard
  • Executive UI/UX Features:
    • Obsidian Glassmorphic Aesthetic: Dark obsidian space theme (#07090e) with multi-layer backdrop-filter blur, subtle neon glows (Cyan, Violet, Emerald), and smooth 3D elevation hover cards.
    • Custom Handcrafted SVG Icons: Self-contained vector icons with glowing badges for Hot-Path Ping, Total System RPS, Error Rate %, Active TCP Sockets, and Target Status.
    • Live Latency Probe Tool: Real-time client-to-cloud round-trip latency probe (⚡ Run Ping) displaying measured ping latency in milliseconds.
    • 1-Click Load Presets: Instant configuration chips (⚡ Quick Direct (100), 🔥 Extreme Direct (1k), 🌐 HTTP Loopback (50)).
    • Quick-Copy API Operations Hub: Interactive endpoints reference with 1-click clipboard copy feedback.
  • Assets Bundled (Compile-Time Embedded):
    • /dashboard/assets/chart.min.js (Vendored Chart.js library)
    • /dashboard/assets/dashboard.js (WebSocket listener, telemetry charts & benchmark manager)

GET /ws/metrics (WebSocket)

Full-duplex WebSocket connection streaming real-time JSON snapshots every 1 second.

  • Protocol: ws:// (or wss:// behind TLS — auto-detected by the dashboard)
  • Sample Inbound Message Frame:
    {
      "timestamp_secs": 1726744362,
      "ping_rps": 4239620,
      "total_rps": 4239621,
      "error_rate_pct": 0.0,
      "active_conns": 1
    }

4.3 Internal Benchmark Engine

POST /internal/bench/start

Triggers an automated in-process load test run.

  • Request Body Parameters:
    • mode (string, optional): "direct" (memory-level) or "loopback" (TCP HTTP stack). Default: "loopback".
    • concurrency (integer, optional): Number of parallel worker tasks (1 to 10000). Default: 100.
    • duration_secs (integer, optional): Duration in seconds (5 to 3600). Default: 30.
    • target_endpoint (string, optional): Target path. Default: "/api/v1/ping".
  • Sample Request (PowerShell):
    Invoke-RestMethod -Uri http://localhost:8080/internal/bench/start `
      -Method Post `
      -ContentType "application/json" `
      -Body '{"mode":"direct","concurrency":50,"duration_secs":10}'
  • Sample Request (cURL — Remote / Render):
    curl -X POST https://your-app.onrender.com/internal/bench/start \
      -H "Content-Type: application/json" \
      -d '{"mode":"direct","concurrency":50,"duration_secs":10}'
  • Sample Response (HTTP 200 OK):
    {
      "bench_id": "2c885c95-25ff-4cd6-b1ce-32856468c42d",
      "started": true
    }

GET /internal/bench/status

Fetches real-time telemetry of the active or most recently completed benchmark session.

  • Sample Request:
    Invoke-RestMethod -Uri http://localhost:8080/internal/bench/status
  • Sample Response (HTTP 200 OK):
    {
      "running": false,
      "mode": "direct",
      "concurrency": 50,
      "elapsed_secs": 12,
      "requests_sent": 42125617,
      "requests_success": 42125617,
      "requests_failed": 0,
      "current_rps": 0,
      "peak_rps": 3510468,
      "p50_ms": 0.0,
      "p95_ms": 0.0,
      "p99_ms": 0.0,
      "target_rps": 1000000,
      "target_reached": true
    }

POST /internal/bench/stop

Immediately aborts an active benchmark run.

  • Sample Request:
    Invoke-RestMethod -Uri http://localhost:8080/internal/bench/stop -Method Post
  • Sample Response (HTTP 200 OK):
    {
      "stopped": true
    }

4.4 Users Resource CRUD API

All user management endpoints interface directly with PostgreSQL via SQLx connection pooling.

1. Create User (POST /api/v1/users)

  • Body: name (string, required), email (string, required, unique, valid email format).
  • Sample Request (PowerShell):
    Invoke-RestMethod -Uri http://localhost:8080/api/v1/users `
      -Method Post `
      -ContentType "application/json" `
      -Body '{"name":"Aman Verma","email":"aman@example.com"}'
  • Sample Request (cURL — Remote / Render):
    curl -X POST https://your-app.onrender.com/api/v1/users \
      -H "Content-Type: application/json" \
      -d '{"name":"Aman Verma","email":"aman@example.com"}'
  • Sample Response (HTTP 201 Created):
    {
      "id": "541d7165-c4dd-4b7f-b88f-7e3895c97b0e",
      "name": "Aman Verma",
      "email": "aman@example.com",
      "created_at": "2026-09-19T11:02:26.260465Z",
      "updated_at": "2026-09-19T11:02:26.260465Z"
    }

2. List & Search Users (GET /api/v1/users)

  • Query Parameters:
    • page (optional, integer, default: 1): Page number for pagination.
    • page_size (optional, integer, default: 20, max: 100): Items per page.
    • email (optional, string): Filter users matching specific email (case-insensitive substring or exact match).
    • name (optional, string): Filter users matching specific name (case-insensitive substring match).
    • search (optional, string): Universal search query matching across both name AND email.
  • Sample Request (Pagination):
    Invoke-RestMethod -Uri "https://<your-app>.onrender.com/api/v1/users?page=1&page_size=10"
  • Sample Request (Find by Email):
    Invoke-RestMethod -Uri "https://<your-app>.onrender.com/api/v1/users?email=abhishek@example.com"
  • Sample Request (Find by Name):
    Invoke-RestMethod -Uri "https://<your-app>.onrender.com/api/v1/users?name=Abhishek"
  • Sample Request (Universal Search across Name & Email):
    Invoke-RestMethod -Uri "https://<your-app>.onrender.com/api/v1/users?search=Abhi"
  • Sample Response (HTTP 200 OK):
    {
      "users": [
        {
          "id": "30fc4bfe-cea1-48d3-9050-87192eca6441",
          "name": "Abhishek",
          "email": "abhishek@example.com",
          "created_at": "2026-09-19T12:51:18.360292Z",
          "updated_at": "2026-09-19T12:51:18.360292Z"
        }
      ],
      "page": 1,
      "page_size": 10,
      "total": 1
    }

3. Get User By ID (GET /api/v1/users/{id})

  • Sample Request:
    Invoke-RestMethod -Uri http://localhost:8080/api/v1/users/541d7165-c4dd-4b7f-b88f-7e3895c97b0e
  • Response: HTTP 200 with User JSON or HTTP 404 Not Found.

4. Update User (PUT /api/v1/users/{id})

  • Sample Request:
    Invoke-RestMethod -Uri http://localhost:8080/api/v1/users/541d7165-c4dd-4b7f-b88f-7e3895c97b0e `
      -Method Put `
      -ContentType "application/json" `
      -Body '{"name":"Aman V. Sharma"}'
  • Sample Response (HTTP 200 OK):
    {
      "id": "541d7165-c4dd-4b7f-b88f-7e3895c97b0e",
      "name": "Aman V. Sharma",
      "email": "aman@example.com",
      "created_at": "2026-09-19T11:02:26.260465Z",
      "updated_at": "2026-09-19T11:15:30.104291Z"
    }

5. Delete User (DELETE /api/v1/users/{id})

  • Sample Request:
    Invoke-WebRequest -Uri http://localhost:8080/api/v1/users/541d7165-c4dd-4b7f-b88f-7e3895c97b0e -Method Delete
  • Sample Response: HTTP/1.1 204 No Content (Subsequent lookup returns HTTP 404).

4.5 Universal Error Response Format

All error conditions across the system converge on a single, predictable structure defined in AppError:

{
  "error": "conflict: email already exists",
  "code": "CONFLICT"
}
HTTP Status Code Meaning
400 Bad Request VALIDATION_ERROR Malformed UUID or query parameter format.
404 Not Found NOT_FOUND Target entity does not exist.
408 Request Timeout REQUEST_TIMEOUT Request exceeded REQUEST_TIMEOUT_SECS limit.
409 Conflict CONFLICT Unique key violation (e.g. email collision).
413 Payload Too Large PAYLOAD_TOO_LARGE Body exceeded BODY_LIMIT_BYTES (1MB).
422 Unprocessable VALIDATION_ERROR Empty name, malformed email, or invalid bench bounds.
500 Internal Server INTERNAL_ERROR Unhandled database or pool connectivity failure.

5. Local Setup & Getting Started (Step-by-Step)

Prerequisites

  1. Rust Stable Toolchain (1.78+): Install rustup
  2. PostgreSQL Server (16+): Running on port 5432

Step 1: Clone & Configure Environment

# Clone the repository
git clone https://github.com/YOUR_USERNAME/RustNexCore.git
cd RustNexCore

# Copy template environment file
copy .env.example .env

Edit your .env to match your local PostgreSQL credentials:

DATABASE_URL=postgresql://ouroboros_user:yourpassword@localhost:5432/ouroboros
PORT=8080
RUST_LOG=ouroboros=info,tower_http=warn
MAX_DB_CONNECTIONS=100
BENCH_MAX_CONCURRENCY=2000
LOG_LEVEL=info

Step 2: Database Initialization (psql / pgAdmin)

In PostgreSQL, create the dedicated role and database:

-- Connect to PostgreSQL as superuser (postgres)
CREATE DATABASE ouroboros;
CREATE USER ouroboros_user WITH PASSWORD 'yourpassword';
GRANT ALL PRIVILEGES ON DATABASE ouroboros TO ouroboros_user;

-- Connect to the ouroboros database and grant schema permissions
\c ouroboros
GRANT ALL ON SCHEMA public TO ouroboros_user;

Note: Tables are created automatically by SQLx migrations on first startup — no manual schema creation needed.


Step 3: Build & Launch Ouroboros

# Build fully-optimized release binary
cargo build --release

# Run the server binary
.\target\release\ouroboros.exe

Console Output:

INFO ouroboros: Starting Ouroboros API v0.1.0
INFO ouroboros: Database connection pool established
INFO ouroboros: Database migrations applied successfully
INFO ouroboros: Metrics reporter started (1s tick)
INFO ouroboros: Listening on 0.0.0.0:8080

Step 4: Quick Smoke Test

# Health check
Invoke-RestMethod -Uri http://localhost:8080/health

# Ping hot-path
Invoke-RestMethod -Uri http://localhost:8080/api/v1/ping

# Create a test user
Invoke-RestMethod -Uri http://localhost:8080/api/v1/users `
  -Method Post -ContentType "application/json" `
  -Body '{"name":"Test User","email":"test@example.com"}'

# List users
Invoke-RestMethod -Uri http://localhost:8080/api/v1/users

Step 5: Open Observatory Dashboard

Visit in your web browser: 👉 http://localhost:8080/dashboard

Or launch directly from PowerShell:

Start-Process http://localhost:8080/dashboard

6. Benchmarking & Stress Testing Guide

6.1 Built-in Benchmark Engine (Browser Dashboard)

  1. Navigate to http://localhost:8080/dashboard.
  2. Scroll to the Built-in Benchmark Engine panel.
  3. Select Mode:
    • Direct (Memory-level hot path): In-memory hot path test bypassing OS network socket overhead. Demonstrates true engine throughput (3,000,000 to 5,850,000+ RPS).
    • Loopback (TCP HTTP stack): Spawns concurrent HTTP client workers communicating over 127.0.0.1:8080.
  4. Set Concurrency (e.g. 50 or 100) and Duration (e.g. 10 seconds).
  5. Click Start Bench and watch real-time RPS graphs update live.

6.2 External Load Testing (k6, oha, bombardier)

Ouroboros includes pre-configured k6 scripts in the k6-scripts/ directory:

Using k6:

# 1. Quick sanity check (10 Virtual Users, 10s)
k6 run k6-scripts/smoke.js

# 2. Stage-based ramp-up test (up to 10,000 VUs)
k6 run k6-scripts/ramp.js

# 3. Peak load test (5,000 VUs, 120s sustained)
k6 run k6-scripts/peak.js

Using oha (Rust HTTP Load Generator):

# Install oha
cargo install oha

# Stress test /api/v1/ping for 10 seconds with 200 concurrent connections
oha -z 10s -c 200 http://127.0.0.1:8080/api/v1/ping

Using Bombardier:

.\bombardier.exe -c 200 -d 10s http://localhost:8080/api/v1/ping

7. Verification, Quality Gates & Acceptance Matrix

Run the automated gate commands before certifying any release:

# 1. Compile release build with LTO and symbol stripping
cargo build --release

# 2. Code formatting verification
cargo fmt -- --check

# 3. Strict compiler linting (0 warnings required)
cargo clippy --all-targets -- -D warnings

# 4. Comprehensive unit & integration testing
cargo test

Complete Acceptance Criteria Traceability Matrix

AC ID Requirement Description Verification Method Status
AC-01 Standalone binary builds in release mode cargo build --release produces standalone executable PASS
AC-02 Binary starts and listens on configured port Binds 0.0.0.0:8080 without manual interventions PASS
AC-03 /health responds with HTTP 200 within 5ms Returns {"status":"ok","uptime_secs":...} PASS
AC-04 /api/v1/ping responds 200 with static body Returns byte-exact pong payload with zero allocations PASS
AC-05 /dashboard serves functional HTML/JS Embedded assets served offline with 200 OK PASS
AC-06 /ws/metrics streams snapshots every second WebSocket channel streams rolling metrics continuously PASS
AC-07 /internal/bench/start starts load test Spawns background worker loop; returns started: true PASS
AC-08 /internal/bench/status reports real-time RPS Reports live throughput, peak RPS, and success count PASS
AC-09 1-second reporter logs RPS window to stdout Background reporter logs rps=... total_rps=... PASS
AC-10 Atomic request counters accuracy Relaxed atomic operations increment without drops PASS
AC-11 Ring buffer retains last 60 seconds Thread-safe circular buffer retains exactly 60 slots PASS
AC-12 cargo test passes all tests 19 unit and integration tests passing green PASS
AC-13 cargo clippy produces 0 warnings Strict gate check passes with -D warnings PASS
AC-14 Database migrations run cleanly 001_init.sql applied automatically to PostgreSQL PASS
AC-15 Users CRUD works against PostgreSQL Complete REST lifecycle (POST, GET, PUT, DELETE) verified PASS
AC-16 Graceful shutdown on Ctrl+C Handlers trap SIGINT/SIGTERM and exit cleanly with code 0 PASS

8. Render.com Deployment Guide (Free Tier)

This section provides complete step-by-step instructions to deploy Project Ouroboros on Render.com Free Tier.

8.1 Prerequisites

Before starting, ensure:

  1. A GitHub account with the RustNexCore repository pushed.
  2. A Render.com account (free signup at render.com).
  3. Your code is committed and pushed to the main branch.
# Push your latest code to GitHub
git add -A
git commit -m "deploy: Render-ready with cloud-tuned pool settings"
git push origin main

8.2 Method A: 1-Click Blueprint Deployment

The repository includes a render.yaml Blueprint file that automatically provisions both the Web Service (Rust binary) and PostgreSQL Database with a single click.

Steps:

  1. Go to https://render.com/deploy.
  2. Paste your GitHub repository URL: https://github.com/YOUR_USERNAME/RustNexCore.
  3. Click Create New Resources.
  4. Render will auto-detect render.yaml and create:
    • ✅ Web Service (ouroboros-api) — Rust native build
    • ✅ PostgreSQL Database (ouroboros-db) — Free tier
  5. The DATABASE_URL environment variable is automatically wired between the database and web service.
  6. Wait for the build to complete (first Rust build takes 10-15 minutes due to compilation).
  7. Once deployed, your app is live at:
    https://ouroboros-api.onrender.com
    

What render.yaml does:

services:
  - type: web
    name: ouroboros-api
    runtime: rust              # Render compiles Rust natively
    buildCommand: cargo build --release
    startCommand: ./target/release/ouroboros
    envVars:
      - key: DATABASE_URL
        fromDatabase:
          name: ouroboros-db   # Auto-injected connection string
          property: connectionString
      - key: PORT
        value: 10000           # Render requires port 10000
      - key: RUST_LOG
        value: ouroboros=info,tower_http=warn
      - key: MAX_DB_CONNECTIONS
        value: 20              # Free tier limit (~20 connections)
      - key: LOG_LEVEL
        value: info

databases:
  - name: ouroboros-db
    databaseName: ouroboros
    user: ouroboros_user
    plan: free                 # Free PostgreSQL instance

8.3 Method B: Manual Dashboard Setup

If you prefer manual control:

Step 1: Create PostgreSQL Database

  1. Go to Render Dashboard → New → PostgreSQL.
  2. Configure:
    • Name: ouroboros-db
    • Database: ouroboros
    • User: ouroboros_user
    • Plan: Free
  3. Click Create Database.
  4. After creation, copy the Internal Database URL from the database info page. It looks like:
    postgresql://ouroboros_user:XXXXXXXX@dpg-XXXXX-a.oregon-postgres.render.com/ouroboros
    

Step 2: Create Web Service

  1. Go to Render Dashboard → New → Web Service.

  2. Connect your GitHub repository (RustNexCore).

  3. Configure:

    • Name: ouroboros-api
    • Runtime: Rust
    • Build Command: cargo build --release
    • Start Command: ./target/release/ouroboros
    • Plan: Free
  4. Add Environment Variables:

    Key Value
    DATABASE_URL (paste Internal Database URL from Step 1)
    PORT 10000
    RUST_LOG ouroboros=info,tower_http=warn
    MAX_DB_CONNECTIONS 20
    LOG_LEVEL info
  5. Click Create Web Service.

  6. Wait for build completion (~10-15 minutes for first build).


8.4 Environment Variables Reference (Render)

Variable Local Default Render Value Notes
DATABASE_URL postgresql://...@localhost/ouroboros Auto-injected by Render Internal connection string; do NOT use External URL
PORT 8080 10000 Render requires services to bind to port 10000
RUST_LOG ouroboros=info,tower_http=warn Same Tracing filter
MAX_DB_CONNECTIONS 100 20 Free tier PostgreSQL allows ~20 connections max
BENCH_MAX_CONCURRENCY 2000 500 (optional) Lower on Free Tier to avoid OOM
LOG_LEVEL info info Application log level

⚠️ IMPORTANT: Render's Free Tier requires PORT=10000. The app reads PORT from environment and binds to it automatically. This is already handled in the code.


8.5 Verify Deployment

After deployment completes, verify all endpoints are operational:

# Replace with your actual Render URL
RENDER_URL="https://ouroboros-api.onrender.com"

# 1. Health Check (may take 30-60s on first hit due to cold start)
curl -i $RENDER_URL/health

# 2. Ping Hot-Path
curl -i $RENDER_URL/api/v1/ping

# 3. Metrics (empty initially)
curl -s $RENDER_URL/api/v1/metrics

# 4. Dashboard (open in browser)
# Visit: https://ouroboros-api.onrender.com/dashboard

# 5. Create a User (verifies PostgreSQL connectivity)
curl -X POST $RENDER_URL/api/v1/users \
  -H "Content-Type: application/json" \
  -d '{"name":"Render Test","email":"render@test.com"}'

# 6. List Users
curl -s $RENDER_URL/api/v1/users

# 7. Run Built-in Benchmark (Direct mode, low concurrency for Free Tier)
curl -X POST $RENDER_URL/internal/bench/start \
  -H "Content-Type: application/json" \
  -d '{"mode":"direct","concurrency":10,"duration_secs":10}'

# 8. Check Benchmark Status
curl -s $RENDER_URL/internal/bench/status

Dashboard Access: Open https://ouroboros-api.onrender.com/dashboard in your browser. The WebSocket connection will auto-upgrade to wss:// over Render's TLS termination.


8.6 Render Free Tier Behaviors & Gotchas

Behavior Details Mitigation Built Into Ouroboros
Cold Start Sleep Free Tier services spin down after 15 minutes of inactivity. First request after sleep takes 30-60 seconds. connect_lazy() in pool.rs defers DB connection until first query, preventing boot-time connection failures. acquire_timeout(15s) gives the DB time to wake up.
Limited RAM (512 MB) Container may OOM-kill if bench concurrency is too high. Keep BENCH_MAX_CONCURRENCY ≤ 500 and benchmark concurrency ≤ 50 on Free Tier.
Shared vCPU CPU is throttled and shared across containers. The engine's hot-path uses zero allocations and atomic operations — minimal CPU overhead per request.
PostgreSQL 1 GB Storage Free tier provides 1 GB storage and 97 days retention. Sufficient for development and portfolio projects.
PostgreSQL ~20 Connections Render Free DB allows limited concurrent connections. MAX_DB_CONNECTIONS=20 in render.yaml. min_connections(1) keeps pool lean.
Build Time (~15 min) Rust's fat LTO release build is CPU-intensive. Subsequent builds use Render's build cache and are faster (~5-8 min).
WebSocket over HTTPS Render terminates TLS at the edge; your app sees plain HTTP. dashboard.js auto-detects https: and uses wss:// accordingly (line 126).

9. Performance Expectations: Local vs Render Free Tier

Key Insight: Ouroboros is engineered for bare-metal throughput. On local hardware it demonstrates millions of RPS. On Render Free Tier, the throughput is constrained by the container's shared CPU/RAM — not by the engine itself.

Metric Local Machine (Bare Metal) Render Free Tier
Direct Mode RPS 3,000,000 – 5,850,000+ 50,000 – 200,000
Loopback Mode RPS 50,000 – 150,000 1,000 – 5,000
External HTTP (curl/k6) 30,000 – 80,000 500 – 2,000 (throttled by network + cold start)
Cold Start Latency 0ms (always running) 30 – 60 seconds (first request after 15 min idle)
P99 Latency (ping) < 0.1ms 5 – 50ms (variable, shared infra)
Database Query Latency 1 – 5ms 5 – 30ms (network hop to managed PG)
Max Concurrent Connections 100 (configurable) 20 (Free Tier PG limit)
Binary Size 4.55 MB 4.55 MB (same binary)
Memory Usage (Idle) ~10 MB ~10 MB

Can Render Free Tier Handle 50 Lakh (5 Million) Requests?

Yes, but not per second — over time:

  • ✅ 50 Lakh total requests over days/weeks: Absolutely. The engine is stateless for ping/health. No storage consumed per request.
  • ❌ 50 Lakh requests per second: Not on Free Tier. You'd need a dedicated instance (Render Starter/Standard at $7-25/month) or bare-metal hardware.
  • 📊 Realistic Free Tier capacity: ~1,000-2,000 external requests/second sustained, with cold-start spikes.

Recommendation for Higher Load

Load Target Recommended Deployment
Development & Portfolio ✅ Render Free Tier
< 10,000 RPS sustained Render Starter ($7/mo) or Railway.app
10,000 – 100,000 RPS Dedicated VPS (DigitalOcean, Hetzner) $5-20/mo
100,000+ RPS Bare-metal server / Cloud VM (c6a.large or similar)
1,000,000+ RPS Multi-core bare-metal with Direct mode benchmarking

10. Strict Repository Constraints

  • C1 & C9 (Zero Container / Orchestrator Bloat): Zero Dockerfile, docker-compose.yml, or k8s/ manifests exist anywhere in this repository.
  • C2 (Compact Binary Footprint): Statically linked release executable is 4.55 MB, easily fitting inside the < 30 MB budget.
  • C3 (Secret Hygiene): .env is strictly gitignored; .env.example contains only placeholder values.
  • C10 (Offline Asset Bundle): Chart.js and frontend dashboard scripts are vendored locally; no CDN dependencies required.

About

No description, website, or topics provided.

Resources

Stars

1 star

Watchers

0 watching

Forks

Releases

Packages

Contributors

Languages