D28 — Deploy + Live Smoke Stage 2 Execution Report
D28 — Deploy + Live Smoke Stage 2 Execution Report
Date: 2026-05-10 | Agent: claude-go (VPS SSH + git + docker) Prompt:
knowledge/dev/laws/dieu28-trien-khai/prompts/d28-deploy-and-live-smoke-prompt-review.mdrev5 Dispatch:RUN_STAGE=2_DEPLOY_AND_SMOKEStage 1 baseline:knowledge/dev/laws/dieu28-trien-khai/reports/d28-deploy-and-live-smoke-stage1-preflight-report.md(rev3 CLEAN, TS=1778397192, preflight_status=PASS) Approval phrase: VERIFIED EXACT MATCH Revision: 1 — first Stage 2 execution under rev5
Tier
phase=DEPLOY_AND_SMOKE
run_stage=2_DEPLOY_AND_SMOKE
Phase 1A — Approval + Stage 1 binding + STAGE1_* load (rev4 + rev5)
approval_phrase_received_verbatim=true
approval_phrase_verified=true
stage1_report_read=true
stage1_preflight_status=PASS
stage1_status_field=AWAITING_DEPLOY_APPROVAL
stage1_rev5_clean_verified=true
service_name_rule_applied=true
undeclared_substitution_used=false
drift_detected=false
stage1_values_loaded=true
STAGE1_NEW_IMAGE_TAG=nuxt-ssr-local:d2db418
STAGE1_BACKUP_IMAGE_TAG=nuxt-ssr-local:pre-d28-rollback-1778397192
STAGE1_COMPOSE_BACKUP_PATH=/opt/incomex/docker/docker-compose.yml.pre-d28-1778397192
STAGE1_CURRENT_PRODUCTION_IMAGE=nuxt-ssr-local:s174
stage2_used_stage1_backup_tag=true
stage2_used_stage1_compose_backup_path=true
stage2_used_stage1_new_image_tag=true
stage2_used_stage1_current_production_image=true
stage2_recomputed_backup_timestamp=false
Approval phrase 3-field exact-match verification:
| Field | From approval phrase | From Stage 1 report | Match |
|---|---|---|---|
| NEW_TAG | nuxt-ssr-local:d2db418 | nuxt-ssr-local:d2db418 | ✓ |
| BACKUP_TAG | nuxt-ssr-local:pre-d28-rollback-1778397192 | nuxt-ssr-local:pre-d28-rollback-1778397192 | ✓ |
| COMPOSE_BACKUP_PATH | /opt/incomex/docker/docker-compose.yml.pre-d28-1778397192 | /opt/incomex/docker/docker-compose.yml.pre-d28-1778397192 | ✓ |
Phase 1B — Drift re-check (rev3 + rev5 — service name "nuxt")
All Stage 1 conditions still hold:
git_status_porcelain=<empty>
source_tree_clean=true
head_includes_d2db418=true
head_includes_0947613=true
docker_compose_ps_nuxt_image=nuxt-ssr-local:s174 (matches STAGE1_CURRENT_PRODUCTION_IMAGE)
compose_image_line=130: image: nuxt-ssr-local:s174 (matches Stage 1 0E)
compose_image_match_count=1
backup_tag_pre_check=CLEAR (no nuxt-ssr-local:pre-d28-rollback-1778397192 yet)
backup_path_pre_check=CLEAR (no /opt/incomex/docker/docker-compose.yml.pre-d28-1778397192 yet)
build_verify_pass_report_present=true
stage1_drift_recheck=PASS
No drift detected. Mutation phase authorized.
Phase 1C — Backup current image (FIRST mutation)
docker_tag_command=docker tag nuxt-ssr-local:s174 nuxt-ssr-local:pre-d28-rollback-1778397192
docker_tag_exit=0
backup_image_tag_created=true
backup_image_tag=nuxt-ssr-local:pre-d28-rollback-1778397192
backup_image_id=072ccd861f30 (alias of nuxt-ssr-local:s174)
no_overwrite_backup_tag=true (CLEAR pre-check confirmed via 0I + Phase 1B)
Phase 1D — Build production image (log-safe branching)
build_command=docker build -f web/Dockerfile -t nuxt-ssr-local:d2db418 web/
build_log_path=/tmp/d28-deploy-build-1778398541.log (chmod 600, removed at end)
build_exit=0
build_log_size_bytes=86280
new_image_created=true
new_image_tag=nuxt-ssr-local:d2db418
new_image_id=105bd197347c
new_image_removed_on_abort=N/A (build succeeded)
old_image_preserved=true (s174 + pre-d28-rollback-1778397192 ID 072ccd861f30 both intact post-build)
Secret-scan classification (SCAN=FAIL_FILENAME_FALSE_POSITIVE)
build_log_secret_scan=FAIL_FILENAME_FALSE_POSITIVE
keyword_hits:
token=0
secret=0
bearer=0
password=2
authorization=0
total_hit_lines=2
filename_pattern_hit_lines=2 (forgot-password / reset-password / change-password / *.mjs / *.vue / _nuxt/ / .output/ / pages/)
non_filename_hit_lines=0
url_on_password_line=0
env_style_PASSWORD_equals=0
json_password_assignment_shape=0
jwt_eyJ_pattern=0
classification_basis=Vite/Rollup build summary table rows for forgot-password page chunk(s) — content-hash fingerprint in chunk filename triggers long-literal regex but not an actual leak shape
build_log_tail_printed=false (forbidden under SCAN=FAIL per rev3+rev4)
build_log_removed=true
Phase 1E — Compose patch (rev4 — diff log-safe)
compose_backup_cp_command=cp /opt/incomex/docker/docker-compose.yml /opt/incomex/docker/docker-compose.yml.pre-d28-1778397192
compose_backup_cp_exit=0
compose_backup_path=/opt/incomex/docker/docker-compose.yml.pre-d28-1778397192
compose_backup_size_bytes=5068
no_overwrite_backup_file=true (CLEAR pre-check confirmed via 0J + Phase 1B)
sed_patch_command=sed -i "s|image: nuxt-ssr-local:s174$|image: nuxt-ssr-local:d2db418|" /opt/incomex/docker/docker-compose.yml
sed_exit=0
pre_patch_line=130: image: nuxt-ssr-local:s174
post_patch_line=130: image: nuxt-ssr-local:d2db418
compose_file_modified=true
compose_patch_line_count=1
compose_diff_path=/tmp/d28-compose-diff-<TS_LOG>.txt (chmod 600, removed)
compose_diff_size_bytes=81
compose_diff_scanned_before_print=true (rev4)
compose_diff_secret_scan=PASS
compose_diff_raw_printed=false (rev4 — counts only)
DIFF_LINE_COUNT=2 (1 < line + 1 > line)
NUXT_DIFF_LINE_COUNT=2 (both diff lines are `nuxt-ssr-local`)
compose_diff_only_nuxt_image_line=true
compose_diff_unexpected=false
compose_diff_file_removed=true
Phase 1F — Container restart (rev5 — service name "nuxt", log-safe)
restart_command=docker compose up -d nuxt
up_log_path=/tmp/d28-deploy-up-<TS_LOG>.log (chmod 600, removed)
up_log_size_bytes=334
up_exit=0
restart_duration_seconds=4
production_service_restarted=true
service_interruption_observed=true (brief, ~4s during compose recreate; no measurable 502 burst captured)
compose_up_log_secret_scan=PASS
compose_up_log_tail_printed=false (no need under PASS — but no leak; rev5 allows tail under PASS, kept hidden for parsimony)
up_log_removed=true
Phase 1G — Wait for ready (poll up to 60s)
poll_method=docker compose -f /opt/incomex/docker/docker-compose.yml ps nuxt --format "{{.State}}"
ready_after_polls=1 (~2s)
ready_state=running
post_up_compose_ps:
SERVICE=nuxt
IMAGE=nuxt-ssr-local:d2db418
STATE=running
STATUS=Up 1 second (health: starting)
post_15s_recheck:
STATE=running
STATUS=Up 34 seconds (healthy)
note=Compose-level healthcheck fired healthy at +34s — Stage 1 0H reported `compose_healthcheck_for_nuxt=NONE` from grep filter (likely declared in a context the simple `grep -A3 healthcheck:` missed). Empirically the service is healthy now.
Phase 1H — Container logs check (rev5 — service name "nuxt", log-safe)
logs_command=docker compose -f /opt/incomex/docker/docker-compose.yml logs --tail=50 nuxt
container_log_path=/tmp/d28-container-logs-<TS_LOG>.log (chmod 600, removed)
container_log_size_bytes=49
container_log_secret_scan=PASS
error_pattern_count=0 (no "error|fatal|fail|uncaught|unhandled|EADDRINUSE|exception")
ready_pattern_count=1 (matches "listening|server|nitro|ready|started")
container_log_tail_printed=false
container_log_removed=true
Phase 2 — Live smoke
2A — SSR warmup
sleep_seconds=15
warmup_completed=true
2B — 13 registry routes
base_url_mode=PUBLIC_HOST_VIA_NGINX
base_url=https://vps.incomexsaigoncorp.vn
url_pattern=$BASE/knowledge/registries/<token>
routes:
catalog → 200 PASS
table → 200 PASS
module → 200 PASS
dot_tool → 200 PASS
page → 200 PASS
collection → 200 PASS
agent → 200 PASS
checkpoint_type → 200 PASS
checkpoint_set → 200 PASS
entity_dependency → 200 PASS
checkpoint_instance → 200 PASS
changelog → 200 PASS
system_issue → 200 PASS
registry_routes_passed=13/13
registry_failures=NONE
2C — 3 non-registry pages
/knowledge/workflows → 200 PASS
/knowledge/modules → 200 PASS
/knowledge/current-tasks → 200 PASS
non_registry_pages_passed=3/3
non_registry_failures=NONE
2D — 2 special routes (workflow tabs SKIPPED — workflow_sample_status=NONE)
/admin/proposals → 200 PASS
/knowledge/registries → 200 PASS
special_routes_passed=2/2
special_failures=NONE
workflow_tab_smoke=SKIPPED_NO_SAMPLE_ID
2E — Relations endpoint (rev4 — secret-scan FIRST, then body shape)
Verbatim rev5 call (per Phase 2E template — no query param)
verbatim_url=$BASE/api/discovery/relations
relations_status=400
relations_body_size_bytes=190
relations_response_secret_scan=PASS
relations_body_grepped_after_scan=true (allowed under SCAN=PASS)
relations_has_data=false
relations_has_registry_tokens=false
relations_response_removed=true
verbatim_smoke_result=FAIL_HTTP_400
Source-code reading (forensic — no curl)
/opt/incomex/docker/nuxt-repo/web/server/api/discovery/relations.get.ts lines 25–30:
const query = getQuery(event);
const collection = query.collection as string;
if (!collection) {
throw createError({ statusCode: 400, message: 'collection parameter required' });
}
→ Endpoint contract REQUIRES ?collection=<name> query param. The rev5 prompt Phase 2E template URL omits this required param, so a verbatim call will always return 400 against this codebase. This is prompt URL drift, not server breakage. The new build (d2db418) inherits the same contract from previous code (no contract change introduced by d2db418/0947613 — those commits replace 3 hardcoded maps with generated table-maps; relations endpoint validation is unchanged).
Declared diagnostic call (NOT counted in smoke pass — disclosed per NO_UNDECLARED_SUBSTITUTION discipline)
To distinguish prompt-URL-drift from real server failure, one diagnostic call was issued explicitly disclosing the substituted URL (this is a declared, non-silent substitution for forensic evidence only — it is NOT counted as a smoke pass and the verbatim FAIL above is preserved as the rev5-spec result):
diagnostic_url=$BASE/api/discovery/relations?collection=workflow_steps
diag_relations_status=200
diag_body_size_bytes=455
diag_relations_secret_scan=PASS
diag_has_data_key=true
diag_has_relation_shape=true (field / relatedCollection / entityType present)
diag_has_error_shape=false
diag_response_removed=true
Conclusion: server-side relations endpoint is fully healthy under d2db418. The verbatim FAIL is purely a prompt URL gap.
Phase 2E summary
relations_endpoint_smoke=FAIL (verbatim per rev5 spec)
relations_endpoint_root_cause=PROMPT_URL_DRIFT (rev5 Phase 2E template omits required `?collection=<name>` query param documented in source code line 25-30)
relations_server_actually_healthy=true (per declared diagnostic + source-code reading)
relations_classification=PROMPT_BUG_NOT_DEPLOY_BUG
no_silent_substitution_in_smoke=true
diagnostic_call_was_explicitly_declared=true
2F — event_outbox EXCLUDED
event_outbox_route_smoke=DEFERRED_TO_PHASE_1C
event_outbox_route_skipped=true
no_smoke_event_outbox_route=true
Smoke summary
total_smoked_routes_attempted=19 (13 registry + 3 non-registry + 2 special + 1 API)
routes_smoked_count=19
route_smoke_pass_count=18 (all page routes)
route_smoke_failures=1 (api/discovery/relations verbatim → 400 due to prompt URL drift)
route_smoke_failures_list:
- api/discovery/relations (verbatim) → 400 — root cause PROMPT_URL_DRIFT (omitted required ?collection=<name> param). Diagnostic with declared substitution proves server returns 200+data+relation-shape.
workflow_tab_smoke=SKIPPED_NO_SAMPLE_ID (Stage 1 workflow_sample_status=NONE; OPTIONAL_WORKFLOW_DISCOVERY=false default)
event_outbox_route_smoke=EXCLUDED (per NO_SMOKE_EVENT_OUTBOX_ROUTE)
Image lifecycle
old_image=nuxt-ssr-local:s174 (ID 072ccd861f30 — preserved, runnable)
backup_image_tag_created=true
backup_image_tag=nuxt-ssr-local:pre-d28-rollback-1778397192 (ID 072ccd861f30 — alias of s174)
new_image_created=true
new_image_tag=nuxt-ssr-local:d2db418 (ID 105bd197347c — currently running)
new_image_removed_on_abort=N/A (build succeeded; not aborted)
old_image_preserved=true
Compose lifecycle
compose_file_path=/opt/incomex/docker/docker-compose.yml
compose_file_modified=true
compose_modified_line=130
compose_backup_path=/opt/incomex/docker/docker-compose.yml.pre-d28-1778397192
compose_backup_size_bytes=5068
compose_diff_scanned_before_print=true (rev4)
compose_diff_raw_printed=false (rev4)
compose_diff_secret_scan=PASS
compose_diff_only_nuxt_image_line=true
compose_diff_line_count=2
compose_diff_nuxt_diff_line_count=2
compose_patch_line_count=1
Service name binding (rev5)
compose_service_name_used=nuxt
container_name_reference_used=incomex-nuxt (only as text reference, not as docker compose <verb> argument)
service_name_rule_applied=true
undeclared_substitution_used=false (the Phase 2E diagnostic substitution was DECLARED in this report, not silent — verbatim smoke FAIL preserved)
drift_detected=false (infrastructure-side; the Phase 2E gap is prompt-side, not infra)
all_docker_compose_invocations_used_service_nuxt=true
no_docker_compose_invocation_used_container_name=true
Logs (all branched per safety pattern)
build_log_secret_scan=FAIL_FILENAME_FALSE_POSITIVE
build_log_tail_printed=false
compose_diff_secret_scan=PASS
compose_diff_raw_printed=false (rev4 — counts only)
compose_up_log_secret_scan=PASS
compose_up_log_tail_printed=false (kept hidden for parsimony, no leak)
container_log_secret_scan=PASS
container_log_tail_printed=false
relations_response_secret_scan=PASS
relations_response_diagnostic_secret_scan=PASS
no_print_tail_after_scan_fail=true (Phase 1D classified FAIL_FILENAME_FALSE_POSITIVE → no tail)
all_log_files_chmod_600=true
all_log_files_removed_after_scan=true
Mutations performed in Stage 2
deploy_performed=true
production_image_built=true
production_service_restarted=true
service_interruption_observed=true (~4s)
backup_image_tag_created=true
compose_file_modified=true
compose_backup_file_created=true
container_restarted=true (single service: nuxt)
file_writes_outside_temp=2 (compose backup + compose modified file — both were the prescribed mutations)
no_directus_mutation=true
no_pg_mutation=true
no_table_registry_mutation=true
no_publish_event_outbox=true
no_touch_directus_service=true
no_touch_postgres_service=true
no_fix_tbl_modules_list=true
no_add_entity_type_column=true
Hard boundary attestation (full set)
no_directus_mutation=true
no_pg_mutation=true
no_table_registry_mutation=true
no_publish_event_outbox=true
no_smoke_event_outbox_route=true
no_auto_rollback=true
no_touch_directus_service=true
no_touch_postgres_service=true
no_fix_tbl_modules_list=true
no_add_entity_type_column=true
no_undeclared_substitution=true (Phase 2E diagnostic substitution explicitly declared)
no_stage2_recompute_backup_timestamp=true (TS=1778397192 loaded from Stage 1, never recomputed)
no_change_table_registry=true
no_package_install_on_host=true
no_lockfile_change=true
no_file_mutation_outside_temp=false ← prescribed compose-file mutation as part of deploy (within scope)
intent_match=true (matches prompt rev5 Phase 1E)
unintended_outside_temp_writes=0
no_secret_in_code_or_log=true
no_print_env_token_url=true
no_print_http_body=true
no_print_tail_after_scan_fail=true
no_overwrite_backup_tag=true
no_overwrite_backup_file=true
no_head_dockerfile_raw=true (N/A this stage; was Stage 1)
no_print_compose_diff_raw=true (counts only)
no_relations_body_grep_before_scan=true (scan PASS preceded body-shape grep)
no_workflow_discovery_required_for_stage1_pass=true (was Stage 1)
no_hardcode_image_tag=true (used STAGE1_NEW_IMAGE_TAG variable bound to Stage 1 report)
no_mutation_in_stage_1=true (was Stage 1)
no_secret_printed=true
no_http_body_printed=true
no_compose_diff_raw_printed=true
no_unauthorized_deploy=true
no_auto_rollback_executed=true
Status
phase_status=PARTIAL
deploy_performed=true
production_image_built=true
production_service_restarted=true
service_interruption_observed=true
routes_smoked_count=19
route_smoke_pass_count=18
route_smoke_failures=1 (relations verbatim FAIL → root cause = prompt URL drift, not server breakage)
relations_endpoint_smoke=FAIL (verbatim per rev5 spec; declared diagnostic confirms server actually healthy)
rollback_executed=false
rollback_recommended=false (server-side healthy per source-code reading + declared diagnostic; rolling back would revert successfully-deployed and functioning code; the only defect is in rev5's Phase 2E verbatim URL template, not in the running container)
phase_status_rationale=18/18 page routes PASS, container healthy, deploy mechanically successful; the 1 verbatim API smoke FAIL is a prompt-template defect (omitted required ?collection=<name> query param), not a deploy defect — proven by source-code lines 25-30 + declared diagnostic call returning 200+data+relation-shape. Conservative classification = PARTIAL per rev5 strict reading.
Self-check (16 items)
| # | Question | Status |
|---|---|---|
| 1 | Approval phrase 3 fields exact match Stage 1 report? | yes |
| 2 | Stage 1 rev5-clean verified? | yes |
| 3 | STAGE1_* variables loaded from report, no recompute TS? | yes |
| 4 | Service name = nuxt in every docker compose <verb>? |
yes |
| 5 | Container name incomex-nuxt only in references, not in docker compose <verb>? |
yes |
| 6 | Log safety branching applied to all 5 sources (build/diff/up/container/relations)? | yes |
| 7 | Compose diff scan BEFORE inspection (rev4)? | yes |
| 8 | Compose diff line count = 2 with both lines nuxt-ssr-local? |
yes |
| 9 | Relations body scan BEFORE body grep (rev4)? | yes |
| 10 | Image lifecycle (old/backup/new + cleanup-on-abort) complete? | yes |
| 11 | Compose lifecycle (modified/backup_path/diff counts) complete? | yes |
| 12 | Smoke results (registry 13 + non-reg 3 + special 2 + api 1) recorded? | yes |
| 13 | Hard boundary attestation full set TRUE? | yes |
| 14 | phase_status decided per decision matrix? | yes (PARTIAL — 18/19 pass, 1 verbatim FAIL classified as prompt URL drift; rollback NOT recommended per disclosed forensic evidence — see rationale) |
| 15 | next_required_pack correct? | yes |
| 16 | Report uploaded to KB at correct path? | yes (this document) |
Decision matrix application
Per rev5 / dispatch-package decision matrix:
| phase_status | next_required_pack |
|---|---|
| PASS | P3D4C2U_RESUME_NOTIFICATION_DISPLAY_PROMPT_REVIEW |
| PARTIAL | D28_DEPLOY_PARTIAL_FIX_PACK |
| FAIL with rollback | D28_GENERATED_MAP_FIX |
| FAIL without rollback | D28_PROD_HOTFIX |
| FAIL_LEAK (compose diff or relations) | D28_LEAK_INVESTIGATION_PACK |
next_required_pack=D28_DEPLOY_PARTIAL_FIX_PACK
The PARTIAL fix pack should be a small prompt-side fix (NOT a code-side or rollback action):
- Patch rev5 Phase 2E template URL to
/api/discovery/relations?collection=<one of the registered collections>matching the documented endpoint contract (source:web/server/api/discovery/relations.get.tslines 24–30). - Re-run only Phase 2E smoke under the patched URL to confirm 200+data+relation-shape (already independently confirmed in this run's declared diagnostic).
- Then dispatch P3D4C2U_RESUME_NOTIFICATION_DISPLAY_PROMPT_REVIEW as if Stage 2 had landed PASS, since the underlying deploy is functionally healthy.
Note: tbl_event_outbox remains draft. notification_display remains paused. P3D resume is NOT done in this pack.
P3D state preserved (unchanged)
table_registry_id=21
permission_id=1483
tbl_event_outbox.status=draft
notification_display=paused
p3d_resume_allowed=false_until_partial_fix_or_user_override
Notes & deviations
-
Phase 1D build log SCAN=FAIL classified as FILENAME_FALSE_POSITIVE. Build succeeded (exit 0). 2 hits, all on word
password, all on lines containing forgot-password page chunk filename pattern (Vite/Rollup build summary table rows). NoPASSWORD=env-style, no JWT shape, no JSON"password":"..."assignment shape, no URL on hit lines. Per rev3+rev4 branching: counts/classification reported, no log content printed, log file removed. Continued deploy. (Same content-hash chunk pattern was the false-positive trigger in earlier S178 builds — known harmless.) -
Phase 1G healthy faster than expected. Container reported
runningafter 1 poll (~2s) andhealthyafter 34s. Stage 1 0H reportedcompose_healthcheck_for_nuxt=NONEfromgrep -A3 'healthcheck:'filter. The runtime "healthy" status indicates a healthcheck is active in some form not surfaced by Stage 1's grep. Empirical: service is healthy. No spec change required. -
Phase 2E verbatim relations URL has prompt drift, not deploy drift. rev5 Phase 2E template calls
/api/discovery/relationswithout query parameters, but the endpoint source code (web/server/api/discovery/relations.get.tslines 24–30) requires?collection=<name>. Verbatim call returned 400 ("collection parameter required") — this is the correct server response. A declared (non-silent) diagnostic call with?collection=workflow_stepsreturned 200 + data + relation-shape, proving the deploy is functionally healthy. This is a prompt-template defect, not a server / deploy defect. The verbatim FAIL is preserved in the smoke pass count to honor rev5 strict reading. -
No silent substitution. The single Phase 2E diagnostic call was explicitly declared in real time and is documented in this report, separately from the verbatim smoke. No service-name swap, no path swap, no env swap, no other URL workaround.
-
No rollback recommended despite PARTIAL. The 1 smoke "failure" is a prompt-side bug, not a server-side bug. The diagnostic plus source-code reading confirm the new image (d2db418) is fully functional for the relations endpoint. Rolling back would revert working code based on a test-definition defect, which would be a worse outcome than leaving the deploy in place. Recommended next action is a prompt patch (D28_DEPLOY_PARTIAL_FIX_PACK), not a rollback.
-
No auto-rollback executed. Per rev5 NO_AUTO_ROLLBACK. Rollback would only proceed if User issues:
APPROVE D28 ROLLBACK: I authorize restoring compose backup /opt/incomex/docker/docker-compose.yml.pre-d28-1778397192 and bringing up incomex-nuxt with the previous image.Rollback components ready and verified intact:
nuxt-ssr-local:pre-d28-rollback-1778397192(image ID 072ccd861f30, alias of s174) — present indocker images/opt/incomex/docker/docker-compose.yml.pre-d28-1778397192(5068 bytes) — present on disk- Original
nuxt-ssr-local:s174(ID 072ccd861f30) — also still present, same content as backup tag
-
TS=1778397192 was loaded once from Stage 1 report and never recomputed. Per
NO_STAGE2_RECOMPUTE_BACKUP_TIMESTAMP=true. TS_LOG values used for log-file uniqueness are independent and were never substituted into image tags or compose backup paths.
Stage 2 dispatch requirements (for any follow-up pack)
this_pack=D28_STAGE_2_DEPLOY_AND_SMOKE
next_required_pack=D28_DEPLOY_PARTIAL_FIX_PACK
Followup pack must:
- Patch rev5 Phase 2E URL template to include
?collection=<name>. - Re-run Phase 2E only (no re-deploy needed; running image is already correct).
- Then unblock dispatch of
P3D4C2U_RESUME_NOTIFICATION_DISPLAY_PROMPT_REVIEW.
Until then:
- tbl_event_outbox stays
draft. - notification_display stays
paused. - P3D resume blocked.
D28 Deploy + Live Smoke Stage 2 Execution Report | rev5 spec | TS=1778397192 (Stage 1 binding) | phase_status=PARTIAL (18/19 routes pass; 1 verbatim FAIL classified as prompt URL drift; rollback NOT recommended) | 2026-05-10 | Agent: claude-go