Expand description
Reading what a PHP application encrypted — PhpEncrypter.
// In a provider, while the ported rows are still in the PHP envelope.
app.instance(Encryption::new(
Arc::new(PhpEncrypter::new(keys)),
Arc::new(HmacSigner::new(keys)),
));Not a preference. A ported application’s database already holds columns
that PHP wrote, and they have to stay readable — so this reads and writes
the {iv, value, mac} envelope PHP MVC frameworks produce, byte for byte,
against the same APP_KEY.
§The format
base64( json( { "iv": base64(iv), "value": base64(ciphertext), "mac": hex(mac) } ) )AES-256-CBC with PKCS#7 padding, and an HMAC-SHA256 over the base64 forms of the IV and the ciphertext concatenated — not over the raw bytes, which is the detail every reimplementation gets wrong and then cannot explain.
§It is encrypt-then-MAC, and the MAC is checked first
The PHP implementation checks the MAC before it decrypts, and so does this. The order is not a preference either: CBC without an authenticated MAC first is a padding oracle, and a padding oracle recovers the plaintext without the key.
§Why this is not a Cipher variant
Cipher selects the AEAD inside Rainier’s own envelope,
which names its algorithm, carries its key id and is URL-safe. The PHP
format is a different envelope with none of those properties. Making it a
cipher variant would mean one Encrypter producing two incompatible
payload shapes depending on a setting, which is exactly the ambiguity the
self-describing envelope exists to avoid.
§Use it to migrate, not to stay
Everything Rainier’s own AeadEncrypter has that
this does not: a key id in the payload, so rotation is possible without
re-encrypting; an algorithm name, so the cipher can change; AEAD, so there
is one primitive to get right instead of two composed in the correct order.
The shape that works is the same one legacy password hashes use: read with this, write with the native encrypter, and let the rows convert as they are touched.
Structs§
- PhpEncrypter
- The
{iv, value, mac}envelope PHP MVC frameworks write, in Rust.
Enums§
- Crypt
Scheme - Which payload envelope this application writes.