Small to medium scale download in OSM format

Small to medium scale download in OSM format#

Overpass API and Overpass Turbo#

The Overpass API allows you to query for OSM data in a very flexible manner through two different query languages: Overpass XML and Overpass QL. Overpass Turbo provides a web front-end which helps you to run Overpass API queries and analyse the resulting OSM data interactively on a map. The integrated Wizard makes creating queries super easy. Below you will find useful example queries.

Advantages
  • get very up-to-date data from OSM

  • extract specific objects up to regional level

  • easy to get temporal/user based changes up to a regional level

  • super flexible query language lets you perform complex analyses such as topological filters

Limitations
  • queries can time out if area is too large or too many objects are requested

  • need to convert raw OSM data into standard geo-data formats after querying the API

overpass-turbo

Quick OSM Plugin for QGIS

QuickOSM allows you to work quickly with OSM data in QGIS and is powered by the Overpass API. At learnOSM you will find a tutorial to get started with QuickOSM. The Plugin provides an interface to do the following (and more!):

  • Write some queries for you by providing a key/value

  • run the query on an area or an extent, e.g. specified by another layer

  • flexible configuration of each query : which layers, which columns…

  • embed your queries in larger workflows using the QGIS Processing functions

You can check out this talk by Astrid Emde at State of the Map 2019 to learn more: How to use OpenStreetMap data with the Desktop GIS QGIS

Overpass API Query Examples

Note

This section is mainly based on a slides created by Marcel Reinmuth.

Further examples can be found in the OSM Wiki and a here is a general language guide for the Overpass API. In Python you can use the OSMPythonTools.

Select/Filter by Tag

