Getting Started

Quick Start

Serve your first map tiles in 5 minutes

Get tileserver-rs running with real map data in just a few minutes.

Prerequisites

Step 1: Download Sample Data

We'll use a sample PMTiles file containing OpenStreetMap data for Florence, Italy:

mkdir -p data/tiles
curl -L -o data/tiles/florence.pmtiles \
  https://github.com/vinayakkulkarni/tileserver-rs/raw/main/data/tiles/protomaps-sample.pmtiles

Step 2: Create Configuration

Create a config.toml file:

cat > config.toml << 'EOF'
[[sources]]
id = "florence"
type = "pmtiles"
path = "/data/tiles/florence.pmtiles"
name = "Florence"
attribution = "© OpenStreetMap contributors"
EOF

Step 3: Start the Server

docker run -p 8080:8080 \
  -v $(pwd)/data:/data:ro \
  -v $(pwd)/config.toml:/app/config.toml:ro \
  ghcr.io/vinayakkulkarni/tileserver-rs:latest

You should see:

INFO tileserver_rs: Loaded 1 tile source(s)
INFO tileserver_rs: Starting tileserver on http://0.0.0.0:8080

Step 4: Explore Your Tiles

Open your browser to http://localhost:8080 to see the built-in map viewer.

Available Endpoints

EndpointDescription
localhost:8080Web UI with map viewer
localhost:8080/data.jsonList all tile sources
localhost:8080/data/florence.jsonTileJSON metadata
localhost:8080/healthHealth check

Fetch a Tile

# Get a vector tile (zoom 14, Florence city center)
curl -I http://localhost:8080/data/florence/14/8704/5972.pbf

# Response:
# HTTP/1.1 200 OK
# content-type: application/x-protobuf
# content-encoding: gzip

Step 5: Display in MapLibre GL JS

Create an index.html file:

<!DOCTYPE html>
<html>
<head>
  <title>My First Tile Server</title>
  <meta charset="utf-8" />
  <meta name="viewport" content="width=device-width, initial-scale=1.0">
  <link href="https://unpkg.com/maplibre-gl@4/dist/maplibre-gl.css" rel="stylesheet" />
  <script src="https://unpkg.com/maplibre-gl@4/dist/maplibre-gl.js"></script>
  <style>
    body { margin: 0; padding: 0; }
    #map { position: absolute; top: 0; bottom: 0; width: 100%; }
  </style>
</head>
<body>
  <div id="map"></div>
  <script>
    const map = new maplibregl.Map({
      container: 'map',
      style: {
        version: 8,
        sources: {
          'florence': {
            type: 'vector',
            url: 'http://localhost:8080/data/florence.json'
          }
        },
        layers: [
          {
            id: 'water',
            type: 'fill',
            source: 'florence',
            'source-layer': 'water',
            paint: { 'fill-color': '#a0cfdf' }
          },
          {
            id: 'roads',
            type: 'line',
            source: 'florence',
            'source-layer': 'transportation',
            paint: { 'line-color': '#888', 'line-width': 1 }
          },
          {
            id: 'buildings',
            type: 'fill',
            source: 'florence',
            'source-layer': 'building',
            paint: { 'fill-color': '#d9c9b9', 'fill-opacity': 0.7 }
          }
        ]
      },
      center: [11.255, 43.77], // Florence, Italy
      zoom: 14
    });
  </script>
</body>
</html>

Open index.html in your browser to see the map!

What's Next?

Configuration

Learn about all configuration options including styles, fonts, and multiple sources.

Static Map Images

Generate static map images for thumbnails, social cards, and print.

API Reference

Explore all available API endpoints.

MapLibre Integration

Deep dive into MapLibre GL JS integration.

Common Issues

Port Already in Use

# Use a different port
docker run -p 3000:8080 ...

# Or with local binary
tileserver-rs --config config.toml --port 3000

Permission Denied (Docker)

Make sure your data directory is readable:

chmod -R 755 data/

Tiles Return 404

Check that your source ID matches the URL path:

  • Config: id = "florence"
  • URL: /data/florence/{z}/{x}/{y}.pbf