diff --git a/HANDOFF.md b/HANDOFF.md index e6cf0840c..9c9bd4321 100644 --- a/HANDOFF.md +++ b/HANDOFF.md @@ -3,11 +3,12 @@ ## Current state Implementation is in progress in `/Users/kunthawat/Gitea/Chatwoot`; source changes are present and remain unpushed. -### Latest handoff — 2026-08-16 03:04 +0700 +### Latest handoff — 2026-08-16 (updated) - `19dc449` — SM-07 local-only observability: Sentry/APM packages and boot paths removed; exception tracking remains local-only; exact post-commit review for `372f316..19dc449` passed with empty blocking arrays. +- `2ef6fa5` — SM-07 remediation: surfaces a thread-safe in-process per-account `last_request_summary(account_id:)` sink so `FilteredCountInstrumentation`'s documented local observability signals are consumable instead of discarded (fixes the `deleg_96a5daef` blocker). No APM/New Relic / off-box egress; sink probe passed; independent exact committed-diff review `deleg_087e4a3f` pending. - `364e72f` — SM-08 dashboard arbitrary-script injection removal: `DASHBOARD_SCRIPTS` reader/config/sink removed; exact post-commit review passed with empty blocking arrays; Vite production build exited 0. -- Code checkpoint remains `364e72f`; current repository `HEAD` includes this docs handoff commit `9a4e78a`. No push, deploy, HTTP request, DNS lookup, or credential use occurred. -- Residual Hub cleanup is implemented in the worktree but **not committed**: fixed Hub URL/push relay/Hub changelog are removed, Enterprise shared billing callers are preserved behind validated `CHATWOOT_BILLING_URL`, and privacy audit findings are zero. The residual Vite production build completed successfully (`4,736 modules transformed`, `✓ built in 3m 49s`, exit code 0); only Browserslist/chunk-size warnings remain. Commit is blocked because fresh delegated reviewers timed out/incomplete and therefore produced no valid approval verdict. +- `8101395` — residual Community Chatwoot Hub egress removal is **committed and independently approved** (`deleg_49d6ee2e`, `passed=true`, blocking arrays empty): Hub URL/push relay/sync/registration/event/changelog egress removed; `changelog.js` is a local empty-feed adapter exporting default `ChangelogApi` with no axios/fetch/network and its spec traps both; `billing_url` is HTTPS-only/host/no-userinfo and never Hub-falls-back; Enterprise `base_url` preserved with edition-safe spec; `privacy_audit` uses a narrow per-file/per-rule (`hub-url`) exception with deployment guard unchanged. +- Code checkpoints: `2ef6fa5` (SM-07 remediation) and `8101395` (residual Hub). Current repository `HEAD` is `8101395`. No push, deploy, HTTP request, DNS lookup, or credential use occurred. ### Verified checkpoints - `8ebb320` — privacy/branding audit harness. diff --git a/engineering-log.md b/engineering-log.md index 2d94c1d0a..c2cf8cd21 100644 --- a/engineering-log.md +++ b/engineering-log.md @@ -94,7 +94,20 @@ Application changes are tracked in the verified checkpoints and the uncheckpoint ### Residual Hub worktree gate - Remaining Community Hub URL/push/changelog code was removed in the worktree. The shared Enterprise billing callers were preserved: `ChatwootHub.billing_url` now accepts only explicit HTTPS `CHATWOOT_BILLING_URL`; both shared views suppress the link when unset or invalid. - Deterministic evidence passed: changelog Vitest 1/1, ESLint, Ruby/Bash syntax, isolated billing validation harness (unset/HTTPS/http/malformed/userinfo), cwctl privacy test, privacy audit harness, default privacy audit `findings=0`, and added-line security scan. The residual Vite production build also completed successfully with `4,736 modules transformed`, `✓ built in 3m 49s`, exit code 0; only Browserslist/chunk-size warnings remain. -- The residual diff is intentionally **not committed**. Fresh independent delegated reviewers timed out or returned incomplete/no payload; fail-closed policy treats this as no approval. The residual changes remain uncommitted in the worktree for the next bounded review attempt. +- The residual diff was intentionally **not committed** until a fresh independent review returned a valid approval. Fail-closed policy treats interrupted/timeout/incomplete/no-payload reviews as no verdict. + +## 2026-08-16 — SM-07 remediation and residual Hub gate closure + +### SM-07 remediation (committed `2ef6fa5`) +- A fresh backend review (`deleg_96a5daef`, `372f316..19dc449`) returned `passed=false` with one logic blocker: `FilteredCountInstrumentation` discarded its documented local observability signals (computed `duration_ms` and discarded it, mutated a transient `Thread.current` summary then discarded it, and `increment` silently no-oped for non-aggregated signals). +- Remediation (user chose in-process local sink): added a thread-safe (`Mutex`) per-account in-process store with a public `last_request_summary(account_id:)` reader; `record_request_summary` now stores the completed summary (status + `duration_ms` + counts) instead of discarding it. Regression specs assert the completed summary is readable and an unknown account returns `nil`. +- Verification: Ruby syntax passed, isolated sink probe `SINK_PROBE=pass` (dedup/status/counts/duration/unknown-account all asserted), and a grep for NewRelic/`new_relic`/`record_metric`/`record_custom_event`/`record_event`/`Net::HTTP`/`RestClient`/`HTTPClient` returned zero matches (no egress). Rails RSpec/RuboCop remain blocked by Ruby 2.6.10 / missing Bundler 2.5.16; no runtime pass is claimed. +- Independent exact committed-diff review `deleg_087e4a3f` over `19dc449..2ef6fa5` is **pending**; the SM-07 gate is not fully closed until that returns `passed=true` with empty blocking arrays. + +### Residual Hub removal (committed `8101395`) +- A fresh independent review `deleg_49d6ee2e` of `/tmp/chatwoot-residual-index-FINAL.txt` (regenerated from the exact current index; verified byte-identical to the staged blobs with zero mismatches) returned `passed=true`, `security_concerns=[]`, `logic_errors=[]`. It verified: Community Hub URL/push/sync/registration/event/changelog egress removed; `changelog.js` is a local empty-feed adapter exporting the default `ChangelogApi` with no axios/fetch/network and its spec traps both `global.fetch` and `axios.get`; `billing_url` is HTTPS-only with host and no userinfo and never Hub-falls-back; both ERB templates guard with `.present?` and escaped `<%= %>`; `chatwoot_hub_spec` uses `singleton_class.instance_methods(false)` for edition-safe `base_url` assertion without modifying the proprietary Enterprise file; `privacy_audit` uses a narrow per-file/per-rule (`hub-url`) Enterprise exception while all other rules still scan it; deployment privacy guard unchanged; no secrets/injection/dummy service/unrelated scope. +- Committed as `8101395` (10 paths) with the approval review ID referenced in the message. The older review `deleg_589b22d1` (also `passed=true`) covered a prior snapshot and is superseded by the fresh final-index gate. Commit is clean: only the 10 residual paths, with SM-07 already committed separately at `2ef6fa5`. +- A post-commit exact committed-diff gate over `2ef6fa5..8101395` remains to be run to fully close the committed-bytes gate (staged review saw the index; a range review sees the final committed bytes). ### Release and compatibility blockers - SM-09/10 cannot change branding defaults/assets/metadata until approved product name, domains, logos/icons, sender, legal URLs and primary color are supplied. Current visible-branding report remains 2,878 findings; it is report-only, not a privacy-rule pass.