tinyhumansai/openhuman · error

Failed to fetch repositories

Error message

Failed to fetch repositories

What it means

RepoPicker verifies an active GitHub connection first (throwing 'NOT_CONNECTED' otherwise), then runs GITHUB_LIST_REPOSITORIES_FOR_THE_AUTHENTICATED_USER via Composio; when the action returns successful=false with an empty error string this fallback message is thrown.

Source

Thrown at app/src/components/skills/inputs/RepoPicker.tsx:69

  const [error, setError] = useState<string | null>(null);

  // ── Fetch repos via Composio (mirrors DevWorkflowPanel) ────────────
  const loadRepos = useCallback(async () => {
    setLoading(true);
    setError(null);
    try {
      // Step 1: Is GitHub connected via Composio?
      const conns = await listConnections();
      const ghConn = conns.connections?.find(
        c =>
          c.toolkit.toLowerCase().includes('github') &&
          (c.status === 'ACTIVE' || c.status === 'CONNECTED')
      );
      if (!ghConn) throw new Error('NOT_CONNECTED');

      // Step 2: Fetch repos.
      const res = await composioExecute('GITHUB_LIST_REPOSITORIES_FOR_THE_AUTHENTICATED_USER', {});
      if (!res.successful) throw new Error(res.error ?? 'Failed to fetch repositories');

      // Step 3: Parse — GitHub API returns an array of repo objects;
      // Composio sometimes wraps it under `.repositories`.
      const raw = res.data;
      const items = Array.isArray(raw)
        ? raw
        : ((raw as Record<string, unknown>)?.repositories ?? []);
      const list: ComposioGhRepo[] = Array.isArray(items)
        ? (items as Record<string, unknown>[]).map(r => ({
            owner: String((r.owner as Record<string, unknown>)?.login ?? r.owner ?? ''),
            repo: String(r.name ?? ''),
            fullName: String(
              r.full_name ?? `${(r.owner as Record<string, unknown>)?.login ?? r.owner}/${r.name}`
            ),
            private: r.private as boolean | undefined,
            defaultBranch: r.default_branch as string | undefined,
            htmlUrl: r.html_url as string | undefined,
          }))

View on GitHub (pinned to a221052e0d)

Solutions

  1. Verify the GitHub (Composio) connection is ACTIVE in Connections; reconnect if stale
  2. Retry after a short wait for rate limits to clear
  3. Reproduce the action from the Composio dashboard to see the underlying error; check Composio status
Defensive patterns

Strategy: try-catch

Validate before calling

// Gate the picker on connection freshness before any fetch:
const conns = await listConnections();
const gh = conns.connections?.find(c =>
  c.toolkit.toLowerCase().includes('github') &&
  (c.status === 'ACTIVE' || c.status === 'CONNECTED')
);
if (!gh) { /* show connect prompt, skip the Composio call entirely */ }

Type guard

const isActiveGithub = (c: { toolkit: string; status: string }): boolean =>
  c.toolkit.toLowerCase().includes('github') &&
  (c.status === 'ACTIVE' || c.status === 'CONNECTED');

Try / catch

try {
  await loadRepos();
} catch (e) {
  const msg = e instanceof Error ? e.message : String(e);
  if (msg === 'NOT_CONNECTED') { promptConnectGithub(); return; }
  if (msg === 'Failed to fetch repositories') { offerRetryAfterDelay(); return; }
  throw e;
}

Prevention

When it happens

Trigger: Composio executes the action but reports failure with res.error empty: rate limit, stale Composio connection token, or a GitHub API error swallowed upstream.

Common situations: Composio connection needs re-auth after token expiry; Composio throttling or outage; OAuth grant revoked on GitHub.

Related errors


AI-assisted analysis of tinyhumansai/openhuman@a221052e0d (2026-08-16). Data as JSON: /api/errors/86aef9e79a1ecc20. Report an issue: GitHub.