{"record":{"id":"3c1dbc6159afbe21","repo":"gohugoio/hugo","slug":"webpanimencoderadd-failed-n","errorCode":null,"errorMessage":"WebPAnimEncoderAdd failed\\n","messagePattern":"WebPAnimEncoderAdd failed\\\\n","errorType":"console","errorClass":null,"httpStatus":null,"severity":"error","filePath":"internal/warpc/genwebp/webp.c","lineNumber":243,"sourceCode":"            return NULL;\n        }\n        pic.use_argb = 1;\n        pic.width = params.width;\n        pic.height = params.height;\n\n        const uint8_t *frame_rgba = all_frames_data + i * frame_rgba_size;\n\n        if (!WebPPictureImportRGBA(&pic, frame_rgba, params.stride))\n        {\n            fprintf(stderr, \"WebPPictureImportRGBA failed\\n\");\n            WebPPictureFree(&pic);\n            WebPAnimEncoderDelete(enc);\n            return NULL;\n        }\n\n        if (!WebPAnimEncoderAdd(enc, &pic, timestamp, config))\n        {\n            fprintf(stderr, \"WebPAnimEncoderAdd failed\\n\");\n            WebPPictureFree(&pic);\n            WebPAnimEncoderDelete(enc);\n            return NULL;\n        }\n        timestamp += params.frameDurations[i];\n        WebPPictureFree(&pic);\n    }\n\n    if (!WebPAnimEncoderAdd(enc, NULL, timestamp, config))\n    {\n        fprintf(stderr, \"WebPAnimEncoderAdd failed for final frame\\n\");\n        WebPAnimEncoderDelete(enc);\n        return NULL;\n    }\n\n    WebPData webp_data_out;\n    WebPDataInit(&webp_data_out);\n    if (!WebPAnimEncoderAssemble(enc, &webp_data_out))","sourceCodeStart":225,"sourceCodeEnd":261,"githubUrl":"https://github.com/gohugoio/hugo/blob/52c9bd7908b4d02d4d0ff8f82a888834d6ee10d2/internal/warpc/genwebp/webp.c#L225-L261","documentation":"Printed inside genwebp's encodeNRGBAAnimated loop (webp.c:243) when WebPAnimEncoderAdd returns false for a regular frame. This means libwebp rejected the frame after the picture was already imported — typically because the WebPConfig is invalid (quality/method out of range, lossless/lossy conflict), the timestamp sequence is non-monotonic, or memory allocation inside the encoder failed. The worker tears down the encoder and returns NULL.","triggerScenarios":"A frame's timestamp (accumulated from params.frameDurations) is not greater than the previous frame's (a zero or negative duration in the array), the WebPConfig combination is rejected by libwebp internally, or the encoder runs out of memory while compressing a frame.","commonSituations":"Animated GIF source with a frame that has duration 0 or that was decoded with duration in the wrong unit (centiseconds vs milliseconds producing non-monotonic or huge jumps), a custom WebPConfig the user supplied via Hugo options that libwebp rejects, or a large-frame OOM.","solutions":["Sanitize params.frameDurations on the Go side: ensure every value is > 0 and that the cumulative timestamp is strictly increasing.","If durations came from a GIF decoder, convert centiseconds to milliseconds consistently and clamp zeros to a small positive default.","Validate WebPConfig fields (quality 1-100, method 0-6, preset resolved from a known hint) before encoding.","For OOM cases, lower resolution or quality, or raise the worker memory limit.","Log the failing frame index and its duration on the Go side to correlate."],"exampleFix":"// before: GIF durations in centiseconds sent raw, some are 0\nparams.FrameDurations = gifDurations\n\n// after: convert to ms, force strictly positive\nfor i, d := range gifDurations {\n    ms := d * 10\n    if ms <= 0 { ms = 100 }\n    params.FrameDurations[i] = ms\n}","handlingStrategy":"validation","validationCode":"// Ensure strictly positive, monotonically increasing cumulative timestamps.\nfunc sanitizeDurations(ms []int) []int {\n    out := make([]int, len(ms))\n    for i, d := range ms {\n        if d <= 0 { d = 100 } // default 100ms\n        out[i] = d\n    }\n    return out\n}","typeGuard":null,"tryCatchPattern":null,"preventionTips":["Coerce any zero/negative frame duration to a small positive default.","Convert GIF centiseconds to milliseconds consistently.","Validate WebPConfig (quality 1-100, method 0-6, preset) before encoding.","Log the failing frame index and duration to correlate with this stderr line."],"tags":["webp","animation","encoding","timestamps","config"],"backgroundTag":null,"analyzedSha":"52c9bd7908b4d02d4d0ff8f82a888834d6ee10d2","analyzedAt":"2026-08-09T21:49:36.660Z","contentChangedAt":null,"schemaVersion":2},"datasetVersion":"2026-09-14T00:17:10.932Z"}