Skip to content

Commit bef6e95

Browse files
authored
give user a warning if IDs will collide (#8)
* give user a warning if IDs will collide * osmosis -> osmium * add --no_collisions flag
1 parent a2911ad commit bef6e95

File tree

1 file changed

+51
-0
lines changed

1 file changed

+51
-0
lines changed

changegen/__main__.py

Lines changed: 51 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,6 @@
11
import logging
22
import os
3+
import subprocess
34
import sys
45

56
import click
@@ -19,6 +20,36 @@
1920
"""
2021

2122

23+
def _get_max_ids(source_extract):
24+
# get the max ID from source extract using osmium
25+
## first ensure that osmium exists
26+
try:
27+
proc = subprocess.check_call(
28+
"osmium --help",
29+
shell=True,
30+
stdout=subprocess.DEVNULL,
31+
stderr=subprocess.DEVNULL,
32+
)
33+
except subprocess.CalledProcessError as e:
34+
logging.warning(
35+
"osmium not found; unable to determine max OSM id in source extract"
36+
)
37+
raise e
38+
39+
ids = {}
40+
for idtype in ["data.maxid.ways", "data.maxid.nodes", "data.maxid.relations"]:
41+
proc = subprocess.Popen(
42+
f"osmium fileinfo -e -g {idtype} --no-progress {source_extract}",
43+
shell=True,
44+
stdout=subprocess.PIPE,
45+
stderr=subprocess.PIPE,
46+
)
47+
if proc.stderr.read():
48+
raise subprocess.CalledProcessError(-1, "osmium", "Error in osmium.")
49+
ids[idtype.split(".")[-1]] = int(proc.stdout.read().strip())
50+
return ids
51+
52+
2253
def _get_db_tables(suffix, dbname, dbport, dbuser, dbpass, dbhost):
2354
c = psy.connect(
2455
dbname=dbname, host=dbhost, user=dbuser, password=dbpass, port=dbport
@@ -67,6 +98,13 @@ def _get_db_tables(suffix, dbname, dbport, dbuser, dbpass, dbhost):
6798
default=0,
6899
show_default=True,
69100
)
101+
@click.option(
102+
"--no_collisions",
103+
help="Stop execution if the chosen ID offset "
104+
"will cause collisions with existing OSM ids."
105+
" (requires osmium).",
106+
is_flag=True,
107+
)
70108
@click.option(
71109
"--self",
72110
"-si",
@@ -103,6 +141,19 @@ def main(*args: tuple, **kwargs: dict):
103141
setup_logging(debug=kwargs["debug"])
104142
logging.debug(f"Args: {kwargs}")
105143

144+
# Check for ID collisions and warn
145+
try:
146+
ids = _get_max_ids(kwargs["osmsrc"])
147+
if any([kwargs["id_offset"] < id for id in ids.values()]):
148+
_log_text = f"Chosen ID offset {kwargs['id_offset']} may cause collisions with existing OSM IDs (max IDs: {ids})."
149+
if kwargs["no_collisions"]:
150+
logging.fatal(_log_text)
151+
sys.exit(-1)
152+
else:
153+
logging.warning(_log_text)
154+
except subprocess.CalledProcessError:
155+
logging.error("Error checking existing OSM max ids.")
156+
106157
new_tables = []
107158
for suffix in kwargs["suffix"]:
108159
new_tables.extend(

0 commit comments

Comments
 (0)