Skip to content
prod e051e98
Browse

3 · Restore customizations

Objective — put your work back on top of the new vendor base: re-apply the vendor-customizations overlay, confirm your ZajModules and schema additions are intact, then prove nothing was lost before deploying.

A vendor update is only safe if your customizations come back. Three kinds of change live in three different places, and they survive the update differently:

  • ZajModules (your new features, in their own packages) — the vendor update never touches them. They survive automatically; you just confirm they’re still loaded.
  • Your schema additionszajm_ module tables and the _zaj columns you added to vendor tables. Your _zaj migrations already ran (recorded in the migrations table), so they’re skipped on update and your columns/tables persist untouched.
  • The vendor-customizations overlay (your edits to vendor files) — this is the fragile one. composer install in the previous step reverted vendor/ to vanilla, so the overlay must be re-applied by the restore script. That’s the work of this page.
flowchart LR
V["vanilla vendor/<br/>after composer install"] --> S["restore script<br/>copies overlay → vendor/"]
O["_CUSTOMIZATIONS log<br/>MOD-NNN registry"] --> S
S --> C["re-run each patch's<br/>own verification"]
C --> D["deploy staging,<br/>then production"]

1. Review the MOD-NNN log before restoring

Section titled “1. Review the MOD-NNN log before restoring”

The log is the registry of every vendor file you patched. After an update, walk it once: a patch may now be redundant if the vendor fixed the underlying bug, or it may need re-checking against the new vendor code.

  1. Walk each MOD-NNN row and confirm it’s still required against the new vendor base.

    • ✅ Each patch is marked still-needed or now-redundant; redundant patches are queued for removal from the overlay.

Keep the list short on purpose. If the log is growing past MOD-003, MOD-004, that’s a signal to refactor those edits into event-driven ZajModules instead — fewer vendor-file patches means fewer things to restore on the next update.

The restore script reads your overlay and copies every customized file back over its now-vanilla vendor counterpart. Run it after composer install — every time vendor/ is rewritten.

  1. Run the restore script and read its per-package summary.

    Terminal window
    php Admin-Local/.../restore-vendor-customizations.php
    # Expected: "Found N customized package(s)" then a per-package "Restored N file(s)" summary
    • ✅ The summary lists each customized package and the count of files it restored.

The script scans resources/vendor-customizations/, finds each customized package folder, and recursively copies its files onto the matching package inside vendor/. A package missing from vendor/ (removed or renamed in this release) is skipped with a warning rather than failing the run — which is itself a useful signal that a vendor file you patched no longer exists.

3. Confirm your ZajModules and schema additions survived

Section titled “3. Confirm your ZajModules and schema additions survived”

These should be untouched — but “should be” isn’t “verified”. A quick check confirms your module tables (zajm_*) are present and your _zaj columns (added to vendor tables) survived the update.

  1. List your module-owned tables — your data tables are zajm_*; the registry is zajmanager_*.

    Terminal window
    php artisan optimize:clear
    php artisan tinker --execute="
    collect(DB::select('SHOW TABLES'))
    ->pluck('Tables_in_'.env('DB_DATABASE'))
    ->filter(fn(\$t) => str_starts_with(\$t, 'zajm_') || str_starts_with(\$t, 'zajmanager_'))
    ->each(fn(\$t) => print(\$t.PHP_EOL));
    "
    # Expected: your zajm_ module tables print — none missing after the update
    • ✅ Every zajm_ table you expected prints, and your ZajModule features load without error.
  2. Confirm your _zaj columns survived — they live on vendor tables and are found by the ZAJ: marker comment in the live schema.

    Terminal window
    php artisan tinker --execute="
    collect(DB::select(\"SELECT CONCAT(table_name,'.',column_name) c FROM information_schema.columns
    WHERE table_schema = DATABASE() AND column_comment LIKE 'ZAJ:%'\"))
    ->each(fn(\$r) => print(\$r->c.PHP_EOL));
    "
    # Expected: every ZAJ:-marked column you added (e.g. users.whitelabel_domain) prints
    • ✅ Each _zaj column you added still appears with its ZAJ: marker intact.

A restore that reports “files copied” still needs a behavioural check — confirm the patched logic produces the right result, not just that the bytes are in place.

  1. Re-run each patch’s own verification. For the MOD-001 migration-scanner example, confirm the file count now matches the database count.

    Terminal window
    php artisan tinker --execute="
    \$files = count(File::glob(database_path('migrations/*.php')));
    \$files += count(File::glob(database_path('migrations-zaj/*.php')));
    \$files += count(File::glob(base_path('packages/ZajModules/*/src/Database/Migrations/*.php')));
    \$db = DB::table('migrations')->count();
    echo 'Files: '.\$files.' | DB: '.\$db.' | Diff: '.(\$files - \$db);
    "
    # Expected: Diff: 0 (or close to 0)
    • ✅ The diff is 0 (or near it), confirming the patched scanner sees every migration path again.
  2. Smoke-test the critical paths before trusting the update.

    PathConfirms
    Login + dashboardThe core app boots on the new base
    Your custom featuresThe overlay + ZajModules work end-to-end
    Payments (Stripe test mode)Billing survived the update
    Email (Mailtrap / logs)Notifications still fire
    • ✅ Every critical path works on the updated, restored app.

Never send a vendor update straight to production. Ship to staging, watch it, and only promote once it’s stable — running the same restore + schema-diff confidence checks at each hop.

  1. Promote to staging and verify the schema synced.

    Terminal window
    git checkout develop && git push origin develop
    dep deploy staging
    atlas schema diff --from "$ATLAS_LOCAL_URL" --to "$ATLAS_STAGING_URL"
    # Expected: deploy succeeds; the diff afterwards reports "Schemas are synced, no changes"
    • ✅ Staging deploys, the restore ran in the deploy, and the post-deploy Atlas diff reports synced.
  2. After the soak window, promote to production and tag the release.

    Terminal window
    git checkout production && git merge develop && git push origin production
    dep deploy production
    git tag vY.Y.Y && git push origin vY.Y.Y
    atlas schema diff --from "$ATLAS_STAGING_URL" --to "$ATLAS_PRODUCTION_URL"
    # Expected: production deploys; the final diff reports "Schemas are synced"
    • ✅ Production runs the new version, the release is tagged, and staging/production schemas are synced.

Do not mark this step done until every box below is checked.

  • 👤 MOD log reviewed — each MOD-NNN patch confirmed still-needed (or queued for removal) against the new vendor base.
  • 🤖 Overlay restoredrestore-vendor-customizations.php ran after composer install and reported each package restored.
  • 🤖 ZajModules + schema intact — packages load; every expected zajm_ table and ZAJ:-marked _zaj column is present.
  • 🤖 Patches verified — each patch’s own check passes (e.g. migration Diff: 0); critical paths smoke-tested.
  • 🔀 Shipped staging-first — deployed to staging, soaked, then promoted to production and tagged vY.Y.Y; Atlas reports synced.

Continuous Develop & Deploy — the everyday loop now that the update is live: code, test, ship, and sync server changes back to git.