@alveus-ai/std 0.1.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.
@@ -0,0 +1,183 @@
1
+ /**
2
+ * Approval Pattern - Human-in-the-Loop Workflows
3
+ *
4
+ * Provides utilities for implementing approval workflows where
5
+ * agents can pause and wait for human decisions.
6
+ *
7
+ * Uses the Event capability for durable waiting:
8
+ * 1. Emit an "approval-needed" event with request details
9
+ * 2. Wait for an "approval-response" event
10
+ * 3. Continue based on the approval decision
11
+ *
12
+ * @example
13
+ * ```ts
14
+ * import { waitForApproval, type ApprovalRequest } from '@alveus-ai/std/patterns';
15
+ *
16
+ * const myAgent = agent$(async (state, event, ctx) => {
17
+ * // Do some work...
18
+ * const result = await performRiskyOperation();
19
+ *
20
+ * // Request human approval before continuing
21
+ * const approval = await waitForApproval(ctx, {
22
+ * action: 'deploy-to-production',
23
+ * details: { version: '1.2.3', environment: 'prod' },
24
+ * message: 'Please approve deployment to production',
25
+ * });
26
+ *
27
+ * if (!approval.approved) {
28
+ * return { status: 'rejected', reason: approval.reason };
29
+ * }
30
+ *
31
+ * // Continue with deployment...
32
+ * return { status: 'deployed', approvedBy: approval.approvedBy };
33
+ * });
34
+ * ```
35
+ */
36
+ /**
37
+ * Topics used for approval events
38
+ */
39
+ export const ApprovalTopics = {
40
+ /** Topic for approval requests */
41
+ NEEDED: 'approval.needed',
42
+ /** Topic for approval responses */
43
+ RESPONSE: 'approval.response',
44
+ };
45
+ /**
46
+ * Wait for human approval
47
+ *
48
+ * Emits an approval request event and durably waits for a response.
49
+ * The workflow will pause until an approval response is received.
50
+ *
51
+ * @param ctx - The execution context
52
+ * @param request - The approval request details
53
+ * @returns The approval response
54
+ * @throws Error if timeout is reached
55
+ */
56
+ export async function waitForApproval(ctx, request) {
57
+ const timeoutMs = request.timeoutMs ?? 24 * 60 * 60 * 1000; // 24 hours default
58
+ // Emit the approval request
59
+ await ctx.events.emit(ApprovalTopics.NEEDED, {
60
+ workflowId: ctx.workflowId,
61
+ action: request.action,
62
+ details: request.details,
63
+ message: request.message,
64
+ requestedAt: Date.now(),
65
+ });
66
+ // Wait for the approval response (durable via Temporal Signals)
67
+ const response = await ctx.events.waitFor(`${ApprovalTopics.RESPONSE}:${ctx.workflowId}`, timeoutMs);
68
+ return {
69
+ approved: response.data?.approved === true,
70
+ approvedBy: response.data?.approvedBy,
71
+ reason: response.data?.reason,
72
+ timestamp: response.timestamp,
73
+ };
74
+ }
75
+ /**
76
+ * Send an approval decision
77
+ *
78
+ * Use this from an approval UI or API to respond to an approval request.
79
+ * The response will be delivered to the waiting workflow via the Event Bridge.
80
+ *
81
+ * @param ctx - The execution context
82
+ * @param workflowId - The ID of the workflow waiting for approval
83
+ * @param approved - Whether to approve or reject
84
+ * @param options - Additional response options
85
+ */
86
+ export async function sendApproval(ctx, workflowId, approved, options = {}) {
87
+ await ctx.events.emit(`${ApprovalTopics.RESPONSE}:${workflowId}`, {
88
+ approved,
89
+ approvedBy: options.approvedBy,
90
+ reason: options.reason,
91
+ respondedAt: Date.now(),
92
+ });
93
+ }
94
+ /**
95
+ * Create an approval-gated operation wrapper
96
+ *
97
+ * Wraps an async operation with an approval requirement.
98
+ * The operation will only execute if approval is granted.
99
+ *
100
+ * @param operation - The operation requiring approval
101
+ * @param getRequest - Function to build the approval request from the input
102
+ * @returns A function that requests approval before executing
103
+ *
104
+ * @example
105
+ * ```ts
106
+ * const safeDelete = requireApproval(
107
+ * async (ctx, userId: string) => {
108
+ * await database.deleteUser(userId);
109
+ * return { deleted: userId };
110
+ * },
111
+ * (userId) => ({
112
+ * action: 'delete-user',
113
+ * details: { userId },
114
+ * message: `Delete user ${userId}?`,
115
+ * })
116
+ * );
117
+ *
118
+ * // In agent handler:
119
+ * const result = await safeDelete(ctx, 'user-123');
120
+ * if (!result.approved) {
121
+ * return { error: 'Deletion rejected' };
122
+ * }
123
+ * return result.result;
124
+ * ```
125
+ */
126
+ export function requireApproval(operation, getRequest) {
127
+ return async (ctx, input) => {
128
+ const request = getRequest(input);
129
+ const approval = await waitForApproval(ctx, request);
130
+ if (!approval.approved) {
131
+ return {
132
+ approved: false,
133
+ reason: approval.reason,
134
+ };
135
+ }
136
+ const result = await operation(ctx, input);
137
+ return {
138
+ approved: true,
139
+ result,
140
+ approvedBy: approval.approvedBy,
141
+ };
142
+ };
143
+ }
144
+ /**
145
+ * Multi-step approval chain
146
+ *
147
+ * Requires multiple approvals before proceeding.
148
+ * Useful for critical operations requiring sign-off from multiple parties.
149
+ *
150
+ * @param ctx - The execution context
151
+ * @param request - The base approval request
152
+ * @param approvers - List of required approver identifiers
153
+ * @returns Array of approval responses
154
+ */
155
+ export async function waitForMultipleApprovals(ctx, request, approvers) {
156
+ const responses = [];
157
+ for (const approver of approvers) {
158
+ // Emit request for this specific approver
159
+ await ctx.events.emit(ApprovalTopics.NEEDED, {
160
+ workflowId: ctx.workflowId,
161
+ action: request.action,
162
+ details: request.details,
163
+ message: `${request.message} (Approval ${responses.length + 1}/${approvers.length} from: ${approver})`,
164
+ requiredApprover: approver,
165
+ requestedAt: Date.now(),
166
+ });
167
+ // Wait for this approver's response
168
+ const response = await ctx.events.waitFor(`${ApprovalTopics.RESPONSE}:${ctx.workflowId}:${approver}`, request.timeoutMs);
169
+ const approval = {
170
+ approved: response.data?.approved === true,
171
+ approvedBy: response.data?.approvedBy || approver,
172
+ reason: response.data?.reason,
173
+ timestamp: response.timestamp,
174
+ };
175
+ responses.push(approval);
176
+ // If any approver rejects, return early
177
+ if (!approval.approved) {
178
+ return responses;
179
+ }
180
+ }
181
+ return responses;
182
+ }
183
+ //# sourceMappingURL=approval.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"approval.js","sourceRoot":"","sources":["../../src/patterns/approval.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,7 @@
1
+ /**
2
+ * Standard Patterns
3
+ *
4
+ * Common workflow patterns for agent development.
5
+ */
6
+ export { waitForApproval, sendApproval, requireApproval, waitForMultipleApprovals, ApprovalTopics, type ApprovalRequest, type ApprovalResponse, } from './approval.js';
7
+ //# sourceMappingURL=index.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/patterns/index.ts"],"names":[],"mappings":"AAAA;;;;GAIG;AAEH,OAAO,EACL,eAAe,EACf,YAAY,EACZ,eAAe,EACf,wBAAwB,EACxB,cAAc,EACd,KAAK,eAAe,EACpB,KAAK,gBAAgB,GACtB,MAAM,eAAe,CAAC"}
@@ -0,0 +1,7 @@
1
+ /**
2
+ * Standard Patterns
3
+ *
4
+ * Common workflow patterns for agent development.
5
+ */
6
+ export { waitForApproval, sendApproval, requireApproval, waitForMultipleApprovals, ApprovalTopics, } from './approval.js';
7
+ //# sourceMappingURL=index.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.js","sourceRoot":"","sources":["../../src/patterns/index.ts"],"names":[],"mappings":"AAAA;;;;GAIG;AAEH,OAAO,EACL,eAAe,EACf,YAAY,EACZ,eAAe,EACf,wBAAwB,EACxB,cAAc,GAGf,MAAM,eAAe,CAAC"}
package/package.json ADDED
@@ -0,0 +1,45 @@
1
+ {
2
+ "name": "@alveus-ai/std",
3
+ "version": "0.1.0",
4
+ "description": "Standard library of reusable agents and utilities for Alveus",
5
+ "type": "module",
6
+ "main": "dist/index.js",
7
+ "types": "dist/index.d.ts",
8
+ "exports": {
9
+ ".": {
10
+ "types": "./dist/index.d.ts",
11
+ "import": "./dist/index.js"
12
+ },
13
+ "./agents": {
14
+ "types": "./dist/agents/index.d.ts",
15
+ "import": "./dist/agents/index.js"
16
+ },
17
+ "./memory": {
18
+ "types": "./dist/memory/index.d.ts",
19
+ "import": "./dist/memory/index.js"
20
+ },
21
+ "./patterns": {
22
+ "types": "./dist/patterns/index.d.ts",
23
+ "import": "./dist/patterns/index.js"
24
+ }
25
+ },
26
+ "files": [
27
+ "dist"
28
+ ],
29
+ "scripts": {
30
+ "build": "tsc",
31
+ "dev": "tsc --watch",
32
+ "clean": "rm -rf dist .alveus"
33
+ },
34
+ "publishConfig": {
35
+ "access": "public"
36
+ },
37
+ "dependencies": {},
38
+ "peerDependencies": {
39
+ "@alveus-ai/core": "^0.1.0"
40
+ },
41
+ "devDependencies": {
42
+ "@alveus-ai/core": "workspace:*",
43
+ "typescript": "^5.3.0"
44
+ }
45
+ }