Skip to main content
Builtins catalog / nika:image_generate

Media

Tool family from the canonical registry.

invoke

Call this builtin through the invoke verb.

Read this contract

This reference preserves the specification at the revision linked below. Source examples are fragments: their surrounding tasks, inputs and permissions are not supplied here. Consult engine status and nika catalog --tools --json for the installed implementation; a registry declaration is not a runtime qualification.

Usage and behavior

illustration
Text-to-image generation as an asset pipeline, not a blob pipe: images are saved to output_dir: and the output carries paths + dimensions + sha256 (+ a provenance manifest) โ€” image bytes NEVER ride workflow outputs (no base64 in tasks.X.output, logs, or traces ยท normative). Filenames (normative grammar) ยท {stem}-{provider}-{modelslug}-{index}-{sha8}.{ext} ยท every component sanitized to [a-z0-9._-] with no separators; name collisions probe -2..-99; an IDENTICAL payload already on disk is an idempotent re-run (no duplicate). The manifest lands beside the assets as {stem}-{provider}-{modelslug}-{batchsha8}.manifest.json (manifest_version: 1 ยท resolved request echo ยท per-image paths/dimensions/sha256 ยท usage ยท warnings ยท caller metadata: โ€” and NEVER a credential: keys live a composition layer away by construction). Output (normalized ยท every provider + mock) ยท { provider, model, mode, prompt, revised_prompt, provider_text, created_at, count, images: [{ index, path, filename, mime_type, format, width, height, size_bytes, sha256, provider, model, seed, variant_id, warnings, metadata }], usage: { input_tokens, output_tokens, total_tokens, thoughts_tokens }, cost_usd, warnings, manifest_path, output_dir } โ€” absent usage axes are null, never zero-that-looks-real. cost_usd is the renderโ€™s REAL spend when the provider reports it exactly (xai bills cost_in_usd_ticks in the response ยท 1 cent = 10โธ ticks) and null otherwise โ€” never an estimate dressed as truth. Invoke-cost metering (normative) ยท a tool whose structured output carries a top-level numeric cost_usd reports real spend; engines SHOULD meter it into the runโ€™s cost ledger through the same honest-spend channel infer: rides. Security (engine MUST) ยท provider endpoints are ENGINE-FIXED constants (never workflow data โ€” the provider egress is engine transport, exactly like infer:; permits.net.http does not govern it, permits.tools + permits.fs DO; the local base URL is ENGINE CONFIG resolved at the composition root โ€” NIKA_IMAGE_LOCAL_URL, default LocalAIโ€™s http://localhost:8080 โ€” still never workflow data) ยท decode validation is HEADER-ONLY (magic bytes + PNG IHDR / JPEG SOF / WebP VP8-VP8L-VP8X dimensions ยท no pixel decode โ†’ no decompression-bomb surface ยท declared-vs-actual mismatch is a warning, a non-image payload is a hard error) ยท atomic writes (temp+rename) ยท API keys are engine-configured (env/config at the composition root), never workflow args, never logged, never echoed. Warnings (normative shape) ยท every tolerated-but-lossy mapping lands a stable code: message warning string (size_conflict: ยท compression_ignored: ยท seed_unsupported: ยท quality_folded: ยท format_mismatch: ยท gemini_size_class: ยท xai_size_class: ยท aspect_remapped: ยท count_shortfall: ยท revised_prompt_clamped: ยท provider_option_unknown: ยท provider_text_clamped: ยท โ€ฆ) in warnings โ€” silent degradation is non-conformant. provider_text/revised_prompt are captions, not payload channels (normative) ยท a providerโ€™s accompanying text MUST be bounded by the engine (the reference engine clamps at 2 000 chars with a provider_text_clamped: warning) โ€” a multimodal response interleaving megabytes of text (or base64-shaped junk) must never ride workflow outputs, the manifest, or the debug: echo unbounded. Result URLs are never fetched (normative) ยท engines request response_format: b64_json on url-capable wires (openai-compat ยท xai) and MUST refuse a url-only response with an actionable error โ€” fetching a provider-supplied result URL would reopen the SSRF/net-boundary surface the const-endpoint design closed. The provenance manifest and output carry endpoint_host (which server actually rendered the asset โ€” load- bearing for local, where the endpoint is configurable). Content credentials: detect-and-PRESERVE (normative) ยท upstream generators sign their returned bytes (OpenAI images and Googleโ€™s media models emit C2PA manifests as of mid-2026 ยท carriage: PNG caBX chunk ยท JPEG APP11 JUMBF ยท WebP/WAV RIFF C2PA ยท MP3 ID3v2 GEOB application/c2pa), and C2PA hard bindings hash the assetโ€™s byte ranges โ€” any engine-side insert into a signed payload converts valid credentials into ยซ present but tampered ยป, which is worse than stripping them. Engines MUST detect these signals before any in-file write, MUST stand their own embed down when credentials are present, and SHOULD surface presence as content_credentials in output + manifest (values are DETECTION labels โ€” an engine that has not cryptographically validated the manifest must never say ยซ verified ยป). Provider-declared watermarking (e.g. SynthID โ€” detectable only by the vendor) MAY be surfaced as a watermark_declared manifest fact, marked as declared, never as verified. Preserving machine-readable marks is also the EU AI Act Article 50 robustness expectation (in force 2026-08-02). Provenance travels IN the file (PNG) ยท engines SHOULD embed the deterministic provenance core (tool ยท engine version ยท provider ยท model ยท clamped prompt ยท seed โ€” no timestamp, so byte-determinism holds) as a nika tEXt chunk in saved PNG renders โ€” the ComfyUI/InvokeAI interchange practice: a sidecar manifest answers ยซ where does this come from? ยป only until the file is copied without it. JPEG/WebP have no equally-universal text container and are documented as manifest-only, never silently faked. Throws ยท NIKA-BUILTIN-IMAGE_GENERATE-001 invalid arguments (incl. the v0.1 RESERVED options ยท validation_error) ยท -002 provider unavailable (missing credentials / image plane unwired ยท validation_error) ยท -003 provider request failed (network_error ยท transient: true for 5xx/408/429 + timeout/connection ยท details.status_code) ยท -004 no image / malformed response (tool_error) ยท -005 content policy block (moderation / safety finish reasons ยท security_error ยท never transient ยท details {finish_reason? ยท moderation_details?}) ยท -006 save/manifest write failed (tool_error) ยท -007 image validation failed (magic mismatch ยท dimension/byte bounds ยท tool_error). Plus the boundary NIKA-SEC-004 (an output_dir: outside permits.fs.write).

Arguments

Pass the values required by the tool contract.

Permissions

Understand authority before granting effects.

Errors and recovery

Read diagnostics and choose a recovery policy.

Workflow templates

Put the fragment inside a complete workflow.

Contract provenance

Read the pinned specification ยท Canonical registry. Tool identity: nika:image_generate. Specification revision: f8c5df2127c7. The Lab language identity is language:tool:image_generate; the registry view is ecosystem:tool/nika:image_generate. They refer to this contract without merging their graph identities.