different-ai/openwork · error · Error

Workspace endpoint unavailable for ${selectedId}.

Error message

Workspace endpoint unavailable for ${selectedId}.

What it means

The settings route's activateWorkspace callback resolves a workspace-scoped server endpoint via workspaceServerClientResolver. resolveWorkspaceEndpoint returns null when the local server handle (baseUrl/token) is missing or the workspace cannot be mapped to an endpoint, so the code throws before calling endpoint.client.activateWorkspace.

Source

Thrown at apps/app/src/react-app/shell/settings-route.tsx:660

          }
        : emptyWorkspaceDisplay,
    [emptyWorkspaceDisplay, selectedWorkspace],
  );
  const workspaceServerClientResolver = useMemo(
    () => createWorkspaceServerClientResolver({ baseUrl, token }),
    [baseUrl, token],
  );
  const workspaceSelectionCommitRef = useRef<(workspaceId: string) => Promise<void>>(async () => undefined);
  workspaceSelectionCommitRef.current = async (workspaceId) => {
    await commitRouteWorkspaceSelection({
      workspaceId,
      desktopRuntime: isDesktopRuntime(),
      setDesktopSelected: workspaceSetSelected,
      setDesktopRuntimeActive: workspaceSetRuntimeActive,
      activateWorkspace: async (selectedId) => {
        const workspace = workspacesRef.current.find((item) => item.id === selectedId) ?? null;
        const endpoint = workspaceServerClientResolver(workspace);
        if (!endpoint) throw new Error(`Workspace endpoint unavailable for ${selectedId}.`);
        if (workspace?.workspaceType === "local" && serverActiveWorkspaceIdRef.current === selectedId) return;
        await endpoint.client.activateWorkspace(endpoint.workspaceId, { persist: true });
        if (workspace?.workspaceType === "local") serverActiveWorkspaceIdRef.current = selectedId;
      },
    });
  };
  const selectedWorkspaceEndpoint = useWorkspaceServerClient(selectedWorkspace, { baseUrl, token });
  const opencodeBaseUrl = selectedWorkspaceEndpoint?.opencodeBaseUrl ?? "";

  routeStateRef.current = {
    activeClient,
    providerBaseUrl: opencodeBaseUrl,
    selectedWorkspaceId,
    selectedWorkspaceRoot,
    selectedWorkspaceType: selectedWorkspace?.workspaceType ?? "local",
    runtimeWorkspaceId: selectedWorkspace?.id ?? null,
    openworkServerClient: openworkClient,
    selectedWorkspaceOpenworkClient: openworkClient,

View on GitHub (pinned to 2b7df46e8a)

Solutions

  1. Reconnect/restart the OpenWork server so a valid LocalServerHandle (baseUrl+token) exists, then retry activation.
  2. Refresh the workspace list so workspacesRef.current contains the workspace and a valid endpoint can be resolved.
  3. Check resolveWorkspaceEndpoint inputs (workspace id, type, remote baseUrl) for the failing workspace.

Example fix

// before
const endpoint = workspaceServerClientResolver(workspace);
if (!endpoint) throw new Error(`Workspace endpoint unavailable for ${selectedId}.`);
// after
const endpoint = workspaceServerClientResolver(workspace);
if (!endpoint) { await reconnectLocalServer(); endpoint = workspaceServerClientResolver(workspace); }
if (!endpoint) throw new Error(`Workspace endpoint unavailable for ${selectedId}.`);
Defensive patterns

Strategy: type-guard

Validate before calling

const workspace = workspacesRef.current.find((i) => i.id === selectedId);
if (!workspace) return; // nothing to activate
const endpoint = workspaceServerClientResolver(workspace);
if (!endpoint) await reconnectLocalServer();

Type guard

function isResolvedEndpoint(e: ReturnType<WorkspaceServerClientResolver>): e is NonNullable<ReturnType<WorkspaceServerClientResolver>> {
  return e !== null && typeof e.client?.activateWorkspace === "function";
}

Try / catch

try {
  await activateWorkspace(selectedId);
} catch (e) {
  if (e instanceof Error && e.message.startsWith("Workspace endpoint unavailable")) {
    await refreshWorkspaceList();
  } else throw e;
}

Prevention

When it happens

Trigger: Activating a workspace in Settings when the local OpenWork server handle has no baseUrl/token (server stopped or reconnecting) and the workspace has no resolvable remote endpoint, or the workspace entry itself is missing/stale in the local list (workspacesRef.current lookup returns null and no endpoint can be derived).

Common situations: Server restarted and handle not yet rehydrated; workspace forgotten on server but cached in UI; local server token rotated so the resolver cache key invalidates to null.


AI-assisted analysis of different-ai/openwork@2b7df46e8a (2026-09-01). Data as JSON: /api/errors/4605bc6d6e5572c2. Report an issue: GitHub.