fast-mvt 0.3.1

Fast Mapbox Vector Tile (MVT) reader and writer
Documentation

fast-mvt

GitHub repo crates.io version crate usage docs.rs status crates.io license CI build status Codecov

fast-mvt is an integer-only Mapbox Vector Tile reader and writer for Rust. Geometry uses geo-types with i32 coordinates. The crate does not project, scale, round, or handle floating point geometry coordinates; callers provide and receive tile-space integers.

Decoding a tile

use fast_mvt::{MvtReaderRef, MvtResult};

fn read_tile(bytes: &[u8]) -> MvtResult<()> {
    let reader = MvtReaderRef::new(bytes)?;

    for layer in reader.layers() {
        for feature in layer.features() {
            let geometry = feature.geometry()?;
            println!("geo: {geometry:?}");
            let id = feature.id();
            println!("id: {id:?}");

            for property in feature.properties() {
                let (key, value) = property?;
                println!("{key} = {value:?}");
            }
        }
    }

    Ok(())
}

Encoding a tile

use fast_mvt::{MvtGeometry, MvtResult, MvtTileBuilder};

fn write_tile() -> MvtResult<Vec<u8>> {
    let tile = MvtTileBuilder::new();
    let layer = tile.layer("places")?;

    let mut feature = layer.feature(MvtGeometry::Point((1, 2).into()))?;
    feature.id(Some(7));
    feature.tag("name", "Example")?;
    feature.tag("visible", true)?;
    let layer = feature.finish();

    let tile = layer.finish();
    Ok(tile.finish())
}

Opening a layer consumes the tile builder, and opening a feature consumes the layer builder. Finishing returns the parent builder with the child committed, so there is no reachable partially committed layer or tile while a child is in progress. A single-layer tile byte buffer is also a framed layer chunk, so multiple independently built layer buffers can be concatenated to form a tile.

Benchmarks

Decoding

Run with just bench-decode:

Decoder Time Compare
fast-mvt 228 ms -
tinymvt 410 ms 80% slower
mvt-reader 1148 ms 403% slower

Encoding

Run with just bench-encode:

Encoder Time Compare
fast-mvt 987 ms -
mvt 11549 ms 1070% slower

Features

Feature Purpose
reader MVT tile decoding from bytes.
writer MVT tile encoding into bytes.
json Enable serde JSON support.
codegen Regenerate checked-in protobuf bindings from src/vector_tile.proto.
arbitrary Derive arbitrary::Arbitrary for generated protobuf types for fuzzing.
views Internal feature, do not use. Must be here due to buffa limitations.

The generated protobuf files are checked in, so normal builds do not require protoc. Run just update-generated to refresh generated code after buffa upgrades.

Development

  • This project is easier to develop with just, a modern alternative to make. Install it with cargo install just.
  • To get a list of available commands, run just.
  • To run tests, use just test.

Credits

The code was inspired by several open source MVT implementations:

  • Encoding and testing from mvt crate by the Minnesota Department of Transportation.
  • Decoding and testing from mvt-reader by Paul Lange.

License

Licensed under either of

Contribution

Unless you explicitly state otherwise, any contribution intentionally submitted for inclusion in the work by you, as defined in the Apache-2.0 license, shall be dual-licensed as above, without any additional terms or conditions.