Authentication & Security
Learn about our dual-authentication system using passwords and client certificates for maximum security.
Overview
Our API uses a two-phase authentication system that combines the convenience of password-based initial login with the enhanced security of mutual TLS (mTLS) using client certificates.
Authentication Flow
1. Password Login → Temporary Token
2. Request Certificate → CA, Client Cert, Private Key
3. Certificate Login → Production Token
4. API Calls → Certificate + Token
Phase 1: Password-Based Authentication
Purpose
- Initial bootstrap only
- Used to request your client certificate
- Token is short-lived and limited in scope
When to Use
- First-time setup
- Certificate renewal (rarely needed)
Security Considerations
- api_key is shown only once during namespace creation
- Store it securely in a secrets manager
- Never commit it to version control
- If lost, you must recreate your namespace
Phase 2: Certificate-Based Authentication
Purpose
- Primary authentication method for all production API calls
- Provides mutual TLS (mTLS) security
- Long-term, renewable credentials
Components
CA Certificate
- Trust anchor for server verification
- Add to your HTTPS client's trust store
- Validates server identity
Client Certificate
- Your public certificate
- Presented during TLS handshake
- Proves your identity to the server
Private Key
- Keep this secret!
- Never share or expose
- Used for TLS handshake
- Store with file permissions 600 (Unix) or restricted access (Windows)
TLS SNI Requirement
What is SNI?
Server Name Indication (SNI) is a TLS extension that specifies which hostname you're connecting to.
Critical Configuration
You must set SNI to: loulilouwai.net
Even though you're connecting to an IP address, the server routing requires this specific SNI value.
Code Examples
Python (requests)
import requests
from requests.adapters import HTTPAdapter
from urllib3.util.ssl_ import create_urllib3_context
class SNIAdapter(HTTPAdapter):
def init_poolmanager(self, *args, **kwargs):
kwargs['server_hostname'] = 'loulilouwai.net'
return super().init_poolmanager(*args, **kwargs)
session = requests.Session()
session.mount('https://', SNIAdapter())Go
tlsConfig := &tls.Config{
ServerName: "loulilouwai.net",
// ... other config
}Token Management
Token Lifecycle
- Tokens expire after a certain period
- When you receive HTTP 403, refresh your token
- No need to request a new certificate
Refresh Strategy
1. Receive 403 Forbidden
2. Call POST /system/login with certificate (password="")
3. Get new token
4. Retry original request
Best Practice: Automatic Refresh
Implement middleware that automatically refreshes tokens on 403 errors:
def api_call_with_auto_refresh(method, endpoint, **kwargs):
response = session.request(method, endpoint, **kwargs)
if response.status_code == 403:
# Refresh token
new_token = certificate_login()
session.headers['X-Molly-Wallet-Token'] = new_token
# Retry
response = session.request(method, endpoint, **kwargs)
return responseSecurity Best Practices
DO
✅ Store api_key in secrets manager (AWS Secrets Manager, HashiCorp Vault)
✅ Set file permissions on private key to 600 (Unix) or equivalent
✅ Use environment variables for sensitive data
✅ Implement automatic token refresh
✅ Monitor certificate expiration dates
✅ Use separate credentials per environment (dev/staging/prod)
DON'T
❌ Store api_key in code or config files
❌ Commit certificates or keys to version control
❌ Share credentials between environments
❌ Ignore 403 errors without refreshing
❌ Use password authentication for production calls
Certificate Expiration
Monitoring
Client certificates typically have a 1-year validity period. Monitor expiration:
openssl x509 -in client_cert.pem -noout -enddateRenewal Process
- Request new certificate using Steps 1-2 from Quick Start
- Update your application configuration
- No service interruption if done before expiry
Troubleshooting
"SSL: CERTIFICATE_VERIFY_FAILED"
- You haven't added the CA certificate to your trust store
"403 Forbidden"
- Token expired → Refresh using certificate login
- Certificate not sent → Check HTTPS client configuration
"Connection Refused" / "Timeout"
- Network/firewall issue
- Check that you can reach the API endpoint
"SSL Handshake Failed"
- SNI not set to
loulilouwai.net - Client certificate/key not properly configured
Next Steps
- Quick Start Guide - Complete authentication setup
- Code Examples - Language-specific implementations
- Troubleshooting - Detailed debugging guide
Updated 2 months ago
