nowo-tech/vault-bundle
A Symfony bundle from Nowo Tech that integrates a secure vault for managing and retrieving application secrets, with a simple configuration-driven setup for PHP projects. It helps centralize credential storage and keep sensitive values out of code and configuration files.
This is a Symfony bundle, not a Laravel package. Before investing time, confirm you can actually consume it: it targets Symfony 8.1 (per the README badge), uses Twig form themes and Doctrine ORM/ODM via nowo-tech/doctrine-encrypt-bundle. In a Laravel app you would be pulling in symfony/form, symfony/twig-bridge, and Doctrine just to render its views — usually not worth it. It fits a Laravel shop best when you have a separate Symfony service (or a Symfony-based admin panel) that owns the vault, and Laravel talks to it over HTTP or a shared DB.
Minimal path in a Symfony host app:
composer require nowo-tech/vault-bundle nowo-tech/doctrine-encrypt-bundle
NowoVaultBundle in config/bundles.php.doctrine-encrypt-bundle — this is the one secret that cannot be regenerated. Put it in your secret manager, not .env.doctrine:migrations:migrate) so the vault item tables exist.vault/item_form.html.twig and vault/share.html.twig — those are the two surfaces you will actually touch, plus the form types they render.If you are on Laravel only, read the "Gotchas" section first — the integration cost is real.
Vault items as the unit of work. Persist secrets as vault items, never as ad-hoc model columns. One item type per shape of secret; the form type is the contract. item_form.html.twig keeps a per-item-type layout, so adding a new item type means: new entity/type class, new form type, and (optionally) a template block — the generic loop at the end of the template picks up anything you didn't hand-place.
Sharing is the day-to-day feature. The share flow is a token-scoped, unauthenticated view of a single item. Pattern: authenticated owner creates a share → store the token hash, not the token → recipient opens the public URL → bundle renders share.html.twig → revoke by deleting the share row. Treat share creation as an auditable action in your app (log who shared what, when).
Views render through the child loop (v1.8.2, REQ-TWIG-003). Both share.html.twig/_share_form_fields.html.twig and item_form.html.twig now iterate {% for child in form %} with not child.rendered + form_row(child) and a grid column per child. Practical consequence: any field you add to the form type renders automatically — you no longer need to edit the template to add a field, and you should not hand-place form_row() calls for new fields unless you need custom ordering. If you have local overrides of these templates from before 1.8.2, re-sync them; a stale override that hand-places _token or hard-codes fields will now diverge from the bundle's behaviour.
Integration tips.
templates/bundles/NowoVaultBundle/vault/item_form.html.twig. Clear cache after.config/vault.php, no Artisan commands. Don't plan on php artisan vendor:publish for its views. Laravel developers typically burn a day discovering this.doctrine-encrypt-bundle (bumped to 2.8.0 here) encrypts at the field level. Lose or rotate the key without a re-encrypt migration and your vault contents are unrecoverable. Test key rotation in staging before you ever need it._token is now emitted by the loop. If a local template override still hand-places _token, you get a duplicate field and a confusing CSRF failure. Delete the manual widget.doctrine/mongodb-odm 2.17.2, mongodb-odm-bundle 5.6.1, form-kit-bundle 2.12.0, phpstan tooling) plus a view refactor. Nothing breaking, but the transitive doctrine-encrypt-bundle 2.5.0 → 2.8.0 jump is worth reading its changelog before you deploy, since it sits directly under your encrypted fields. Pin exact versions and run a decrypt/read smoke test after upgrading.UPGRADING.md#to-182 if you do..env.test, Spec Kit inventory) moved a lot in this release; docs-only churn, safe to ignore for upgrade decisions.How can I help you explore Laravel packages today?