{"record":{"id":"24b1b72739f67c2c","repo":"QuestPDF/QuestPDF","slug":"the-layers-component-needs-to-have-exactly-one-pri-24b1b7","errorCode":null,"errorMessage":"The Layers component needs to have exactly one primary layer. It has {primaryLayers}.","messagePattern":"The Layers component needs to have exactly one primary layer\\. It has (.+?)\\.","errorType":"exception","errorClass":"DocumentComposeException","httpStatus":null,"severity":"error","filePath":"src/dotnet/library/QuestPDF/Fluent/LayerExtensions.cs","lineNumber":58,"sourceCode":"        public IContainer Layer() => Layer(false);\n        \n        /// <summary>\n        /// Sets the primary content for the container. \n        /// </summary>\n        /// <remarks>\n        /// Exactly one primary layer should be defined.\n        /// </remarks>\n        public IContainer PrimaryLayer() => Layer(true);\n\n        internal void Validate()\n        {\n            var primaryLayers = Layers.Children.Count(x => x.IsPrimary);\n\n            if (primaryLayers == 0)\n                throw new DocumentComposeException(\"The Layers component needs to have exactly one primary layer. It has none.\");\n            \n            if (primaryLayers != 1)\n                throw new DocumentComposeException($\"The Layers component needs to have exactly one primary layer. It has {primaryLayers}.\");\n        }\n    }\n    \n    public static class LayerExtensions\n    {\n        /// <summary>\n        /// <para>Adds content either underneath (as a background) or on top of (as a watermark) the main content.</para>\n        /// <para>The main layer supports paging, can span multiple pages, and determines the container's target length.</para>\n        /// <para>Additional layers can also span multiple pages and are repeated on each one.</para>\n        /// <a href=\"https://www.questpdf.com/api-reference/layers.html\">Learn more</a>\n        /// </summary>\n        /// <param name=\"handler\">Handler for defining content of the container, including exactly one primary layer and any additional layers in a specified order.</param>\n        public static void Layers(this IContainer element, Action<LayersDescriptor> handler)\n        {\n            var descriptor = new LayersDescriptor();\n\n            handler(descriptor);\n            descriptor.Validate();","sourceCodeStart":40,"sourceCodeEnd":76,"githubUrl":"https://github.com/QuestPDF/QuestPDF/blob/43ab12559671556e10a6a0a5afe542c919f48a21/src/dotnet/library/QuestPDF/Fluent/LayerExtensions.cs#L40-L76","documentation":"The Layers component's Validate() also throws when more than one primary layer exists, because multiple primary layers would conflict over which content drives paging and target length. The message interpolates the actual count. Exactly one PrimaryLayer() call is permitted per Layers handler.","triggerScenarios":"Calling desc.PrimaryLayer() two or more times within a single .Layers(handler) block.","commonSituations":"Copy-paste that duplicated PrimaryLayer(); merging two layout fragments that each declared their own primary; misunderstanding that Layer(true)/PrimaryLayer must be unique.","solutions":["Keep exactly one desc.PrimaryLayer() in the handler; convert extras to desc.Layer() (secondary/background/watermark).","Audit the handler for all PrimaryLayer() calls and retain a single one.","Decide which content is the main flow and nest the rest as secondary layers."],"exampleFix":"// before\ncontainer.Layers(desc => {\n    desc.PrimaryLayer().Text(\"a\");\n    desc.PrimaryLayer().Text(\"b\"); // count=2 -> throws\n});\n\n// after\ncontainer.Layers(desc => {\n    desc.PrimaryLayer().Text(\"a\");\n    desc.Layer().Text(\"b\"); // secondary layer\n});","handlingStrategy":"validation","validationCode":"container.Layers(desc => {\n    desc.PrimaryLayer().Element(mainBody); // single primary\n    foreach (var extra in extras)\n        desc.Layer().Element(extra);        // secondary layers, not primary\n});","typeGuard":"// Guard at authoring time: search the Layers handler for 'PrimaryLayer' and ensure count == 1.\n// Combine all main content into the single primary layer; use desc.Layer() for the rest.","tryCatchPattern":"try { /* generate document */ }\ncatch (DocumentComposeException ex) when (ex.Message.Contains(\"exactly one primary layer\")) {\n    // Remove duplicate PrimaryLayer() calls; convert extras to desc.Layer().\n    throw;\n}","preventionTips":["Keep exactly one desc.PrimaryLayer() per Layers handler.","Convert duplicate primaries into secondary layers.","Review copy-pasted Layers blocks for duplicated primary calls."],"tags":["questpdf","fluent-api","layers","compose","invalid-state"],"backgroundTag":null,"analyzedSha":"43ab12559671556e10a6a0a5afe542c919f48a21","analyzedAt":"2026-08-13T17:02:41.303Z","schemaVersion":2},"datasetVersion":"2026-08-13T19:17:28.613Z"}