openkbs 0.0.65 → 0.0.66

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.
Files changed (36) hide show
  1. package/README.md +0 -2
  2. package/package.json +1 -1
  3. package/src/actions.js +41 -85
  4. package/src/index.js +8 -9
  5. package/templates/.claude/skills/openkbs/SKILL.md +184 -0
  6. package/templates/.claude/skills/openkbs/metadata.json +1 -0
  7. package/templates/.claude/skills/openkbs/reference/backend-sdk.md +428 -0
  8. package/templates/.claude/skills/openkbs/reference/commands.md +370 -0
  9. package/templates/.claude/skills/openkbs/reference/elastic-services.md +327 -0
  10. package/templates/.claude/skills/openkbs/reference/frontend-sdk.md +299 -0
  11. package/version.json +3 -3
  12. package/templates/.openkbs/knowledge/metadata.json +0 -3
  13. package/templates/CLAUDE.md +0 -655
  14. /package/templates/{.openkbs/knowledge → .claude/skills/openkbs}/examples/ai-copywriter-agent/app/icon.png +0 -0
  15. /package/templates/{.openkbs/knowledge → .claude/skills/openkbs}/examples/ai-copywriter-agent/app/instructions.txt +0 -0
  16. /package/templates/{.openkbs/knowledge → .claude/skills/openkbs}/examples/ai-copywriter-agent/app/settings.json +0 -0
  17. /package/templates/{.openkbs/knowledge → .claude/skills/openkbs}/examples/ai-copywriter-agent/scripts/run_job.js +0 -0
  18. /package/templates/{.openkbs/knowledge → .claude/skills/openkbs}/examples/ai-copywriter-agent/scripts/utils/agent_client.js +0 -0
  19. /package/templates/{.openkbs/knowledge → .claude/skills/openkbs}/examples/ai-copywriter-agent/src/Events/actions.js +0 -0
  20. /package/templates/{.openkbs/knowledge → .claude/skills/openkbs}/examples/ai-copywriter-agent/src/Events/handler.js +0 -0
  21. /package/templates/{.openkbs/knowledge → .claude/skills/openkbs}/examples/ai-copywriter-agent/src/Events/onRequest.js +0 -0
  22. /package/templates/{.openkbs/knowledge → .claude/skills/openkbs}/examples/ai-copywriter-agent/src/Events/onRequest.json +0 -0
  23. /package/templates/{.openkbs/knowledge → .claude/skills/openkbs}/examples/ai-copywriter-agent/src/Events/onResponse.js +0 -0
  24. /package/templates/{.openkbs/knowledge → .claude/skills/openkbs}/examples/ai-copywriter-agent/src/Events/onResponse.json +0 -0
  25. /package/templates/{.openkbs/knowledge → .claude/skills/openkbs}/examples/ai-copywriter-agent/src/Frontend/contentRender.js +0 -0
  26. /package/templates/{.openkbs/knowledge → .claude/skills/openkbs}/examples/ai-copywriter-agent/src/Frontend/contentRender.json +0 -0
  27. /package/templates/{.openkbs/knowledge → .claude/skills/openkbs}/examples/ai-marketing-agent/README.md +0 -0
  28. /package/templates/{.openkbs/knowledge → .claude/skills/openkbs}/examples/ai-marketing-agent/app/instructions.txt +0 -0
  29. /package/templates/{.openkbs/knowledge → .claude/skills/openkbs}/examples/ai-marketing-agent/app/settings.json +0 -0
  30. /package/templates/{.openkbs/knowledge → .claude/skills/openkbs}/examples/ai-marketing-agent/src/Events/actions.js +0 -0
  31. /package/templates/{.openkbs/knowledge → .claude/skills/openkbs}/examples/ai-marketing-agent/src/Events/onRequest.js +0 -0
  32. /package/templates/{.openkbs/knowledge → .claude/skills/openkbs}/examples/ai-marketing-agent/src/Events/onRequest.json +0 -0
  33. /package/templates/{.openkbs/knowledge → .claude/skills/openkbs}/examples/ai-marketing-agent/src/Events/onResponse.js +0 -0
  34. /package/templates/{.openkbs/knowledge → .claude/skills/openkbs}/examples/ai-marketing-agent/src/Events/onResponse.json +0 -0
  35. /package/templates/{.openkbs/knowledge → .claude/skills/openkbs}/examples/ai-marketing-agent/src/Frontend/contentRender.js +0 -0
  36. /package/templates/{.openkbs/knowledge → .claude/skills/openkbs}/examples/ai-marketing-agent/src/Frontend/contentRender.json +0 -0
