From 235b2d62f32296afb8e33dea5412a41c4417a297 Mon Sep 17 00:00:00 2001 From: Claude Date: Thu, 6 Aug 2026 19:39:40 +0000 Subject: [PATCH 1/2] docs(web): stop implying Ghost calls external APIs today MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit The "So is this just browser automation?" section said "where a real API exists that is the better path, and the same controls sit on top of it unchanged". Read in present tense that claims API execution works. It does not. `apiCall` and `sendEmail` parse, the classifier gates them as sensitive, and compensate/expr handle them — but applyStep returns `{}` for both, they are listed in UNIMPLEMENTED_ACTION_TYPES, and editable-steps.test.ts enforces that the editor never offers them, precisely so nobody can author a step that silently does nothing while the run reports success. The Connector model is schema-only: "no UI or command reads these yet." So the page now states outright that today every step runs through a browser, names what exists (step type, connector model, sensitivity rules) and what does not (the executor), and explains why the step is withheld from the editor. The honest version is also the more convincing one: it is the same reasoning that keeps the step out of the editor in the first place. CLAUDE.md rule 10 — marketing must not promise capabilities the app cannot support. This is that rule applied to a sentence I wrote two commits ago. Validation: typecheck, lint, build, web test suite all pass. Co-Authored-By: Claude Opus 5 Claude-Session: https://claude.ai/code/session_01VLqLtoLgi4RDrWaYVJVGuX --- cloud/apps/web/src/app/page.tsx | 26 +++++++++++++++++++------- 1 file changed, 19 insertions(+), 7 deletions(-) diff --git a/cloud/apps/web/src/app/page.tsx b/cloud/apps/web/src/app/page.tsx index 43db79a..6eadb3a 100644 --- a/cloud/apps/web/src/app/page.tsx +++ b/cloud/apps/web/src/app/page.tsx @@ -238,13 +238,25 @@ export default async function Home() {

- No. Driving a browser is the easy part — Playwright and Selenium have done it for - years, and a dozen no-code tools wrap them. The browser is simply how Ghost - reaches a system, and it is the least preferred way. Where a real API - exists that is the better path, and the same controls sit on top of it unchanged. - Ghost leads with the browser because the systems this work actually lives in — - supplier portals, ERPs, insurer sites, internal admin panels — mostly have no API, - or have one nobody has integrated. + Driving a browser is the easy part — Playwright and Selenium have done it for + years, and a dozen no-code tools wrap them. The browser is how Ghost reaches a + system, not what Ghost is. +

+

+ Being exact about it: + today every step runs through a browser. Calling a system’s API + directly is the better path where one exists, and the pieces for it are designed + in — an apiCall step type, the + connector model, and the rules that decide an API action is sensitive all exist + already. The executor behind them is not written yet, so Ghost does not call + external APIs on your behalf. The step is deliberately not offered in the editor + until it does, because a step that silently does nothing while the run reports + success is worse than no step at all. +

+

+ Which matters less than it sounds, because the systems this work actually lives + in — supplier portals, ERPs, insurer sites, internal admin panels — mostly have no + API, or have one nobody has integrated. The browser is what reaches them all.

What Ghost is, is the layer between something wanting to act and the From 1f77f02c7d88e587c0edd46bbee15060250d40f2 Mon Sep 17 00:00:00 2001 From: Claude Date: Fri, 7 Aug 2026 16:22:15 +0000 Subject: [PATCH 2/2] chore: retrigger CI on this PR MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit No code change. GitHub Actions has created no workflow run for this PR, or for #414, or for #414's merge commit on master — every workflow is active and every trigger matches, so the runs are being suppressed rather than failing. This commit is a discriminator. #414 and #415 were both opened through a GitHub App installation token, and the merge was performed the same way. A push from the git credential here is a different token class (an OAuth app — it was refused `workflow` scope earlier, which GITHUB_TOKEN would not have been). If a `pull_request: synchronize` run appears from this push, the cause is token-related. If nothing appears, it is repository-level: exhausted Actions minutes or an Actions restriction, neither of which any workflow file can fix. Worth knowing because the PR currently reports mergeable_state "blocked" with no check runs in existence — a required check that was never created sits "Expected — Waiting for status" forever, which is the exact failure mode described in the header of .github/workflows/rust.yml. Co-Authored-By: Claude Opus 5 Claude-Session: https://claude.ai/code/session_01VLqLtoLgi4RDrWaYVJVGuX