mirror of
https://github.com/openclaw/openclaw.git
synced 2026-07-19 09:21:37 +00:00
fix(node-pairing): require operator.admin to approve browser.proxy nodes (#104491)
Approving a node whose pairing surface advertises browser.proxy only required operator.write, while invoking browser.proxy already requires operator.admin (server-methods/nodes.ts). resolveNodePairApprovalScopes bumped the approval scope to operator.admin only for NODE_SYSTEM_RUN_COMMANDS, so a write-scoped operator could trust a browser.proxy-capable node that later routes bundled browser-tool traffic. Add NODE_BROWSER_PROXY_COMMAND to the admin-approval set so approval scope matches the invoke-time gate.
This commit is contained in:
@@ -10,6 +10,13 @@ describe("resolveNodePairApprovalScopes", () => {
|
||||
]);
|
||||
});
|
||||
|
||||
it("requires operator.admin for browser.proxy commands", () => {
|
||||
expect(resolveNodePairApprovalScopes(["browser.proxy"])).toEqual([
|
||||
"operator.pairing",
|
||||
"operator.admin",
|
||||
]);
|
||||
});
|
||||
|
||||
it("requires operator.write for non-exec commands", () => {
|
||||
expect(resolveNodePairApprovalScopes(["canvas.present"])).toEqual([
|
||||
"operator.pairing",
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
// Maps node pairing command declarations to required operator scopes.
|
||||
import { NODE_SYSTEM_RUN_COMMANDS } from "./node-commands.js";
|
||||
import { NODE_BROWSER_PROXY_COMMAND, NODE_SYSTEM_RUN_COMMANDS } from "./node-commands.js";
|
||||
|
||||
/** Operator scopes required to approve a pending node pairing surface. */
|
||||
export type NodeApprovalScope = "operator.pairing" | "operator.write" | "operator.admin";
|
||||
@@ -8,13 +8,15 @@ const OPERATOR_PAIRING_SCOPE: NodeApprovalScope = "operator.pairing";
|
||||
const OPERATOR_WRITE_SCOPE: NodeApprovalScope = "operator.write";
|
||||
const OPERATOR_ADMIN_SCOPE: NodeApprovalScope = "operator.admin";
|
||||
|
||||
const ADMIN_APPROVAL_COMMANDS = [...NODE_SYSTEM_RUN_COMMANDS, NODE_BROWSER_PROXY_COMMAND];
|
||||
|
||||
/** Map declared node commands to the least operator scopes needed for approval. */
|
||||
export function resolveNodePairApprovalScopes(commands: unknown): NodeApprovalScope[] {
|
||||
const normalized = Array.isArray(commands)
|
||||
? commands.filter((command): command is string => typeof command === "string")
|
||||
: [];
|
||||
if (
|
||||
normalized.some((command) => NODE_SYSTEM_RUN_COMMANDS.some((allowed) => allowed === command))
|
||||
normalized.some((command) => ADMIN_APPROVAL_COMMANDS.some((allowed) => allowed === command))
|
||||
) {
|
||||
return [OPERATOR_PAIRING_SCOPE, OPERATOR_ADMIN_SCOPE];
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user