feat: consume manifest-driven native roads
This commit is contained in:
@@ -10,6 +10,7 @@ The expected values are derived from the geometry, not captured from the
|
||||
implementation — a test that just records current output would ratify a bug.
|
||||
"""
|
||||
|
||||
import json
|
||||
import math
|
||||
import os
|
||||
import sys
|
||||
@@ -30,7 +31,8 @@ from osmassets.geom import (
|
||||
sample_tree_row,
|
||||
signed_polygon_area,
|
||||
)
|
||||
from osmassets.catalog import NATIVE_ROAD_LAYERS, ROAD_LAYERS
|
||||
from osmassets.catalog import ROAD_LAYERS
|
||||
from osmassets.native_road_manifest import CONTRACT, load as load_native_road_manifest
|
||||
from osmassets.osm import Projector, parse_height, parse_osm, tags
|
||||
|
||||
|
||||
@@ -46,24 +48,6 @@ class RoadLayerCatalogTest(unittest.TestCase):
|
||||
self.assertNotEqual(layers["road_surface"]["z"],
|
||||
layers["intersection_surface"]["z"])
|
||||
|
||||
def test_native_provider_maps_to_existing_material_layers(self):
|
||||
layers = {layer["id"] for layer in ROAD_LAYERS}
|
||||
self.assertEqual(
|
||||
[(entry["source"], entry["material_layer"])
|
||||
for entry in NATIVE_ROAD_LAYERS],
|
||||
[("road_surface", "road_surface"),
|
||||
("edge_lines", "lane_separators"),
|
||||
("intersection_surface", "intersection_surface"),
|
||||
("sidewalk_surface", "sidewalks"),
|
||||
("lane_separators", "lane_separators"),
|
||||
("center_lines", "center_lines"),
|
||||
("direction_arrows", "lane_arrows_webscale"),
|
||||
("turn_arrows", "lane_arrows_webscale"),
|
||||
("crosswalks", "crosswalks"),
|
||||
("vehicle_stop_lines", "vehicle_stop_lines")])
|
||||
self.assertTrue(all(entry["material_layer"] in layers
|
||||
for entry in NATIVE_ROAD_LAYERS))
|
||||
|
||||
def test_cesium_export_keeps_signal_assets_optional(self):
|
||||
exporter = os.path.join(os.path.dirname(os.path.abspath(__file__)),
|
||||
"..", "export_cesium.py")
|
||||
@@ -72,6 +56,66 @@ class RoadLayerCatalogTest(unittest.TestCase):
|
||||
self.assertIn('if not args.get(key):\n continue', source)
|
||||
|
||||
|
||||
class NativeRoadManifestTest(unittest.TestCase):
|
||||
def setUp(self):
|
||||
self.root = tempfile.TemporaryDirectory()
|
||||
self.layers_dir = os.path.join(self.root.name, "layers")
|
||||
os.mkdir(self.layers_dir)
|
||||
|
||||
def tearDown(self):
|
||||
self.root.cleanup()
|
||||
|
||||
def write_manifest(self, layers):
|
||||
with open(os.path.join(self.root.name, "manifest.json"), "w", encoding="utf-8") as handle:
|
||||
json.dump({"contract": CONTRACT, "areaId": "test", "layers": layers}, handle)
|
||||
for layer in layers:
|
||||
with open(os.path.join(self.layers_dir, layer["source"] + ".geojson"), "w",
|
||||
encoding="utf-8") as handle:
|
||||
json.dump({"type": "FeatureCollection", "features": []}, handle)
|
||||
|
||||
def test_accepts_semantic_and_split_layers(self):
|
||||
layers = [
|
||||
{"source": "road_surface", "role": "surface", "materialLayer": "road_surface"},
|
||||
{"source": "center_lines", "role": "marking", "materialLayer": "center_lines",
|
||||
"splitBy": {"prop": "color", "cases": [
|
||||
{"match": "white", "material": "native_center_line_white"},
|
||||
{"default": True, "material": "center_lines"},
|
||||
]}},
|
||||
{"source": "connectors", "role": "semantic"},
|
||||
]
|
||||
self.write_manifest(layers)
|
||||
self.assertEqual(load_native_road_manifest(self.root.name)["layers"], layers)
|
||||
|
||||
def test_rejects_undeclared_or_missing_geojson(self):
|
||||
layers = [{"source": "road_surface", "role": "surface",
|
||||
"materialLayer": "road_surface"}]
|
||||
self.write_manifest(layers)
|
||||
with open(os.path.join(self.layers_dir, "extra.geojson"), "w", encoding="utf-8") as handle:
|
||||
handle.write("{}")
|
||||
with self.assertRaisesRegex(RuntimeError, "mismatch"):
|
||||
load_native_road_manifest(self.root.name)
|
||||
os.unlink(os.path.join(self.layers_dir, "extra.geojson"))
|
||||
os.unlink(os.path.join(self.layers_dir, "road_surface.geojson"))
|
||||
with self.assertRaisesRegex(RuntimeError, "mismatch"):
|
||||
load_native_road_manifest(self.root.name)
|
||||
|
||||
def test_rejects_invalid_semantic_and_split_definitions(self):
|
||||
self.write_manifest([{"source": "connectors", "role": "semantic",
|
||||
"materialLayer": "road_surface"}])
|
||||
with self.assertRaisesRegex(RuntimeError, "semantic"):
|
||||
load_native_road_manifest(self.root.name)
|
||||
|
||||
self.write_manifest([{"source": "center_lines", "role": "marking",
|
||||
"materialLayer": "center_lines", "splitBy": {
|
||||
"prop": "color", "cases": [
|
||||
{"match": "white", "material": "native_center_line_white"},
|
||||
{"default": True, "material": "center_lines"},
|
||||
{"default": True, "material": "center_lines"},
|
||||
]}}])
|
||||
with self.assertRaisesRegex(RuntimeError, "exactly one default"):
|
||||
load_native_road_manifest(self.root.name)
|
||||
|
||||
|
||||
class GeometryRingsTest(unittest.TestCase):
|
||||
def test_polygon_keeps_only_the_exterior_ring(self):
|
||||
geometry = {"type": "Polygon", "coordinates": [["outer"], ["hole"]]}
|
||||
|
||||
Reference in New Issue
Block a user