UNPKG

sd-parsers

Version:

A library to read metadata from images created by Stable Diffusion

121 lines 5.14 kB
"use strict"; Object.defineProperty(exports, "__esModule", { value: true }); exports.AUTOMATIC1111Parser = void 0; const parser_1 = require("./parser"); const data_1 = require("../data"); const exceptions_1 = require("../exceptions"); const SAMPLER_PARAMS = ['Sampler', 'CFG scale', 'Seed', 'Steps', 'ENSD', 'Schedule type', 'Denoising strength', 'Clip skip']; const REPLACEMENT_RULES = [ ['Schedule type', 'scheduler'], ['CFG scale', 'cfg_scale'], ['Seed', 'seed'], ['Steps', 'steps'], ['Denoising strength', 'denoising_strength'], ['Clip skip', 'clip_skip'] ]; /** * Parser for images generated by AUTOMATIC1111's stable-diffusion-webui or similar */ class AUTOMATIC1111Parser extends parser_1.Parser { constructor() { super(...arguments); this.generator = data_1.Generators.AUTOMATIC1111; } async parse(parameters) { let lines; try { if (!parameters.parameters || typeof parameters.parameters !== 'string') { throw new Error('parameters field is missing or not a string'); } lines = parameters.parameters.split('\n'); } catch (error) { throw new exceptions_1.ParserError(`Error reading parameter string: ${error}`); } try { const { infoIndex, samplerInfo, metadata } = getSamplerInfo(lines); const prompts = lines.slice(0, infoIndex).join('\n').split('Negative prompt:'); const prompt = prompts[0]?.trim() || ''; const negativePrompt = prompts[1]?.trim() || ''; const samplerParams = Object.fromEntries((0, parser_1.popKeys)(SAMPLER_PARAMS, samplerInfo)); const samplerName = samplerParams.Sampler || 'unknown'; delete samplerParams.Sampler; const normalizedParams = this.normalizeParameters(samplerParams, REPLACEMENT_RULES); const modelName = metadata.Model; const modelHash = metadata['Model hash']; delete metadata.Model; delete metadata['Model hash']; const model = (modelName || modelHash) ? (0, data_1.createModel)({ name: modelName, hash: modelHash }) : undefined; const promptList = prompt ? [(0, data_1.createPrompt)(prompt)] : []; const negativePromptList = negativePrompt ? [(0, data_1.createPrompt)(negativePrompt)] : []; const sampler = (0, data_1.createSampler)(samplerName, normalizedParams, { model, prompts: promptList, negativePrompts: negativePromptList }); return (0, data_1.createPromptInfo)(this.generator, [sampler], metadata, parameters); } catch (error) { // Fallback: if no sampler info found, treat entire string as prompt const fullText = lines.join('\n'); const prompts = fullText.split('Negative prompt:'); const prompt = prompts[0]?.trim() || ''; const negativePrompt = prompts[1]?.trim() || ''; const promptList = prompt ? [(0, data_1.createPrompt)(prompt)] : []; const negativePromptList = negativePrompt ? [(0, data_1.createPrompt)(negativePrompt)] : []; const sampler = (0, data_1.createSampler)('unknown', {}, { prompts: promptList, negativePrompts: negativePromptList }); return (0, data_1.createPromptInfo)(this.generator, [sampler], {}, parameters); } } } exports.AUTOMATIC1111Parser = AUTOMATIC1111Parser; /** * Extract sampler information from parameter lines */ function getSamplerInfo(lines) { for (let index = lines.length - 1; index >= 0; index--) { const line = lines[index]; const metadata = extractMetadata(line); const samplerInfo = Object.fromEntries((0, parser_1.popKeys)(SAMPLER_PARAMS, { ...metadata })); if (Object.keys(samplerInfo).length >= 3) { return { infoIndex: index, samplerInfo, metadata }; } } throw new exceptions_1.ParserError('No sampler information found'); } /** * Extract metadata from a parameter line */ function extractMetadata(line) { const metadata = {}; // Try to extract hashes const hashMatch = line.match(/(?:,\s*)?Hashes:\s*(\{[^}]*\})\s*/); if (hashMatch) { try { metadata.Hashes = JSON.parse(hashMatch[1]); line = line.substring(0, hashMatch.index) + line.substring(hashMatch.index + hashMatch[0].length); } catch (error) { // Ignore JSON parse errors } } // Extract key-value pairs for (const item of line.split(',')) { try { const colonIndex = item.indexOf(':'); if (colonIndex > 0) { const key = item.substring(0, colonIndex).trim(); const value = item.substring(colonIndex + 1).trim(); metadata[key] = value; } } catch (error) { // Ignore parsing errors for individual items } } return metadata; } //# sourceMappingURL=automatic1111.js.map