Path: blob/main/tests/complex/netconvert/osm_sidewalk_access/runner.py
428379 views
#!/usr/bin/env python1# -*- coding: utf-8 -*-2# Eclipse SUMO, Simulation of Urban MObility; see https://eclipse.dev/sumo3# Copyright (C) 2008-2026 German Aerospace Center (DLR) and others.4# This program and the accompanying materials are made available under the5# terms of the Eclipse Public License 2.0 which is available at6# https://www.eclipse.org/legal/epl-2.0/7# This Source Code may also be made available under the following Secondary8# Licenses when the conditions for such availability set forth in the Eclipse9# Public License 2.0 are satisfied: GNU General Public License, version 210# or later which is available at11# https://www.gnu.org/licenses/old-licenses/gpl-2.0-standalone.html12# SPDX-License-Identifier: EPL-2.0 OR GPL-2.0-or-later1314# @file runner.py15# @author Michael Behrisch16# @date 2026-03-251718"""19Test netconvert OSM import for correct pedestrian access handling under20various sidewalk tag combinations. Refs https://github.com/eclipse-sumo/sumo/issues/177582122Rules under test:23- sidewalk=separate/separated -> pedestrians must NOT be on the road24(unless foot=yes explicitly overrides)25- foot=no / foot=use_sidepath -> pedestrians excluded from road26- foot=yes -> pedestrians explicitly allowed on road27- sidewalk=both/left/right -> separate sidewalk lane added under28--osm.sidewalks; pedestrians off road lanes29- No sidewalk tags -> pedestrians follow typemap defaults30"""3132from __future__ import print_function33import os34import subprocess35import sys3637if "SUMO_HOME" in os.environ:38sys.path.append(os.path.join(os.environ["SUMO_HOME"], "tools"))39import sumolib # noqa4041OSM_TEMPLATE = """\42<?xml version="1.0" encoding="UTF-8"?>43<osm version="0.6">44<node id="1" lat="51.500" lon="0.000"/>45<node id="2" lat="51.501" lon="0.000"/>46<way id="101">47<nd ref="1"/>48<nd ref="2"/>49<tag k="highway" v="secondary"/>50<tag k="lanes" v="2"/>51<tag k="maxspeed" v="50"/>52<tag k="name" v="Test Road"/>53{tags}54</way>55</osm>56"""575859def _is_sidewalk_lane(lane):60"""True if the lane is a dedicated sidewalk (pedestrian-only lane)."""61return lane.getPermissions().issubset({"pedestrian", "wheelchair"})626364def run_case(extra_tags, use_osm_sidewalks, guess_sidewalks, typemap):65# Build OSM XML66tag_lines = "\n".join(' <tag k="{}" v="{}"/>'.format(k, v) for k, v in extra_tags)67osm_text = OSM_TEMPLATE.format(tags=tag_lines)68with open("osm.xml", "w") as fh:69fh.write(osm_text)7071# Run netconvert72cmd = [sumolib.checkBinary("netconvert"), "--osm-files", "osm.xml", "--output-file", "test.net.xml"]73if typemap:74cmd += ["--type-files", typemap]75if use_osm_sidewalks:76cmd.append("--osm.sidewalks")77if guess_sidewalks:78cmd.append("--sidewalks.guess")79subprocess.check_call(cmd, stdout=subprocess.DEVNULL)8081# Inspect the network82net = sumolib.net.readNet("test.net.xml")83any_sidewalk = False84any_ped_on_road = False85for edge in net.getEdges():86lanes = edge.getLanes()87sidewalk_lanes = [la for la in lanes if _is_sidewalk_lane(la)]88road_lanes = [la for la in lanes if not _is_sidewalk_lane(la)]89if sidewalk_lanes:90any_sidewalk = True91if any(la.allows("pedestrian") for la in road_lanes):92any_ped_on_road = True93print("tags:", extra_tags, " ".join(["netconvert"] + cmd[5:]).replace(os.environ["SUMO_HOME"], ""))94print(" sidewalk:", any_sidewalk, "peds_on_road:", any_ped_on_road)959697if __name__ == "__main__":98pedmap = os.path.join(os.environ["SUMO_HOME"], "data", "typemap", "osmNetconvertPedestrians.typ.xml")99for osm in (False, True):100for guess in (False, True):101for typemap in (None, pedmap):102for sidewalk in (None, "yes", "no", "both", "left", "right", "separate", "none"):103sidewalk_tag = [("sidewalk", sidewalk)] if sidewalk else []104for foot in (None, "yes", "no", "designated", "use_sidepath"):105foot_tag = [("foot", foot)] if foot else []106run_case(sidewalk_tag + foot_tag, osm, guess, typemap)107108109