mirror of
https://github.com/garrytan/gbrain.git
synced 2026-07-27 22:15:33 +00:00
fix(ai): Ollama compatibility fixes for local-first usage (#1854 takeover)
Four of the five fixes from #1854, rebased onto current master: 1. budget-tracker: FREE_LOCAL_CHAT_PROVIDERS (ollama, llama-server) returns zero pricing for local chat providers so --max-cost bounded brainstorm/lsd no longer TX2 hard-fails on local inference. Sibling to FREE_LOCAL_EMBED_PROVIDERS / FREE_LOCAL_RERANK_PROVIDERS. 2. brainstorm/judges: coerce numeric idea ids (5 -> "Idea 05") before the string type check; some models (e.g. Kimi K2 via Ollama) emit numeric ids and previously had every idea silently rejected. 3. think: the buildGracefulMessage "no LLM available" text now points at chat_model / expansion_model / anthropic_api_key, not just the Anthropic key, since that sentinel can fire for any provider. 4. ollama recipe: add chat + expansion touchpoints (llama3.3, qwen3, deepseek-r1; supports_tools, zero cost) so recipes can route reasoning calls to Ollama. The fifth fix from #1854 (scope the NO_ANTHROPIC_API_KEY warning to the anthropic provider) was superseded on master by the #1698 probe work: probeChatModel only returns 'unavailable' for anthropic-no-key, so non-Anthropic providers already get MODEL_NOT_USABLE instead. Co-authored-by: Luna <luna@starstudiolabs.com> Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
This commit is contained in:
co-authored by
Luna
Claude Fable 5
parent
1a449bf501
commit
10e087bbaf
@@ -33,6 +33,20 @@ export const ollama: Recipe = {
|
||||
// OLLAMA_NUM_PARALLEL config; no static cap to declare. v0.32 (#779).
|
||||
no_batch_cap: true,
|
||||
},
|
||||
chat: {
|
||||
models: ['llama3.3', 'qwen3', 'deepseek-r1'],
|
||||
supports_tools: true,
|
||||
supports_subagent_loop: false,
|
||||
supports_prompt_cache: false,
|
||||
cost_per_1m_input_usd: 0,
|
||||
cost_per_1m_output_usd: 0,
|
||||
price_last_verified: '2026-06-02',
|
||||
},
|
||||
expansion: {
|
||||
models: ['llama3.3', 'qwen3', 'deepseek-r1'],
|
||||
cost_per_1m_tokens_usd: 0,
|
||||
price_last_verified: '2026-06-02',
|
||||
},
|
||||
},
|
||||
setup_hint: 'Install Ollama from https://ollama.ai, then `ollama pull nomic-embed-text` and `ollama serve`.',
|
||||
};
|
||||
|
||||
@@ -361,6 +361,11 @@ function isAxisScoreInRange(n: unknown): n is number {
|
||||
function validateIdeaShape(raw: unknown): { id: string; scores: JudgeAxisScores; note: string } | null {
|
||||
if (typeof raw !== 'object' || raw === null) return null;
|
||||
const r = raw as Record<string, unknown>;
|
||||
// Some models (e.g. Kimi K2) return numeric ids instead of string ids like "Idea 01".
|
||||
// Coerce to string for compatibility.
|
||||
if (typeof r.id === 'number') {
|
||||
r.id = 'Idea ' + String(r.id).padStart(2, '0');
|
||||
}
|
||||
if (typeof r.id !== 'string') return null;
|
||||
const note = typeof r.note === 'string' ? r.note : '';
|
||||
const s = r.scores;
|
||||
|
||||
@@ -155,6 +155,20 @@ const FREE_LOCAL_EMBED_PROVIDERS: ReadonlySet<string> = new Set([
|
||||
'llama-server',
|
||||
]);
|
||||
|
||||
/**
|
||||
* Provider id prefixes whose chat models run on local inference (electricity,
|
||||
* not API tokens) and so price at $0. Without this, a `--max-cost`-bounded
|
||||
* brainstorm/lsd configured for a local chat provider TX2 hard-fails because
|
||||
* lookupPricing has no entry for them. Matched against the provider half
|
||||
* of the `provider:model` string.
|
||||
*
|
||||
* Sibling to FREE_LOCAL_EMBED_PROVIDERS and FREE_LOCAL_RERANK_PROVIDERS.
|
||||
*/
|
||||
const FREE_LOCAL_CHAT_PROVIDERS: ReadonlySet<string> = new Set([
|
||||
'ollama',
|
||||
'llama-server',
|
||||
]);
|
||||
|
||||
/**
|
||||
* Look up `modelId` in the chat or embedding pricing maps. Returns a
|
||||
* per-1M-token price tuple, or null when unknown.
|
||||
@@ -201,6 +215,9 @@ function lookupPricing(modelId: string, kind: BudgetKind): ModelPricing | null {
|
||||
if (kind === 'rerank' && providerId && FREE_LOCAL_RERANK_PROVIDERS.has(providerId)) {
|
||||
return { input: 0, output: 0 };
|
||||
}
|
||||
if (kind === 'chat' && providerId && FREE_LOCAL_CHAT_PROVIDERS.has(providerId)) {
|
||||
return { input: 0, output: 0 };
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
||||
|
||||
@@ -815,7 +815,7 @@ function buildGracefulMessage(modelStr: string): {
|
||||
type: 'message',
|
||||
role: 'assistant',
|
||||
model: modelStr,
|
||||
content: [{ type: 'text', text: '(no LLM available — set anthropic_api_key via gbrain config or ANTHROPIC_API_KEY env)' }],
|
||||
content: [{ type: 'text', text: '(no LLM available — set chat_model, expansion_model, or anthropic_api_key via gbrain config)' }],
|
||||
usage: { input_tokens: 0, output_tokens: 0 },
|
||||
stop_reason: 'end_turn',
|
||||
};
|
||||
|
||||
Reference in New Issue
Block a user