Pipeline
SalesWorkspaceMap
A read-only React Flow map of how a workspace's lists, signals, campaigns, rules and pipelines connect.
Guidelines#
Use it for the sales workspace page's Map view.
What you provide:
graph: SalesWorkspaceGraph, shaped{ nodes, edges, updatedAt, notices }.- Each node is
{ id, kind, label, description?, status?, href, stats? }. - Each edge is
{ id, source, target, kind, label, status? }, withstatusone ofactive,paused,draft,configured.
- Each node is
selectedId(ornull) andonSelect(id).
Layout: a node's kind decides its lane:
- 0: lists and signals;
- 1: campaigns;
- 2: workflows and stage rules;
- 3: pipelines, stages and meetings.
Nodes sit at x = lane × 310, y = row × 165. The view fits the content, with zoom 0.15–1.5.
Anatomy:
- A node is
w-60 rounded-xl border bg-card p-4 shadow-sm: atext-[10px]uppercase kind, the label intext-sm font-semibold, and the status in mutedtext-xs("Configured" when absent). - The selected node, and every node connected to it, gets
border-primary ring-2 ring-primary/15. - Edges are smoothstep with arrows: 2.5px
var(--primary)when they touch the selection, otherwise 1pxvar(--muted-foreground). Draft and paused edges are dashed5 5. - The container is
h-[580px] rounded-xl border bg-muted/10.
Don't use it to edit: nodes can't be dragged or connected. Changes are made on the source item.
Known issue: it doesn't pass colorMode, so in dark themes React Flow's zoom controls stay light and their icons are hard to see.
Facts#
| Group | Pipeline |
|---|---|
| Product | Max |
| Global | window.DigitalCrew.SalesWorkspaceMap |
| Source | max-agent: src/features/sales-workspace/ui/sales-workspace-map.tsx |
| Import in the app | import { SalesWorkspaceMap } from "@/features/sales-workspace/ui/sales-workspace-map"; |
API#
TypeScript declarations emitted from src/features/sales-workspace/ui/sales-workspace-map.tsx.
export declare const KIND_LABELS: Record<SalesWorkspaceNodeKind, string>;
export declare function SalesWorkspaceMap({ graph, selectedId, onSelect }: {
graph: SalesWorkspaceGraph;
selectedId: string | null;
onSelect: (id: string) => void;
}): JSX.Element;Example#
The code of the preview above: plain React.createElement against window.DigitalCrew, with realistic data.
<div id="root" class="p-6"></div>
<script>
(function () {
var h = React.createElement, DC = window.DigitalCrew, I = DC.Icons;
// SalesWorkspaceGraph (features/sales-workspace/schemas/sales-workspace.schema.ts).
// Node ids follow the builder's "<kind>:<id>" shape; lanes come from the node kind.
function node(kind, id, label, status, href, description) {
return { id: kind + ":" + id, kind: kind, label: label, status: status, href: href, description: description };
}
function edge(id, source, target, kind, label, status) {
return { id: id, source: source, target: target, kind: kind, label: label, status: status };
}
var GRAPH = {
updatedAt: "2026-09-26T08:30:00.000Z",
notices: [],
nodes: [
node("list", "l1", "DACH logistics CFOs", "ready", "/prospect-lists/l1", "Audience list"),
node("signal", "s1", "Hiring SDRs monitor", "active", "/signals", "company · linkedin"),
node("campaign", "c1", "Q4 DACH logistics — CFO outreach", "active", "/campaigns/c1", "Outreach sequence"),
node("campaign", "c2", "Hiring-signal follow-up", "draft", "/campaigns/c2", "Outreach sequence"),
node("stage_rule", "r1", "Create deal", "active", "/pipeline", "When entering Interested"),
node("workflow", "w1", "Notify AE on positive reply", "active", "/workflows/w1"),
node("people_stage", "ps1", "Replied", "active", "/pipeline"),
node("people_stage", "ps2", "Interested", "active", "/pipeline"),
node("deal_stage", "ds1", "Meeting booked", "open", "/deals")
],
edges: [
edge("m1", "list:l1", "campaign:c1", "membership", "Included audience", "configured"),
edge("a1", "signal:s1", "campaign:c2", "automation", "Changed signal → launch if draft or stopped", "active"),
edge("r1", "campaign:c1", "people_stage:ps1", "automation", "On replied", "active"),
edge("p1", "people_stage:ps1", "people_stage:ps2", "automation", "Move on stage entry", "active"),
edge("e1", "people_stage:ps2", "stage_rule:r1", "automation", "On entering stage", "active"),
edge("d1", "stage_rule:r1", "deal_stage:ds1", "automation", "Create deal", "active")
]
};
function App() {
var s = React.useState("campaign:c1"), selected = s[0], setSelected = s[1];
return h(DC.SalesWorkspaceMap, { graph: GRAPH, selectedId: selected, onSelect: setSelected });
}
ReactDOM.createRoot(document.getElementById("root")).render(h(DC.TooltipProvider, { delayDuration: 80 }, h(App)));
})();
</script>