summaryrefslogtreecommitdiff
path: root/searx/engines/openstreetmap.py
blob: 733ba62034c15e102e46e40d684119e3a881fa22 (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
"""
 OpenStreetMap (Map)

 @website     https://openstreetmap.org/
 @provide-api yes (http://wiki.openstreetmap.org/wiki/Nominatim)

 @using-api   yes
 @results     JSON
 @stable      yes
 @parse       url, title
"""

from json import loads

# engine dependent config
categories = ['map']
paging = False

# search-url
base_url = 'https://nominatim.openstreetmap.org/'
search_string = 'search/{query}?format=json&polygon_geojson=1&addressdetails=1'
result_base_url = 'https://openstreetmap.org/{osm_type}/{osm_id}'


# do search-request
def request(query, params):
    params['url'] = base_url + search_string.format(query=query)

    return params


# get response from search-request
def response(resp):
    results = []
    json = loads(resp.text)

    # parse results
    for r in json:
        if 'display_name' not in r:
            continue

        title = r['display_name'] or u''
        osm_type = r.get('osm_type', r.get('type'))
        url = result_base_url.format(osm_type=osm_type,
                                     osm_id=r['osm_id'])

        osm = {'type': osm_type,
               'id': r['osm_id']}

        geojson = r.get('geojson')

        # if no geojson is found and osm_type is a node, add geojson Point
        if not geojson and osm_type == 'node':
            geojson = {u'type': u'Point', u'coordinates': [r['lon'], r['lat']]}

        address_raw = r.get('address')
        address = {}

        # get name
        if r['class'] == 'amenity' or\
           r['class'] == 'shop' or\
           r['class'] == 'tourism' or\
           r['class'] == 'leisure':
            if address_raw.get('address29'):
                address = {'name': address_raw.get('address29')}
            else:
                address = {'name': address_raw.get(r['type'])}

        # add rest of adressdata, if something is already found
        if address.get('name'):
            address.update({'house_number': address_raw.get('house_number'),
                           'road': address_raw.get('road'),
                           'locality': address_raw.get('city',
                                       address_raw.get('town',          # noqa
                                       address_raw.get('village'))),    # noqa
                           'postcode': address_raw.get('postcode'),
                           'country': address_raw.get('country'),
                           'country_code': address_raw.get('country_code')})
        else:
            address = None

        # append result
        results.append({'template': 'map.html',
                        'title': title,
                        'content': '',
                        'longitude': r['lon'],
                        'latitude': r['lat'],
                        'boundingbox': r['boundingbox'],
                        'geojson': geojson,
                        'address': address,
                        'osm': osm,
                        'url': url})

    # return results
    return results