{"record":{"id":"425653f2bc11e908","repo":"PHPOffice/PhpSpreadsheet","slug":"worksheet-no-longer-exists","errorCode":null,"errorMessage":"Worksheet no longer exists","messagePattern":"Worksheet no longer exists","errorType":"exception","errorClass":"SpreadsheetException","httpStatus":null,"severity":"error","filePath":"src/PhpSpreadsheet/Cell/Cell.php","lineNumber":838,"sourceCode":"        return $this->parent;\n    }\n\n    /**\n     * Get parent worksheet.\n     *\n     * @throws SpreadsheetException\n     */\n    public function getWorksheet(): Worksheet\n    {\n        $parent = $this->parent;\n        if ($parent !== null) {\n            $worksheet = $parent->getParent();\n        } else {\n            $worksheet = null;\n        }\n\n        if ($worksheet === null) {\n            throw new SpreadsheetException('Worksheet no longer exists');\n        }\n\n        return $worksheet;\n    }\n\n    public function getWorksheetOrNull(): ?Worksheet\n    {\n        $parent = $this->parent;\n        if ($parent !== null) {\n            $worksheet = $parent->getParent();\n        } else {\n            $worksheet = null;\n        }\n\n        return $worksheet;\n    }\n\n    /**","sourceCodeStart":820,"sourceCodeEnd":856,"githubUrl":"https://github.com/PHPOffice/PhpSpreadsheet/blob/65b080eef4d9fd11a5796135ab145883e5c3d6a6/src/PhpSpreadsheet/Cell/Cell.php#L820-L856","documentation":"getWorksheet() resolves the two-hop chain Cell -> Cells (parent) -> Worksheet; if either hop is null (cell detached from its collection, or collection detached from its worksheet, e.g. after removal/destruction), it throws. Use the sibling getWorksheetOrNull() when you want a null instead of an exception during teardown-sensitive code.","triggerScenarios":"Calling getWorksheet() on a Cell retained after unset($spreadsheet) or removeSheetByIndex(); accessing cells during worksheet destruction; debugging variables after the workbook went out of scope.","commonSituations":"Long pipelines and queue workers holding Cell references; code cloning sheets/cells and reusing originals; exception reporters inspecting cells captured in earlier frames.","solutions":["Use $cell->getWorksheetOrNull() and handle the null case explicitly","Guard the chain yourself: $cell->getParent()?->getParent() before calling getWorksheet()","Refetch cells from a live spreadsheet via coordinates instead of keeping references","Restructure so worksheet-dependent work finishes before teardown"],"exampleFix":"// before\n$ws = $cell->getWorksheet(); // throws when worksheet is gone\n\n// after\n$ws = $cell->getWorksheetOrNull();\nif ($ws === null) {\n    $ws = $spreadsheet->getSheetByName($sheetName); // recover via live spreadsheet\n}","handlingStrategy":"validation","validationCode":"$ws = $cell->getWorksheetOrNull();\nif ($ws === null) {\n    $ws = $spreadsheet->getSheetByName($sheetName); // recover or fail explicitly\n    if ($ws === null) {\n        throw new RuntimeException(\"Worksheet '$sheetName' is gone; cannot process cell $coord\");\n    }\n}","typeGuard":"function cellIsBoundToWorksheet(Cell $cell): bool\n{\n    return $cell->getParent() !== null && $cell->getParent()->getParent() !== null;\n}","tryCatchPattern":"null","preventionTips":["Prefer getWorksheetOrNull() plus an explicit null branch in teardown-sensitive code","Finish worksheet-dependent work before removing sheets or discarding the spreadsheet","Keep (sheetName, coordinate) as the canonical cell identity in long pipelines"],"tags":["phpspreadsheet","cell","worksheet","detached-object","lifecycle"],"backgroundTag":"detached-object-access","analyzedSha":"65b080eef4d9fd11a5796135ab145883e5c3d6a6","analyzedAt":"2026-08-17T05:40:41.646Z","schemaVersion":2},"datasetVersion":"2026-08-17T09:17:11.063Z"}