Chiffrer le code

protect et run, l'expiration, un verrou à deux facteurs plus fort, et les artefacts portables qui n'ont pas besoin de verrouillage machine du tout.

magiclock protect transforme un fichier .py en .pya — un conteneur chiffré et verrouillé — sans compilateur et sans jamais téléverser votre source où que ce soit. magiclock run l'exécute.

Utilisation de base

shell
# First run: signs you in and activates this machine, then encrypts.
# Every encrypt after that is instant and non-interactive.
magiclock protect app.py            # -> app.pya
magiclock run app.pya

# Point at a directory to protect a whole project tree recursively
# (.venv/venv/__pycache__/.git/dist/build are skipped automatically).
magiclock protect src/

Les fichiers .pya sont des fichiers ordinaires que vous pouvez committer, copier ou livrer par les canaux que vous utilisez déjà pour distribuer votre application — le chiffrement voyage avec le fichier.

Comment ça fonctionne

Un .pya est un petit conteneur versionné enveloppant une enveloppe chiffrée. magiclock run app.pya le déchiffre en mémoire, installe un hook d'import pour tout ce qu'il importe, puis l'exécute — rien n'est jamais réécrit sur disque en clair. Comme le bytecode marshalé qu'il contient est lié à la version de CPython qui l'a chiffré, un .pya produit sur Python 3.12 ne se chargera pas sur 3.13 ; relancez protect après avoir mis à niveau votre interpréteur.

Supprimer le fichier en clair

shell
magiclock protect app.py --remove   # encrypt, then delete app.py

Expiration : artefacts à durée limitée et à autodestruction

Ces options inscrivent une expiration dans l'artefact chiffré lui-même — indépendamment de votre licence — après laquelle il refuse de se déchiffrer :

shell
magiclock protect app.py --expires-in 30d        # stops decrypting in 30 days
magiclock protect app.py --expires-at 2026-12-31  # stops decrypting on a date
magiclock protect app.py --trial                  # fixed 48-hour self-destruct — for demos and evaluations

--trial, --expires-in et --expires-at sont mutuellement exclusifs — choisissez-en un par fichier.

Plus fort : verrou à deux facteurs (machine + phrase secrète)

Par défaut, un artefact n'a besoin que d'être sur la bonne machine pour se déchiffrer. Ajoutez une phrase secrète comme second facteur :

shell
magiclock protect app.py --lock-passphrase
# prompts for a passphrase (or reads $MAGICLOCK_PASSPHRASE non-interactively)

magiclock run app.pya --passphrase

Portable : aucun verrouillage machine

Il arrive qu'un artefact doive s'exécuter sur une machine que vous n'avez pas activée — la machine d'un client, une machine que vous ne contrôlez pas. Le mode portable abandonne le verrouillage machine et se déverrouille à la place avec un secret partagé — plus faible, mais distribuable :

shell
# Passphrase-protected, no machine lock:
magiclock protect app.py --no-bind-machine --passphrase
magiclock run app.pya --passphrase

# Or hand out a generated key instead of a passphrase:
magiclock protect app.py --no-bind-machine --emit-key
magiclock run app.pya --key <the-printed-key>

--lock-passphrase et les options portables (--no-bind-machine, --passphrase, --emit-key) sont mutuellement exclusifs — un artefact est soit verrouillé sur une machine (avec éventuellement une phrase secrète en second facteur), soit portable (déverrouillé par phrase secrète/clé au lieu de l'identité de la machine), mais pas les deux.

Pour la CI et les exécutions scriptées, la phrase secrète comme la clé portable peuvent venir de l'environnement plutôt que d'une invite :

shell
export MAGICLOCK_PASSPHRASE=...     # for --lock-passphrase or portable --passphrase artifacts
export MAGICLOCK_DECRYPT_KEY=...    # alternative to `run --key` for --emit-key artifacts
magiclock run app.pya

La suite