mirror of
https://github.com/azaion/loader.git
synced 2026-04-22 21:56:33 +00:00
8f7deb3fca
Made-with: Cursor
2.9 KiB
2.9 KiB
Security Approach
Authentication
- Mechanism: JWT Bearer tokens issued by Azaion Resource API
- Token handling: Decoded without signature verification (
options={"verify_signature": False}) — trusts the API server - Token refresh: Automatic re-login on 401/403 responses (single retry)
- Credential storage: In-memory only (Credentials object); not persisted to disk
Authorization
- Model: Role-based (RoleEnum with 7 levels: NONE through ApiAdmin)
- Enforcement: Roles are parsed from JWT and stored on the User object, but no endpoint-level authorization is enforced by the loader. All endpoints are accessible once credentials are set.
Encryption
Resource Encryption (binary-split scheme)
- Algorithm: AES-256-CBC with PKCS7 padding
- Key expansion: SHA-256 hash of string key → 32-byte AES key
- IV: Random 16-byte IV prepended to ciphertext
Key Derivation
| Key Type | Derivation | Scope |
|---|---|---|
| API download key | SHA-384(email + password + hw_hash + salt) |
Per-user, per-machine |
| Hardware hash | SHA-384("Azaion_" + hardware_fingerprint + salt) |
Per-machine |
| Resource encryption key | SHA-384(fixed_salt_string) |
Global (shared across all users) |
| Archive decryption key | SHA-256(key_fragment_from_api) |
Per-unlock operation |
Binary Split
- Resources encrypted with shared resource key, then split into:
- Small part (≤3KB or 30%): uploaded to authenticated API
- Big part (remainder): uploaded to CDN
- Decryption requires both parts — compromise of either storage alone is insufficient
Hardware Binding
- Hardware fingerprint: CPU model, GPU, memory size, drive serial number
- Used to derive per-machine encryption keys for API resource downloads
- Prevents extraction of downloaded resources to different hardware
IP Protection
- Security-sensitive modules (security, api_client, credentials, etc.) are Cython
.pyxfiles compiled to native.soextensions - Key derivation salts and logic are in compiled code, not readable Python
Secrets Management
- CDN credentials stored in
cdn.yaml, downloaded encrypted from the API - User credentials exist only in memory
- JWT tokens exist only in memory
- No
.envfile or secrets manager — environment variables for runtime config
Input Validation
- Pydantic models validate request structure (LoginRequest, LoadRequest)
- No additional input sanitization beyond Pydantic type checking
- No rate limiting on any endpoint
Known Security Gaps
- JWT decoded without signature verification
- No endpoint-level authorization enforcement
- No rate limiting
- Resource encryption key is static/shared — not per-user
subprocesswithshell=Truein hardware_service (not user-input-driven, but still a risk pattern)- No HTTPS termination within the service (assumes reverse proxy or direct Docker network)