{"record":{"id":"81e318368d6e0f00","repo":"BoundaryML/baml","slug":"badserialization-type-media-type-is-not-supported-in-outputs","errorCode":"BadSerialization","errorMessage":"type '{media_type}' is not supported in outputs","messagePattern":"type '(.+?)' is not supported in outputs","errorType":"exception","errorClass":"minijinja::Error","httpStatus":null,"severity":"error","filePath":"engine/baml-lib/jinja-runtime/src/output_format/types.rs","lineNumber":699,"sourceCode":"    /// This function is the entry point for recursive schema rendering.\n    ///\n    /// Read the documentation of [`Self::render_possibly_hoisted_type`] for\n    /// more details.\n    fn inner_type_render(\n        &self,\n        options: &RenderOptions,\n        field: &TypeIR,\n        render_ctx: &RenderCtx,\n    ) -> Result<String, minijinja::Error> {\n        Ok(match field {\n            TypeIR::Primitive(t, _) => match t {\n                TypeValue::String => \"string\".to_string(),\n                TypeValue::Int => \"int\".to_string(),\n                TypeValue::Float => \"float\".to_string(),\n                TypeValue::Bool => \"bool\".to_string(),\n                TypeValue::Null => self.render_null_type(options).to_string(),\n                TypeValue::Media(media_type) => {\n                    return Err(minijinja::Error::new(\n                        minijinja::ErrorKind::BadSerialization,\n                        format!(\"type '{media_type}' is not supported in outputs\"),\n                    ))\n                }\n            },\n            TypeIR::Literal(v, _) => v.to_string(),\n            TypeIR::Enum { name: e, .. } => {\n                let Some(enm) = self.enums.get(e) else {\n                    return Err(minijinja::Error::new(\n                        minijinja::ErrorKind::BadSerialization,\n                        format!(\"Enum {e} not found\"),\n                    ));\n                };\n\n                if render_ctx.hoisted_enums.contains(&enm.name.name) {\n                    enm.name.rendered_name().to_string()\n                } else {\n                    enm.values","sourceCodeStart":681,"sourceCodeEnd":717,"githubUrl":"https://github.com/BoundaryML/baml/blob/bd85ce9dee1463ff04d27efd20531013a4ff46c1/engine/baml-lib/jinja-runtime/src/output_format/types.rs#L681-L717","documentation":"While rendering the output schema for a prompt, BAML encountered a type whose kind is a media type (image, audio, video, pdf). Media types are valid in function inputs but cannot be represented in the text schema shown to the LLM, so the serializer raises BadSerialization. The function's output type must be restricted to primitives, enums, classes, lists, maps, and unions.","triggerScenarios":"Declaring a BAML function whose return type is or contains `image`, `audio`, `video`, or `pdf` (e.g. `function F() -> image`), which causes output_format rendering to hit TypeValue::Media.","commonSituations":"Copy-pasting an input type to the output position; wrapping media in unions/classes that appear in outputs; intending the model to 'return an image' without realizing outputs are text schemas.","solutions":["Change the function's return type to a non-media type (e.g. string, or a class with a url/path string field).","Move the media type to the function inputs; outputs must be serializable text schema types.","If you need binary results, have the LLM return a reference (URL/path) as a string field instead."],"exampleFix":"// before\nfunction ExtractImage() -> image\n// after\nfunction ExtractImage() -> string  // or a class with an image_url string field","handlingStrategy":"validation","validationCode":"// scan BAML function signatures for media types in outputs before compiling\nconst MEDIA = [\"image\",\"audio\",\"video\",\"pdf\"];\nconst bad = functions.filter(f => MEDIA.some(m => f.outputType.includes(m)));\nif (bad.length) throw new Error(`Media types not allowed in outputs: ${bad.map(f=>f.name)}`);","typeGuard":"const outputHasMediaType = (sig: string) =>\n  /->\\s*.*(image|audio|video|pdf)\\b/.test(sig);","tryCatchPattern":"try {\n  await renderOutputFormat(fn);\n} catch (e) {\n  if (String(e).includes(\"is not supported in outputs\")) {\n    throw new Error(`Function ${fn.name} must not return media types`);\n  }\n  throw e;\n}","preventionTips":["Restrict function outputs to primitives, enums, classes, lists, maps, and unions.","Return URLs/paths as strings when binary data is involved.","Keep media types in function inputs only.","Add a code review check for media keywords after `->` in .baml files."],"tags":["baml","types","media","output-schema"],"backgroundTag":"unsupported-operation","analyzedSha":"bd85ce9dee1463ff04d27efd20531013a4ff46c1","analyzedAt":"2026-09-12T03:38:25.718Z","contentChangedAt":"2026-09-12T03:38:25.718Z","schemaVersion":2},"datasetVersion":"2026-09-23T08:17:48.524Z"}