lua-cli 3.0.0-alpha.9 → 3.0.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.
- package/README.md +850 -0
- package/dist/api/chat.api.service.d.ts +8 -0
- package/dist/api/chat.api.service.js +55 -0
- package/dist/api/products.api.service.d.ts +2 -1
- package/dist/api/products.api.service.js +11 -10
- package/dist/api-exports.d.ts +1 -1
- package/dist/api-exports.js +6 -1
- package/dist/commands/chat.js +35 -32
- package/dist/commands/init.js +10 -2
- package/dist/index.js +2 -2
- package/dist/interfaces/message.d.ts +2 -2
- package/dist/utils/agent-management.d.ts +1 -1
- package/dist/utils/agent-management.js +5 -3
- package/dist/utils/init-helpers.d.ts +10 -1
- package/dist/utils/init-helpers.js +44 -1
- package/dist/utils/pre-bundle-jobs.js +9 -9
- package/dist/utils/sandbox.js +1 -2
- package/package.json +3 -3
- package/template/QUICKSTART.md +693 -191
- package/template/README.md +673 -802
- package/template/package.json +1 -1
- package/template/src/index.ts +18 -252
- package/template/src/postprocessors/modifyResponse.ts +21 -0
- package/template/src/preprocessors/messageMatching.ts +22 -0
- package/template/src/skills/basket.skill.ts +12 -0
- package/template/src/skills/product.skill.ts +13 -0
- package/template/src/{tools → skills/tools}/ProductsTool.ts +2 -1
- package/template/src/skills/tools/UserDataTool.ts +75 -0
- package/template/src/skills/user.skill.ts +13 -0
- package/template/src/seed.ts +0 -46
- package/template/src/tools/UserDataTool.ts +0 -33
- /package/template/src/{tools → skills/tools}/BasketTool.ts +0 -0
- /package/template/src/{tools → skills/tools}/CreateInlineJob.ts +0 -0
- /package/template/src/{tools → skills/tools}/CreatePostTool.ts +0 -0
- /package/template/src/{tools → skills/tools}/CustomDataTool.ts +0 -0
- /package/template/src/{tools → skills/tools}/GameScoreTrackerTool.ts +0 -0
- /package/template/src/{tools → skills/tools}/GetWeatherTool.ts +0 -0
- /package/template/src/{tools → skills/tools}/OrderTool.ts +0 -0
- /package/template/src/{tools → skills/tools}/PaymentTool.ts +0 -0
- /package/template/src/{tools → skills/tools}/SmartBasketTool.ts +0 -0
package/template/QUICKSTART.md
CHANGED
|
@@ -1,325 +1,827 @@
|
|
|
1
|
-
# Quick Start
|
|
1
|
+
# 🚀 Quick Start Guide
|
|
2
2
|
|
|
3
|
-
|
|
3
|
+
Welcome to your Lua AI Agent! This template provides a complete example of how to build powerful AI agents with custom tools, webhooks, scheduled jobs, and more.
|
|
4
4
|
|
|
5
|
-
|
|
6
|
-
|
|
7
|
-
## ⚡ Super Quick Start
|
|
5
|
+
## 📋 Table of Contents
|
|
8
6
|
|
|
9
|
-
|
|
10
|
-
|
|
11
|
-
|
|
7
|
+
- [Getting Started](#getting-started)
|
|
8
|
+
- [Essential Commands](#essential-commands)
|
|
9
|
+
- [Understanding LuaAgent](#understanding-luaagent)
|
|
10
|
+
- [Project Structure](#project-structure)
|
|
11
|
+
- [Next Steps](#next-steps)
|
|
12
12
|
|
|
13
|
-
|
|
14
|
-
lua dev
|
|
13
|
+
---
|
|
15
14
|
|
|
16
|
-
|
|
17
|
-
# Try: "What's the weather in London?"
|
|
15
|
+
## 🎯 Getting Started
|
|
18
16
|
|
|
19
|
-
|
|
17
|
+
Your project has been initialized with everything you need to build and deploy an AI agent!
|
|
20
18
|
|
|
21
|
-
|
|
22
|
-
lua push
|
|
23
|
-
lua deploy
|
|
24
|
-
```
|
|
19
|
+
### What's Included
|
|
25
20
|
|
|
26
|
-
**
|
|
21
|
+
✅ **Example Skills** - Pre-built tools for weather, user data, products, baskets, orders
|
|
22
|
+
✅ **Example Webhooks** - HTTP endpoints that receive external events
|
|
23
|
+
✅ **Example Jobs** - Scheduled tasks that run automatically
|
|
24
|
+
✅ **Example Processors** - Pre/post-process chat messages
|
|
25
|
+
✅ **LuaAgent Configuration** - Unified agent setup in `src/index.ts`
|
|
27
26
|
|
|
28
27
|
---
|
|
29
28
|
|
|
30
|
-
##
|
|
29
|
+
## 🛠️ Essential Commands
|
|
30
|
+
|
|
31
|
+
### 1. Test Your Tools & Skills
|
|
32
|
+
|
|
33
|
+
Test individual tools interactively before deploying:
|
|
31
34
|
|
|
32
35
|
```bash
|
|
33
36
|
lua test
|
|
34
37
|
```
|
|
35
38
|
|
|
36
|
-
**
|
|
39
|
+
**What it does:**
|
|
40
|
+
- Lets you select a tool/webhook/job to test
|
|
41
|
+
- Prompts for input values
|
|
42
|
+
- Executes in a local sandbox
|
|
43
|
+
- Shows the output
|
|
44
|
+
|
|
45
|
+
**Perfect for:**
|
|
46
|
+
- Testing tool logic before deployment
|
|
47
|
+
- Debugging input/output schemas
|
|
48
|
+
- Validating webhook handlers
|
|
49
|
+
|
|
50
|
+
---
|
|
51
|
+
|
|
52
|
+
### 2. Chat with Your Agent
|
|
53
|
+
|
|
54
|
+
Have a conversation with your agent to see tools in action:
|
|
37
55
|
|
|
38
|
-
|
|
39
|
-
|
|
40
|
-
|
|
56
|
+
```bash
|
|
57
|
+
lua chat
|
|
58
|
+
```
|
|
41
59
|
|
|
42
|
-
|
|
43
|
-
|
|
44
|
-
|
|
60
|
+
**Select environment:**
|
|
61
|
+
- **🔧 Sandbox** - Test with your local code (not deployed yet)
|
|
62
|
+
- **🚀 Production** - Chat with your deployed agent
|
|
45
63
|
|
|
46
|
-
|
|
47
|
-
|
|
48
|
-
|
|
64
|
+
**Try asking:**
|
|
65
|
+
- "What's the weather in London?"
|
|
66
|
+
- "Show me all products"
|
|
67
|
+
- "Create a basket for user 123"
|
|
49
68
|
|
|
50
|
-
**
|
|
69
|
+
**Pro tip:** Use sandbox mode to test changes before deploying!
|
|
51
70
|
|
|
52
71
|
---
|
|
53
72
|
|
|
54
|
-
|
|
73
|
+
### 3. Deploy to Production
|
|
74
|
+
|
|
75
|
+
When ready, push your skills to the server:
|
|
55
76
|
|
|
56
77
|
```bash
|
|
57
|
-
|
|
58
|
-
|
|
78
|
+
# Interactive deployment (recommended for first time)
|
|
79
|
+
lua push
|
|
59
80
|
|
|
60
|
-
|
|
81
|
+
# Or push all components at once
|
|
82
|
+
lua push all --force
|
|
61
83
|
|
|
62
|
-
|
|
63
|
-
|
|
64
|
-
|
|
65
|
-
- "Create a movie called Inception directed by Christopher Nolan in 2010"
|
|
66
|
-
- "Search for movies about dreams"
|
|
67
|
-
- "Create a shopping basket and add a laptop"
|
|
84
|
+
# Push and deploy to production in one command
|
|
85
|
+
lua push all --force --auto-deploy
|
|
86
|
+
```
|
|
68
87
|
|
|
69
|
-
**What
|
|
88
|
+
**What happens:**
|
|
89
|
+
1. Compiles your code
|
|
90
|
+
2. Bundles all tools/webhooks/jobs
|
|
91
|
+
3. Pushes new version to server
|
|
92
|
+
4. Updates `lua.skill.yaml` with new version
|
|
93
|
+
5. Optionally deploys to production
|
|
70
94
|
|
|
71
95
|
---
|
|
72
96
|
|
|
73
|
-
##
|
|
97
|
+
## 🤖 Understanding LuaAgent
|
|
74
98
|
|
|
75
|
-
|
|
99
|
+
The `LuaAgent` is the **central configuration** for your AI agent. It's defined in `src/index.ts`:
|
|
76
100
|
|
|
77
101
|
```typescript
|
|
78
|
-
|
|
79
|
-
|
|
80
|
-
|
|
81
|
-
|
|
82
|
-
|
|
83
|
-
|
|
84
|
-
|
|
85
|
-
|
|
86
|
-
|
|
87
|
-
tools: [
|
|
88
|
-
new GetWeatherTool()
|
|
89
|
-
]
|
|
102
|
+
export const agent = new LuaAgent({
|
|
103
|
+
name: 'my-assistant',
|
|
104
|
+
persona: 'You are a helpful AI assistant...',
|
|
105
|
+
welcomeMessage: 'Hello! How can I help you today?',
|
|
106
|
+
skills: [generalSkill, userSkill, productSkill],
|
|
107
|
+
webhooks: [paymentWebhook],
|
|
108
|
+
jobs: [dailyCleanupJob],
|
|
109
|
+
preProcessors: [messageMatchingProcessor],
|
|
110
|
+
postProcessors: [responseModifierProcessor]
|
|
90
111
|
});
|
|
91
112
|
```
|
|
92
113
|
|
|
93
|
-
|
|
114
|
+
### Key Properties
|
|
94
115
|
|
|
95
|
-
|
|
116
|
+
#### `name` (string)
|
|
117
|
+
- Your agent's identifier
|
|
118
|
+
- Used for logging and organization
|
|
119
|
+
- Example: `'customer-support-agent'`
|
|
96
120
|
|
|
97
|
-
|
|
121
|
+
#### `persona` (string)
|
|
122
|
+
- Defines your agent's personality and behavior
|
|
123
|
+
- How the AI should respond to users
|
|
124
|
+
- What tone and style to use
|
|
98
125
|
|
|
99
|
-
|
|
126
|
+
**Example:**
|
|
127
|
+
```typescript
|
|
128
|
+
persona: `You are Emma, a friendly customer support agent for Acme Corp.
|
|
129
|
+
You're helpful, patient, and always prioritize customer satisfaction.
|
|
130
|
+
Use a warm, professional tone and offer solutions proactively.`
|
|
131
|
+
```
|
|
100
132
|
|
|
101
|
-
|
|
133
|
+
#### `welcomeMessage` (string, optional)
|
|
134
|
+
- First message users see when starting a chat
|
|
135
|
+
- Should be welcoming and set expectations
|
|
102
136
|
|
|
103
|
-
|
|
137
|
+
**Example:**
|
|
138
|
+
```typescript
|
|
139
|
+
welcomeMessage: "Hi! I'm Emma from Acme Corp. How can I assist you today?"
|
|
140
|
+
```
|
|
104
141
|
|
|
105
|
-
|
|
106
|
-
|
|
107
|
-
|
|
108
|
-
|
|
142
|
+
#### `skills` (array of LuaSkill)
|
|
143
|
+
- Collections of tools grouped by functionality
|
|
144
|
+
- Each skill contains multiple related tools
|
|
145
|
+
- Agents can use all tools from all skills
|
|
109
146
|
|
|
110
|
-
**
|
|
111
|
-
|
|
147
|
+
**Example:**
|
|
148
|
+
```typescript
|
|
149
|
+
skills: [
|
|
150
|
+
generalSkill, // Weather, posts, calculations
|
|
151
|
+
productSkill, // Product search, CRUD operations
|
|
152
|
+
basketSkill, // Shopping cart management
|
|
153
|
+
orderSkill // Order processing
|
|
154
|
+
]
|
|
155
|
+
```
|
|
112
156
|
|
|
113
|
-
|
|
157
|
+
#### `webhooks` (array of LuaWebhook, optional)
|
|
158
|
+
- HTTP endpoints that receive external events
|
|
159
|
+
- Trigger actions based on external systems
|
|
160
|
+
- Examples: Payment notifications, order updates
|
|
114
161
|
|
|
115
|
-
|
|
162
|
+
**Example:**
|
|
163
|
+
```typescript
|
|
164
|
+
webhooks: [
|
|
165
|
+
paymentWebhook, // Stripe payment confirmations
|
|
166
|
+
userEventWebhook // External system notifications
|
|
167
|
+
]
|
|
168
|
+
```
|
|
116
169
|
|
|
117
|
-
|
|
118
|
-
-
|
|
119
|
-
-
|
|
120
|
-
-
|
|
121
|
-
- **CRM** → Create customer management tools
|
|
170
|
+
#### `jobs` (array of LuaJob, optional)
|
|
171
|
+
- Scheduled tasks that run automatically
|
|
172
|
+
- Can be one-time, recurring, or cron-based
|
|
173
|
+
- Examples: Daily cleanups, health checks, reminders
|
|
122
174
|
|
|
123
|
-
**
|
|
124
|
-
|
|
175
|
+
**Example:**
|
|
176
|
+
```typescript
|
|
177
|
+
jobs: [
|
|
178
|
+
dailyCleanupJob, // Runs every day at midnight
|
|
179
|
+
abandonedBasketProcessor // Checks for abandoned baskets hourly
|
|
180
|
+
]
|
|
181
|
+
```
|
|
125
182
|
|
|
126
|
-
|
|
183
|
+
#### `preProcessors` (array of PreProcessor, optional)
|
|
184
|
+
- Run **before** messages reach the agent
|
|
185
|
+
- Modify, filter, or enhance incoming messages
|
|
186
|
+
- Examples: Profanity filtering, intent detection, routing
|
|
127
187
|
|
|
128
|
-
|
|
188
|
+
**Example:**
|
|
189
|
+
```typescript
|
|
190
|
+
preProcessors: [
|
|
191
|
+
messageMatchingProcessor // Routes messages based on patterns
|
|
192
|
+
]
|
|
193
|
+
```
|
|
129
194
|
|
|
130
|
-
|
|
131
|
-
-
|
|
132
|
-
-
|
|
133
|
-
-
|
|
134
|
-
- Best practices
|
|
195
|
+
#### `postProcessors` (array of PostProcessor, optional)
|
|
196
|
+
- Run **after** the agent generates a response
|
|
197
|
+
- Modify, enhance, or format responses
|
|
198
|
+
- Examples: Add disclaimers, translate, format
|
|
135
199
|
|
|
136
|
-
**
|
|
137
|
-
|
|
200
|
+
**Example:**
|
|
201
|
+
```typescript
|
|
202
|
+
postProcessors: [
|
|
203
|
+
responseModifierProcessor // Adds custom formatting
|
|
204
|
+
]
|
|
205
|
+
```
|
|
138
206
|
|
|
139
207
|
---
|
|
140
208
|
|
|
141
|
-
##
|
|
209
|
+
## 📁 Project Structure
|
|
142
210
|
|
|
143
|
-
|
|
211
|
+
```
|
|
212
|
+
your-project/
|
|
213
|
+
├── src/
|
|
214
|
+
│ ├── index.ts # 🎯 Main file - LuaAgent definition
|
|
215
|
+
│ ├── skills/ # Skills grouped by functionality
|
|
216
|
+
│ │ ├── tools/ # Individual tool implementations
|
|
217
|
+
│ │ │ ├── GetWeatherTool.ts
|
|
218
|
+
│ │ │ ├── ProductsTool.ts
|
|
219
|
+
│ │ │ └── BasketTool.ts
|
|
220
|
+
│ │ ├── product.skill.ts # Product skill (groups product tools)
|
|
221
|
+
│ │ └── basket.skill.ts # Basket skill (groups basket tools)
|
|
222
|
+
│ ├── webhooks/ # HTTP webhook handlers
|
|
223
|
+
│ │ ├── PaymentWebhook.ts
|
|
224
|
+
│ │ └── UserEventWebhook.ts
|
|
225
|
+
│ ├── jobs/ # Scheduled background tasks
|
|
226
|
+
│ │ ├── DailyCleanupJob.ts
|
|
227
|
+
│ │ └── HealthCheckJob.ts
|
|
228
|
+
│ ├── preprocessors/ # Message preprocessors
|
|
229
|
+
│ │ └── messageMatching.ts
|
|
230
|
+
│ ├── postprocessors/ # Response postprocessors
|
|
231
|
+
│ │ └── modifyResponse.ts
|
|
232
|
+
│ └── services/ # Shared utilities
|
|
233
|
+
│ ├── ApiService.ts
|
|
234
|
+
│ └── GetWeather.ts
|
|
235
|
+
├── lua.skill.yaml # 📝 Configuration & metadata
|
|
236
|
+
├── package.json
|
|
237
|
+
└── tsconfig.json
|
|
238
|
+
```
|
|
144
239
|
|
|
145
|
-
|
|
146
|
-
|
|
147
|
-
|
|
148
|
-
|
|
240
|
+
---
|
|
241
|
+
|
|
242
|
+
## 🎓 Key Concepts
|
|
243
|
+
|
|
244
|
+
### Skills vs Tools
|
|
149
245
|
|
|
150
|
-
|
|
246
|
+
**Tools** are individual functions:
|
|
247
|
+
```typescript
|
|
248
|
+
export default class GetWeatherTool implements LuaTool {
|
|
249
|
+
name = "get_weather";
|
|
250
|
+
description = "Get weather for a city";
|
|
251
|
+
// ... implementation
|
|
252
|
+
}
|
|
253
|
+
```
|
|
254
|
+
|
|
255
|
+
**Skills** group related tools:
|
|
256
|
+
```typescript
|
|
257
|
+
export const weatherSkill = new LuaSkill({
|
|
258
|
+
name: 'weather-skill',
|
|
259
|
+
description: 'Weather information tools',
|
|
260
|
+
context: 'Use these tools to get weather data',
|
|
261
|
+
tools: [getWeatherTool, forecastTool]
|
|
262
|
+
});
|
|
263
|
+
```
|
|
264
|
+
|
|
265
|
+
**Why?** Skills help organize tools and provide context to the AI about when to use them.
|
|
266
|
+
|
|
267
|
+
### The LuaAgent Advantage
|
|
268
|
+
|
|
269
|
+
Instead of exporting individual skills, webhooks, and jobs separately, the **LuaAgent** provides a single, unified configuration:
|
|
270
|
+
|
|
271
|
+
**❌ Old Way (Legacy):**
|
|
272
|
+
```typescript
|
|
273
|
+
export const skill1 = new LuaSkill({...});
|
|
274
|
+
export const skill2 = new LuaSkill({...});
|
|
275
|
+
export const webhook1 = new LuaWebhook({...});
|
|
276
|
+
// Hard to manage, hard to see the big picture
|
|
151
277
|
```
|
|
152
278
|
|
|
279
|
+
**✅ New Way (LuaAgent):**
|
|
280
|
+
```typescript
|
|
281
|
+
export const agent = new LuaAgent({
|
|
282
|
+
name: 'my-agent',
|
|
283
|
+
persona: '...',
|
|
284
|
+
skills: [skill1, skill2],
|
|
285
|
+
webhooks: [webhook1],
|
|
286
|
+
jobs: [job1]
|
|
287
|
+
});
|
|
288
|
+
// Everything in one place, easy to understand
|
|
289
|
+
```
|
|
290
|
+
|
|
291
|
+
**Benefits:**
|
|
292
|
+
- 📦 Single source of truth
|
|
293
|
+
- 🎯 Clear agent configuration
|
|
294
|
+
- 🔄 Automatic YAML sync
|
|
295
|
+
- 📝 Better organization
|
|
296
|
+
|
|
297
|
+
---
|
|
298
|
+
|
|
299
|
+
## 🧪 Development Workflow
|
|
300
|
+
|
|
301
|
+
### Typical Development Flow
|
|
302
|
+
|
|
303
|
+
1. **Create/Modify Tools**
|
|
304
|
+
```bash
|
|
305
|
+
# Edit your tools in src/skills/tools/
|
|
306
|
+
vim src/skills/tools/MyNewTool.ts
|
|
307
|
+
```
|
|
308
|
+
|
|
309
|
+
2. **Test Locally**
|
|
310
|
+
```bash
|
|
311
|
+
# Test the specific tool
|
|
312
|
+
lua test
|
|
313
|
+
```
|
|
314
|
+
|
|
315
|
+
3. **Chat Test (Sandbox)**
|
|
316
|
+
```bash
|
|
317
|
+
# Chat with your agent using local code
|
|
318
|
+
lua chat
|
|
319
|
+
# Select: Sandbox
|
|
320
|
+
```
|
|
321
|
+
|
|
322
|
+
4. **Compile**
|
|
323
|
+
```bash
|
|
324
|
+
# Bundle everything
|
|
325
|
+
lua compile
|
|
326
|
+
```
|
|
327
|
+
|
|
328
|
+
5. **Push to Server**
|
|
329
|
+
```bash
|
|
330
|
+
# Upload new version
|
|
331
|
+
lua push
|
|
332
|
+
```
|
|
333
|
+
|
|
334
|
+
6. **Chat Test (Production)**
|
|
335
|
+
```bash
|
|
336
|
+
# Chat with deployed agent
|
|
337
|
+
lua chat
|
|
338
|
+
# Select: Production
|
|
339
|
+
```
|
|
340
|
+
|
|
153
341
|
---
|
|
154
342
|
|
|
155
|
-
|
|
343
|
+
## 🚀 Quick Examples
|
|
344
|
+
|
|
345
|
+
### Example 1: Adding a New Tool
|
|
346
|
+
|
|
347
|
+
Create a new tool file:
|
|
156
348
|
|
|
157
|
-
1. **Create** `src/tools/MyTool.ts`:
|
|
158
349
|
```typescript
|
|
159
|
-
|
|
350
|
+
// src/skills/tools/GreetingTool.ts
|
|
351
|
+
import { LuaTool } from "lua-cli/skill";
|
|
160
352
|
import { z } from "zod";
|
|
161
353
|
|
|
162
|
-
export default class
|
|
163
|
-
name = "
|
|
164
|
-
description = "
|
|
165
|
-
|
|
354
|
+
export default class GreetingTool implements LuaTool {
|
|
355
|
+
name = "greet_user";
|
|
356
|
+
description = "Generate a personalized greeting";
|
|
357
|
+
|
|
358
|
+
inputSchema = z.object({
|
|
359
|
+
name: z.string(),
|
|
360
|
+
language: z.enum(['en', 'es', 'fr']).optional()
|
|
361
|
+
});
|
|
166
362
|
|
|
167
|
-
async execute(input:
|
|
168
|
-
|
|
363
|
+
async execute(input: z.infer<typeof this.inputSchema>) {
|
|
364
|
+
const greetings = {
|
|
365
|
+
en: `Hello, ${input.name}!`,
|
|
366
|
+
es: `¡Hola, ${input.name}!`,
|
|
367
|
+
fr: `Bonjour, ${input.name}!`
|
|
368
|
+
};
|
|
369
|
+
|
|
370
|
+
const lang = input.language || 'en';
|
|
371
|
+
return { greeting: greetings[lang] };
|
|
169
372
|
}
|
|
170
373
|
}
|
|
171
374
|
```
|
|
172
375
|
|
|
173
|
-
|
|
376
|
+
Add it to your skill:
|
|
377
|
+
|
|
174
378
|
```typescript
|
|
175
|
-
|
|
379
|
+
// src/skills/general.skill.ts
|
|
380
|
+
import GreetingTool from './tools/GreetingTool';
|
|
176
381
|
|
|
177
|
-
const
|
|
178
|
-
|
|
382
|
+
export const generalSkill = new LuaSkill({
|
|
383
|
+
name: 'general-skill',
|
|
384
|
+
description: 'General purpose utilities',
|
|
385
|
+
context: 'Use these for common tasks',
|
|
386
|
+
tools: [
|
|
387
|
+
new GetWeatherTool(),
|
|
388
|
+
new GreetingTool(), // ✅ Add your new tool
|
|
389
|
+
]
|
|
179
390
|
});
|
|
180
391
|
```
|
|
181
392
|
|
|
182
|
-
|
|
393
|
+
Test it:
|
|
183
394
|
```bash
|
|
184
395
|
lua test
|
|
185
|
-
# Select
|
|
396
|
+
# Select: greet_user
|
|
397
|
+
# Input name: "Alice"
|
|
398
|
+
# Input language: "es"
|
|
399
|
+
# Output: { greeting: "¡Hola, Alice!" }
|
|
186
400
|
```
|
|
187
401
|
|
|
188
|
-
|
|
402
|
+
### Example 2: Creating a Scheduled Job
|
|
189
403
|
|
|
190
|
-
|
|
404
|
+
```typescript
|
|
405
|
+
// src/jobs/DailyReportJob.ts
|
|
406
|
+
import { LuaJob, User } from "lua-cli";
|
|
191
407
|
|
|
192
|
-
|
|
408
|
+
export default new LuaJob({
|
|
409
|
+
name: "daily-report",
|
|
410
|
+
version: "1.0.0",
|
|
411
|
+
description: "Send daily summary to admin",
|
|
412
|
+
|
|
413
|
+
schedule: {
|
|
414
|
+
type: "cron",
|
|
415
|
+
pattern: "0 9 * * *" // Every day at 9 AM
|
|
416
|
+
},
|
|
417
|
+
|
|
418
|
+
execute: async (job) => {
|
|
419
|
+
const user = await job.user();
|
|
420
|
+
|
|
421
|
+
// Generate report
|
|
422
|
+
const report = `Daily Summary for ${new Date().toDateString()}`;
|
|
423
|
+
|
|
424
|
+
// Send to user
|
|
425
|
+
await user.send([{
|
|
426
|
+
type: "text",
|
|
427
|
+
text: report
|
|
428
|
+
}]);
|
|
429
|
+
|
|
430
|
+
return { success: true, sent: true };
|
|
431
|
+
}
|
|
432
|
+
});
|
|
433
|
+
```
|
|
193
434
|
|
|
435
|
+
Add to LuaAgent:
|
|
194
436
|
```typescript
|
|
195
|
-
|
|
196
|
-
|
|
197
|
-
|
|
198
|
-
|
|
199
|
-
|
|
200
|
-
|
|
437
|
+
import dailyReportJob from './jobs/DailyReportJob';
|
|
438
|
+
|
|
439
|
+
export const agent = new LuaAgent({
|
|
440
|
+
// ...
|
|
441
|
+
jobs: [dailyReportJob]
|
|
442
|
+
});
|
|
443
|
+
```
|
|
444
|
+
|
|
445
|
+
### Example 3: Creating a Webhook
|
|
446
|
+
|
|
447
|
+
```typescript
|
|
448
|
+
// src/webhooks/OrderWebhook.ts
|
|
449
|
+
import { LuaWebhook, Orders } from "lua-cli";
|
|
450
|
+
import { z } from "zod";
|
|
451
|
+
|
|
452
|
+
export default new LuaWebhook({
|
|
453
|
+
name: "order-notification",
|
|
454
|
+
version: "1.0.0",
|
|
455
|
+
description: "Receive order updates from external systems",
|
|
201
456
|
|
|
202
|
-
|
|
203
|
-
|
|
204
|
-
|
|
457
|
+
bodySchema: z.object({
|
|
458
|
+
orderId: z.string(),
|
|
459
|
+
status: z.string(),
|
|
460
|
+
amount: z.number()
|
|
461
|
+
}),
|
|
462
|
+
|
|
463
|
+
execute: async ({ body }) => {
|
|
464
|
+
// Update order in your system
|
|
465
|
+
await Orders.updateStatus(body.status, body.orderId);
|
|
466
|
+
|
|
467
|
+
return {
|
|
468
|
+
status: 200,
|
|
469
|
+
body: { success: true, orderId: body.orderId }
|
|
470
|
+
};
|
|
471
|
+
}
|
|
472
|
+
});
|
|
205
473
|
```
|
|
206
474
|
|
|
207
475
|
---
|
|
208
476
|
|
|
209
|
-
|
|
477
|
+
## 📚 Available APIs
|
|
210
478
|
|
|
211
|
-
|
|
479
|
+
Your tools and jobs have access to these powerful APIs:
|
|
212
480
|
|
|
481
|
+
### User Data
|
|
213
482
|
```typescript
|
|
214
|
-
|
|
483
|
+
const user = await User.get();
|
|
484
|
+
await user.update({ preferences: 'dark mode' });
|
|
485
|
+
await user.send([{ type: "text", text: "Hello!" }]);
|
|
486
|
+
```
|
|
215
487
|
|
|
216
|
-
|
|
217
|
-
|
|
218
|
-
|
|
219
|
-
|
|
220
|
-
|
|
221
|
-
|
|
222
|
-
|
|
223
|
-
|
|
224
|
-
|
|
488
|
+
### Products
|
|
489
|
+
```typescript
|
|
490
|
+
const products = await Products.get();
|
|
491
|
+
const product = await Products.create({ name: "Widget", price: 29.99 });
|
|
492
|
+
await product.update({ price: 24.99 });
|
|
493
|
+
```
|
|
494
|
+
|
|
495
|
+
### Baskets
|
|
496
|
+
```typescript
|
|
497
|
+
const basket = await Baskets.create();
|
|
498
|
+
await basket.addItem({ productId: "123", quantity: 2 });
|
|
499
|
+
await basket.placeOrder();
|
|
500
|
+
```
|
|
501
|
+
|
|
502
|
+
### Orders
|
|
503
|
+
```typescript
|
|
504
|
+
const orders = await Orders.get();
|
|
505
|
+
await Orders.updateStatus('confirmed', orderId);
|
|
506
|
+
```
|
|
507
|
+
|
|
508
|
+
### Custom Data
|
|
509
|
+
```typescript
|
|
510
|
+
const movies = await Data.get('movies');
|
|
511
|
+
await Data.create('movies', { title: "Inception", year: 2010 });
|
|
512
|
+
```
|
|
513
|
+
|
|
514
|
+
### Jobs (Dynamic)
|
|
515
|
+
```typescript
|
|
516
|
+
const job = await Jobs.create({
|
|
517
|
+
name: "remind-user",
|
|
518
|
+
schedule: { type: "once", executeAt: new Date(Date.now() + 3600000) },
|
|
519
|
+
metadata: { message: "Time for your meeting!" },
|
|
520
|
+
execute: async (job) => {
|
|
521
|
+
const user = await job.user();
|
|
522
|
+
await user.send([{ type: "text", text: job.metadata.message }]);
|
|
523
|
+
return { success: true };
|
|
524
|
+
}
|
|
525
|
+
});
|
|
526
|
+
```
|
|
527
|
+
|
|
528
|
+
---
|
|
529
|
+
|
|
530
|
+
## 🔑 Key Features
|
|
531
|
+
|
|
532
|
+
### Auto-Sync Between Code and YAML
|
|
533
|
+
|
|
534
|
+
Your `lua.skill.yaml` and `LuaAgent` in `index.ts` stay synchronized automatically:
|
|
535
|
+
|
|
536
|
+
**When you run `lua init`:**
|
|
537
|
+
- ✅ Agent name, persona, and welcome message are added to both YAML and code
|
|
538
|
+
|
|
539
|
+
**When you run `lua compile`:**
|
|
540
|
+
- ✅ LuaAgent persona and welcome message sync to YAML
|
|
541
|
+
|
|
542
|
+
**Why?** This ensures your configuration is always consistent!
|
|
543
|
+
|
|
544
|
+
### Environment Variables
|
|
545
|
+
|
|
546
|
+
Use `.env` for API keys and sensitive data:
|
|
547
|
+
|
|
548
|
+
```bash
|
|
549
|
+
# .env
|
|
550
|
+
OPENAI_API_KEY=your-key-here
|
|
551
|
+
STRIPE_SECRET_KEY=your-stripe-key
|
|
552
|
+
PINECONE_API_KEY=your-pinecone-key
|
|
553
|
+
LUA_API_KEY=your-lua-api-key # Optional: for CI/CD
|
|
554
|
+
```
|
|
555
|
+
|
|
556
|
+
Access in your code:
|
|
557
|
+
```typescript
|
|
558
|
+
import { env } from "lua-cli/skill";
|
|
559
|
+
|
|
560
|
+
const apiKey = env('OPENAI_API_KEY');
|
|
561
|
+
```
|
|
562
|
+
|
|
563
|
+
---
|
|
564
|
+
|
|
565
|
+
## 📖 Common Patterns
|
|
566
|
+
|
|
567
|
+
### Pattern 1: Tool with External API
|
|
568
|
+
|
|
569
|
+
```typescript
|
|
570
|
+
import { LuaTool } from "lua-cli/skill";
|
|
571
|
+
import { z } from "zod";
|
|
572
|
+
import axios from "axios";
|
|
573
|
+
import { env } from "lua-cli/skill";
|
|
574
|
+
|
|
575
|
+
export default class WeatherTool implements LuaTool {
|
|
576
|
+
name = "get_weather";
|
|
577
|
+
description = "Get current weather for a city";
|
|
225
578
|
|
|
226
|
-
|
|
579
|
+
inputSchema = z.object({
|
|
580
|
+
city: z.string()
|
|
581
|
+
});
|
|
582
|
+
|
|
583
|
+
async execute(input: z.infer<typeof this.inputSchema>) {
|
|
584
|
+
const apiKey = env('WEATHER_API_KEY');
|
|
585
|
+
|
|
586
|
+
const response = await axios.get(`https://api.weather.com/current`, {
|
|
587
|
+
params: { city: input.city, apiKey }
|
|
588
|
+
});
|
|
589
|
+
|
|
590
|
+
return {
|
|
591
|
+
temperature: response.data.temp,
|
|
592
|
+
condition: response.data.condition,
|
|
593
|
+
city: input.city
|
|
594
|
+
};
|
|
595
|
+
}
|
|
227
596
|
}
|
|
228
597
|
```
|
|
229
598
|
|
|
230
|
-
|
|
599
|
+
### Pattern 2: Tool that Creates a Job
|
|
231
600
|
|
|
232
|
-
|
|
601
|
+
```typescript
|
|
602
|
+
import { LuaTool, Jobs, JobInstance } from "lua-cli";
|
|
603
|
+
import { z } from "zod";
|
|
233
604
|
|
|
234
|
-
|
|
605
|
+
export default class ReminderTool implements LuaTool {
|
|
606
|
+
name = "set_reminder";
|
|
607
|
+
description = "Set a reminder for later";
|
|
608
|
+
|
|
609
|
+
inputSchema = z.object({
|
|
610
|
+
message: z.string(),
|
|
611
|
+
delayMinutes: z.number()
|
|
612
|
+
});
|
|
235
613
|
|
|
236
|
-
|
|
237
|
-
|
|
238
|
-
|
|
239
|
-
|
|
240
|
-
|
|
241
|
-
|
|
242
|
-
|
|
243
|
-
|
|
614
|
+
async execute(input: z.infer<typeof this.inputSchema>) {
|
|
615
|
+
// Create a job that will notify the user later
|
|
616
|
+
const job = await Jobs.create({
|
|
617
|
+
name: `reminder-${Date.now()}`,
|
|
618
|
+
description: "User reminder",
|
|
619
|
+
metadata: {
|
|
620
|
+
message: input.message // ✅ Pass data via metadata
|
|
621
|
+
},
|
|
622
|
+
schedule: {
|
|
623
|
+
type: "once",
|
|
624
|
+
executeAt: new Date(Date.now() + input.delayMinutes * 60000)
|
|
625
|
+
},
|
|
626
|
+
execute: async (jobInstance: JobInstance) => {
|
|
627
|
+
const user = await jobInstance.user();
|
|
628
|
+
const message = jobInstance.metadata.message;
|
|
629
|
+
|
|
630
|
+
await user.send([{
|
|
631
|
+
type: "text",
|
|
632
|
+
text: `⏰ Reminder: ${message}`
|
|
633
|
+
}]);
|
|
634
|
+
|
|
635
|
+
return { success: true };
|
|
636
|
+
}
|
|
637
|
+
});
|
|
638
|
+
|
|
639
|
+
return {
|
|
640
|
+
success: true,
|
|
641
|
+
message: `Reminder set for ${input.delayMinutes} minutes from now`,
|
|
642
|
+
jobId: job.id
|
|
643
|
+
};
|
|
644
|
+
}
|
|
645
|
+
}
|
|
646
|
+
```
|
|
244
647
|
|
|
245
|
-
|
|
648
|
+
**Important:** Job execute functions must be self-contained. Use `metadata` to pass data!
|
|
246
649
|
|
|
247
|
-
|
|
248
|
-
- ✅ Data - Custom data with search
|
|
249
|
-
- ✅ Products - Product catalog
|
|
250
|
-
- ✅ Baskets - Shopping carts
|
|
251
|
-
- ✅ Orders - Order processing
|
|
650
|
+
### Pattern 3: Webhook that Triggers Job
|
|
252
651
|
|
|
253
|
-
|
|
652
|
+
```typescript
|
|
653
|
+
import { LuaWebhook, Jobs } from "lua-cli";
|
|
654
|
+
import { z } from "zod";
|
|
254
655
|
|
|
255
|
-
|
|
256
|
-
|
|
257
|
-
|
|
258
|
-
|
|
259
|
-
|
|
656
|
+
export default new LuaWebhook({
|
|
657
|
+
name: "order-received",
|
|
658
|
+
version: "1.0.0",
|
|
659
|
+
description: "Handle new order notifications",
|
|
660
|
+
|
|
661
|
+
bodySchema: z.object({
|
|
662
|
+
orderId: z.string(),
|
|
663
|
+
userId: z.string()
|
|
664
|
+
}),
|
|
665
|
+
|
|
666
|
+
execute: async ({ body }) => {
|
|
667
|
+
// Create a job to process the order in 5 minutes
|
|
668
|
+
await Jobs.create({
|
|
669
|
+
name: `process-order-${body.orderId}`,
|
|
670
|
+
metadata: { orderId: body.orderId },
|
|
671
|
+
schedule: {
|
|
672
|
+
type: "once",
|
|
673
|
+
executeAt: new Date(Date.now() + 300000)
|
|
674
|
+
},
|
|
675
|
+
execute: async (job) => {
|
|
676
|
+
// Process order logic here
|
|
677
|
+
return { success: true };
|
|
678
|
+
}
|
|
679
|
+
});
|
|
680
|
+
|
|
681
|
+
return {
|
|
682
|
+
status: 200,
|
|
683
|
+
body: { received: true, orderId: body.orderId }
|
|
684
|
+
};
|
|
685
|
+
}
|
|
686
|
+
});
|
|
687
|
+
```
|
|
260
688
|
|
|
261
689
|
---
|
|
262
690
|
|
|
263
|
-
##
|
|
691
|
+
## 🎯 Next Steps
|
|
264
692
|
|
|
265
|
-
###
|
|
693
|
+
### 1. Customize Your Agent
|
|
694
|
+
|
|
695
|
+
Edit `src/index.ts` and update:
|
|
696
|
+
- Agent name
|
|
697
|
+
- Persona (how your agent behaves)
|
|
698
|
+
- Welcome message
|
|
699
|
+
|
|
700
|
+
### 2. Explore Example Tools
|
|
701
|
+
|
|
702
|
+
Look in `src/skills/tools/` to see:
|
|
703
|
+
- `GetWeatherTool.ts` - External API integration
|
|
704
|
+
- `ProductsTool.ts` - CRUD operations with Products API
|
|
705
|
+
- `BasketTool.ts` - Shopping cart management
|
|
706
|
+
- `GameScoreTrackerTool.ts` - Complex state management
|
|
707
|
+
|
|
708
|
+
### 3. Test Everything
|
|
266
709
|
|
|
267
|
-
**"How do I test?"**
|
|
268
710
|
```bash
|
|
269
|
-
|
|
711
|
+
# Test individual tools
|
|
712
|
+
lua test
|
|
713
|
+
|
|
714
|
+
# Chat with your agent
|
|
715
|
+
lua chat
|
|
716
|
+
|
|
717
|
+
# Compile and check for errors
|
|
718
|
+
lua compile
|
|
270
719
|
```
|
|
271
720
|
|
|
272
|
-
|
|
721
|
+
### 4. Deploy
|
|
722
|
+
|
|
273
723
|
```bash
|
|
274
|
-
|
|
724
|
+
# Push new version
|
|
725
|
+
lua push
|
|
726
|
+
|
|
727
|
+
# Or push everything at once
|
|
728
|
+
lua push all --force --auto-deploy
|
|
275
729
|
```
|
|
276
730
|
|
|
277
|
-
|
|
731
|
+
### 5. Monitor & Manage
|
|
732
|
+
|
|
278
733
|
```bash
|
|
279
|
-
|
|
280
|
-
lua
|
|
281
|
-
```
|
|
734
|
+
# View production status
|
|
735
|
+
lua production
|
|
282
736
|
|
|
283
|
-
|
|
284
|
-
|
|
285
|
-
|
|
286
|
-
|
|
287
|
-
|
|
737
|
+
# Manage environment variables
|
|
738
|
+
lua env production
|
|
739
|
+
|
|
740
|
+
# Update persona
|
|
741
|
+
lua persona production
|
|
742
|
+
|
|
743
|
+
# View logs
|
|
744
|
+
lua logs
|
|
745
|
+
```
|
|
288
746
|
|
|
289
747
|
---
|
|
290
748
|
|
|
291
|
-
|
|
749
|
+
## 💡 Tips & Best Practices
|
|
750
|
+
|
|
751
|
+
### Tool Design
|
|
752
|
+
✅ **Clear names** - Use descriptive tool names like `get_weather`, not `weather`
|
|
753
|
+
✅ **Validate inputs** - Use Zod schemas to ensure data quality
|
|
754
|
+
✅ **Good descriptions** - Help the AI understand when to use your tool
|
|
755
|
+
✅ **Handle errors** - Return error messages instead of throwing
|
|
756
|
+
|
|
757
|
+
### Job Design
|
|
758
|
+
✅ **Self-contained** - Jobs should not depend on parent scope variables
|
|
759
|
+
✅ **Use metadata** - Pass data through `metadata` field
|
|
760
|
+
✅ **Proper scheduling** - Choose appropriate schedule types (once, cron, interval)
|
|
761
|
+
✅ **Idempotent** - Jobs should be safe to run multiple times
|
|
762
|
+
|
|
763
|
+
### Webhook Design
|
|
764
|
+
✅ **Validate inputs** - Use schemas for query, headers, and body
|
|
765
|
+
✅ **Return proper status** - Use HTTP status codes (200, 400, etc.)
|
|
766
|
+
✅ **Handle failures** - Return error responses gracefully
|
|
767
|
+
✅ **Security** - Validate signatures for production webhooks
|
|
292
768
|
|
|
293
|
-
|
|
294
|
-
|
|
295
|
-
|
|
296
|
-
|
|
297
|
-
|
|
769
|
+
### Agent Persona
|
|
770
|
+
✅ **Be specific** - Define personality, tone, and behavior clearly
|
|
771
|
+
✅ **Set boundaries** - Explain what the agent can and cannot do
|
|
772
|
+
✅ **Give examples** - Show how the agent should respond
|
|
773
|
+
✅ **Update regularly** - Refine based on user interactions
|
|
298
774
|
|
|
299
775
|
---
|
|
300
776
|
|
|
301
|
-
##
|
|
777
|
+
## 🆘 Need Help?
|
|
302
778
|
|
|
303
|
-
|
|
304
|
-
|
|
305
|
-
|
|
306
|
-
|
|
307
|
-
|
|
779
|
+
### Commands
|
|
780
|
+
```bash
|
|
781
|
+
lua --help # All available commands
|
|
782
|
+
lua compile --help # Compilation help
|
|
783
|
+
lua push --help # Deployment help
|
|
784
|
+
lua test --help # Testing help
|
|
785
|
+
```
|
|
786
|
+
|
|
787
|
+
### Common Issues
|
|
788
|
+
|
|
789
|
+
**Q: Tool not showing up in agent?**
|
|
790
|
+
- ✅ Make sure it's added to a skill
|
|
791
|
+
- ✅ Make sure the skill is added to LuaAgent
|
|
792
|
+
- ✅ Run `lua compile`
|
|
793
|
+
|
|
794
|
+
**Q: Job execute function has undefined variables?**
|
|
795
|
+
- ✅ Use `metadata` to pass data to the job
|
|
796
|
+
- ✅ Job functions must be self-contained
|
|
797
|
+
|
|
798
|
+
**Q: Changes not reflecting in production?**
|
|
799
|
+
- ✅ Run `lua compile` first
|
|
800
|
+
- ✅ Run `lua push` to upload
|
|
801
|
+
- ✅ Select the right environment in `lua chat`
|
|
308
802
|
|
|
309
803
|
---
|
|
310
804
|
|
|
311
|
-
##
|
|
805
|
+
## 🎉 You're Ready!
|
|
806
|
+
|
|
807
|
+
You now have everything you need to build powerful AI agents with Lua. Start by:
|
|
808
|
+
|
|
809
|
+
1. Testing the example tools with `lua test`
|
|
810
|
+
2. Chatting with your agent using `lua chat`
|
|
811
|
+
3. Exploring the code in `src/skills/tools/`
|
|
812
|
+
4. Customizing the agent persona in `src/index.ts`
|
|
813
|
+
|
|
814
|
+
Happy building! 🚀
|
|
815
|
+
|
|
816
|
+
---
|
|
312
817
|
|
|
313
|
-
|
|
314
|
-
1. Run `lua dev`
|
|
315
|
-
2. Chat: "What's the weather in your city?"
|
|
316
|
-
3. Edit `GetWeatherTool.ts` to add a fun fact about the city
|
|
317
|
-
4. Save and see it auto-reload
|
|
318
|
-
5. Chat again and see your change
|
|
818
|
+
## 📞 Support
|
|
319
819
|
|
|
320
|
-
**
|
|
820
|
+
- **Documentation:** https://docs.heylua.ai
|
|
821
|
+
- **GitHub:** https://github.com/heylua/lua-cli
|
|
822
|
+
- **Email:** support@heylua.ai
|
|
321
823
|
|
|
322
824
|
---
|
|
323
825
|
|
|
324
|
-
|
|
826
|
+
*This template is part of lua-cli v3.0.0. For the latest updates, run `npm install -g lua-cli`*
|
|
325
827
|
|