Crosstalk-Solutions/project-nomad · error · Error

pmtiles extract for world basemap failed: ${err.message}. st

Error message

pmtiles extract for world basemap failed: ${err.message}. stderr: ${err.stderr ?? ''}

What it means

Setting up the world basemap runs a 'pmtiles extract' subprocess (with a timeout and buffer cap) to carve a smaller world basemap out of a downloaded source. If the child process errors, times out, or exceeds maxBuffer, the partial output file is deleted and this error wraps the subprocess message and stderr.

Source

Thrown at admin/app/services/map_service.ts:487

    const args = buildPmtilesExtractArgs({
      sourceUrl: info.url,
      outputFilepath: filepath,
      maxzoom: WORLD_BASEMAP_MAX_ZOOM,
      downloadThreads: 4,
    })

    logger.info(
      `[MapService] Extracting world basemap (z0-${WORLD_BASEMAP_MAX_ZOOM}) from ${info.url}`
    )
    try {
      await execFileAsync(PMTILES_BINARY_PATH, args, {
        timeout: WORLD_BASEMAP_EXTRACT_TIMEOUT_MS,
        maxBuffer: DRY_RUN_MAX_BUFFER,
      })
      this.worldBasemapReady = true
    } catch (err: any) {
      await deleteFileIfExists(filepath)
      throw new Error(
        `pmtiles extract for world basemap failed: ${err.message}. stderr: ${err.stderr ?? ''}`
      )
    }
  }

  private async checkBaseAssetsExist(useCache: boolean = true): Promise<boolean> {
    // Return cached result if available and caching is enabled
    if (useCache && this.baseAssetsExistCache !== null) {
      return this.baseAssetsExistCache
    }

    await ensureDirectoryExists(this.baseDirPath)

    const baseStylePath = join(this.baseDirPath, this.baseStylesFile)
    const basemapsAssetsPath = join(this.baseDirPath, this.basemapsAssetsDir)

    const [baseStyleExists, basemapsAssetsExists] = await Promise.all([
      getFileStatsIfExists(baseStylePath),

View on GitHub (pinned to 0bd1c6f4f9)

Solutions

  1. Read the embedded stderr in the message — it usually names the exact cause (ENOENT for missing binary, memory/disk messages, etc.)
  2. Verify the pmtiles CLI is installed and on PATH: pmtiles --version
  3. Increase WORLD_BASEMAP_EXTRACT_TIMEOUT_MS / DRY_RUN_MAX_BUFFER on slow or memory-constrained hosts
  4. Delete the source .pmtiles so it re-downloads, in case the input is corrupted
Defensive patterns

Strategy: retry

Validate before calling

import { execFile } from 'child_process'
const ok = await new Promise<boolean>(res => execFile('pmtiles', ['--version'], t => res(!t)))
if (!ok) throw new Error('pmtiles CLI not available')

Try / catch

try { await mapService.ensureWorldBasemap() } catch (e) { if (e instanceof Error && e.message.includes('pmtiles extract')) { logger.error(e.message) /* parse stderr, fix env, retry once */ } throw e }

Prevention

When it happens

Trigger: The pmtiles CLI not installed or not on PATH; the extract exceeding WORLD_BASEMAP_EXTRACT_TIMEOUT_MS; output exceeding DRY_RUN_MAX_BUFFER; corrupted source .pmtiles; disk full during extract.

Common situations: Docker images missing the pmtiles binary; low-memory containers hitting the buffer cap; slow disk/network making extraction exceed the timeout; truncated source download from a flaky CDN.

Related errors


AI-assisted analysis of Crosstalk-Solutions/project-nomad@0bd1c6f4f9 (2026-08-27). Data as JSON: /api/errors/6a59b7f2e330d35c. Report an issue: GitHub.