# AI image generation pipeline configuration # # Consumed exclusively by scripts/content/generate-images.nu (dev tooling). # NOT merged into site/config/index.ncl — this is not a runtime site config. # # Load: nickel export --format json site/config/image-generation.ncl # | from json | get image_generation # # Sensitive values (OPENAI_API_KEY) live in .env — never inline here. let DalleSizeContract = std.contract.from_validator (fun value => if (std.is_string value) && ( value == "1024x1024" || value == "1024x1792" || value == "1792x1024" ) then 'Ok else ('Error "Must be a valid DALL-E 3 dimension: 1024x1024, 1024x1792, or 1792x1024") ) in let DalleQualityContract = std.contract.from_validator (fun value => # dall-e-3: "standard" | "hd" # gpt-image-1: "low" | "medium" | "high" if value == "standard" || value == "hd" || value == "low" || value == "medium" || value == "high" then 'Ok else ('Error "Must be 'standard', 'hd' (dall-e-3) or 'low', 'medium', 'high' (gpt-image-1)") ) in let NonEmptyString = std.contract.from_validator (fun value => if (std.is_string value) && (std.string.length value > 0) then 'Ok else ('Error "Must be a non-empty string") ) in let ImageSizesContract = { thumbnail | String | DalleSizeContract, feature | String | DalleSizeContract, } in let ImageStylesContract = { blog | String | NonEmptyString, recipes | String | NonEmptyString, activities | String | NonEmptyString, projects | String | NonEmptyString, } in let ImageGenerationConfig = { model | String | NonEmptyString | doc "Image model: 'dall-e-3' (hd/standard) or 'gpt-image-1' (low/medium/high)", quality | String | DalleQualityContract | doc "dall-e-3: 'standard' | 'hd' gpt-image-1: 'low' | 'medium' | 'high'", templates_dir | String | NonEmptyString | doc "Path to Tera prompt template files relative to project root", sizes | ImageSizesContract | doc "DALL-E image dimensions per image type", styles | ImageStylesContract | doc "Visual style directives per content type — appended to every prompt", } in { image_generation = { model = "dall-e-3", quality = "hd", templates_dir = "site/templates/image-prompts", sizes = { thumbnail = "1024x1024", feature = "1792x1024", }, styles = { blog = "Dark terminal/editor aesthetic. Rust-orange (#CE422B) accent on deep charcoal. Code or circuit motifs. No humans. High contrast. 16:9 composition.", recipes = "Clean technical blueprint/schematic. Dark navy, crisp white line-art, cyan accent. Engineering diagram feel. No humans. 16:9.", activities = "Professional conference keynote. Dark stage, single bold centered composition. Abstract geometric. No stock photos. No humans. 16:9.", projects = "Product showcase and brand reveal. Dark background, Rust-orange and slate-blue palette. Technical, premium, minimal. No humans. 16:9.", }, } | ImageGenerationConfig, }