Skip to content

Commit 036d5cd

Browse files
committed
fix: sync bar state for unlinked models, ghost edges between ref nodes
- Show "No codebase linked yet" instead of green dot + "In sync" when no projectPath is set on the model - Block edge creation between two reference nodes
1 parent 073ecbf commit 036d5cd

File tree

2 files changed

+34
-13
lines changed

2 files changed

+34
-13
lines changed

src/App.tsx

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -518,9 +518,10 @@ function Flow() {
518518
const onConnect: OnConnect = useCallback(
519519
(connection) => {
520520
if (currentParentKind === "component") return;
521+
if (refNodeIds.has(connection.source) && refNodeIds.has(connection.target)) return;
521522
setEdges((eds) => addEdge({ ...connection, data: { label: "" } }, eds) as C4Edge[]);
522523
},
523-
[currentParentKind],
524+
[currentParentKind, refNodeIds],
524525
);
525526

526527
const updateEdgeData = useCallback(
@@ -1050,6 +1051,7 @@ function Flow() {
10501051
structureChanged={structureChanged}
10511052
syncStatus={syncStatus}
10521053
syncMessage={syncMessage}
1054+
projectPath={projectPath}
10531055
onSync={handleSync}
10541056
onCancelSync={handleCancelSync}
10551057
onDismissMessage={() => { setSyncMessage(null); if (syncStatus === "error") setSyncStatus("idle"); }}

src/SyncBar.tsx

Lines changed: 31 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -9,14 +9,15 @@ interface SyncBarProps {
99
structureChanged: boolean;
1010
syncStatus: "idle" | "running" | "error";
1111
syncMessage: string | null;
12+
projectPath: string | undefined;
1213
onSync: () => void;
1314
onCancelSync: () => void;
1415
onDismissMessage: () => void;
1516
onDismissDrift: () => void;
1617
onNavigateToNode?: (nodeId: string) => void;
1718
}
1819

19-
export function SyncBar({ activeAgent, driftedNodes, structureChanged, syncStatus, syncMessage, onSync, onCancelSync, onDismissMessage, onDismissDrift, onNavigateToNode }: SyncBarProps) {
20+
export function SyncBar({ activeAgent, driftedNodes, structureChanged, syncStatus, syncMessage, projectPath, onSync, onCancelSync, onDismissMessage, onDismissDrift, onNavigateToNode }: SyncBarProps) {
2021
const [expanded, setExpanded] = useState(false);
2122
const sortedDriftedNodes = useMemo(
2223
() => [...driftedNodes].sort((a, b) => a.nodeName.localeCompare(b.nodeName)),
@@ -34,25 +35,43 @@ export function SyncBar({ activeAgent, driftedNodes, structureChanged, syncStatu
3435
return () => clearTimeout(timer);
3536
}, [isSuccess]);
3637

37-
// Don't render at all if no agent is available
38-
if (!activeAgent?.available) return null;
38+
// Don't render if no agent and no useful state to show
39+
if (!activeAgent?.available && projectPath) return null;
40+
if (!activeAgent?.available && !projectPath) {
41+
return (
42+
<div className="shrink-0 border-t border-zinc-200 dark:border-zinc-700 bg-zinc-50 dark:bg-zinc-900 select-none">
43+
<div className="flex items-center h-7 px-3 gap-3 text-[11px]">
44+
<div className="flex items-center gap-1.5 text-zinc-400 dark:text-zinc-500">
45+
<span>No codebase linked yet</span>
46+
</div>
47+
</div>
48+
</div>
49+
);
50+
}
3951

40-
const agentName = activeAgent.name;
52+
const agentName = activeAgent!.name;
4153

4254
return (
4355
<div className="shrink-0 border-t border-zinc-200 dark:border-zinc-700 bg-zinc-50 dark:bg-zinc-900 select-none">
4456
{/* Main bar row */}
4557
<div className="flex items-center h-7 px-3 gap-3 text-[11px]">
46-
{/* Agent identity */}
47-
<div className="flex items-center gap-1.5 shrink-0">
48-
<div className="h-1.5 w-1.5 rounded-full bg-emerald-500 shrink-0" />
49-
<span className="text-zinc-500 dark:text-zinc-400 font-medium">{agentName}</span>
50-
</div>
51-
52-
<div className="w-px h-3 bg-zinc-200 dark:bg-zinc-700" />
58+
{/* Agent identity — only when linked to a codebase */}
59+
{projectPath ? (
60+
<>
61+
<div className="flex items-center gap-1.5 shrink-0">
62+
<div className="h-1.5 w-1.5 rounded-full bg-emerald-500 shrink-0" />
63+
<span className="text-zinc-500 dark:text-zinc-400 font-medium">{agentName}</span>
64+
</div>
65+
<div className="w-px h-3 bg-zinc-200 dark:bg-zinc-700" />
66+
</>
67+
) : null}
5368

5469
{/* Sync status */}
55-
{syncStatus === "running" ? (
70+
{!projectPath ? (
71+
<div className="flex items-center gap-1.5 text-zinc-400 dark:text-zinc-500">
72+
<span>No codebase linked yet</span>
73+
</div>
74+
) : syncStatus === "running" ? (
5675
<>
5776
<div className="flex items-center gap-1.5 text-amber-600 dark:text-amber-400">
5877
<Loader2 className="h-3 w-3 animate-spin" />

0 commit comments

Comments
 (0)