{"record":{"id":"f0f8c614bf0dc937","repo":"PHPOffice/PhpSpreadsheet","slug":"problem-reading-filename-f0f8c6","errorCode":null,"errorMessage":"Problem reading {$filename}","messagePattern":"Problem reading (.+?)","errorType":"exception","errorClass":"PhpOffice\\PhpSpreadsheet\\Reader\\Exception","httpStatus":null,"severity":"error","filePath":"src/PhpSpreadsheet/Reader/Xml.php","lineNumber":196,"sourceCode":"    }\n\n    /**\n     * Return worksheet info (Name, Last Column Letter, Last Column Index, Total Rows, Total Columns).\n     *\n     * @return array<int, array{worksheetName: string, lastColumnLetter: string, lastColumnIndex: int, totalRows: int, totalColumns: int, sheetState: string}>\n     */\n    public function listWorksheetInfo(string $filename): array\n    {\n        File::assertFile($filename);\n        if (!$this->canRead($filename)) {\n            throw new Exception($filename . ' is an Invalid Spreadsheet file.');\n        }\n\n        $worksheetInfo = [];\n\n        $xml = $this->trySimpleXMLLoadStringPrivate($filename);\n        if ($xml === false) {\n            throw new Exception(\"Problem reading {$filename}\");\n        }\n\n        $worksheetID = 1;\n        $xml_ss = $xml->children(self::NAMESPACES_SS);\n        foreach ($xml_ss->Worksheet as $worksheet) {\n            $worksheet_ss = self::getAttributes($worksheet, self::NAMESPACES_SS);\n\n            $tmpInfo = [];\n            $tmpInfo['worksheetName'] = '';\n            $tmpInfo['lastColumnLetter'] = 'A';\n            $tmpInfo['lastColumnIndex'] = 0;\n            $tmpInfo['totalRows'] = 0;\n            $tmpInfo['totalColumns'] = 0;\n\n            $tmpInfo['worksheetName'] = \"Worksheet_{$worksheetID}\";\n            if (isset($worksheet_ss['Name'])) {\n                $tmpInfo['worksheetName'] = (string) $worksheet_ss['Name'];\n            }","sourceCodeStart":178,"sourceCodeEnd":214,"githubUrl":"https://github.com/PHPOffice/PhpSpreadsheet/blob/65b080eef4d9fd11a5796135ab145883e5c3d6a6/src/PhpSpreadsheet/Reader/Xml.php#L178-L214","documentation":"In listWorksheetInfo(), canRead() succeeded but trySimpleXMLLoadStringPrivate() returned false: the bytes contain both signature substrings yet are not well-formed XML, so simplexml refuses the document.","triggerScenarios":"Malformed SpreadsheetML: unescaped special characters, mismatched tags, truncation after the header, or scanner-modified content that no longer parses.","commonSituations":"Hand-built XML exports with escaping bugs; files cut off mid-transfer; XML containing raw ampersands in URLs or unescaped < in text nodes.","solutions":["Validate with xmllint or a simplexml pre-pass to surface the exact error position","Fix entity escaping (&amp;, &lt;, &gt;) in the generating process","Re-upload or re-export a complete file"],"exampleFix":null,"handlingStrategy":"try-catch","validationCode":"libxml_use_internal_errors(true);\nif (simplexml_load_file($path) === false) {\n    $err = libxml_get_errors()[0] ?? null;\n    throw new InvalidArgumentException('Bad XML: ' . ($err ? $err->message . ' line ' . $err->line : 'unknown'));\n}","typeGuard":null,"tryCatchPattern":"try {\n    $info = $reader->listWorksheetInfo($path);\n} catch (\\PhpOffice\\PhpSpreadsheet\\Reader\\Exception $e) {\n    if (str_contains($e->getMessage(), 'Problem reading')) {\n        // malformed despite passing signature: request corrected export\n    }\n}","preventionTips":["Escape &, <, > in the generating process","Validate documents with xmllint in your export test suite","Re-transfer files that were cut off mid-stream"],"tags":["xml","malformed-xml","simplexml","phpspreadsheet"],"backgroundTag":"invalid-xml","analyzedSha":"65b080eef4d9fd11a5796135ab145883e5c3d6a6","analyzedAt":"2026-08-17T05:40:41.646Z","schemaVersion":2},"datasetVersion":"2026-08-17T09:17:11.063Z"}