@alfe.ai/openclaw-identity 0.1.26 → 0.1.28
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/README.md +14 -0
- package/dist/index.cjs +2 -2
- package/dist/index.d.cts +40 -28
- package/dist/index.d.ts +40 -28
- package/dist/index.js +2 -2
- package/dist/plugin.cjs +5 -1
- package/dist/plugin.d.cts +25 -15
- package/dist/plugin.d.ts +25 -15
- package/dist/plugin2.cjs +161 -193
- package/dist/plugin2.d.cts +2 -0
- package/dist/plugin2.d.ts +2 -0
- package/dist/plugin2.js +150 -182
- package/package.json +4 -3
package/README.md
ADDED
|
@@ -0,0 +1,14 @@
|
|
|
1
|
+
# `@alfe.ai/openclaw-identity`
|
|
2
|
+
|
|
3
|
+
OpenClaw plugin for Alfe identity resolution, self-service verification, and
|
|
4
|
+
role-based `agent:exec` tool gating.
|
|
5
|
+
|
|
6
|
+
The plugin registers identity tools, prepares a short-lived sender context from
|
|
7
|
+
inbound messages, and evaluates tool calls with `@auriclabs/roles`. The
|
|
8
|
+
`OPENCLAW_TOOL_GATING` environment variable accepts `fail-open` or
|
|
9
|
+
`fail-closed`; it intentionally defaults to `fail-open` while the staged
|
|
10
|
+
permission rollout is incomplete.
|
|
11
|
+
|
|
12
|
+
This package is installed by the core Alfe integration. For platform setup and
|
|
13
|
+
documentation, visit [alfe.ai](https://alfe.ai) and
|
|
14
|
+
[docs.alfe.ai](https://docs.alfe.ai).
|
package/dist/index.cjs
CHANGED
|
@@ -7,7 +7,7 @@ const require_plugin = require("./plugin2.cjs");
|
|
|
7
7
|
/**
|
|
8
8
|
* Build the gate context object used by sift evaluation. This is the
|
|
9
9
|
* round-6 "strict namespacing" shape — `args` is a top-level field, not
|
|
10
|
-
* spread, so an attacker-controlled `tool` field inside `
|
|
10
|
+
* spread, so an attacker-controlled `tool` field inside `params` cannot
|
|
11
11
|
* override the gate's `tool` value.
|
|
12
12
|
*
|
|
13
13
|
* Stage E's gate calls:
|
|
@@ -19,7 +19,7 @@ const require_plugin = require("./plugin2.cjs");
|
|
|
19
19
|
function buildGateContext(event) {
|
|
20
20
|
return {
|
|
21
21
|
tool: event.toolName,
|
|
22
|
-
args: event.
|
|
22
|
+
args: event.params
|
|
23
23
|
};
|
|
24
24
|
}
|
|
25
25
|
//#endregion
|
package/dist/index.d.cts
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import plugin from "./plugin.cjs";
|
|
1
|
+
import { t as plugin } from "./plugin.cjs";
|
|
2
2
|
|
|
3
3
|
//#region src/runtime-contract.d.ts
|
|
4
4
|
|
|
@@ -11,18 +11,19 @@ import plugin from "./plugin.cjs";
|
|
|
11
11
|
* permit/deny decision via `@auriclabs/roles`.
|
|
12
12
|
*
|
|
13
13
|
* Contract:
|
|
14
|
-
* - `ToolCallEvent` describes the tool being called (name +
|
|
15
|
-
* - `ToolCallContext`
|
|
14
|
+
* - `ToolCallEvent` describes the tool being called (name + params).
|
|
15
|
+
* - `ToolCallContext` mirrors the fields OpenClaw actually supplies.
|
|
16
16
|
*
|
|
17
|
-
* The hook receives `(event, ctx)`.
|
|
18
|
-
*
|
|
19
|
-
*
|
|
20
|
-
*
|
|
17
|
+
* The hook receives `(event, ctx)`. OpenClaw currently supplies tool identity,
|
|
18
|
+
* run/session identity, and an optional agent id. It does not supply tenant,
|
|
19
|
+
* conversation, actor, auth-method, or token-permission fields. The plugin
|
|
20
|
+
* bridges the active conversation from `message_received` into the run instead
|
|
21
|
+
* of pretending those absent fields are runtime guarantees.
|
|
21
22
|
*
|
|
22
23
|
* Round 6 note (gate context shape): the gate context passed to `sift` is
|
|
23
|
-
* `{ tool: event.toolName, args: event.
|
|
24
|
+
* `{ tool: event.toolName, args: event.params }` with strict namespacing
|
|
24
25
|
* (no spread). This prevents an attacker-controlled `tool` field inside
|
|
25
|
-
* `
|
|
26
|
+
* `params` from overriding the gate's value.
|
|
26
27
|
*/
|
|
27
28
|
/**
|
|
28
29
|
* Per-agent fallback policy when an optional `ctx.actingIdentityId` is
|
|
@@ -47,7 +48,11 @@ interface ToolCallEvent {
|
|
|
47
48
|
/** Namespaced tool name, e.g. "gmail:send_email". */
|
|
48
49
|
readonly toolName: string;
|
|
49
50
|
/** Arbitrary argument bag passed to the tool's `execute` function. */
|
|
50
|
-
readonly
|
|
51
|
+
readonly params: Record<string, unknown>;
|
|
52
|
+
/** Stable run identifier for this invocation, when supplied. */
|
|
53
|
+
readonly runId?: string;
|
|
54
|
+
/** Provider-specific tool-call identifier, when supplied. */
|
|
55
|
+
readonly toolCallId?: string;
|
|
51
56
|
}
|
|
52
57
|
/**
|
|
53
58
|
* What initiated the tool call. Three buckets:
|
|
@@ -97,18 +102,24 @@ interface RuntimePermission {
|
|
|
97
102
|
readonly type?: "can" | "cannot";
|
|
98
103
|
}
|
|
99
104
|
/**
|
|
100
|
-
* Calling context for the tool call.
|
|
101
|
-
*
|
|
105
|
+
* Calling context for the tool call. This is the production OpenClaw hook
|
|
106
|
+
* shape (verified against the installed runtime), not an aspirational Alfe
|
|
107
|
+
* authorization envelope.
|
|
102
108
|
*/
|
|
103
109
|
interface ToolCallContext {
|
|
104
|
-
|
|
105
|
-
readonly
|
|
106
|
-
|
|
107
|
-
readonly
|
|
108
|
-
|
|
109
|
-
readonly
|
|
110
|
-
/**
|
|
111
|
-
|
|
110
|
+
readonly toolName: string;
|
|
111
|
+
readonly agentId?: string;
|
|
112
|
+
readonly sessionKey?: string;
|
|
113
|
+
readonly sessionId?: string;
|
|
114
|
+
readonly runId?: string;
|
|
115
|
+
readonly toolCallId?: string;
|
|
116
|
+
/**
|
|
117
|
+
* Compatibility fields for an Alfe-augmented runtime. Stock OpenClaw does
|
|
118
|
+
* not currently populate these; callers must not depend on their presence.
|
|
119
|
+
*/
|
|
120
|
+
readonly tenantId?: string;
|
|
121
|
+
readonly authMethod?: ToolCallAuthMethod;
|
|
122
|
+
readonly trigger?: ToolCallTrigger;
|
|
112
123
|
/**
|
|
113
124
|
* The identity (`idn_*`) the agent is acting on behalf of. Resolution
|
|
114
125
|
* order:
|
|
@@ -136,25 +147,26 @@ interface ToolCallContext {
|
|
|
136
147
|
readonly channelId?: string;
|
|
137
148
|
}
|
|
138
149
|
/**
|
|
139
|
-
*
|
|
140
|
-
* - `undefined` — allow.
|
|
141
|
-
* - `{
|
|
142
|
-
*
|
|
150
|
+
* Relevant subset of OpenClaw's `before_tool_call` return value.
|
|
151
|
+
* - `undefined` — allow without changing parameters.
|
|
152
|
+
* - `{ params }` — allow with parameters merged into the tool invocation.
|
|
153
|
+
* - `{ block: true, blockReason }` — deny with a surfaced reason.
|
|
143
154
|
*/
|
|
144
155
|
type ToolCallHookResult = undefined | {
|
|
156
|
+
params: Record<string, unknown>;
|
|
157
|
+
} | {
|
|
145
158
|
block: true;
|
|
146
159
|
blockReason: string;
|
|
147
160
|
};
|
|
148
161
|
/**
|
|
149
|
-
* Strongly-typed `before_tool_call` hook signature
|
|
150
|
-
*
|
|
151
|
-
* sift gate against `@auriclabs/roles`.
|
|
162
|
+
* Strongly-typed `before_tool_call` hook signature used by the live
|
|
163
|
+
* `agent:exec` + sift gate against `@auriclabs/roles`.
|
|
152
164
|
*/
|
|
153
165
|
type BeforeToolCallHook = (event: ToolCallEvent, ctx: ToolCallContext) => Promise<ToolCallHookResult>;
|
|
154
166
|
/**
|
|
155
167
|
* Build the gate context object used by sift evaluation. This is the
|
|
156
168
|
* round-6 "strict namespacing" shape — `args` is a top-level field, not
|
|
157
|
-
* spread, so an attacker-controlled `tool` field inside `
|
|
169
|
+
* spread, so an attacker-controlled `tool` field inside `params` cannot
|
|
158
170
|
* override the gate's `tool` value.
|
|
159
171
|
*
|
|
160
172
|
* Stage E's gate calls:
|
package/dist/index.d.ts
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import plugin from "./plugin.js";
|
|
1
|
+
import { t as plugin } from "./plugin.js";
|
|
2
2
|
|
|
3
3
|
//#region src/runtime-contract.d.ts
|
|
4
4
|
|
|
@@ -11,18 +11,19 @@ import plugin from "./plugin.js";
|
|
|
11
11
|
* permit/deny decision via `@auriclabs/roles`.
|
|
12
12
|
*
|
|
13
13
|
* Contract:
|
|
14
|
-
* - `ToolCallEvent` describes the tool being called (name +
|
|
15
|
-
* - `ToolCallContext`
|
|
14
|
+
* - `ToolCallEvent` describes the tool being called (name + params).
|
|
15
|
+
* - `ToolCallContext` mirrors the fields OpenClaw actually supplies.
|
|
16
16
|
*
|
|
17
|
-
* The hook receives `(event, ctx)`.
|
|
18
|
-
*
|
|
19
|
-
*
|
|
20
|
-
*
|
|
17
|
+
* The hook receives `(event, ctx)`. OpenClaw currently supplies tool identity,
|
|
18
|
+
* run/session identity, and an optional agent id. It does not supply tenant,
|
|
19
|
+
* conversation, actor, auth-method, or token-permission fields. The plugin
|
|
20
|
+
* bridges the active conversation from `message_received` into the run instead
|
|
21
|
+
* of pretending those absent fields are runtime guarantees.
|
|
21
22
|
*
|
|
22
23
|
* Round 6 note (gate context shape): the gate context passed to `sift` is
|
|
23
|
-
* `{ tool: event.toolName, args: event.
|
|
24
|
+
* `{ tool: event.toolName, args: event.params }` with strict namespacing
|
|
24
25
|
* (no spread). This prevents an attacker-controlled `tool` field inside
|
|
25
|
-
* `
|
|
26
|
+
* `params` from overriding the gate's value.
|
|
26
27
|
*/
|
|
27
28
|
/**
|
|
28
29
|
* Per-agent fallback policy when an optional `ctx.actingIdentityId` is
|
|
@@ -47,7 +48,11 @@ interface ToolCallEvent {
|
|
|
47
48
|
/** Namespaced tool name, e.g. "gmail:send_email". */
|
|
48
49
|
readonly toolName: string;
|
|
49
50
|
/** Arbitrary argument bag passed to the tool's `execute` function. */
|
|
50
|
-
readonly
|
|
51
|
+
readonly params: Record<string, unknown>;
|
|
52
|
+
/** Stable run identifier for this invocation, when supplied. */
|
|
53
|
+
readonly runId?: string;
|
|
54
|
+
/** Provider-specific tool-call identifier, when supplied. */
|
|
55
|
+
readonly toolCallId?: string;
|
|
51
56
|
}
|
|
52
57
|
/**
|
|
53
58
|
* What initiated the tool call. Three buckets:
|
|
@@ -97,18 +102,24 @@ interface RuntimePermission {
|
|
|
97
102
|
readonly type?: "can" | "cannot";
|
|
98
103
|
}
|
|
99
104
|
/**
|
|
100
|
-
* Calling context for the tool call.
|
|
101
|
-
*
|
|
105
|
+
* Calling context for the tool call. This is the production OpenClaw hook
|
|
106
|
+
* shape (verified against the installed runtime), not an aspirational Alfe
|
|
107
|
+
* authorization envelope.
|
|
102
108
|
*/
|
|
103
109
|
interface ToolCallContext {
|
|
104
|
-
|
|
105
|
-
readonly
|
|
106
|
-
|
|
107
|
-
readonly
|
|
108
|
-
|
|
109
|
-
readonly
|
|
110
|
-
/**
|
|
111
|
-
|
|
110
|
+
readonly toolName: string;
|
|
111
|
+
readonly agentId?: string;
|
|
112
|
+
readonly sessionKey?: string;
|
|
113
|
+
readonly sessionId?: string;
|
|
114
|
+
readonly runId?: string;
|
|
115
|
+
readonly toolCallId?: string;
|
|
116
|
+
/**
|
|
117
|
+
* Compatibility fields for an Alfe-augmented runtime. Stock OpenClaw does
|
|
118
|
+
* not currently populate these; callers must not depend on their presence.
|
|
119
|
+
*/
|
|
120
|
+
readonly tenantId?: string;
|
|
121
|
+
readonly authMethod?: ToolCallAuthMethod;
|
|
122
|
+
readonly trigger?: ToolCallTrigger;
|
|
112
123
|
/**
|
|
113
124
|
* The identity (`idn_*`) the agent is acting on behalf of. Resolution
|
|
114
125
|
* order:
|
|
@@ -136,25 +147,26 @@ interface ToolCallContext {
|
|
|
136
147
|
readonly channelId?: string;
|
|
137
148
|
}
|
|
138
149
|
/**
|
|
139
|
-
*
|
|
140
|
-
* - `undefined` — allow.
|
|
141
|
-
* - `{
|
|
142
|
-
*
|
|
150
|
+
* Relevant subset of OpenClaw's `before_tool_call` return value.
|
|
151
|
+
* - `undefined` — allow without changing parameters.
|
|
152
|
+
* - `{ params }` — allow with parameters merged into the tool invocation.
|
|
153
|
+
* - `{ block: true, blockReason }` — deny with a surfaced reason.
|
|
143
154
|
*/
|
|
144
155
|
type ToolCallHookResult = undefined | {
|
|
156
|
+
params: Record<string, unknown>;
|
|
157
|
+
} | {
|
|
145
158
|
block: true;
|
|
146
159
|
blockReason: string;
|
|
147
160
|
};
|
|
148
161
|
/**
|
|
149
|
-
* Strongly-typed `before_tool_call` hook signature
|
|
150
|
-
*
|
|
151
|
-
* sift gate against `@auriclabs/roles`.
|
|
162
|
+
* Strongly-typed `before_tool_call` hook signature used by the live
|
|
163
|
+
* `agent:exec` + sift gate against `@auriclabs/roles`.
|
|
152
164
|
*/
|
|
153
165
|
type BeforeToolCallHook = (event: ToolCallEvent, ctx: ToolCallContext) => Promise<ToolCallHookResult>;
|
|
154
166
|
/**
|
|
155
167
|
* Build the gate context object used by sift evaluation. This is the
|
|
156
168
|
* round-6 "strict namespacing" shape — `args` is a top-level field, not
|
|
157
|
-
* spread, so an attacker-controlled `tool` field inside `
|
|
169
|
+
* spread, so an attacker-controlled `tool` field inside `params` cannot
|
|
158
170
|
* override the gate's `tool` value.
|
|
159
171
|
*
|
|
160
172
|
* Stage E's gate calls:
|
package/dist/index.js
CHANGED
|
@@ -3,7 +3,7 @@ import { t as plugin } from "./plugin2.js";
|
|
|
3
3
|
/**
|
|
4
4
|
* Build the gate context object used by sift evaluation. This is the
|
|
5
5
|
* round-6 "strict namespacing" shape — `args` is a top-level field, not
|
|
6
|
-
* spread, so an attacker-controlled `tool` field inside `
|
|
6
|
+
* spread, so an attacker-controlled `tool` field inside `params` cannot
|
|
7
7
|
* override the gate's `tool` value.
|
|
8
8
|
*
|
|
9
9
|
* Stage E's gate calls:
|
|
@@ -15,7 +15,7 @@ import { t as plugin } from "./plugin2.js";
|
|
|
15
15
|
function buildGateContext(event) {
|
|
16
16
|
return {
|
|
17
17
|
tool: event.toolName,
|
|
18
|
-
args: event.
|
|
18
|
+
args: event.params
|
|
19
19
|
};
|
|
20
20
|
}
|
|
21
21
|
//#endregion
|
package/dist/plugin.cjs
CHANGED
package/dist/plugin.d.cts
CHANGED
|
@@ -1,5 +1,28 @@
|
|
|
1
1
|
import { TSchema } from "@sinclair/typebox";
|
|
2
2
|
|
|
3
|
+
//#region ../openclaw-plugin-kit/dist/index.d.ts
|
|
4
|
+
|
|
5
|
+
//# sourceMappingURL=types.d.ts.map
|
|
6
|
+
//#endregion
|
|
7
|
+
//#region src/tools.d.ts
|
|
8
|
+
/** Shape returned to OpenClaw from a tool `execute`. */
|
|
9
|
+
interface ToolResult {
|
|
10
|
+
content: {
|
|
11
|
+
type: "text";
|
|
12
|
+
text: string;
|
|
13
|
+
}[];
|
|
14
|
+
details: unknown;
|
|
15
|
+
isError?: boolean;
|
|
16
|
+
}
|
|
17
|
+
interface ToolDef<TParameters = unknown> {
|
|
18
|
+
name: string;
|
|
19
|
+
description: string;
|
|
20
|
+
label: string;
|
|
21
|
+
parameters: TParameters;
|
|
22
|
+
execute: (toolCallId: string, params: Record<string, unknown>) => Promise<ToolResult>;
|
|
23
|
+
}
|
|
24
|
+
/** Deliberately model-safe validation/usage failure. Other exceptions stay private. */
|
|
25
|
+
//#endregion
|
|
3
26
|
//#region src/plugin.d.ts
|
|
4
27
|
|
|
5
28
|
interface PluginLogger {
|
|
@@ -8,23 +31,10 @@ interface PluginLogger {
|
|
|
8
31
|
error: (...args: unknown[]) => void;
|
|
9
32
|
debug: (...args: unknown[]) => void;
|
|
10
33
|
}
|
|
11
|
-
interface ToolDef {
|
|
12
|
-
name: string;
|
|
13
|
-
description: string;
|
|
14
|
-
label: string;
|
|
15
|
-
parameters: TSchema;
|
|
16
|
-
execute: (toolCallId: string, params: Record<string, unknown>) => Promise<{
|
|
17
|
-
content: {
|
|
18
|
-
type: "text";
|
|
19
|
-
text: string;
|
|
20
|
-
}[];
|
|
21
|
-
details: unknown;
|
|
22
|
-
}>;
|
|
23
|
-
}
|
|
24
34
|
interface PluginApi {
|
|
25
35
|
logger: PluginLogger;
|
|
26
36
|
registrationMode?: "full" | "setup-only" | "setup-runtime" | "cli-metadata";
|
|
27
|
-
registerTool: (tool: ToolDef) => void;
|
|
37
|
+
registerTool: (tool: ToolDef<TSchema>) => void;
|
|
28
38
|
on: (event: string, handler: (...args: unknown[]) => Promise<unknown>, options?: {
|
|
29
39
|
priority?: number;
|
|
30
40
|
}) => void;
|
|
@@ -38,4 +48,4 @@ declare const plugin: {
|
|
|
38
48
|
deactivate(api: PluginApi): void;
|
|
39
49
|
};
|
|
40
50
|
//#endregion
|
|
41
|
-
export { plugin as
|
|
51
|
+
export { plugin as t };
|
package/dist/plugin.d.ts
CHANGED
|
@@ -1,5 +1,28 @@
|
|
|
1
1
|
import { TSchema } from "@sinclair/typebox";
|
|
2
2
|
|
|
3
|
+
//#region ../openclaw-plugin-kit/dist/index.d.ts
|
|
4
|
+
|
|
5
|
+
//# sourceMappingURL=types.d.ts.map
|
|
6
|
+
//#endregion
|
|
7
|
+
//#region src/tools.d.ts
|
|
8
|
+
/** Shape returned to OpenClaw from a tool `execute`. */
|
|
9
|
+
interface ToolResult {
|
|
10
|
+
content: {
|
|
11
|
+
type: "text";
|
|
12
|
+
text: string;
|
|
13
|
+
}[];
|
|
14
|
+
details: unknown;
|
|
15
|
+
isError?: boolean;
|
|
16
|
+
}
|
|
17
|
+
interface ToolDef<TParameters = unknown> {
|
|
18
|
+
name: string;
|
|
19
|
+
description: string;
|
|
20
|
+
label: string;
|
|
21
|
+
parameters: TParameters;
|
|
22
|
+
execute: (toolCallId: string, params: Record<string, unknown>) => Promise<ToolResult>;
|
|
23
|
+
}
|
|
24
|
+
/** Deliberately model-safe validation/usage failure. Other exceptions stay private. */
|
|
25
|
+
//#endregion
|
|
3
26
|
//#region src/plugin.d.ts
|
|
4
27
|
|
|
5
28
|
interface PluginLogger {
|
|
@@ -8,23 +31,10 @@ interface PluginLogger {
|
|
|
8
31
|
error: (...args: unknown[]) => void;
|
|
9
32
|
debug: (...args: unknown[]) => void;
|
|
10
33
|
}
|
|
11
|
-
interface ToolDef {
|
|
12
|
-
name: string;
|
|
13
|
-
description: string;
|
|
14
|
-
label: string;
|
|
15
|
-
parameters: TSchema;
|
|
16
|
-
execute: (toolCallId: string, params: Record<string, unknown>) => Promise<{
|
|
17
|
-
content: {
|
|
18
|
-
type: "text";
|
|
19
|
-
text: string;
|
|
20
|
-
}[];
|
|
21
|
-
details: unknown;
|
|
22
|
-
}>;
|
|
23
|
-
}
|
|
24
34
|
interface PluginApi {
|
|
25
35
|
logger: PluginLogger;
|
|
26
36
|
registrationMode?: "full" | "setup-only" | "setup-runtime" | "cli-metadata";
|
|
27
|
-
registerTool: (tool: ToolDef) => void;
|
|
37
|
+
registerTool: (tool: ToolDef<TSchema>) => void;
|
|
28
38
|
on: (event: string, handler: (...args: unknown[]) => Promise<unknown>, options?: {
|
|
29
39
|
priority?: number;
|
|
30
40
|
}) => void;
|
|
@@ -38,4 +48,4 @@ declare const plugin: {
|
|
|
38
48
|
deactivate(api: PluginApi): void;
|
|
39
49
|
};
|
|
40
50
|
//#endregion
|
|
41
|
-
export { plugin as
|
|
51
|
+
export { plugin as t };
|