From 06cb13a23fc60c5a8dfd17593de6f08488443b46 Mon Sep 17 00:00:00 2001
From: "mintlify[bot]" <109931778+mintlify[bot]@users.noreply.github.com>
Date: Mon, 6 Apr 2026 00:23:23 +0000
Subject: [PATCH] Deduplicate error handling docs, fix image sizes, add Mistral
vision example
Generated-By: mintlify-agent
---
docs/api/providers/mistral.mdx | 25 ++
docs/concepts/error-handling.mdx | 543 ++++++-------------------------
docs/guides/image-generation.mdx | 26 +-
3 files changed, 142 insertions(+), 452 deletions(-)
diff --git a/docs/api/providers/mistral.mdx b/docs/api/providers/mistral.mdx
index 0a2bb50..d0b56f9 100644
--- a/docs/api/providers/mistral.mdx
+++ b/docs/api/providers/mistral.mdx
@@ -207,6 +207,31 @@ for (const [i, embedding] of result.embeddings.entries()) {
}
```
+### Vision
+
+```typescript
+const result = await generate({
+ model: mistral.chatModel('mistral-small-2506'),
+ messages: [
+ {
+ role: 'user',
+ content: [
+ { type: 'text', text: 'Describe what you see in this image.' },
+ {
+ type: 'image',
+ source: {
+ type: 'url',
+ url: 'https://example.com/photo.jpg',
+ },
+ },
+ ],
+ },
+ ],
+});
+
+console.log(result.content);
+```
+
### Code generation
```typescript
diff --git a/docs/concepts/error-handling.mdx b/docs/concepts/error-handling.mdx
index de155be..586c876 100644
--- a/docs/concepts/error-handling.mdx
+++ b/docs/concepts/error-handling.mdx
@@ -5,146 +5,45 @@ description: CoreAIError, ProviderError, and structured output error types in co
## Overview
-core-ai provides a hierarchy of error types that help you handle failures gracefully. For the complete API surface, see the [errors reference](/api/core/errors).
+core-ai provides a hierarchy of error types that help you handle failures gracefully. All errors extend from `CoreAIError`, letting you catch any library error with a single `instanceof` check or target specific failure types for fine-grained handling.
-## Error Hierarchy
+For complete class definitions and constructor signatures, see the [errors reference](/api/core/errors).
-```typescript
-Error
-└── CoreAIError
- ├── ValidationError
- ├── AbortedError
- │ └── StreamAbortedError
- ├── ProviderError
- └── StructuredOutputError
- ├── StructuredOutputNoObjectGeneratedError
- ├── StructuredOutputParseError
- └── StructuredOutputValidationError
-```
-
-## CoreAIError
-
-Base error class for all core-ai errors.
-
-```typescript
-class CoreAIError extends Error {
- public readonly provider?: string;
- public readonly cause?: unknown;
-
- constructor(message: string, cause?: unknown, provider?: string);
-}
-```
-
-**Usage:**
-
-```typescript
-import { CoreAIError, generate } from '@core-ai/core-ai';
-
-try {
- const result = await generate({
- model,
- messages: [], // Empty messages array
- });
-} catch (error) {
- if (error instanceof CoreAIError) {
- console.error('core-ai error:', error.message);
- if (error.cause) {
- console.error('Caused by:', error.cause);
- }
- }
-}
-```
-
-
- Check for the most specific error types first, then fall back to `CoreAIError` to catch any standardized library error.
-
-
-## ValidationError
-
-Thrown when core-ai rejects invalid caller input or local request configuration before making a provider call.
+## Error hierarchy
-```typescript
-class ValidationError extends CoreAIError {
- constructor(message: string, cause?: unknown, provider?: string);
-}
-```
-
-**When thrown:**
-- Empty messages array
-- Empty input for embeddings
-- Empty prompt for image generation
-- Invalid local request configuration
-
-## AbortedError
-
-Thrown when an operation is cancelled via an `AbortSignal`.
-
-```typescript
-class AbortedError extends CoreAIError {
- constructor(cause?: unknown, provider?: string);
-}
-```
-
-## StreamAbortedError
-
-Thrown when a streaming operation is aborted via an `AbortSignal`.
-
-```typescript
-class StreamAbortedError extends AbortedError {
- constructor(cause?: unknown, provider?: string);
-}
```
-
-**Usage:**
-
-```typescript
-import { stream, StreamAbortedError } from '@core-ai/core-ai';
-
-const controller = new AbortController();
-setTimeout(() => controller.abort(), 5000);
-
-try {
- const chatStream = await stream({
- model,
- messages: [{ role: 'user', content: 'Write a long essay' }],
- signal: controller.signal,
- });
-
- for await (const event of chatStream) {
- if (event.type === 'text-delta') process.stdout.write(event.text);
- }
-} catch (error) {
- if (error instanceof StreamAbortedError) {
- console.log('Stream was cancelled');
- }
-}
+CoreAIError
+├── ValidationError
+├── AbortedError
+│ └── StreamAbortedError
+├── ProviderError
+└── StructuredOutputError
+ ├── StructuredOutputNoObjectGeneratedError
+ ├── StructuredOutputParseError
+ └── StructuredOutputValidationError
```
-
- `StreamAbortedError` applies to an in-flight stream. Validation errors such as empty `messages` throw `ValidationError`.
-
-
-## ProviderError
+| Error | When thrown |
+|-------|-----------|
+| `ValidationError` | Invalid caller input (empty messages, empty embedding input, empty prompt) |
+| `AbortedError` | Operation cancelled via `AbortSignal` |
+| `StreamAbortedError` | Streaming operation cancelled via `AbortSignal` |
+| `ProviderError` | Provider API failures (network errors, rate limits, auth failures) |
+| `StructuredOutputNoObjectGeneratedError` | Model did not produce structured output |
+| `StructuredOutputParseError` | Model output is not valid JSON |
+| `StructuredOutputValidationError` | Model output does not match the Zod schema |
-Error specific to provider API failures (network errors, API errors, rate limits, etc.).
-
-```typescript
-class ProviderError extends CoreAIError {
- public readonly statusCode?: number;
-
- constructor(
- message: string,
- provider: string,
- statusCode?: number,
- cause?: unknown
- );
-}
-```
+## Catching errors
-**Usage:**
+Check for the most specific error types first, then fall back to `CoreAIError`:
```typescript
-import { generate, ProviderError } from '@core-ai/core-ai';
+import {
+ CoreAIError,
+ generate,
+ ProviderError,
+ ValidationError,
+} from '@core-ai/core-ai';
try {
const result = await generate({ model, messages });
@@ -152,249 +51,96 @@ try {
if (error instanceof ProviderError) {
console.error(`Provider: ${error.provider}`);
console.error(`Status: ${error.statusCode}`);
- console.error(`Message: ${error.message}`);
-
- // Handle specific status codes
+
if (error.statusCode === 429) {
console.log('Rate limited - retry with backoff');
} else if (error.statusCode === 401) {
console.log('Authentication failed - check API key');
}
+ } else if (error instanceof ValidationError) {
+ console.error('Invalid input:', error.message);
+ } else if (error instanceof CoreAIError) {
+ console.error('core-ai error:', error.message);
}
}
```
-**Common Status Codes:**
-
-| Code | Meaning | Recommended Action |
-|------|---------|--------------------|
-| 401 | Authentication failed | Check API key |
-| 403 | Forbidden | Check API permissions |
-| 429 | Rate limit exceeded | Implement retry with exponential backoff |
-| 500 | Server error | Retry request |
-| 503 | Service unavailable | Wait and retry |
-
-**When thrown:**
-- Invalid API key
-- Rate limits exceeded
-- Network failures
-- Provider API errors
-- Timeout errors
-
-## Structured Output Errors
-
-Errors specific to structured output generation (`generateObject` and `streamObject`).
-
-### StructuredOutputError
-
-Base class for all structured output errors.
-
-```typescript
-class StructuredOutputError extends CoreAIError {
- public readonly rawOutput?: string;
- public readonly statusCode?: number;
-
- constructor(
- message: string,
- provider: string,
- options: {
- statusCode?: number;
- cause?: unknown;
- rawOutput?: string;
- }
- );
-}
-```
-
-**Properties:**
-- `rawOutput`: The raw text output from the model (if available)
-- `provider`: Which provider was used
-- `statusCode`: HTTP status code (if applicable)
-- `cause`: Underlying error that caused this error
-
-### StructuredOutputNoObjectGeneratedError
+## Handling structured output errors
-Thrown when the model doesn't generate any structured output.
+When using `generateObject()` or `streamObject()`, you may encounter structured output errors in addition to the general error types:
```typescript
-import { generateObject, StructuredOutputNoObjectGeneratedError } from '@core-ai/core-ai';
+import {
+ generateObject,
+ StructuredOutputNoObjectGeneratedError,
+ StructuredOutputParseError,
+ StructuredOutputValidationError,
+} from '@core-ai/core-ai';
import { z } from 'zod';
-const schema = z.object({
- name: z.string(),
- age: z.number(),
-});
-
-try {
- const result = await generateObject({
- model,
- messages: [{ role: 'user', content: 'Hello' }],
- schema,
- });
-} catch (error) {
- if (error instanceof StructuredOutputNoObjectGeneratedError) {
- console.error('Model did not generate structured output');
- console.error('Raw output:', error.rawOutput);
- }
-}
-```
-
-**When thrown:**
-- Model responds with regular text instead of structured output
-- Tool call for structured output was not made
-- Finish reason is not 'stop' or 'tool-calls'
-
-### StructuredOutputParseError
-
-Thrown when the model's output cannot be parsed as JSON.
-
-```typescript
-import { generateObject, StructuredOutputParseError } from '@core-ai/core-ai';
-
try {
const result = await generateObject({
model,
messages: [{ role: 'user', content: 'Generate user data' }],
- schema,
+ schema: z.object({
+ name: z.string(),
+ age: z.number().int().positive(),
+ }),
});
} catch (error) {
- if (error instanceof StructuredOutputParseError) {
- console.error('Failed to parse JSON output');
- console.error('Raw output:', error.rawOutput);
- console.error('Parse error:', error.cause);
+ if (error instanceof StructuredOutputValidationError) {
+ console.error('Schema validation failed');
+ error.issues.forEach((issue) => console.error(`- ${issue}`));
+ } else if (error instanceof StructuredOutputParseError) {
+ console.error('Failed to parse JSON:', error.rawOutput);
+ } else if (error instanceof StructuredOutputNoObjectGeneratedError) {
+ console.error('Model did not generate structured output');
}
}
```
-**When thrown:**
-- Model output is not valid JSON
-- JSON syntax errors in model output
-- Malformed structured output
-
-### StructuredOutputValidationError
+## Handling stream cancellation
-Thrown when the model's output doesn't match the Zod schema.
+Cancel long-running streams with `AbortSignal`:
```typescript
-import { generateObject, StructuredOutputValidationError } from '@core-ai/core-ai';
+import { stream, StreamAbortedError } from '@core-ai/core-ai';
-const schema = z.object({
- name: z.string().min(1),
- age: z.number().int().positive(),
- email: z.string().email(),
-});
+const controller = new AbortController();
+setTimeout(() => controller.abort(), 5000);
try {
- const result = await generateObject({
+ const chatStream = await stream({
model,
- messages: [{ role: 'user', content: 'Generate user data' }],
- schema,
+ messages: [{ role: 'user', content: 'Write a long essay' }],
+ signal: controller.signal,
});
+
+ for await (const event of chatStream) {
+ if (event.type === 'text-delta') process.stdout.write(event.text);
+ }
} catch (error) {
- if (error instanceof StructuredOutputValidationError) {
- console.error('Schema validation failed');
- console.error('Issues:', error.issues);
- console.error('Raw output:', error.rawOutput);
-
- // Display each validation issue
- error.issues.forEach((issue, i) => {
- console.log(`${i + 1}. ${issue}`);
- });
+ if (error instanceof StreamAbortedError) {
+ console.log('Stream was cancelled');
}
}
```
-**Properties:**
-- `issues`: Array of human-readable validation error messages
+## Common status codes
-**When thrown:**
-- Missing required fields
-- Wrong data types
-- Values that don't match schema constraints
-- Invalid enum values
+| Code | Meaning | Recommended action |
+|------|---------|--------------------|
+| 401 | Authentication failed | Check API key |
+| 403 | Forbidden | Check API permissions |
+| 429 | Rate limit exceeded | Retry with exponential backoff |
+| 500 | Server error | Retry request |
+| 503 | Service unavailable | Wait and retry |
-## Complete Error Handling Example
+## Retry with exponential backoff
```typescript
-import {
- CoreAIError,
- generate,
- generateObject,
- ProviderError,
- StructuredOutputError,
- StructuredOutputNoObjectGeneratedError,
- StructuredOutputParseError,
- StructuredOutputValidationError,
-} from '@core-ai/core-ai';
-import { z } from 'zod';
-
-async function generateUserProfile(prompt: string) {
- const schema = z.object({
- name: z.string(),
- age: z.number(),
- email: z.string().email(),
- });
-
- try {
- const result = await generateObject({
- model,
- messages: [{ role: 'user', content: prompt }],
- schema,
- schemaName: 'UserProfile',
- });
-
- return result.object;
- } catch (error) {
- // Handle validation errors - most specific
- if (error instanceof StructuredOutputValidationError) {
- console.error('Schema validation failed:');
- error.issues.forEach(issue => console.error(`- ${issue}`));
- throw new Error('Invalid user profile format');
- }
-
- // Handle parse errors
- if (error instanceof StructuredOutputParseError) {
- console.error('Failed to parse JSON output');
- console.error('Raw output:', error.rawOutput);
- throw new Error('Model returned invalid JSON');
- }
-
- // Handle missing output
- if (error instanceof StructuredOutputNoObjectGeneratedError) {
- console.error('Model did not generate structured output');
- throw new Error('Model did not follow instructions');
- }
-
- // Handle provider errors
- if (error instanceof ProviderError) {
- if (error.statusCode === 429) {
- console.log('Rate limited - implementing retry...');
- await new Promise(resolve => setTimeout(resolve, 5000));
- return generateUserProfile(prompt); // Retry
- }
-
- console.error(`Provider error (${error.provider}):`, error.message);
- throw new Error('AI service unavailable');
- }
-
- // Handle generic core-ai errors
- if (error instanceof CoreAIError) {
- console.error('core-ai error:', error.message);
- throw new Error('AI request failed');
- }
-
- // Handle unexpected errors
- console.error('Unexpected error:', error);
- throw error;
- }
-}
-```
-
-## Retry Strategies
-
-### Exponential Backoff
+import { generate, ProviderError } from '@core-ai/core-ai';
-```typescript
async function generateWithRetry(
model: ChatModel,
messages: Message[],
@@ -405,137 +151,58 @@ async function generateWithRetry(
return await generate({ model, messages });
} catch (error) {
if (error instanceof ProviderError && error.statusCode === 429) {
- const delay = Math.pow(2, attempt) * 1000; // 1s, 2s, 4s
+ const delay = Math.pow(2, attempt) * 1000;
console.log(`Rate limited. Retrying in ${delay}ms...`);
- await new Promise(resolve => setTimeout(resolve, delay));
+ await new Promise((resolve) => setTimeout(resolve, delay));
continue;
}
- throw error; // Don't retry other errors
+ throw error;
}
}
throw new Error('Max retries exceeded');
}
```
-### Circuit Breaker
+## Provider fallback
-```typescript
-class CircuitBreaker {
- private failures = 0;
- private lastFailureTime = 0;
- private readonly threshold = 5;
- private readonly timeout = 60000; // 1 minute
-
- async execute(fn: () => Promise): Promise {
- if (this.isOpen()) {
- throw new Error('Circuit breaker is open');
- }
+Fall back to a different provider when the primary one fails:
- try {
- const result = await fn();
- this.onSuccess();
- return result;
- } catch (error) {
- this.onFailure();
- throw error;
- }
- }
+```typescript
+import { generate, ProviderError } from '@core-ai/core-ai';
- private isOpen(): boolean {
- if (this.failures >= this.threshold) {
- const timeSinceLastFailure = Date.now() - this.lastFailureTime;
- return timeSinceLastFailure < this.timeout;
+async function generateWithFallback(
+ primaryModel: ChatModel,
+ fallbackModel: ChatModel,
+ messages: Message[]
+) {
+ try {
+ return await generate({ model: primaryModel, messages });
+ } catch (error) {
+ if (error instanceof ProviderError) {
+ console.warn('Primary model failed, using fallback');
+ return await generate({ model: fallbackModel, messages });
}
- return false;
- }
-
- private onSuccess() {
- this.failures = 0;
- }
-
- private onFailure() {
- this.failures++;
- this.lastFailureTime = Date.now();
+ throw error;
}
}
-
-const breaker = new CircuitBreaker();
-
-const result = await breaker.execute(() =>
- generate({ model, messages })
-);
```
-## Validation Best Practices
+## Best practices
- **Validate inputs before sending:** Check for empty messages, validate file sizes, and ensure proper content types before making API calls to avoid unnecessary errors.
+ Check for the most specific error types first, then fall back to `CoreAIError` to catch any standardized library error.
-```typescript
-function validateMessages(messages: Message[]): void {
- if (messages.length === 0) {
- throw new ValidationError('messages must not be empty');
- }
-
- for (const message of messages) {
- if (message.role === 'user' && typeof message.content === 'string') {
- if (message.content.trim().length === 0) {
- throw new ValidationError('user message content must not be empty');
- }
- }
- }
-}
-```
-
-## Logging Errors
+
+ Don't retry `StructuredOutputValidationError` — it indicates a schema mismatch that won't resolve by retrying.
+
- **Log error details for debugging:** Include provider, model, status codes, and raw output when available to help diagnose issues.
+ Log error details including `provider`, `statusCode`, and `rawOutput` for debugging. See the [errors reference](/api/core/errors) for all available properties.
-```typescript
-import { ProviderError } from '@core-ai/core-ai';
-
-function logError(error: unknown, context: Record) {
- const errorInfo: Record = {
- ...context,
- message: error instanceof Error ? error.message : String(error),
- name: error instanceof Error ? error.name : 'Unknown',
- };
-
- if (error instanceof ProviderError) {
- errorInfo.provider = error.provider;
- errorInfo.statusCode = error.statusCode;
- }
-
- if (error instanceof StructuredOutputError) {
- errorInfo.rawOutput = error.rawOutput;
- }
-
- if (error instanceof StructuredOutputValidationError) {
- errorInfo.validationIssues = error.issues;
- }
-
- console.error('AI Error:', JSON.stringify(errorInfo, null, 2));
-}
-
-// Usage
-try {
- const result = await generate({ model, messages });
-} catch (error) {
- logError(error, {
- operation: 'generate',
- model: model.modelId,
- provider: model.provider,
- messageCount: messages.length,
- });
- throw error;
-}
-```
-
-## Next Steps
+## Next steps
+- See the full [errors reference](/api/core/errors) for class definitions and constructor signatures
- Learn about [Providers](/concepts/providers) for provider-specific behavior
-- Explore [Configuration](/concepts/configuration) for controlling generation
-- Understand [Messages](/concepts/messages) for building conversations
\ No newline at end of file
+- Configure models with [Configuration](/concepts/configuration) options
diff --git a/docs/guides/image-generation.mdx b/docs/guides/image-generation.mdx
index dea5c82..05c240e 100644
--- a/docs/guides/image-generation.mdx
+++ b/docs/guides/image-generation.mdx
@@ -53,9 +53,7 @@ const result = await generateImage({
Available sizes depend on the provider and model. Common sizes include:
- - `256x256`
- - `512x512`
- - `1024x1024`
+ - `1024x1024` (square)
- `1792x1024` (landscape)
- `1024x1792` (portrait)
@@ -85,7 +83,7 @@ const result = await generateImage({
model,
prompt: 'A minimalist logo for a tech startup',
n: 4, // Generate 4 variations
- size: '512x512',
+ size: '1024x1024',
});
console.log(`Generated ${result.images.length} images`);
@@ -373,7 +371,7 @@ const result = await generateImage({
`clean design, professional, vector style, ` +
`white background, high contrast`,
n: 3,
- size: '512x512',
+ size: '1024x1024',
});
return result.images;
@@ -466,21 +464,21 @@ const result = await generateImage({
- Smaller sizes are faster and cheaper:
+ Choose the right aspect ratio for your content:
```typescript
- // Thumbnail: use smaller size
- const thumbnail = await generateImage({
+ // Square: icons, logos, social media
+ const square = await generateImage({
model,
- prompt: 'icon design',
- size: '256x256',
+ prompt: 'a centered logo design',
+ size: '1024x1024',
});
- // High quality print: use larger size
- const print = await generateImage({
+ // Landscape: banners, headers, scenic images
+ const landscape = await generateImage({
model,
- prompt: 'artwork',
- size: '1024x1024',
+ prompt: 'a wide panoramic landscape',
+ size: '1792x1024',
});
```