mirror of
https://github.com/diegosouzapw/OmniRoute.git
synced 2026-09-16 03:42:21 +03:00
Landed with the design call resolved per the owner's pick — **option 1**: the synced store is now endpoint-agnostic (persistDiscoveredModels and managedModelImport no longer drop non-chat models at write time), and chat selectability moved to read time (auto-pool expansion in autoStrategy applies filterChatSelectableModels; the models-route projection already had its chatOnly filter). Your discovery test now passes end-to-end (3/3): /api/show capabilities persist per connection and image/embedding requests route through the advertising host. Reconciliation notes: conflicted areas merged onto the current tip (adobe discovery import, requestedModel preflight signature, resolvedProvider fast-path coexists with the synced-route override — explicit resolution wins); carried base-red drains (#10055 memoization, #11071 test variants) dropped as already-landed; the managed-model-import exclusion test was propagated to the new contract (image/video models persist; the read filter still hides them from chat pickers — pinned by a new assertion). Full battery: 205/206 focused (the one red is a confirmed periodic-timer timing flake on the loaded devbox — 20/20 isolated), autoCombo vitest 30/30, combo suites 46/46, gates + typecheck clean. Thank you @yourspraveen — the capability probe + routing design was right; it just needed the store contract opened up. Fixes #11087.
83 lines
2.5 KiB
TypeScript
83 lines
2.5 KiB
TypeScript
/**
|
|
* usage/firecrawl.ts — Firecrawl team credit usage for Provider Limits.
|
|
*
|
|
* GET /v2/team/credit-usage via firecrawlQuotaFetcher; shapes remaining/plan
|
|
* credits into the standard `{ plan, quotas }` response.
|
|
*/
|
|
|
|
import {
|
|
fetchFirecrawlQuota,
|
|
getFirecrawlBaseUrl,
|
|
type FirecrawlQuota,
|
|
} from "../firecrawlQuotaFetcher.ts";
|
|
import { createQuotaFromUsage, parseResetTime } from "./quota.ts";
|
|
|
|
function createFirecrawlPlanQuota(q: FirecrawlQuota) {
|
|
if (q.overPlan) {
|
|
return {
|
|
used: 0,
|
|
total: q.planCredits,
|
|
remaining: q.remainingCredits,
|
|
remainingPercentage: q.planCredits > 0 ? (q.remainingCredits / q.planCredits) * 100 : 100,
|
|
resetAt: parseResetTime(q.resetAt),
|
|
unlimited: false,
|
|
extraCreditsInferred: q.extraCreditsInferred,
|
|
overPlan: true,
|
|
};
|
|
}
|
|
|
|
return {
|
|
...createQuotaFromUsage(q.used, q.total, q.resetAt),
|
|
extraCreditsInferred: 0,
|
|
overPlan: false,
|
|
};
|
|
}
|
|
|
|
export async function getFirecrawlUsage(
|
|
connectionId: string,
|
|
apiKey?: string,
|
|
connection?: Record<string, unknown>
|
|
) {
|
|
if (!connectionId) {
|
|
return { message: "Firecrawl: connection id unavailable." };
|
|
}
|
|
|
|
const customBase = getFirecrawlBaseUrl(connection);
|
|
if (customBase) {
|
|
return {
|
|
plan: "Firecrawl · Self-Hosted Local",
|
|
quotas: {},
|
|
message: `Connected to self-hosted Firecrawl instance (${customBase})`,
|
|
};
|
|
}
|
|
|
|
try {
|
|
// The explicit `apiKey` argument was silently dropped when #91bb6aa619 moved
|
|
// this to fetchFirecrawlQuota(connectionId, connection): the fetcher reads the
|
|
// key off the connection record, so a caller that passes the key directly —
|
|
// without a connection carrying it — always got "API key not available".
|
|
const resolvedConnection = apiKey ? { ...(connection || {}), apiKey } : connection;
|
|
const live = await fetchFirecrawlQuota(connectionId, resolvedConnection);
|
|
if (!live) {
|
|
return { message: "Firecrawl API key not available or credit usage unavailable." };
|
|
}
|
|
|
|
const q = live as FirecrawlQuota;
|
|
const monthly = createFirecrawlPlanQuota(q);
|
|
|
|
return {
|
|
plan: "Firecrawl · Monthly credits",
|
|
quotas: {
|
|
monthly,
|
|
},
|
|
remainingCredits: q.remainingCredits,
|
|
planCredits: q.planCredits,
|
|
extraCreditsInferred: q.extraCreditsInferred,
|
|
overPlan: q.overPlan,
|
|
limitReached: q.limitReached,
|
|
};
|
|
} catch (error) {
|
|
return { message: `Firecrawl usage error: ${(error as Error).message}` };
|
|
}
|
|
}
|