- Security Overview
- Authentication & Authorization
- Input Validation
- Command Execution Security
- Encryption & Secrets
- Network Security
- WebSocket Security
- Rate Limiting & Account Protection
- Audit Logging
- Production Deployment
- Security Best Practices
- Vulnerability Reporting
BloxOS implements defense-in-depth security with multiple layers of protection:
| Layer | Protection |
|---|---|
| Network | HTTPS/HSTS, CORS, Security Headers |
| Authentication | JWT tokens, session management, account lockout |
| Authorization | Farm-based RBAC, resource ownership validation |
| Input | Validation, sanitization, command whitelisting |
| Output | XSS prevention, error sanitization |
| Data | AES-256-GCM encryption, PBKDF2 key derivation |
| Monitoring | Audit logging, rate limiting, request tracing |
- 100% Critical vulnerabilities addressed
- 100% High-severity vulnerabilities addressed
- Production-ready security posture
BloxOS uses JSON Web Tokens (JWT) for authentication:
| Token Type | Expiration | Purpose |
|---|---|---|
| Access Token | 4 hours | API authentication |
| Refresh Token | 7 days | Obtain new access tokens |
Token Flow:
- User logs in with email/password
- Server returns access token + refresh token
- Access token sent in
Authorization: Bearer <token>header - When access token expires, use refresh token to get new one
- On logout, both tokens are blacklisted
| Requirement | Value |
|---|---|
| Minimum length | 12 characters |
| Uppercase | Required |
| Lowercase | Required |
| Numbers | Required |
| Special characters | Required |
Accepted special characters: !@#$%^&*()_+-=[]{};\:'",.<>?/\|~
| Role | Permissions |
|---|---|
| ADMIN | Full access to all resources |
| USER | Access to owned farms and rigs only |
| MONITOR | Read-only access to assigned resources |
Users can only access rigs that belong to farms they own:
User → Owns → Farm → Contains → Rigs
- Regular users see only their own farms/rigs
- Admins can see all farms/rigs
- All rig operations verify farm ownership
- Schema Validation - Zod schemas validate request structure
- Business Validation - Domain-specific rules
- Sanitization - Remove/escape dangerous characters
| Input Type | Validation |
|---|---|
| RFC 5322 format | |
| Password | Complexity requirements |
| IP Address | IPv4/IPv6 format |
| Hostname | DNS-valid format |
| Wallet Address | Alphanumeric, 20-128 chars |
| Pool URL | Valid URL with allowed protocols |
| Miner Name | Whitelist only |
| Algorithm | Whitelist only |
| OC Values | Safe numeric ranges |
All user-provided strings are sanitized:
- HTML tags removed (
<,>) - Trimmed to max length
- Control characters removed
BloxOS executes commands on mining rigs via SSH. All commands are validated:
Allowed Commands (Whitelist):
- System info:
hostname,uname,uptime,date - Monitoring:
nvidia-smi,rocm-smi,ps,top,free - Network:
ip addr,ifconfig,hostname -I - Miner status:
pgrep,pidof,screen -ls
Blocked Commands:
- Destructive:
rm,rmdir,mkfs,dd - Privilege escalation:
sudo(except controlled paths),su - Network exfiltration:
wget,curl -o,nc -l - Code execution:
eval,exec,python -c,bash -c - System modification:
shutdown,reboot,systemctl disable
Blocked Patterns:
- Command chaining:
;,&&,||,| - Redirects:
>,>> - Variable expansion:
$, backticks - Subshells:
(,)
Miner commands use array-based construction to prevent injection:
// Safe: Array-based construction
const args = ['-a', algo, '-o', poolUrl, '-u', wallet];
const command = `${minerPath} ${args.join(' ')}`;
// NOT used: String interpolation (vulnerable)
// const command = `${minerPath} -a ${algo} -o ${poolUrl}`;When sudo is required, passwords are sent via PTY stdin:
- Password never appears in command line
- Password not visible in process lists
- Uses pseudo-terminal for secure entry
SSH credentials (passwords, private keys) are encrypted at rest:
| Parameter | Value |
|---|---|
| Algorithm | AES-256-GCM |
| Key Derivation | PBKDF2 |
| Iterations | 100,000 |
| Hash | SHA-512 |
| IV Length | 16 bytes (random per encryption) |
| Auth Tag | 16 bytes |
| Variable | Purpose | Example |
|---|---|---|
JWT_SECRET |
Signs JWT tokens | 64+ random chars |
ENCRYPTION_KEY |
Encrypts SSH credentials | 64+ random chars |
COOKIE_SECRET |
Signs cookies | 32+ random chars |
DATABASE_URL |
PostgreSQL connection | postgresql://... |
Generate secure secrets:
# Generate a 64-character random secret
openssl rand -base64 48
# Or using Node.js
node -e "console.log(require('crypto').randomBytes(48).toString('base64'))"In production (NODE_ENV=production):
- All secrets MUST be set via environment variables
- Missing secrets cause immediate startup failure
- No fallback defaults are used
In development:
- Warnings are logged for missing secrets
- Insecure defaults used (clearly marked)
| Environment | Configuration |
|---|---|
| Development | All origins allowed |
| Production | Only CORS_ORIGINS allowed |
Set allowed origins in production:
CORS_ORIGINS=https://dashboard.example.com,https://admin.example.com| Header | Value |
|---|---|
| Content-Security-Policy | default-src 'self' |
| X-Content-Type-Options | nosniff |
| X-Frame-Options | DENY |
| X-XSS-Protection | 1; mode=block |
| Referrer-Policy | strict-origin-when-cross-origin |
In production:
Strict-Transport-Security: max-age=31536000; includeSubDomains; preload
- 1 year max-age
- Includes subdomains
- Preload eligible
Enable HTTPS redirect in production:
FORCE_HTTPS=trueThis redirects all HTTP requests to HTTPS (301 redirect).
BloxOS uses the double-submit cookie pattern:
- Server sets
csrf_tokencookie (readable by JavaScript) - Client includes token in
X-CSRF-Tokenheader - Server verifies cookie and header match (timing-safe comparison)
Exempt paths:
/api/agent/*(uses API key auth)/api/auth/login(creates session)/api/auth/register/api/health
WebSocket connections require authentication within 10 seconds:
Option 1: Query parameter
const ws = new WebSocket('wss://api.example.com/ws?token=YOUR_JWT_TOKEN');Option 2: Auth message
const ws = new WebSocket('wss://api.example.com/ws');
ws.onopen = () => {
ws.send(JSON.stringify({ type: 'auth', token: 'YOUR_JWT_TOKEN' }));
};- Client connects
- 10-second authentication timer starts
- Client sends auth token
- Server validates token, clears timer
- Server sends
authenticatedmessage - Client can now send/receive data
If authentication fails or times out, connection is closed with appropriate error code.
All WebSocket messages are sanitized before sending:
- HTML entities escaped
- Prevents XSS attacks via WebSocket data
- Terminal output filtered for dangerous sequences
Incoming WebSocket messages are validated:
- Must be valid JSON
- Must have
typefield - Type must match alphanumeric pattern
- Invalid messages are rejected
| Limit | Value |
|---|---|
| Default | 100 requests/minute per IP |
| Auth endpoints | 10 requests/minute per IP |
| Agent endpoints | 60 requests/minute per IP |
Protection against brute-force attacks:
| Parameter | Value |
|---|---|
| Max attempts | 5 |
| Lockout duration | 15 minutes |
| Attempt window | 15 minutes |
Behavior:
- Failed login increments attempt counter
- After 5 failures, account is locked
- Lockout expires after 15 minutes
- Successful login clears attempt counter
Note: Lockout applies per email address, not per IP, to prevent distributed attacks.
| Limit | Value |
|---|---|
| Body size | 1 MB |
| Request timeout | 30 seconds |
| WebSocket auth timeout | 10 seconds |
| Category | Events |
|---|---|
| Authentication | Login, logout, failed attempts, lockouts |
| Authorization | Access denied, permission checks |
| User Management | Create, update, delete, password reset |
| Rig Operations | Create, update, delete, commands |
| SSH | Connection tests, command execution |
| Security | CSRF failures, rate limiting |
{
"timestamp": "2026-01-06T12:00:00.000Z",
"userId": "user_123",
"action": "login",
"resource": "user",
"resourceId": "user_123",
"ip": "192.168.1.1",
"userAgent": "Mozilla/5.0...",
"success": true,
"details": { "method": "password" }
}Every request gets a unique ID:
- Header:
X-Request-ID - Used for correlating logs
- Returned in responses
# Required
NODE_ENV=production
JWT_SECRET=<64-char-random-string>
ENCRYPTION_KEY=<64-char-random-string>
COOKIE_SECRET=<32-char-random-string>
DATABASE_URL=postgresql://user:pass@host:5432/bloxos
# Recommended
CORS_ORIGINS=https://your-dashboard.com
FORCE_HTTPS=true
API_HOST=0.0.0.0
API_PORT=3001
# Optional
REDIS_URL=redis://host:6379 # For distributed sessionsserver {
listen 443 ssl http2;
server_name api.example.com;
ssl_certificate /path/to/cert.pem;
ssl_certificate_key /path/to/key.pem;
ssl_protocols TLSv1.2 TLSv1.3;
ssl_ciphers ECDHE-ECDSA-AES128-GCM-SHA256:ECDHE-RSA-AES128-GCM-SHA256;
ssl_prefer_server_ciphers off;
location / {
proxy_pass http://127.0.0.1:3001;
proxy_http_version 1.1;
proxy_set_header Upgrade $http_upgrade;
proxy_set_header Connection "upgrade";
proxy_set_header Host $host;
proxy_set_header X-Real-IP $remote_addr;
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
proxy_set_header X-Forwarded-Proto $scheme;
}
}# docker-compose.yml security settings
services:
api:
security_opt:
- no-new-privileges:true
read_only: true
tmpfs:
- /tmp
environment:
- NODE_ENV=production
# Don't run as root
user: "1000:1000"- All environment variables set
- Secrets are strong and unique
- HTTPS configured with valid certificate
- CORS origins restricted
- Database credentials secured
- Firewall configured (only 443 exposed)
- Monitoring/alerting set up
- Backup strategy in place
- Log aggregation configured
-
Keep secrets secure
- Never commit secrets to git
- Use secret management (Vault, AWS Secrets Manager)
- Rotate secrets periodically
-
Monitor security events
- Review audit logs regularly
- Set up alerts for failed logins
- Monitor rate limiting triggers
-
Keep software updated
- Update dependencies regularly
- Apply security patches promptly
- Monitor for CVEs
-
Backup and recovery
- Regular database backups
- Test restoration procedures
- Encrypt backups at rest
-
Use strong passwords
- 12+ characters minimum
- Mix of character types
- Don't reuse passwords
-
Secure your account
- Log out when done
- Don't share credentials
- Report suspicious activity
-
Secure your rigs
- Use SSH keys when possible
- Keep rig OS updated
- Firewall unnecessary ports
If you discover a security vulnerability in BloxOS:
- DO NOT open a public GitHub issue
- Email security concerns to: [security@bloxos.example.com]
- Include:
- Description of the vulnerability
- Steps to reproduce
- Potential impact
- Suggested fix (if any)
| Phase | Timeline |
|---|---|
| Acknowledgment | 24 hours |
| Initial assessment | 72 hours |
| Fix development | Depends on severity |
| Public disclosure | After fix deployed |
| Severity | Description | Response |
|---|---|---|
| Critical | RCE, data breach, auth bypass | Immediate fix |
| High | Privilege escalation, significant data exposure | Fix within 7 days |
| Medium | Limited impact vulnerabilities | Fix within 30 days |
| Low | Best practice improvements | Scheduled maintenance |
Security Hardening Release
- Implemented command injection prevention
- Added rate limiting and account lockout
- Implemented CSRF protection
- Added farm-based RBAC authorization
- Implemented session management with token blacklisting
- Added comprehensive audit logging
- Configured security headers (Helmet)
- Added HSTS and HTTPS redirect support
- Implemented WebSocket authentication timeout
- Added XSS prevention for WebSocket output
- Improved encryption (PBKDF2 key derivation)
- Added array-based miner command construction
Last Updated: January 2026 Security Rating: A- (Excellent)