diff --git a/web/workspace/src/lib/workspace-sidebar/ObjectivesNavSection.svelte b/web/workspace/src/lib/workspace-sidebar/ObjectivesNavSection.svelte
new file mode 100644
index 00000000..e448e99e
--- /dev/null
+++ b/web/workspace/src/lib/workspace-sidebar/ObjectivesNavSection.svelte
@@ -0,0 +1,157 @@
+
+
+
+
+
objectives
+ {#if !loading && !error}
+ {objectives.length}
+ {/if}
+
+
+ {#if loading}
+ Loading objectives…
+ {:else if error}
+ {error}
+ {:else if objectives.length === 0}
+ No objectives found.
+ {:else}
+
+ {#each objectives as objective (objective.id)}
+ -
+ {objective.title}
+ {objective.state}
+
+ {/each}
+
+ {/if}
+
+ {#if invalidRecordCount > 0}
+ {invalidRecordCount} invalid objective record(s) hidden.
+ {/if}
+
+
+
diff --git a/web/workspace/src/lib/workspace-sidebar/RepositoriesNavSection.svelte b/web/workspace/src/lib/workspace-sidebar/RepositoriesNavSection.svelte
new file mode 100644
index 00000000..759e8899
--- /dev/null
+++ b/web/workspace/src/lib/workspace-sidebar/RepositoriesNavSection.svelte
@@ -0,0 +1,106 @@
+
+
+
+
+
repositories
+ 1
+
+
+
+ -
+ {workspace?.display_name ?? 'local workspace'}
+ local project records
+
+
+
+
+ Repository API is not wired yet; this placeholder keeps the navigation seam
+ ready without adding repository authority.
+
+
+
+
diff --git a/web/workspace/src/lib/workspace-sidebar/WorkersNavSection.svelte b/web/workspace/src/lib/workspace-sidebar/WorkersNavSection.svelte
new file mode 100644
index 00000000..90a7f19d
--- /dev/null
+++ b/web/workspace/src/lib/workspace-sidebar/WorkersNavSection.svelte
@@ -0,0 +1,198 @@
+
+
+
+
+
workers
+ {#if !loading && !error && workers.length > 0}
+ {workers.length}
+ {/if}
+
+
+ {#if loading}
+ Checking workers…
+ {:else if error}
+ {error}
+ {:else if workers.length === 0}
+ {placeholder ?? 'Workers will appear here when an API is connected.'}
+ {:else}
+
+ {#each workers as worker (worker.id)}
+ -
+ {worker.label}
+
+ {worker.status}{worker.detail ? ` · ${worker.detail}` : ''}
+
+
+ {/each}
+
+ {/if}
+
+
+
diff --git a/web/workspace/src/lib/workspace-sidebar/WorkspaceSidebar.svelte b/web/workspace/src/lib/workspace-sidebar/WorkspaceSidebar.svelte
new file mode 100644
index 00000000..ecc85e69
--- /dev/null
+++ b/web/workspace/src/lib/workspace-sidebar/WorkspaceSidebar.svelte
@@ -0,0 +1,124 @@
+
+
+
+
+
diff --git a/web/workspace/src/lib/workspace-sidebar/types.ts b/web/workspace/src/lib/workspace-sidebar/types.ts
new file mode 100644
index 00000000..deaaddc9
--- /dev/null
+++ b/web/workspace/src/lib/workspace-sidebar/types.ts
@@ -0,0 +1,38 @@
+export type WorkspaceResponse = {
+ workspace_id: string;
+ display_name: string;
+ record_authority: string;
+ extension_points: {
+ event_stream: { status: string; note: string };
+ runner_connection: { status: string; note: string };
+ };
+};
+
+export type ObjectiveSummary = {
+ id: string;
+ title: string;
+ state: string;
+ updated_at?: string | null;
+ linked_tickets?: string[];
+ record_source?: string;
+};
+
+export type InvalidProjectRecord = {
+ label: string;
+ reason: string;
+};
+
+export type ObjectiveListResponse = {
+ workspace_id: string;
+ limit: number;
+ items: ObjectiveSummary[];
+ invalid_records: InvalidProjectRecord[];
+ record_authority: string;
+};
+
+export type WorkerSummary = {
+ id: string;
+ label: string;
+ status: string;
+ detail?: string | null;
+};
diff --git a/web/workspace/src/routes/+page.svelte b/web/workspace/src/routes/+page.svelte
index d905974c..c7a60db8 100644
--- a/web/workspace/src/routes/+page.svelte
+++ b/web/workspace/src/routes/+page.svelte
@@ -1,13 +1,6 @@