alea-q
SDK Python officiel pour l'API ALEA-Q / CERTROPI — génération d'entiers aléatoires certifiés Device-Independent depuis des ordinateurs quantiques réels.
Installation
pip install alea-q
# Avec vérification de certificats d'attestation
pip install "alea-q[verify]"
# Avec streaming Silver en temps réel
pip install "alea-q[stream]"
Démarrage rapide
from alea_q import AleaQClient
# Clé API dans le constructeur ou variable d'env ALEA_Q_API_KEY
client = AleaQClient(api_key="sk_plat_xxx")
# Platinum — entier DI-certifié depuis un ordinateur quantique réel
result = client.platinum.generate(n_bits=256)
print(result.as_hex()) # 0x3f2a...
print(result.certificate) # dict d'attestation SHA-3/ECDSA
# Silver — DRBG seedé QPU
result = client.silver.generate(n_bits=128)
# Ivory — batch haute vitesse
batch = client.ivory.batch(size=10000, n_bits=32)
print(batch.values[:5])
Authentification
# Option 1 — clé dans le constructeur
client = AleaQClient(api_key="sk_plat_xxx")
# Option 2 — variable d'environnement
import os
os.environ["ALEA_Q_API_KEY"] = "sk_plat_xxx"
client = AleaQClient()
Le tier est détecté automatiquement depuis le préfixe de la clé
(sk_ivor_ / sk_silv_ / sk_plat_) :
client = AleaQClient(api_key="sk_plat_xxx")
print(client.tier) # "platinum"
Compte authentifié
info = client.me()
print(info.tier) # "platinum"
print(info.quota.remaining_today) # entiers restants aujourd'hui
print(info.usage.total_calls) # appels cumulés
Tiers disponibles
| Tier | Source | Certification | Latence |
|---|---|---|---|
| Platinum | Ordinateur quantique réel | Device-Independent | < 1ms pool |
| Silver | DRBG seedé quantique | Seed quantique | < 1ms |
| Ivory | Simulateur Toeplitz | Haute qualité stat. | < 0.1ms |
Vérification des certificats Platinum
Chaque réponse Platinum inclut un certificat d'attestation vérifiable sans contacter CERTROPI.
# Vérification automatique à la génération
result = client.platinum.generate(
n_bits=256,
verify=True,
pubkey_path="certropi_public.pem",
)
# Vérification manuelle depuis un dict
from alea_q import verify_certificate_dict
S = verify_certificate_dict(result.certificate, pubkey_path="certropi_public.pem")
print(f"Certificat valide — S={S:.4f}")
# Vérification depuis un fichier JSON
from alea_q import verify_certificate
verify_certificate("cert.json", pubkey_path="certropi_public.pem")
Récupérer la clé publique CERTROPI :
curl https://api.alea-q.com/v1/platinum/pubkey -o certropi_public.pem
# ou
python -c "
from alea_q import AleaQClient
client = AleaQClient()
open('certropi_public.pem', 'wb').write(client.platinum.get_public_key())
"
Context manager
with AleaQClient(api_key="sk_plat_xxx") as client:
result = client.platinum.generate(n_bits=256)
Client asynchrone
import asyncio
from alea_q import AsyncAleaQClient
async def main():
async with AsyncAleaQClient(api_key="sk_plat_xxx") as client:
result = await client.platinum.generate(n_bits=256)
print(result.as_hex())
asyncio.run(main())
Streaming Silver (temps réel)
Flux continu d'entiers en WebSocket — utile pour alimenter en continu un consommateur d'entropie (HSM, pool applicatif, génération de clés en masse) sans refaire une requête HTTP par lot.
Nécessite l'extra stream : pip install "alea-q[stream]"
import asyncio
from alea_q import AsyncAleaQClient
async def main():
async with AsyncAleaQClient(api_key="sk_silv_xxx") as client:
count = 0
async for value in client.silver.stream(bits_per_second=100_000, n_bits=256):
print(value)
count += 1
if count >= 1000:
break # ferme proprement le flux côté client
asyncio.run(main())
Le débit est exprimé en bits/seconde, pas en nombre d'entiers — cohérent
avec la facturation volumétrique du service et indépendant de n_bits
(la largeur de chaque entier livré). Le flux reste ouvert tant que la
boucle async for n'est pas interrompue (break) et que la clé reste
valide — une révocation de clé en cours de flux le referme immédiatement.
Gestion des erreurs spécifiques au streaming :
from alea_q import AuthenticationError, InsufficientBalance, QuotaExceeded
async def main():
async with AsyncAleaQClient(api_key="sk_silv_xxx") as client:
try:
async for value in client.silver.stream(bits_per_second=100_000):
...
except AuthenticationError:
print("Clé invalide ou révoquée en cours de flux")
except InsufficientBalance:
print("Solde prépayé épuisé — recharger via le support")
except QuotaExceeded:
print("Capacité de débit disponible dépassée — réessayer plus tard")
asyncio.run(main())
Le client synchrone (AleaQClient) ne propose pas le streaming — le
flux est intrinsèquement asynchrone, utiliser AsyncAleaQClient.
Livraison chiffrée post-quantique (Platinum, recipient_pk)
Pour ne jamais faire transiter la valeur générée en clair, generate()
accepte (Platinum uniquement) un recipient_pk — une clé publique
ML-KEM-768 que vous générez localement. La valeur revient alors
enveloppée (ML-KEM + AES-256-GCM + signature SLH-DSA) dans .envelope
au lieu d'être renvoyée en clair dans .value :
import base64
from alea_q import mlkem_decaps
# my_mlkem_dk / my_mlkem_pubkey_hex : paire de clés ML-KEM-768 générée
# localement (ex. via pyca/cryptography — jamais transmise au serveur).
result = client.platinum.generate(n_bits=256, recipient_pk=my_mlkem_pubkey_hex)
if result.envelope:
# result.value est vide — la valeur réelle est dans
# result.envelope["encrypted_payload"], chiffrée pour my_mlkem_pubkey_hex.
# La décapsulation reste locale : le serveur ne voit jamais votre clé
# privée ni le secret déchiffré.
#
# Nécessite l'extra 'verify' : pip install 'alea-q[verify]'
#
# ATTENTION : les champs de l'enveloppe (ciphertext, encrypted_payload,
# nonce, signature, certropi_pk) sont en BASE64.
ciphertext = base64.b64decode(result.envelope["ciphertext"])
shared_key = mlkem_decaps(my_mlkem_dk, ciphertext, param_set="ML_KEM_768")
# shared_key (32 octets) est la clé AES-256-GCM utilisée pour chiffrer
# result.envelope["encrypted_payload"] (nonce en base64 lui aussi) —
# déchiffrement AES-GCM restant à la charge de l'appelant, non fourni
# par ce SDK à ce jour.
Gestion des erreurs
from alea_q import AleaQClient
from alea_q.exceptions import BackendUnavailable, AuthenticationError, InsufficientBalance
import time
client = AleaQClient()
try:
result = client.platinum.generate(n_bits=256)
except BackendUnavailable as e:
print(f"QPU indisponible — réessayer dans {e.retry_after}s")
time.sleep(e.retry_after or 300)
except AuthenticationError:
print("Clé API invalide")
except InsufficientBalance:
print("Solde prépayé épuisé (mode pay-as-you-go) — recharger via le support")
Configuration
| Variable d'env | Description | Défaut |
|---|---|---|
ALEA_Q_API_KEY |
Clé API | — |
ALEA_Q_BASE_URL |
URL de base de l'API | https://api.alea-q.com |
ALEA_Q_TIMEOUT |
Timeout HTTP en secondes | 60 |
ALEA_Q_MAX_RETRIES |
Nombre de retries automatiques | 2 |
ALEA_Q_PUBKEY_PATH |
Chemin clé publique CERTROPI | certropi_public.pem |
https://api.certropi.com est un alias B2B de la même API — les deux
domaines répondent de manière identique, ALEA_Q_BASE_URL accepte
indifféremment l'un ou l'autre.
Développement
pip install -e ".[dev]"
# Suite de tests (mock HTTP via respx — aucun accès réseau requis)
pytest
# Avec couverture
pytest --cov=alea_q --cov-report=term-missing
# Tests contre l'API réelle (marqués `smoke`, nécessitent ALEA_Q_API_KEY
# et un accès réseau — exclus par défaut)
pytest -m smoke
Licence
Propriétaire — CERTROPI © 2026
Download files
Download the file for your platform. If you're not sure which to choose, learn more about installing packages.
Source Distribution
Built Distribution
Filter files by name, interpreter, ABI, and platform.
If you're not sure about the file name format, learn more about wheel file names.
Copy a direct link to the current filters
File details
Details for the file alea_q-0.2.1.tar.gz.
File metadata
- Download URL: alea_q-0.2.1.tar.gz
- Upload date:
- Size: 25.1 kB
- Tags: Source
- Uploaded using Trusted Publishing? No
- Uploaded via:
twine/7.0.0 CPython/3.11.9
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
3ec65990f021cab3548025802a4c35ef859c0f966fd09ccd76df047451cdf7b6
|
|
| MD5 |
3417c6fdb41d7f73bcd41311e02e1de0
|
|
| BLAKE2b-256 |
ec33536f8fb0fc84985e8353017e62692bc04564d4b6bab9d54cbe3aff5a84ae
|
File details
Details for the file alea_q-0.2.1-py3-none-any.whl.
File metadata
- Download URL: alea_q-0.2.1-py3-none-any.whl
- Upload date:
- Size: 22.9 kB
- Tags: Python 3
- Uploaded using Trusted Publishing? No
- Uploaded via:
twine/7.0.0 CPython/3.11.9
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
51334caa98e0e6f7b7cbd38f18953f4764fa901f514fd1ec9233b7a15bdaa674
|
|
| MD5 |
f741c1633d1af77e0f54cb3e42fead04
|
|
| BLAKE2b-256 |
1bdbd1a21e89c376604212edc0fd78a1d910b3fdc306842fbe9f4a7200b3c65d
|