PMTiles Documentation

repository·main·Indexed 23 days ago

https://github.com/protomaps/pmtiles

PMTiles is a single-file archive format for tiled geospatial data optimized for serverless, low-cost hosting on commodity cloud storage like Amazon S3. It provides libraries for JavaScript (including MapLibre GL JS, Leaflet, and OpenLayers via ol-pmtiles), Python, and Go. The ecosystem includes a CLI for converting MBTiles or Shapefiles to PMTiles, tools for S3 uploads, and serverless deployment options for AWS Lambda and Cloudflare Workers.

Tokens
9.4K
Snippets
24
Records
76
Agent score
84%

What's inside PMTiles

  1. Overview of PMTiles

    main

    PMTiles is a single-file archive format for tiled data designed for low-cost, zero-maintenance, and 'serverless' map applications. It allows you to host tiled data on commodity storage platforms like Amazon S3, eliminating the need for a custom tile backend or third-party provider.

    Key resources:

    • PMTiles Viewer: https://pmtiles.io/ (use this to inspect and preview local or remote archives).
    • Note on CORS: Archives hosted on cloud storage may require CORS configuration to allow requests from the origin https://protomaps.github.io.
    • Map Compatibility: Demos typically require MapLibre GL JS v1.15 or later.
  2. PMTiles Version 3 Archive Structure

    main

    A PMTiles archive is a single-file format for tiled data with the recommended MIME type application/vnd.pmtiles. The archive consists of five main sections:

    1. Header: A fixed-size 127-byte header at the start of the file.
    2. Root Directory: Contains the directory structure. Requirement: The root directory MUST be contained within the first 16,384 bytes (16 KiB) to allow latency-optimized clients to retrieve it in advance.
    3. JSON Metadata: Contains metadata for the archive.
    4. Leaf Directories (Optional): Additional directory layers.
    5. Tile Data: The actual tile blobs.

    While these sections are typically ordered sequentially, all sections except the header can be relocated arbitrarily within the archive.

  3. Develop Protomaps on Cloudflare using Wrangler

    main

    For advanced development using Wrangler, ensure you configure your development bucket in wrangler.toml by updating the preview_bucket_name key.

    To run the Worker locally, use npm run start. The Worker will be available at http://localhost:8787. Note that the cache is not active during local development.

    npm run start
  4. Decode a PMTiles Directory

    main

    To decode a directory, perform the following steps in order:

    1. Decompress the input buffer using the compression method specified in the header.
    2. Read the number of entries n as a variable-width integer.
    3. Read n delta-encoded TileIDs and reconstruct the absolute IDs.
    4. Read n RunLengths as variable-width integers.
    5. Read n Lengths as variable-width integers.
    6. Read n Offsets as variable-width integers. If an offset is 0 and it is not the first entry, it indicates the entry is contiguous with the previous one (offset = prev_offset + prev_length). Otherwise, the absolute offset is value - 1.
    input_buffer = the input byte-buffer
    
    buffer = decompress(input_buffer)
    
    num_entries = read_varint(buffer)
    
    entries = empty list of entries
    
    last_id = 0
    for i in num_entries {
        value = read_varint(buffer)
        last_id = last_id + value
    
        entries[i] = Entry { tile_id: last_id }
    }
    
    for i in num_entries {
        entries[i].run_length = read_varint(buffer)
    }
    
    for i in num_entries {
        entries[i].length = read_varint(buffer)
    }
    
    for i in num_entries {
        value = read_varint(buffer)
    
        if value == 0 && i > 0 {
            // offset = 0 -> entry is directly after previous entry
            prev_entry = entries[i - 1];
    
            entries[i].offset = prev_entry.offset + prev_entry.length;
        } else {
            entries[i].offset = value - 1;
        }
    }
  5. Upload PMTiles to S3

    main

    You can upload a PMTiles archive directly to an S3 bucket using the pmtiles CLI tool. This requires the AWS_ACCESS_KEY_ID and AWS_SECRET_ACCESS_KEY environment variables to be set in your environment.

    pmtiles upload OUTPUT.pmtiles s3://my-bucket?region=us-west-2
  6. Upload PMTiles using PMTiles CLI or RClone

    main

    There are two primary ways to upload PMTiles to cloud storage:

    1. Using the PMTiles CLI tool: Provide the S3 URI including the endpoint and region as query parameters.

    2. Using RClone: Ensure you have configured RClone first (rclone config). Use copyto with flags for chunk size and concurrency to optimize the upload.

  7. Configure CORS for Cloud Storage

    main
    When hosting PMTiles on cloud storage (such as Cloudflare R2, Amazon S3, or Google Cloud Storage), you must configure CORS (Cross-Origin Resource Sharing) to allow your web application to fetch the tiles. Refer to the Protomaps documentation for specific configuration steps for your provider.
  8. Build the Protomaps AWS Lambda ZIP

    main

    To build the Lambda deployment package, you must first prepare the shared JavaScript dependencies.

    1. Navigate to the top-level js/ directory, run npm install, and then npm run build.
    2. Navigate to the serverless/aws directory and run npm install.
    3. Run the build command to generate the ZIP file.

    The resulting deployment artifact is located at dist/lambda_function.zip. Alternatively, you can manually copy the contents of dist/index.mjs into the Lambda console.

    npm run build-zip