# Auth Rules Management System - Current Status

## Executive Summary

The auth rules management system is **fully implemented** with a database schema that differs from c-relay. This document outlines the current state and proposes alignment with c-relay's schema.

## Current Database Schema

### Ginxsom Schema (Current)
```sql
CREATE TABLE auth_rules (
    id INTEGER PRIMARY KEY AUTOINCREMENT,
    rule_type TEXT NOT NULL,              -- 'pubkey_blacklist', 'pubkey_whitelist', etc.
    rule_target TEXT NOT NULL,            -- The pubkey, hash, or MIME type to match
    operation TEXT NOT NULL DEFAULT '*',  -- 'upload', 'delete', 'list', or '*'
    enabled INTEGER NOT NULL DEFAULT 1,   -- 1 = enabled, 0 = disabled
    priority INTEGER NOT NULL DEFAULT 100,-- Lower number = higher priority
    description TEXT,                     -- Human-readable description
    created_by TEXT,                      -- Admin pubkey who created the rule
    created_at INTEGER NOT NULL DEFAULT (strftime('%s', 'now')),
    updated_at INTEGER NOT NULL DEFAULT (strftime('%s', 'now')),
    
    CHECK (rule_type IN ('pubkey_blacklist', 'pubkey_whitelist', 
                         'hash_blacklist', 'mime_blacklist', 'mime_whitelist')),
    CHECK (operation IN ('upload', 'delete', 'list', '*')),
    CHECK (enabled IN (0, 1)),
    CHECK (priority >= 0),
    UNIQUE(rule_type, rule_target, operation)
);
```

### C-Relay Schema (Target)
```sql
CREATE TABLE auth_rules (
    id INTEGER PRIMARY KEY AUTOINCREMENT,
    rule_type TEXT NOT NULL,
    pattern_type TEXT NOT NULL,
    pattern_value TEXT NOT NULL,
    active INTEGER NOT NULL DEFAULT 1,
    created_at INTEGER NOT NULL DEFAULT (strftime('%s', 'now')),
    updated_at INTEGER NOT NULL DEFAULT (strftime('%s', 'now'))
);
```

## Schema Differences

| Field | Ginxsom | C-Relay | Notes |
|-------|---------|---------|-------|
| `id` | ✅ | ✅ | Same |
| `rule_type` | ✅ | ✅ | Same |
| `rule_target` | ✅ | ❌ | Ginxsom-specific |
| `pattern_type` | ❌ | ✅ | C-relay-specific |
| `pattern_value` | ❌ | ✅ | C-relay-specific |
| `operation` | ✅ | ❌ | Ginxsom-specific |
| `enabled` | ✅ (1/0) | ❌ | Ginxsom uses `enabled` |
| `active` | ❌ | ✅ (1/0) | C-relay uses `active` |
| `priority` | ✅ | ❌ | Ginxsom-specific |
| `description` | ✅ | ❌ | Ginxsom-specific |
| `created_by` | ✅ | ❌ | Ginxsom-specific |
| `created_at` | ✅ | ✅ | Same |
| `updated_at` | ✅ | ✅ | Same |

## What Has Been Implemented

### ✅ Database Layer
- **Schema Created**: [`auth_rules`](../db/52e366edfa4e9cc6a6d4653828e51ccf828a2f5a05227d7a768f33b5a198681a.db) table exists with full schema
- **Indexes**: 5 indexes for performance optimization
- **Constraints**: CHECK constraints for data validation
- **Unique Constraint**: Prevents duplicate rules

