{"record":{"id":"6251f3f72370f356","repo":"apache/druid","slug":"failed-to-mount-partial-metadata-for-segment-s","errorCode":null,"errorMessage":"Failed to mount partial metadata for segment[%s]","messagePattern":"Failed to mount partial metadata for segment\\[(.+?)\\]","errorType":"exception","errorClass":"SegmentLoadingException","httpStatus":null,"severity":"error","filePath":"server/src/main/java/org/apache/druid/segment/loading/SegmentLocalCacheManager.java","lineNumber":1099,"sourceCode":"          final PartialSegmentMetadataCacheEntry metadata = reserved.metadata();\n          // findOrReservePartial only invokes reservePartial (which writes the info file) on the fresh-reserve\n          // branch. On the find-existing branch the info file on disk still carries the PRIOR rule's wrapped\n          // load spec, so a rule swap here would apply in memory only. Rewrite unconditionally before mount.\n          try {\n            rewriteInfoFile(dataSegment);\n          }\n          catch (IOException e) {\n            throw new SegmentLoadingException(\n                e,\n                \"Failed to write partial info file for segment[%s]\",\n                dataSegment.getId()\n            );\n          }\n          try {\n            metadata.mount(reserved.location());\n          }\n          catch (IOException e) {\n            throw new SegmentLoadingException(\n                e,\n                \"Failed to mount partial metadata for segment[%s]\",\n                dataSegment.getId()\n            );\n          }\n          final PartialSegmentFileMapperV10 mapper = metadata.getFileMapper();\n          if (mapper == null) {\n            throw DruidException.defensive(\n                \"Partial metadata for segment[%s] mounted without a file mapper\",\n                dataSegment.getId()\n            );\n          }\n          // Register the info-file cleanup hook BEFORE anything that could throw. Any throw between mount and\n          // awaitEagerDownloadsOrClearRule leaves the metadata entry weak-reserved with the hook attached; when\n          // cache eventually reclaims, the info file gets deleted along with the entry.\n          metadata.setOnUnmount(() -> deleteSegmentInfoFile(dataSegment));\n          final Set<String> selected = Set.copyOf(\n              wrapper.getSelectedBundleNames(dataSegment, mapper.getSegmentFileMetadata())","sourceCodeStart":1081,"sourceCodeEnd":1117,"githubUrl":"https://github.com/apache/druid/blob/9b90983fd291f26935af934383ce360473179e4d/server/src/main/java/org/apache/druid/segment/loading/SegmentLocalCacheManager.java#L1081-L1117","documentation":"After reserving a location and writing the partial info file, SegmentLocalCacheManager mounts the PartialSegmentMetadataCacheEntry at the location. An IOException during mount (file materialization, mapping, or file-locking failure) is wrapped in this SegmentLoadingException.","triggerScenarios":"metadata.mount(reserved.location()) throws IOException during the partial-load load path — e.g. failure creating files/directories or acquiring the mount at the reserved cache location.","commonSituations":"Cache location disk full or failing; concurrent load/eviction race corrupting the mount state; permissions problems on the cache directory; underlying storage of the partial files unavailable.","solutions":["Check the wrapped IOException cause for the root disk/permission problem on the cache location.","Verify the cache location directories exist, are writable, and have free space.","Retry the load after resolving disk issues; the coordinator load queue will re-attempt.","Check logs for concurrent eviction/load races on the same segment id and location."],"exampleFix":null,"handlingStrategy":"retry","validationCode":"final File loc = reserved.location().getPath();\nif (!loc.exists() || !loc.canWrite() || loc.getUsableSpace() < MIN_FREE_BYTES) {\n  throw new IllegalStateException(\"Cache location unusable for mount: \" + loc);\n}","typeGuard":null,"tryCatchPattern":"try {\n  cacheManager.loadPartial(segment, rule);\n} catch (SegmentLoadingException e) {\n  if (e.getMessage() != null && e.getMessage().startsWith(\"Failed to mount partial metadata\")) {\n    retryWithBackoff(e); // transient disk/IO issues often resolve on retry\n  } else {\n    throw e;\n  }\n}","preventionTips":["Keep cache locations healthy: free space, writable, not failing hardware.","Avoid concurrent load/drop races by coordinating rule changes through the coordinator.","Watch logs for repeated mount failures indicating corrupt cache state; clear the location if needed.","Retry loads with exponential backoff rather than tight loops."],"tags":["segment-mount","io","disk","partial-load"],"backgroundTag":"file-write-failed","analyzedSha":"9b90983fd291f26935af934383ce360473179e4d","analyzedAt":"2026-09-07T13:32:30.957Z","contentChangedAt":"2026-09-07T13:32:30.957Z","schemaVersion":2},"datasetVersion":"2026-09-14T05:17:10.506Z"}