{"record":{"id":"df98a5bec1c850de","repo":"PHPOffice/PhpSpreadsheet","slug":"couldn-t-import-bitmap","errorCode":null,"errorMessage":"Couldn't import $bitmap","messagePattern":"Couldn't import \\$bitmap","errorType":"exception","errorClass":"PhpOffice\\PhpSpreadsheet\\Writer\\Exception","httpStatus":null,"severity":"error","filePath":"src/PhpSpreadsheet/Writer/Xls/Worksheet.php","lineNumber":2465,"sourceCode":"    /**\n     * Convert a 24 bit bitmap into the modified internal format used by Windows.\n     * This is described in BITMAPCOREHEADER and BITMAPCOREINFO structures in the\n     * MSDN library.\n     *\n     * @deprecated 5.5.0 No replacement.\n     *\n     * @param string $bitmap The bitmap to process\n     *\n     * @return array{0: int, 1: int, 2: int, 3: string} Data and properties of the bitmap\n     *\n     * @codeCoverageIgnore\n     */\n    public function processBitmap(string $bitmap): array\n    {\n        // Open file.\n        $bmp_fd = @fopen($bitmap, 'rb');\n        if ($bmp_fd === false || 0 === (int) filesize($bitmap)) {\n            throw new WriterException(\"Couldn't import $bitmap\");\n        }\n\n        // Slurp the file into a string.\n        $data = (string) fread($bmp_fd, (int) filesize($bitmap));\n\n        // Check that the file is big enough to be a bitmap.\n        if (strlen($data) <= 0x36) {\n            throw new WriterException(\"$bitmap doesn't contain enough data.\\n\");\n        }\n\n        // The first 2 bytes are used to identify the bitmap.\n\n        $identity = unpack('A2ident', $data);\n        if ($identity === false || $identity['ident'] != 'BM') {\n            throw new WriterException(\"$bitmap doesn't appear to be a valid bitmap image.\\n\");\n        }\n\n        // Remove bitmap data: ID.","sourceCodeStart":2447,"sourceCodeEnd":2483,"githubUrl":"https://github.com/PHPOffice/PhpSpreadsheet/blob/65b080eef4d9fd11a5796135ab145883e5c3d6a6/src/PhpSpreadsheet/Writer/Xls/Worksheet.php#L2447-L2483","documentation":"Writer\\Xls\\Worksheet::processBitmap() - reached via the deprecated insertBitmap() - opens the given path with fopen('rb'). If the open fails (file missing, unreadable, or path invalid) or the file is exactly 0 bytes, this exception aborts the operation. It is the pre-check before any BMP header parsing happens.","triggerScenarios":"Calling insertBitmap($row, $col, '/path/img.bmp') where the path does not exist, lacks read permission, or points to an empty (0-byte) file; relative paths resolved against an unexpected current working directory.","commonSituations":"User-uploaded image deleted or moved before the write; CLI vs web cwd differences producing broken relative paths; permission changes on storage mounts.","solutions":["Pass an absolute path (e.g. via realpath()) to an existing file","Check is_file(), is_readable() and filesize() > 0 before inserting","Prefer the Drawing/MemoryDrawing API (PNG/JPEG) instead of the deprecated insertBitmap()","Restore the missing file or fix filesystem permissions"],"exampleFix":"// before\n$worksheetWriter->insertBitmap(1, 1, $relativePath);\n\n// after\n$path = realpath($relativePath);\nif ($path === false || !is_readable($path) || filesize($path) === 0) {\n    throw new InvalidArgumentException(\"Image not readable: $relativePath\");\n}\n$worksheetWriter->insertBitmap(1, 1, $path);","handlingStrategy":"validation","validationCode":"function assertBitmapReadable(string $path): void\n{\n    if (!is_file($path) || !is_readable($path)) {\n        throw new InvalidArgumentException(\"Image missing or unreadable: $path\");\n    }\n    if (filesize($path) === 0) {\n        throw new InvalidArgumentException(\"Image file is empty: $path\");\n    }\n}\n\nassertBitmapReadable($bitmapPath);\n$worksheetWriter->insertBitmap($row, $col, realpath($bitmapPath));","typeGuard":null,"tryCatchPattern":"try {\n    $worksheetWriter->insertBitmap($row, $col, $path);\n} catch (\\PhpOffice\\PhpSpreadsheet\\Writer\\Exception $e) {\n    if (str_contains($e->getMessage(), \"Couldn't import\")) {\n        // log and continue without the image rather than losing the whole export\n        error_log(\"Skipping missing image: $path\");\n    } else {\n        throw $e;\n    }\n}","preventionTips":["Always resolve image paths with realpath() before use","Copy user-supplied images to your own storage before referencing them in exports","Prefer the Drawing API (PNG/JPEG) over the deprecated insertBitmap()"],"tags":["phpspreadsheet","xls","bitmap","image","file-not-found"],"backgroundTag":"image-file-unreadable","analyzedSha":"65b080eef4d9fd11a5796135ab145883e5c3d6a6","analyzedAt":"2026-08-17T05:40:41.646Z","schemaVersion":2},"datasetVersion":"2026-08-17T09:17:11.063Z"}