novelai-image-sdk 1.0.0 → 1.1.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/dist/index.cjs +58 -4
- package/dist/index.cjs.map +1 -1
- package/dist/index.d.cts +44 -2
- package/dist/index.d.ts +44 -2
- package/dist/index.js +58 -5
- package/dist/index.js.map +1 -1
- package/package.json +2 -2
package/dist/index.cjs
CHANGED
|
@@ -291,6 +291,16 @@ function validateSeed(seed) {
|
|
|
291
291
|
throw new ValidationError(`Seed must be between 0 and 2^32-1, got ${seed}`);
|
|
292
292
|
}
|
|
293
293
|
}
|
|
294
|
+
function checkPromptLength(prompt, limit = 2e3) {
|
|
295
|
+
const length = prompt.length;
|
|
296
|
+
const isWarning = length > limit;
|
|
297
|
+
return {
|
|
298
|
+
isWarning,
|
|
299
|
+
message: isWarning ? `Prompt length (${length} chars) exceeds recommended limit of ${limit}. This may cause truncation or unexpected results.` : void 0,
|
|
300
|
+
length,
|
|
301
|
+
limit
|
|
302
|
+
};
|
|
303
|
+
}
|
|
294
304
|
|
|
295
305
|
// src/builder/ImageRequestBuilder.ts
|
|
296
306
|
var ImageRequestBuilder = class {
|
|
@@ -302,14 +312,17 @@ var ImageRequestBuilder = class {
|
|
|
302
312
|
this.prompt = "";
|
|
303
313
|
this.characterPrompts = [];
|
|
304
314
|
this.negativePrompt = "";
|
|
315
|
+
this.characterNegativePrompts = [];
|
|
305
316
|
this.seed = Math.floor(Math.random() * 4294967295);
|
|
306
317
|
this.steps = 23;
|
|
307
318
|
this.scale = 5;
|
|
319
|
+
this.nSamples = 1;
|
|
308
320
|
this.sampler = "k_euler_ancestral" /* EulerAncestral */;
|
|
309
321
|
this.ucPreset = 0 /* Heavy */;
|
|
310
322
|
this.qualityToggle = true;
|
|
311
323
|
this.smea = false;
|
|
312
324
|
this.smeaDyn = false;
|
|
325
|
+
this.dynamicThresholding = false;
|
|
313
326
|
this.noiseSchedule = "karras" /* Karras */;
|
|
314
327
|
this.client = client;
|
|
315
328
|
}
|
|
@@ -350,9 +363,21 @@ var ImageRequestBuilder = class {
|
|
|
350
363
|
}
|
|
351
364
|
/**
|
|
352
365
|
* Set the negative prompt (what to avoid in generation)
|
|
366
|
+
* Optionally provide per-character negative prompts
|
|
367
|
+
*/
|
|
368
|
+
setNegativePrompt(base, characterNegatives) {
|
|
369
|
+
this.negativePrompt = base;
|
|
370
|
+
if (characterNegatives) {
|
|
371
|
+
this.characterNegativePrompts = characterNegatives;
|
|
372
|
+
}
|
|
373
|
+
return this;
|
|
374
|
+
}
|
|
375
|
+
/**
|
|
376
|
+
* Add a per-character negative prompt
|
|
377
|
+
* Should correspond to character prompts added via addCharacter()
|
|
353
378
|
*/
|
|
354
|
-
|
|
355
|
-
this.negativePrompt
|
|
379
|
+
addCharacterNegative(negativePrompt) {
|
|
380
|
+
this.characterNegativePrompts.push(negativePrompt);
|
|
356
381
|
return this;
|
|
357
382
|
}
|
|
358
383
|
/**
|
|
@@ -381,6 +406,18 @@ var ImageRequestBuilder = class {
|
|
|
381
406
|
this.scale = scale;
|
|
382
407
|
return this;
|
|
383
408
|
}
|
|
409
|
+
/**
|
|
410
|
+
* Set the number of images to generate in a single request
|
|
411
|
+
* Note: Each additional sample consumes Anlas credits
|
|
412
|
+
* @param count - Number of images (1-4 typically supported)
|
|
413
|
+
*/
|
|
414
|
+
setBatchSize(count) {
|
|
415
|
+
if (!Number.isInteger(count) || count < 1) {
|
|
416
|
+
throw new Error("Batch size must be a positive integer");
|
|
417
|
+
}
|
|
418
|
+
this.nSamples = count;
|
|
419
|
+
return this;
|
|
420
|
+
}
|
|
384
421
|
/**
|
|
385
422
|
* Set the sampling algorithm
|
|
386
423
|
*/
|
|
@@ -426,6 +463,21 @@ var ImageRequestBuilder = class {
|
|
|
426
463
|
this.noiseSchedule = schedule;
|
|
427
464
|
return this;
|
|
428
465
|
}
|
|
466
|
+
/**
|
|
467
|
+
* Enable dynamic thresholding
|
|
468
|
+
* Enhances contrast at high CFG scales (scale > 7)
|
|
469
|
+
*/
|
|
470
|
+
enableDynamicThresholding() {
|
|
471
|
+
this.dynamicThresholding = true;
|
|
472
|
+
return this;
|
|
473
|
+
}
|
|
474
|
+
/**
|
|
475
|
+
* Disable dynamic thresholding
|
|
476
|
+
*/
|
|
477
|
+
disableDynamicThresholding() {
|
|
478
|
+
this.dynamicThresholding = false;
|
|
479
|
+
return this;
|
|
480
|
+
}
|
|
429
481
|
/**
|
|
430
482
|
* Build the V4 condition input structure for prompts
|
|
431
483
|
*/
|
|
@@ -460,12 +512,12 @@ var ImageRequestBuilder = class {
|
|
|
460
512
|
scale: this.scale,
|
|
461
513
|
sampler: this.sampler,
|
|
462
514
|
steps: this.steps,
|
|
463
|
-
n_samples:
|
|
515
|
+
n_samples: this.nSamples,
|
|
464
516
|
seed: this.seed,
|
|
465
517
|
negative_prompt: this.negativePrompt,
|
|
466
518
|
// V4-specific structured prompts
|
|
467
519
|
v4_prompt: this.buildV4ConditionInput(this.prompt, this.characterPrompts),
|
|
468
|
-
v4_negative_prompt: this.buildV4ConditionInput(this.negativePrompt,
|
|
520
|
+
v4_negative_prompt: this.buildV4ConditionInput(this.negativePrompt, this.characterNegativePrompts),
|
|
469
521
|
// Quality and preset controls (camelCase - API requirement)
|
|
470
522
|
qualityToggle: this.qualityToggle,
|
|
471
523
|
ucPreset: this.ucPreset,
|
|
@@ -474,6 +526,7 @@ var ImageRequestBuilder = class {
|
|
|
474
526
|
noise_schedule: this.noiseSchedule,
|
|
475
527
|
sm: this.smea,
|
|
476
528
|
sm_dyn: this.smeaDyn,
|
|
529
|
+
dynamic_thresholding: this.dynamicThresholding,
|
|
477
530
|
prefer_brownian: true,
|
|
478
531
|
deliberate_euler_ancestral_bug: true,
|
|
479
532
|
legacy: false,
|
|
@@ -540,6 +593,7 @@ exports.NovelAISampler = NovelAISampler;
|
|
|
540
593
|
exports.NovelAIServerError = NovelAIServerError;
|
|
541
594
|
exports.NovelAIValidationError = NovelAIValidationError;
|
|
542
595
|
exports.UCPreset = UCPreset;
|
|
596
|
+
exports.checkPromptLength = checkPromptLength;
|
|
543
597
|
exports.toBase64 = toBase64;
|
|
544
598
|
exports.toDataURL = toDataURL;
|
|
545
599
|
exports.validateResolution = validateResolution;
|
package/dist/index.cjs.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"sources":["../src/errors/index.ts","../src/utils/ZipParser.ts","../src/network/APIClient.ts","../src/types/Model.ts","../src/types/Sampler.ts","../src/utils/Validators.ts","../src/builder/ImageRequestBuilder.ts","../src/client/NovelAIClient.ts"],"names":["NovelAIModel","NovelAISampler","UCPreset","NoiseSchedule"],"mappings":"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","file":"index.cjs","sourcesContent":["/**\n * Base error class for all NovelAI SDK errors\n */\nexport class NovelAIError extends Error {\n public readonly statusCode?: number;\n\n constructor(message: string, statusCode?: number) {\n super(message);\n this.name = 'NovelAIError';\n this.statusCode = statusCode;\n }\n}\n\n/**\n * Authentication error (401/403)\n * Thrown when the API token is invalid or expired\n */\nexport class NovelAIAuthError extends NovelAIError {\n constructor(message = 'Authentication failed. Check your Persistent API Token (pst-...).') {\n super(message, 401);\n this.name = 'NovelAIAuthError';\n }\n}\n\n/**\n * Payment required error (402)\n * Thrown when the user has insufficient Anlas credits\n */\nexport class NovelAIPaymentError extends NovelAIError {\n constructor(message = 'Insufficient Anlas credits for this generation.') {\n super(message, 402);\n this.name = 'NovelAIPaymentError';\n }\n}\n\n/**\n * Validation error (400)\n * Thrown when the API rejects the payload due to schema issues\n */\nexport class NovelAIValidationError extends NovelAIError {\n public readonly details?: string;\n\n constructor(message: string, details?: string) {\n super(message, 400);\n this.name = 'NovelAIValidationError';\n this.details = details;\n }\n}\n\n/**\n * Network error\n * Thrown on timeouts, connection failures, or other network issues\n */\nexport class NovelAINetworkError extends NovelAIError {\n public readonly cause?: Error;\n\n constructor(message: string, cause?: Error) {\n super(message);\n this.name = 'NovelAINetworkError';\n this.cause = cause;\n }\n}\n\n/**\n * Rate limit error (429)\n * Thrown when too many requests are made\n */\nexport class NovelAIRateLimitError extends NovelAIError {\n public readonly retryAfter?: number;\n\n constructor(message = 'Rate limit exceeded. Please wait before retrying.', retryAfter?: number) {\n super(message, 429);\n this.name = 'NovelAIRateLimitError';\n this.retryAfter = retryAfter;\n }\n}\n\n/**\n * Server error (500+)\n * Thrown when the NovelAI server encounters an internal error\n */\nexport class NovelAIServerError extends NovelAIError {\n public readonly correlationId?: string;\n\n constructor(message = 'NovelAI server error. This may be due to payload schema issues.', correlationId?: string) {\n super(message, 500);\n this.name = 'NovelAIServerError';\n this.correlationId = correlationId;\n }\n}\n","/**\n * Isomorphic ZIP parser that works in both Node.js and browser environments\n * Extracts PNG files from NovelAI's application/x-zip-compressed response\n */\n\n/**\n * Detects if we're running in a Node.js environment\n */\nfunction isNodeEnvironment(): boolean {\n return (\n typeof process !== 'undefined' &&\n process.versions != null &&\n process.versions.node != null\n );\n}\n\n/**\n * Extract PNG files from a ZIP archive buffer\n * @param data - The raw ZIP archive data\n * @returns Array of extracted PNG file contents\n */\nexport async function extractImagesFromZip(\n data: ArrayBuffer | Uint8Array\n): Promise<Uint8Array[]> {\n const buffer = data instanceof ArrayBuffer ? new Uint8Array(data) : data;\n\n if (isNodeEnvironment()) {\n return extractWithAdmZip(buffer);\n } else {\n return extractWithFflate(buffer);\n }\n}\n\n/**\n * Node.js extraction using adm-zip\n */\nasync function extractWithAdmZip(buffer: Uint8Array): Promise<Uint8Array[]> {\n // Dynamic import for Node.js environment\n const AdmZip = (await import('adm-zip')).default;\n const zip = new AdmZip(Buffer.from(buffer));\n const entries = zip.getEntries();\n const images: Uint8Array[] = [];\n\n for (const entry of entries) {\n if (entry.entryName.endsWith('.png') && !entry.isDirectory) {\n const data = entry.getData();\n images.push(new Uint8Array(data));\n }\n }\n\n return images;\n}\n\n/**\n * Browser extraction using fflate\n */\nasync function extractWithFflate(buffer: Uint8Array): Promise<Uint8Array[]> {\n // Dynamic import for browser environment\n const { unzipSync } = await import('fflate');\n const unzipped = unzipSync(buffer);\n const images: Uint8Array[] = [];\n\n for (const [filename, data] of Object.entries(unzipped)) {\n if (filename.endsWith('.png')) {\n images.push(data);\n }\n }\n\n return images;\n}\n\n/**\n * Convert Uint8Array to Base64 string (useful for browser display)\n */\nexport function toBase64(data: Uint8Array): string {\n if (isNodeEnvironment()) {\n return Buffer.from(data).toString('base64');\n } else {\n // Browser environment\n let binary = '';\n for (let i = 0; i < data.length; i++) {\n binary += String.fromCharCode(data[i]);\n }\n return btoa(binary);\n }\n}\n\n/**\n * Convert Uint8Array to data URL for direct use in img src\n */\nexport function toDataURL(data: Uint8Array, mimeType = 'image/png'): string {\n return `data:${mimeType};base64,${toBase64(data)}`;\n}\n","import type { GenerateImagePayload, ImageResponse, APIErrorResponse } from '../types';\nimport {\n NovelAIError,\n NovelAIAuthError,\n NovelAIPaymentError,\n NovelAIValidationError,\n NovelAINetworkError,\n NovelAIRateLimitError,\n NovelAIServerError,\n} from '../errors';\nimport { extractImagesFromZip } from '../utils/ZipParser';\n\nconst DEFAULT_BASE_URL = 'https://image.novelai.net';\nconst DEFAULT_TIMEOUT = 60000;\nconst GENERATE_ENDPOINT = '/ai/generate-image';\n\nexport interface APIClientConfig {\n token: string;\n baseUrl?: string;\n timeout?: number;\n}\n\n/**\n * Low-level HTTP client for NovelAI API\n * Handles authentication, binary response parsing, and error mapping\n */\nexport class APIClient {\n private readonly token: string;\n private readonly baseUrl: string;\n private readonly timeout: number;\n\n constructor(config: APIClientConfig) {\n this.token = config.token;\n this.baseUrl = config.baseUrl ?? DEFAULT_BASE_URL;\n this.timeout = config.timeout ?? DEFAULT_TIMEOUT;\n }\n\n /**\n * Generate an image using the NovelAI API\n */\n async generateImage(payload: GenerateImagePayload): Promise<ImageResponse> {\n const url = `${this.baseUrl}${GENERATE_ENDPOINT}`;\n\n // Generate correlation ID for debugging\n const correlationId = this.generateCorrelationId();\n\n const controller = new AbortController();\n const timeoutId = setTimeout(() => controller.abort(), this.timeout);\n\n try {\n const response = await fetch(url, {\n method: 'POST',\n headers: {\n 'Authorization': `Bearer ${this.token}`,\n 'Content-Type': 'application/json',\n 'Accept': 'application/x-zip-compressed, application/json',\n 'x-correlation-id': correlationId,\n },\n body: JSON.stringify(payload),\n signal: controller.signal,\n });\n\n clearTimeout(timeoutId);\n\n if (!response.ok) {\n await this.handleErrorResponse(response, correlationId);\n }\n\n // Parse the ZIP response\n const arrayBuffer = await response.arrayBuffer();\n const images = await extractImagesFromZip(arrayBuffer);\n\n return {\n images,\n metadata: {\n seed: payload.parameters.seed,\n prompt: payload.input,\n model: payload.model,\n sampler: payload.parameters.sampler as string,\n steps: payload.parameters.steps,\n scale: payload.parameters.scale,\n },\n };\n } catch (error) {\n clearTimeout(timeoutId);\n\n if (error instanceof NovelAIError) {\n throw error;\n }\n\n if (error instanceof Error) {\n if (error.name === 'AbortError') {\n throw new NovelAINetworkError(`Request timed out after ${this.timeout}ms`, error);\n }\n throw new NovelAINetworkError(`Network error: ${error.message}`, error);\n }\n\n throw new NovelAINetworkError('An unknown error occurred');\n }\n }\n\n /**\n * Handle non-2xx responses and throw appropriate errors\n */\n private async handleErrorResponse(response: Response, correlationId: string): Promise<never> {\n let errorBody: APIErrorResponse | null = null;\n\n try {\n errorBody = await response.json() as APIErrorResponse;\n } catch {\n // Response may not be JSON\n }\n\n const message = errorBody?.message ?? errorBody?.error ?? response.statusText;\n\n switch (response.status) {\n case 400:\n throw new NovelAIValidationError(\n `Bad request: ${message}`,\n JSON.stringify(errorBody)\n );\n case 401:\n case 403:\n throw new NovelAIAuthError(message);\n case 402:\n throw new NovelAIPaymentError(message);\n case 429: {\n const retryAfter = response.headers.get('retry-after');\n throw new NovelAIRateLimitError(message, retryAfter ? parseInt(retryAfter) : undefined);\n }\n case 500:\n case 502:\n case 503:\n case 504:\n throw new NovelAIServerError(\n `Server error (${response.status}): ${message}. This may be caused by payload schema issues.`,\n correlationId\n );\n default:\n throw new NovelAIError(\n `HTTP ${response.status}: ${message}`,\n response.status\n );\n }\n }\n\n /**\n * Generate a 6-character alphanumeric correlation ID for debugging\n */\n private generateCorrelationId(): string {\n const chars = 'ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789';\n let result = '';\n for (let i = 0; i < 6; i++) {\n result += chars.charAt(Math.floor(Math.random() * chars.length));\n }\n return result;\n }\n}\n","/**\n * Supported NovelAI image generation models\n */\nexport enum NovelAIModel {\n /** V4.5 Full - Latest model with T5 encoding and multi-character support */\n V45_Full = \"nai-diffusion-4-5-full\",\n /** V4 Curated - More conservative aesthetic choices */\n V4_Curated = \"nai-diffusion-4-curated\",\n /** V4 Inpainting - For image editing and inpainting tasks */\n Inpainting = \"nai-diffusion-4-inpainting\",\n}\n","/**\n * Supported sampling algorithms for image generation\n */\nexport enum NovelAISampler {\n /** Standard Euler sampler */\n Euler = \"k_euler\",\n /** Euler Ancestral - recommended for anime-style generations */\n EulerAncestral = \"k_euler_ancestral\",\n /** DPM++ 2M - stable and aesthetic */\n DPM_2M = \"k_dpmpp_2m\",\n /** DPM++ 2S Ancestral */\n DPM_2S_Ancestral = \"k_dpmpp_2s_ancestral\",\n /** DPM++ SDE */\n DPM_SDE = \"k_dpmpp_sde\",\n /** DDIM V3 */\n DDIM = \"ddim_v3\",\n}\n\n/**\n * Preset negative prompt configurations\n */\nexport enum UCPreset {\n /** Heavy - Low Quality + Bad Anatomy */\n Heavy = 0,\n /** Light - Low Quality only */\n Light = 1,\n /** None - Use custom negative prompt only */\n None = 2,\n}\n\n/**\n * Noise schedule algorithms\n */\nexport enum NoiseSchedule {\n Native = \"native\",\n Karras = \"karras\",\n Exponential = \"exponential\",\n Polyexponential = \"polyexponential\",\n}\n","/**\n * Validation error for invalid SDK parameters\n */\nexport class ValidationError extends Error {\n constructor(message: string) {\n super(message);\n this.name = 'ValidationError';\n }\n}\n\n/**\n * Validates that image dimensions are multiples of 64\n * @throws ValidationError if dimensions are invalid\n */\nexport function validateResolution(width: number, height: number): void {\n if (!Number.isInteger(width) || !Number.isInteger(height)) {\n throw new ValidationError('Width and height must be integers');\n }\n if (width <= 0 || height <= 0) {\n throw new ValidationError('Width and height must be positive');\n }\n if (width % 64 !== 0) {\n throw new ValidationError(`Width must be a multiple of 64, got ${width}`);\n }\n if (height % 64 !== 0) {\n throw new ValidationError(`Height must be a multiple of 64, got ${height}`);\n }\n}\n\n/**\n * Validates that step count is within acceptable range\n * @throws ValidationError if steps are out of range\n */\nexport function validateSteps(steps: number): void {\n if (!Number.isInteger(steps)) {\n throw new ValidationError('Steps must be an integer');\n }\n if (steps < 1 || steps > 50) {\n throw new ValidationError(`Steps must be between 1 and 50, got ${steps}`);\n }\n}\n\n/**\n * Validates that scale (CFG) is within acceptable range\n * @throws ValidationError if scale is out of range\n */\nexport function validateScale(scale: number): void {\n if (typeof scale !== 'number' || isNaN(scale)) {\n throw new ValidationError('Scale must be a number');\n }\n if (scale < 0 || scale > 10) {\n throw new ValidationError(`Scale must be between 0 and 10, got ${scale}`);\n }\n}\n\n/**\n * Validates that seed is a valid unsigned 32-bit integer\n */\nexport function validateSeed(seed: number): void {\n if (!Number.isInteger(seed)) {\n throw new ValidationError('Seed must be an integer');\n }\n if (seed < 0 || seed > 4294967295) {\n throw new ValidationError(`Seed must be between 0 and 2^32-1, got ${seed}`);\n }\n}\n","import type { NovelAIClient } from '../client/NovelAIClient';\nimport type {\n GenerateImagePayload,\n NovelAIParameters,\n V4ConditionInput,\n ImageResponse,\n} from '../types';\nimport { NovelAIModel, NovelAISampler, UCPreset, NoiseSchedule } from '../types';\nimport { validateResolution, validateSteps, validateScale, validateSeed } from '../utils/Validators';\n\n/**\n * Fluent builder for constructing NovelAI image generation requests\n * Provides method chaining and compile-time type safety\n */\nexport class ImageRequestBuilder {\n private client: NovelAIClient;\n\n // Core parameters with sensible defaults\n private model: NovelAIModel = NovelAIModel.V45_Full;\n private width = 832;\n private height = 1216;\n private prompt = '';\n private characterPrompts: string[] = [];\n private negativePrompt = '';\n private seed: number = Math.floor(Math.random() * 4294967295);\n private steps = 23;\n private scale = 5.0;\n private sampler: NovelAISampler = NovelAISampler.EulerAncestral;\n private ucPreset: UCPreset = UCPreset.Heavy;\n private qualityToggle = true;\n private smea = false;\n private smeaDyn = false;\n private noiseSchedule: NoiseSchedule = NoiseSchedule.Karras;\n\n constructor(client: NovelAIClient) {\n this.client = client;\n }\n\n /**\n * Set the model to use for generation\n */\n setModel(model: NovelAIModel): this {\n this.model = model;\n return this;\n }\n\n /**\n * Set the output image dimensions\n * @throws ValidationError if dimensions are not multiples of 64\n */\n setSize(width: number, height: number): this {\n validateResolution(width, height);\n this.width = width;\n this.height = height;\n return this;\n }\n\n /**\n * Set the main prompt (base scene description)\n * For multi-character prompts, use the array overload\n */\n setPrompt(base: string, characters?: string[]): this {\n this.prompt = base;\n if (characters) {\n this.characterPrompts = characters;\n }\n return this;\n }\n\n /**\n * Add character prompts for multi-character scenes\n */\n addCharacter(characterPrompt: string): this {\n this.characterPrompts.push(characterPrompt);\n return this;\n }\n\n /**\n * Set the negative prompt (what to avoid in generation)\n */\n setNegativePrompt(negative: string): this {\n this.negativePrompt = negative;\n return this;\n }\n\n /**\n * Set the random seed for reproducible generations\n */\n setSeed(seed: number): this {\n validateSeed(seed);\n this.seed = seed;\n return this;\n }\n\n /**\n * Set the number of sampling steps\n * @throws ValidationError if steps are out of range (1-50)\n */\n setSteps(steps: number): this {\n validateSteps(steps);\n this.steps = steps;\n return this;\n }\n\n /**\n * Set the guidance scale (CFG)\n * @throws ValidationError if scale is out of range (0-10)\n */\n setScale(scale: number): this {\n validateScale(scale);\n this.scale = scale;\n return this;\n }\n\n /**\n * Set the sampling algorithm\n */\n setSampler(sampler: NovelAISampler): this {\n this.sampler = sampler;\n return this;\n }\n\n /**\n * Set the UC preset (predefined negative prompt configuration)\n */\n setUCPreset(preset: UCPreset): this {\n this.ucPreset = preset;\n return this;\n }\n\n /**\n * Toggle automatic quality tags insertion\n */\n setQualityToggle(enabled: boolean): this {\n this.qualityToggle = enabled;\n return this;\n }\n\n /**\n * Enable SMEA (Sinusoidal Multipass Euler Ancestral)\n * @param dynamic - If true, enables dynamic SMEA variant\n */\n enableSMEA(dynamic = false): this {\n this.smea = true;\n this.smeaDyn = dynamic;\n return this;\n }\n\n /**\n * Disable SMEA\n */\n disableSMEA(): this {\n this.smea = false;\n this.smeaDyn = false;\n return this;\n }\n\n /**\n * Set the noise schedule algorithm\n */\n setNoiseSchedule(schedule: NoiseSchedule): this {\n this.noiseSchedule = schedule;\n return this;\n }\n\n /**\n * Build the V4 condition input structure for prompts\n */\n private buildV4ConditionInput(base: string, characters: string[]): V4ConditionInput {\n return {\n caption: {\n base_caption: base,\n char_captions: characters,\n },\n use_coords: false,\n use_order: true,\n legacy_uc: false,\n };\n }\n\n /**\n * Build the formatted input string for the API\n * Combines base prompt with character prompts using pipe delimiter\n */\n private buildInputString(): string {\n if (this.characterPrompts.length === 0) {\n return this.prompt;\n }\n return [this.prompt, ...this.characterPrompts].join(' | ');\n }\n\n /**\n * Build the complete API payload\n */\n buildPayload(): GenerateImagePayload {\n const parameters: NovelAIParameters = {\n width: this.width,\n height: this.height,\n scale: this.scale,\n sampler: this.sampler,\n steps: this.steps,\n n_samples: 1,\n seed: this.seed,\n negative_prompt: this.negativePrompt,\n\n // V4-specific structured prompts\n v4_prompt: this.buildV4ConditionInput(this.prompt, this.characterPrompts),\n v4_negative_prompt: this.buildV4ConditionInput(this.negativePrompt, []),\n\n // Quality and preset controls (camelCase - API requirement)\n qualityToggle: this.qualityToggle,\n ucPreset: this.ucPreset,\n\n // Technical flags (snake_case - API requirement)\n params_version: 3,\n noise_schedule: this.noiseSchedule,\n sm: this.smea,\n sm_dyn: this.smeaDyn,\n prefer_brownian: true,\n deliberate_euler_ancestral_bug: true,\n legacy: false,\n legacy_v3_extend: false,\n };\n\n return {\n input: this.buildInputString(),\n model: this.model,\n action: 'generate',\n parameters,\n };\n }\n\n /**\n * Execute the image generation request\n */\n async generate(): Promise<ImageResponse> {\n const payload = this.buildPayload();\n return this.client._execute(payload);\n }\n}\n","import type { ClientConfig, GenerateImagePayload, ImageResponse } from '../types';\nimport { APIClient } from '../network/APIClient';\nimport { ImageRequestBuilder } from '../builder/ImageRequestBuilder';\n\n/**\n * Main entry point for the NovelAI Image SDK\n * \n * @example\n * ```typescript\n * const client = new NovelAIClient({ token: process.env.NAI_TOKEN });\n * \n * const result = await client.image()\n * .setPrompt('1girl, cyberpunk, neon lights')\n * .setSize(832, 1216)\n * .generate();\n * \n * fs.writeFileSync('output.png', result.images[0]);\n * ```\n */\nexport class NovelAIClient {\n private readonly apiClient: APIClient;\n\n /**\n * Create a new NovelAI client\n * @param config - Client configuration including token and optional base URL\n */\n constructor(config: ClientConfig) {\n if (!config.token) {\n throw new Error('NovelAI API token is required');\n }\n\n this.apiClient = new APIClient({\n token: config.token,\n baseUrl: config.baseUrl,\n timeout: config.timeout,\n });\n }\n\n /**\n * Start building an image generation request\n * @returns A new ImageRequestBuilder instance\n */\n image(): ImageRequestBuilder {\n return new ImageRequestBuilder(this);\n }\n\n /**\n * Execute a generation request (called internally by the builder)\n * @internal\n */\n async _execute(payload: GenerateImagePayload): Promise<ImageResponse> {\n return this.apiClient.generateImage(payload);\n }\n}\n"]}
|
|
1
|
+
{"version":3,"sources":["../src/errors/index.ts","../src/utils/ZipParser.ts","../src/network/APIClient.ts","../src/types/Model.ts","../src/types/Sampler.ts","../src/utils/Validators.ts","../src/builder/ImageRequestBuilder.ts","../src/client/NovelAIClient.ts"],"names":["NovelAIModel","NovelAISampler","UCPreset","NoiseSchedule"],"mappings":"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","file":"index.cjs","sourcesContent":["/**\n * Base error class for all NovelAI SDK errors\n */\nexport class NovelAIError extends Error {\n public readonly statusCode?: number;\n\n constructor(message: string, statusCode?: number) {\n super(message);\n this.name = 'NovelAIError';\n this.statusCode = statusCode;\n }\n}\n\n/**\n * Authentication error (401/403)\n * Thrown when the API token is invalid or expired\n */\nexport class NovelAIAuthError extends NovelAIError {\n constructor(message = 'Authentication failed. Check your Persistent API Token (pst-...).') {\n super(message, 401);\n this.name = 'NovelAIAuthError';\n }\n}\n\n/**\n * Payment required error (402)\n * Thrown when the user has insufficient Anlas credits\n */\nexport class NovelAIPaymentError extends NovelAIError {\n constructor(message = 'Insufficient Anlas credits for this generation.') {\n super(message, 402);\n this.name = 'NovelAIPaymentError';\n }\n}\n\n/**\n * Validation error (400)\n * Thrown when the API rejects the payload due to schema issues\n */\nexport class NovelAIValidationError extends NovelAIError {\n public readonly details?: string;\n\n constructor(message: string, details?: string) {\n super(message, 400);\n this.name = 'NovelAIValidationError';\n this.details = details;\n }\n}\n\n/**\n * Network error\n * Thrown on timeouts, connection failures, or other network issues\n */\nexport class NovelAINetworkError extends NovelAIError {\n public readonly cause?: Error;\n\n constructor(message: string, cause?: Error) {\n super(message);\n this.name = 'NovelAINetworkError';\n this.cause = cause;\n }\n}\n\n/**\n * Rate limit error (429)\n * Thrown when too many requests are made\n */\nexport class NovelAIRateLimitError extends NovelAIError {\n public readonly retryAfter?: number;\n\n constructor(message = 'Rate limit exceeded. Please wait before retrying.', retryAfter?: number) {\n super(message, 429);\n this.name = 'NovelAIRateLimitError';\n this.retryAfter = retryAfter;\n }\n}\n\n/**\n * Server error (500+)\n * Thrown when the NovelAI server encounters an internal error\n */\nexport class NovelAIServerError extends NovelAIError {\n public readonly correlationId?: string;\n\n constructor(message = 'NovelAI server error. This may be due to payload schema issues.', correlationId?: string) {\n super(message, 500);\n this.name = 'NovelAIServerError';\n this.correlationId = correlationId;\n }\n}\n","/**\n * Isomorphic ZIP parser that works in both Node.js and browser environments\n * Extracts PNG files from NovelAI's application/x-zip-compressed response\n */\n\n/**\n * Detects if we're running in a Node.js environment\n */\nfunction isNodeEnvironment(): boolean {\n return (\n typeof process !== 'undefined' &&\n process.versions != null &&\n process.versions.node != null\n );\n}\n\n/**\n * Extract PNG files from a ZIP archive buffer\n * @param data - The raw ZIP archive data\n * @returns Array of extracted PNG file contents\n */\nexport async function extractImagesFromZip(\n data: ArrayBuffer | Uint8Array\n): Promise<Uint8Array[]> {\n const buffer = data instanceof ArrayBuffer ? new Uint8Array(data) : data;\n\n if (isNodeEnvironment()) {\n return extractWithAdmZip(buffer);\n } else {\n return extractWithFflate(buffer);\n }\n}\n\n/**\n * Node.js extraction using adm-zip\n */\nasync function extractWithAdmZip(buffer: Uint8Array): Promise<Uint8Array[]> {\n // Dynamic import for Node.js environment\n const AdmZip = (await import('adm-zip')).default;\n const zip = new AdmZip(Buffer.from(buffer));\n const entries = zip.getEntries();\n const images: Uint8Array[] = [];\n\n for (const entry of entries) {\n if (entry.entryName.endsWith('.png') && !entry.isDirectory) {\n const data = entry.getData();\n images.push(new Uint8Array(data));\n }\n }\n\n return images;\n}\n\n/**\n * Browser extraction using fflate\n */\nasync function extractWithFflate(buffer: Uint8Array): Promise<Uint8Array[]> {\n // Dynamic import for browser environment\n const { unzipSync } = await import('fflate');\n const unzipped = unzipSync(buffer);\n const images: Uint8Array[] = [];\n\n for (const [filename, data] of Object.entries(unzipped)) {\n if (filename.endsWith('.png')) {\n images.push(data);\n }\n }\n\n return images;\n}\n\n/**\n * Convert Uint8Array to Base64 string (useful for browser display)\n */\nexport function toBase64(data: Uint8Array): string {\n if (isNodeEnvironment()) {\n return Buffer.from(data).toString('base64');\n } else {\n // Browser environment\n let binary = '';\n for (let i = 0; i < data.length; i++) {\n binary += String.fromCharCode(data[i]);\n }\n return btoa(binary);\n }\n}\n\n/**\n * Convert Uint8Array to data URL for direct use in img src\n */\nexport function toDataURL(data: Uint8Array, mimeType = 'image/png'): string {\n return `data:${mimeType};base64,${toBase64(data)}`;\n}\n","import type { GenerateImagePayload, ImageResponse, APIErrorResponse } from '../types';\nimport {\n NovelAIError,\n NovelAIAuthError,\n NovelAIPaymentError,\n NovelAIValidationError,\n NovelAINetworkError,\n NovelAIRateLimitError,\n NovelAIServerError,\n} from '../errors';\nimport { extractImagesFromZip } from '../utils/ZipParser';\n\nconst DEFAULT_BASE_URL = 'https://image.novelai.net';\nconst DEFAULT_TIMEOUT = 60000;\nconst GENERATE_ENDPOINT = '/ai/generate-image';\n\nexport interface APIClientConfig {\n token: string;\n baseUrl?: string;\n timeout?: number;\n}\n\n/**\n * Low-level HTTP client for NovelAI API\n * Handles authentication, binary response parsing, and error mapping\n */\nexport class APIClient {\n private readonly token: string;\n private readonly baseUrl: string;\n private readonly timeout: number;\n\n constructor(config: APIClientConfig) {\n this.token = config.token;\n this.baseUrl = config.baseUrl ?? DEFAULT_BASE_URL;\n this.timeout = config.timeout ?? DEFAULT_TIMEOUT;\n }\n\n /**\n * Generate an image using the NovelAI API\n */\n async generateImage(payload: GenerateImagePayload): Promise<ImageResponse> {\n const url = `${this.baseUrl}${GENERATE_ENDPOINT}`;\n\n // Generate correlation ID for debugging\n const correlationId = this.generateCorrelationId();\n\n const controller = new AbortController();\n const timeoutId = setTimeout(() => controller.abort(), this.timeout);\n\n try {\n const response = await fetch(url, {\n method: 'POST',\n headers: {\n 'Authorization': `Bearer ${this.token}`,\n 'Content-Type': 'application/json',\n 'Accept': 'application/x-zip-compressed, application/json',\n 'x-correlation-id': correlationId,\n },\n body: JSON.stringify(payload),\n signal: controller.signal,\n });\n\n clearTimeout(timeoutId);\n\n if (!response.ok) {\n await this.handleErrorResponse(response, correlationId);\n }\n\n // Parse the ZIP response\n const arrayBuffer = await response.arrayBuffer();\n const images = await extractImagesFromZip(arrayBuffer);\n\n return {\n images,\n metadata: {\n seed: payload.parameters.seed,\n prompt: payload.input,\n model: payload.model,\n sampler: payload.parameters.sampler as string,\n steps: payload.parameters.steps,\n scale: payload.parameters.scale,\n },\n };\n } catch (error) {\n clearTimeout(timeoutId);\n\n if (error instanceof NovelAIError) {\n throw error;\n }\n\n if (error instanceof Error) {\n if (error.name === 'AbortError') {\n throw new NovelAINetworkError(`Request timed out after ${this.timeout}ms`, error);\n }\n throw new NovelAINetworkError(`Network error: ${error.message}`, error);\n }\n\n throw new NovelAINetworkError('An unknown error occurred');\n }\n }\n\n /**\n * Handle non-2xx responses and throw appropriate errors\n */\n private async handleErrorResponse(response: Response, correlationId: string): Promise<never> {\n let errorBody: APIErrorResponse | null = null;\n\n try {\n errorBody = await response.json() as APIErrorResponse;\n } catch {\n // Response may not be JSON\n }\n\n const message = errorBody?.message ?? errorBody?.error ?? response.statusText;\n\n switch (response.status) {\n case 400:\n throw new NovelAIValidationError(\n `Bad request: ${message}`,\n JSON.stringify(errorBody)\n );\n case 401:\n case 403:\n throw new NovelAIAuthError(message);\n case 402:\n throw new NovelAIPaymentError(message);\n case 429: {\n const retryAfter = response.headers.get('retry-after');\n throw new NovelAIRateLimitError(message, retryAfter ? parseInt(retryAfter) : undefined);\n }\n case 500:\n case 502:\n case 503:\n case 504:\n throw new NovelAIServerError(\n `Server error (${response.status}): ${message}. This may be caused by payload schema issues.`,\n correlationId\n );\n default:\n throw new NovelAIError(\n `HTTP ${response.status}: ${message}`,\n response.status\n );\n }\n }\n\n /**\n * Generate a 6-character alphanumeric correlation ID for debugging\n */\n private generateCorrelationId(): string {\n const chars = 'ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789';\n let result = '';\n for (let i = 0; i < 6; i++) {\n result += chars.charAt(Math.floor(Math.random() * chars.length));\n }\n return result;\n }\n}\n","/**\n * Supported NovelAI image generation models\n */\nexport enum NovelAIModel {\n /** V4.5 Full - Latest model with T5 encoding and multi-character support */\n V45_Full = \"nai-diffusion-4-5-full\",\n /** V4 Curated - More conservative aesthetic choices */\n V4_Curated = \"nai-diffusion-4-curated\",\n /** V4 Inpainting - For image editing and inpainting tasks */\n Inpainting = \"nai-diffusion-4-inpainting\",\n}\n","/**\n * Supported sampling algorithms for image generation\n */\nexport enum NovelAISampler {\n /** Standard Euler sampler */\n Euler = \"k_euler\",\n /** Euler Ancestral - recommended for anime-style generations */\n EulerAncestral = \"k_euler_ancestral\",\n /** DPM++ 2M - stable and aesthetic */\n DPM_2M = \"k_dpmpp_2m\",\n /** DPM++ 2S Ancestral */\n DPM_2S_Ancestral = \"k_dpmpp_2s_ancestral\",\n /** DPM++ SDE */\n DPM_SDE = \"k_dpmpp_sde\",\n /** DDIM V3 */\n DDIM = \"ddim_v3\",\n}\n\n/**\n * Preset negative prompt configurations\n */\nexport enum UCPreset {\n /** Heavy - Low Quality + Bad Anatomy */\n Heavy = 0,\n /** Light - Low Quality only */\n Light = 1,\n /** None - Use custom negative prompt only */\n None = 2,\n}\n\n/**\n * Noise schedule algorithms\n */\nexport enum NoiseSchedule {\n Native = \"native\",\n Karras = \"karras\",\n Exponential = \"exponential\",\n Polyexponential = \"polyexponential\",\n}\n","/**\n * Validation error for invalid SDK parameters\n */\nexport class ValidationError extends Error {\n constructor(message: string) {\n super(message);\n this.name = 'ValidationError';\n }\n}\n\n/**\n * Validates that image dimensions are multiples of 64\n * @throws ValidationError if dimensions are invalid\n */\nexport function validateResolution(width: number, height: number): void {\n if (!Number.isInteger(width) || !Number.isInteger(height)) {\n throw new ValidationError('Width and height must be integers');\n }\n if (width <= 0 || height <= 0) {\n throw new ValidationError('Width and height must be positive');\n }\n if (width % 64 !== 0) {\n throw new ValidationError(`Width must be a multiple of 64, got ${width}`);\n }\n if (height % 64 !== 0) {\n throw new ValidationError(`Height must be a multiple of 64, got ${height}`);\n }\n}\n\n/**\n * Validates that step count is within acceptable range\n * @throws ValidationError if steps are out of range\n */\nexport function validateSteps(steps: number): void {\n if (!Number.isInteger(steps)) {\n throw new ValidationError('Steps must be an integer');\n }\n if (steps < 1 || steps > 50) {\n throw new ValidationError(`Steps must be between 1 and 50, got ${steps}`);\n }\n}\n\n/**\n * Validates that scale (CFG) is within acceptable range\n * @throws ValidationError if scale is out of range\n */\nexport function validateScale(scale: number): void {\n if (typeof scale !== 'number' || isNaN(scale)) {\n throw new ValidationError('Scale must be a number');\n }\n if (scale < 0 || scale > 10) {\n throw new ValidationError(`Scale must be between 0 and 10, got ${scale}`);\n }\n}\n\n/**\n * Validates that seed is a valid unsigned 32-bit integer\n */\nexport function validateSeed(seed: number): void {\n if (!Number.isInteger(seed)) {\n throw new ValidationError('Seed must be an integer');\n }\n if (seed < 0 || seed > 4294967295) {\n throw new ValidationError(`Seed must be between 0 and 2^32-1, got ${seed}`);\n }\n}\n\n/**\n * Warning result for prompt length check\n */\nexport interface PromptWarning {\n isWarning: boolean;\n message?: string;\n length: number;\n limit: number;\n}\n\n/**\n * Check if prompt length exceeds recommended limit\n * T5 encoder has different tokenization than CLIP, so this is a heuristic\n * @param prompt - The full prompt string\n * @param limit - Character limit (default: 2000)\n * @returns Warning object with details\n */\nexport function checkPromptLength(prompt: string, limit = 2000): PromptWarning {\n const length = prompt.length;\n const isWarning = length > limit;\n \n return {\n isWarning,\n message: isWarning \n ? `Prompt length (${length} chars) exceeds recommended limit of ${limit}. This may cause truncation or unexpected results.`\n : undefined,\n length,\n limit,\n };\n}\n","import type { NovelAIClient } from '../client/NovelAIClient';\nimport type {\n GenerateImagePayload,\n NovelAIParameters,\n V4ConditionInput,\n ImageResponse,\n} from '../types';\nimport { NovelAIModel, NovelAISampler, UCPreset, NoiseSchedule } from '../types';\nimport { validateResolution, validateSteps, validateScale, validateSeed } from '../utils/Validators';\n\n/**\n * Fluent builder for constructing NovelAI image generation requests\n * Provides method chaining and compile-time type safety\n */\nexport class ImageRequestBuilder {\n private client: NovelAIClient;\n\n // Core parameters with sensible defaults\n private model: NovelAIModel = NovelAIModel.V45_Full;\n private width = 832;\n private height = 1216;\n private prompt = '';\n private characterPrompts: string[] = [];\n private negativePrompt = '';\n private characterNegativePrompts: string[] = [];\n private seed: number = Math.floor(Math.random() * 4294967295);\n private steps = 23;\n private scale = 5.0;\n private nSamples = 1;\n private sampler: NovelAISampler = NovelAISampler.EulerAncestral;\n private ucPreset: UCPreset = UCPreset.Heavy;\n private qualityToggle = true;\n private smea = false;\n private smeaDyn = false;\n private dynamicThresholding = false;\n private noiseSchedule: NoiseSchedule = NoiseSchedule.Karras;\n\n constructor(client: NovelAIClient) {\n this.client = client;\n }\n\n /**\n * Set the model to use for generation\n */\n setModel(model: NovelAIModel): this {\n this.model = model;\n return this;\n }\n\n /**\n * Set the output image dimensions\n * @throws ValidationError if dimensions are not multiples of 64\n */\n setSize(width: number, height: number): this {\n validateResolution(width, height);\n this.width = width;\n this.height = height;\n return this;\n }\n\n /**\n * Set the main prompt (base scene description)\n * For multi-character prompts, use the array overload\n */\n setPrompt(base: string, characters?: string[]): this {\n this.prompt = base;\n if (characters) {\n this.characterPrompts = characters;\n }\n return this;\n }\n\n /**\n * Add character prompts for multi-character scenes\n */\n addCharacter(characterPrompt: string): this {\n this.characterPrompts.push(characterPrompt);\n return this;\n }\n\n /**\n * Set the negative prompt (what to avoid in generation)\n * Optionally provide per-character negative prompts\n */\n setNegativePrompt(base: string, characterNegatives?: string[]): this {\n this.negativePrompt = base;\n if (characterNegatives) {\n this.characterNegativePrompts = characterNegatives;\n }\n return this;\n }\n\n /**\n * Add a per-character negative prompt\n * Should correspond to character prompts added via addCharacter()\n */\n addCharacterNegative(negativePrompt: string): this {\n this.characterNegativePrompts.push(negativePrompt);\n return this;\n }\n\n /**\n * Set the random seed for reproducible generations\n */\n setSeed(seed: number): this {\n validateSeed(seed);\n this.seed = seed;\n return this;\n }\n\n /**\n * Set the number of sampling steps\n * @throws ValidationError if steps are out of range (1-50)\n */\n setSteps(steps: number): this {\n validateSteps(steps);\n this.steps = steps;\n return this;\n }\n\n /**\n * Set the guidance scale (CFG)\n * @throws ValidationError if scale is out of range (0-10)\n */\n setScale(scale: number): this {\n validateScale(scale);\n this.scale = scale;\n return this;\n }\n\n /**\n * Set the number of images to generate in a single request\n * Note: Each additional sample consumes Anlas credits\n * @param count - Number of images (1-4 typically supported)\n */\n setBatchSize(count: number): this {\n if (!Number.isInteger(count) || count < 1) {\n throw new Error('Batch size must be a positive integer');\n }\n this.nSamples = count;\n return this;\n }\n\n /**\n * Set the sampling algorithm\n */\n setSampler(sampler: NovelAISampler): this {\n this.sampler = sampler;\n return this;\n }\n\n /**\n * Set the UC preset (predefined negative prompt configuration)\n */\n setUCPreset(preset: UCPreset): this {\n this.ucPreset = preset;\n return this;\n }\n\n /**\n * Toggle automatic quality tags insertion\n */\n setQualityToggle(enabled: boolean): this {\n this.qualityToggle = enabled;\n return this;\n }\n\n /**\n * Enable SMEA (Sinusoidal Multipass Euler Ancestral)\n * @param dynamic - If true, enables dynamic SMEA variant\n */\n enableSMEA(dynamic = false): this {\n this.smea = true;\n this.smeaDyn = dynamic;\n return this;\n }\n\n /**\n * Disable SMEA\n */\n disableSMEA(): this {\n this.smea = false;\n this.smeaDyn = false;\n return this;\n }\n\n /**\n * Set the noise schedule algorithm\n */\n setNoiseSchedule(schedule: NoiseSchedule): this {\n this.noiseSchedule = schedule;\n return this;\n }\n\n /**\n * Enable dynamic thresholding\n * Enhances contrast at high CFG scales (scale > 7)\n */\n enableDynamicThresholding(): this {\n this.dynamicThresholding = true;\n return this;\n }\n\n /**\n * Disable dynamic thresholding\n */\n disableDynamicThresholding(): this {\n this.dynamicThresholding = false;\n return this;\n }\n\n /**\n * Build the V4 condition input structure for prompts\n */\n private buildV4ConditionInput(base: string, characters: string[]): V4ConditionInput {\n return {\n caption: {\n base_caption: base,\n char_captions: characters,\n },\n use_coords: false,\n use_order: true,\n legacy_uc: false,\n };\n }\n\n /**\n * Build the formatted input string for the API\n * Combines base prompt with character prompts using pipe delimiter\n */\n private buildInputString(): string {\n if (this.characterPrompts.length === 0) {\n return this.prompt;\n }\n return [this.prompt, ...this.characterPrompts].join(' | ');\n }\n\n /**\n * Build the complete API payload\n */\n buildPayload(): GenerateImagePayload {\n const parameters: NovelAIParameters = {\n width: this.width,\n height: this.height,\n scale: this.scale,\n sampler: this.sampler,\n steps: this.steps,\n n_samples: this.nSamples,\n seed: this.seed,\n negative_prompt: this.negativePrompt,\n\n // V4-specific structured prompts\n v4_prompt: this.buildV4ConditionInput(this.prompt, this.characterPrompts),\n v4_negative_prompt: this.buildV4ConditionInput(this.negativePrompt, this.characterNegativePrompts),\n\n // Quality and preset controls (camelCase - API requirement)\n qualityToggle: this.qualityToggle,\n ucPreset: this.ucPreset,\n\n // Technical flags (snake_case - API requirement)\n params_version: 3,\n noise_schedule: this.noiseSchedule,\n sm: this.smea,\n sm_dyn: this.smeaDyn,\n dynamic_thresholding: this.dynamicThresholding,\n prefer_brownian: true,\n deliberate_euler_ancestral_bug: true,\n legacy: false,\n legacy_v3_extend: false,\n };\n\n return {\n input: this.buildInputString(),\n model: this.model,\n action: 'generate',\n parameters,\n };\n }\n\n /**\n * Execute the image generation request\n */\n async generate(): Promise<ImageResponse> {\n const payload = this.buildPayload();\n return this.client._execute(payload);\n }\n}\n","import type { ClientConfig, GenerateImagePayload, ImageResponse } from '../types';\nimport { APIClient } from '../network/APIClient';\nimport { ImageRequestBuilder } from '../builder/ImageRequestBuilder';\n\n/**\n * Main entry point for the NovelAI Image SDK\n * \n * @example\n * ```typescript\n * const client = new NovelAIClient({ token: process.env.NAI_TOKEN });\n * \n * const result = await client.image()\n * .setPrompt('1girl, cyberpunk, neon lights')\n * .setSize(832, 1216)\n * .generate();\n * \n * fs.writeFileSync('output.png', result.images[0]);\n * ```\n */\nexport class NovelAIClient {\n private readonly apiClient: APIClient;\n\n /**\n * Create a new NovelAI client\n * @param config - Client configuration including token and optional base URL\n */\n constructor(config: ClientConfig) {\n if (!config.token) {\n throw new Error('NovelAI API token is required');\n }\n\n this.apiClient = new APIClient({\n token: config.token,\n baseUrl: config.baseUrl,\n timeout: config.timeout,\n });\n }\n\n /**\n * Start building an image generation request\n * @returns A new ImageRequestBuilder instance\n */\n image(): ImageRequestBuilder {\n return new ImageRequestBuilder(this);\n }\n\n /**\n * Execute a generation request (called internally by the builder)\n * @internal\n */\n async _execute(payload: GenerateImagePayload): Promise<ImageResponse> {\n return this.apiClient.generateImage(payload);\n }\n}\n"]}
|
package/dist/index.d.cts
CHANGED
|
@@ -82,6 +82,7 @@ interface NovelAIParameters {
|
|
|
82
82
|
noise_schedule: NoiseSchedule | string;
|
|
83
83
|
sm: boolean;
|
|
84
84
|
sm_dyn: boolean;
|
|
85
|
+
dynamic_thresholding: boolean;
|
|
85
86
|
prefer_brownian: boolean;
|
|
86
87
|
deliberate_euler_ancestral_bug: boolean;
|
|
87
88
|
legacy: boolean;
|
|
@@ -161,14 +162,17 @@ declare class ImageRequestBuilder {
|
|
|
161
162
|
private prompt;
|
|
162
163
|
private characterPrompts;
|
|
163
164
|
private negativePrompt;
|
|
165
|
+
private characterNegativePrompts;
|
|
164
166
|
private seed;
|
|
165
167
|
private steps;
|
|
166
168
|
private scale;
|
|
169
|
+
private nSamples;
|
|
167
170
|
private sampler;
|
|
168
171
|
private ucPreset;
|
|
169
172
|
private qualityToggle;
|
|
170
173
|
private smea;
|
|
171
174
|
private smeaDyn;
|
|
175
|
+
private dynamicThresholding;
|
|
172
176
|
private noiseSchedule;
|
|
173
177
|
constructor(client: NovelAIClient);
|
|
174
178
|
/**
|
|
@@ -191,8 +195,14 @@ declare class ImageRequestBuilder {
|
|
|
191
195
|
addCharacter(characterPrompt: string): this;
|
|
192
196
|
/**
|
|
193
197
|
* Set the negative prompt (what to avoid in generation)
|
|
198
|
+
* Optionally provide per-character negative prompts
|
|
194
199
|
*/
|
|
195
|
-
setNegativePrompt(
|
|
200
|
+
setNegativePrompt(base: string, characterNegatives?: string[]): this;
|
|
201
|
+
/**
|
|
202
|
+
* Add a per-character negative prompt
|
|
203
|
+
* Should correspond to character prompts added via addCharacter()
|
|
204
|
+
*/
|
|
205
|
+
addCharacterNegative(negativePrompt: string): this;
|
|
196
206
|
/**
|
|
197
207
|
* Set the random seed for reproducible generations
|
|
198
208
|
*/
|
|
@@ -207,6 +217,12 @@ declare class ImageRequestBuilder {
|
|
|
207
217
|
* @throws ValidationError if scale is out of range (0-10)
|
|
208
218
|
*/
|
|
209
219
|
setScale(scale: number): this;
|
|
220
|
+
/**
|
|
221
|
+
* Set the number of images to generate in a single request
|
|
222
|
+
* Note: Each additional sample consumes Anlas credits
|
|
223
|
+
* @param count - Number of images (1-4 typically supported)
|
|
224
|
+
*/
|
|
225
|
+
setBatchSize(count: number): this;
|
|
210
226
|
/**
|
|
211
227
|
* Set the sampling algorithm
|
|
212
228
|
*/
|
|
@@ -232,6 +248,15 @@ declare class ImageRequestBuilder {
|
|
|
232
248
|
* Set the noise schedule algorithm
|
|
233
249
|
*/
|
|
234
250
|
setNoiseSchedule(schedule: NoiseSchedule): this;
|
|
251
|
+
/**
|
|
252
|
+
* Enable dynamic thresholding
|
|
253
|
+
* Enhances contrast at high CFG scales (scale > 7)
|
|
254
|
+
*/
|
|
255
|
+
enableDynamicThresholding(): this;
|
|
256
|
+
/**
|
|
257
|
+
* Disable dynamic thresholding
|
|
258
|
+
*/
|
|
259
|
+
disableDynamicThresholding(): this;
|
|
235
260
|
/**
|
|
236
261
|
* Build the V4 condition input structure for prompts
|
|
237
262
|
*/
|
|
@@ -367,5 +392,22 @@ declare function validateScale(scale: number): void;
|
|
|
367
392
|
* Validates that seed is a valid unsigned 32-bit integer
|
|
368
393
|
*/
|
|
369
394
|
declare function validateSeed(seed: number): void;
|
|
395
|
+
/**
|
|
396
|
+
* Warning result for prompt length check
|
|
397
|
+
*/
|
|
398
|
+
interface PromptWarning {
|
|
399
|
+
isWarning: boolean;
|
|
400
|
+
message?: string;
|
|
401
|
+
length: number;
|
|
402
|
+
limit: number;
|
|
403
|
+
}
|
|
404
|
+
/**
|
|
405
|
+
* Check if prompt length exceeds recommended limit
|
|
406
|
+
* T5 encoder has different tokenization than CLIP, so this is a heuristic
|
|
407
|
+
* @param prompt - The full prompt string
|
|
408
|
+
* @param limit - Character limit (default: 2000)
|
|
409
|
+
* @returns Warning object with details
|
|
410
|
+
*/
|
|
411
|
+
declare function checkPromptLength(prompt: string, limit?: number): PromptWarning;
|
|
370
412
|
|
|
371
|
-
export { type ClientConfig, type GenerateImagePayload, type ImageGenerationOptions, type ImageMetadata, ImageRequestBuilder, type ImageResponse, NoiseSchedule, NovelAIAuthError, NovelAIClient, NovelAIError, NovelAIModel, NovelAINetworkError, type NovelAIParameters, NovelAIPaymentError, NovelAIRateLimitError, NovelAISampler, NovelAIServerError, NovelAIValidationError, UCPreset, type V4ConditionInput, toBase64, toDataURL, validateResolution, validateScale, validateSeed, validateSteps };
|
|
413
|
+
export { type ClientConfig, type GenerateImagePayload, type ImageGenerationOptions, type ImageMetadata, ImageRequestBuilder, type ImageResponse, NoiseSchedule, NovelAIAuthError, NovelAIClient, NovelAIError, NovelAIModel, NovelAINetworkError, type NovelAIParameters, NovelAIPaymentError, NovelAIRateLimitError, NovelAISampler, NovelAIServerError, NovelAIValidationError, type PromptWarning, UCPreset, type V4ConditionInput, checkPromptLength, toBase64, toDataURL, validateResolution, validateScale, validateSeed, validateSteps };
|
package/dist/index.d.ts
CHANGED
|
@@ -82,6 +82,7 @@ interface NovelAIParameters {
|
|
|
82
82
|
noise_schedule: NoiseSchedule | string;
|
|
83
83
|
sm: boolean;
|
|
84
84
|
sm_dyn: boolean;
|
|
85
|
+
dynamic_thresholding: boolean;
|
|
85
86
|
prefer_brownian: boolean;
|
|
86
87
|
deliberate_euler_ancestral_bug: boolean;
|
|
87
88
|
legacy: boolean;
|
|
@@ -161,14 +162,17 @@ declare class ImageRequestBuilder {
|
|
|
161
162
|
private prompt;
|
|
162
163
|
private characterPrompts;
|
|
163
164
|
private negativePrompt;
|
|
165
|
+
private characterNegativePrompts;
|
|
164
166
|
private seed;
|
|
165
167
|
private steps;
|
|
166
168
|
private scale;
|
|
169
|
+
private nSamples;
|
|
167
170
|
private sampler;
|
|
168
171
|
private ucPreset;
|
|
169
172
|
private qualityToggle;
|
|
170
173
|
private smea;
|
|
171
174
|
private smeaDyn;
|
|
175
|
+
private dynamicThresholding;
|
|
172
176
|
private noiseSchedule;
|
|
173
177
|
constructor(client: NovelAIClient);
|
|
174
178
|
/**
|
|
@@ -191,8 +195,14 @@ declare class ImageRequestBuilder {
|
|
|
191
195
|
addCharacter(characterPrompt: string): this;
|
|
192
196
|
/**
|
|
193
197
|
* Set the negative prompt (what to avoid in generation)
|
|
198
|
+
* Optionally provide per-character negative prompts
|
|
194
199
|
*/
|
|
195
|
-
setNegativePrompt(
|
|
200
|
+
setNegativePrompt(base: string, characterNegatives?: string[]): this;
|
|
201
|
+
/**
|
|
202
|
+
* Add a per-character negative prompt
|
|
203
|
+
* Should correspond to character prompts added via addCharacter()
|
|
204
|
+
*/
|
|
205
|
+
addCharacterNegative(negativePrompt: string): this;
|
|
196
206
|
/**
|
|
197
207
|
* Set the random seed for reproducible generations
|
|
198
208
|
*/
|
|
@@ -207,6 +217,12 @@ declare class ImageRequestBuilder {
|
|
|
207
217
|
* @throws ValidationError if scale is out of range (0-10)
|
|
208
218
|
*/
|
|
209
219
|
setScale(scale: number): this;
|
|
220
|
+
/**
|
|
221
|
+
* Set the number of images to generate in a single request
|
|
222
|
+
* Note: Each additional sample consumes Anlas credits
|
|
223
|
+
* @param count - Number of images (1-4 typically supported)
|
|
224
|
+
*/
|
|
225
|
+
setBatchSize(count: number): this;
|
|
210
226
|
/**
|
|
211
227
|
* Set the sampling algorithm
|
|
212
228
|
*/
|
|
@@ -232,6 +248,15 @@ declare class ImageRequestBuilder {
|
|
|
232
248
|
* Set the noise schedule algorithm
|
|
233
249
|
*/
|
|
234
250
|
setNoiseSchedule(schedule: NoiseSchedule): this;
|
|
251
|
+
/**
|
|
252
|
+
* Enable dynamic thresholding
|
|
253
|
+
* Enhances contrast at high CFG scales (scale > 7)
|
|
254
|
+
*/
|
|
255
|
+
enableDynamicThresholding(): this;
|
|
256
|
+
/**
|
|
257
|
+
* Disable dynamic thresholding
|
|
258
|
+
*/
|
|
259
|
+
disableDynamicThresholding(): this;
|
|
235
260
|
/**
|
|
236
261
|
* Build the V4 condition input structure for prompts
|
|
237
262
|
*/
|
|
@@ -367,5 +392,22 @@ declare function validateScale(scale: number): void;
|
|
|
367
392
|
* Validates that seed is a valid unsigned 32-bit integer
|
|
368
393
|
*/
|
|
369
394
|
declare function validateSeed(seed: number): void;
|
|
395
|
+
/**
|
|
396
|
+
* Warning result for prompt length check
|
|
397
|
+
*/
|
|
398
|
+
interface PromptWarning {
|
|
399
|
+
isWarning: boolean;
|
|
400
|
+
message?: string;
|
|
401
|
+
length: number;
|
|
402
|
+
limit: number;
|
|
403
|
+
}
|
|
404
|
+
/**
|
|
405
|
+
* Check if prompt length exceeds recommended limit
|
|
406
|
+
* T5 encoder has different tokenization than CLIP, so this is a heuristic
|
|
407
|
+
* @param prompt - The full prompt string
|
|
408
|
+
* @param limit - Character limit (default: 2000)
|
|
409
|
+
* @returns Warning object with details
|
|
410
|
+
*/
|
|
411
|
+
declare function checkPromptLength(prompt: string, limit?: number): PromptWarning;
|
|
370
412
|
|
|
371
|
-
export { type ClientConfig, type GenerateImagePayload, type ImageGenerationOptions, type ImageMetadata, ImageRequestBuilder, type ImageResponse, NoiseSchedule, NovelAIAuthError, NovelAIClient, NovelAIError, NovelAIModel, NovelAINetworkError, type NovelAIParameters, NovelAIPaymentError, NovelAIRateLimitError, NovelAISampler, NovelAIServerError, NovelAIValidationError, UCPreset, type V4ConditionInput, toBase64, toDataURL, validateResolution, validateScale, validateSeed, validateSteps };
|
|
413
|
+
export { type ClientConfig, type GenerateImagePayload, type ImageGenerationOptions, type ImageMetadata, ImageRequestBuilder, type ImageResponse, NoiseSchedule, NovelAIAuthError, NovelAIClient, NovelAIError, NovelAIModel, NovelAINetworkError, type NovelAIParameters, NovelAIPaymentError, NovelAIRateLimitError, NovelAISampler, NovelAIServerError, NovelAIValidationError, type PromptWarning, UCPreset, type V4ConditionInput, checkPromptLength, toBase64, toDataURL, validateResolution, validateScale, validateSeed, validateSteps };
|
package/dist/index.js
CHANGED
|
@@ -289,6 +289,16 @@ function validateSeed(seed) {
|
|
|
289
289
|
throw new ValidationError(`Seed must be between 0 and 2^32-1, got ${seed}`);
|
|
290
290
|
}
|
|
291
291
|
}
|
|
292
|
+
function checkPromptLength(prompt, limit = 2e3) {
|
|
293
|
+
const length = prompt.length;
|
|
294
|
+
const isWarning = length > limit;
|
|
295
|
+
return {
|
|
296
|
+
isWarning,
|
|
297
|
+
message: isWarning ? `Prompt length (${length} chars) exceeds recommended limit of ${limit}. This may cause truncation or unexpected results.` : void 0,
|
|
298
|
+
length,
|
|
299
|
+
limit
|
|
300
|
+
};
|
|
301
|
+
}
|
|
292
302
|
|
|
293
303
|
// src/builder/ImageRequestBuilder.ts
|
|
294
304
|
var ImageRequestBuilder = class {
|
|
@@ -300,14 +310,17 @@ var ImageRequestBuilder = class {
|
|
|
300
310
|
this.prompt = "";
|
|
301
311
|
this.characterPrompts = [];
|
|
302
312
|
this.negativePrompt = "";
|
|
313
|
+
this.characterNegativePrompts = [];
|
|
303
314
|
this.seed = Math.floor(Math.random() * 4294967295);
|
|
304
315
|
this.steps = 23;
|
|
305
316
|
this.scale = 5;
|
|
317
|
+
this.nSamples = 1;
|
|
306
318
|
this.sampler = "k_euler_ancestral" /* EulerAncestral */;
|
|
307
319
|
this.ucPreset = 0 /* Heavy */;
|
|
308
320
|
this.qualityToggle = true;
|
|
309
321
|
this.smea = false;
|
|
310
322
|
this.smeaDyn = false;
|
|
323
|
+
this.dynamicThresholding = false;
|
|
311
324
|
this.noiseSchedule = "karras" /* Karras */;
|
|
312
325
|
this.client = client;
|
|
313
326
|
}
|
|
@@ -348,9 +361,21 @@ var ImageRequestBuilder = class {
|
|
|
348
361
|
}
|
|
349
362
|
/**
|
|
350
363
|
* Set the negative prompt (what to avoid in generation)
|
|
364
|
+
* Optionally provide per-character negative prompts
|
|
365
|
+
*/
|
|
366
|
+
setNegativePrompt(base, characterNegatives) {
|
|
367
|
+
this.negativePrompt = base;
|
|
368
|
+
if (characterNegatives) {
|
|
369
|
+
this.characterNegativePrompts = characterNegatives;
|
|
370
|
+
}
|
|
371
|
+
return this;
|
|
372
|
+
}
|
|
373
|
+
/**
|
|
374
|
+
* Add a per-character negative prompt
|
|
375
|
+
* Should correspond to character prompts added via addCharacter()
|
|
351
376
|
*/
|
|
352
|
-
|
|
353
|
-
this.negativePrompt
|
|
377
|
+
addCharacterNegative(negativePrompt) {
|
|
378
|
+
this.characterNegativePrompts.push(negativePrompt);
|
|
354
379
|
return this;
|
|
355
380
|
}
|
|
356
381
|
/**
|
|
@@ -379,6 +404,18 @@ var ImageRequestBuilder = class {
|
|
|
379
404
|
this.scale = scale;
|
|
380
405
|
return this;
|
|
381
406
|
}
|
|
407
|
+
/**
|
|
408
|
+
* Set the number of images to generate in a single request
|
|
409
|
+
* Note: Each additional sample consumes Anlas credits
|
|
410
|
+
* @param count - Number of images (1-4 typically supported)
|
|
411
|
+
*/
|
|
412
|
+
setBatchSize(count) {
|
|
413
|
+
if (!Number.isInteger(count) || count < 1) {
|
|
414
|
+
throw new Error("Batch size must be a positive integer");
|
|
415
|
+
}
|
|
416
|
+
this.nSamples = count;
|
|
417
|
+
return this;
|
|
418
|
+
}
|
|
382
419
|
/**
|
|
383
420
|
* Set the sampling algorithm
|
|
384
421
|
*/
|
|
@@ -424,6 +461,21 @@ var ImageRequestBuilder = class {
|
|
|
424
461
|
this.noiseSchedule = schedule;
|
|
425
462
|
return this;
|
|
426
463
|
}
|
|
464
|
+
/**
|
|
465
|
+
* Enable dynamic thresholding
|
|
466
|
+
* Enhances contrast at high CFG scales (scale > 7)
|
|
467
|
+
*/
|
|
468
|
+
enableDynamicThresholding() {
|
|
469
|
+
this.dynamicThresholding = true;
|
|
470
|
+
return this;
|
|
471
|
+
}
|
|
472
|
+
/**
|
|
473
|
+
* Disable dynamic thresholding
|
|
474
|
+
*/
|
|
475
|
+
disableDynamicThresholding() {
|
|
476
|
+
this.dynamicThresholding = false;
|
|
477
|
+
return this;
|
|
478
|
+
}
|
|
427
479
|
/**
|
|
428
480
|
* Build the V4 condition input structure for prompts
|
|
429
481
|
*/
|
|
@@ -458,12 +510,12 @@ var ImageRequestBuilder = class {
|
|
|
458
510
|
scale: this.scale,
|
|
459
511
|
sampler: this.sampler,
|
|
460
512
|
steps: this.steps,
|
|
461
|
-
n_samples:
|
|
513
|
+
n_samples: this.nSamples,
|
|
462
514
|
seed: this.seed,
|
|
463
515
|
negative_prompt: this.negativePrompt,
|
|
464
516
|
// V4-specific structured prompts
|
|
465
517
|
v4_prompt: this.buildV4ConditionInput(this.prompt, this.characterPrompts),
|
|
466
|
-
v4_negative_prompt: this.buildV4ConditionInput(this.negativePrompt,
|
|
518
|
+
v4_negative_prompt: this.buildV4ConditionInput(this.negativePrompt, this.characterNegativePrompts),
|
|
467
519
|
// Quality and preset controls (camelCase - API requirement)
|
|
468
520
|
qualityToggle: this.qualityToggle,
|
|
469
521
|
ucPreset: this.ucPreset,
|
|
@@ -472,6 +524,7 @@ var ImageRequestBuilder = class {
|
|
|
472
524
|
noise_schedule: this.noiseSchedule,
|
|
473
525
|
sm: this.smea,
|
|
474
526
|
sm_dyn: this.smeaDyn,
|
|
527
|
+
dynamic_thresholding: this.dynamicThresholding,
|
|
475
528
|
prefer_brownian: true,
|
|
476
529
|
deliberate_euler_ancestral_bug: true,
|
|
477
530
|
legacy: false,
|
|
@@ -525,6 +578,6 @@ var NovelAIClient = class {
|
|
|
525
578
|
}
|
|
526
579
|
};
|
|
527
580
|
|
|
528
|
-
export { ImageRequestBuilder, NoiseSchedule, NovelAIAuthError, NovelAIClient, NovelAIError, NovelAIModel, NovelAINetworkError, NovelAIPaymentError, NovelAIRateLimitError, NovelAISampler, NovelAIServerError, NovelAIValidationError, UCPreset, toBase64, toDataURL, validateResolution, validateScale, validateSeed, validateSteps };
|
|
581
|
+
export { ImageRequestBuilder, NoiseSchedule, NovelAIAuthError, NovelAIClient, NovelAIError, NovelAIModel, NovelAINetworkError, NovelAIPaymentError, NovelAIRateLimitError, NovelAISampler, NovelAIServerError, NovelAIValidationError, UCPreset, checkPromptLength, toBase64, toDataURL, validateResolution, validateScale, validateSeed, validateSteps };
|
|
529
582
|
//# sourceMappingURL=index.js.map
|
|
530
583
|
//# sourceMappingURL=index.js.map
|
package/dist/index.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"sources":["../src/errors/index.ts","../src/utils/ZipParser.ts","../src/network/APIClient.ts","../src/types/Model.ts","../src/types/Sampler.ts","../src/utils/Validators.ts","../src/builder/ImageRequestBuilder.ts","../src/client/NovelAIClient.ts"],"names":["NovelAIModel","NovelAISampler","UCPreset","NoiseSchedule"],"mappings":"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","file":"index.js","sourcesContent":["/**\n * Base error class for all NovelAI SDK errors\n */\nexport class NovelAIError extends Error {\n public readonly statusCode?: number;\n\n constructor(message: string, statusCode?: number) {\n super(message);\n this.name = 'NovelAIError';\n this.statusCode = statusCode;\n }\n}\n\n/**\n * Authentication error (401/403)\n * Thrown when the API token is invalid or expired\n */\nexport class NovelAIAuthError extends NovelAIError {\n constructor(message = 'Authentication failed. Check your Persistent API Token (pst-...).') {\n super(message, 401);\n this.name = 'NovelAIAuthError';\n }\n}\n\n/**\n * Payment required error (402)\n * Thrown when the user has insufficient Anlas credits\n */\nexport class NovelAIPaymentError extends NovelAIError {\n constructor(message = 'Insufficient Anlas credits for this generation.') {\n super(message, 402);\n this.name = 'NovelAIPaymentError';\n }\n}\n\n/**\n * Validation error (400)\n * Thrown when the API rejects the payload due to schema issues\n */\nexport class NovelAIValidationError extends NovelAIError {\n public readonly details?: string;\n\n constructor(message: string, details?: string) {\n super(message, 400);\n this.name = 'NovelAIValidationError';\n this.details = details;\n }\n}\n\n/**\n * Network error\n * Thrown on timeouts, connection failures, or other network issues\n */\nexport class NovelAINetworkError extends NovelAIError {\n public readonly cause?: Error;\n\n constructor(message: string, cause?: Error) {\n super(message);\n this.name = 'NovelAINetworkError';\n this.cause = cause;\n }\n}\n\n/**\n * Rate limit error (429)\n * Thrown when too many requests are made\n */\nexport class NovelAIRateLimitError extends NovelAIError {\n public readonly retryAfter?: number;\n\n constructor(message = 'Rate limit exceeded. Please wait before retrying.', retryAfter?: number) {\n super(message, 429);\n this.name = 'NovelAIRateLimitError';\n this.retryAfter = retryAfter;\n }\n}\n\n/**\n * Server error (500+)\n * Thrown when the NovelAI server encounters an internal error\n */\nexport class NovelAIServerError extends NovelAIError {\n public readonly correlationId?: string;\n\n constructor(message = 'NovelAI server error. This may be due to payload schema issues.', correlationId?: string) {\n super(message, 500);\n this.name = 'NovelAIServerError';\n this.correlationId = correlationId;\n }\n}\n","/**\n * Isomorphic ZIP parser that works in both Node.js and browser environments\n * Extracts PNG files from NovelAI's application/x-zip-compressed response\n */\n\n/**\n * Detects if we're running in a Node.js environment\n */\nfunction isNodeEnvironment(): boolean {\n return (\n typeof process !== 'undefined' &&\n process.versions != null &&\n process.versions.node != null\n );\n}\n\n/**\n * Extract PNG files from a ZIP archive buffer\n * @param data - The raw ZIP archive data\n * @returns Array of extracted PNG file contents\n */\nexport async function extractImagesFromZip(\n data: ArrayBuffer | Uint8Array\n): Promise<Uint8Array[]> {\n const buffer = data instanceof ArrayBuffer ? new Uint8Array(data) : data;\n\n if (isNodeEnvironment()) {\n return extractWithAdmZip(buffer);\n } else {\n return extractWithFflate(buffer);\n }\n}\n\n/**\n * Node.js extraction using adm-zip\n */\nasync function extractWithAdmZip(buffer: Uint8Array): Promise<Uint8Array[]> {\n // Dynamic import for Node.js environment\n const AdmZip = (await import('adm-zip')).default;\n const zip = new AdmZip(Buffer.from(buffer));\n const entries = zip.getEntries();\n const images: Uint8Array[] = [];\n\n for (const entry of entries) {\n if (entry.entryName.endsWith('.png') && !entry.isDirectory) {\n const data = entry.getData();\n images.push(new Uint8Array(data));\n }\n }\n\n return images;\n}\n\n/**\n * Browser extraction using fflate\n */\nasync function extractWithFflate(buffer: Uint8Array): Promise<Uint8Array[]> {\n // Dynamic import for browser environment\n const { unzipSync } = await import('fflate');\n const unzipped = unzipSync(buffer);\n const images: Uint8Array[] = [];\n\n for (const [filename, data] of Object.entries(unzipped)) {\n if (filename.endsWith('.png')) {\n images.push(data);\n }\n }\n\n return images;\n}\n\n/**\n * Convert Uint8Array to Base64 string (useful for browser display)\n */\nexport function toBase64(data: Uint8Array): string {\n if (isNodeEnvironment()) {\n return Buffer.from(data).toString('base64');\n } else {\n // Browser environment\n let binary = '';\n for (let i = 0; i < data.length; i++) {\n binary += String.fromCharCode(data[i]);\n }\n return btoa(binary);\n }\n}\n\n/**\n * Convert Uint8Array to data URL for direct use in img src\n */\nexport function toDataURL(data: Uint8Array, mimeType = 'image/png'): string {\n return `data:${mimeType};base64,${toBase64(data)}`;\n}\n","import type { GenerateImagePayload, ImageResponse, APIErrorResponse } from '../types';\nimport {\n NovelAIError,\n NovelAIAuthError,\n NovelAIPaymentError,\n NovelAIValidationError,\n NovelAINetworkError,\n NovelAIRateLimitError,\n NovelAIServerError,\n} from '../errors';\nimport { extractImagesFromZip } from '../utils/ZipParser';\n\nconst DEFAULT_BASE_URL = 'https://image.novelai.net';\nconst DEFAULT_TIMEOUT = 60000;\nconst GENERATE_ENDPOINT = '/ai/generate-image';\n\nexport interface APIClientConfig {\n token: string;\n baseUrl?: string;\n timeout?: number;\n}\n\n/**\n * Low-level HTTP client for NovelAI API\n * Handles authentication, binary response parsing, and error mapping\n */\nexport class APIClient {\n private readonly token: string;\n private readonly baseUrl: string;\n private readonly timeout: number;\n\n constructor(config: APIClientConfig) {\n this.token = config.token;\n this.baseUrl = config.baseUrl ?? DEFAULT_BASE_URL;\n this.timeout = config.timeout ?? DEFAULT_TIMEOUT;\n }\n\n /**\n * Generate an image using the NovelAI API\n */\n async generateImage(payload: GenerateImagePayload): Promise<ImageResponse> {\n const url = `${this.baseUrl}${GENERATE_ENDPOINT}`;\n\n // Generate correlation ID for debugging\n const correlationId = this.generateCorrelationId();\n\n const controller = new AbortController();\n const timeoutId = setTimeout(() => controller.abort(), this.timeout);\n\n try {\n const response = await fetch(url, {\n method: 'POST',\n headers: {\n 'Authorization': `Bearer ${this.token}`,\n 'Content-Type': 'application/json',\n 'Accept': 'application/x-zip-compressed, application/json',\n 'x-correlation-id': correlationId,\n },\n body: JSON.stringify(payload),\n signal: controller.signal,\n });\n\n clearTimeout(timeoutId);\n\n if (!response.ok) {\n await this.handleErrorResponse(response, correlationId);\n }\n\n // Parse the ZIP response\n const arrayBuffer = await response.arrayBuffer();\n const images = await extractImagesFromZip(arrayBuffer);\n\n return {\n images,\n metadata: {\n seed: payload.parameters.seed,\n prompt: payload.input,\n model: payload.model,\n sampler: payload.parameters.sampler as string,\n steps: payload.parameters.steps,\n scale: payload.parameters.scale,\n },\n };\n } catch (error) {\n clearTimeout(timeoutId);\n\n if (error instanceof NovelAIError) {\n throw error;\n }\n\n if (error instanceof Error) {\n if (error.name === 'AbortError') {\n throw new NovelAINetworkError(`Request timed out after ${this.timeout}ms`, error);\n }\n throw new NovelAINetworkError(`Network error: ${error.message}`, error);\n }\n\n throw new NovelAINetworkError('An unknown error occurred');\n }\n }\n\n /**\n * Handle non-2xx responses and throw appropriate errors\n */\n private async handleErrorResponse(response: Response, correlationId: string): Promise<never> {\n let errorBody: APIErrorResponse | null = null;\n\n try {\n errorBody = await response.json() as APIErrorResponse;\n } catch {\n // Response may not be JSON\n }\n\n const message = errorBody?.message ?? errorBody?.error ?? response.statusText;\n\n switch (response.status) {\n case 400:\n throw new NovelAIValidationError(\n `Bad request: ${message}`,\n JSON.stringify(errorBody)\n );\n case 401:\n case 403:\n throw new NovelAIAuthError(message);\n case 402:\n throw new NovelAIPaymentError(message);\n case 429: {\n const retryAfter = response.headers.get('retry-after');\n throw new NovelAIRateLimitError(message, retryAfter ? parseInt(retryAfter) : undefined);\n }\n case 500:\n case 502:\n case 503:\n case 504:\n throw new NovelAIServerError(\n `Server error (${response.status}): ${message}. This may be caused by payload schema issues.`,\n correlationId\n );\n default:\n throw new NovelAIError(\n `HTTP ${response.status}: ${message}`,\n response.status\n );\n }\n }\n\n /**\n * Generate a 6-character alphanumeric correlation ID for debugging\n */\n private generateCorrelationId(): string {\n const chars = 'ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789';\n let result = '';\n for (let i = 0; i < 6; i++) {\n result += chars.charAt(Math.floor(Math.random() * chars.length));\n }\n return result;\n }\n}\n","/**\n * Supported NovelAI image generation models\n */\nexport enum NovelAIModel {\n /** V4.5 Full - Latest model with T5 encoding and multi-character support */\n V45_Full = \"nai-diffusion-4-5-full\",\n /** V4 Curated - More conservative aesthetic choices */\n V4_Curated = \"nai-diffusion-4-curated\",\n /** V4 Inpainting - For image editing and inpainting tasks */\n Inpainting = \"nai-diffusion-4-inpainting\",\n}\n","/**\n * Supported sampling algorithms for image generation\n */\nexport enum NovelAISampler {\n /** Standard Euler sampler */\n Euler = \"k_euler\",\n /** Euler Ancestral - recommended for anime-style generations */\n EulerAncestral = \"k_euler_ancestral\",\n /** DPM++ 2M - stable and aesthetic */\n DPM_2M = \"k_dpmpp_2m\",\n /** DPM++ 2S Ancestral */\n DPM_2S_Ancestral = \"k_dpmpp_2s_ancestral\",\n /** DPM++ SDE */\n DPM_SDE = \"k_dpmpp_sde\",\n /** DDIM V3 */\n DDIM = \"ddim_v3\",\n}\n\n/**\n * Preset negative prompt configurations\n */\nexport enum UCPreset {\n /** Heavy - Low Quality + Bad Anatomy */\n Heavy = 0,\n /** Light - Low Quality only */\n Light = 1,\n /** None - Use custom negative prompt only */\n None = 2,\n}\n\n/**\n * Noise schedule algorithms\n */\nexport enum NoiseSchedule {\n Native = \"native\",\n Karras = \"karras\",\n Exponential = \"exponential\",\n Polyexponential = \"polyexponential\",\n}\n","/**\n * Validation error for invalid SDK parameters\n */\nexport class ValidationError extends Error {\n constructor(message: string) {\n super(message);\n this.name = 'ValidationError';\n }\n}\n\n/**\n * Validates that image dimensions are multiples of 64\n * @throws ValidationError if dimensions are invalid\n */\nexport function validateResolution(width: number, height: number): void {\n if (!Number.isInteger(width) || !Number.isInteger(height)) {\n throw new ValidationError('Width and height must be integers');\n }\n if (width <= 0 || height <= 0) {\n throw new ValidationError('Width and height must be positive');\n }\n if (width % 64 !== 0) {\n throw new ValidationError(`Width must be a multiple of 64, got ${width}`);\n }\n if (height % 64 !== 0) {\n throw new ValidationError(`Height must be a multiple of 64, got ${height}`);\n }\n}\n\n/**\n * Validates that step count is within acceptable range\n * @throws ValidationError if steps are out of range\n */\nexport function validateSteps(steps: number): void {\n if (!Number.isInteger(steps)) {\n throw new ValidationError('Steps must be an integer');\n }\n if (steps < 1 || steps > 50) {\n throw new ValidationError(`Steps must be between 1 and 50, got ${steps}`);\n }\n}\n\n/**\n * Validates that scale (CFG) is within acceptable range\n * @throws ValidationError if scale is out of range\n */\nexport function validateScale(scale: number): void {\n if (typeof scale !== 'number' || isNaN(scale)) {\n throw new ValidationError('Scale must be a number');\n }\n if (scale < 0 || scale > 10) {\n throw new ValidationError(`Scale must be between 0 and 10, got ${scale}`);\n }\n}\n\n/**\n * Validates that seed is a valid unsigned 32-bit integer\n */\nexport function validateSeed(seed: number): void {\n if (!Number.isInteger(seed)) {\n throw new ValidationError('Seed must be an integer');\n }\n if (seed < 0 || seed > 4294967295) {\n throw new ValidationError(`Seed must be between 0 and 2^32-1, got ${seed}`);\n }\n}\n","import type { NovelAIClient } from '../client/NovelAIClient';\nimport type {\n GenerateImagePayload,\n NovelAIParameters,\n V4ConditionInput,\n ImageResponse,\n} from '../types';\nimport { NovelAIModel, NovelAISampler, UCPreset, NoiseSchedule } from '../types';\nimport { validateResolution, validateSteps, validateScale, validateSeed } from '../utils/Validators';\n\n/**\n * Fluent builder for constructing NovelAI image generation requests\n * Provides method chaining and compile-time type safety\n */\nexport class ImageRequestBuilder {\n private client: NovelAIClient;\n\n // Core parameters with sensible defaults\n private model: NovelAIModel = NovelAIModel.V45_Full;\n private width = 832;\n private height = 1216;\n private prompt = '';\n private characterPrompts: string[] = [];\n private negativePrompt = '';\n private seed: number = Math.floor(Math.random() * 4294967295);\n private steps = 23;\n private scale = 5.0;\n private sampler: NovelAISampler = NovelAISampler.EulerAncestral;\n private ucPreset: UCPreset = UCPreset.Heavy;\n private qualityToggle = true;\n private smea = false;\n private smeaDyn = false;\n private noiseSchedule: NoiseSchedule = NoiseSchedule.Karras;\n\n constructor(client: NovelAIClient) {\n this.client = client;\n }\n\n /**\n * Set the model to use for generation\n */\n setModel(model: NovelAIModel): this {\n this.model = model;\n return this;\n }\n\n /**\n * Set the output image dimensions\n * @throws ValidationError if dimensions are not multiples of 64\n */\n setSize(width: number, height: number): this {\n validateResolution(width, height);\n this.width = width;\n this.height = height;\n return this;\n }\n\n /**\n * Set the main prompt (base scene description)\n * For multi-character prompts, use the array overload\n */\n setPrompt(base: string, characters?: string[]): this {\n this.prompt = base;\n if (characters) {\n this.characterPrompts = characters;\n }\n return this;\n }\n\n /**\n * Add character prompts for multi-character scenes\n */\n addCharacter(characterPrompt: string): this {\n this.characterPrompts.push(characterPrompt);\n return this;\n }\n\n /**\n * Set the negative prompt (what to avoid in generation)\n */\n setNegativePrompt(negative: string): this {\n this.negativePrompt = negative;\n return this;\n }\n\n /**\n * Set the random seed for reproducible generations\n */\n setSeed(seed: number): this {\n validateSeed(seed);\n this.seed = seed;\n return this;\n }\n\n /**\n * Set the number of sampling steps\n * @throws ValidationError if steps are out of range (1-50)\n */\n setSteps(steps: number): this {\n validateSteps(steps);\n this.steps = steps;\n return this;\n }\n\n /**\n * Set the guidance scale (CFG)\n * @throws ValidationError if scale is out of range (0-10)\n */\n setScale(scale: number): this {\n validateScale(scale);\n this.scale = scale;\n return this;\n }\n\n /**\n * Set the sampling algorithm\n */\n setSampler(sampler: NovelAISampler): this {\n this.sampler = sampler;\n return this;\n }\n\n /**\n * Set the UC preset (predefined negative prompt configuration)\n */\n setUCPreset(preset: UCPreset): this {\n this.ucPreset = preset;\n return this;\n }\n\n /**\n * Toggle automatic quality tags insertion\n */\n setQualityToggle(enabled: boolean): this {\n this.qualityToggle = enabled;\n return this;\n }\n\n /**\n * Enable SMEA (Sinusoidal Multipass Euler Ancestral)\n * @param dynamic - If true, enables dynamic SMEA variant\n */\n enableSMEA(dynamic = false): this {\n this.smea = true;\n this.smeaDyn = dynamic;\n return this;\n }\n\n /**\n * Disable SMEA\n */\n disableSMEA(): this {\n this.smea = false;\n this.smeaDyn = false;\n return this;\n }\n\n /**\n * Set the noise schedule algorithm\n */\n setNoiseSchedule(schedule: NoiseSchedule): this {\n this.noiseSchedule = schedule;\n return this;\n }\n\n /**\n * Build the V4 condition input structure for prompts\n */\n private buildV4ConditionInput(base: string, characters: string[]): V4ConditionInput {\n return {\n caption: {\n base_caption: base,\n char_captions: characters,\n },\n use_coords: false,\n use_order: true,\n legacy_uc: false,\n };\n }\n\n /**\n * Build the formatted input string for the API\n * Combines base prompt with character prompts using pipe delimiter\n */\n private buildInputString(): string {\n if (this.characterPrompts.length === 0) {\n return this.prompt;\n }\n return [this.prompt, ...this.characterPrompts].join(' | ');\n }\n\n /**\n * Build the complete API payload\n */\n buildPayload(): GenerateImagePayload {\n const parameters: NovelAIParameters = {\n width: this.width,\n height: this.height,\n scale: this.scale,\n sampler: this.sampler,\n steps: this.steps,\n n_samples: 1,\n seed: this.seed,\n negative_prompt: this.negativePrompt,\n\n // V4-specific structured prompts\n v4_prompt: this.buildV4ConditionInput(this.prompt, this.characterPrompts),\n v4_negative_prompt: this.buildV4ConditionInput(this.negativePrompt, []),\n\n // Quality and preset controls (camelCase - API requirement)\n qualityToggle: this.qualityToggle,\n ucPreset: this.ucPreset,\n\n // Technical flags (snake_case - API requirement)\n params_version: 3,\n noise_schedule: this.noiseSchedule,\n sm: this.smea,\n sm_dyn: this.smeaDyn,\n prefer_brownian: true,\n deliberate_euler_ancestral_bug: true,\n legacy: false,\n legacy_v3_extend: false,\n };\n\n return {\n input: this.buildInputString(),\n model: this.model,\n action: 'generate',\n parameters,\n };\n }\n\n /**\n * Execute the image generation request\n */\n async generate(): Promise<ImageResponse> {\n const payload = this.buildPayload();\n return this.client._execute(payload);\n }\n}\n","import type { ClientConfig, GenerateImagePayload, ImageResponse } from '../types';\nimport { APIClient } from '../network/APIClient';\nimport { ImageRequestBuilder } from '../builder/ImageRequestBuilder';\n\n/**\n * Main entry point for the NovelAI Image SDK\n * \n * @example\n * ```typescript\n * const client = new NovelAIClient({ token: process.env.NAI_TOKEN });\n * \n * const result = await client.image()\n * .setPrompt('1girl, cyberpunk, neon lights')\n * .setSize(832, 1216)\n * .generate();\n * \n * fs.writeFileSync('output.png', result.images[0]);\n * ```\n */\nexport class NovelAIClient {\n private readonly apiClient: APIClient;\n\n /**\n * Create a new NovelAI client\n * @param config - Client configuration including token and optional base URL\n */\n constructor(config: ClientConfig) {\n if (!config.token) {\n throw new Error('NovelAI API token is required');\n }\n\n this.apiClient = new APIClient({\n token: config.token,\n baseUrl: config.baseUrl,\n timeout: config.timeout,\n });\n }\n\n /**\n * Start building an image generation request\n * @returns A new ImageRequestBuilder instance\n */\n image(): ImageRequestBuilder {\n return new ImageRequestBuilder(this);\n }\n\n /**\n * Execute a generation request (called internally by the builder)\n * @internal\n */\n async _execute(payload: GenerateImagePayload): Promise<ImageResponse> {\n return this.apiClient.generateImage(payload);\n }\n}\n"]}
|
|
1
|
+
{"version":3,"sources":["../src/errors/index.ts","../src/utils/ZipParser.ts","../src/network/APIClient.ts","../src/types/Model.ts","../src/types/Sampler.ts","../src/utils/Validators.ts","../src/builder/ImageRequestBuilder.ts","../src/client/NovelAIClient.ts"],"names":["NovelAIModel","NovelAISampler","UCPreset","NoiseSchedule"],"mappings":"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","file":"index.js","sourcesContent":["/**\n * Base error class for all NovelAI SDK errors\n */\nexport class NovelAIError extends Error {\n public readonly statusCode?: number;\n\n constructor(message: string, statusCode?: number) {\n super(message);\n this.name = 'NovelAIError';\n this.statusCode = statusCode;\n }\n}\n\n/**\n * Authentication error (401/403)\n * Thrown when the API token is invalid or expired\n */\nexport class NovelAIAuthError extends NovelAIError {\n constructor(message = 'Authentication failed. Check your Persistent API Token (pst-...).') {\n super(message, 401);\n this.name = 'NovelAIAuthError';\n }\n}\n\n/**\n * Payment required error (402)\n * Thrown when the user has insufficient Anlas credits\n */\nexport class NovelAIPaymentError extends NovelAIError {\n constructor(message = 'Insufficient Anlas credits for this generation.') {\n super(message, 402);\n this.name = 'NovelAIPaymentError';\n }\n}\n\n/**\n * Validation error (400)\n * Thrown when the API rejects the payload due to schema issues\n */\nexport class NovelAIValidationError extends NovelAIError {\n public readonly details?: string;\n\n constructor(message: string, details?: string) {\n super(message, 400);\n this.name = 'NovelAIValidationError';\n this.details = details;\n }\n}\n\n/**\n * Network error\n * Thrown on timeouts, connection failures, or other network issues\n */\nexport class NovelAINetworkError extends NovelAIError {\n public readonly cause?: Error;\n\n constructor(message: string, cause?: Error) {\n super(message);\n this.name = 'NovelAINetworkError';\n this.cause = cause;\n }\n}\n\n/**\n * Rate limit error (429)\n * Thrown when too many requests are made\n */\nexport class NovelAIRateLimitError extends NovelAIError {\n public readonly retryAfter?: number;\n\n constructor(message = 'Rate limit exceeded. Please wait before retrying.', retryAfter?: number) {\n super(message, 429);\n this.name = 'NovelAIRateLimitError';\n this.retryAfter = retryAfter;\n }\n}\n\n/**\n * Server error (500+)\n * Thrown when the NovelAI server encounters an internal error\n */\nexport class NovelAIServerError extends NovelAIError {\n public readonly correlationId?: string;\n\n constructor(message = 'NovelAI server error. This may be due to payload schema issues.', correlationId?: string) {\n super(message, 500);\n this.name = 'NovelAIServerError';\n this.correlationId = correlationId;\n }\n}\n","/**\n * Isomorphic ZIP parser that works in both Node.js and browser environments\n * Extracts PNG files from NovelAI's application/x-zip-compressed response\n */\n\n/**\n * Detects if we're running in a Node.js environment\n */\nfunction isNodeEnvironment(): boolean {\n return (\n typeof process !== 'undefined' &&\n process.versions != null &&\n process.versions.node != null\n );\n}\n\n/**\n * Extract PNG files from a ZIP archive buffer\n * @param data - The raw ZIP archive data\n * @returns Array of extracted PNG file contents\n */\nexport async function extractImagesFromZip(\n data: ArrayBuffer | Uint8Array\n): Promise<Uint8Array[]> {\n const buffer = data instanceof ArrayBuffer ? new Uint8Array(data) : data;\n\n if (isNodeEnvironment()) {\n return extractWithAdmZip(buffer);\n } else {\n return extractWithFflate(buffer);\n }\n}\n\n/**\n * Node.js extraction using adm-zip\n */\nasync function extractWithAdmZip(buffer: Uint8Array): Promise<Uint8Array[]> {\n // Dynamic import for Node.js environment\n const AdmZip = (await import('adm-zip')).default;\n const zip = new AdmZip(Buffer.from(buffer));\n const entries = zip.getEntries();\n const images: Uint8Array[] = [];\n\n for (const entry of entries) {\n if (entry.entryName.endsWith('.png') && !entry.isDirectory) {\n const data = entry.getData();\n images.push(new Uint8Array(data));\n }\n }\n\n return images;\n}\n\n/**\n * Browser extraction using fflate\n */\nasync function extractWithFflate(buffer: Uint8Array): Promise<Uint8Array[]> {\n // Dynamic import for browser environment\n const { unzipSync } = await import('fflate');\n const unzipped = unzipSync(buffer);\n const images: Uint8Array[] = [];\n\n for (const [filename, data] of Object.entries(unzipped)) {\n if (filename.endsWith('.png')) {\n images.push(data);\n }\n }\n\n return images;\n}\n\n/**\n * Convert Uint8Array to Base64 string (useful for browser display)\n */\nexport function toBase64(data: Uint8Array): string {\n if (isNodeEnvironment()) {\n return Buffer.from(data).toString('base64');\n } else {\n // Browser environment\n let binary = '';\n for (let i = 0; i < data.length; i++) {\n binary += String.fromCharCode(data[i]);\n }\n return btoa(binary);\n }\n}\n\n/**\n * Convert Uint8Array to data URL for direct use in img src\n */\nexport function toDataURL(data: Uint8Array, mimeType = 'image/png'): string {\n return `data:${mimeType};base64,${toBase64(data)}`;\n}\n","import type { GenerateImagePayload, ImageResponse, APIErrorResponse } from '../types';\nimport {\n NovelAIError,\n NovelAIAuthError,\n NovelAIPaymentError,\n NovelAIValidationError,\n NovelAINetworkError,\n NovelAIRateLimitError,\n NovelAIServerError,\n} from '../errors';\nimport { extractImagesFromZip } from '../utils/ZipParser';\n\nconst DEFAULT_BASE_URL = 'https://image.novelai.net';\nconst DEFAULT_TIMEOUT = 60000;\nconst GENERATE_ENDPOINT = '/ai/generate-image';\n\nexport interface APIClientConfig {\n token: string;\n baseUrl?: string;\n timeout?: number;\n}\n\n/**\n * Low-level HTTP client for NovelAI API\n * Handles authentication, binary response parsing, and error mapping\n */\nexport class APIClient {\n private readonly token: string;\n private readonly baseUrl: string;\n private readonly timeout: number;\n\n constructor(config: APIClientConfig) {\n this.token = config.token;\n this.baseUrl = config.baseUrl ?? DEFAULT_BASE_URL;\n this.timeout = config.timeout ?? DEFAULT_TIMEOUT;\n }\n\n /**\n * Generate an image using the NovelAI API\n */\n async generateImage(payload: GenerateImagePayload): Promise<ImageResponse> {\n const url = `${this.baseUrl}${GENERATE_ENDPOINT}`;\n\n // Generate correlation ID for debugging\n const correlationId = this.generateCorrelationId();\n\n const controller = new AbortController();\n const timeoutId = setTimeout(() => controller.abort(), this.timeout);\n\n try {\n const response = await fetch(url, {\n method: 'POST',\n headers: {\n 'Authorization': `Bearer ${this.token}`,\n 'Content-Type': 'application/json',\n 'Accept': 'application/x-zip-compressed, application/json',\n 'x-correlation-id': correlationId,\n },\n body: JSON.stringify(payload),\n signal: controller.signal,\n });\n\n clearTimeout(timeoutId);\n\n if (!response.ok) {\n await this.handleErrorResponse(response, correlationId);\n }\n\n // Parse the ZIP response\n const arrayBuffer = await response.arrayBuffer();\n const images = await extractImagesFromZip(arrayBuffer);\n\n return {\n images,\n metadata: {\n seed: payload.parameters.seed,\n prompt: payload.input,\n model: payload.model,\n sampler: payload.parameters.sampler as string,\n steps: payload.parameters.steps,\n scale: payload.parameters.scale,\n },\n };\n } catch (error) {\n clearTimeout(timeoutId);\n\n if (error instanceof NovelAIError) {\n throw error;\n }\n\n if (error instanceof Error) {\n if (error.name === 'AbortError') {\n throw new NovelAINetworkError(`Request timed out after ${this.timeout}ms`, error);\n }\n throw new NovelAINetworkError(`Network error: ${error.message}`, error);\n }\n\n throw new NovelAINetworkError('An unknown error occurred');\n }\n }\n\n /**\n * Handle non-2xx responses and throw appropriate errors\n */\n private async handleErrorResponse(response: Response, correlationId: string): Promise<never> {\n let errorBody: APIErrorResponse | null = null;\n\n try {\n errorBody = await response.json() as APIErrorResponse;\n } catch {\n // Response may not be JSON\n }\n\n const message = errorBody?.message ?? errorBody?.error ?? response.statusText;\n\n switch (response.status) {\n case 400:\n throw new NovelAIValidationError(\n `Bad request: ${message}`,\n JSON.stringify(errorBody)\n );\n case 401:\n case 403:\n throw new NovelAIAuthError(message);\n case 402:\n throw new NovelAIPaymentError(message);\n case 429: {\n const retryAfter = response.headers.get('retry-after');\n throw new NovelAIRateLimitError(message, retryAfter ? parseInt(retryAfter) : undefined);\n }\n case 500:\n case 502:\n case 503:\n case 504:\n throw new NovelAIServerError(\n `Server error (${response.status}): ${message}. This may be caused by payload schema issues.`,\n correlationId\n );\n default:\n throw new NovelAIError(\n `HTTP ${response.status}: ${message}`,\n response.status\n );\n }\n }\n\n /**\n * Generate a 6-character alphanumeric correlation ID for debugging\n */\n private generateCorrelationId(): string {\n const chars = 'ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789';\n let result = '';\n for (let i = 0; i < 6; i++) {\n result += chars.charAt(Math.floor(Math.random() * chars.length));\n }\n return result;\n }\n}\n","/**\n * Supported NovelAI image generation models\n */\nexport enum NovelAIModel {\n /** V4.5 Full - Latest model with T5 encoding and multi-character support */\n V45_Full = \"nai-diffusion-4-5-full\",\n /** V4 Curated - More conservative aesthetic choices */\n V4_Curated = \"nai-diffusion-4-curated\",\n /** V4 Inpainting - For image editing and inpainting tasks */\n Inpainting = \"nai-diffusion-4-inpainting\",\n}\n","/**\n * Supported sampling algorithms for image generation\n */\nexport enum NovelAISampler {\n /** Standard Euler sampler */\n Euler = \"k_euler\",\n /** Euler Ancestral - recommended for anime-style generations */\n EulerAncestral = \"k_euler_ancestral\",\n /** DPM++ 2M - stable and aesthetic */\n DPM_2M = \"k_dpmpp_2m\",\n /** DPM++ 2S Ancestral */\n DPM_2S_Ancestral = \"k_dpmpp_2s_ancestral\",\n /** DPM++ SDE */\n DPM_SDE = \"k_dpmpp_sde\",\n /** DDIM V3 */\n DDIM = \"ddim_v3\",\n}\n\n/**\n * Preset negative prompt configurations\n */\nexport enum UCPreset {\n /** Heavy - Low Quality + Bad Anatomy */\n Heavy = 0,\n /** Light - Low Quality only */\n Light = 1,\n /** None - Use custom negative prompt only */\n None = 2,\n}\n\n/**\n * Noise schedule algorithms\n */\nexport enum NoiseSchedule {\n Native = \"native\",\n Karras = \"karras\",\n Exponential = \"exponential\",\n Polyexponential = \"polyexponential\",\n}\n","/**\n * Validation error for invalid SDK parameters\n */\nexport class ValidationError extends Error {\n constructor(message: string) {\n super(message);\n this.name = 'ValidationError';\n }\n}\n\n/**\n * Validates that image dimensions are multiples of 64\n * @throws ValidationError if dimensions are invalid\n */\nexport function validateResolution(width: number, height: number): void {\n if (!Number.isInteger(width) || !Number.isInteger(height)) {\n throw new ValidationError('Width and height must be integers');\n }\n if (width <= 0 || height <= 0) {\n throw new ValidationError('Width and height must be positive');\n }\n if (width % 64 !== 0) {\n throw new ValidationError(`Width must be a multiple of 64, got ${width}`);\n }\n if (height % 64 !== 0) {\n throw new ValidationError(`Height must be a multiple of 64, got ${height}`);\n }\n}\n\n/**\n * Validates that step count is within acceptable range\n * @throws ValidationError if steps are out of range\n */\nexport function validateSteps(steps: number): void {\n if (!Number.isInteger(steps)) {\n throw new ValidationError('Steps must be an integer');\n }\n if (steps < 1 || steps > 50) {\n throw new ValidationError(`Steps must be between 1 and 50, got ${steps}`);\n }\n}\n\n/**\n * Validates that scale (CFG) is within acceptable range\n * @throws ValidationError if scale is out of range\n */\nexport function validateScale(scale: number): void {\n if (typeof scale !== 'number' || isNaN(scale)) {\n throw new ValidationError('Scale must be a number');\n }\n if (scale < 0 || scale > 10) {\n throw new ValidationError(`Scale must be between 0 and 10, got ${scale}`);\n }\n}\n\n/**\n * Validates that seed is a valid unsigned 32-bit integer\n */\nexport function validateSeed(seed: number): void {\n if (!Number.isInteger(seed)) {\n throw new ValidationError('Seed must be an integer');\n }\n if (seed < 0 || seed > 4294967295) {\n throw new ValidationError(`Seed must be between 0 and 2^32-1, got ${seed}`);\n }\n}\n\n/**\n * Warning result for prompt length check\n */\nexport interface PromptWarning {\n isWarning: boolean;\n message?: string;\n length: number;\n limit: number;\n}\n\n/**\n * Check if prompt length exceeds recommended limit\n * T5 encoder has different tokenization than CLIP, so this is a heuristic\n * @param prompt - The full prompt string\n * @param limit - Character limit (default: 2000)\n * @returns Warning object with details\n */\nexport function checkPromptLength(prompt: string, limit = 2000): PromptWarning {\n const length = prompt.length;\n const isWarning = length > limit;\n \n return {\n isWarning,\n message: isWarning \n ? `Prompt length (${length} chars) exceeds recommended limit of ${limit}. This may cause truncation or unexpected results.`\n : undefined,\n length,\n limit,\n };\n}\n","import type { NovelAIClient } from '../client/NovelAIClient';\nimport type {\n GenerateImagePayload,\n NovelAIParameters,\n V4ConditionInput,\n ImageResponse,\n} from '../types';\nimport { NovelAIModel, NovelAISampler, UCPreset, NoiseSchedule } from '../types';\nimport { validateResolution, validateSteps, validateScale, validateSeed } from '../utils/Validators';\n\n/**\n * Fluent builder for constructing NovelAI image generation requests\n * Provides method chaining and compile-time type safety\n */\nexport class ImageRequestBuilder {\n private client: NovelAIClient;\n\n // Core parameters with sensible defaults\n private model: NovelAIModel = NovelAIModel.V45_Full;\n private width = 832;\n private height = 1216;\n private prompt = '';\n private characterPrompts: string[] = [];\n private negativePrompt = '';\n private characterNegativePrompts: string[] = [];\n private seed: number = Math.floor(Math.random() * 4294967295);\n private steps = 23;\n private scale = 5.0;\n private nSamples = 1;\n private sampler: NovelAISampler = NovelAISampler.EulerAncestral;\n private ucPreset: UCPreset = UCPreset.Heavy;\n private qualityToggle = true;\n private smea = false;\n private smeaDyn = false;\n private dynamicThresholding = false;\n private noiseSchedule: NoiseSchedule = NoiseSchedule.Karras;\n\n constructor(client: NovelAIClient) {\n this.client = client;\n }\n\n /**\n * Set the model to use for generation\n */\n setModel(model: NovelAIModel): this {\n this.model = model;\n return this;\n }\n\n /**\n * Set the output image dimensions\n * @throws ValidationError if dimensions are not multiples of 64\n */\n setSize(width: number, height: number): this {\n validateResolution(width, height);\n this.width = width;\n this.height = height;\n return this;\n }\n\n /**\n * Set the main prompt (base scene description)\n * For multi-character prompts, use the array overload\n */\n setPrompt(base: string, characters?: string[]): this {\n this.prompt = base;\n if (characters) {\n this.characterPrompts = characters;\n }\n return this;\n }\n\n /**\n * Add character prompts for multi-character scenes\n */\n addCharacter(characterPrompt: string): this {\n this.characterPrompts.push(characterPrompt);\n return this;\n }\n\n /**\n * Set the negative prompt (what to avoid in generation)\n * Optionally provide per-character negative prompts\n */\n setNegativePrompt(base: string, characterNegatives?: string[]): this {\n this.negativePrompt = base;\n if (characterNegatives) {\n this.characterNegativePrompts = characterNegatives;\n }\n return this;\n }\n\n /**\n * Add a per-character negative prompt\n * Should correspond to character prompts added via addCharacter()\n */\n addCharacterNegative(negativePrompt: string): this {\n this.characterNegativePrompts.push(negativePrompt);\n return this;\n }\n\n /**\n * Set the random seed for reproducible generations\n */\n setSeed(seed: number): this {\n validateSeed(seed);\n this.seed = seed;\n return this;\n }\n\n /**\n * Set the number of sampling steps\n * @throws ValidationError if steps are out of range (1-50)\n */\n setSteps(steps: number): this {\n validateSteps(steps);\n this.steps = steps;\n return this;\n }\n\n /**\n * Set the guidance scale (CFG)\n * @throws ValidationError if scale is out of range (0-10)\n */\n setScale(scale: number): this {\n validateScale(scale);\n this.scale = scale;\n return this;\n }\n\n /**\n * Set the number of images to generate in a single request\n * Note: Each additional sample consumes Anlas credits\n * @param count - Number of images (1-4 typically supported)\n */\n setBatchSize(count: number): this {\n if (!Number.isInteger(count) || count < 1) {\n throw new Error('Batch size must be a positive integer');\n }\n this.nSamples = count;\n return this;\n }\n\n /**\n * Set the sampling algorithm\n */\n setSampler(sampler: NovelAISampler): this {\n this.sampler = sampler;\n return this;\n }\n\n /**\n * Set the UC preset (predefined negative prompt configuration)\n */\n setUCPreset(preset: UCPreset): this {\n this.ucPreset = preset;\n return this;\n }\n\n /**\n * Toggle automatic quality tags insertion\n */\n setQualityToggle(enabled: boolean): this {\n this.qualityToggle = enabled;\n return this;\n }\n\n /**\n * Enable SMEA (Sinusoidal Multipass Euler Ancestral)\n * @param dynamic - If true, enables dynamic SMEA variant\n */\n enableSMEA(dynamic = false): this {\n this.smea = true;\n this.smeaDyn = dynamic;\n return this;\n }\n\n /**\n * Disable SMEA\n */\n disableSMEA(): this {\n this.smea = false;\n this.smeaDyn = false;\n return this;\n }\n\n /**\n * Set the noise schedule algorithm\n */\n setNoiseSchedule(schedule: NoiseSchedule): this {\n this.noiseSchedule = schedule;\n return this;\n }\n\n /**\n * Enable dynamic thresholding\n * Enhances contrast at high CFG scales (scale > 7)\n */\n enableDynamicThresholding(): this {\n this.dynamicThresholding = true;\n return this;\n }\n\n /**\n * Disable dynamic thresholding\n */\n disableDynamicThresholding(): this {\n this.dynamicThresholding = false;\n return this;\n }\n\n /**\n * Build the V4 condition input structure for prompts\n */\n private buildV4ConditionInput(base: string, characters: string[]): V4ConditionInput {\n return {\n caption: {\n base_caption: base,\n char_captions: characters,\n },\n use_coords: false,\n use_order: true,\n legacy_uc: false,\n };\n }\n\n /**\n * Build the formatted input string for the API\n * Combines base prompt with character prompts using pipe delimiter\n */\n private buildInputString(): string {\n if (this.characterPrompts.length === 0) {\n return this.prompt;\n }\n return [this.prompt, ...this.characterPrompts].join(' | ');\n }\n\n /**\n * Build the complete API payload\n */\n buildPayload(): GenerateImagePayload {\n const parameters: NovelAIParameters = {\n width: this.width,\n height: this.height,\n scale: this.scale,\n sampler: this.sampler,\n steps: this.steps,\n n_samples: this.nSamples,\n seed: this.seed,\n negative_prompt: this.negativePrompt,\n\n // V4-specific structured prompts\n v4_prompt: this.buildV4ConditionInput(this.prompt, this.characterPrompts),\n v4_negative_prompt: this.buildV4ConditionInput(this.negativePrompt, this.characterNegativePrompts),\n\n // Quality and preset controls (camelCase - API requirement)\n qualityToggle: this.qualityToggle,\n ucPreset: this.ucPreset,\n\n // Technical flags (snake_case - API requirement)\n params_version: 3,\n noise_schedule: this.noiseSchedule,\n sm: this.smea,\n sm_dyn: this.smeaDyn,\n dynamic_thresholding: this.dynamicThresholding,\n prefer_brownian: true,\n deliberate_euler_ancestral_bug: true,\n legacy: false,\n legacy_v3_extend: false,\n };\n\n return {\n input: this.buildInputString(),\n model: this.model,\n action: 'generate',\n parameters,\n };\n }\n\n /**\n * Execute the image generation request\n */\n async generate(): Promise<ImageResponse> {\n const payload = this.buildPayload();\n return this.client._execute(payload);\n }\n}\n","import type { ClientConfig, GenerateImagePayload, ImageResponse } from '../types';\nimport { APIClient } from '../network/APIClient';\nimport { ImageRequestBuilder } from '../builder/ImageRequestBuilder';\n\n/**\n * Main entry point for the NovelAI Image SDK\n * \n * @example\n * ```typescript\n * const client = new NovelAIClient({ token: process.env.NAI_TOKEN });\n * \n * const result = await client.image()\n * .setPrompt('1girl, cyberpunk, neon lights')\n * .setSize(832, 1216)\n * .generate();\n * \n * fs.writeFileSync('output.png', result.images[0]);\n * ```\n */\nexport class NovelAIClient {\n private readonly apiClient: APIClient;\n\n /**\n * Create a new NovelAI client\n * @param config - Client configuration including token and optional base URL\n */\n constructor(config: ClientConfig) {\n if (!config.token) {\n throw new Error('NovelAI API token is required');\n }\n\n this.apiClient = new APIClient({\n token: config.token,\n baseUrl: config.baseUrl,\n timeout: config.timeout,\n });\n }\n\n /**\n * Start building an image generation request\n * @returns A new ImageRequestBuilder instance\n */\n image(): ImageRequestBuilder {\n return new ImageRequestBuilder(this);\n }\n\n /**\n * Execute a generation request (called internally by the builder)\n * @internal\n */\n async _execute(payload: GenerateImagePayload): Promise<ImageResponse> {\n return this.apiClient.generateImage(payload);\n }\n}\n"]}
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "novelai-image-sdk",
|
|
3
|
-
"version": "1.
|
|
3
|
+
"version": "1.1.0",
|
|
4
4
|
"description": "Type-safe TypeScript SDK for NovelAI V4.5 image generation API",
|
|
5
5
|
"type": "module",
|
|
6
6
|
"main": "./dist/index.cjs",
|
|
@@ -40,7 +40,7 @@
|
|
|
40
40
|
"sdk"
|
|
41
41
|
],
|
|
42
42
|
"author": "",
|
|
43
|
-
"license": "
|
|
43
|
+
"license": "Apache-2.0",
|
|
44
44
|
"dependencies": {
|
|
45
45
|
"adm-zip": "^0.5.10",
|
|
46
46
|
"fflate": "^0.8.2"
|