Remove AI config approval flow
This commit is contained in:
+1
-1
@@ -13,7 +13,7 @@ A game management plugin defines how the platform creates and manages one type o
|
||||
- Optional remote access methods and remote run capabilities.
|
||||
- Optional runtime profiles for discovery, lifecycle modes, dependency probes, install plans, log sources, transports, and plugin-owned component declarations.
|
||||
- Optional plugin pages hosted by platform_web.
|
||||
- AI/file/log permissions declared for platform authorization, including `ai.mediation=platform` and `ai.configWritePolicy=review-required`.
|
||||
- AI/file/log permissions declared for platform authorization, including `ai.mediation=platform`. AI configuration requests are dispatched through the platform's typed config-write job path.
|
||||
- Production lifecycle operations, dependency policy, and disruptive approval requirements.
|
||||
|
||||
## Required Directory Plan
|
||||
|
||||
@@ -159,7 +159,6 @@
|
||||
"config.suggest",
|
||||
"logs.diagnose"
|
||||
],
|
||||
"mediation": "platform",
|
||||
"configWritePolicy": "review-required"
|
||||
"mediation": "platform"
|
||||
}
|
||||
}
|
||||
|
||||
@@ -22,7 +22,7 @@ function renderConfigPage(e: ReactLike["createElement"], input: any) {
|
||||
return renderPanel(e, "配置工作台", "配置入口由插件页面声明,平台只提供运行上下文。", input, [
|
||||
["文件权限", (input.context?.permissions ?? []).filter((value: string) => value.includes("files")).join(" / ") || "未声明"],
|
||||
["AI 能力", (input.context?.permissions ?? []).includes("ai.invoke") ? "可请求平台 AI" : "未声明"],
|
||||
["写入策略", "平台审查后派发"]
|
||||
["写入策略", "平台校验后直接派发"]
|
||||
]);
|
||||
}
|
||||
|
||||
|
||||
@@ -55,6 +55,7 @@
|
||||
"files.list",
|
||||
"files.read",
|
||||
"files.write",
|
||||
"config.write",
|
||||
"files.patch",
|
||||
"logs.read",
|
||||
"remote.run.files.read",
|
||||
@@ -294,8 +295,7 @@
|
||||
"config.suggest",
|
||||
"logs.diagnose"
|
||||
],
|
||||
"mediation": "platform",
|
||||
"configWritePolicy": "review-required"
|
||||
"mediation": "platform"
|
||||
},
|
||||
"runtimeProfiles": {
|
||||
"discovery": [
|
||||
@@ -323,6 +323,7 @@
|
||||
"process.stop",
|
||||
"process.restart",
|
||||
"process.status",
|
||||
"config.write",
|
||||
"remote.run.process.start",
|
||||
"remote.run.process.stop"
|
||||
],
|
||||
|
||||
@@ -62,6 +62,7 @@
|
||||
"process.status",
|
||||
"files.list",
|
||||
"files.read",
|
||||
"config.write",
|
||||
"files.patch",
|
||||
"logs.read",
|
||||
"remote.ftp.read",
|
||||
@@ -1071,8 +1072,7 @@
|
||||
"purposes": [
|
||||
"config.suggest"
|
||||
],
|
||||
"mediation": "platform",
|
||||
"configWritePolicy": "review-required"
|
||||
"mediation": "platform"
|
||||
},
|
||||
"runtimeProfiles": {
|
||||
"discovery": [
|
||||
@@ -1102,6 +1102,7 @@
|
||||
"process.stop",
|
||||
"process.restart",
|
||||
"process.status",
|
||||
"config.write",
|
||||
"remote.run.process.start",
|
||||
"remote.run.process.stop",
|
||||
"remote.run.rcon.command"
|
||||
|
||||
@@ -187,12 +187,11 @@
|
||||
"fileWorkspace": { "type": "object", "required": ["defaultDirectoryKey", "directories", "files", "configFields"], "additionalProperties": false, "properties": { "defaultDirectoryKey": { "$ref": "#/$defs/logicalKey" }, "directories": { "type": "array", "items": { "$ref": "#/$defs/pluginLogicalDirectory" } }, "files": { "type": "array", "items": { "$ref": "#/$defs/pluginLogicalFile" } }, "configFields": { "type": "array", "items": { "$ref": "#/$defs/pluginConfigField" } } } },
|
||||
"ai": {
|
||||
"type": "object",
|
||||
"required": ["mediation", "configWritePolicy"],
|
||||
"required": ["mediation"],
|
||||
"additionalProperties": false,
|
||||
"properties": {
|
||||
"purposes": { "type": "array", "items": { "$ref": "#/$defs/aiPurpose" }, "uniqueItems": true },
|
||||
"mediation": { "const": "platform" },
|
||||
"configWritePolicy": { "const": "review-required" }
|
||||
"mediation": { "const": "platform" }
|
||||
}
|
||||
}
|
||||
},
|
||||
|
||||
@@ -24,7 +24,7 @@ Plugin pages build execution requests with `createBridgeExecutionRequest` and ha
|
||||
|
||||
Execution responses use `requestId`, plugin/page/server scope, action, status, optional result refs, and optional safe errors. Use `parseBridgeExecutionResponse` before reading results so plugin code handles denied, deferred, and failed states uniformly.
|
||||
|
||||
AI requests use `createAIInvocationRequest` with an explicit manifest-declared purpose, prompt, and scoped context refs. Use `parseAIInvocationResponse` to consume recommendations, reviewable `diffId` metadata, and safe errors. Plugin code must not choose or receive provider API keys, provider base URLs, bearer tokens, or direct transport details. Config writes require a separate Platform operator approval.
|
||||
AI requests use `createAIInvocationRequest` with an explicit manifest-declared purpose, prompt, and scoped context refs. Use `parseAIInvocationResponse` to consume recommendations, optional `configExecution` job metadata, and safe errors. For config purposes Platform validates the current config and dispatches the bounded `config.write` job immediately; plugin code must not choose or receive provider API keys, provider base URLs, bearer tokens, or direct transport details.
|
||||
|
||||
Artifact open requests use `createArtifactOpenRequest` with an artifact ID that belongs to the current server/job scope. Use `parseArtifactReference` to consume the bridge result. Parsed references contain platform-owned download URLs, filename, content type, size, checksum, expiry, range support, and chunk size; they do not contain bytes or raw storage adapter locations.
|
||||
|
||||
|
||||
@@ -122,7 +122,8 @@ export interface PluginAIInvocationResponse {
|
||||
purpose: AIPurpose;
|
||||
status: "ok" | "denied" | "error" | string;
|
||||
recommendation?: string;
|
||||
configRecommendation?: { diffId: string; key: string; suggestedConfig: string; diffSummary: string; expiresAt: string };
|
||||
configRecommendation?: { key: string; suggestedConfig: string; diffSummary: string };
|
||||
configExecution?: { status: string; jobId: string; capability: string; targetKey?: string; inputRef?: string };
|
||||
usage?: { model?: string; mocked?: boolean; inputTokens?: number; outputTokens?: number };
|
||||
error?: PluginBridgeError;
|
||||
}
|
||||
@@ -574,7 +575,6 @@ export interface GamePluginManifest {
|
||||
ai?: {
|
||||
purposes?: AIPurpose[];
|
||||
mediation: "platform";
|
||||
configWritePolicy: "review-required";
|
||||
};
|
||||
}
|
||||
|
||||
@@ -866,6 +866,7 @@ export function parseAIInvocationResponse(response: PluginAIInvocationResponse):
|
||||
status: response.status,
|
||||
recommendation: response.recommendation,
|
||||
configRecommendation: response.configRecommendation ? { ...response.configRecommendation } : undefined,
|
||||
configExecution: response.configExecution ? { ...response.configExecution } : undefined,
|
||||
usage: response.usage ? { ...response.usage } : undefined,
|
||||
error: response.error ? bridgeError(response.error.code, response.error.message, response.error.details ?? []) : undefined
|
||||
};
|
||||
|
||||
Reference in New Issue
Block a user