windmill-labs/windmill · error · Error
Invalid image object${typeof resolvedConfig.source}
Error message
Invalid image object${typeof resolvedConfig.source} What it means
AppImage.svelte's loadImage() resolves the image component's configuration source. After trying configured resource/URL resolution, it accepts only a string source; if resolvedConfig.source is truthy but not a string (e.g. an object), it throws 'Invalid image object<type>' to signal a malformed app component configuration.
Source
Thrown at frontend/src/lib/components/apps/components/display/AppImage.svelte:63
let imageUrl: string | undefined = $state(undefined)
let token = getContext<{ token?: string }>('AuthToken')
async function loadImage() {
if (isPartialS3Object(resolvedConfig.source)) {
imageUrl = await getS3File({
source: resolvedConfig.source.s3,
storage: resolvedConfig.source.storage,
presigned: resolvedConfig.source.presigned,
appPath: $appPath,
username: $userStore?.username,
workspace,
token: token?.token,
isEditor,
configuration
})
} else if (resolvedConfig.source && typeof resolvedConfig.source !== 'string') {
throw new Error('Invalid image object' + typeof resolvedConfig.source)
} else if (
resolvedConfig.sourceKind === 's3 (workspace storage)' ||
resolvedConfig.source?.startsWith('s3://')
) {
imageUrl = await getS3File({
source: resolvedConfig.source?.replace('s3://', ''),
appPath: $appPath,
username: $userStore?.username,
workspace,
token: token?.token,
isEditor,
configuration
})
} else if (resolvedConfig.sourceKind === 'png encoded as base64') {
imageUrl = 'data:image/png;base64,' + resolvedConfig.source
} else if (resolvedConfig.sourceKind === 'jpeg encoded as base64') {
imageUrl = 'data:image/jpeg;base64,' + resolvedConfig.source
} else if (resolvedConfig.sourceKind === 'svg encoded as base64') {View on GitHub (pinned to e474e8803c)
Solutions
- Inspect the component's source config in the app editor and make it resolve to a string (e.g. append .url or .path to the bound step output)
- If the value comes from a variable/step output, stringify the URL at the producing step
- Use the resource-based branch (configured resource or s3:// string) instead of passing a raw object
Example fix
// before
source: `${inputs1.result}` // resolves to an object
// after
source: `${inputs1.result.url}` Defensive patterns
Strategy: validation
Validate before calling
const src = resolvedConfig.source
if (src && typeof src !== 'string') {
throw new TypeError(`Image source must be a string URL, got ${typeof src}`)
} Type guard
function isStringSource(s: unknown): s is string {
return typeof s === 'string'
} Try / catch
try {
await loadImage()
} catch (e) {
if (e.message.startsWith('Invalid image object')) {
console.error('Fix image component source: it resolved to a non-string', e)
} else throw e
} Prevention
- Bind the image source to a string field (.url/.path), never a whole object result
- Preview the component with sample data to catch non-string resolutions early
- Use resources or s3:// strings for stored images
When it happens
Trigger: A windmill app image component whose 'source' configuration field (possibly template-resolved via configuration) evaluates to an object or array instead of a URL string.
Common situations: Binding the image source to a step output that returns an object (e.g. {url: ...}) instead of a string; forgetting to append .url/.path on a JSON result; a misconfigured resource template resolving to structured data.
Related errors
- Invalid PDF source object${typeof source}
- ${what} failed:\n${output}
- No instance found, please add one first
- No local instance profile named ${instanceName}
- No active instance. Run 'wmill instance add' or pass --insta
AI-assisted analysis of windmill-labs/windmill@e474e8803c (2026-09-03).
Data as JSON: /api/errors/d17988a45fc2f016.
Report an issue: GitHub.