From 92d76cad89e00ece4bc7a91dd1f28a3b2b22ee54 Mon Sep 17 00:00:00 2001 From: Sergey Galuza Date: Sat, 11 Apr 2026 07:39:16 +0200 Subject: [PATCH] feat(cliproxy): add --json flag to catalog command Add machine-readable JSON output for `ccs cliproxy catalog --json` to enable programmatic access to available models per provider. Output format: { "provider": [{ "id": "...", "name": "..." }, ...] } Closes CCS-1 Built [OnSteroids](https://onsteroids.ai) --- src/commands/cliproxy/catalog-subcommand.ts | 15 +++++++++++++++ src/commands/cliproxy/index.ts | 5 +++++ 2 files changed, 20 insertions(+) diff --git a/src/commands/cliproxy/catalog-subcommand.ts b/src/commands/cliproxy/catalog-subcommand.ts index 13374e65..a41cb56f 100644 --- a/src/commands/cliproxy/catalog-subcommand.ts +++ b/src/commands/cliproxy/catalog-subcommand.ts @@ -5,6 +5,7 @@ import { SYNCABLE_PROVIDERS, getResolvedCatalog, refreshCatalogFromProxy, + getAllResolvedCatalogs, } from '../../cliproxy/catalog-cache'; import { getCatalogRoutingSnapshot } from '../../cliproxy/catalog-routing'; import { ensureManagedModelPrefixes } from '../../cliproxy/managed-model-prefixes'; @@ -173,6 +174,20 @@ export async function handleCatalogRefresh(verbose: boolean): Promise { console.log(''); } +/** + * Output catalog as JSON for programmatic consumption. + * Used by OnSteroids and other tools to get available models per provider. + * Format: { provider: [{ id, name }], ... } + */ +export function handleCatalogJson(): void { + const catalogs = getAllResolvedCatalogs(); + const result: Record> = {}; + for (const [provider, catalog] of Object.entries(catalogs)) { + result[provider] = catalog.models.map((m) => ({ id: m.id, name: m.name })); + } + console.log(JSON.stringify(result)); +} + /** Reset catalog cache */ export async function handleCatalogReset(): Promise { await initUI(); diff --git a/src/commands/cliproxy/index.ts b/src/commands/cliproxy/index.ts index 50c9013a..bad626b4 100644 --- a/src/commands/cliproxy/index.ts +++ b/src/commands/cliproxy/index.ts @@ -40,6 +40,7 @@ import { handleCatalogStatus, handleCatalogRefresh, handleCatalogReset, + handleCatalogJson, } from './catalog-subcommand'; /** @@ -146,6 +147,10 @@ export async function handleCliproxyCommand(args: string[]): Promise { // Catalog commands if (command === 'catalog') { + if (hasAnyFlag(remainingArgs, ['--json'])) { + handleCatalogJson(); + return; + } const subcommand = remainingArgs[1]; if (subcommand === 'refresh') { await handleCatalogRefresh(verbose);