@@ -1,655 +0,0 @@
1
- # Claude Code Instructions
2
-
3
- > **Full Documentation**: For comprehensive SDK reference, API details, and advanced examples, fetch the official documentation:
4
- > `https://raw.githubusercontent.com/open-kbs/openkbs/refs/heads/main/README.md`
5
- > Or visit: https://github.com/open-kbs/openkbs
6
-
7
- # MANDATORY FIRST STEPS
8
-
9
- **CRITICAL**: Before taking ANY action, you must:
10
-
11
- **FIRST**: Update the knowledge base:
12
- ```bash
13
- openkbs update
14
- ```
15
-
16
- **SECOND**: Read the https://github.com/open-kbs/tutorials and all files in `.openkbs/knowledge/examples/` directory and subdirectories using the Read tool (skip icon.png, src/Frontend/Presentational/*, src/Events/Helpers/*).
17
- ``
18
- **THIRD**: Read existing agent code in `./app/` and `./src/` folders.
19
-
20
- # Critical Rules
21
- - Never skip reading examples
22
- - Never guess framework methods, settings or variables — always reference the examples
23
- - In src/Events and src/Frontend always use Imports (not Require)
24
- - Valid values for `_meta_actions` key are `[]` or `["REQUEST_CHAT_MODEL"]`
25
- - Add npm dependencies only if necessary
26
- - Before using third-party services in handlers, ask the user for permission
27
-
28
- ---
29
-
30
- # OpenKBS Framework Overview
31
-
32
- ## What is OpenKBS?
33
-
34
- OpenKBS is a framework for building **AI agents** - intelligent assistants that can:
35
- - Converse with users via LLM (Claude, GPT, etc.)
36
- - Execute commands (generate images, send emails, search web, etc.)
37
- - Store and retrieve data (memory system)
38
- - Run scheduled tasks (cronjobs)
39
- - Provide custom UI (React-based frontend)
40
-
41
- ## How It Works - The Request/Response Cycle
42
-
43
- ```
44
- ┌─────────────────────────────────────────────────────────────────────────────┐
45
- │ USER SENDS MESSAGE │
46
- └─────────────────────────────────────────────────────────────────────────────┘
47
-
48
-
49
- ┌─────────────────────────────────────────────────────────────────────────────┐
50
- │ 1. onRequest Handler (optional) │
51
- │ - Pre-process user message │
52
- │ - Inject context (memory items, user data) │
53
- │ - Validate or transform input │
54
- └─────────────────────────────────────────────────────────────────────────────┘
55
-
56
-
57
- ┌─────────────────────────────────────────────────────────────────────────────┐
58
- │ 2. LLM Processing │
59
- │ - System instructions from app/instructions.txt │
60
- │ - Conversation history │
61
- │ - LLM generates response (may include <command> tags) │
62
- └─────────────────────────────────────────────────────────────────────────────┘
63
-
64
-
65
- ┌─────────────────────────────────────────────────────────────────────────────┐
66
- │ 3. onResponse Handler │
67
- │ - Parse LLM response for commands: <commandName>{...}</commandName> │
68
- │ - Execute matching actions from actions.js │
69
- │ - Return result with _meta_actions: │
70
- │ • [] = stop, show result to user │
71
- │ • ["REQUEST_CHAT_MODEL"] = send result back to LLM for continuation │
72
- └─────────────────────────────────────────────────────────────────────────────┘
73
-
74
- ┌───────────────┴───────────────┐
75
- │ │
76
- ▼ ▼
77
- ┌───────────────────┐ ┌───────────────────┐
78
- │ _meta_actions: [] │ │ REQUEST_CHAT_MODEL│
79
- │ Show to user │ │ Loop back to LLM │
80
- └───────────────────┘ └───────────────────┘
81
- ```
82
-
83
- ## Project Structure
84
-
85
- ```
86
- my-agent/
87
- ├── app/
88
- │ ├── settings.json # Agent config (model, title, tools)
89
- │ ├── instructions.txt # System prompt for LLM
90
- │ └── icon.png # Agent icon
91
- ├── src/
92
- │ ├── Events/ # Backend handlers (serverless)
93
- │ │ ├── onRequest.js # Pre-process user messages
94
- │ │ ├── onResponse.js # Execute commands from LLM
95
- │ │ ├── actions.js # Command implementations
96
- │ │ ├── onCronjob.js # Scheduled tasks
97
- │ │ └── *.json # NPM dependencies per handler
98
- │ └── Frontend/ # Browser-side React code
99
- │ ├── contentRender.js # Custom UI (Header, message rendering)
100
- │ └── contentRender.json # Frontend NPM dependencies
101
- └── README.md
102
- ```
103
-
104
- ## Two Execution Environments
105
-
106
- ### 1. Backend (Cloud) - `src/Events/`
107
- - Runs in **serverless Lambda** (Node.js)
108
- - Stateless, ephemeral execution
109
- - Has `openkbs` SDK object with full capabilities
110
- - Can access external APIs, databases, send emails
111
- - Triggered by: user messages, LLM responses, cronjobs, API calls
112
-
113
- ### 2. Frontend (Browser) - `src/Frontend/`
114
- - Runs in **user's browser** (React)
115
- - Customizes chat UI (header, message rendering)
116
- - Has `openkbs` object with item CRUD, Files API, Sharing API
117
- - Cannot access secrets or server-side resources
118
-
119
- ## Event Handlers
120
-
121
- | Handler | Trigger | Purpose |
122
- |---------|---------|---------|
123
- | `onRequest` | User sends message | Pre-process, inject context, validate |
124
- | `onResponse` | LLM generates response | Parse commands, execute actions |
125
- | `onCronjob` | Cron schedule | Automated tasks, cleanup, reports |
126
- | `onAddMessages` | API adds messages | Process external integrations |
127
- | `onPublicAPIRequest` | Public API call | Webhooks, external triggers |
128
-
129
- ## The Command Pattern
130
-
131
- LLM outputs commands as XML tags. Backend parses and executes them:
132
-
133
- ```
134
- User: "Generate an image of a sunset"
135
-
136
- LLM: "I'll create that for you. <createAIImage>{"prompt": "sunset"}</createAIImage>"
137
-
138
- onResponse: Matches pattern, calls openkbs.generateImage()
139
-
140
- Returns: { type: 'CHAT_IMAGE', data: { imageUrl: '...' }, _meta_actions: [] }
141
-
142
- Frontend: Renders image to user
143
- ```
144
-
145
- ## Memory System
146
-
147
- Persistent key-value storage with automatic encryption:
148
-
149
- ```javascript
150
- // Backend
151
- await openkbs.createItem({ itemType: 'memory', itemId: 'memory_user_prefs', body: { theme: 'dark' } });
152
- const item = await openkbs.getItem('memory_user_prefs');
153
-
154
- // Frontend (same API)
155
- await openkbs.createItem({ itemType: 'memory', itemId: 'memory_key', body: { data: 'value' } });
156
- ```
157
-
158
- Items are auto-encrypted and scoped to the KB. Use prefixes for organization:
159
- - `memory_` - User/agent memory
160
- - `agent_` - Agent configuration
161
- - `cache_` - Temporary cached data
162
-
163
- ## Frontend Framework
164
-
165
- The frontend is an **extendable React application** that runs in the user's browser. You customize it through `contentRender.js` which exports specific functions:
166
-
167
- ```
168
- ┌─────────────────────────────────────────────────────────────────────────────┐
169
- │ CHAT APPLICATION (React) │
170
- ├─────────────────────────────────────────────────────────────────────────────┤
171
- │ ┌─────────────────────────────────────────────────────────────────────┐ │
172
- │ │ Header Component (optional) │ │
173
- │ │ - Custom UI above chat (settings panels, navigation, branding) │ │
174
- │ │ - Receives: openkbs, setRenderSettings, setSystemAlert, etc. │ │
175
- │ └─────────────────────────────────────────────────────────────────────┘ │
176
- │ │
177
- │ ┌─────────────────────────────────────────────────────────────────────┐ │
178
- │ │ Chat Messages Area │ │
179
- │ │ ┌─────────────────────────────────────────────────────────────┐ │ │
180
- │ │ │ Each message passes through onRenderChatMessage() │ │ │
181
- │ │ │ - Return React component → custom rendering │ │ │
182
- │ │ │ - Return null → default markdown rendering │ │ │
183
- │ │ │ - Return HIDDEN_MESSAGE → hide message completely │ │ │
184
- │ │ └─────────────────────────────────────────────────────────────┘ │ │
185
- │ └─────────────────────────────────────────────────────────────────────┘ │
186
- │ │
187
- │ ┌─────────────────────────────────────────────────────────────────────┐ │
188
- │ │ Input Area (built-in, customizable via setRenderSettings) │ │
189
- │ └─────────────────────────────────────────────────────────────────────┘ │
190
- └─────────────────────────────────────────────────────────────────────────────┘
191
- ```
192
-
193
- **Key Extension Points:**
194
-
195
- | Export | Purpose |
196
- |--------|---------|
197
- | `Header` | Custom header component (settings panels, branding, navigation) |
198
- | `onRenderChatMessage` | Custom message rendering (widgets, images, hidden messages) |
199
-
200
- **What You Can Do:**
201
-
202
- 1. **Custom Command Widgets** - Render `<createAIImage>` as icon instead of raw XML
203
- 2. **Settings Panels** - Add tabbed panels for Memory, Files, Sharing management
204
- 3. **Hide System Messages** - Filter out technical responses from UI
205
- 4. **Custom Interactions** - Buttons that send follow-up messages via `RequestChatAPI`
206
- 5. **Branding** - Custom logos, colors via `setRenderSettings`
207
-
208
- **Built-in Libraries** (no need to install):
209
- - `react` - React 18
210
- - `@mui/material` - Material UI components
211
- - `@mui/icons-material` - Material icons
212
- - `@emotion/react` - CSS-in-JS styling
213
-
214
- **Frontend SDK (`openkbs` object):**
215
- - Item CRUD - same API as backend
216
- - `openkbs.Files` - Upload, list, delete files
217
- - `openkbs.KBAPI` - Share KB with users
218
- - `openkbs.kbId`, `openkbs.isMobile` - Context info
219
-
220
- ---
221
-
222
- # Architecture Details
223
-
224
- OpenKBS provides **two execution environments**:
225
-
226
- ## Cloud Environment (`./src/Events/`)
227
- Runs in serverless compute (stateless, ephemeral). Can only reach internet-accessible resources.
228
-
229
- ### Backend Handlers
230
- - **`onRequest`**: Triggered on user message, allows pre-processing
231
- - **`onResponse`**: Activated after LLM response, enables command extraction and action execution
232
- - **`onCronjob`**: Scheduled task execution (define schedule with `handler.CRON_SCHEDULE`)
233
- - **`onAddMessages`**: Intercept messages added via API
234
- - **`onPublicAPIRequest`**: Handle public API requests (no auth required)
235
-
236
- ### Command Format
237
- Commands use XML tags with JSON content. The LLM outputs these as regular text:
238
- ```xml
239
- <commandName>
240
- {
241
- "param1": "value1",
242
- "param2": "value2"
243
- }
244
- </commandName>
245
- ```
246
-
247
- Self-closing tags for commands without parameters:
248
- ```xml
249
- <commandName/>
250
- ```
251
-
252
- ### Action Pattern
253
- ```javascript
254
- // src/Events/actions.js
255
- export const getActions = (meta, event) => [
256
- // Basic command with JSON parsing
257
- [/<commandName>([\s\S]*?)<\/commandName>/s, async (match) => {
258
- const data = JSON.parse(match[1].trim());
259
- return { type: 'RESULT', data: result, ...meta, _meta_actions: ['REQUEST_CHAT_MODEL'] };
260
- }],
261
-
262
- // View image - adds to LLM vision context
263
- [/<viewImage>([\s\S]*?)<\/viewImage>/s, async (match) => {
264
- const data = JSON.parse(match[1].trim());
265
- return {
266
- data: [
267
- { type: "text", text: `Viewing: ${data.url}` },
268
- { type: "image_url", image_url: { url: data.url } }
269
- ],
270
- ...meta, _meta_actions: ['REQUEST_CHAT_MODEL']
271
- };
272
- }],
273
-
274
- // Memory operations
275
- [/<setMemory>([\s\S]*?)<\/setMemory>/s, async (match) => {
276
- const data = JSON.parse(match[1].trim());
277
- await openkbs.updateItem({
278
- itemType: 'memory',
279
- itemId: data.itemId.startsWith('memory_') ? data.itemId : `memory_${data.itemId}`,
280
- body: { value: data.value, updatedAt: new Date().toISOString() }
281
- });
282
- return { type: 'MEMORY_UPDATED', itemId: data.itemId, ...meta, _meta_actions: ['REQUEST_CHAT_MODEL'] };
283
- }],
284
-
285
- // Delete item
286
- [/<deleteItem>([\s\S]*?)<\/deleteItem>/s, async (match) => {
287
- const data = JSON.parse(match[1].trim());
288
- await openkbs.deleteItem(data.itemId);
289
- return { type: 'ITEM_DELETED', itemId: data.itemId, ...meta, _meta_actions: ['REQUEST_CHAT_MODEL'] };
290
- }],
291
- ];
292
- ```
293
-
294
- ### onCronjob Handler
295
- ```javascript
296
- // src/Events/onCronjob.js
297
- export const handler = async (event) => {
298
- // Create a new chat with notification
299
- await openkbs.chats({
300
- chatTitle: 'Scheduled Report',
301
- message: JSON.stringify([{ type: "text", text: "Daily report" }])
302
- });
303
- return { success: true };
304
- };
305
-
306
- // IMPORTANT: Define schedule at end of file
307
- handler.CRON_SCHEDULE = "0 * * * *"; // Every hour
308
- ```
309
-
310
- Cron patterns: `* * * * *` (every min), `*/5 * * * *` (5 min), `0 * * * *` (hourly), `0 0 * * *` (daily)
311
-
312
- ## Backend SDK (openkbs object)
313
-
314
- ### Image & Video Generation
315
- ```javascript
316
- // Generate image with Gemini (supports editing with reference images)
317
- const images = await openkbs.generateImage(prompt, {
318
- model: 'gemini-2.5-flash-image', // or 'gpt-image-1' (better for text)
319
- aspect_ratio: '16:9', // gemini: 1:1, 16:9, 9:16, 4:3, 3:4
320
- imageUrls: ['reference.jpg'], // gemini only - for editing
321
- size: '1024x1024' // gpt-image-1: 1024x1024, 1536x1024, 1024x1536
322
- });
323
- const uploaded = await openkbs.uploadImage(images[0].b64_json, 'output.png', 'image/png');
324
- console.log(uploaded.url);
325
-
326
- // Generate video with Sora 2
327
- const video = await openkbs.generateVideo(prompt, {
328
- video_model: 'sora-2', // or 'sora-2-pro' (higher quality)
329
- seconds: 8, // 4, 8, or 12
330
- size: '1280x720', // or '720x1280' (portrait)
331
- input_reference_url: 'img.jpg' // optional reference image
332
- });
333
- // Check status if pending
334
- if (video[0]?.status === 'pending') {
335
- const status = await openkbs.checkVideoStatus(video[0].video_id);
336
- }
337
- ```
338
-
339
- ### Item Storage (Memory System)
340
- ```javascript
341
- // Create/Update item (upsert pattern)
342
- async function upsertItem(itemType, itemId, body) {
343
- try {
344
- await openkbs.updateItem({ itemType, itemId, body });
345
- } catch (e) {
346
- await openkbs.createItem({ itemType, itemId, body });
347
- }
348
- }
349
-
350
- // Memory with expiration
351
- await upsertItem('memory', 'memory_user_preferences', {
352
- value: { theme: 'dark', language: 'en' },
353
- updatedAt: new Date().toISOString(),
354
- exp: new Date(Date.now() + 60 * 60 * 1000).toISOString() // 1 hour
355
- });
356
-
357
- // Get single item (body is auto-decrypted)
358
- const item = await openkbs.getItem('memory_user_preferences');
359
- console.log(item.item.body.value);
360
-
361
- // Fetch multiple items with filters
362
- const items = await openkbs.fetchItems({
363
- itemType: 'memory',
364
- beginsWith: 'memory_',
365
- limit: 100
366
- });
367
-
368
- // Delete item
369
- await openkbs.deleteItem('memory_user_preferences');
370
-
371
- // Cleanup expired items
372
- const now = new Date();
373
- for (const item of items.items) {
374
- if (item.item?.body?.exp && new Date(item.item.body.exp) < now) {
375
- await openkbs.deleteItem(item.meta.itemId);
376
- }
377
- }
378
- ```
379
-
380
- ### Search & Content
381
- ```javascript
382
- // Google Search
383
- const results = await openkbs.googleSearch('AI trends 2025');
384
- const images = await openkbs.googleSearch('sunset', { searchType: 'image' });
385
-
386
- // Extract text from webpage
387
- const text = await openkbs.webpageToText('https://example.com');
388
-
389
- // OCR - extract text from image
390
- const ocr = await openkbs.imageToText('https://example.com/document.jpg');
391
- console.log(ocr.results);
392
-
393
- // Extract text from PDF/DOC
394
- const docText = await openkbs.documentToText('https://example.com/file.pdf');
395
- ```
396
-
397
- ### Communication
398
- ```javascript
399
- // Send email (HTML supported)
400
- await openkbs.sendMail('user@example.com', 'Subject', '<h1>Hello</h1><p>Content</p>');
401
-
402
- // Text to speech
403
- const audio = await openkbs.textToSpeech('Hello world');
404
- console.log(audio.audioContent); // base64
405
-
406
- // Speech to text
407
- const transcript = await openkbs.speechToText('https://example.com/audio.mp3');
408
-
409
- // Translation
410
- const { translation } = await openkbs.translate('Hello world', 'bg');
411
-
412
- // Language detection
413
- const { language } = await openkbs.detectLanguage('Здравей свят');
414
- ```
415
-
416
- ### Chat Operations
417
- ```javascript
418
- // Create new chat (for notifications, scheduled tasks)
419
- await openkbs.chats({
420
- chatTitle: 'Alert: Fire Detected',
421
- message: JSON.stringify([{ type: "text", text: "Fire detected at location X" }])
422
- });
423
-
424
- // Update chat title and icon
425
- await openkbs.chats({
426
- action: "updateChat",
427
- title: await openkbs.encrypt('New Title'),
428
- chatIcon: '🔥',
429
- chatId: event.payload.chatId
430
- });
431
- ```
432
-
433
- ### Scheduled Tasks
434
- ```javascript
435
- // Create scheduled task (fires at specific time, creates new chat)
436
- await openkbs.kb({
437
- action: 'createScheduledTask',
438
- scheduledTime: Date.now() + 3600000, // 1 hour from now (ms)
439
- taskPayload: {
440
- message: '[SCHEDULED_TASK] Send weekly report',
441
- customData: { reportType: 'weekly' }
442
- },
443
- description: 'Weekly report'
444
- });
445
-
446
- // List scheduled tasks
447
- const tasks = await openkbs.kb({ action: 'getScheduledTasks' });
448
-
449
- // Delete scheduled task
450
- await openkbs.kb({ action: 'deleteScheduledTask', timestamp: 1704067200000 });
451
- ```
452
-
453
- ### File Upload with Presigned URL
454
- ```javascript
455
- // Download file and upload to KB storage
456
- const fileResponse = await axios.get(sourceUrl, { responseType: 'arraybuffer' });
457
-
458
- const presigned = await openkbs.kb({
459
- action: 'createPresignedURL',
460
- namespace: 'files',
461
- fileName: 'uploaded.jpg',
462
- fileType: 'image/jpeg',
463
- presignedOperation: 'putObject'
464
- });
465
-
466
- await axios.put(presigned, fileResponse.data, {
467
- headers: { 'Content-Type': 'image/jpeg', 'Content-Length': fileResponse.data.length }
468
- });
469
-
470
- const publicUrl = `https://your-domain.file.vpc1.us/files/${openkbs.kbId}/uploaded.jpg`;
471
- ```
472
-
473
- ### Utilities
474
- ```javascript
475
- // Exchange rates (latest, historical, time series)
476
- const rates = await openkbs.getExchangeRates({ base: 'EUR', symbols: 'USD,GBP' });
477
- const historical = await openkbs.getExchangeRates({ base: 'EUR', symbols: 'USD', period: '2024-01-15' });
478
- const series = await openkbs.getExchangeRates({ base: 'EUR', symbols: 'USD', period: '2024-01-01..2024-01-31' });
479
-
480
- // VAT validation
481
- const vat = await openkbs.checkVAT('BG123456789');
482
-
483
- // Parse JSON from text (handles LLM output with extra text)
484
- const data = openkbs.parseJSONFromText('Some text {"key": "value"} more text');
485
-
486
- // Encryption (uses KB's AES key)
487
- const encrypted = await openkbs.encrypt(JSON.stringify(sensitiveData));
488
- const decrypted = JSON.parse(await openkbs.decrypt(encrypted));
489
-
490
- // Create embeddings
491
- const { embeddings, totalTokens } = await openkbs.createEmbeddings('Text to embed', 'text-embedding-3-large');
492
- ```
493
-
494
- ### Properties
495
- ```javascript
496
- openkbs.kbId // Current Knowledge Base ID
497
- openkbs.clientHeaders // Request headers (IP, user-agent, etc.)
498
- openkbs.AESKey // Encryption key
499
- openkbs.chatJWT // Current chat JWT token
500
- ```
501
-
502
- ### NPM Dependencies
503
- Add to handler's JSON file (e.g., `onResponse.json`):
504
- ```json
505
- {
506
- "dependencies": { "mysql2": "latest", "decimal.js": "^10.4.3" }
507
- }
508
- ```
509
-
510
- ### Secrets Management
511
- Use `{{secrets.KEY}}` placeholders (replaced at runtime):
512
- ```javascript
513
- const apiKey = "{{secrets.EXTERNAL_API_KEY}}";
514
- const telegramToken = "{{secrets.TELEGRAM_BOT_TOKEN}}";
515
- ```
516
-
517
- ## Browser Environment (`./src/Frontend/`)
518
- Runs in user's browser at `https://[kbId].apps.openkbs.com`. React-based UI customization.
519
-
520
- ### contentRender.js
521
-
522
- **`onRenderChatMessage(params)`** - Custom message rendering. Key params:
523
- - `msgIndex`, `messages`, `setMessages` - message context
524
- - `setSystemAlert({ severity, message })` - show alerts (severity: 'success', 'error', 'warning', 'info')
525
- - `setBlockingLoading(bool)` - loading overlay
526
- - `RequestChatAPI(messages)` - send chat messages
527
- - `kbUserData()`, `generateMsgId()` - user info and ID generation
528
- - `markdownHandler`, `theme` - rendering utilities
529
-
530
- Return: React component, `null` for default, `JSON.stringify({ type: 'HIDDEN_MESSAGE' })` to hide.
531
-
532
- **`Header(props)`** - Custom header component. Same props plus `openkbs` object.
533
-
534
- ```javascript
535
- import React, { useState, useEffect } from 'react';
536
- import { Box, Button, CircularProgress } from '@mui/material';
537
-
538
- const onRenderChatMessage = async (params) => {
539
- const { content, role } = params.messages[params.msgIndex];
540
- const { msgIndex, messages, setSystemAlert, RequestChatAPI, kbUserData, generateMsgId } = params;
541
-
542
- // Hide system messages
543
- if (role === 'system') return JSON.stringify({ type: 'HIDDEN_MESSAGE' });
544
-
545
- // Custom rendering for commands
546
- if (content.includes('<myCommand>')) {
547
- return <MyComponent content={content} />;
548
- }
549
-
550
- // Send follow-up message example
551
- const sendFollowUp = async () => {
552
- await RequestChatAPI([...messages, {
553
- role: 'user',
554
- content: 'Follow up',
555
- userId: kbUserData().chatUsername,
556
- msgId: generateMsgId()
557
- }]);
558
- };
559
-
560
- return null; // Use default rendering
561
- };
562
-
563
- const Header = ({ setRenderSettings, openkbs, setSystemAlert, setBlockingLoading }) => {
564
- const [loading, setLoading] = useState(false);
565
-
566
- useEffect(() => {
567
- setRenderSettings({
568
- disableEmojiButton: true,
569
- disableBalanceView: false,
570
- backgroundOpacity: 0.02
571
- });
572
- }, [setRenderSettings]);
573
-
574
- return <Box>Custom Header</Box>;
575
- };
576
-
577
- const exports = { onRenderChatMessage, Header };
578
- window.contentRender = exports;
579
- export default exports;
580
- ```
581
-
582
- ### Frontend openkbs Object
583
-
584
- ```javascript
585
- // Item CRUD (auto-encrypted)
586
- await openkbs.createItem({ itemType: 'memory', itemId: 'memory_key', body: { value: 'data' } });
587
- await openkbs.updateItem({ itemType: 'memory', itemId: 'memory_key', body: { value: 'updated' } });
588
- const item = await openkbs.getItem('memory_key');
589
- console.log(item.item.body.value);
590
-
591
- // Fetch with filters
592
- const items = await openkbs.fetchItems({
593
- itemType: 'memory',
594
- beginsWith: 'memory_',
595
- limit: 100
596
- });
597
- items.items.forEach(({ item, meta }) => {
598
- console.log(meta.itemId, item.body);
599
- });
600
-
601
- await openkbs.deleteItem('memory_key');
602
- ```
603
-
604
- ### Files API
605
- ```javascript
606
- // List files in namespace
607
- const files = await openkbs.Files.listFiles('files');
608
- // Returns: [{ Key: 'files/kbId/filename.jpg', Size: 12345, LastModified: '...' }]
609
-
610
- // Upload file with progress
611
- const onProgress = (percent) => console.log(`${percent}% uploaded`);
612
- await openkbs.Files.uploadFileAPI(fileObject, 'files', onProgress);
613
-
614
- // Delete file
615
- await openkbs.Files.deleteRawKBFile('filename.jpg', 'files');
616
-
617
- // Rename file
618
- await openkbs.Files.renameFile('old-path/file.jpg', 'new-path/file.jpg', 'files');
619
-
620
- // File URL pattern
621
- const fileUrl = `https://your-domain.file.vpc1.us/files/${openkbs.kbId}/filename.jpg`;
622
- ```
623
-
624
- ### Sharing API
625
- ```javascript
626
- // Share KB with another user
627
- await openkbs.KBAPI.shareKBWith('user@example.com');
628
-
629
- // Get current shares
630
- const shares = await openkbs.KBAPI.getKBShares();
631
- // Returns: { sharedWith: ['email1@example.com', 'email2@example.com'] }
632
-
633
- // Remove share
634
- await openkbs.KBAPI.unshareKBWith('user@example.com');
635
- ```
636
-
637
- ### Other Frontend Properties
638
- ```javascript
639
- openkbs.kbId // Current KB ID
640
- openkbs.isMobile // Boolean - is mobile device
641
- openkbs.KBData // KB metadata (title, description, etc.)
642
- ```
643
-
644
- ### NPM Dependencies
645
- Add to `contentRender.json`. Built-in (fixed): react, @mui/material, @mui/icons-material, @emotion/react.
646
-
647
- # OpenKBS Commands
648
- - `openkbs create my-agent` - Create new agent
649
- - `openkbs push` - Deploy to cloud
650
- - `openkbs update` - Update knowledge base
651
-
652
- # Development Guidelines
653
- - Backend deps → `onRequest.json`, `onResponse.json`, `onCronjob.json`
654
- - Frontend deps → `contentRender.json`
655
- - Provide README.md for the agent