You can also query only specific OSM types, e.g. only nodes (example: https://overpass-turbo.eu/s/16ma).

[out:json][timeout:25];
(
node["amenity"="university"]({{bbox}});
way["amenity"="university"]({{bbox}});
relation ["amenity"="university"]({{bbox}});
);
out meta;
>;
out skel qt;
from OSMPythonTools.overpass import Overpass
from OSMPythonTools.overpass import overpassQueryBuilder
from OSMPythonTools.nominatim import Nominatim

nominatim = Nominatim()
overpass = Overpass()

query = overpassQueryBuilder(
    area=nominatim.query('Heidelberg').areaId(),
    elementType=['node', 'way', 'relation'],
    selector=['"amenity"="university"']
)

result = overpass.query(query)

print(f"Nodes: {len(result.nodes())}")
print(f"Ways: {len(result.ways())}")
print(f"Relations: {len(result.relations())}")

Quick-Exercise

Go to Overpass-Turbo and get some OSM data by using a simple filter, e.g. amenity=school. Use the example above to get the syntax right. (You might need to adjust the timeout to something bigger.)

Filter by Username

This uses the current username of an OSM contributor and is based on the latest OSM snapshot (example: http://overpass-turbo.eu/s/16mf).

[out:json][timeout:25];
// gather results
(
  // query part for: “user:maze2p0”
  node(user:"maze2p0")({{bbox}});
  way(user:"maze2p0")({{bbox}});
  relation(user:"maze2p0")({{bbox}});
);
// print results
out body;
>;
out skel qt;
from OSMPythonTools.overpass import Overpass
from OSMPythonTools.overpass import overpassQueryBuilder
from OSMPythonTools.nominatim import Nominatim

nominatim = Nominatim()
overpass = Overpass()

query = overpassQueryBuilder(
    area=nominatim.query('Heidelberg').areaId(),
    elementType=['node', 'way', 'relation'],
    user="maze2p0"
)

result = overpass.query(query)

print(f"Nodes: {len(result.nodes())}")
print(f"Ways: {len(result.ways())}")
print(f"Relations: {len(result.relations())}")

Filter by time - objects recently edited

Get only objects that have been edited since a specific date (example: http://overpass-turbo.eu/s/16mD).

[out:json][timeout:25];
// gather results
(
  node["highway"](newer:"2021-04-16T00:00:00Z")({{bbox}});
  way["highway"](newer:"2021-04-16T00:00:00Z")({{bbox}});
  relation["highway"](newer:"2021-04-16T00:00:00Z")({{bbox}});
);
// print results
out meta;
>;
out skel qt;
from OSMPythonTools.overpass import Overpass
from OSMPythonTools.overpass import overpassQueryBuilder
from OSMPythonTools.nominatim import Nominatim

nominatim = Nominatim()
overpass = Overpass()

query = overpassQueryBuilder(
    area=nominatim.query('Heidelberg').areaId(),
    elementType=['node', 'way', 'relation'],
    selector=['"highway"'],
    since="2022-08-05T00:00:00Z"
)

result = overpass.query(query)

print(f"Nodes: {len(result.nodes())}")
print(f"Ways: {len(result.ways())}")
print(f"Relations: {len(result.relations())}")

Filter by time - historic snapshots

Get OSM data for a specific point in time that is in the past, e.g. get the road network as it was back in 2013 (example: http://overpass-turbo.eu/s/16mF).

[out:json][timeout:25][date:"2013-01-01T00:00:00Z"];
// gather results
(
  // query part for: “amenity=bar”
  node["highway"]({{bbox}});
  way["highway"]({{bbox}});
  relation["highway"]({{bbox}});
);
// print results
out meta;
>;
out skel qt;
from OSMPythonTools.overpass import Overpass
from OSMPythonTools.overpass import overpassQueryBuilder
from OSMPythonTools.nominatim import Nominatim

nominatim = Nominatim()
overpass = Overpass()

query = overpassQueryBuilder(
    area=nominatim.query('Heidelberg').areaId(),
    elementType=['node', 'way', 'relation'],
    selector=['"highway"'],
    to="2013-01-01T00:00:00Z"
)

result = overpass.query(query)

print(f"Nodes: {len(result.nodes())}")
print(f"Ways: {len(result.ways())}")
print(f"Relations: {len(result.relations())}")

Count

Count the objects and not return the objects themselves (example: http://overpass-turbo.eu/s/16mB). This is usually much faster than extracting all the elements and counting in a second step.

[out:json][timeout:25];
// gather results
(
  // query part for: “amenity=school”
  node["amenity"="school"]({{bbox}});
  way["amenity"="school"]({{bbox}});
  relation["amenity"="school"]({{bbox}});
);
// print results
out count;
from OSMPythonTools.overpass import Overpass
from OSMPythonTools.overpass import overpassQueryBuilder
from OSMPythonTools.nominatim import Nominatim

nominatim = Nominatim()
overpass = Overpass()

query = overpassQueryBuilder(
    area=nominatim.query('Heidelberg').areaId(),
    elementType=['node', 'way', 'relation'],
    selector=['"amenity"="school"'],
    to="2013-01-01T00:00:00Z"
)

result = overpass.query(query)

print(f"Nodes: {result.countNodes()}")
print(f"Ways: {result.countWays()}")
print(f"Relations: {result.countRelations()}")

Complex geospatial analysis

Get hospitals and apply a buffer of 100 meters to filter waterways (example: http://overpass-turbo.eu/s/16mI).

[out:json];

//your Area of Interest
(area[name="Malawi"]; )->.region_of_interest;

// Get all hospitals in current bounding box
( way["amenity"="hospital"](area.region_of_interest);
  node["amenity"="hospital"](area.region_of_interest);
  rel["amenity"="hospital"](area.region_of_interest);
)->.hospitals;

// find waterways around hospitals with radius 100m

way(around.hospitals:100)[waterway]->.waterways;

// get hospitals in 100m distance for all identified relevant waterways
( node.hospitals(around.waterways:100);
  way.hospitals(around.waterways:100);
  rel.hospitals(around.waterways:100);
 )->.matchinghospitals;

// return results, hospitals and waterways
(.matchinghospitals; .waterways;);
out geom;
out meta;