-
Notifications
You must be signed in to change notification settings - Fork 40
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Add WrappedProcessor to help reading MVTs #222
Conversation
Sorry this sat here for so long! I really like the direction of this, but I have some proposed amendments for clarity and ergonomics - see |
Also, looking at your example, I wonder if in the future, more of this should be built into geozero's mvt support. Currently it looks like we only implement FeatureProcessor for a single |
Thank you for the fixes; merged them in here.
I'd vote yes, but I'm not sure how to design the API. Would we want optional dependencies on Or maybe the mvt::process function could take optional info about the current tile (the tile x and y, the zoom level, and the extent) and handle the math? |
I think that would be unavoidable, right? It seems reasonable to me, but I'm not actually a user of the rust mbtiles integration, so I'd try to defer to what other users think.
These are very good questions that I haven't thought about. My first guess would be to add some kind of new types to geozero for managing this logic: // 1. read everything
let tile_iter = MBTilesReader::new(some_impl_read).select_all();
// 2. read a contiguous range (like your example)
let tile_iter = MBTilesReader::new(some_impl_read).select_range(x1..=x2, y1..=y2, zoom..=zoom)
// 3. read arbitrary sequence of tiles given an iterator of tile ids (x, y, zoom)
// NOTE: getting every other tile is a contrived example, but it seems reasonable that
// eventually someone will want something more flexible than what's offered by (2.)
let tile_id_iter = (x1..=x2).step_by(2).flat_map(|x| y1..=y2.iter().step_by(2) ).map(|y| (x, y, zoom))
let tile_iter = MBTilesReader::new(some_impl_read).select_tiles_by_iter(tile_id_iter)
// TileIter is the thing that implements the geozero::FeatureProcessor
let geojson = tile_iter.to_geojson() It might even make sense to upstream these Reader/Selection APIs to mbtiles, but I wouldn't hold my breath. |
i would love to have proper iterator support in the |
1. Rename to clarify it's wrapping XY processing. I'm hopeful we might have pre-processors for other fields! 2. Make mutable instead of passing a value - this makes the pre-processor signature closer to the processor signature. 3. Add "builder" api to convert FeatureProcessor into XYPreProcessor 4. Add a test!
736d12a
to
d4d46b8
Compare
I've just rebased and clarified the test cases. What do you think about this API addition @pka? I think it implies that we could add similar pre-processing methods for pipelining other transformations. |
d4d46b8
to
878fc29
Compare
It was one of the initial goals to support processing pipelines like reprojections, but I never found a good way to implement it (see also https://github.com/georust/geozero/blob/main/geozero/src/multiplex.rs for an experimental chained processor). Having said that, the |
878fc29
to
58f346f
Compare
There's only so many algorithms that can be solved in a single pass. Even simple things, like what @kylebarron ran into in #237 (comment), are hindered by this. That said, I think a reasonable Simplification implementation would work OK with the current APIs. |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Would you mind taking another look at my amendments @dabreegster? If they look good to you, I'll go ahead and merge.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Looks great to me, thanks so much for taking over this!
i would love to have proper iterator support in the mbtiles crate. PRs welcome
When I get some time, I'll rewrite my example reader with the changes here, and see how an iterator API might work
My ultimate aim is to read an mbtiles file with a single zoom level and extract features from it. It contains compressed MVT data. To that end, I wrote https://github.com/acteng/will-it-fit/blob/main/data_prep/fix_osmm/src/main.rs using geozero and some other crates. It works like this:
mbtiles
crate to open the fileflate2
to gunzip itgeozero::mvt::Tile
protoWrappedProcessor
to delegate to anotherFeatureProcessor
(anFgbWriter
in this example), but call a function on every coordinate firstThis PR adds the
WrappedProcessor
, in case it might be helpful for other use cases. But I'm not sure this approach is the nicest one -- maybe the mvt::process function should instead take optional info about the current tile (the tile x and y, the zoom level, and the extent), plumb it through the private methods in that file, and apply in process_coord?I'm not opinionated about the best way to read an mvt tile doing this coordinate transformation, so happy to implement the other approach or something else entirely. Thanks!