"""
This file is part of OSM-flex.
Copyright (C) 2023 OSM-flex contributors listed in AUTHORS.
OSM-flex is free software: you can redistribute it and/or modify it under the
terms of the GNU General Public License as published by the Free
Software Foundation, version 3.
OSM-flex is distributed in the hope that it will be useful, but WITHOUT ANY
WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A
PARTICULAR PURPOSE. See the GNU General Public License for more details.
-----
downloading functions
"""
import logging
from pathlib import Path
import urllib.request
from urllib.parse import urljoin
from osm_flex.config import DICT_GEOFABRIK, GEOFABRIK_URL, PLANET_URL, OSM_DATA_DIR
[docs]
LOGGER = logging.getLogger(__name__)
# =============================================================================
# DOWNLOAD METHODS
# =============================================================================
[docs]
def _create_gf_download_url(iso3, file_format):
"""
create string with download-url from geofabrik
Parameters
----------
iso3 : str
ISO3 code of country to download
file_format : str
Format in which file should be downloaded; ESRI Shapefiles ('shp')
or osm-Protocolbuffer Binary Format ('pbf')
Returns
-------
url: str
Geofabrik download URL for the requested country.
See also
--------
DICT_GEOFABRIK for exceptions / special regions.
"""
# Retrieve Geofabrik definitions
try:
continent, country = DICT_GEOFABRIK[iso3]
except KeyError as err:
if iso3 == "RUS":
raise KeyError(
"Russia comes in two files. Please specify either RUS-A for the Asian "
"or RUS-E for the European part."
) from err
raise KeyError(
"The provided iso3 seems not to be available on Geofabrik.de. You can clip "
"it from the planet file or an adequate regional file, instead. See the "
"methods in the clip module for this."
) from err
# Set file extension
if file_format == "shp":
ext = "-free.shp.zip"
elif file_format == "pbf":
ext = ".osm.pbf"
else:
raise NotImplementedError(
f"Invalid file format '{file_format}'. Please choose one of [shp, pbf]"
)
# Join to URL
return urljoin(GEOFABRIK_URL, f"{continent}/{country}-latest{ext}")
[docs]
def _download_file(download_url: str, filepath: Path, overwrite: bool = True):
"""Download a file located at an URL to a local file path
Parameters
----------
download_url : str
URL of the file to download
filepath : str or Path
Local file path to store the file
overwrite : bool, optional
Overwrite existing files. If ``False``, the download will be skipped for
existing files. Defaults to ``True``.
"""
if not Path(filepath).is_file() or overwrite:
LOGGER.info(f"Download file: {filepath}")
urllib.request.urlretrieve(download_url, filepath)
else:
LOGGER.info(f"Skip existing file: {filepath}")
# TODO: decide whether to issue warnings for multi-country files
[docs]
def get_country_geofabrik(iso3, file_format='pbf', save_path=OSM_DATA_DIR,
overwrite=False):
"""
Download country files with all OSM map info from the provider
Geofabrik.de.
Parameters
----------
iso3 : str
ISO3 code of country to download
Exceptions: Russia is divided into European and Asian part
('RUS-E', 'RUS-A'), Canary Islands are 'IC'.
file_format : str
Format in which file should be downloaded; options are
ESRI Shapefiles (shp), which can easily be loaded into gdfs,
or osm-Protocolbuffer Binary Format (pbf), which is smaller in
size, but has a more complicated query syntax to load (functions
are provided in the OSMFileQuery class).
save_path : str or pathlib.Path
Folder in which to save the file
Returns
-------
filepath : Path
The path to the downloaded file (``save_path`` + the Geofabrik filename)
See also
--------
DICT_GEOFABRIK for exceptions / special regions.
"""
download_url = _create_gf_download_url(iso3, file_format)
filepath = Path(save_path, Path(download_url).name)
_download_file(download_url, filepath, overwrite)
return filepath
# TODO: allow for several spelling options like "Central America", "Australia", ...
[docs]
def get_region_geofabrik(region, save_path=OSM_DATA_DIR, overwrite=False):
"""
Download regions files with all OSM map info from the provider
Geofabrik.de
Parameters
----------
region: str
one of Africa, Antarctica, Asia, Australia-and-Oceania,
Central-America, Europe, North-America, South-America
save_path : str or pathlib.Path
Folder in which to save the file
Returns
-------
filepath : Path
The path to the downloaded file
"""
download_url = f'{GEOFABRIK_URL}{region.lower()}-latest.osm.pbf'
filepath = Path(save_path, Path(download_url).name)
_download_file(download_url, filepath, overwrite)
return filepath
[docs]
def get_planet_file(save_path=Path(OSM_DATA_DIR,'planet-latest.osm.pbf'),
overwrite=False):
"""
Download the entire planet file from the OSM server (ca. 60 GB).
Parameters
----------
save_path : str or pathlib.Path
The path to store the file.
Returns
-------
save_path : Path
The path to the downloaded file. Returned for consistency with other download
functions.
"""
_download_file(PLANET_URL, save_path, overwrite)
return Path(save_path)