@juspay/neurolink
Version:
The pipe layer of an AI nervous system: one interface connecting provider neurons to your application, across three inference types — generate, stream and decide. `decide` returns typed, calibrated judgements from a non-generative model (~400ms, ~$0.00002
78 lines (77 loc) • 2.76 kB
JavaScript
export function inferClaudeProxyModelTier(modelName) {
const normalized = modelName.toLowerCase();
if (normalized.includes("opus")) {
return "opus";
}
if (normalized.includes("sonnet")) {
return "sonnet";
}
if (normalized.includes("haiku")) {
return "haiku";
}
return "other";
}
/**
* Build a translation plan for a Claude-compatible proxy request.
* The plan lists the primary provider followed by eligible fallback targets.
* All configured fallback entries are always eligible — no contract-based gating.
* An "auto-provider" entry is appended only when explicitly enabled by the
* caller. This keeps an empty fallback chain from silently escaping to an
* unrelated provider.
*/
export function buildProxyTranslationPlan(primary, fallbackChain, requestedModel, _parsed, allowAutoFallback = false) {
const attempts = [
{
provider: primary.provider,
model: primary.model,
label: `${primary.provider}/${primary.model ?? "unknown"}`,
},
];
for (const fallback of fallbackChain) {
if (fallback.provider === primary.provider &&
fallback.model === primary.model) {
continue;
}
attempts.push({
provider: fallback.provider,
model: fallback.model,
...(fallback.reasoningEffort !== undefined
? { reasoningEffort: fallback.reasoningEffort }
: {}),
label: `${fallback.provider}/${fallback.model}`,
});
}
// A provider chosen by the translation layer is an explicit opt-in. It is
// intentionally not a default when configured entries are absent or deduped.
if (allowAutoFallback &&
(fallbackChain.length === 0 || attempts.length === 1)) {
attempts.push({ label: "auto-provider" });
}
return {
requestedModel,
modelTier: inferClaudeProxyModelTier(requestedModel),
attempts,
skipped: [],
};
}
// ---------------------------------------------------------------------------
// Retry-after parsing helper
// ---------------------------------------------------------------------------
/**
* Parse the retry-after header from an upstream 429 response.
* Returns milliseconds to wait, or 0 if no valid header present.
*/
export function parseRetryAfterMs(retryAfterHeader) {
if (!retryAfterHeader) {
return 0;
}
const seconds = parseInt(retryAfterHeader, 10);
if (!Number.isNaN(seconds)) {
return Math.max(1, seconds) * 1000;
}
const date = new Date(retryAfterHeader);
if (!Number.isNaN(date.getTime())) {
return Math.max(1000, date.getTime() - Date.now());
}
return 0;
}