llmjs2 0.0.2 → 1.0.1

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/LICENSE ADDED
@@ -0,0 +1,21 @@
1
+ MIT License
2
+
3
+ Copyright (c) 2024 littlellmjs
4
+
5
+ Permission is hereby granted, free of charge, to any person obtaining a copy
6
+ of this software and associated documentation files (the "Software"), to deal
7
+ in the Software without restriction, including without limitation the rights
8
+ to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9
+ copies of the Software, and to permit persons to whom the Software is
10
+ furnished to do so, subject to the following conditions:
11
+
12
+ The above copyright notice and this permission notice shall be included in all
13
+ copies or substantial portions of the Software.
14
+
15
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16
+ IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17
+ FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18
+ AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19
+ LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20
+ OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
21
+ SOFTWARE.
package/README.md CHANGED
@@ -1 +1,472 @@
1
- llmjs
1
+ # llmjs2
2
+
3
+ LLM abstraction layer for Node.js. Unified API for multiple LLM providers with error handling and automatic retry logic.
4
+
5
+ **Supported Providers**: Ollama
6
+
7
+ ## Features
8
+
9
+ - 🚀 **Unified API**: Single interface for Ollama provider
10
+ - **Automatic Retries**: Exponential backoff retry logic with configurable parameters
11
+ - ⚙️ **Type-Safe**: Full TypeScript support with comprehensive type definitions
12
+ - 🛡️ **Robust Error Handling**: Custom error types with retryability information
13
+ - 🔍 **Debugging**: Built-in logging and debug mode for troubleshooting
14
+ - 📦 **Zero Dependencies**: Pure Node.js with no external dependencies
15
+ - ✅ **Production-Ready**: Enterprise-grade error handling and validation
16
+
17
+ ## Installation
18
+
19
+ ```bash
20
+ npm install llmjs2
21
+ ```
22
+
23
+ ## Quick Start
24
+
25
+ ### Basic Completion (Ollama)
26
+
27
+ ```javascript
28
+ import { completion } from 'llmjs2';
29
+
30
+ const result = await completion({
31
+ model: 'ollama/mistral',
32
+ baseUrl: 'http://localhost:11434',
33
+ messages: [
34
+ { role: 'system', content: 'You are a helpful assistant.' },
35
+ { role: 'user', content: 'What is TypeScript?' }
36
+ ]
37
+ });
38
+
39
+ console.log(result.content);
40
+ ```
41
+
42
+ ### Using Ollama Locally
43
+
44
+ ```javascript
45
+ import { completion } from 'llmjs2';
46
+
47
+ const result = await completion({
48
+ model: 'ollama/mistral',
49
+ baseUrl: 'http://localhost:11434', // Default Ollama URL
50
+ messages: [
51
+ { role: 'user', content: 'Explain quantum computing' }
52
+ ]
53
+ });
54
+
55
+ console.log(result.content);
56
+ ```
57
+
58
+ ### Using Agent for Stateful Conversations
59
+
60
+ ```javascript
61
+ import { Agent } from 'llmjs2';
62
+
63
+ const agent = new Agent({
64
+ model: 'ollama/qwen3.5:397b-cloud',
65
+ baseUrl: 'https://ollama.com',
66
+ instruction: 'You are a helpful assistant that explains technical concepts.',
67
+ tools: [], // Optional function calling
68
+ });
69
+
70
+ // Generate response (maintains conversation history)
71
+ const result = await agent.generate({
72
+ userPrompt: 'What is TypeScript?',
73
+ images: [],
74
+ references: [],
75
+ context: { role: 'student', level: 'beginner' }
76
+ });
77
+
78
+ console.log(result.response);
79
+
80
+ // Continue conversation (history automatically maintained)
81
+ const followUp = await agent.generate({
82
+ userPrompt: 'Can you give me an example?'
83
+ });
84
+
85
+ console.log(followUp.response);
86
+
87
+ // Stream the response
88
+ const stream = agent.generateStream({
89
+ userPrompt: 'Explain decorators in TypeScript'
90
+ });
91
+
92
+ for await (const chunk of stream) {
93
+ process.stdout.write(chunk.delta);
94
+ }
95
+
96
+ // Manage conversation history
97
+ console.log(agent.getHistory()); // Get all messages
98
+ agent.clearHistory(); // Clear history (keeps system instruction)
99
+ agent.addMessage('system', 'New instruction');
100
+ ```
101
+
102
+ ## API Reference
103
+
104
+ ### `completion(request: CompletionRequest): Promise<CompletionResponse>`
105
+
106
+ Create a completion request. Supports Ollama.
107
+
108
+ **Parameters:**
109
+
110
+ - `model` (string, required): Model identifier
111
+ - Ollama: `ollama/mistral`, `ollama/neural-chat`, `ollama/qwen3.5:397b-cloud`, etc.
112
+
113
+ - `messages` (Message[], required): Array of messages with `role` and `content`
114
+
115
+ - `baseUrl` (string, optional): Custom API endpoint (mainly for Ollama)
116
+
117
+ - `maxTokens` (number, optional): Maximum tokens to generate
118
+
119
+ - `temperature` (number, optional): Sampling temperature (0-2). Higher = more random
120
+
121
+ - `topP` (number, optional): Nucleus sampling parameter (0-1)
122
+
123
+ - `topK` (number, optional): Top-k sampling (Ollama)
124
+
125
+ - `frequencyPenalty` (number, optional): Frequency penalty (-2 to 2)
126
+
127
+ - `presencePenalty` (number, optional): Presence penalty (-2 to 2)
128
+
129
+ - `stop` (string[], optional): Stop sequences
130
+
131
+ - `timeout` (number, optional): Request timeout in milliseconds
132
+
133
+ - `retry` (object, optional): Retry configuration
134
+ - `maxRetries` (number): Maximum retry attempts
135
+ - `backoffMultiplier` (number): Exponential backoff multiplier
136
+ - `initialDelayMs` (number): Initial retry delay
137
+
138
+ **Returns:** `CompletionResponse`
139
+
140
+ ```typescript
141
+ {
142
+ content: string; // Generated text
143
+ model: string; // Model used
144
+ stopReason?: string; // Stop reason
145
+ usage?: { // Token usage (if available)
146
+ promptTokens?: number;
147
+ completionTokens?: number;
148
+ totalTokens?: number;
149
+ };
150
+ raw?: unknown; // Raw provider response
151
+ toolCalls?: Array<{ // Function calls (if any)
152
+ id?: string;
153
+ name: string;
154
+ arguments: Record<string, unknown>;
155
+ }>;
156
+ }
157
+ ```
158
+
159
+ ### `configure(options: CompletionOptions): void`
160
+
161
+ Configure global settings for all completions.
162
+
163
+ ```javascript
164
+ import { configure } from 'llmjs2';
165
+
166
+ configure({
167
+ debug: true, // Enable debug logging
168
+ globalTimeout: 60000, // 60 second default timeout
169
+ globalRetry: {
170
+ maxRetries: 5,
171
+ backoffMultiplier: 2,
172
+ initialDelayMs: 1000
173
+ },
174
+ logger: (level, message, data) => {
175
+ console.log(`[${level}] ${message}`, data);
176
+ }
177
+ });
178
+ ```
179
+
180
+ ### `validateProvider(model: string, apiKey?: string, baseUrl?: string): Promise<void>`
181
+
182
+ Validate that a provider is configured correctly and accessible.
183
+
184
+ ```javascript
185
+ import { validateProvider } from 'llmjs2';
186
+
187
+ try {
188
+ await validateProvider('ollama/mistral', process.env.OLLAMA_CLOUD_API_KEY);
189
+ console.log('Ollama provider is valid');
190
+ } catch (error) {
191
+ console.error('Provider validation failed:', error.message);
192
+ }
193
+ ```
194
+
195
+ ## Agent - Stateful Conversations
196
+
197
+ ### `new Agent(config: AgentConfig): Agent`
198
+
199
+ Create a stateful agent for managing conversations with automatic history tracking.
200
+
201
+ **Configuration:**
202
+
203
+ ```typescript
204
+ interface AgentConfig {
205
+ model: string; // Model identifier (required)
206
+ apiKey?: string; // API key (if needed)
207
+ baseUrl?: string; // Custom endpoint
208
+ instruction?: string; // System instruction/role
209
+ tools?: Tool[]; // Available functions
210
+ maxTokens?: number; // Max response tokens
211
+ temperature?: number; // Sampling temperature
212
+ timeout?: number; // Request timeout
213
+ }
214
+ ```
215
+
216
+ **Methods:**
217
+
218
+ ### `agent.generate(request: AgentGenerateRequest): Promise<AgentGenerateResponse>`
219
+
220
+ Generate a response while maintaining conversation history.
221
+
222
+ **Parameters:**
223
+ - `userPrompt` (string, required): User message
224
+ - `images` (string[], optional): Image data/URLs
225
+ - `references` (string[], optional): Reference documents
226
+ - `context` (Record, optional): Additional context variables
227
+
228
+ **Returns:**
229
+ ```typescript
230
+ {
231
+ response: string; // Generated text
232
+ completion: CompletionResponse; // Full provider response
233
+ toolCalls?: Array<{ // Function calls if any
234
+ name: string;
235
+ arguments: Record<string, unknown>;
236
+ }>;
237
+ }
238
+ ```
239
+
240
+ **Example:**
241
+ ```javascript
242
+ const agent = new Agent({
243
+ model: 'ollama/qwen3.5:397b-cloud',
244
+ baseUrl: 'https://ollama.com',
245
+ instruction: 'You are a coding expert.'
246
+ });
247
+
248
+ const result = await agent.generate({
249
+ userPrompt: 'How do I use async/await?',
250
+ context: { language: 'JavaScript' }
251
+ });
252
+
253
+ console.log(result.response);
254
+ ```
255
+
256
+ ### `agent.getHistory(): Message[]`
257
+
258
+ Get the current conversation history.
259
+
260
+ ```javascript
261
+ const messages = agent.getHistory();
262
+ console.log(messages);
263
+ ```
264
+
265
+ ### `agent.clearHistory(): void`
266
+
267
+ Clear conversation history (system instruction is preserved).
268
+
269
+ ```javascript
270
+ agent.clearHistory();
271
+ ```
272
+
273
+ ### `agent.addMessage(role, content): void`
274
+
275
+ Manually add a message to the history.
276
+
277
+ ```javascript
278
+ agent.addMessage('assistant', 'Custom response');
279
+ agent.addMessage('user', 'Follow-up question');
280
+ ```
281
+
282
+ ### `agent.getConfig(): AgentConfig`
283
+
284
+ Get the current agent configuration.
285
+
286
+ ```javascript
287
+ const config = agent.getConfig();
288
+ ```
289
+
290
+ ## Error Handling
291
+
292
+ All errors are instances of `LLMError` with additional properties:
293
+
294
+ ```typescript
295
+ interface LLMError extends Error {
296
+ code?: string; // Error code
297
+ statusCode?: number; // HTTP status code
298
+ details?: unknown; // Additional error details
299
+ retryable?: boolean; // Whether to retry
300
+ }
301
+ ```
302
+
303
+ **Example:**
304
+
305
+ ```javascript
306
+ import { completion, LLMError } from 'llmjs2';
307
+
308
+ try {
309
+ const result = await completion({
310
+ model: 'ollama/mistral',
311
+ baseUrl: 'http://localhost:11434',
312
+ messages: [{ role: 'user', content: 'Hello' }]
313
+ });
314
+ } catch (error) {
315
+ if (error instanceof LLMError) {
316
+ console.error(`Error [${error.code}]:`, error.message);
317
+
318
+ if (error.retryable) {
319
+ console.log('Error is retryable, will retry...');
320
+ }
321
+ }
322
+ }
323
+ ```
324
+
325
+ ## Advanced Usage
326
+
327
+ ### Function Calling (Ollama + embedded handlers)
328
+
329
+ ```javascript
330
+ import { completion } from 'llmjs2';
331
+
332
+ const result = await completion({
333
+ model: 'ollama/mistral',
334
+ baseUrl: 'http://localhost:11434',
335
+ messages: [
336
+ { role: 'user', content: 'What is the weather in San Francisco?' }
337
+ ],
338
+ tools: [
339
+ {
340
+ name: 'get_weather',
341
+ description: 'Get weather for a location',
342
+ parameters: {
343
+ location: { type: 'string', required: true },
344
+ unit: { type: 'string', enum: ['celsius', 'fahrenheit'] }
345
+ },
346
+ }
347
+ }
348
+ }
349
+ ]
350
+ });
351
+
352
+ if (result.toolCalls) {
353
+ for (const call of result.toolCalls) {
354
+ console.log(`Function: ${call.name}`);
355
+ console.log(`Arguments:`, call.arguments);
356
+ }
357
+ }
358
+ ```
359
+
360
+ ### Custom Request Headers
361
+
362
+ ```javascript
363
+ import { completion } from 'llmjs2';
364
+
365
+ const result = await completion({
366
+ model: 'ollama/mistral',
367
+ baseUrl: 'http://localhost:11434',
368
+ messages: [{ role: 'user', content: 'Hello' }],
369
+ headers: {
370
+ 'X-Custom-Header': 'custom-value'
371
+ }
372
+ });
373
+ ```
374
+
375
+ ### Provider-Specific Configuration
376
+
377
+ For Ollama with custom settings:
378
+ ```javascript
379
+ import { completion } from 'llmjs2';
380
+
381
+ const result = await completion({
382
+ model: 'ollama/mistral',
383
+ baseUrl: 'http://192.168.1.100:11434',
384
+ messages: [
385
+ { role: 'user', content: 'Explain AI' }
386
+ ],
387
+ temperature: 0.7,
388
+ topK: 40,
389
+ topP: 0.9,
390
+ maxTokens: 2048
391
+ });
392
+ ```
393
+
394
+ ## Environment Variables
395
+
396
+ **Ollama:**
397
+ - Ollama reads from local `http://localhost:11434` by default
398
+ - Override with `baseUrl` parameter in request
399
+
400
+ ## Type Definitions
401
+
402
+ Full TypeScript support with comprehensive types:
403
+
404
+ ```typescript
405
+ import type {
406
+ CompletionRequest,
407
+ CompletionResponse,
408
+ CompletionChunk,
409
+ Message,
410
+ MessageRole,
411
+ Tool,
412
+ ProviderType,
413
+ ProviderConfig,
414
+ ProviderError,
415
+ CompletionOptions,
416
+ AgentConfig,
417
+ AgentGenerateRequest,
418
+ AgentGenerateResponse
419
+ } from 'llmjs2';
420
+
421
+ import { Agent } from 'llmjs2';
422
+ ```
423
+
424
+ ## Performance Considerations
425
+
426
+ 1. **Batching**: Batch multiple requests to reduce API calls
427
+ 2. **Caching**: Implement caching for common queries
428
+ 3. **Timeouts**: Configure appropriate timeouts for your use case
429
+ 4. **Retry Logic**: Automatic exponential backoff is built-in and configurable
430
+
431
+ ## Testing
432
+
433
+ ```bash
434
+ # Run tests
435
+ npm test
436
+
437
+ # Run tests in watch mode
438
+ npm run test:watch
439
+ ```
440
+
441
+ ## Building
442
+
443
+ ```bash
444
+ # Build TypeScript to JavaScript
445
+ npm run build
446
+
447
+ # Build in watch mode
448
+ npm run build:watch
449
+
450
+ # Clean build artifacts
451
+ npm run clean
452
+ ```
453
+
454
+ ## License
455
+
456
+ MIT - See LICENSE file for details
457
+
458
+ ## Support
459
+
460
+ - GitHub Issues: [github.com/littlellmjs/llmjs2/issues](https://github.com/littlellmjs/llmjs2/issues)
461
+ - Documentation: Full API reference above
462
+
463
+ ## Changelog
464
+
465
+ ### 1.0.0
466
+ - Initial production release
467
+ - Ollama support
468
+ - Streaming API with async generators
469
+ - Automatic retry with exponential backoff
470
+ - Comprehensive error handling
471
+ - TypeScript 5+ support
472
+ - Zero external dependencies
@@ -0,0 +1,80 @@
1
+ /**
2
+ * Agent - Stateful conversation manager with tool support
3
+ */
4
+ import { CompletionResponse, CompletionChunk, Message, Tool } from './index.js';
5
+ /**
6
+ * Agent configuration
7
+ */
8
+ export interface AgentConfig {
9
+ /** Model identifier (e.g., 'ollama/qwen3.5:397b-cloud') */
10
+ model: string;
11
+ /** API key for the provider (optional, reads from OLLAMA_CLOUD_API_KEY env by default) */
12
+ apiKey?: string;
13
+ /** Base URL for the API (optional, defaults to https://ollama.com) */
14
+ baseUrl?: string;
15
+ /** System instruction for the agent */
16
+ instruction?: string;
17
+ /** Available tools/functions with optional embedded handlers */
18
+ tools?: Tool[];
19
+ /** Tool executor function - receives tool name and arguments (deprecated: use tool.handler instead) */
20
+ toolExecutor?: (toolName: string, args: Record<string, unknown>) => string;
21
+ }
22
+ /**
23
+ * Agent generation request
24
+ */
25
+ export interface AgentGenerateRequest {
26
+ /** User prompt/message */
27
+ userPrompt: string;
28
+ /** Optional images (base64 or URLs) */
29
+ images?: string[];
30
+ /** Optional reference documents or context */
31
+ references?: string[];
32
+ /** Additional context variables */
33
+ context?: Record<string, unknown>;
34
+ }
35
+ /**
36
+ * Agent generation response
37
+ */
38
+ export interface AgentGenerateResponse {
39
+ /** Generated response */
40
+ response: string;
41
+ /** Full completion response from provider */
42
+ completion: CompletionResponse;
43
+ }
44
+ /**
45
+ * Stateful agent for conversations and tool use
46
+ */
47
+ export declare class Agent {
48
+ private config;
49
+ private conversationHistory;
50
+ constructor(config: AgentConfig);
51
+ /**
52
+ * Generate a response for a user message
53
+ */
54
+ generate(request: AgentGenerateRequest): Promise<AgentGenerateResponse>;
55
+ /**
56
+ * Get completion from the model
57
+ */
58
+ private getCompletion;
59
+ /**
60
+ * Stream a response for a user message
61
+ */
62
+ generateStream(request: AgentGenerateRequest): AsyncIterable<CompletionChunk>;
63
+ /**
64
+ * Get conversation history
65
+ */
66
+ getHistory(): Message[];
67
+ /**
68
+ * Clear conversation history (keeps system instruction if set)
69
+ */
70
+ clearHistory(): void;
71
+ /**
72
+ * Add a message to history
73
+ */
74
+ addMessage(role: 'system' | 'user' | 'assistant', content: string): void;
75
+ /**
76
+ * Get the current configuration
77
+ */
78
+ getConfig(): AgentConfig;
79
+ }
80
+ //# sourceMappingURL=agent.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"agent.d.ts","sourceRoot":"","sources":["../src/agent.ts"],"names":[],"mappings":"AAAA;;GAEG;AAEH,OAAO,EAIL,kBAAkB,EAClB,eAAe,EACf,OAAO,EACP,IAAI,EAEL,MAAM,YAAY,CAAC;AAEpB;;GAEG;AACH,MAAM,WAAW,WAAW;IAC1B,2DAA2D;IAC3D,KAAK,EAAE,MAAM,CAAC;IAEd,0FAA0F;IAC1F,MAAM,CAAC,EAAE,MAAM,CAAC;IAEhB,sEAAsE;IACtE,OAAO,CAAC,EAAE,MAAM,CAAC;IAEjB,uCAAuC;IACvC,WAAW,CAAC,EAAE,MAAM,CAAC;IAErB,gEAAgE;IAChE,KAAK,CAAC,EAAE,IAAI,EAAE,CAAC;IAEf,uGAAuG;IACvG,YAAY,CAAC,EAAE,CAAC,QAAQ,EAAE,MAAM,EAAE,IAAI,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,KAAK,MAAM,CAAC;CAC5E;AAED;;GAEG;AACH,MAAM,WAAW,oBAAoB;IACnC,0BAA0B;IAC1B,UAAU,EAAE,MAAM,CAAC;IAEnB,uCAAuC;IACvC,MAAM,CAAC,EAAE,MAAM,EAAE,CAAC;IAElB,8CAA8C;IAC9C,UAAU,CAAC,EAAE,MAAM,EAAE,CAAC;IAEtB,mCAAmC;IACnC,OAAO,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,CAAC;CACnC;AAED;;GAEG;AACH,MAAM,WAAW,qBAAqB;IACpC,yBAAyB;IACzB,QAAQ,EAAE,MAAM,CAAC;IAEjB,6CAA6C;IAC7C,UAAU,EAAE,kBAAkB,CAAC;CAChC;AAED;;GAEG;AACH,qBAAa,KAAK;IAChB,OAAO,CAAC,MAAM,CAAc;IAC5B,OAAO,CAAC,mBAAmB,CAAiB;gBAEhC,MAAM,EAAE,WAAW;IAgB/B;;OAEG;IACG,QAAQ,CAAC,OAAO,EAAE,oBAAoB,GAAG,OAAO,CAAC,qBAAqB,CAAC;IA2F7E;;OAEG;YACW,aAAa;IAY3B;;OAEG;IACI,cAAc,CACnB,OAAO,EAAE,oBAAoB,GAC5B,aAAa,CAAC,eAAe,CAAC;IAoDjC;;OAEG;IACH,UAAU,IAAI,OAAO,EAAE;IAIvB;;OAEG;IACH,YAAY,IAAI,IAAI;IAapB;;OAEG;IACH,UAAU,CAAC,IAAI,EAAE,QAAQ,GAAG,MAAM,GAAG,WAAW,EAAE,OAAO,EAAE,MAAM,GAAG,IAAI;IAOxE;;OAEG;IACH,SAAS,IAAI,WAAW;CAGzB"}