lua-cli 3.0.0-alpha.1 → 3.0.0-alpha.5
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/api/job.api.service.d.ts +16 -7
- package/dist/api/job.api.service.js +21 -5
- package/dist/api/postprocessor.api.service.d.ts +61 -1
- package/dist/api/postprocessor.api.service.js +35 -0
- package/dist/api/preprocessor.api.service.d.ts +61 -1
- package/dist/api/preprocessor.api.service.js +35 -0
- package/dist/api-exports.d.ts +26 -6
- package/dist/api-exports.js +42 -29
- package/dist/cli/command-definitions.js +13 -6
- package/dist/commands/chat.js +32 -5
- package/dist/commands/compile.js +16 -2
- package/dist/commands/dev.js +23 -2
- package/dist/commands/push.d.ts +6 -2
- package/dist/commands/push.js +412 -6
- package/dist/commands/test.js +18 -2
- package/dist/common/job.instance.d.ts +3 -0
- package/dist/common/job.instance.js +8 -0
- package/dist/config/constants.d.ts +6 -5
- package/dist/config/constants.js +12 -10
- package/dist/interfaces/chat.d.ts +30 -1
- package/dist/interfaces/jobs.d.ts +21 -0
- package/dist/types/skill.d.ts +75 -56
- package/dist/types/skill.js +53 -59
- package/dist/utils/bundling.d.ts +13 -4
- package/dist/utils/bundling.js +83 -26
- package/dist/utils/compile.js +27 -6
- package/dist/utils/dev-api.d.ts +42 -2
- package/dist/utils/dev-api.js +177 -4
- package/dist/utils/dev-server.d.ts +1 -1
- package/dist/utils/dev-server.js +4 -4
- package/dist/utils/dynamic-job-bundler.d.ts +17 -0
- package/dist/utils/dynamic-job-bundler.js +143 -0
- package/dist/utils/pre-bundle-jobs.d.ts +26 -0
- package/dist/utils/pre-bundle-jobs.js +176 -0
- package/dist/utils/sandbox-storage.d.ts +48 -0
- package/dist/utils/sandbox-storage.js +114 -0
- package/dist/utils/sandbox.d.ts +2 -2
- package/dist/utils/sandbox.js +23 -7
- package/package.json +1 -1
- package/template/lua.skill.yaml +47 -0
- package/template/package-lock.json +10505 -0
- package/template/package.json +2 -1
- package/template/src/index.ts +65 -3
- package/template/src/tools/CreateInlineJob.ts +42 -0
- package/API_REFERENCE.md +0 -1408
- package/CHANGELOG.md +0 -236
- package/CLI_REFERENCE.md +0 -908
- package/GETTING_STARTED.md +0 -1040
- package/INSTANCE_TYPES.md +0 -1158
- package/README.md +0 -865
- package/TEMPLATE_GUIDE.md +0 -1398
- package/USER_DATA_INSTANCE.md +0 -621
- package/template/AGENT_CONFIGURATION.md +0 -251
- package/template/COMPLEX_JOB_EXAMPLES.md +0 -795
- package/template/DYNAMIC_JOB_CREATION.md +0 -371
- package/template/TOOL_EXAMPLES.md +0 -655
- package/template/WEBHOOKS_JOBS_QUICKSTART.md +0 -318
- package/template/WEBHOOK_JOB_EXAMPLES.md +0 -817
- package/template/src/index-agent-example.ts +0 -201
- package/template/src/postprocessors/ResponseFormatter.ts +0 -151
- package/template/src/preprocessors/MessageFilter.ts +0 -91
package/USER_DATA_INSTANCE.md
DELETED
|
@@ -1,621 +0,0 @@
|
|
|
1
|
-
# UserDataInstance API Reference
|
|
2
|
-
|
|
3
|
-
## Overview
|
|
4
|
-
|
|
5
|
-
`UserDataInstance` is a powerful, proxy-enhanced class that provides a fluent API for managing user-specific data in Lua AI tools. It automatically handles data sanitization, provides intuitive property access, and includes methods for updating and clearing user data.
|
|
6
|
-
|
|
7
|
-
## Table of Contents
|
|
8
|
-
|
|
9
|
-
- [Features](#features)
|
|
10
|
-
- [Installation](#installation)
|
|
11
|
-
- [Quick Start](#quick-start)
|
|
12
|
-
- [API Reference](#api-reference)
|
|
13
|
-
- [Property Access](#property-access)
|
|
14
|
-
- [Methods](#methods)
|
|
15
|
-
- [Examples](#examples)
|
|
16
|
-
- [Best Practices](#best-practices)
|
|
17
|
-
- [TypeScript Support](#typescript-support)
|
|
18
|
-
|
|
19
|
-
## Features
|
|
20
|
-
|
|
21
|
-
✨ **Direct Property Access** - Access data with `user.name` instead of `user.data.name`
|
|
22
|
-
🔒 **Automatic Sanitization** - Removes sensitive fields (agentId, userId) automatically
|
|
23
|
-
🔄 **Async Updates** - Built-in methods for updating and clearing user data
|
|
24
|
-
📝 **Console-Friendly** - Clean output when logging with `console.log()`
|
|
25
|
-
🎯 **Type-Safe** - Full TypeScript support with proper type definitions
|
|
26
|
-
⚡ **Proxy-Powered** - Seamless property access via JavaScript Proxy
|
|
27
|
-
🔙 **Backward Compatible** - Works with both new and old access patterns
|
|
28
|
-
|
|
29
|
-
## Installation
|
|
30
|
-
|
|
31
|
-
```bash
|
|
32
|
-
npm install lua-cli
|
|
33
|
-
```
|
|
34
|
-
|
|
35
|
-
## Quick Start
|
|
36
|
-
|
|
37
|
-
```typescript
|
|
38
|
-
import { UserDataTool } from 'lua-cli';
|
|
39
|
-
|
|
40
|
-
// In your LuaSkill tool
|
|
41
|
-
class MyTool extends LuaTool {
|
|
42
|
-
async execute(input: any, context: ToolContext) {
|
|
43
|
-
// Access user data through context
|
|
44
|
-
const user = context.user;
|
|
45
|
-
|
|
46
|
-
// Direct property access (NEW! ✨)
|
|
47
|
-
console.log(user.name);
|
|
48
|
-
console.log(user.email);
|
|
49
|
-
console.log(user.preferences);
|
|
50
|
-
|
|
51
|
-
// Set properties directly
|
|
52
|
-
user.favoriteColor = "blue";
|
|
53
|
-
|
|
54
|
-
// Update on server
|
|
55
|
-
await user.update({ favoriteColor: "blue" });
|
|
56
|
-
|
|
57
|
-
return { success: true };
|
|
58
|
-
}
|
|
59
|
-
}
|
|
60
|
-
```
|
|
61
|
-
|
|
62
|
-
## API Reference
|
|
63
|
-
|
|
64
|
-
### Constructor
|
|
65
|
-
|
|
66
|
-
```typescript
|
|
67
|
-
constructor(api: UserDataAPI, data: UserData)
|
|
68
|
-
```
|
|
69
|
-
|
|
70
|
-
**Parameters:**
|
|
71
|
-
- `api` - The UserDataAPI instance for making API calls
|
|
72
|
-
- `data` - The user data from the API (will be sanitized automatically)
|
|
73
|
-
|
|
74
|
-
**Returns:** A proxied instance that allows direct access to data properties
|
|
75
|
-
|
|
76
|
-
**Note:** You typically don't need to instantiate this directly. It's provided through the `context.user` object in your tools.
|
|
77
|
-
|
|
78
|
-
## Property Access
|
|
79
|
-
|
|
80
|
-
### Direct Access (Recommended ✨)
|
|
81
|
-
|
|
82
|
-
```typescript
|
|
83
|
-
// Reading properties
|
|
84
|
-
const name = user.name;
|
|
85
|
-
const email = user.email;
|
|
86
|
-
const settings = user.settings;
|
|
87
|
-
|
|
88
|
-
// Setting properties (updates local instance only)
|
|
89
|
-
user.name = "John Doe";
|
|
90
|
-
user.email = "john@example.com";
|
|
91
|
-
user.settings = { theme: "dark" };
|
|
92
|
-
|
|
93
|
-
// Checking if property exists
|
|
94
|
-
if ('name' in user) {
|
|
95
|
-
console.log('User has a name');
|
|
96
|
-
}
|
|
97
|
-
```
|
|
98
|
-
|
|
99
|
-
### Traditional Access (Still Supported)
|
|
100
|
-
|
|
101
|
-
```typescript
|
|
102
|
-
// Reading through .data property
|
|
103
|
-
const name = user.data.name;
|
|
104
|
-
const email = user.data.email;
|
|
105
|
-
|
|
106
|
-
// Setting through .data property
|
|
107
|
-
user.data.name = "John Doe";
|
|
108
|
-
```
|
|
109
|
-
|
|
110
|
-
### Property Enumeration
|
|
111
|
-
|
|
112
|
-
```typescript
|
|
113
|
-
// Get all user data keys
|
|
114
|
-
const keys = Object.keys(user); // Returns all data keys + methods
|
|
115
|
-
|
|
116
|
-
// Iterate over properties
|
|
117
|
-
for (const key in user) {
|
|
118
|
-
console.log(`${key}: ${user[key]}`);
|
|
119
|
-
}
|
|
120
|
-
```
|
|
121
|
-
|
|
122
|
-
## Methods
|
|
123
|
-
|
|
124
|
-
### `update(data: Record<string, any>): Promise<any>`
|
|
125
|
-
|
|
126
|
-
Updates the user's data on the server and locally.
|
|
127
|
-
|
|
128
|
-
**Parameters:**
|
|
129
|
-
- `data` - Object containing the fields to update or add
|
|
130
|
-
|
|
131
|
-
**Returns:** Promise resolving to the updated sanitized user data
|
|
132
|
-
|
|
133
|
-
**Throws:** Error if the update fails
|
|
134
|
-
|
|
135
|
-
**Example:**
|
|
136
|
-
```typescript
|
|
137
|
-
// Update single field
|
|
138
|
-
await user.update({ name: "John Doe" });
|
|
139
|
-
|
|
140
|
-
// Update multiple fields
|
|
141
|
-
await user.update({
|
|
142
|
-
name: "John Doe",
|
|
143
|
-
email: "john@example.com",
|
|
144
|
-
preferences: {
|
|
145
|
-
theme: "dark",
|
|
146
|
-
notifications: true
|
|
147
|
-
}
|
|
148
|
-
});
|
|
149
|
-
|
|
150
|
-
// Access updated data
|
|
151
|
-
console.log(user.name); // "John Doe"
|
|
152
|
-
console.log(user.preferences.theme); // "dark"
|
|
153
|
-
```
|
|
154
|
-
|
|
155
|
-
### `clear(): Promise<boolean>`
|
|
156
|
-
|
|
157
|
-
Clears all user data for the current user on the server.
|
|
158
|
-
|
|
159
|
-
**Returns:** Promise resolving to `true` if clearing was successful
|
|
160
|
-
|
|
161
|
-
**Throws:** Error if the clear operation fails
|
|
162
|
-
|
|
163
|
-
**Example:**
|
|
164
|
-
```typescript
|
|
165
|
-
try {
|
|
166
|
-
const success = await user.clear();
|
|
167
|
-
if (success) {
|
|
168
|
-
console.log('User data cleared successfully');
|
|
169
|
-
}
|
|
170
|
-
} catch (error) {
|
|
171
|
-
console.error('Failed to clear user data');
|
|
172
|
-
}
|
|
173
|
-
```
|
|
174
|
-
|
|
175
|
-
### `toJSON(): Record<string, any>`
|
|
176
|
-
|
|
177
|
-
Custom serialization method used when converting to JSON or logging.
|
|
178
|
-
|
|
179
|
-
**Returns:** The sanitized user data object
|
|
180
|
-
|
|
181
|
-
**Example:**
|
|
182
|
-
```typescript
|
|
183
|
-
// Automatic usage in JSON.stringify
|
|
184
|
-
const json = JSON.stringify(user);
|
|
185
|
-
|
|
186
|
-
// Explicit usage
|
|
187
|
-
const dataObject = user.toJSON();
|
|
188
|
-
```
|
|
189
|
-
|
|
190
|
-
## Data Sanitization
|
|
191
|
-
|
|
192
|
-
The `UserDataInstance` automatically removes sensitive fields before storing data locally:
|
|
193
|
-
|
|
194
|
-
**Removed Fields:**
|
|
195
|
-
- `agentId`
|
|
196
|
-
- `userId`
|
|
197
|
-
|
|
198
|
-
**Accessible Fields:** All other fields including:
|
|
199
|
-
- `name`, `email`, `phone`
|
|
200
|
-
- Custom data fields
|
|
201
|
-
- API keys and tokens (if stored in user data)
|
|
202
|
-
- Preferences and settings
|
|
203
|
-
|
|
204
|
-
```typescript
|
|
205
|
-
// Server returns:
|
|
206
|
-
{
|
|
207
|
-
userId: "12345", // ❌ Removed
|
|
208
|
-
agentId: "agent-123", // ❌ Removed
|
|
209
|
-
name: "John Doe", // ✅ Accessible
|
|
210
|
-
email: "john@example.com", // ✅ Accessible
|
|
211
|
-
customKey: "value" // ✅ Accessible
|
|
212
|
-
}
|
|
213
|
-
|
|
214
|
-
// Local user instance has:
|
|
215
|
-
{
|
|
216
|
-
name: "John Doe",
|
|
217
|
-
email: "john@example.com",
|
|
218
|
-
customKey: "value"
|
|
219
|
-
}
|
|
220
|
-
```
|
|
221
|
-
|
|
222
|
-
## Examples
|
|
223
|
-
|
|
224
|
-
### Example 1: Storing User Preferences
|
|
225
|
-
|
|
226
|
-
```typescript
|
|
227
|
-
class PreferencesTool extends LuaTool {
|
|
228
|
-
schema = {
|
|
229
|
-
input: z.object({
|
|
230
|
-
theme: z.enum(['light', 'dark']).optional(),
|
|
231
|
-
language: z.string().optional(),
|
|
232
|
-
notifications: z.boolean().optional()
|
|
233
|
-
}),
|
|
234
|
-
output: z.object({
|
|
235
|
-
message: z.string(),
|
|
236
|
-
preferences: z.any()
|
|
237
|
-
})
|
|
238
|
-
};
|
|
239
|
-
|
|
240
|
-
async execute(input: any, context: ToolContext) {
|
|
241
|
-
const user = context.user;
|
|
242
|
-
|
|
243
|
-
// Get current preferences or initialize
|
|
244
|
-
const currentPrefs = user.preferences || {};
|
|
245
|
-
|
|
246
|
-
// Update with new values
|
|
247
|
-
const newPrefs = {
|
|
248
|
-
...currentPrefs,
|
|
249
|
-
...input
|
|
250
|
-
};
|
|
251
|
-
|
|
252
|
-
// Save to server
|
|
253
|
-
await user.update({ preferences: newPrefs });
|
|
254
|
-
|
|
255
|
-
return {
|
|
256
|
-
message: 'Preferences updated successfully',
|
|
257
|
-
preferences: user.preferences
|
|
258
|
-
};
|
|
259
|
-
}
|
|
260
|
-
}
|
|
261
|
-
```
|
|
262
|
-
|
|
263
|
-
### Example 2: User Profile Management
|
|
264
|
-
|
|
265
|
-
```typescript
|
|
266
|
-
class ProfileTool extends LuaTool {
|
|
267
|
-
schema = {
|
|
268
|
-
input: z.object({
|
|
269
|
-
action: z.enum(['get', 'update', 'clear']),
|
|
270
|
-
profile: z.object({
|
|
271
|
-
firstName: z.string().optional(),
|
|
272
|
-
lastName: z.string().optional(),
|
|
273
|
-
bio: z.string().optional(),
|
|
274
|
-
avatar: z.string().url().optional()
|
|
275
|
-
}).optional()
|
|
276
|
-
}),
|
|
277
|
-
output: z.object({
|
|
278
|
-
success: z.boolean(),
|
|
279
|
-
profile: z.any().optional(),
|
|
280
|
-
message: z.string()
|
|
281
|
-
})
|
|
282
|
-
};
|
|
283
|
-
|
|
284
|
-
async execute(input: any, context: ToolContext) {
|
|
285
|
-
const user = context.user;
|
|
286
|
-
|
|
287
|
-
switch (input.action) {
|
|
288
|
-
case 'get':
|
|
289
|
-
return {
|
|
290
|
-
success: true,
|
|
291
|
-
profile: {
|
|
292
|
-
firstName: user.firstName,
|
|
293
|
-
lastName: user.lastName,
|
|
294
|
-
bio: user.bio,
|
|
295
|
-
avatar: user.avatar
|
|
296
|
-
},
|
|
297
|
-
message: 'Profile retrieved'
|
|
298
|
-
};
|
|
299
|
-
|
|
300
|
-
case 'update':
|
|
301
|
-
await user.update(input.profile);
|
|
302
|
-
return {
|
|
303
|
-
success: true,
|
|
304
|
-
profile: input.profile,
|
|
305
|
-
message: 'Profile updated successfully'
|
|
306
|
-
};
|
|
307
|
-
|
|
308
|
-
case 'clear':
|
|
309
|
-
await user.clear();
|
|
310
|
-
return {
|
|
311
|
-
success: true,
|
|
312
|
-
message: 'Profile cleared successfully'
|
|
313
|
-
};
|
|
314
|
-
|
|
315
|
-
default:
|
|
316
|
-
throw new Error('Invalid action');
|
|
317
|
-
}
|
|
318
|
-
}
|
|
319
|
-
}
|
|
320
|
-
```
|
|
321
|
-
|
|
322
|
-
### Example 3: Shopping Cart Persistence
|
|
323
|
-
|
|
324
|
-
```typescript
|
|
325
|
-
class CartTool extends LuaTool {
|
|
326
|
-
schema = {
|
|
327
|
-
input: z.object({
|
|
328
|
-
action: z.enum(['add', 'remove', 'get', 'clear']),
|
|
329
|
-
productId: z.string().optional(),
|
|
330
|
-
quantity: z.number().optional()
|
|
331
|
-
}),
|
|
332
|
-
output: z.object({
|
|
333
|
-
cart: z.array(z.any()),
|
|
334
|
-
total: z.number()
|
|
335
|
-
})
|
|
336
|
-
};
|
|
337
|
-
|
|
338
|
-
async execute(input: any, context: ToolContext) {
|
|
339
|
-
const user = context.user;
|
|
340
|
-
|
|
341
|
-
// Get current cart (direct access!)
|
|
342
|
-
let cart = user.cart || [];
|
|
343
|
-
|
|
344
|
-
switch (input.action) {
|
|
345
|
-
case 'add':
|
|
346
|
-
const existing = cart.find((item: any) =>
|
|
347
|
-
item.productId === input.productId
|
|
348
|
-
);
|
|
349
|
-
|
|
350
|
-
if (existing) {
|
|
351
|
-
existing.quantity += input.quantity;
|
|
352
|
-
} else {
|
|
353
|
-
cart.push({
|
|
354
|
-
productId: input.productId,
|
|
355
|
-
quantity: input.quantity
|
|
356
|
-
});
|
|
357
|
-
}
|
|
358
|
-
|
|
359
|
-
await user.update({ cart });
|
|
360
|
-
break;
|
|
361
|
-
|
|
362
|
-
case 'remove':
|
|
363
|
-
cart = cart.filter((item: any) =>
|
|
364
|
-
item.productId !== input.productId
|
|
365
|
-
);
|
|
366
|
-
await user.update({ cart });
|
|
367
|
-
break;
|
|
368
|
-
|
|
369
|
-
case 'clear':
|
|
370
|
-
await user.update({ cart: [] });
|
|
371
|
-
cart = [];
|
|
372
|
-
break;
|
|
373
|
-
|
|
374
|
-
case 'get':
|
|
375
|
-
// Just return current cart
|
|
376
|
-
break;
|
|
377
|
-
}
|
|
378
|
-
|
|
379
|
-
const total = cart.reduce((sum: number, item: any) =>
|
|
380
|
-
sum + (item.quantity || 0), 0
|
|
381
|
-
);
|
|
382
|
-
|
|
383
|
-
return { cart, total };
|
|
384
|
-
}
|
|
385
|
-
}
|
|
386
|
-
```
|
|
387
|
-
|
|
388
|
-
### Example 4: Session State Management
|
|
389
|
-
|
|
390
|
-
```typescript
|
|
391
|
-
class SessionTool extends LuaTool {
|
|
392
|
-
async execute(input: any, context: ToolContext) {
|
|
393
|
-
const user = context.user;
|
|
394
|
-
|
|
395
|
-
// Track page visits
|
|
396
|
-
const visits = user.pageVisits || 0;
|
|
397
|
-
await user.update({ pageVisits: visits + 1 });
|
|
398
|
-
|
|
399
|
-
// Track last seen timestamp
|
|
400
|
-
await user.update({
|
|
401
|
-
lastSeen: new Date().toISOString(),
|
|
402
|
-
sessionCount: (user.sessionCount || 0) + 1
|
|
403
|
-
});
|
|
404
|
-
|
|
405
|
-
// Check if returning user
|
|
406
|
-
const isReturning = visits > 0;
|
|
407
|
-
|
|
408
|
-
return {
|
|
409
|
-
isReturning,
|
|
410
|
-
visits: user.pageVisits,
|
|
411
|
-
sessionCount: user.sessionCount,
|
|
412
|
-
lastSeen: user.lastSeen
|
|
413
|
-
};
|
|
414
|
-
}
|
|
415
|
-
}
|
|
416
|
-
```
|
|
417
|
-
|
|
418
|
-
### Example 5: Multi-Step Form Data
|
|
419
|
-
|
|
420
|
-
```typescript
|
|
421
|
-
class FormStateTool extends LuaTool {
|
|
422
|
-
async execute(input: any, context: ToolContext) {
|
|
423
|
-
const user = context.user;
|
|
424
|
-
|
|
425
|
-
// Get or initialize form state
|
|
426
|
-
const formData = user.multiStepForm || {
|
|
427
|
-
step: 1,
|
|
428
|
-
completed: {},
|
|
429
|
-
currentData: {}
|
|
430
|
-
};
|
|
431
|
-
|
|
432
|
-
// Update current step data
|
|
433
|
-
formData.completed[input.step] = true;
|
|
434
|
-
formData.currentData = {
|
|
435
|
-
...formData.currentData,
|
|
436
|
-
...input.data
|
|
437
|
-
};
|
|
438
|
-
|
|
439
|
-
// Move to next step
|
|
440
|
-
formData.step = input.step + 1;
|
|
441
|
-
|
|
442
|
-
// Save state
|
|
443
|
-
await user.update({ multiStepForm: formData });
|
|
444
|
-
|
|
445
|
-
return {
|
|
446
|
-
currentStep: formData.step,
|
|
447
|
-
completedSteps: Object.keys(formData.completed),
|
|
448
|
-
isComplete: formData.step > 5
|
|
449
|
-
};
|
|
450
|
-
}
|
|
451
|
-
}
|
|
452
|
-
```
|
|
453
|
-
|
|
454
|
-
## Best Practices
|
|
455
|
-
|
|
456
|
-
### ✅ DO
|
|
457
|
-
|
|
458
|
-
```typescript
|
|
459
|
-
// Use direct property access for cleaner code
|
|
460
|
-
const name = user.name;
|
|
461
|
-
|
|
462
|
-
// Update multiple fields at once
|
|
463
|
-
await user.update({
|
|
464
|
-
field1: value1,
|
|
465
|
-
field2: value2
|
|
466
|
-
});
|
|
467
|
-
|
|
468
|
-
// Check for property existence before accessing
|
|
469
|
-
if ('preferences' in user) {
|
|
470
|
-
console.log(user.preferences);
|
|
471
|
-
}
|
|
472
|
-
|
|
473
|
-
// Initialize nested objects carefully
|
|
474
|
-
const prefs = user.preferences || {};
|
|
475
|
-
```
|
|
476
|
-
|
|
477
|
-
### ❌ DON'T
|
|
478
|
-
|
|
479
|
-
```typescript
|
|
480
|
-
// Don't mutate and forget to call update()
|
|
481
|
-
user.name = "John";
|
|
482
|
-
// ❌ This only updates locally! Must call user.update()
|
|
483
|
-
|
|
484
|
-
// Don't assume sensitive fields are available
|
|
485
|
-
console.log(user.userId); // undefined (sanitized)
|
|
486
|
-
console.log(user.agentId); // undefined (sanitized)
|
|
487
|
-
|
|
488
|
-
// Don't make unnecessary update calls
|
|
489
|
-
await user.update({ field1: value1 });
|
|
490
|
-
await user.update({ field2: value2 }); // Combine these!
|
|
491
|
-
```
|
|
492
|
-
|
|
493
|
-
## TypeScript Support
|
|
494
|
-
|
|
495
|
-
### Type Definitions
|
|
496
|
-
|
|
497
|
-
```typescript
|
|
498
|
-
interface UserDataInstance {
|
|
499
|
-
data: Record<string, any>;
|
|
500
|
-
|
|
501
|
-
// Methods
|
|
502
|
-
update(data: Record<string, any>): Promise<any>;
|
|
503
|
-
clear(): Promise<boolean>;
|
|
504
|
-
toJSON(): Record<string, any>;
|
|
505
|
-
|
|
506
|
-
// Index signature for dynamic property access
|
|
507
|
-
[key: string]: any;
|
|
508
|
-
}
|
|
509
|
-
```
|
|
510
|
-
|
|
511
|
-
### Usage with Types
|
|
512
|
-
|
|
513
|
-
```typescript
|
|
514
|
-
// Define your user data shape
|
|
515
|
-
interface MyUserData {
|
|
516
|
-
name: string;
|
|
517
|
-
email: string;
|
|
518
|
-
preferences: {
|
|
519
|
-
theme: 'light' | 'dark';
|
|
520
|
-
notifications: boolean;
|
|
521
|
-
};
|
|
522
|
-
}
|
|
523
|
-
|
|
524
|
-
// Access with type checking
|
|
525
|
-
const user = context.user;
|
|
526
|
-
const name: string = user.name;
|
|
527
|
-
const prefs: MyUserData['preferences'] = user.preferences;
|
|
528
|
-
```
|
|
529
|
-
|
|
530
|
-
## Console Output
|
|
531
|
-
|
|
532
|
-
The `UserDataInstance` includes custom serialization for clean console output:
|
|
533
|
-
|
|
534
|
-
```typescript
|
|
535
|
-
console.log(user);
|
|
536
|
-
// Output:
|
|
537
|
-
// {
|
|
538
|
-
// name: "John Doe",
|
|
539
|
-
// email: "john@example.com",
|
|
540
|
-
// preferences: { theme: "dark" }
|
|
541
|
-
// }
|
|
542
|
-
|
|
543
|
-
// Methods and internal properties are hidden
|
|
544
|
-
// Only the actual user data is displayed
|
|
545
|
-
```
|
|
546
|
-
|
|
547
|
-
## Reserved Properties
|
|
548
|
-
|
|
549
|
-
The following properties are reserved and cannot be overwritten via proxy:
|
|
550
|
-
|
|
551
|
-
- `data` - The internal data storage
|
|
552
|
-
- `userAPI` - The API client (non-enumerable)
|
|
553
|
-
- `update` - The update method
|
|
554
|
-
- `clear` - The clear method
|
|
555
|
-
- `toJSON` - The serialization method
|
|
556
|
-
|
|
557
|
-
Attempting to set these will maintain the original instance behavior.
|
|
558
|
-
|
|
559
|
-
## Performance Considerations
|
|
560
|
-
|
|
561
|
-
- **Proxy Overhead**: Minimal performance impact for property access
|
|
562
|
-
- **Update Batching**: Combine multiple field updates into a single `update()` call
|
|
563
|
-
- **Local Changes**: Setting properties directly only updates the local instance
|
|
564
|
-
- **Server Sync**: Always call `update()` to persist changes to the server
|
|
565
|
-
|
|
566
|
-
## Backward Compatibility
|
|
567
|
-
|
|
568
|
-
The new direct property access pattern is fully backward compatible:
|
|
569
|
-
|
|
570
|
-
```typescript
|
|
571
|
-
// Old pattern (still works)
|
|
572
|
-
user.data.name = "John";
|
|
573
|
-
await user.update({ name: user.data.name });
|
|
574
|
-
|
|
575
|
-
// New pattern (recommended)
|
|
576
|
-
user.name = "John";
|
|
577
|
-
await user.update({ name: user.name });
|
|
578
|
-
|
|
579
|
-
// Mixed usage (also works)
|
|
580
|
-
console.log(user.name); // Direct access
|
|
581
|
-
console.log(user.data.email); // Traditional access
|
|
582
|
-
```
|
|
583
|
-
|
|
584
|
-
## Error Handling
|
|
585
|
-
|
|
586
|
-
```typescript
|
|
587
|
-
try {
|
|
588
|
-
await user.update({
|
|
589
|
-
name: "John Doe",
|
|
590
|
-
email: "john@example.com"
|
|
591
|
-
});
|
|
592
|
-
} catch (error) {
|
|
593
|
-
console.error('Failed to update user data:', error);
|
|
594
|
-
// Handle error appropriately
|
|
595
|
-
}
|
|
596
|
-
|
|
597
|
-
try {
|
|
598
|
-
await user.clear();
|
|
599
|
-
} catch (error) {
|
|
600
|
-
console.error('Failed to clear user data:', error);
|
|
601
|
-
}
|
|
602
|
-
```
|
|
603
|
-
|
|
604
|
-
## Related Resources
|
|
605
|
-
|
|
606
|
-
- [LuaTool Documentation](./TEMPLATE_GUIDE.md)
|
|
607
|
-
- [API Reference](./API_REFERENCE.md)
|
|
608
|
-
- [Getting Started](./GETTING_STARTED.md)
|
|
609
|
-
- [UserDataTool Example](./template/src/tools/UserDataTool.ts)
|
|
610
|
-
|
|
611
|
-
## Support
|
|
612
|
-
|
|
613
|
-
For issues, questions, or contributions:
|
|
614
|
-
- GitHub: [lua-ai-global/lua-cli](https://github.com/lua-ai-global/lua-cli)
|
|
615
|
-
- Email: stefan@heylua.ai
|
|
616
|
-
|
|
617
|
-
---
|
|
618
|
-
|
|
619
|
-
**Version:** 2.5.0
|
|
620
|
-
**Last Updated:** October 7, 2025
|
|
621
|
-
**License:** MIT
|