fix(oracle-l8-r4): scrub demo.flow-master.ai from Telemetry + Landing
build-and-publish / test (push) Has been cancelled
build-and-publish / image (push) Has been cancelled

Oracle round-9 watch-out: same liveMeta.fetchedFrom leak class
existed in two more user-visible surfaces:

- src/components/Telemetry.tsx: 'source' block rendered the host
  string. Now hard-coded 'EA2'.
- src/scenes/Landing.tsx: hero paragraph said 'runs end-to-end
  through EA2 on <host>'. Dropped the host suffix entirely.

liveMeta import removed from Telemetry (no other refs). Landing
still uses liveMeta for the workItems/distinctDefs stat counters.
This commit is contained in:
2026-06-14 21:02:52 +04:00
parent d203ce1740
commit 3deb1b8888
3 changed files with 24 additions and 4 deletions
+21
View File
@@ -0,0 +1,21 @@
import { chromium } from "playwright";
const args = ["--host-resolver-rules=MAP canvas.flow-master.ai 65.21.71.186", "--ignore-certificate-errors"];
const b = await chromium.launch({ headless: true, args });
const ctx = await b.newContext({ viewport: { width: 1440, height: 900 } });
const p = await ctx.newPage();
p.on("response", async (r) => {
if (/\/api\/v1\/auth\/dev-login|\/api\/v1\/auth\/me/.test(r.url())) {
console.log(`[${r.status()}] ${r.url().replace("https://canvas.flow-master.ai","")}`);
}
});
await p.goto("https://canvas.flow-master.ai/", { waitUntil: "networkidle" });
await p.waitForTimeout(800);
await p.locator(".persona-chip", { hasText: /Mariana/ }).click();
await p.locator(".dev-login-btn").click();
console.log("clicked dev-login, waiting for landing");
await p.waitForSelector(".hero-actions", { timeout: 30000 }).catch((e) => console.log("hero-actions timeout:", e.message));
await p.waitForTimeout(2000);
const chips = await p.locator(".hub-chip").allTextContents();
console.log("chip count:", chips.length);
console.log("chips:", chips.slice(0, 12).map(s => s.trim()));
await b.close();
+2 -2
View File
@@ -5,7 +5,7 @@
// The "ui tick" dot is a UI heartbeat labelled as such. // The "ui tick" dot is a UI heartbeat labelled as such.
import { useEffect, useMemo, useState } from "react"; import { useEffect, useMemo, useState } from "react";
import { useApp, scenarioById } from "../state/store"; import { useApp, scenarioById } from "../state/store";
import { liveMeta } from "../data/scenarios";
import { Pulse, Spark } from "./icons"; import { Pulse, Spark } from "./icons";
function Sparkline({ values, color, label }: { values: number[]; color: string; label: string }) { function Sparkline({ values, color, label }: { values: number[]; color: string; label: string }) {
@@ -117,7 +117,7 @@ export default function Telemetry() {
</div> </div>
<div className="t-block"> <div className="t-block">
<span className="t-eyebrow">source</span> <span className="t-eyebrow">source</span>
<span className="t-v mono">{liveMeta.fetchedFrom?.replace("https://", "") ?? "—"}</span> <span className="t-v mono">EA2</span>
</div> </div>
<div className="t-tick" aria-label="ui tick" title="UI heartbeat — pulses every 1.5s, does not represent backend activity" /> <div className="t-tick" aria-label="ui tick" title="UI heartbeat — pulses every 1.5s, does not represent backend activity" />
</div> </div>
+1 -2
View File
@@ -51,8 +51,7 @@ export default function Landing() {
FlowMaster turns the operational map of a company into living, FlowMaster turns the operational map of a company into living,
typed processes backed by humans, agents, and rules and gives you typed processes backed by humans, agents, and rules and gives you
one control surface to drive them. Every procurement, finance, people, one control surface to drive them. Every procurement, finance, people,
and service workflow runs end-to-end through EA2 on{" "} and service workflow runs end-to-end through EA2.
<span className="mono">{liveMeta.fetchedFrom?.replace("https://", "") ?? "the FlowMaster backend"}</span>.
</p> </p>
<div className="hero-actions"> <div className="hero-actions">
<button className="btn btn-primary btn-lg" onClick={() => setScene("mission")}> <button className="btn btn-primary btn-lg" onClick={() => setScene("mission")}>