Files
openclaw/extensions/github-copilot/auth.ts
Pengfei Ni 55d00f335a feat(github-copilot): add embedding provider for memory search
Add GitHub Copilot as a memory search embedding provider so users with
Copilot subscriptions can use embeddings without a separate API key.

- Extract resolveFirstGithubToken to shared auth.ts for reuse
- Add MemoryEmbeddingProviderAdapter with dynamic model discovery
  via the Copilot /models endpoint, auto-selecting the best
  available embedding model (prefers text-embedding-3-small)
- Register the provider at auto-selection priority 15 (between
  local and OpenAI) and declare the memoryEmbeddingProviders
  contract in the plugin manifest
- Match models by ID pattern when supported_endpoints is empty,
  as the Copilot API lists embedding models without declaring
  their endpoint
- Add docs for memory search provider tables, config reference,
  and the GitHub Copilot provider page
2026-04-15 10:38:39 +01:00

41 lines
1.3 KiB
TypeScript

import {
coerceSecretRef,
ensureAuthProfileStore,
listProfilesForProvider,
} from "openclaw/plugin-sdk/provider-auth";
import { PROVIDER_ID } from "./models.js";
export function resolveFirstGithubToken(params: { agentDir?: string; env: NodeJS.ProcessEnv }): {
githubToken: string;
hasProfile: boolean;
} {
const authStore = ensureAuthProfileStore(params.agentDir, {
allowKeychainPrompt: false,
});
const hasProfile = listProfilesForProvider(authStore, PROVIDER_ID).length > 0;
const envToken =
params.env.COPILOT_GITHUB_TOKEN ?? params.env.GH_TOKEN ?? params.env.GITHUB_TOKEN ?? "";
const githubToken = envToken.trim();
if (githubToken || !hasProfile) {
return { githubToken, hasProfile };
}
const profileId = listProfilesForProvider(authStore, PROVIDER_ID)[0];
const profile = profileId ? authStore.profiles[profileId] : undefined;
if (profile?.type !== "token") {
return { githubToken: "", hasProfile };
}
const directToken = profile.token?.trim() ?? "";
if (directToken) {
return { githubToken: directToken, hasProfile };
}
const tokenRef = coerceSecretRef(profile.tokenRef);
if (tokenRef?.source === "env" && tokenRef.id.trim()) {
return {
githubToken: (params.env[tokenRef.id] ?? process.env[tokenRef.id] ?? "").trim(),
hasProfile,
};
}
return { githubToken: "", hasProfile };
}