Squashed 'vendor/ruvector/' content from commit b64c2172
git-subtree-dir: vendor/ruvector git-subtree-split: b64c21726f2bb37286d9ee36a7869fef60cc6900
This commit is contained in:
302
examples/edge-net/docs/SECURITY_QUICK_REFERENCE.md
Normal file
302
examples/edge-net/docs/SECURITY_QUICK_REFERENCE.md
Normal file
@@ -0,0 +1,302 @@
|
||||
# Edge-Net Relay Security Quick Reference
|
||||
|
||||
**Last Updated**: 2026-01-03
|
||||
**Component**: WebSocket Relay Server (`/relay/index.js`)
|
||||
**Security Status**: ✅ SECURE (development) | ⚠️ NEEDS SIGNATURES (production)
|
||||
|
||||
---
|
||||
|
||||
## 🔒 Security Features Summary
|
||||
|
||||
| Feature | Status | Implementation |
|
||||
|---------|--------|----------------|
|
||||
| Task Assignment Verification | ✅ **SECURE** | Tracked in `assignedTasks` Map |
|
||||
| Replay Attack Prevention | ✅ **SECURE** | `completedTasks` Set with pre-credit marking |
|
||||
| Credit Self-Reporting Block | ✅ **SECURE** | `ledger_update` rejected, relay-only crediting |
|
||||
| QDAG Ledger (Firestore) | ✅ **SECURE** | Server-side source of truth |
|
||||
| Rate Limiting | ✅ **IMPLEMENTED** | 100 msg/min per node |
|
||||
| Message Size Limits | ✅ **IMPLEMENTED** | 64KB max payload |
|
||||
| Connection Limits | ✅ **IMPLEMENTED** | 5 per IP |
|
||||
| Origin Validation | ✅ **IMPLEMENTED** | CORS whitelist |
|
||||
| Signature Verification | ❌ **NOT IMPLEMENTED** | Placeholder only |
|
||||
|
||||
---
|
||||
|
||||
## 🎯 Attack Vector Status
|
||||
|
||||
### ✅ **PROTECTED**
|
||||
|
||||
1. **Task Completion Spoofing**
|
||||
- Nodes cannot complete tasks not assigned to them
|
||||
- Verified via `assignment.assignedTo === nodeId`
|
||||
|
||||
2. **Replay Attacks**
|
||||
- Tasks cannot be completed twice
|
||||
- `completedTasks` Set prevents duplicates
|
||||
|
||||
3. **Credit Self-Reporting**
|
||||
- Clients cannot claim their own credits
|
||||
- `ledger_update` messages rejected
|
||||
|
||||
### ⚠️ **PARTIALLY PROTECTED**
|
||||
|
||||
4. **Public Key Spoofing**
|
||||
- ✅ Cannot steal credits (assigned at task time)
|
||||
- ⚠️ Can check another user's balance (read-only spoofing)
|
||||
- ❌ No cryptographic proof of key ownership
|
||||
|
||||
---
|
||||
|
||||
## 🚨 Critical Issues for Production
|
||||
|
||||
### 1. Missing Signature Verification (CRITICAL)
|
||||
|
||||
**Current Code** (Lines 281-286):
|
||||
```javascript
|
||||
function validateSignature(nodeId, message, signature, publicKey) {
|
||||
// TODO: In production, verify Ed25519 signature from PiKey
|
||||
return nodes.has(nodeId); // Placeholder
|
||||
}
|
||||
```
|
||||
|
||||
**Required Fix**:
|
||||
```javascript
|
||||
import { verify } from '@noble/ed25519';
|
||||
|
||||
async function validateSignature(message, signature, publicKey) {
|
||||
try {
|
||||
const msgHash = createHash('sha256').update(JSON.stringify(message)).digest();
|
||||
return await verify(signature, msgHash, publicKey);
|
||||
} catch {
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
// Require on sensitive operations
|
||||
case 'task_complete':
|
||||
if (!message.signature || !await validateSignature(message, message.signature, ws.publicKey)) {
|
||||
ws.send(JSON.stringify({ type: 'error', message: 'Invalid signature' }));
|
||||
break;
|
||||
}
|
||||
```
|
||||
|
||||
**Priority**: 🔴 **CRITICAL** - Must implement before production
|
||||
|
||||
### 2. Unbounded Memory Growth (MEDIUM)
|
||||
|
||||
**Issue**: `completedTasks` Set grows forever
|
||||
|
||||
**Fix**:
|
||||
```javascript
|
||||
// Add timestamp tracking
|
||||
const completedTasks = new Map(); // taskId -> timestamp
|
||||
|
||||
// Cleanup old completed tasks
|
||||
setInterval(() => {
|
||||
const CLEANUP_AGE = 24 * 60 * 60 * 1000; // 24 hours
|
||||
const cutoff = Date.now() - CLEANUP_AGE;
|
||||
for (const [taskId, timestamp] of completedTasks) {
|
||||
if (timestamp < cutoff) {
|
||||
completedTasks.delete(taskId);
|
||||
}
|
||||
}
|
||||
}, 60 * 60 * 1000); // Every hour
|
||||
```
|
||||
|
||||
**Priority**: 🟡 **MEDIUM** - Implement before long-running deployment
|
||||
|
||||
---
|
||||
|
||||
## 🧪 Security Test Suite
|
||||
|
||||
### Running Tests
|
||||
|
||||
```bash
|
||||
cd /workspaces/ruvector/examples/edge-net/tests
|
||||
npm install
|
||||
npm test
|
||||
```
|
||||
|
||||
### Test Coverage
|
||||
|
||||
- ✅ Task completion spoofing (2 tests)
|
||||
- ✅ Replay attacks (1 test)
|
||||
- ✅ Credit self-reporting (2 tests)
|
||||
- ✅ Public key spoofing (2 tests)
|
||||
- ✅ Rate limiting (1 test)
|
||||
- ✅ Message size limits (1 test)
|
||||
- ✅ Connection limits (1 test)
|
||||
- ✅ Combined attack scenario (1 test)
|
||||
|
||||
**Total**: 12 security tests in `relay-security.test.ts`
|
||||
|
||||
---
|
||||
|
||||
## 📋 Security Checklist
|
||||
|
||||
### Before Development Deployment
|
||||
|
||||
- [x] Task assignment tracking
|
||||
- [x] Replay attack prevention
|
||||
- [x] Credit self-reporting blocked
|
||||
- [x] QDAG Firestore ledger
|
||||
- [x] Rate limiting
|
||||
- [x] Message size limits
|
||||
- [x] Connection limits
|
||||
- [x] Origin validation
|
||||
- [x] Security test suite
|
||||
|
||||
### Before Production Deployment
|
||||
|
||||
- [ ] **Ed25519 signature verification** (CRITICAL)
|
||||
- [ ] **Challenge-response on registration** (CRITICAL)
|
||||
- [ ] Completed tasks cleanup (MEDIUM)
|
||||
- [ ] Global connection limit (MEDIUM)
|
||||
- [ ] API key for non-browser clients (MEDIUM)
|
||||
- [ ] Rate-limit balance queries (LOW)
|
||||
- [ ] Generic error messages (LOW)
|
||||
- [ ] Firestore security rules validation (LOW)
|
||||
|
||||
---
|
||||
|
||||
## 🔍 Code Review Findings
|
||||
|
||||
### Security Strengths
|
||||
|
||||
1. **QDAG Architecture** - Excellent design
|
||||
- Firestore as single source of truth
|
||||
- Credits keyed by public key (identity-based)
|
||||
- Server-side only credit increases
|
||||
- Persistent across sessions
|
||||
|
||||
2. **Task Assignment Security** - Well implemented
|
||||
- Assignment tracked with metadata
|
||||
- Node ID verification on completion
|
||||
- Public key stored at assignment time
|
||||
- Task expiration (5 minutes)
|
||||
|
||||
3. **Defense in Depth** - Multiple layers
|
||||
- Origin validation (CORS)
|
||||
- Connection limits (per IP)
|
||||
- Rate limiting (per node)
|
||||
- Message size limits
|
||||
- Heartbeat timeout
|
||||
|
||||
### Security Weaknesses
|
||||
|
||||
1. **No Cryptographic Verification** - Major gap
|
||||
- Public key ownership not proven
|
||||
- Allows read-only spoofing
|
||||
- Required for production
|
||||
|
||||
2. **Memory Leaks** - Minor issues
|
||||
- `completedTasks` grows unbounded
|
||||
- Easy to fix with periodic cleanup
|
||||
|
||||
3. **Distributed Attacks** - Missing protections
|
||||
- No global connection limit
|
||||
- Vulnerable to distributed DoS
|
||||
- Can be mitigated with cloud-level protections
|
||||
|
||||
---
|
||||
|
||||
## 🛡️ Security Best Practices
|
||||
|
||||
### For Developers
|
||||
|
||||
1. **Never trust client input**
|
||||
- All credits server-generated
|
||||
- Task assignments server-controlled
|
||||
- Ledger state from Firestore only
|
||||
|
||||
2. **Validate everything**
|
||||
- Check task assignment before crediting
|
||||
- Verify node registration before operations
|
||||
- Rate-limit all message types
|
||||
|
||||
3. **Defense in depth**
|
||||
- Multiple security layers
|
||||
- Fail securely (default deny)
|
||||
- Log security events
|
||||
|
||||
### For Operations
|
||||
|
||||
1. **Monitor security metrics**
|
||||
- Failed authentication attempts
|
||||
- Rate limit violations
|
||||
- Connection flooding
|
||||
- Unusual credit patterns
|
||||
|
||||
2. **Configure Firestore security**
|
||||
- Validate security rules
|
||||
- Restrict ledger write access
|
||||
- Enable audit logging
|
||||
|
||||
3. **Network security**
|
||||
- Use TLS/WSS in production
|
||||
- Configure firewall rules
|
||||
- Enable DDoS protection
|
||||
|
||||
---
|
||||
|
||||
## 📊 Security Metrics
|
||||
|
||||
### Current Implementation
|
||||
|
||||
| Metric | Value | Status |
|
||||
|--------|-------|--------|
|
||||
| Authentication | Public key (unverified) | ⚠️ Development only |
|
||||
| Authorization | Task assignment tracking | ✅ Secure |
|
||||
| Credit System | Firestore QDAG | ✅ Secure |
|
||||
| Rate Limiting | 100 msg/min | ✅ Good |
|
||||
| Max Message Size | 64KB | ✅ Good |
|
||||
| Connections per IP | 5 | ✅ Good |
|
||||
| Connection Timeout | 30s | ✅ Good |
|
||||
| Task Expiration | 5 min | ✅ Good |
|
||||
|
||||
### Recommended Production Values
|
||||
|
||||
| Metric | Development | Production |
|
||||
|--------|-------------|------------|
|
||||
| Authentication | Public key | Ed25519 signature |
|
||||
| Rate Limit | 100 msg/min | 50 msg/min + adaptive |
|
||||
| Max Connections | 5 per IP | 3 per IP + global limit |
|
||||
| Task Timeout | 5 min | 2 min |
|
||||
| Completed Tasks TTL | None | 24 hours |
|
||||
|
||||
---
|
||||
|
||||
## 📚 Related Documentation
|
||||
|
||||
- **Full Audit Report**: `/docs/SECURITY_AUDIT_REPORT.md`
|
||||
- **Test Suite**: `/tests/relay-security.test.ts`
|
||||
- **Test README**: `/tests/README.md`
|
||||
- **Relay Source**: `/relay/index.js`
|
||||
|
||||
---
|
||||
|
||||
## 🆘 Security Incident Response
|
||||
|
||||
### If you suspect an attack:
|
||||
|
||||
1. **Check relay logs** for suspicious patterns
|
||||
2. **Query Firestore** for unexpected credit increases
|
||||
3. **Review rate limit logs** for flooding attempts
|
||||
4. **Audit task completions** for spoofing attempts
|
||||
5. **Contact security team** if confirmed breach
|
||||
|
||||
### Emergency shutdown:
|
||||
|
||||
```bash
|
||||
# Stop relay server
|
||||
pkill -f "node.*relay/index.js"
|
||||
|
||||
# Or send SIGTERM for graceful shutdown
|
||||
kill -TERM $(pgrep -f "node.*relay/index.js")
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
**Security Contact**: [Your security team contact]
|
||||
**Last Security Audit**: 2026-01-03
|
||||
**Next Scheduled Audit**: After signature verification implementation
|
||||
Reference in New Issue
Block a user