apache/druid · error · SegmentLoadingException

%s

Error message

%s

What it means

BroadcastJoinableMMappedQueryableSegmentizerFactory.factorize wraps any IOException encountered while mmapping/loading the segment files into a SegmentLoadingException whose message is the underlying IOException's message. It signals that the segment data on disk could not be read or mapped for broadcast join use.

Source

Thrown at processing/src/main/java/org/apache/druid/segment/loading/BroadcastJoinableMMappedQueryableSegmentizerFactory.java:77

  @Override
  public Segment factorize(DataSegment dataSegment, File parentDir, boolean lazy, SegmentLazyLoadFailCallback loadFailed) throws SegmentLoadingException
  {
    try {
      return new QueryableIndexSegment(indexIO.loadIndex(parentDir, lazy, loadFailed), dataSegment.getId()) {
        @Nullable
        @Override
        public <T> T as(Class<T> clazz)
        {
          if (clazz.equals(IndexedTable.class)) {
            return (T) new BroadcastSegmentIndexedTable(this, keyColumns, dataSegment.getVersion());
          }
          return super.as(clazz);
        }
      };
    }
    catch (IOException e) {
      throw new SegmentLoadingException(e, "%s", e.getMessage());
    }
  }

  @Override
  public boolean equals(Object o)
  {
    if (this == o) {
      return true;
    }
    if (o == null || getClass() != o.getClass()) {
      return false;
    }
    BroadcastJoinableMMappedQueryableSegmentizerFactory that = (BroadcastJoinableMMappedQueryableSegmentizerFactory) o;
    return Objects.equals(keyColumns, that.keyColumns);
  }

  @Override
  public int hashCode()

View on GitHub (pinned to 9b90983fd2)

Solutions

  1. Check the segment directory exists and contains all segment files (meta.json, index.drd, etc.)
  2. Fix filesystem permissions on the segment cache directory
  3. Reload/re-download the segment by clearing the local segment cache for that segment
  4. Inspect the cause chain of the SegmentLoadingException for the root IOException

Example fix

// before
// silently retrying with corrupted cache dir
// after
if (!new File(parentDir, "meta.json").exists()) { segmentCacheManager.delete(segId); /* re-fetch */ }
Segment seg = factory.factorize(dataSegment, parentDir, lazy, loadFailed);
Defensive patterns

Strategy: try-catch

Validate before calling

File segDir = new File(parentDir, dataSegment.getId().toString()); if (!segDir.isDirectory() || !new File(segDir, "meta.json").exists()) { refetchSegment(dataSegment); }

Type guard

boolean segmentFilesPresent(File dir) { return dir != null && dir.isDirectory() && dir.listFiles() != null && dir.listFiles().length > 0; }

Try / catch

try { seg = factory.factorize(segment, dir, lazy, cb); } catch (SegmentLoadingException e) { log.error(e, "Failed to load broadcast segment %s", segment.getId()); cacheCleaner.cleanup(dir); throw e; }

Prevention

When it happens

Trigger: factorize(dataSegment, parentDir, ...) is called but the segment's index.zix/meta files are missing, unreadable, or fail during mmapping, causing an IOException from mapFile/SegmentFileSelector operations.

Common situations: Deep storage pull succeeded but local cache directory is corrupted or truncated; permissions changed on the segment directory; disk full during segment materialization; partially written segment after a crash.

Understand the failure class

Background: "failed to read file", EACCES, ENOENT and "could not read <path>" errors: when a program can't read a file from disk — this error's family across 49 libraries.

Related errors


AI-assisted analysis of apache/druid@9b90983fd2 (2026-09-07). Data as JSON: /api/errors/592de4d59e305e46. Report an issue: GitHub.