{"record":{"id":"e20657a9b03af793","repo":"gchq/CyberChef","slug":"error-changing-image-opacity-err","errorCode":null,"errorMessage":"Error changing image opacity. (${err})","messagePattern":"Error changing image opacity\\. \\((.+?)\\)","errorType":"exception","errorClass":"OperationError","httpStatus":null,"severity":"error","filePath":"src/core/operations/ImageOpacity.mjs","lineNumber":72,"sourceCode":"        try {\n            image = await Jimp.read(input);\n        } catch (err) {\n            throw new OperationError(`Error loading image. (${err})`);\n        }\n        try {\n            if (isWorkerEnvironment())\n                self.sendStatusMessage(\"Changing image opacity...\");\n            image.opacity(opacity / 100);\n\n            let imageBuffer;\n            if (image.mime === \"image/gif\") {\n                imageBuffer = await image.getBuffer(JimpMime.png);\n            } else {\n                imageBuffer = await image.getBuffer(image.mime);\n            }\n            return imageBuffer.buffer;\n        } catch (err) {\n            throw new OperationError(`Error changing image opacity. (${err})`);\n        }\n    }\n\n    /**\n     * Displays the image using HTML for web apps\n     * @param {ArrayBuffer} data\n     * @returns {html}\n     */\n    present(data) {\n        if (!data.byteLength) return \"\";\n        const dataArray = new Uint8Array(data);\n\n        const type = isImage(dataArray);\n        if (!type) {\n            throw new OperationError(\"Invalid file type.\");\n        }\n\n        return `<img src=\"data:${type};base64,${toBase64(dataArray)}\">`;","sourceCodeStart":54,"sourceCodeEnd":90,"githubUrl":"https://github.com/gchq/CyberChef/blob/4290ea753912378913b1f3f54e0fc5720afeda5d/src/core/operations/ImageOpacity.mjs#L54-L90","documentation":"Catches any exception during image.opacity(opacity/100) or getBuffer and re-wraps it. opacity is divided by 100, so a non-numeric or out-of-range opacity yields NaN or a value Jimp rejects. GIF outputs are re-encoded as PNG. The interpolated err gives the Jimp cause.","triggerScenarios":"opacity arg is NaN (e.g. from empty string), negative, or >100, producing an opacity fraction outside [0,1] that Jimp refuses; or getBuffer fails during PNG encode. Large-image memory pressure can also surface here.","commonSituations":"Opacity slider cleared or set to a non-number, a corrupted pixel buffer, or an oversized image during encode.","solutions":["Clamp opacity to [0,100] and coerce to a number before calling.","Downscale the image and retry to rule out memory issues.","Re-encode source to PNG so the GIF branch is clean.","If err names a Jimp method, adjust jimp version."],"exampleFix":"// before\nopacityOp.run(png, [NaN]); // -> Error changing image opacity.\n// after\nconst opacity = Math.max(0, Math.min(100, Number(args[0]) || 0));\nopacityOp.run(png, [opacity]);","handlingStrategy":"validation","validationCode":"const opacity = Math.max(0, Math.min(100, Number(args[0])));\nif (!Number.isFinite(opacity)) throw new Error('opacity must be a number in [0,100]');","typeGuard":"function isValidOpacity(v) {\n  const n = Number(v);\n  return Number.isFinite(n) && n >= 0 && n <= 100;\n}","tryCatchPattern":null,"preventionTips":["Coerce and clamp opacity to [0,100].","Reject empty/non-numeric slider values upstream.","Downscale large images before encode-heavy ops.","Isolate the processing try/catch so encode failures carry the Jimp cause."],"tags":["image","jimp","argument-validation","cyberchef","error-handling"],"backgroundTag":null,"analyzedSha":"4290ea753912378913b1f3f54e0fc5720afeda5d","analyzedAt":"2026-08-13T06:05:50.210Z","schemaVersion":2},"datasetVersion":"2026-08-13T09:17:06.757Z"}