@sema-agent/server 7.61.0 → 7.62.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/config-center/skills-mcp.js +4 -2
- package/dist/config-center/types.d.ts +3 -0
- package/dist/config-provider.js +2 -0
- package/dist/mcp-source-label.d.ts +11 -0
- package/dist/mcp-source-label.js +14 -0
- package/dist/observability/fail-open.d.ts +4 -0
- package/dist/observability/fail-open.js +4 -0
- package/dist/task-mcp.js +2 -0
- package/package.json +3 -3
|
@@ -1,3 +1,4 @@
|
|
|
1
|
+
import { readMcpSourceLabel } from "../mcp-source-label.js";
|
|
1
2
|
import { skillContentHash } from "@sema-agent/settings-schema";
|
|
2
3
|
import { CONTENT_ORIGIN_WORDS, describeBadContentOrigin, isContentOriginWord } from "../mcp-content-origin.js";
|
|
3
4
|
import { fetchSkillContent } from "./http-client.js";
|
|
@@ -95,13 +96,14 @@ export function resolveMcpServers(mcp, logger) {
|
|
|
95
96
|
note: "declaration DROPPED — this server's tools keep the pre-378 default (external content, session gets marked). Fix the center entry; the server itself still mounts.",
|
|
96
97
|
});
|
|
97
98
|
}
|
|
99
|
+
const source = readMcpSourceLabel(s.name, s.source);
|
|
98
100
|
if (s.transport.kind === "stdio") {
|
|
99
101
|
const env = resolveRefs(s.transport.envRefs, s.name, "env", logger);
|
|
100
102
|
if (env === null)
|
|
101
103
|
continue;
|
|
102
104
|
out.push({
|
|
103
105
|
scenarios: s.scenarios ?? [],
|
|
104
|
-
spec: { name: s.name, transport: { kind: "stdio", command: s.transport.command, args: s.transport.args, ...(Object.keys(env).length ? { env } : {}) }, ...allow, ...elicit, ...contentOrigin },
|
|
106
|
+
spec: { name: s.name, transport: { kind: "stdio", command: s.transport.command, args: s.transport.args, ...(Object.keys(env).length ? { env } : {}) }, ...allow, ...elicit, ...contentOrigin, ...source },
|
|
105
107
|
});
|
|
106
108
|
}
|
|
107
109
|
else {
|
|
@@ -110,7 +112,7 @@ export function resolveMcpServers(mcp, logger) {
|
|
|
110
112
|
continue;
|
|
111
113
|
out.push({
|
|
112
114
|
scenarios: s.scenarios ?? [],
|
|
113
|
-
spec: { name: s.name, transport: { kind: "http", url: s.transport.url, ...(Object.keys(headers).length ? { headers } : {}), ...(s.transport.principalHeader ? { principalHeader: s.transport.principalHeader } : {}) }, ...allow, ...elicit, ...contentOrigin },
|
|
115
|
+
spec: { name: s.name, transport: { kind: "http", url: s.transport.url, ...(Object.keys(headers).length ? { headers } : {}), ...(s.transport.principalHeader ? { principalHeader: s.transport.principalHeader } : {}) }, ...allow, ...elicit, ...contentOrigin, ...source },
|
|
114
116
|
});
|
|
115
117
|
}
|
|
116
118
|
}
|
|
@@ -113,6 +113,9 @@ export interface CenterMcpServer {
|
|
|
113
113
|
* 自动翻红逼销账。
|
|
114
114
|
*/
|
|
115
115
|
contentOrigin?: ToolContentOrigin;
|
|
116
|
+
/** B-036 / S-143:声明方自述的分组标签(开集,非空 ≤80;settings-schema 1.7.0 `McpServerSpec.source`)——上 core
|
|
117
|
+
* `McpServerSpec.source`,由 `wiring_manifest.mcp[].source` 逐字回显。显示用,不进信任轴。 */
|
|
118
|
+
source?: string;
|
|
116
119
|
transport: {
|
|
117
120
|
kind: "stdio";
|
|
118
121
|
command: string;
|
package/dist/config-provider.js
CHANGED
|
@@ -1,3 +1,4 @@
|
|
|
1
|
+
import { readMcpSourceLabel } from "./mcp-source-label.js";
|
|
1
2
|
import { createHmac, randomBytes } from "node:crypto";
|
|
2
3
|
import { foldEffectiveReadWarning } from "./config-center/read-warnings.js";
|
|
3
4
|
import { FileConfigStore } from "@sema-agent/settings-schema/node";
|
|
@@ -142,6 +143,7 @@ export function mapToServiceEffective(eff, version) {
|
|
|
142
143
|
...(s.allowTools !== undefined ? { allowTools: s.allowTools } : {}),
|
|
143
144
|
...(s.elicitation !== undefined ? { elicitation: s.elicitation } : {}),
|
|
144
145
|
...(s.contentOrigin !== undefined ? { contentOrigin: s.contentOrigin } : {}),
|
|
146
|
+
...readMcpSourceLabel(s.name, s.source),
|
|
145
147
|
};
|
|
146
148
|
if (s.transport.kind === "stdio") {
|
|
147
149
|
return {
|
|
@@ -0,0 +1,11 @@
|
|
|
1
|
+
/** 与 core `mcpManifestEntries` 的 `inlineUntrusted(entry.source, 80)` 同数。 */
|
|
2
|
+
export declare const MCP_SOURCE_LABEL_MAX = 80;
|
|
3
|
+
export declare function isMcpSourceLabel(v: unknown): v is string;
|
|
4
|
+
/**
|
|
5
|
+
* 从任一腿的原始条目里读出 `source`:合法 ⇒ `{ source }`(可直接 spread 进 spec);缺席 ⇒ `{}`;坏形 ⇒ `{}` +
|
|
6
|
+
* 留痕(`server` 与值的形进 detail,不进值本身——标签是 UNTRUSTED-for-display 的自由文本)。
|
|
7
|
+
*/
|
|
8
|
+
export declare function readMcpSourceLabel(server: string, v: unknown): {
|
|
9
|
+
source?: string;
|
|
10
|
+
};
|
|
11
|
+
//# sourceMappingURL=mcp-source-label.d.ts.map
|
|
@@ -0,0 +1,14 @@
|
|
|
1
|
+
import { recordFailOpen } from "./observability/fail-open.js";
|
|
2
|
+
export const MCP_SOURCE_LABEL_MAX = 80;
|
|
3
|
+
export function isMcpSourceLabel(v) {
|
|
4
|
+
return typeof v === "string" && v.length > 0 && v.length <= MCP_SOURCE_LABEL_MAX;
|
|
5
|
+
}
|
|
6
|
+
export function readMcpSourceLabel(server, v) {
|
|
7
|
+
if (v === undefined)
|
|
8
|
+
return {};
|
|
9
|
+
if (isMcpSourceLabel(v))
|
|
10
|
+
return { source: v };
|
|
11
|
+
recordFailOpen("server.task-mcp.source-label-dropped", `${server}: ${typeof v === "string" ? (v.length === 0 ? "empty string" : `string of ${v.length} chars (> ${MCP_SOURCE_LABEL_MAX})`) : typeof v}`);
|
|
12
|
+
return {};
|
|
13
|
+
}
|
|
14
|
+
//# sourceMappingURL=mcp-source-label.js.map
|
|
@@ -9,6 +9,10 @@ export interface FailOpenTagEntry {
|
|
|
9
9
|
}
|
|
10
10
|
/** 闭集 tag 词表。形=`<repo>.<domain>.<site>`(跨仓同形,便于三仓遥测并表)。 */
|
|
11
11
|
export declare const FAIL_OPEN_TAGS: {
|
|
12
|
+
readonly "server.task-mcp.source-label-dropped": {
|
|
13
|
+
readonly cls: "F";
|
|
14
|
+
readonly note: "B-036 / S-143(`mcp-source-label.ts readMcpSourceLabel`,请求腿 + center 腿共用):`mcpServers[].source`(分组标签,显示用、开集)坏形——空串 / 超 80 字 / 非字符串——**丢键留 server**。放行的最坏后果=这台 server 在 wiring_manifest.mcp[] 里没有分组标签(难看),不是门/权限/凭证;本地 config.d 腿由 settings-schema 1.7.0 在解析处拒,故本臂只在请求腿与远端 /effective 直读 JSON 腿可达。";
|
|
15
|
+
};
|
|
12
16
|
readonly "server.memory-optout-grant.onfault-hook-threw": {
|
|
13
17
|
readonly cls: "F";
|
|
14
18
|
readonly note: "design/383 S-1(applyMemoryOptOutGrant):本地 grant 腿故障时的**披露钩子**(onFault → warn 日志)自己抛了。钩子只是观测面:吞掉它保住的是「resolver 不因一行日志失败而 reject」(那会把一条腿的故障扩成整车故障 —— core 的 resolver-throw 降级臂作废同一次解析里 center 已答好的 allowWorkflows/allowFork);代价是**那一行披露丢了**,而 `allowMemoryOptOut` 键缺席这件事本身不受影响(fail-closed/fail-safe 极性由 core 按姿态判)。本计数让「披露钩子一直在炸」显形。";
|
|
@@ -1,5 +1,9 @@
|
|
|
1
1
|
import { appendFileSync } from "node:fs";
|
|
2
2
|
export const FAIL_OPEN_TAGS = {
|
|
3
|
+
"server.task-mcp.source-label-dropped": {
|
|
4
|
+
cls: "F",
|
|
5
|
+
note: "B-036 / S-143(`mcp-source-label.ts readMcpSourceLabel`,请求腿 + center 腿共用):`mcpServers[].source`(分组标签,显示用、开集)坏形——空串 / 超 80 字 / 非字符串——**丢键留 server**。放行的最坏后果=这台 server 在 wiring_manifest.mcp[] 里没有分组标签(难看),不是门/权限/凭证;本地 config.d 腿由 settings-schema 1.7.0 在解析处拒,故本臂只在请求腿与远端 /effective 直读 JSON 腿可达。",
|
|
6
|
+
},
|
|
3
7
|
"server.memory-optout-grant.onfault-hook-threw": {
|
|
4
8
|
cls: "F",
|
|
5
9
|
note: "design/383 S-1(applyMemoryOptOutGrant):本地 grant 腿故障时的**披露钩子**(onFault → warn 日志)自己抛了。钩子只是观测面:吞掉它保住的是「resolver 不因一行日志失败而 reject」(那会把一条腿的故障扩成整车故障 —— core 的 resolver-throw 降级臂作废同一次解析里 center 已答好的 allowWorkflows/allowFork);代价是**那一行披露丢了**,而 `allowMemoryOptOut` 键缺席这件事本身不受影响(fail-closed/fail-safe 极性由 core 按姿态判)。本计数让「披露钩子一直在炸」显形。",
|
package/dist/task-mcp.js
CHANGED
|
@@ -1,6 +1,7 @@
|
|
|
1
1
|
import { resolveComplianceDenies } from "@sema-agent/core";
|
|
2
2
|
import { HttpError } from "./security.js";
|
|
3
3
|
import { CONTENT_ORIGIN_WORDS, describeBadContentOrigin, isContentOriginWord } from "./mcp-content-origin.js";
|
|
4
|
+
import { readMcpSourceLabel } from "./mcp-source-label.js";
|
|
4
5
|
export const MAX_REQUEST_MCP_SERVERS = 32;
|
|
5
6
|
export function mcpInjectionHonored(config) {
|
|
6
7
|
if (config.lockedConfigKeys?.includes("mcp") === true)
|
|
@@ -77,6 +78,7 @@ function normalizeServer(e, noteBadOrigin) {
|
|
|
77
78
|
else
|
|
78
79
|
noteBadOrigin(spec.name, o.contentOrigin);
|
|
79
80
|
}
|
|
81
|
+
Object.assign(spec, readMcpSourceLabel(spec.name, o.source));
|
|
80
82
|
return spec;
|
|
81
83
|
}
|
|
82
84
|
export function validateRequestMcp(raw) {
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@sema-agent/server",
|
|
3
|
-
"version": "7.
|
|
3
|
+
"version": "7.62.0",
|
|
4
4
|
"description": "Sema Server — the server/API implementation layer for Sema, wiring core, registry, model providers, and cloud agent execution. Built on @sema-agent/core.",
|
|
5
5
|
"type": "module",
|
|
6
6
|
"license": "BUSL-1.1",
|
|
@@ -54,8 +54,8 @@
|
|
|
54
54
|
"build:binary:run-local:darwin-arm64": "bun build --compile --target=bun-darwin-arm64 src/run-local.ts --outfile dist/run-local-darwin-arm64"
|
|
55
55
|
},
|
|
56
56
|
"dependencies": {
|
|
57
|
-
"@sema-agent/core": "7.5.
|
|
58
|
-
"@sema-agent/settings-schema": "1.
|
|
57
|
+
"@sema-agent/core": "7.5.2",
|
|
58
|
+
"@sema-agent/settings-schema": "1.7.1",
|
|
59
59
|
"e2b": "^2.28.0",
|
|
60
60
|
"libsodium-wrappers": "^0.8.4",
|
|
61
61
|
"mysql2": "^3.22.4",
|