gracious/doctrine-encryption-bundle
A Symfony bundle that adds transparent encryption for Doctrine entity fields, helping protect sensitive data at rest with minimal changes to existing mappings and persistence code.
Framing correction (unchanged): Despite the ticket describing this as a "Laravel/PHP package," gracious/doctrine-encryption-bundle is a Symfony bundle that registers a Doctrine DBAL custom type. It has no Laravel service provider, no Eloquent integration, and no Composer extra.laravel config. Any evaluation must be scoped as "Symfony/Doctrine encryption type, usable in Laravel only via laravel-doctrine/orm."
What 5.0.0 changes. The release content is a single line: "Make compatible with Symfony 7.x." Assessment impact is narrow but real — it resolves one of the open compatibility questions, and it introduces a version-constraint hazard. It changes nothing about the crypto implementation, key handling, or the dependency's governance profile. A release whose entire content is a constraint bump also implies no security fixes landed in this version.
Architecture fit. The design pattern remains sound and conventional: a DBAL custom type intercepts convertToDatabaseValue / convertToPHPValue, so encryption is transparent to entities and repositories. This is the right layer for field-level encryption at rest — it keeps crypto out of domain code and composes with Doctrine's existing type system. It fits cleanly only where Doctrine is the persistence layer. Nothing in 5.0.0 alters this.
Integration feasibility. Moderate-to-low in a Laravel context, with a new constraint wrinkle:
composer.json), those stacks are pinned to 4.x or must upgrade Laravel.dbal.types in config/doctrine.php, every encrypted column declared with the custom type name.TEXT/BLOB (schema migration unavoidable); the bundle's key source must be reachable from Laravel's container (typically a Symfony parameter/env var needing a bridge).Technical risk. High and unchanged — driven by the security domain, not code complexity:
secretbox vs. OpenSSL AES-GCM)? Is it AEAD (authenticated) or raw encryption? Is the nonce random per write and where is it stored? Is a KDF applied to the configured key, or is a raw key used directly? Is there any key rotation or re-encryption path?WHERE-filtered, sorted, LIKE-searched, or uniquely indexed. Any lookup requirement on an encrypted field needs a blind-index sidecar.Key questions for the maintainer (revised):
null vs. exception).Stack fit. Two distinct paths, chosen explicitly rather than by default:
encrypted cast and Crypt facade backed by a maintained, widely-deployed library. Reaching for a 5-star Symfony bundle here is negative value, and 5.0.0 does not change that.laravel-doctrine/orm). Still plausible, but 5.0.0 makes the version matrix the deciding factor. Confirm your Laravel major first: Laravel 11+ (Symfony 7 components) can take 5.x; Laravel 10 and below will be stuck on 4.x. Where Doctrine is mandatory, compare against a thin in-house DBAL type wrapping Laravel's own Crypt/Encrypter — same transparency, a dependency you already trust and can patch, and no Symfony-major coupling.Migration path. Unchanged — encryption rollout is a data migration, not a config change:
TEXT (do not alter in place).Compatibility. 5.0.0 sharpens this from a checklist item to a gating step. Pin exact versions. Verify: required Symfony component major against your resolved symfony/* set; DBAL major alignment (DBAL 3→4 changed custom type registration semantics); that the bundle's type name does not collide with existing types; and that DBAL type conversion does not strip binary payloads. Treat the 4.x → 5.x jump as a breaking change until proven otherwise — a major bump for a compatibility-only change tells you this project bumps majors for constraint changes.
Sequencing. Start with one low-sensitivity column in a non-production environment. Prove: round-trip correctness, failure behavior on corrupted ciphertext, payload size impact, and query-plan impact. Only then expand to regulated fields (PII, tokens, health data). If you are on Laravel 10 or below and cannot upgrade, stop here — the Symfony 7 requirement converts this from "adopt with caution" to "fork or close."
Maintenance. Still the dominant cost. A single-maintainer package at 0.145 with no dependents remains an unhedged dependency for a security-critical path. 5.0.0 is a modest positive signal — the project is alive and tracking upstream framework releases — but a one-line release with no upgrade notes, no changelog detail, and no test/CI evidence attached is a weak liveness signal, not a governance improvement. Given MIT licensing, the realistic posture is unchanged: vendor or fork it, own the crypto code, treat upstream as reference rather than runtime dependency. Budget for periodic review of the fork as PHP and DBAL versions advance. Note that the fork also insulates you from the next forced major.
Support. No SLA, no security disclosure policy visible, GitHub issues as the only channel. 5.0.0 does not add a changelog discipline, security policy, or release cadence. For a component where a bug means either data loss or a breach, that is a governance gap — not a preference.
Scaling. Two concrete costs, both unaffected by 5.0.0: (a) per-row CPU for encrypt/decrypt on every hydration, linear and material on large result sets or batch reports; (b) loss of index usage on encrypted columns, turning previously indexed lookups into full scans. Expect ~33%+ storage inflation from base64 encoding plus nonce/tag overhead — resize columns before backfill, not after.
Failure modes to design for explicitly:
composer update on a security-sensitive path can pull a version with unreviewed changes. Pin exact versions and review every major as a security review, or fork.Ramp-up. The API surface is small, so engineering onboarding is hours — not the bottleneck. The real ramp-up is organizational: key management, rotation runbooks, break-glass decryption procedure, and on-call guidance for decrypt exceptions. Estimate that work in weeks, and treat it as the gating item.
Recommendation (updated). Do not adopt as-is for regulated data. 5.0.0 is a compatibility release, not a security or capability release — it does not close the audit, rotation, or non-determinism gaps. If Doctrine is mandatory and you are on Laravel 11+, fork and own a DBAL type built on a vetted crypto library; if you are on Laravel 10 or below, the Symfony 7 requirement makes this a non-starter without a Laravel upgrade you likely cannot justify for this dependency. If Eloquent is the stack, close this ticket and use Laravel's native encrypted cast.
How can I help you explore Laravel packages today?