bizrouter 0.3.0 → 0.3.2
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/AGENT_MANUAL.md +3 -1
- package/dist/commands/console.js +3 -1
- package/dist/commands/misc.js +1 -1
- package/dist/commands/setup.js +10 -2
- package/dist/harness/codex.js +7 -0
- package/dist/harness/hermes.js +5 -4
- package/package.json +1 -1
package/AGENT_MANUAL.md
CHANGED
|
@@ -228,5 +228,7 @@ user; when `calls` is empty, say the answer came from the model alone.
|
|
|
228
228
|
- Model calls return 400 `model not found` → the key's allowed-model list or
|
|
229
229
|
the organization's model policy excludes it (`bizrouter models` shows what the
|
|
230
230
|
key may use).
|
|
231
|
-
- Hermes + model with output cap under 65536 →
|
|
231
|
+
- Hermes + model with output cap under 65536 → the gateway lowers Hermes'
|
|
232
|
+
fixed `max_tokens` to the cap, so the run works but one answer cannot exceed
|
|
233
|
+
the cap; pick a model with a higher cap only when long answers matter
|
|
232
234
|
(`bizrouter hermes --model anthropic/claude-sonnet-5`).
|
package/dist/commands/console.js
CHANGED
|
@@ -313,7 +313,9 @@ export async function billingCommand(argv) {
|
|
|
313
313
|
return emit(parsed, { credits, monthly }, () => {
|
|
314
314
|
const type = credits.payment_type === 'prepaid' ? '선불(크레딧)' : credits.payment_type === 'postpaid' ? '후불' : credits.payment_type;
|
|
315
315
|
print(c.bold(`결제 방식 ${type}${credits.has_contract ? ' · 계약 고객' : ''}${credits.auto_card_billing ? ' · 카드 자동 충전' : ''}`));
|
|
316
|
-
|
|
316
|
+
const effectiveLimit = credits.effective_monthly_limit !== undefined ? credits.effective_monthly_limit : credits.monthly_limit;
|
|
317
|
+
const hardCap = credits.admin_monthly_hard_cap;
|
|
318
|
+
print(` 현재 크레딧 ${formatKrw(Number(credits.current_credits))} · 누적 사용 ${formatKrw(Number(credits.used_credits))}${effectiveLimit != null ? ` · 월 한도 ${formatKrw(Number(effectiveLimit))}` : ''}${hardCap != null ? ` (운영자 상한 ${formatKrw(Number(hardCap))})` : ''}`);
|
|
317
319
|
print(` 이번 달 사용 ${formatKrw(monthly.current_month_amount_krw)}${monthly.current_available_amount_krw != null ? ` · 사용 가능 ${formatKrw(monthly.current_available_amount_krw)}` : ''}`);
|
|
318
320
|
print();
|
|
319
321
|
table(['월', '상태', 'API 사용', '청구 합계', '요청 수'], monthly.items.map((m) => [m.month, `${m.status}${m.payment_status ? `/${m.payment_status}` : ''}`, formatKrw(m.api_usage_krw), formatKrw(m.total_amount_krw), m.request_count.toLocaleString('ko-KR')]));
|
package/dist/commands/misc.js
CHANGED
|
@@ -2,7 +2,7 @@ import { spawn } from 'node:child_process';
|
|
|
2
2
|
import { ENV_KEY_NAME } from '../config.js';
|
|
3
3
|
import { c, info, print } from '../ui.js';
|
|
4
4
|
import { requireApiKey } from './shared.js';
|
|
5
|
-
export const VERSION = '0.3.
|
|
5
|
+
export const VERSION = '0.3.2';
|
|
6
6
|
/** `eval "$(bizrouter env)"` exports the saved key for tools configured by `bizrouter setup`. */
|
|
7
7
|
export function envCommand() {
|
|
8
8
|
const key = requireApiKey();
|
package/dist/commands/setup.js
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import { copyFileSync, existsSync, mkdirSync, readFileSync, writeFileSync } from 'node:fs';
|
|
1
|
+
import { chmodSync, copyFileSync, existsSync, mkdirSync, readFileSync, writeFileSync } from 'node:fs';
|
|
2
2
|
import { homedir } from 'node:os';
|
|
3
3
|
import { dirname, join } from 'node:path';
|
|
4
4
|
import { fetchCatalog } from '../api.js';
|
|
@@ -29,7 +29,15 @@ function backup(path) {
|
|
|
29
29
|
}
|
|
30
30
|
function writeText(path, text) {
|
|
31
31
|
mkdirSync(dirname(path), { recursive: true });
|
|
32
|
-
|
|
32
|
+
// These files carry the API key: owner-only, and tighten an existing file
|
|
33
|
+
// that was created with the default umask.
|
|
34
|
+
writeFileSync(path, text, { mode: 0o600 });
|
|
35
|
+
try {
|
|
36
|
+
chmodSync(path, 0o600);
|
|
37
|
+
}
|
|
38
|
+
catch {
|
|
39
|
+
// Windows/ACL filesystems: best effort.
|
|
40
|
+
}
|
|
33
41
|
}
|
|
34
42
|
/** Merge BizRouter's env block into a Claude Code settings.json object. */
|
|
35
43
|
export function mergeClaudeSettings(existing, env) {
|
package/dist/harness/codex.js
CHANGED
|
@@ -30,6 +30,13 @@ export function codexOverrides(options) {
|
|
|
30
30
|
}
|
|
31
31
|
if (options.resetServiceTier)
|
|
32
32
|
overrides.push(`service_tier=${tomlString('default')}`);
|
|
33
|
+
// Codex 0.144+ ships the OpenAI-hosted `web_search` tool on every turn. BizRouter has no
|
|
34
|
+
// pricing contract for that hosted tool and answers 400 ("No reviewed pricing contract is
|
|
35
|
+
// available for hosted tool web_search"), which kills the very first turn. Turn it off for
|
|
36
|
+
// this launch; BizRouter Search stays available through the `bizrouter_search` MCP tool.
|
|
37
|
+
if (!(options.passthrough ?? []).some((arg, i) => /^web_search\s*=/.test(arg) || ((options.passthrough ?? [])[i - 1] === '-c' && /^web_search\s*=/.test(arg)))) {
|
|
38
|
+
overrides.push(`web_search=${tomlString('disabled')}`);
|
|
39
|
+
}
|
|
33
40
|
return overrides.flatMap((o) => ['-c', o]);
|
|
34
41
|
}
|
|
35
42
|
export function buildCodexPlan(options) {
|
package/dist/harness/hermes.js
CHANGED
|
@@ -1,14 +1,15 @@
|
|
|
1
1
|
/** Hermes sends this max_tokens to custom OpenAI-compatible endpoints regardless of the model. */
|
|
2
2
|
export const HERMES_FIXED_MAX_TOKENS = 65536;
|
|
3
3
|
/**
|
|
4
|
-
*
|
|
5
|
-
*
|
|
6
|
-
*
|
|
4
|
+
* The gateway lowers an over-cap max_tokens to the model's output cap instead
|
|
5
|
+
* of rejecting the call, so a model whose cap is below Hermes' fixed value
|
|
6
|
+
* still works; its answers just cannot run past the cap. Say so before
|
|
7
|
+
* launching so a truncated long answer is not mistaken for a gateway fault.
|
|
7
8
|
*/
|
|
8
9
|
export function hermesOutputCapWarning(model, maxOutputTokens) {
|
|
9
10
|
if (maxOutputTokens === undefined || maxOutputTokens >= HERMES_FIXED_MAX_TOKENS)
|
|
10
11
|
return undefined;
|
|
11
|
-
return `Hermes는 max_tokens ${HERMES_FIXED_MAX_TOKENS.toLocaleString('en-US')}을 고정으로 보내는데 ${model}의 출력 한도는 ${maxOutputTokens.toLocaleString('en-US')} 입니다.
|
|
12
|
+
return `Hermes는 max_tokens ${HERMES_FIXED_MAX_TOKENS.toLocaleString('en-US')}을 고정으로 보내는데 ${model}의 출력 한도는 ${maxOutputTokens.toLocaleString('en-US')} 입니다. BizRouter가 요청을 ${maxOutputTokens.toLocaleString('en-US')}으로 잘라 보내므로 실행은 되지만, 한 번의 답은 그 길이를 넘지 못합니다.`;
|
|
12
13
|
}
|
|
13
14
|
const HERMES_SUBCOMMANDS = new Set(['chat']);
|
|
14
15
|
/**
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "bizrouter",
|
|
3
|
-
"version": "0.3.
|
|
3
|
+
"version": "0.3.2",
|
|
4
4
|
"description": "BizRouter CLI - run Claude Code, Codex, OpenCode, and Hermes through BizRouter, operate the BizRouter console (API keys, usage, policies, audit logs) from the terminal or as an MCP server, and ask BizRouter Search for answers grounded in 50+ live data sources",
|
|
5
5
|
"license": "UNLICENSED",
|
|
6
6
|
"type": "module",
|