@skillfm/local 2.7.0 → 2.7.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/dist/agent-hints.d.ts.map +1 -1
- package/dist/agent-hints.js +40 -13
- package/dist/agent-hints.js.map +1 -1
- package/dist/index.js +33 -0
- package/dist/index.js.map +1 -1
- package/dist/mcp/_vendored-contracts/beacon-mcp-tools-v1.d.ts +1 -1
- package/dist/mcp/_vendored-contracts/beacon-mcp-tools-v1.d.ts.map +1 -1
- package/dist/mcp/_vendored-contracts/beacon-mcp-tools-v1.js +3 -0
- package/dist/mcp/_vendored-contracts/beacon-mcp-tools-v1.js.map +1 -1
- package/dist/mcp/index.d.ts.map +1 -1
- package/dist/mcp/index.js +6 -0
- package/dist/mcp/index.js.map +1 -1
- package/dist/mcp/tools/credential-tools.d.ts +37 -0
- package/dist/mcp/tools/credential-tools.d.ts.map +1 -0
- package/dist/mcp/tools/credential-tools.js +109 -0
- package/dist/mcp/tools/credential-tools.js.map +1 -0
- package/dist/mcp/tools/explain-provider-key.d.ts +36 -0
- package/dist/mcp/tools/explain-provider-key.d.ts.map +1 -0
- package/dist/mcp/tools/explain-provider-key.js +187 -0
- package/dist/mcp/tools/explain-provider-key.js.map +1 -0
- package/dist/mcp/tools/index.d.ts +3 -0
- package/dist/mcp/tools/index.d.ts.map +1 -1
- package/dist/mcp/tools/index.js +55 -0
- package/dist/mcp/tools/index.js.map +1 -1
- package/dist/scheduler/brain-push-client.d.ts +13 -0
- package/dist/scheduler/brain-push-client.d.ts.map +1 -0
- package/dist/scheduler/brain-push-client.js +46 -0
- package/dist/scheduler/brain-push-client.js.map +1 -0
- package/dist/scheduler/index.d.ts +2 -0
- package/dist/scheduler/index.d.ts.map +1 -1
- package/dist/scheduler/index.js +1 -0
- package/dist/scheduler/index.js.map +1 -1
- package/package.json +1 -1
|
@@ -0,0 +1,109 @@
|
|
|
1
|
+
// sdk/skillfm-local/src/mcp/tools/credential-tools.ts
|
|
2
|
+
//
|
|
3
|
+
// MCP tools for vault — Phase 2 走通 Beacon
|
|
4
|
+
// skillfm_save_credential — vault.put(provider, key)
|
|
5
|
+
// skillfm_get_credential — { provider } → { has_key } (不返真值, 防 agent 把 key 暴露给 user/log)
|
|
6
|
+
// skillfm_list_credentials — vault.list() (只返 provider 名, 不返 key 值)
|
|
7
|
+
// skillfm_remove_credential — vault.delete(provider)
|
|
8
|
+
//
|
|
9
|
+
// BYOK 红线: API key 永远不出节点。Vault 用 AES-256-GCM 加密存 ~/.skillfm/vault.enc,
|
|
10
|
+
// master key 在 ~/.skillfm/vault.key (chmod 0600)。
|
|
11
|
+
// handler 不返 key 值给 agent — agent 不需要知道 key 真值。
|
|
12
|
+
// agent 只需知道 "用户已配某 provider" 就能引导补缺。
|
|
13
|
+
// ── handlers ──────────────────────────────────────────────────────────
|
|
14
|
+
const ALLOWED_PROVIDER_PATTERN = /^[a-z0-9_-]+$/i;
|
|
15
|
+
function validateProvider(provider) {
|
|
16
|
+
if (typeof provider !== 'string' || provider.length === 0) {
|
|
17
|
+
return { ok: false, msg: 'provider required' };
|
|
18
|
+
}
|
|
19
|
+
if (provider.length > 64) {
|
|
20
|
+
return { ok: false, msg: 'provider too long (max 64)' };
|
|
21
|
+
}
|
|
22
|
+
if (!ALLOWED_PROVIDER_PATTERN.test(provider)) {
|
|
23
|
+
return { ok: false, msg: 'provider must match [a-z0-9_-]+' };
|
|
24
|
+
}
|
|
25
|
+
return { ok: true, v: provider };
|
|
26
|
+
}
|
|
27
|
+
export async function handleSaveCredential(input, deps) {
|
|
28
|
+
const v = validateProvider(input?.provider);
|
|
29
|
+
if (!v.ok) {
|
|
30
|
+
return { ok: false, error: { code: 'INPUT.INVALID', message: v.msg, retryable: false } };
|
|
31
|
+
}
|
|
32
|
+
if (typeof input?.key !== 'string' || input.key.length === 0) {
|
|
33
|
+
return { ok: false, error: { code: 'INPUT.INVALID', message: 'key required', retryable: false } };
|
|
34
|
+
}
|
|
35
|
+
if (input.key.length > 4096) {
|
|
36
|
+
return { ok: false, error: { code: 'INPUT.INVALID', message: 'key too long (max 4096)', retryable: false } };
|
|
37
|
+
}
|
|
38
|
+
try {
|
|
39
|
+
await deps.vault.put(v.v, input.key);
|
|
40
|
+
return { ok: true, data: { saved: true, provider: v.v } };
|
|
41
|
+
}
|
|
42
|
+
catch (e) {
|
|
43
|
+
return {
|
|
44
|
+
ok: false,
|
|
45
|
+
error: {
|
|
46
|
+
code: 'VAULT.IO_ERROR',
|
|
47
|
+
message: e instanceof Error ? e.message : String(e),
|
|
48
|
+
retryable: true,
|
|
49
|
+
},
|
|
50
|
+
};
|
|
51
|
+
}
|
|
52
|
+
}
|
|
53
|
+
export async function handleGetCredential(input, deps) {
|
|
54
|
+
const v = validateProvider(input?.provider);
|
|
55
|
+
if (!v.ok) {
|
|
56
|
+
return { ok: false, error: { code: 'INPUT.INVALID', message: v.msg, retryable: false } };
|
|
57
|
+
}
|
|
58
|
+
try {
|
|
59
|
+
const val = await deps.vault.get(v.v);
|
|
60
|
+
return { ok: true, data: { provider: v.v, has_key: val !== null } };
|
|
61
|
+
}
|
|
62
|
+
catch (e) {
|
|
63
|
+
return {
|
|
64
|
+
ok: false,
|
|
65
|
+
error: {
|
|
66
|
+
code: 'VAULT.IO_ERROR',
|
|
67
|
+
message: e instanceof Error ? e.message : String(e),
|
|
68
|
+
retryable: true,
|
|
69
|
+
},
|
|
70
|
+
};
|
|
71
|
+
}
|
|
72
|
+
}
|
|
73
|
+
export async function handleListCredentials(_input, deps) {
|
|
74
|
+
try {
|
|
75
|
+
const providers = await deps.vault.list();
|
|
76
|
+
return { ok: true, data: { providers, count: providers.length } };
|
|
77
|
+
}
|
|
78
|
+
catch (e) {
|
|
79
|
+
return {
|
|
80
|
+
ok: false,
|
|
81
|
+
error: {
|
|
82
|
+
code: 'VAULT.IO_ERROR',
|
|
83
|
+
message: e instanceof Error ? e.message : String(e),
|
|
84
|
+
retryable: true,
|
|
85
|
+
},
|
|
86
|
+
};
|
|
87
|
+
}
|
|
88
|
+
}
|
|
89
|
+
export async function handleRemoveCredential(input, deps) {
|
|
90
|
+
const v = validateProvider(input?.provider);
|
|
91
|
+
if (!v.ok) {
|
|
92
|
+
return { ok: false, error: { code: 'INPUT.INVALID', message: v.msg, retryable: false } };
|
|
93
|
+
}
|
|
94
|
+
try {
|
|
95
|
+
const removed = await deps.vault.delete(v.v);
|
|
96
|
+
return { ok: true, data: { removed, provider: v.v } };
|
|
97
|
+
}
|
|
98
|
+
catch (e) {
|
|
99
|
+
return {
|
|
100
|
+
ok: false,
|
|
101
|
+
error: {
|
|
102
|
+
code: 'VAULT.IO_ERROR',
|
|
103
|
+
message: e instanceof Error ? e.message : String(e),
|
|
104
|
+
retryable: true,
|
|
105
|
+
},
|
|
106
|
+
};
|
|
107
|
+
}
|
|
108
|
+
}
|
|
109
|
+
//# sourceMappingURL=credential-tools.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"credential-tools.js","sourceRoot":"","sources":["../../../src/mcp/tools/credential-tools.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,36 @@
|
|
|
1
|
+
import type { SkillFmToolResult } from '../_vendored-contracts/beacon-mcp-tools-v1.js';
|
|
2
|
+
interface ExplainProviderKeyInput {
|
|
3
|
+
provider: string;
|
|
4
|
+
}
|
|
5
|
+
export interface ProviderKeyExplanation {
|
|
6
|
+
provider: string;
|
|
7
|
+
display_name: string;
|
|
8
|
+
/** 给用户看的 key 类型名称 (中文友好) */
|
|
9
|
+
key_label: string;
|
|
10
|
+
/** 该 provider 是否有专用 admin/usage key (vs 跟普通调用 key 共用) */
|
|
11
|
+
has_dedicated_admin_key: boolean;
|
|
12
|
+
/** 推荐 scope (如 OpenAI/Anthropic), 没有 scope 概念时 null */
|
|
13
|
+
scope_recommended: string[] | null;
|
|
14
|
+
scope_warning: string | null;
|
|
15
|
+
/** 为什么 SkillFM 需要这个 key */
|
|
16
|
+
why_needed: string;
|
|
17
|
+
/** 一步一步的获取流程 (含真链接) */
|
|
18
|
+
steps: string[];
|
|
19
|
+
/** 'LOW' / 'MEDIUM' / 'HIGH' */
|
|
20
|
+
risk_level: 'LOW' | 'MEDIUM' | 'HIGH';
|
|
21
|
+
/** 风险解释 — 此 key 能干啥, 不能干啥 */
|
|
22
|
+
risk_explain: string;
|
|
23
|
+
/** 撤销 / 删除 key 的链接 */
|
|
24
|
+
revoke_url: string;
|
|
25
|
+
/** BYOK 保护承诺 (固定文案) */
|
|
26
|
+
byok_safety: string;
|
|
27
|
+
/** key 格式 hint, 帮 agent 验证用户给的是不是对的 key */
|
|
28
|
+
key_format_hint: string;
|
|
29
|
+
/** 中高风险 provider 的额外建议 (建议建独立 key / 充小额 / 设限额) */
|
|
30
|
+
extra_recommendations: string[];
|
|
31
|
+
}
|
|
32
|
+
export declare function handleExplainProviderKey(input: ExplainProviderKeyInput): Promise<SkillFmToolResult<ProviderKeyExplanation>>;
|
|
33
|
+
/** Exposed for testing — list of all supported providers */
|
|
34
|
+
export declare const SUPPORTED_PROVIDERS: string[];
|
|
35
|
+
export {};
|
|
36
|
+
//# sourceMappingURL=explain-provider-key.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"explain-provider-key.d.ts","sourceRoot":"","sources":["../../../src/mcp/tools/explain-provider-key.ts"],"names":[],"mappings":"AAeA,OAAO,KAAK,EAAE,iBAAiB,EAAE,MAAM,+CAA+C,CAAC;AAEvF,UAAU,uBAAuB;IAC/B,QAAQ,EAAE,MAAM,CAAC;CAClB;AAED,MAAM,WAAW,sBAAsB;IACrC,QAAQ,EAAE,MAAM,CAAC;IACjB,YAAY,EAAE,MAAM,CAAC;IACrB,4BAA4B;IAC5B,SAAS,EAAE,MAAM,CAAC;IAClB,yDAAyD;IACzD,uBAAuB,EAAE,OAAO,CAAC;IACjC,uDAAuD;IACvD,iBAAiB,EAAE,MAAM,EAAE,GAAG,IAAI,CAAC;IACnC,aAAa,EAAE,MAAM,GAAG,IAAI,CAAC;IAC7B,2BAA2B;IAC3B,UAAU,EAAE,MAAM,CAAC;IACnB,uBAAuB;IACvB,KAAK,EAAE,MAAM,EAAE,CAAC;IAChB,gCAAgC;IAChC,UAAU,EAAE,KAAK,GAAG,QAAQ,GAAG,MAAM,CAAC;IACtC,6BAA6B;IAC7B,YAAY,EAAE,MAAM,CAAC;IACrB,sBAAsB;IACtB,UAAU,EAAE,MAAM,CAAC;IACnB,uBAAuB;IACvB,WAAW,EAAE,MAAM,CAAC;IACpB,2CAA2C;IAC3C,eAAe,EAAE,MAAM,CAAC;IACxB,kDAAkD;IAClD,qBAAqB,EAAE,MAAM,EAAE,CAAC;CACjC;AAwKD,wBAAsB,wBAAwB,CAC5C,KAAK,EAAE,uBAAuB,GAC7B,OAAO,CAAC,iBAAiB,CAAC,sBAAsB,CAAC,CAAC,CAqBpD;AAED,4DAA4D;AAC5D,eAAO,MAAM,mBAAmB,UAAuC,CAAC"}
|
|
@@ -0,0 +1,187 @@
|
|
|
1
|
+
// sdk/skillfm-local/src/mcp/tools/explain-provider-key.ts
|
|
2
|
+
//
|
|
3
|
+
// MCP tool: skillfm_explain_provider_key
|
|
4
|
+
//
|
|
5
|
+
// 让 agent 在让用户给 API key 之前, **必须**先调此 tool 拿引导, 转译为自然语言
|
|
6
|
+
// 给用户. 解决 Phase 2 onboarding 痛点: 用户不懂 "billing-only key" 是啥 +
|
|
7
|
+
// 给 API key 是敏感操作需要清楚的 why / how / risk / revoke / BYOK 保护说明.
|
|
8
|
+
//
|
|
9
|
+
// 6 个 provider 风险分层:
|
|
10
|
+
// - LOW : OpenAI / Anthropic — 有专用 admin key + read-only scope
|
|
11
|
+
// - MEDIUM : Qwen / Doubao — API key 跟调用同 key, 但能在控制台限额
|
|
12
|
+
// - HIGH : DeepSeek / Kimi — 同上, 但平台不一定能限额, 建议建独立 key + 充小额
|
|
13
|
+
//
|
|
14
|
+
// 格式: 静态结构化数据, agent 调用即返, 不依赖 brain / network。
|
|
15
|
+
const BYOK_SAFETY = '你的 key 加密存本地 ~/.skillfm/vault.enc (AES-256-GCM, master key 在 ~/.skillfm/vault.key chmod 0600), 永不出节点。如担心可随时去 provider 控制台删 key 立即吊销。';
|
|
16
|
+
const PROVIDER_CONFIGS = {
|
|
17
|
+
openai: {
|
|
18
|
+
provider: 'openai',
|
|
19
|
+
display_name: 'OpenAI',
|
|
20
|
+
key_label: 'Admin API Key (read-only scope)',
|
|
21
|
+
has_dedicated_admin_key: true,
|
|
22
|
+
scope_recommended: ['api.usage.read'],
|
|
23
|
+
scope_warning: '⚠️ 不要勾 api.management.write — 那个能管 API keys 风险大, SkillFM 不需要',
|
|
24
|
+
why_needed: '让 SkillFM 能查询你 OpenAI 的用量数据 (token / cost / model 细分), 定期告诉你哪能省',
|
|
25
|
+
steps: [
|
|
26
|
+
'1. 打开 https://platform.openai.com/settings/organization/admin-keys',
|
|
27
|
+
'2. 点 "Create new admin key"',
|
|
28
|
+
'3. Name: SkillFM Beacon (或你喜欢的名字)',
|
|
29
|
+
'4. Permissions: 仅勾选 "api.usage.read" (read-only, 只能查用量)',
|
|
30
|
+
'5. Create → 复制 sk-admin-... 给我',
|
|
31
|
+
],
|
|
32
|
+
risk_level: 'LOW',
|
|
33
|
+
risk_explain: '此 key 只能查用量数据,不能花钱、不能管账户、不能改设置。即使泄露给别人最大风险只是别人看到你 OpenAI 用了多少钱',
|
|
34
|
+
revoke_url: 'https://platform.openai.com/settings/organization/admin-keys',
|
|
35
|
+
byok_safety: BYOK_SAFETY,
|
|
36
|
+
key_format_hint: 'sk-admin-... (40+ 字符)',
|
|
37
|
+
extra_recommendations: [],
|
|
38
|
+
},
|
|
39
|
+
anthropic: {
|
|
40
|
+
provider: 'anthropic',
|
|
41
|
+
display_name: 'Anthropic (Claude API)',
|
|
42
|
+
key_label: 'Organization Admin API Key',
|
|
43
|
+
has_dedicated_admin_key: true,
|
|
44
|
+
scope_recommended: null,
|
|
45
|
+
scope_warning: '⚠️ Anthropic 的 admin key 默认有较多权限 (能管 API keys 等), SkillFM 只读用量。建议独立建一个专用于监控的, 用完了删',
|
|
46
|
+
why_needed: '让 SkillFM 能查询你 Anthropic 组织的用量数据 (Claude 各模型 token / cost), 定期告诉你哪能省',
|
|
47
|
+
steps: [
|
|
48
|
+
'1. 打开 https://console.anthropic.com',
|
|
49
|
+
'2. 进入 Organization → API keys (顶部菜单)',
|
|
50
|
+
'3. 切到 "Admin keys" tab',
|
|
51
|
+
'4. 点 "Create admin key"',
|
|
52
|
+
'5. Name: SkillFM Beacon',
|
|
53
|
+
'6. Create → 复制 sk-ant-admin-... 给我',
|
|
54
|
+
],
|
|
55
|
+
risk_level: 'LOW',
|
|
56
|
+
risk_explain: 'Admin key 理论上权限较大 (能调 admin API 含管 keys), 但 SkillFM 只调 organization/usage_report 端点。如担心可随时撤销重发',
|
|
57
|
+
revoke_url: 'https://console.anthropic.com (Organization → Admin keys)',
|
|
58
|
+
byok_safety: BYOK_SAFETY,
|
|
59
|
+
key_format_hint: 'sk-ant-admin-... (60+ 字符)',
|
|
60
|
+
extra_recommendations: [
|
|
61
|
+
'建议独立建一个 admin key 专给 SkillFM 用, 不要复用其他工具的',
|
|
62
|
+
],
|
|
63
|
+
},
|
|
64
|
+
deepseek: {
|
|
65
|
+
provider: 'deepseek',
|
|
66
|
+
display_name: 'DeepSeek',
|
|
67
|
+
key_label: 'API Key',
|
|
68
|
+
has_dedicated_admin_key: false,
|
|
69
|
+
scope_recommended: null,
|
|
70
|
+
scope_warning: null,
|
|
71
|
+
why_needed: 'DeepSeek 没公开专用 admin/usage API, SkillFM 用 /user/balance 端点定期查余额, 反推用量',
|
|
72
|
+
steps: [
|
|
73
|
+
'1. 打开 https://platform.deepseek.com/api_keys',
|
|
74
|
+
'2. 点 "Create new API key"',
|
|
75
|
+
'3. Name: SkillFM Monitor (建议独立建一个, 别复用调用 key)',
|
|
76
|
+
'4. Create → 复制 sk-... 给我',
|
|
77
|
+
],
|
|
78
|
+
risk_level: 'HIGH',
|
|
79
|
+
risk_explain: '⚠️ 此 key 跟普通调用 key 是同一种 — 既能查余额, 也能调 LLM 花你钱。如果泄露别人能用你的额度。建议: (1) 独立建一个专给 SkillFM 用的 key (2) 给账户充小额 (如 $10) 上限可控',
|
|
80
|
+
revoke_url: 'https://platform.deepseek.com/api_keys',
|
|
81
|
+
byok_safety: BYOK_SAFETY,
|
|
82
|
+
key_format_hint: 'sk-... (32+ 字符)',
|
|
83
|
+
extra_recommendations: [
|
|
84
|
+
'建议独立建一个新 key 专给 SkillFM, 不复用你现在 IDE / agent 在用的',
|
|
85
|
+
'如果担心被滥用, 给 DeepSeek 账户先充小额 (如 $10), 风险即上限',
|
|
86
|
+
],
|
|
87
|
+
},
|
|
88
|
+
doubao: {
|
|
89
|
+
provider: 'doubao',
|
|
90
|
+
display_name: '豆包 / 火山方舟 Ark',
|
|
91
|
+
key_label: 'Ark API Key',
|
|
92
|
+
has_dedicated_admin_key: false,
|
|
93
|
+
scope_recommended: null,
|
|
94
|
+
scope_warning: null,
|
|
95
|
+
why_needed: '让 SkillFM 查你火山方舟的 endpoints + 调用统计, 跨 LLM 看你的 AI 花费',
|
|
96
|
+
steps: [
|
|
97
|
+
'1. 打开 https://console.volcengine.com/ark',
|
|
98
|
+
'2. 左侧菜单 "API Key 管理"',
|
|
99
|
+
'3. 点 "创建 API Key"',
|
|
100
|
+
'4. 名称: SkillFM Monitor (建议独立)',
|
|
101
|
+
'5. 创建 → 复制完整 key 给我',
|
|
102
|
+
],
|
|
103
|
+
risk_level: 'MEDIUM',
|
|
104
|
+
risk_explain: 'Ark API key 能调 LLM 花钱。但火山控制台支持设额度 / 限速, 可以预先限制风险上限',
|
|
105
|
+
revoke_url: 'https://console.volcengine.com/ark (API Key 管理)',
|
|
106
|
+
byok_safety: BYOK_SAFETY,
|
|
107
|
+
key_format_hint: 'Ark API key (一般 40+ 字符)',
|
|
108
|
+
extra_recommendations: [
|
|
109
|
+
'建议独立建一个 key 专给 SkillFM',
|
|
110
|
+
'在火山控制台给该 key 设月度额度上限',
|
|
111
|
+
],
|
|
112
|
+
},
|
|
113
|
+
qwen: {
|
|
114
|
+
provider: 'qwen',
|
|
115
|
+
display_name: 'Qwen / 阿里百炼 DashScope',
|
|
116
|
+
key_label: 'DashScope API Key',
|
|
117
|
+
has_dedicated_admin_key: false,
|
|
118
|
+
scope_recommended: null,
|
|
119
|
+
scope_warning: null,
|
|
120
|
+
why_needed: '让 SkillFM 查你 DashScope 部署的模型 + 调用统计, 跨 LLM 看 AI 花费',
|
|
121
|
+
steps: [
|
|
122
|
+
'1. 打开 https://bailian.console.aliyun.com',
|
|
123
|
+
'2. 顶部菜单 "API-KEY"',
|
|
124
|
+
'3. 点 "创建我的 API-KEY"',
|
|
125
|
+
'4. 描述: SkillFM Monitor',
|
|
126
|
+
'5. 创建 → 复制 sk-... 给我',
|
|
127
|
+
],
|
|
128
|
+
risk_level: 'MEDIUM',
|
|
129
|
+
risk_explain: 'DashScope key 能调 Qwen 模型花钱。阿里云账户可以给 key 设调用频率限制 / 月度额度',
|
|
130
|
+
revoke_url: 'https://bailian.console.aliyun.com (API-KEY)',
|
|
131
|
+
byok_safety: BYOK_SAFETY,
|
|
132
|
+
key_format_hint: 'sk-... (32+ 字符)',
|
|
133
|
+
extra_recommendations: [
|
|
134
|
+
'建议独立建一个 key 专给 SkillFM',
|
|
135
|
+
'在百炼控制台给该 key 设调用频率 / 月度额度',
|
|
136
|
+
],
|
|
137
|
+
},
|
|
138
|
+
kimi: {
|
|
139
|
+
provider: 'kimi',
|
|
140
|
+
display_name: 'Kimi / Moonshot',
|
|
141
|
+
key_label: 'API Key',
|
|
142
|
+
has_dedicated_admin_key: false,
|
|
143
|
+
scope_recommended: null,
|
|
144
|
+
scope_warning: null,
|
|
145
|
+
why_needed: 'Kimi 没公开专用 admin/usage API, SkillFM 用 /v1/users/me/balance 端点定期查余额反推用量',
|
|
146
|
+
steps: [
|
|
147
|
+
'1. 打开 https://platform.moonshot.cn/console/api-keys',
|
|
148
|
+
'2. 点 "新建"',
|
|
149
|
+
'3. 名称: SkillFM Monitor (建议独立)',
|
|
150
|
+
'4. 创建 → 复制 sk-... 给我',
|
|
151
|
+
],
|
|
152
|
+
risk_level: 'HIGH',
|
|
153
|
+
risk_explain: '⚠️ Kimi 的 API key 跟普通调用 key 是同一种 — 既能查余额, 也能调 Kimi 花你钱。建议: (1) 独立建一个 (2) 账户充小额风险有限',
|
|
154
|
+
revoke_url: 'https://platform.moonshot.cn/console/api-keys',
|
|
155
|
+
byok_safety: BYOK_SAFETY,
|
|
156
|
+
key_format_hint: 'sk-... (32+ 字符)',
|
|
157
|
+
extra_recommendations: [
|
|
158
|
+
'建议独立建一个 key 专给 SkillFM',
|
|
159
|
+
'在 Kimi 账户充小额 (如 ¥10), 风险即上限',
|
|
160
|
+
],
|
|
161
|
+
},
|
|
162
|
+
};
|
|
163
|
+
export async function handleExplainProviderKey(input) {
|
|
164
|
+
const provider = (input?.provider ?? '').toLowerCase().trim();
|
|
165
|
+
if (!provider) {
|
|
166
|
+
return {
|
|
167
|
+
ok: false,
|
|
168
|
+
error: { code: 'INPUT.INVALID', message: 'provider required', retryable: false },
|
|
169
|
+
};
|
|
170
|
+
}
|
|
171
|
+
const cfg = PROVIDER_CONFIGS[provider];
|
|
172
|
+
if (!cfg) {
|
|
173
|
+
const supported = Object.keys(PROVIDER_CONFIGS).sort().join(' / ');
|
|
174
|
+
return {
|
|
175
|
+
ok: false,
|
|
176
|
+
error: {
|
|
177
|
+
code: 'PROVIDER.NOT_SUPPORTED',
|
|
178
|
+
message: `provider '${provider}' not supported. Supported: ${supported}`,
|
|
179
|
+
retryable: false,
|
|
180
|
+
},
|
|
181
|
+
};
|
|
182
|
+
}
|
|
183
|
+
return { ok: true, data: cfg };
|
|
184
|
+
}
|
|
185
|
+
/** Exposed for testing — list of all supported providers */
|
|
186
|
+
export const SUPPORTED_PROVIDERS = Object.keys(PROVIDER_CONFIGS).sort();
|
|
187
|
+
//# sourceMappingURL=explain-provider-key.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"explain-provider-key.js","sourceRoot":"","sources":["../../../src/mcp/tools/explain-provider-key.ts"],"names":[],"mappings":"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"}
|
|
@@ -24,12 +24,15 @@
|
|
|
24
24
|
import type { McpServer } from '@modelcontextprotocol/sdk/server/mcp.js';
|
|
25
25
|
import type { BrainClient } from '../brain-client.js';
|
|
26
26
|
import type { MemoryStore } from '../../memory/index.js';
|
|
27
|
+
import type { Vault } from '../../vault/index.js';
|
|
27
28
|
export interface ToolRegistryDeps {
|
|
28
29
|
brain: BrainClient;
|
|
29
30
|
/** Phase 0: derived from `agentToken !== null`; Week 5: real claim. */
|
|
30
31
|
isProTier: boolean;
|
|
31
32
|
/** Mem0 self-host client (Day 6 B1, Pro-only); null = 未配置, MCP tools 返 NOT_CONFIGURED */
|
|
32
33
|
memory?: MemoryStore | null;
|
|
34
|
+
/** Local credential vault (BYOK: keys 加密存本地节点 ~/.skillfm/vault.{key,enc}, 不出节点) */
|
|
35
|
+
vault?: Vault | null;
|
|
33
36
|
}
|
|
34
37
|
/**
|
|
35
38
|
* Register every Phase 0 beacon MCP tool. Called once by src/index.ts on
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../../src/mcp/tools/index.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;;;;;GAsBG;AAEH,OAAO,KAAK,EAAE,SAAS,EAAE,MAAM,yCAAyC,CAAC;AAazE,OAAO,KAAK,EAAE,WAAW,EAAE,MAAM,oBAAoB,CAAC;
|
|
1
|
+
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../../src/mcp/tools/index.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;;;;;GAsBG;AAEH,OAAO,KAAK,EAAE,SAAS,EAAE,MAAM,yCAAyC,CAAC;AAazE,OAAO,KAAK,EAAE,WAAW,EAAE,MAAM,oBAAoB,CAAC;AAqBtD,OAAO,KAAK,EAAE,WAAW,EAAE,MAAM,uBAAuB,CAAC;AACzD,OAAO,KAAK,EAAE,KAAK,EAAE,MAAM,sBAAsB,CAAC;AAMlD,MAAM,WAAW,gBAAgB;IAC/B,KAAK,EAAE,WAAW,CAAC;IACnB,uEAAuE;IACvE,SAAS,EAAE,OAAO,CAAC;IACnB,yFAAyF;IACzF,MAAM,CAAC,EAAE,WAAW,GAAG,IAAI,CAAC;IAC5B,mFAAmF;IACnF,KAAK,CAAC,EAAE,KAAK,GAAG,IAAI,CAAC;CACtB;AAmQD;;;GAGG;AACH,wBAAgB,gBAAgB,CAAC,MAAM,EAAE,SAAS,EAAE,IAAI,EAAE,gBAAgB,GAAG,IAAI,CAGhF;AAED,yEAAyE;AACzE,wBAAgB,2BAA2B,IAAI,MAAM,EAAE,CAEtD"}
|
package/dist/mcp/tools/index.js
CHANGED
|
@@ -35,6 +35,8 @@ import { makePlaceholderHandler } from './_placeholder.js';
|
|
|
35
35
|
import { handleMemorySearch } from './memory-search.js';
|
|
36
36
|
import { handleMemorySave } from './memory-save.js';
|
|
37
37
|
import { handleMemoryRecent } from './memory-recent.js';
|
|
38
|
+
import { handleSaveCredential, handleGetCredential, handleListCredentials, handleRemoveCredential, } from './credential-tools.js';
|
|
39
|
+
import { handleExplainProviderKey } from './explain-provider-key.js';
|
|
38
40
|
// ============================================================================
|
|
39
41
|
// Minimal input shape — every Phase 0 tool accepts a free-form object.
|
|
40
42
|
// Validation is done inside handlers (so failures come back as
|
|
@@ -98,6 +100,53 @@ function registerKeyTools(server, deps) {
|
|
|
98
100
|
const env = await handleMemoryRecent(input, memoryDeps);
|
|
99
101
|
return wrapEnvelope(env);
|
|
100
102
|
});
|
|
103
|
+
// ─── Phase 2: Credential vault tools (BYOK: keys 加密存本地, 不出节点) ───
|
|
104
|
+
// Agent 装 SkillFM 后引导用户加 LLM provider 的 billing API key, 启用 Beacon 监控。
|
|
105
|
+
const vaultDeps = deps.vault ? { vault: deps.vault } : null;
|
|
106
|
+
server.tool('skillfm_save_credential', 'Save a BYOK provider API key to the local encrypted vault (AES-256-GCM, never leaves the user node). Use this when onboarding a user — ask them which LLM provider (openai/anthropic/deepseek/doubao/qwen/kimi) or asset registrar (cloudflare/namecheap/godaddy/...) they want monitored, then save the billing-only API key here. Beacon scheduler reads this vault to poll provider billing APIs every 30 minutes.', PASSTHROUGH_SCHEMA.shape, async (input) => {
|
|
107
|
+
if (!vaultDeps) {
|
|
108
|
+
return wrapEnvelope({
|
|
109
|
+
ok: false,
|
|
110
|
+
error: { code: 'VAULT.NOT_CONFIGURED', message: 'Local vault not available in this MCP transport.', retryable: false },
|
|
111
|
+
});
|
|
112
|
+
}
|
|
113
|
+
const env = await handleSaveCredential(input, vaultDeps);
|
|
114
|
+
return wrapEnvelope(env);
|
|
115
|
+
});
|
|
116
|
+
server.tool('skillfm_get_credential', 'Check whether a credential exists in the vault for a given provider. Returns { has_key: bool } — does NOT return the key value (security). Use this to decide if the user needs to add a key for a particular provider.', PASSTHROUGH_SCHEMA.shape, async (input) => {
|
|
117
|
+
if (!vaultDeps) {
|
|
118
|
+
return wrapEnvelope({
|
|
119
|
+
ok: false,
|
|
120
|
+
error: { code: 'VAULT.NOT_CONFIGURED', message: 'Local vault not available in this MCP transport.', retryable: false },
|
|
121
|
+
});
|
|
122
|
+
}
|
|
123
|
+
const env = await handleGetCredential(input, vaultDeps);
|
|
124
|
+
return wrapEnvelope(env);
|
|
125
|
+
});
|
|
126
|
+
server.tool('skillfm_list_credentials', 'List the provider names currently in the local vault. Does NOT return key values. Use this at session start to know which providers Beacon is already monitoring vs which ones to ask the user to add.', PASSTHROUGH_SCHEMA.shape, async (input) => {
|
|
127
|
+
if (!vaultDeps) {
|
|
128
|
+
return wrapEnvelope({
|
|
129
|
+
ok: false,
|
|
130
|
+
error: { code: 'VAULT.NOT_CONFIGURED', message: 'Local vault not available in this MCP transport.', retryable: false },
|
|
131
|
+
});
|
|
132
|
+
}
|
|
133
|
+
const env = await handleListCredentials(input, vaultDeps);
|
|
134
|
+
return wrapEnvelope(env);
|
|
135
|
+
});
|
|
136
|
+
server.tool('skillfm_remove_credential', 'Remove a provider credential from the vault (e.g. user revoked the key, no longer wants Beacon to monitor that provider). Returns { removed: bool, provider }.', PASSTHROUGH_SCHEMA.shape, async (input) => {
|
|
137
|
+
if (!vaultDeps) {
|
|
138
|
+
return wrapEnvelope({
|
|
139
|
+
ok: false,
|
|
140
|
+
error: { code: 'VAULT.NOT_CONFIGURED', message: 'Local vault not available in this MCP transport.', retryable: false },
|
|
141
|
+
});
|
|
142
|
+
}
|
|
143
|
+
const env = await handleRemoveCredential(input, vaultDeps);
|
|
144
|
+
return wrapEnvelope(env);
|
|
145
|
+
});
|
|
146
|
+
server.tool('skillfm_explain_provider_key', 'CRITICAL — call this BEFORE asking the user for any provider API key. Returns structured guidance: key type, why needed, step-by-step generation link, scope recommendations, risk level (LOW/MEDIUM/HIGH), what the key can do (and cannot do), revoke URL, BYOK safety promise, and key format hint. Translate the response into natural language for the user — never just ask for "your API key" without first explaining via this tool. Supported: openai / anthropic / deepseek / doubao / qwen / kimi.', PASSTHROUGH_SCHEMA.shape, async (input) => {
|
|
147
|
+
const env = await handleExplainProviderKey(input);
|
|
148
|
+
return wrapEnvelope(env);
|
|
149
|
+
});
|
|
101
150
|
}
|
|
102
151
|
// ============================================================================
|
|
103
152
|
// Placeholder tools — names reserved by contract but Phase 0 = NOT_IMPLEMENTED
|
|
@@ -111,6 +160,12 @@ const KEY_TOOL_NAMES = new Set([
|
|
|
111
160
|
'skillfm_record_acceptance',
|
|
112
161
|
'skillfm_record_rejection',
|
|
113
162
|
'skillfm_user_preferences',
|
|
163
|
+
// Phase 2: vault credential tools (real handlers, not placeholders)
|
|
164
|
+
'skillfm_save_credential',
|
|
165
|
+
'skillfm_get_credential',
|
|
166
|
+
'skillfm_list_credentials',
|
|
167
|
+
'skillfm_remove_credential',
|
|
168
|
+
'skillfm_explain_provider_key',
|
|
114
169
|
]);
|
|
115
170
|
function registerPlaceholderTools(server) {
|
|
116
171
|
const allNames = Object.values(SKILLFM_TOOL_NAMES).flat();
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.js","sourceRoot":"","sources":["../../../src/mcp/tools/index.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;;;;;GAsBG;AAGH,OAAO,EAAE,CAAC,EAAE,MAAM,KAAK,CAAC;AAExB,OAAO,EACL,kBAAkB,GAOnB,MAAM,+CAA+C,CAAC;AAIvD,OAAO,EAAE,gBAAgB,EAAE,MAAM,kBAAkB,CAAC;AACpD,OAAO,EAAE,kBAAkB,EAAE,MAAM,oBAAoB,CAAC;AACxD,OAAO,EAAE,iBAAiB,EAAE,MAAM,mBAAmB,CAAC;AACtD,OAAO,EAAE,kBAAkB,EAAE,MAAM,oBAAoB,CAAC;AACxD,OAAO,EAAE,qBAAqB,EAAE,MAAM,wBAAwB,CAAC;AAC/D,OAAO,EAAE,sBAAsB,EAAE,MAAM,wBAAwB,CAAC;AAChE,OAAO,EAAE,qBAAqB,EAAE,MAAM,uBAAuB,CAAC;AAC9D,OAAO,EAAE,qBAAqB,EAAE,MAAM,uBAAuB,CAAC;AAC9D,OAAO,EAAE,sBAAsB,EAAE,MAAM,mBAAmB,CAAC;AAC3D,OAAO,EAAE,kBAAkB,EAAE,MAAM,oBAAoB,CAAC;AACxD,OAAO,EAAE,gBAAgB,EAAE,MAAM,kBAAkB,CAAC;AACpD,OAAO,EAAE,kBAAkB,EAAE,MAAM,oBAAoB,CAAC;
|
|
1
|
+
{"version":3,"file":"index.js","sourceRoot":"","sources":["../../../src/mcp/tools/index.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,13 @@
|
|
|
1
|
+
import type { BrainPushClient } from './types.js';
|
|
2
|
+
export interface BrainPushClientOptions {
|
|
3
|
+
/** brain api root, e.g. https://api.skillfm.ai */
|
|
4
|
+
apiRoot: string;
|
|
5
|
+
/** X-Agent-Token (从 sidecar state.brainKey 透传) */
|
|
6
|
+
agentToken: string;
|
|
7
|
+
/** User-Agent (PKG_NAME/PKG_VERSION) */
|
|
8
|
+
userAgent: string;
|
|
9
|
+
/** 单次 push 超时,默认 30s */
|
|
10
|
+
timeoutMs?: number;
|
|
11
|
+
}
|
|
12
|
+
export declare function createBrainPushClient(opts: BrainPushClientOptions): BrainPushClient;
|
|
13
|
+
//# sourceMappingURL=brain-push-client.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"brain-push-client.d.ts","sourceRoot":"","sources":["../../src/scheduler/brain-push-client.ts"],"names":[],"mappings":"AAKA,OAAO,KAAK,EAAE,eAAe,EAAE,MAAM,YAAY,CAAC;AAElD,MAAM,WAAW,sBAAsB;IACrC,kDAAkD;IAClD,OAAO,EAAE,MAAM,CAAC;IAChB,kDAAkD;IAClD,UAAU,EAAE,MAAM,CAAC;IACnB,wCAAwC;IACxC,SAAS,EAAE,MAAM,CAAC;IAClB,wBAAwB;IACxB,SAAS,CAAC,EAAE,MAAM,CAAC;CACpB;AAKD,wBAAgB,qBAAqB,CAAC,IAAI,EAAE,sBAAsB,GAAG,eAAe,CAsCnF"}
|
|
@@ -0,0 +1,46 @@
|
|
|
1
|
+
// sdk/skillfm-local/src/scheduler/brain-push-client.ts
|
|
2
|
+
//
|
|
3
|
+
// Default BrainPushClient — POST 到 brain /v1/beacon/usage/snapshot + /v1/beacon/assets/registry
|
|
4
|
+
// 用于 sidecar 启动时 wire 自动 monitoring (Phase 2 走通 Beacon)。
|
|
5
|
+
const USAGE_PATH = '/v1/beacon/usage/snapshot';
|
|
6
|
+
const ASSETS_PATH = '/v1/beacon/assets/registry';
|
|
7
|
+
export function createBrainPushClient(opts) {
|
|
8
|
+
const { apiRoot, agentToken, userAgent, timeoutMs = 30_000 } = opts;
|
|
9
|
+
const headers = {
|
|
10
|
+
'Content-Type': 'application/json',
|
|
11
|
+
'X-Agent-Token': agentToken,
|
|
12
|
+
'User-Agent': userAgent,
|
|
13
|
+
};
|
|
14
|
+
async function postJson(path, body) {
|
|
15
|
+
const ctrl = new AbortController();
|
|
16
|
+
const timer = setTimeout(() => ctrl.abort(), timeoutMs);
|
|
17
|
+
try {
|
|
18
|
+
const res = await fetch(`${apiRoot}${path}`, {
|
|
19
|
+
method: 'POST',
|
|
20
|
+
headers,
|
|
21
|
+
body: JSON.stringify(body),
|
|
22
|
+
signal: ctrl.signal,
|
|
23
|
+
});
|
|
24
|
+
if (!res.ok) {
|
|
25
|
+
const text = await res.text().catch(() => '');
|
|
26
|
+
return { ok: false, error: `${res.status} ${text.slice(0, 200)}` };
|
|
27
|
+
}
|
|
28
|
+
return { ok: true };
|
|
29
|
+
}
|
|
30
|
+
catch (e) {
|
|
31
|
+
return { ok: false, error: e instanceof Error ? e.message : String(e) };
|
|
32
|
+
}
|
|
33
|
+
finally {
|
|
34
|
+
clearTimeout(timer);
|
|
35
|
+
}
|
|
36
|
+
}
|
|
37
|
+
return {
|
|
38
|
+
async pushUsageSnapshot(records) {
|
|
39
|
+
return postJson(USAGE_PATH, { snapshots: records, client_timestamp: new Date().toISOString() });
|
|
40
|
+
},
|
|
41
|
+
async pushAssetRegistry(assets) {
|
|
42
|
+
return postJson(ASSETS_PATH, { assets, client_timestamp: new Date().toISOString() });
|
|
43
|
+
},
|
|
44
|
+
};
|
|
45
|
+
}
|
|
46
|
+
//# sourceMappingURL=brain-push-client.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"brain-push-client.js","sourceRoot":"","sources":["../../src/scheduler/brain-push-client.ts"],"names":[],"mappings":"AAAA,uDAAuD;AACvD,EAAE;AACF,gGAAgG;AAChG,yDAAyD;AAezD,MAAM,UAAU,GAAG,2BAA2B,CAAC;AAC/C,MAAM,WAAW,GAAG,4BAA4B,CAAC;AAEjD,MAAM,UAAU,qBAAqB,CAAC,IAA4B;IAChE,MAAM,EAAE,OAAO,EAAE,UAAU,EAAE,SAAS,EAAE,SAAS,GAAG,MAAM,EAAE,GAAG,IAAI,CAAC;IACpE,MAAM,OAAO,GAAG;QACd,cAAc,EAAE,kBAAkB;QAClC,eAAe,EAAE,UAAU;QAC3B,YAAY,EAAE,SAAS;KACxB,CAAC;IAEF,KAAK,UAAU,QAAQ,CAAC,IAAY,EAAE,IAAa;QACjD,MAAM,IAAI,GAAG,IAAI,eAAe,EAAE,CAAC;QACnC,MAAM,KAAK,GAAG,UAAU,CAAC,GAAG,EAAE,CAAC,IAAI,CAAC,KAAK,EAAE,EAAE,SAAS,CAAC,CAAC;QACxD,IAAI,CAAC;YACH,MAAM,GAAG,GAAG,MAAM,KAAK,CAAC,GAAG,OAAO,GAAG,IAAI,EAAE,EAAE;gBAC3C,MAAM,EAAE,MAAM;gBACd,OAAO;gBACP,IAAI,EAAE,IAAI,CAAC,SAAS,CAAC,IAAI,CAAC;gBAC1B,MAAM,EAAE,IAAI,CAAC,MAAM;aACpB,CAAC,CAAC;YACH,IAAI,CAAC,GAAG,CAAC,EAAE,EAAE,CAAC;gBACZ,MAAM,IAAI,GAAG,MAAM,GAAG,CAAC,IAAI,EAAE,CAAC,KAAK,CAAC,GAAG,EAAE,CAAC,EAAE,CAAC,CAAC;gBAC9C,OAAO,EAAE,EAAE,EAAE,KAAK,EAAE,KAAK,EAAE,GAAG,GAAG,CAAC,MAAM,IAAI,IAAI,CAAC,KAAK,CAAC,CAAC,EAAE,GAAG,CAAC,EAAE,EAAE,CAAC;YACrE,CAAC;YACD,OAAO,EAAE,EAAE,EAAE,IAAI,EAAE,CAAC;QACtB,CAAC;QAAC,OAAO,CAAC,EAAE,CAAC;YACX,OAAO,EAAE,EAAE,EAAE,KAAK,EAAE,KAAK,EAAE,CAAC,YAAY,KAAK,CAAC,CAAC,CAAC,CAAC,CAAC,OAAO,CAAC,CAAC,CAAC,MAAM,CAAC,CAAC,CAAC,EAAE,CAAC;QAC1E,CAAC;gBAAS,CAAC;YACT,YAAY,CAAC,KAAK,CAAC,CAAC;QACtB,CAAC;IACH,CAAC;IAED,OAAO;QACL,KAAK,CAAC,iBAAiB,CAAC,OAAO;YAC7B,OAAO,QAAQ,CAAC,UAAU,EAAE,EAAE,SAAS,EAAE,OAAO,EAAE,gBAAgB,EAAE,IAAI,IAAI,EAAE,CAAC,WAAW,EAAE,EAAE,CAAC,CAAC;QAClG,CAAC;QACD,KAAK,CAAC,iBAAiB,CAAC,MAAM;YAC5B,OAAO,QAAQ,CAAC,WAAW,EAAE,EAAE,MAAM,EAAE,gBAAgB,EAAE,IAAI,IAAI,EAAE,CAAC,WAAW,EAAE,EAAE,CAAC,CAAC;QACvF,CAAC;KACF,CAAC;AACJ,CAAC"}
|
|
@@ -1,4 +1,6 @@
|
|
|
1
1
|
export type { ScheduleInterval, PollResult, PollSummary, BrainPushClient, SchedulerConfig, } from './types.js';
|
|
2
2
|
export { pollOnce } from './poll.js';
|
|
3
3
|
export { BeaconScheduler } from './scheduler.js';
|
|
4
|
+
export { createBrainPushClient } from './brain-push-client.js';
|
|
5
|
+
export type { BrainPushClientOptions } from './brain-push-client.js';
|
|
4
6
|
//# sourceMappingURL=index.d.ts.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/scheduler/index.ts"],"names":[],"mappings":"AAEA,YAAY,EACV,gBAAgB,EAChB,UAAU,EACV,WAAW,EACX,eAAe,EACf,eAAe,GAChB,MAAM,YAAY,CAAC;AACpB,OAAO,EAAE,QAAQ,EAAE,MAAM,WAAW,CAAC;AACrC,OAAO,EAAE,eAAe,EAAE,MAAM,gBAAgB,CAAC"}
|
|
1
|
+
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/scheduler/index.ts"],"names":[],"mappings":"AAEA,YAAY,EACV,gBAAgB,EAChB,UAAU,EACV,WAAW,EACX,eAAe,EACf,eAAe,GAChB,MAAM,YAAY,CAAC;AACpB,OAAO,EAAE,QAAQ,EAAE,MAAM,WAAW,CAAC;AACrC,OAAO,EAAE,eAAe,EAAE,MAAM,gBAAgB,CAAC;AACjD,OAAO,EAAE,qBAAqB,EAAE,MAAM,wBAAwB,CAAC;AAC/D,YAAY,EAAE,sBAAsB,EAAE,MAAM,wBAAwB,CAAC"}
|
package/dist/scheduler/index.js
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.js","sourceRoot":"","sources":["../../src/scheduler/index.ts"],"names":[],"mappings":"AAAA,2CAA2C;AAS3C,OAAO,EAAE,QAAQ,EAAE,MAAM,WAAW,CAAC;AACrC,OAAO,EAAE,eAAe,EAAE,MAAM,gBAAgB,CAAC"}
|
|
1
|
+
{"version":3,"file":"index.js","sourceRoot":"","sources":["../../src/scheduler/index.ts"],"names":[],"mappings":"AAAA,2CAA2C;AAS3C,OAAO,EAAE,QAAQ,EAAE,MAAM,WAAW,CAAC;AACrC,OAAO,EAAE,eAAe,EAAE,MAAM,gBAAgB,CAAC;AACjD,OAAO,EAAE,qBAAqB,EAAE,MAAM,wBAAwB,CAAC"}
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@skillfm/local",
|
|
3
|
-
"version": "2.7.
|
|
3
|
+
"version": "2.7.2",
|
|
4
4
|
"description": "SkillFM local — single npm package for the SkillFM platform on user nodes. Subcommand router exposes (1) Beacon MCP stdio server (cost-optimizer for any agent; merged in from @skillfm/beacon-mcp on 2026-05-01), (2) skill runtime (BYOK Playwright / brain reverse-tunnel), (3) sidecar HTTP proxy + OAuth 2.1 device-flow activation. Writes ~/.skillfm/local.json for service discovery.",
|
|
5
5
|
"type": "module",
|
|
6
6
|
"main": "./dist/index.js",
|