X-Git-Url: https://git.openstreetmap.org./nominatim.git/blobdiff_plain/c50c534d19889d7cdea46049d1214a0081a8dcb1..6dac643d2c48c00065c68e575f7dbbc092175245:/lib-sql/functions/placex_triggers.sql diff --git a/lib-sql/functions/placex_triggers.sql b/lib-sql/functions/placex_triggers.sql index 6ab73a3b..8a65c555 100644 --- a/lib-sql/functions/placex_triggers.sql +++ b/lib-sql/functions/placex_triggers.sql @@ -26,6 +26,7 @@ CREATE OR REPLACE FUNCTION placex_indexing_prepare(p placex) DECLARE location RECORD; result prepare_update_info; + extra_names HSTORE; BEGIN -- For POI nodes, check if the address should be derived from a surrounding -- building. @@ -58,8 +59,11 @@ BEGIN END LOOP; END IF; + -- remove internal and derived names result.address := result.address - '_unlisted_place'::TEXT; - result.name := p.name; + SELECT hstore(array_agg(key), array_agg(value)) INTO result.name + FROM each(p.name) WHERE key not like '\_%'; + result.class := p.class; result.type := p.type; result.country_code := p.country_code; @@ -72,8 +76,20 @@ BEGIN IF location.place_id is not NULL THEN result.linked_place_id := location.place_id; - IF NOT location.name IS NULL THEN - result.name := location.name || result.name; + IF location.name is not NULL THEN + {% if debug %}RAISE WARNING 'Names original: %, location: %', result.name, location.name;{% endif %} + -- Add all names from the place nodes that deviate from the name + -- in the relation with the prefix '_place_'. Deviation means that + -- either the value is different or a given key is missing completely + SELECT hstore(array_agg('_place_' || key), array_agg(value)) INTO extra_names + FROM each(location.name - result.name); + {% if debug %}RAISE WARNING 'Extra names: %', extra_names;{% endif %} + + IF extra_names is not null THEN + result.name := result.name || extra_names; + END IF; + + {% if debug %}RAISE WARNING 'Final names: %', result.name;{% endif %} END IF; END IF; @@ -342,9 +358,10 @@ BEGIN WHERE s.place_id = parent_place_id; FOR addr_item IN - SELECT (get_addr_tag_rank(key, country)).*, key, + SELECT ranks.*, key, token_get_address_search_tokens(token_info, key) as search_tokens - FROM token_get_address_keys(token_info) as key + FROM token_get_address_keys(token_info) as key, + LATERAL get_addr_tag_rank(key, country) as ranks WHERE not token_get_address_search_tokens(token_info, key) <@ parent_address_vector LOOP addr_place := get_address_place(in_partition, geometry, @@ -432,6 +449,7 @@ CREATE OR REPLACE FUNCTION insert_addresslines(obj_place_id BIGINT, maxrank SMALLINT, token_info JSONB, geometry GEOMETRY, + centroid GEOMETRY, country TEXT, OUT parent_place_id BIGINT, OUT postcode TEXT, @@ -456,10 +474,12 @@ BEGIN address_havelevel := array_fill(false, ARRAY[maxrank]); FOR location IN - SELECT (get_address_place(partition, geometry, from_rank, to_rank, - extent, token_info, key)).*, key - FROM (SELECT (get_addr_tag_rank(key, country)).*, key - FROM token_get_address_keys(token_info) as key) x + SELECT apl.*, key + FROM (SELECT extra.*, key + FROM token_get_address_keys(token_info) as key, + LATERAL get_addr_tag_rank(key, country) as extra) x, + LATERAL get_address_place(partition, geometry, from_rank, to_rank, + extent, token_info, key) as apl ORDER BY rank_address, distance, isguess desc LOOP IF location.place_id is null THEN @@ -492,7 +512,7 @@ BEGIN END LOOP; FOR location IN - SELECT * FROM getNearFeatures(partition, geometry, maxrank) + SELECT * FROM getNearFeatures(partition, geometry, centroid, maxrank) WHERE not addr_place_ids @> ARRAY[place_id] ORDER BY rank_address, isguess asc, distance * @@ -1044,16 +1064,22 @@ BEGIN AND NEW.class = 'boundary' AND NEW.type = 'administrative' AND NEW.country_code IS NOT NULL AND NEW.osm_type = 'R' THEN - -- Update the list of country names. Adding an additional sanity - -- check here: make sure the country does overlap with the area where - -- we expect it to be as per static country grid. + -- Update the list of country names. + -- Only take the name from the largest area for the given country code + -- in the hope that this is the authoritive one. + -- Also replace any old names so that all mapping mistakes can + -- be fixed through regular OSM updates. FOR location IN - SELECT country_code FROM country_osm_grid - WHERE ST_Covers(geometry, NEW.centroid) and country_code = NEW.country_code + SELECT osm_id FROM placex + WHERE rank_search = 4 and osm_type = 'R' + and country_code = NEW.country_code + ORDER BY ST_Area(geometry) desc LIMIT 1 LOOP - {% if debug %}RAISE WARNING 'Updating names for country '%' with: %', NEW.country_code, NEW.name;{% endif %} - UPDATE country_name SET name = name || NEW.name WHERE country_code = NEW.country_code; + IF location.osm_id = NEW.osm_id THEN + {% if debug %}RAISE WARNING 'Updating names for country '%' with: %', NEW.country_code, NEW.name;{% endif %} + UPDATE country_name SET derived_name = NEW.name WHERE country_code = NEW.country_code; + END IF; END LOOP; END IF; @@ -1081,7 +1107,8 @@ BEGIN END IF; SELECT * FROM insert_addresslines(NEW.place_id, NEW.partition, max_rank, - NEW.token_info, geom, NEW.country_code) + NEW.token_info, geom, NEW.centroid, + NEW.country_code) INTO NEW.parent_place_id, NEW.postcode, nameaddress_vector; {% if debug %}RAISE WARNING 'RETURN insert_addresslines: %, %, %', NEW.parent_place_id, NEW.postcode, nameaddress_vector;{% endif %}