Files
openclaw/src/agents/models-config.providers.nvidia.test.ts
2026-04-30 02:58:40 +01:00

193 lines
6.0 KiB
TypeScript

import { describe, expect, it, vi } from "vitest";
import type { ModelDefinitionConfig, ModelProviderConfig } from "../config/types.models.js";
import { resolveEnvApiKey } from "./model-auth-env.js";
import {
resolveEnvApiKeyVarName,
resolveMissingProviderApiKey,
} from "./models-config.providers.secret-helpers.js";
vi.mock("../plugins/setup-registry.js", () => ({
resolvePluginSetupProvider: () => undefined,
}));
vi.mock("../infra/shell-env.js", () => ({
getShellEnvAppliedKeys: () => [],
}));
vi.mock("./provider-auth-aliases.js", () => ({
resolveProviderAuthAliasMap: () => ({}),
resolveProviderIdForAuth: (provider: string) => provider.trim().toLowerCase(),
}));
vi.mock("./model-auth-env-vars.js", () => {
const candidates = {
minimax: ["MINIMAX_API_KEY"],
"minimax-portal": ["MINIMAX_OAUTH_TOKEN"],
nvidia: ["NVIDIA_API_KEY"],
vllm: ["VLLM_API_KEY"],
} as const;
return {
PROVIDER_ENV_API_KEY_CANDIDATES: candidates,
listKnownProviderEnvApiKeyNames: () => [...new Set(Object.values(candidates).flat())],
resolveProviderEnvApiKeyCandidates: () => candidates,
resolveProviderEnvAuthEvidence: () => ({}),
};
});
const NVIDIA_BASE_URL = "https://integrate.api.nvidia.com/v1";
const MINIMAX_BASE_URL = "https://api.minimax.io/anthropic";
const VLLM_DEFAULT_BASE_URL = "http://127.0.0.1:8000/v1";
function createTestModel(id: string): ModelDefinitionConfig {
return {
id,
name: id,
reasoning: false,
input: ["text"],
cost: { input: 0, output: 0, cacheRead: 0, cacheWrite: 0 },
contextWindow: 8192,
maxTokens: 4096,
};
}
function resolveMinimaxCatalogBaseUrl(env: NodeJS.ProcessEnv = process.env): string {
const rawHost = env.MINIMAX_API_HOST?.trim();
if (!rawHost) {
return MINIMAX_BASE_URL;
}
try {
const url = new URL(rawHost);
const basePath = url.pathname.replace(/\/+$/, "");
if (basePath.endsWith("/anthropic")) {
return `${url.origin}${basePath}`;
}
return `${url.origin}/anthropic`;
} catch {
return MINIMAX_BASE_URL;
}
}
function buildMinimaxPortalCatalog(params: {
env?: NodeJS.ProcessEnv;
envApiKey?: string;
explicitApiKey?: string;
explicitBaseUrl?: string;
hasProfiles?: boolean;
}): ModelProviderConfig | null {
const apiKey =
params.envApiKey ??
params.explicitApiKey ??
(params.hasProfiles ? "MINIMAX_OAUTH_TOKEN" : undefined);
if (!apiKey) {
return null;
}
return {
baseUrl: params.explicitBaseUrl || resolveMinimaxCatalogBaseUrl(params.env),
api: "anthropic-messages",
authHeader: true,
apiKey,
models: [createTestModel("MiniMax-M2.7")],
};
}
describe("NVIDIA provider", () => {
it("should include nvidia when NVIDIA_API_KEY is configured", () => {
const provider = resolveMissingProviderApiKey({
providerKey: "nvidia",
provider: {
baseUrl: NVIDIA_BASE_URL,
api: "openai-completions",
models: [createTestModel("nvidia/test-model")],
},
env: { NVIDIA_API_KEY: "test-key" } as NodeJS.ProcessEnv,
profileApiKey: undefined,
});
expect(provider.apiKey).toBe("NVIDIA_API_KEY");
expect(provider.models?.length).toBeGreaterThan(0);
});
it("resolves the nvidia api key value from env", () => {
const auth = resolveEnvApiKey("nvidia", {
NVIDIA_API_KEY: "nvidia-test-api-key",
} as NodeJS.ProcessEnv);
expect(auth).toEqual({
apiKey: "nvidia-test-api-key",
source: "env: NVIDIA_API_KEY",
});
});
});
describe("MiniMax implicit provider (#15275)", () => {
it("should use anthropic-messages API for API-key provider", () => {
const provider = resolveMissingProviderApiKey({
providerKey: "minimax",
provider: {
baseUrl: MINIMAX_BASE_URL,
api: "anthropic-messages",
authHeader: true,
models: [createTestModel("MiniMax-M2.7")],
},
env: { MINIMAX_API_KEY: "test-key" } as NodeJS.ProcessEnv,
profileApiKey: undefined,
});
expect(provider.api).toBe("anthropic-messages");
expect(provider.authHeader).toBe(true);
expect(provider.apiKey).toBe("MINIMAX_API_KEY");
expect(provider.baseUrl).toBe("https://api.minimax.io/anthropic");
});
it("should respect MINIMAX_API_HOST env var for CN endpoint (#34487)", () => {
const env = {
MINIMAX_API_KEY: "test-key",
MINIMAX_API_HOST: "https://api.minimaxi.com",
} as NodeJS.ProcessEnv;
expect(resolveMinimaxCatalogBaseUrl(env)).toBe("https://api.minimaxi.com/anthropic");
expect(buildMinimaxPortalCatalog({ env, envApiKey: "MINIMAX_API_KEY" })?.baseUrl).toBe(
"https://api.minimaxi.com/anthropic",
);
});
it("should set authHeader for minimax portal provider", () => {
expect(buildMinimaxPortalCatalog({ hasProfiles: true })?.authHeader).toBe(true);
});
it("should include minimax portal provider when MINIMAX_OAUTH_TOKEN is configured", () => {
expect(
resolveEnvApiKeyVarName("minimax-portal", {
MINIMAX_OAUTH_TOKEN: "portal-token",
} as NodeJS.ProcessEnv),
).toBe("MINIMAX_OAUTH_TOKEN");
const provider = buildMinimaxPortalCatalog({ hasProfiles: true });
expect(provider?.authHeader).toBe(true);
expect(provider?.apiKey).toBe("MINIMAX_OAUTH_TOKEN");
});
});
describe("vLLM provider", () => {
it("should not include vllm when no API key is configured", () => {
expect(resolveEnvApiKeyVarName("vllm", {} as NodeJS.ProcessEnv)).toBeUndefined();
});
it("should include vllm when VLLM_API_KEY is set", () => {
const provider = resolveMissingProviderApiKey({
providerKey: "vllm",
provider: {
baseUrl: VLLM_DEFAULT_BASE_URL,
api: "openai-completions",
models: [createTestModel("meta-llama/Meta-Llama-3-8B-Instruct")],
},
env: { VLLM_API_KEY: "test-key" } as NodeJS.ProcessEnv,
profileApiKey: undefined,
});
expect(provider.apiKey).toBe("VLLM_API_KEY");
expect(provider.baseUrl).toBe(VLLM_DEFAULT_BASE_URL);
expect(provider.api).toBe("openai-completions");
expect(provider.models).toHaveLength(1);
});
});