### ✅ Rule Evaluation Engine
Location: [`src/request_validator.c:1318-1592`](../src/request_validator.c#L1318-L1592)

**Implemented Features:**
1. **Pubkey Blacklist** (Priority 1) - Lines 1346-1377
2. **Hash Blacklist** (Priority 2) - Lines 1382-1420
3. **MIME Blacklist** (Priority 3) - Lines 1423-1462
4. **Pubkey Whitelist** (Priority 4) - Lines 1464-1491
5. **MIME Whitelist** (Priority 5) - Lines 1493-1526
6. **Whitelist Default Denial** (Priority 6) - Lines 1528-1591

**Features:**
- ✅ Priority-based rule evaluation
- ✅ Wildcard operation matching (`*`)
- ✅ MIME type pattern matching (`image/*`)
- ✅ Whitelist default-deny behavior
- ✅ Detailed violation tracking
- ✅ Performance-optimized queries

### ✅ Admin API Commands
Location: [`src/admin_commands.c`](../src/admin_commands.c)

**Implemented Commands:**
- ✅ `config_query` - Query configuration values
- ✅ `config_update` - Update configuration
- ✅ `stats_query` - Get system statistics (includes auth_rules count)
- ✅ `system_status` - System health check
- ✅ `blob_list` - List stored blobs
- ✅ `storage_stats` - Storage statistics
- ✅ `sql_query` - Direct SQL queries (read-only)

**Note:** The stats_query command already queries auth_rules:
```c
// Line 390-395
sql = "SELECT COUNT(*) FROM auth_rules WHERE enabled = 1";
rc = sqlite3_prepare_v2(db, sql, -1, &stmt, NULL);
if (rc == SQLITE_OK && sqlite3_step(stmt) == SQLITE_ROW) {
    cJSON_AddNumberToObject(stats, "active_auth_rules", sqlite3_column_int(stmt, 0));
}
```

### ❌ Missing Admin API Endpoints

The following endpoints from [`docs/AUTH_RULES_IMPLEMENTATION_PLAN.md`](../docs/AUTH_RULES_IMPLEMENTATION_PLAN.md) are **NOT implemented**:

1. **GET /api/rules** - List authentication rules
2. **POST /api/rules** - Create new rule
3. **PUT /api/rules/:id** - Update existing rule
4. **DELETE /api/rules/:id** - Delete rule
5. **POST /api/rules/clear-cache** - Clear auth cache
6. **GET /api/rules/test** - Test rule evaluation

### ✅ Configuration System
- ✅ `auth_rules_enabled` config flag (checked in [`reload_auth_config()`](../src/request_validator.c#L1049-L1145))
- ✅ Cache system with 5-minute TTL
- ✅ Environment variable support (`GINX_NO_CACHE`, `GINX_CACHE_TIMEOUT`)

### ✅ Documentation
- ✅ [`docs/AUTH_API.md`](../docs/AUTH_API.md) - Complete authentication flow
- ✅ [`docs/AUTH_RULES_IMPLEMENTATION_PLAN.md`](../docs/AUTH_RULES_IMPLEMENTATION_PLAN.md) - Implementation plan
- ✅ Flow diagrams and performance metrics

## Proposed Schema Migration to C-Relay Format

### Option 1: Minimal Changes (Recommended)
Keep Ginxsom's richer schema but rename fields for compatibility:

```sql
ALTER TABLE auth_rules RENAME COLUMN enabled TO active;
ALTER TABLE auth_rules ADD COLUMN pattern_type TEXT;
ALTER TABLE auth_rules ADD COLUMN pattern_value TEXT;

-- Populate new fields from existing data
UPDATE auth_rules SET 
    pattern_type = CASE 
        WHEN rule_type LIKE '%pubkey%' THEN 'pubkey'
        WHEN rule_type LIKE '%hash%' THEN 'hash'
        WHEN rule_type LIKE '%mime%' THEN 'mime'
    END,
    pattern_value = rule_target;
```

**Pros:**
- Maintains all Ginxsom features (operation, priority, description)
- Adds c-relay compatibility fields
- No data loss
- Backward compatible

**Cons:**
- Redundant fields (`rule_target` + `pattern_value`)
- Larger schema

### Option 2: Full Migration to C-Relay Schema
Drop Ginxsom-specific fields and adopt c-relay schema:

```sql
-- Create new table with c-relay schema
CREATE TABLE auth_rules_new (
    id INTEGER PRIMARY KEY AUTOINCREMENT,
    rule_type TEXT NOT NULL,
    pattern_type TEXT NOT NULL,
    pattern_value TEXT NOT NULL,
    active INTEGER NOT NULL DEFAULT 1,
    created_at INTEGER NOT NULL DEFAULT (strftime('%s', 'now')),
    updated_at INTEGER NOT NULL DEFAULT (strftime('%s', 'now'))
);

-- Migrate data
INSERT INTO auth_rules_new (id, rule_type, pattern_type, pattern_value, active, created_at, updated_at)
SELECT 
    id,
    rule_type,
    CASE 
        WHEN rule_type LIKE '%pubkey%' THEN 'pubkey'
        WHEN rule_type LIKE '%hash%' THEN 'hash'
        WHEN rule_type LIKE '%mime%' THEN 'mime'
    END as pattern_type,
    rule_target as pattern_value,
    enabled as active,
    created_at,
    updated_at
FROM auth_rules;

-- Replace old table
DROP TABLE auth_rules;
ALTER TABLE auth_rules_new RENAME TO auth_rules;
```

**Pros:**
- Full c-relay compatibility
- Simpler schema
- Smaller database

**Cons:**
- **Loss of operation-specific rules** (upload/delete/list)
- **Loss of priority system**
- **Loss of description and created_by tracking**
- **Breaking change** - requires code updates in [`request_validator.c`](../src/request_validator.c)

## Code Impact Analysis

### Files Requiring Updates for C-Relay Schema

1. **[`src/request_validator.c`](../src/request_validator.c)**
   - Lines 1346-1591: Rule evaluation queries need field name changes
   - Change `enabled` → `active`
   - Change `rule_target` → `pattern_value`
   - Add `pattern_type` to queries if using Option 1

2. **[`src/admin_commands.c`](../src/admin_commands.c)**
   - Line 390: Stats query uses `enabled` field
   - Any future rule management endpoints

3. **[`docs/AUTH_RULES_IMPLEMENTATION_PLAN.md`](../docs/AUTH_RULES_IMPLEMENTATION_PLAN.md)**
   - Update schema documentation
   - Update API endpoint specifications

## Recommendations

### For C-Relay Alignment
**Use Option 1 (Minimal Changes)** because:
1. Preserves Ginxsom's advanced features (operation-specific rules, priority)
2. Adds c-relay compatibility without breaking existing functionality
3. Minimal code changes required
4. No data loss

### For Admin API Completion
Implement the missing endpoints in priority order:
1. **POST /api/rules** - Create rules (highest priority)
2. **GET /api/rules** - List rules
3. **DELETE /api/rules/:id** - Delete rules
4. **PUT /api/rules/:id** - Update rules
5. **GET /api/rules/test** - Test rules
6. **POST /api/rules/clear-cache** - Clear cache

### Migration Script
```bash
#!/bin/bash
# migrate_auth_rules_to_crelay.sh

DB_PATH="db/52e366edfa4e9cc6a6d4653828e51ccf828a2f5a05227d7a768f33b5a198681a.db"

sqlite3 "$DB_PATH" <<EOF
-- Backup current table
CREATE TABLE auth_rules_backup AS SELECT * FROM auth_rules;

-- Add c-relay compatibility fields
ALTER TABLE auth_rules ADD COLUMN pattern_type TEXT;
ALTER TABLE auth_rules ADD COLUMN pattern_value TEXT;

-- Populate new fields
UPDATE auth_rules SET 
    pattern_type = CASE 
        WHEN rule_type LIKE '%pubkey%' THEN 'pubkey'
        WHEN rule_type LIKE '%hash%' THEN 'hash'
        WHEN rule_type LIKE '%mime%' THEN 'mime'
    END,
    pattern_value = rule_target;

-- Rename enabled to active for c-relay compatibility
-- Note: SQLite doesn't support RENAME COLUMN directly in older versions
-- So we'll keep both fields for now
ALTER TABLE auth_rules ADD COLUMN active INTEGER NOT NULL DEFAULT 1;
UPDATE auth_rules SET active = enabled;

-- Verify migration
SELECT COUNT(*) as total_rules FROM auth_rules;
SELECT COUNT(*) as rules_with_pattern FROM auth_rules WHERE pattern_type IS NOT NULL;
EOF
```

## Summary

**Current State:**
- ✅ Database schema exists and is functional
- ✅ Rule evaluation engine fully implemented
- ✅ Configuration system working
- ✅ Documentation complete
- ❌ Admin API endpoints for rule management missing

**To Align with C-Relay:**
- Add `pattern_type` and `pattern_value` fields
- Optionally rename `enabled` to `active`
- Keep Ginxsom's advanced features (operation, priority, description)
- Update queries to use new field names

**Next Steps:**
1. Decide on migration strategy (Option 1 recommended)
2. Run migration script
3. Update code to use new field names
4. Implement missing Admin API endpoints
5. Test rule evaluation with new schema