@acarmisc/backstage-plugin-litellm-backend 0.22.0 → 0.23.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/client.d.ts +12 -1
- package/dist/client.js +91 -0
- package/dist/index.cjs.js +121 -4
- package/dist/index.cjs.js.map +3 -3
- package/dist/router.js +3 -1
- package/dist/routes/insights.d.ts +3 -0
- package/dist/routes/insights.js +43 -0
- package/dist/types.cjs.js.map +1 -1
- package/dist/types.d.ts +1 -1
- package/package.json +2 -2
package/dist/router.js
CHANGED
|
@@ -56,6 +56,7 @@ const opencode_2 = require("./routes/opencode");
|
|
|
56
56
|
const teams_1 = require("./routes/teams");
|
|
57
57
|
const objectPermissions_1 = require("./routes/objectPermissions");
|
|
58
58
|
const teamUsage_1 = require("./routes/teamUsage");
|
|
59
|
+
const insights_1 = require("./routes/insights");
|
|
59
60
|
const bridge_1 = require("./routes/bridge");
|
|
60
61
|
const teamFetch_1 = require("./http/teamFetch");
|
|
61
62
|
async function createRouter(options) {
|
|
@@ -311,7 +312,7 @@ async function createRouter(options) {
|
|
|
311
312
|
// string or body — so service/external principals (and anonymous callers)
|
|
312
313
|
// are rejected instead of being allowed to name an arbitrary user_id.
|
|
313
314
|
const requireUser = (0, withUser_1.createRequireUser)(ctx);
|
|
314
|
-
router.use(['/user/info', '/keys', '/usage'], requireUser);
|
|
315
|
+
router.use(['/user/info', '/keys', '/usage', '/insights'], requireUser);
|
|
315
316
|
// Register config routes (/health, /config, /openapi.json, /provisioning/preview)
|
|
316
317
|
(0, config_1.registerConfigRoutes)(router, ctx);
|
|
317
318
|
(0, keys_1.registerKeysRoutes)(router, ctx);
|
|
@@ -319,6 +320,7 @@ async function createRouter(options) {
|
|
|
319
320
|
(0, teams_1.registerTeamsRoutes)(router, ctx);
|
|
320
321
|
(0, objectPermissions_1.registerObjectPermissionsRoutes)(router, ctx);
|
|
321
322
|
(0, teamUsage_1.registerTeamUsageRoutes)(router, ctx);
|
|
323
|
+
(0, insights_1.registerInsightsRoutes)(router, ctx);
|
|
322
324
|
(0, bridge_1.registerBridgeRoutes)(router, ctx, { config, tokenVerifier: options.tokenVerifier });
|
|
323
325
|
return router;
|
|
324
326
|
}
|
|
@@ -0,0 +1,43 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.registerInsightsRoutes = registerInsightsRoutes;
|
|
4
|
+
const provisioning_1 = require("../provisioning");
|
|
5
|
+
const errors_1 = require("../errors");
|
|
6
|
+
const withUser_1 = require("./middleware/withUser");
|
|
7
|
+
function registerInsightsRoutes(router, ctx) {
|
|
8
|
+
const { client, catalogClient, auth, logger, auditGroup } = ctx;
|
|
9
|
+
const requireUser = (0, withUser_1.createRequireUser)(ctx);
|
|
10
|
+
router.get('/insights/spend-logs', requireUser, async (req, res) => {
|
|
11
|
+
try {
|
|
12
|
+
const { start_date, end_date, userId, teamId, page, page_size } = req.query;
|
|
13
|
+
if (!start_date || !end_date) {
|
|
14
|
+
res.status(400).json({ error: 'start_date and end_date are required' });
|
|
15
|
+
return;
|
|
16
|
+
}
|
|
17
|
+
const tokenEntityRef = res.locals.tokenEntityRef;
|
|
18
|
+
await (0, withUser_1.getProvisionedUser)(ctx, res);
|
|
19
|
+
const callerId = res.locals.userId;
|
|
20
|
+
const isAudit = auditGroup
|
|
21
|
+
? await (0, provisioning_1.isUserMemberOfGroup)(tokenEntityRef, auditGroup, catalogClient, auth, logger)
|
|
22
|
+
: false;
|
|
23
|
+
// Server-side scoping: only audit-group members may query other
|
|
24
|
+
// users/teams — everyone else is forced to their own user_id.
|
|
25
|
+
const result = await client.getSpendLogs({
|
|
26
|
+
startDate: start_date,
|
|
27
|
+
endDate: end_date,
|
|
28
|
+
userId: isAudit ? userId || callerId : callerId,
|
|
29
|
+
teamId: isAudit ? teamId : undefined,
|
|
30
|
+
page: page ? Number(page) : undefined,
|
|
31
|
+
pageSize: page_size ? Number(page_size) : undefined,
|
|
32
|
+
});
|
|
33
|
+
res.json(result);
|
|
34
|
+
}
|
|
35
|
+
catch (error) {
|
|
36
|
+
if (error instanceof provisioning_1.ProvisioningError) {
|
|
37
|
+
res.status(error.status).json(error.body);
|
|
38
|
+
return;
|
|
39
|
+
}
|
|
40
|
+
(0, errors_1.sendError)(res, error, logger, 'fetch spend logs');
|
|
41
|
+
}
|
|
42
|
+
});
|
|
43
|
+
}
|
package/dist/types.cjs.js.map
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
{
|
|
2
2
|
"version": 3,
|
|
3
3
|
"sources": ["../src/types.ts"],
|
|
4
|
-
"sourcesContent": ["// Re-export common types for backward compatibility\nexport {\n type UserInfo,\n type TeamMember,\n type TeamObjectPermission,\n type TeamInfo,\n type CreateTeamResponse,\n type VirtualKey,\n type ModelInfo,\n type UsageModelBreakdown,\n type UsageKeyBreakdown,\n type UsageDailyPoint,\n type UsageDailyModelPoint,\n type UsageMetrics,\n type TeamMemberUsage,\n type TeamMemberUsageRow,\n type GenerateKeyRequest,\n type UpdateKeyRequest,\n type GenerateKeyResponse,\n type AuditLogEntry,\n type PaginatedAuditLogs,\n} from '@acarmisc/backstage-plugin-litellm-common';\n\nexport interface CreateTeamRequest {\n team_alias: string;\n models?: string[];\n max_budget?: number;\n budget_duration?: string;\n tpm_limit?: number;\n rpm_limit?: number;\n metadata?: Record<string, unknown>;\n object_permission?: {\n vector_stores?: string[];\n mcp_servers?: string[];\n mcp_access_groups?: string[];\n };\n}\n\nexport interface UpdateTeamRequest extends Partial<CreateTeamRequest> {\n team_id: string;\n blocked?: boolean;\n}\n\n/**\n * Shape of a single entry inside LiteLLM's `/user/info` `keys` array.\n * Differs from VirtualKey: uses `expires` (not `expires_at`), exposes\n * both a hashed `token` and a masked `key_name`, and fields are nullable\n * rather than optional.\n */\nexport interface LiteLLMUserKey {\n token: string;\n key_name?: string;\n key_alias?: string | null;\n spend?: number;\n expires?: string | null;\n models?: string[];\n tpm_limit?: number | null;\n rpm_limit?: number | null;\n max_budget?: number | null;\n budget_duration?: string | null;\n user_id?: string | null;\n team_id?: string | null;\n created_at: string;\n blocked?: boolean | null;\n /** Arbitrary metadata stored on the key record. */\n metadata?: Record<string, unknown> | null;\n}\n\nexport interface DeleteKeyRequest {\n keys: string[];\n}\n\nexport interface LiteLLMConfig {\n baseUrl: string;\n masterKey: string;\n}\n\nexport interface ProvisioningDefaults {\n maxBudget: number;\n budgetDuration: string;\n models: string[];\n teams: string[];\n tpmLimit?: number;\n rpmLimit?: number;\n /**\n * LiteLLM user role applied on /user/new. Defaults to \"internal_user\"\n * which grants self-service Create/Delete/View on the user's own keys.\n * Valid values: proxy_admin, proxy_admin_viewer, internal_user,\n * internal_user_viewer, team.\n */\n userRole?: string;\n metadata: Record<string, string>;\n}\n\nexport interface RoleConfig {\n group: string;\n maxBudget?: number;\n budgetDuration?: string;\n models?: string[];\n teams?: string[];\n tpmLimit?: number;\n rpmLimit?: number;\n userRole?: string;\n metadata?: Record<string, string>;\n}\n\nexport interface CreateUserRequest {\n user_id: string;\n user_email?: string;\n user_alias?: string;\n user_role?: string;\n max_budget?: number;\n budget_duration?: string;\n models?: string[];\n teams?: string[];\n tpm_limit?: number;\n rpm_limit?: number;\n metadata?: Record<string, string>;\n auto_create_key?: boolean;\n}\n\nexport interface CreateUserResponse {\n user_id: string;\n user_email?: string;\n max_budget?: number;\n models?: string[];\n teams?: string[];\n}\n\n\nexport interface AuditLogsParams {\n page?: number;\n page_size?: number;\n start_date?: string;\n end_date?: string;\n action?: string;\n table_name?: string;\n changed_by?: string;\n sort_by?: string;\n sort_order?: 'asc' | 'desc';\n}\n"],
|
|
4
|
+
"sourcesContent": ["// Re-export common types for backward compatibility\nexport {\n type UserInfo,\n type TeamMember,\n type TeamObjectPermission,\n type TeamInfo,\n type CreateTeamResponse,\n type VirtualKey,\n type ModelInfo,\n type UsageModelBreakdown,\n type UsageKeyBreakdown,\n type UsageDailyPoint,\n type UsageDailyModelPoint,\n type UsageMetrics,\n type TeamMemberUsage,\n type TeamMemberUsageRow,\n type GenerateKeyRequest,\n type UpdateKeyRequest,\n type GenerateKeyResponse,\n type AuditLogEntry,\n type PaginatedAuditLogs,\n type SpendLogEntry,\n type SpendLogsParams,\n type PaginatedSpendLogs,\n} from '@acarmisc/backstage-plugin-litellm-common';\n\nexport interface CreateTeamRequest {\n team_alias: string;\n models?: string[];\n max_budget?: number;\n budget_duration?: string;\n tpm_limit?: number;\n rpm_limit?: number;\n metadata?: Record<string, unknown>;\n object_permission?: {\n vector_stores?: string[];\n mcp_servers?: string[];\n mcp_access_groups?: string[];\n };\n}\n\nexport interface UpdateTeamRequest extends Partial<CreateTeamRequest> {\n team_id: string;\n blocked?: boolean;\n}\n\n/**\n * Shape of a single entry inside LiteLLM's `/user/info` `keys` array.\n * Differs from VirtualKey: uses `expires` (not `expires_at`), exposes\n * both a hashed `token` and a masked `key_name`, and fields are nullable\n * rather than optional.\n */\nexport interface LiteLLMUserKey {\n token: string;\n key_name?: string;\n key_alias?: string | null;\n spend?: number;\n expires?: string | null;\n models?: string[];\n tpm_limit?: number | null;\n rpm_limit?: number | null;\n max_budget?: number | null;\n budget_duration?: string | null;\n user_id?: string | null;\n team_id?: string | null;\n created_at: string;\n blocked?: boolean | null;\n /** Arbitrary metadata stored on the key record. */\n metadata?: Record<string, unknown> | null;\n}\n\nexport interface DeleteKeyRequest {\n keys: string[];\n}\n\nexport interface LiteLLMConfig {\n baseUrl: string;\n masterKey: string;\n}\n\nexport interface ProvisioningDefaults {\n maxBudget: number;\n budgetDuration: string;\n models: string[];\n teams: string[];\n tpmLimit?: number;\n rpmLimit?: number;\n /**\n * LiteLLM user role applied on /user/new. Defaults to \"internal_user\"\n * which grants self-service Create/Delete/View on the user's own keys.\n * Valid values: proxy_admin, proxy_admin_viewer, internal_user,\n * internal_user_viewer, team.\n */\n userRole?: string;\n metadata: Record<string, string>;\n}\n\nexport interface RoleConfig {\n group: string;\n maxBudget?: number;\n budgetDuration?: string;\n models?: string[];\n teams?: string[];\n tpmLimit?: number;\n rpmLimit?: number;\n userRole?: string;\n metadata?: Record<string, string>;\n}\n\nexport interface CreateUserRequest {\n user_id: string;\n user_email?: string;\n user_alias?: string;\n user_role?: string;\n max_budget?: number;\n budget_duration?: string;\n models?: string[];\n teams?: string[];\n tpm_limit?: number;\n rpm_limit?: number;\n metadata?: Record<string, string>;\n auto_create_key?: boolean;\n}\n\nexport interface CreateUserResponse {\n user_id: string;\n user_email?: string;\n max_budget?: number;\n models?: string[];\n teams?: string[];\n}\n\n\nexport interface AuditLogsParams {\n page?: number;\n page_size?: number;\n start_date?: string;\n end_date?: string;\n action?: string;\n table_name?: string;\n changed_by?: string;\n sort_by?: string;\n sort_order?: 'asc' | 'desc';\n}\n"],
|
|
5
5
|
"mappings": ";;;;;;;;;;;;;;;;AAAA;AAAA;",
|
|
6
6
|
"names": []
|
|
7
7
|
}
|
package/dist/types.d.ts
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
export { type UserInfo, type TeamMember, type TeamObjectPermission, type TeamInfo, type CreateTeamResponse, type VirtualKey, type ModelInfo, type UsageModelBreakdown, type UsageKeyBreakdown, type UsageDailyPoint, type UsageDailyModelPoint, type UsageMetrics, type TeamMemberUsage, type TeamMemberUsageRow, type GenerateKeyRequest, type UpdateKeyRequest, type GenerateKeyResponse, type AuditLogEntry, type PaginatedAuditLogs, } from '@acarmisc/backstage-plugin-litellm-common';
|
|
1
|
+
export { type UserInfo, type TeamMember, type TeamObjectPermission, type TeamInfo, type CreateTeamResponse, type VirtualKey, type ModelInfo, type UsageModelBreakdown, type UsageKeyBreakdown, type UsageDailyPoint, type UsageDailyModelPoint, type UsageMetrics, type TeamMemberUsage, type TeamMemberUsageRow, type GenerateKeyRequest, type UpdateKeyRequest, type GenerateKeyResponse, type AuditLogEntry, type PaginatedAuditLogs, type SpendLogEntry, type SpendLogsParams, type PaginatedSpendLogs, } from '@acarmisc/backstage-plugin-litellm-common';
|
|
2
2
|
export interface CreateTeamRequest {
|
|
3
3
|
team_alias: string;
|
|
4
4
|
models?: string[];
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@acarmisc/backstage-plugin-litellm-backend",
|
|
3
|
-
"version": "0.
|
|
3
|
+
"version": "0.23.0",
|
|
4
4
|
"description": "The Backstage backend plugin for LiteLLM governance",
|
|
5
5
|
"backstage": {
|
|
6
6
|
"role": "backend-plugin",
|
|
@@ -35,7 +35,7 @@
|
|
|
35
35
|
"prepack": "npm run build"
|
|
36
36
|
},
|
|
37
37
|
"dependencies": {
|
|
38
|
-
"@acarmisc/backstage-plugin-litellm-common": "0.
|
|
38
|
+
"@acarmisc/backstage-plugin-litellm-common": "0.3.0",
|
|
39
39
|
"@backstage/backend-plugin-api": "^1.9.1",
|
|
40
40
|
"@backstage/catalog-client": "^1.9.0",
|
|
41
41
|
"@backstage/config": "^1.3.0",
|