Gotchas
Resources · cheat sheet
The traps that cost hours the first time. Scan the table, apply the fix. Each row links to the playbook page that explains it.
At a glance
Section titled “At a glance”| Gotcha | What goes wrong | The fix |
|---|---|---|
APP_DEBUG=true off local | Stack traces and the full env leak to visitors in production | APP_DEBUG=false on staging and production; APP_ENV=production. Only local gets APP_DEBUG=true. |
Shared APP_KEY across environments | One leaked key compromises every encrypted value and signed cookie everywhere | Generate a unique APP_KEY per environment. Leave it blank in templates; php artisan key:generate fills local, the first deploy generates it on the server. |
Regenerating a set APP_KEY | Re-running key:generate invalidates all existing encrypted data and sessions | Run key:generate only if APP_KEY is empty. Never re-key a live environment. |
3-byte utf8 database | CodeCanyon apps storing emoji / multi-byte content throw collation errors | Create the schema as utf8mb4 / utf8mb4_unicode_ci from the start. |
composer install over a customized vendor/ | It restores vanilla vendor files and silently wipes your overlay edits | Run the restore script after every composer install, deploy, or vendor update — before you trust the app. |
| Destructive migration with no backup | DROP COLUMN / DROP TABLE / TRUNCATE destroys customer data on deploy | Clear the Atlas gate first — STOP on DS102/DS103. Back up + get approval + prove on staging. TRUNCATE = manual approval only. |
| Secrets in a server sync | .env, *.key, *.pem, or credentials get committed into git | Screen git status before staging; never commit secrets. If one was pushed: revert immediately and rotate the credential. |
| Cloudflare SSL = Flexible | Redirect loops and an insecure edge↔origin hop behind Cloudflare | Set SSL mode to Full (Strict) + enable Always Use HTTPS. |
| Cloudflare Rocket Loader ON | Defers/reorders JS — breaks CSRF injection, Livewire/Alpine/Vite scripts | Leave Rocket Loader OFF for Laravel. |
| Editing a vendor migration | The next vendor update overwrites your change | Never touch it — add columns via an additive _zaj migration (add_{cols}_to_{table}_zaj.php) with a ZAJ: comment; the Atlas diff catches a clash — see the customization decision. |
The .env quick rules
Section titled “The .env quick rules”Per-environment values that must differ — never copy one environment’s .env to another:
| Key | local | staging | production |
|---|---|---|---|
APP_ENV | local | staging | production |
APP_DEBUG | true | false | false |
APP_KEY | unique (key:generate) | unique (per env) | unique (per env) |
Plus: double-quote every secret value, ship .env.example with fail-loud placeholders (blank or obviously fake) so a missing value crashes immediately instead of booting against the wrong database, and never stage a real .env.
The vendor-overlay rule, spelled out
Section titled “The vendor-overlay rule, spelled out”Any time vendor/ is rewritten — a fresh composer install, a deploy, or a vendor update — your resources/vendor-customizations/ overlay is gone until the restore script re-applies it.
composer installphp Admin-Local/.../restore-vendor-customizations.php# Expected: a per-package "Restored N file(s)" summarySource playbook pages
Section titled “Source playbook pages” Env templates (full) Three-environment template set, per-env APP_KEY, APP_DEBUG matrix.
Local database (full) The utf8mb4 schema and pointing .env at it.
Cloudflare CDN (full) Full (Strict) SSL, HSTS, and Rocket Loader OFF for Laravel.
Restore customizations (full) Re-applying the overlay after composer install.