{"record":{"id":"7d2c530fd03588cc","repo":"vercel/next.js","slug":"block-of-08-sst-is-the-last-block-but-not-an-index-block","errorCode":null,"errorMessage":"block {} of {:08}.sst is the last block but not an index block (type {})","messagePattern":"block (.+?) of (.+?)\\.sst is the last block but not an index block \\(type (.+?)\\)","errorType":"validation","errorClass":null,"httpStatus":null,"severity":"error","filePath":"turbopack/crates/turbo-persistence/src/static_sorted_file.rs","lineNumber":418,"sourceCode":"        verify_checksum(meta, data, checksum, block_index)?;\n\n        ensure!(\n            data.len() >= INDEX_BLOCK_HEADER_SIZE,\n            \"index block {} of {:08}.sst is too short ({} bytes)\",\n            block_index,\n            meta.sequence_number,\n            data.len()\n        );\n        ensure!(\n            be::read_u8(data) == BLOCK_TYPE_INDEX,\n            \"block {} of {:08}.sst is the last block but not an index block (type {})\",\n            block_index,\n            meta.sequence_number,\n            be::read_u8(data)\n        );\n        let first_block = be::read_u16(&data[1..]);\n        let entry_bytes = &data[INDEX_BLOCK_HEADER_SIZE..];\n        ensure!(\n            entry_bytes.len().is_multiple_of(INDEX_BLOCK_ENTRY_SIZE),\n            \"index block {} of {:08}.sst has {} trailing bytes past its last entry\",\n            block_index,\n            meta.sequence_number,\n            entry_bytes.len() % INDEX_BLOCK_ENTRY_SIZE\n        );\n\n        let entries = match backing {\n            // Store a range, not the slice: `StaticSortedFile` owns the mmap these bytes live in.\n            #[cfg(feature = \"mmap\")]\n            StaticSortedFileBacking::Mmap(mmap) => {\n                let start = entry_bytes.as_ptr() as usize - mmap.as_ptr() as usize;\n                IndexEntries::Mmap(start..start + entry_bytes.len())\n            }\n            StaticSortedFileBacking::File { .. } => IndexEntries::Owned(entry_bytes.into()),\n        };\n        Ok(Self {\n            entries,","sourceCodeStart":400,"sourceCodeEnd":436,"githubUrl":"https://github.com/vercel/next.js/blob/34433fd12ee8074ea3f47af9f36255c7390d0301/turbopack/crates/turbo-persistence/src/static_sorted_file.rs#L400-L436","documentation":"When parsing the final block of an SST file, turbo-persistence requires that the last block be the index block (type BLOCK_TYPE_INDEX). This error means the last block's type byte is something else, so the file's footer/index layout is corrupt or was written by an incompatible writer.","triggerScenarios":"Reading a {:08}.sst file whose last block type byte does not equal BLOCK_TYPE_INDEX — truncated file tail, partially flushed write, or a file written by a different turbo-persistence version with a changed block format.","commonSituations":"Cache written by a newer/older Next.js or Turbopack version being read after an upgrade or downgrade; interrupted write leaving a partial block as the file tail.","solutions":["Delete the SST file or the whole persistent cache directory and rebuild the cache.","Ensure the cache directory is not shared between different Turbopack/Next.js versions; clear it when switching versions.","Check that writes to the cache volume complete cleanly (no abrupt shutdown, sufficient space).","If it reproduces after a version change, report it with the file version metadata."],"exampleFix":null,"handlingStrategy":"fallback","validationCode":"if (isSstFileTruncated(path)) { fs.rmSync(path, { force: true }); }","typeGuard":null,"tryCatchPattern":"try {\n  openCache(cacheDir);\n} catch (e) {\n  if (/not an index block/.test(String(e))) {\n    fs.rmSync(cacheDir, { recursive: true, force: true });\n    openCache(cacheDir);\n  } else throw e;\n}","preventionTips":["Clear the cache directory when upgrading or downgrading Next.js/Turbopack.","Ensure clean shutdowns; interrupted writes corrupt the SST tail.","Do not share one cache directory across versions or concurrent builds."],"tags":["storage","corruption","cache","rust"],"backgroundTag":"internal-invariant-violation","analyzedSha":"34433fd12ee8074ea3f47af9f36255c7390d0301","analyzedAt":"2026-09-20T18:20:20.576Z","contentChangedAt":"2026-09-20T18:20:20.576Z","schemaVersion":2},"datasetVersion":"2026-09-23T08:17:48.524Z"}