]> git.openstreetmap.org Git - nominatim.git/commitdiff
Merge remote-tracking branch 'upstream/master'
authorSarah Hoffmann <lonvia@denofr.de>
Fri, 6 Mar 2015 06:57:20 +0000 (07:57 +0100)
committerSarah Hoffmann <lonvia@denofr.de>
Fri, 6 Mar 2015 06:57:20 +0000 (07:57 +0100)
Conflicts:
sql/functions.sql
sql/tables.sql

15 files changed:
data/country_name.sql
data/gb_postcode_table.sql
osm2pgsql
sql/functions.sql
sql/tables.sql
tests/README.md
tests/features/db/import/interpolation.feature
tests/features/db/import/parenting.feature
tests/features/db/update/interpolation.feature [new file with mode: 0644]
tests/scenes/data/parallel-road.wkt [new file with mode: 0644]
tests/scenes/data/roads.osm
tests/steps/db_results.py
tests/steps/db_setup.py
tests/steps/terrain.py
utils/specialphrases.php

index eb52cc5da2764116c97bb8d228619165e3688e3e..352337a7ba9121753477a59928c58b7ef91ab83c 100644 (file)
@@ -295,7 +295,6 @@ CREATE INDEX idx_country_name_country_code ON country_name USING btree (country_
 --
 
 REVOKE ALL ON TABLE country_name FROM PUBLIC;
-GRANT SELECT ON TABLE country_name TO "www-data";
 
 
 --
index 7cd3f6940ab004a96139efeb59098f5376886fc3..bee8a964f191003ae6e7117a9302b239186ad47c 100644 (file)
@@ -24,4 +24,3 @@ CREATE TABLE gb_postcode (
     CONSTRAINT enforce_srid_geometry CHECK ((st_srid(geometry) = 4326))
 );
 
-GRANT SELECT ON TABLE gb_postcode TO "www-data";
index 10c274f851b63547d8e1a194231a67f8f0f8aed6..d2afef62a4a0d72c547103392cffcdda25687c6e 160000 (submodule)
--- a/osm2pgsql
+++ b/osm2pgsql
@@ -1 +1 @@
-Subproject commit 10c274f851b63547d8e1a194231a67f8f0f8aed6
+Subproject commit d2afef62a4a0d72c547103392cffcdda25687c6e
index 29e6544c4500014a8c9f5161dea5ee674b25cfde..c3590c1ebb837a3d6a65b78969019550a205bf91 100644 (file)
@@ -747,8 +747,77 @@ END;
 $$
 LANGUAGE plpgsql;
 
+-- find the parant road of an interpolation
+CREATE OR REPLACE FUNCTION get_interpolation_parent(wayid BIGINT, street TEXT, place TEXT,
+                                                    partition INTEGER, centroid GEOMETRY, geom GEOMETRY)
+RETURNS BIGINT AS $$
+DECLARE
+  addr_street TEXT;
+  addr_place TEXT;
+  parent_place_id BIGINT;
+  address_street_word_ids INTEGER[];
+
+  waynodes BIGINT[];
+
+  location RECORD;
+BEGIN
+  addr_street = street;
+  addr_place = place;
+
+  IF addr_street is null and addr_place is null THEN
+    select nodes from planet_osm_ways where id = wayid INTO waynodes;
+    FOR location IN SELECT placex.street, placex.addr_place from placex 
+                    where osm_type = 'N' and osm_id = ANY(waynodes)
+                          and (placex.street is not null or placex.addr_place is not null)
+                          and indexed_status < 100
+                    limit 1 LOOP
+      addr_street = location.street;
+      addr_place = location.addr_place;
+    END LOOP;
+  END IF;
+
+  IF addr_street IS NOT NULL THEN
+    address_street_word_ids := get_name_ids(make_standard_name(addr_street));
+    IF address_street_word_ids IS NOT NULL THEN
+      FOR location IN SELECT place_id from getNearestNamedRoadFeature(partition, centroid, address_street_word_ids) LOOP
+        parent_place_id := location.place_id;
+      END LOOP;
+    END IF;
+  END IF;
+
+  IF parent_place_id IS NULL AND addr_place IS NOT NULL THEN
+    address_street_word_ids := get_name_ids(make_standard_name(addr_place));
+    IF address_street_word_ids IS NOT NULL THEN
+      FOR location IN SELECT place_id from getNearestNamedPlaceFeature(partition, centroid, address_street_word_ids) LOOP
+        parent_place_id := location.place_id;
+      END LOOP;
+    END IF;
+  END IF;
+
+  IF parent_place_id is null THEN
+    FOR location IN SELECT place_id FROM placex
+        WHERE ST_DWithin(geom, placex.geometry, 0.001) and placex.rank_search = 26
+        ORDER BY (ST_distance(placex.geometry, ST_LineInterpolatePoint(geom,0))+
+                  ST_distance(placex.geometry, ST_LineInterpolatePoint(geom,0.5))+
+                  ST_distance(placex.geometry, ST_LineInterpolatePoint(geom,1))) ASC limit 1
+    LOOP
+      parent_place_id := location.place_id;
+    END LOOP;
+  END IF;
+
+  IF parent_place_id is null THEN
+    RETURN 0;
+  END IF;
 
-CREATE OR REPLACE FUNCTION create_interpolation(wayid BIGINT, interpolationtype TEXT) RETURNS INTEGER
+  RETURN parent_place_id;
+END;
+$$
+LANGUAGE plpgsql;
+
+CREATE OR REPLACE FUNCTION create_interpolation(wayid BIGINT, interpolationtype TEXT,
+                                                parent_id BIGINT, partition INTEGER,
+                                                country_code TEXT,  geometry_sector INTEGER,
+                                                defpostalcode TEXT, geom GEOMETRY) RETURNS INTEGER
   AS $$
 DECLARE
 
@@ -766,10 +835,12 @@ DECLARE
   linegeo GEOMETRY;
   splitline GEOMETRY;
   sectiongeo GEOMETRY;
-  search_place_id BIGINT;
-  defpostalcode TEXT;
+  pointgeo GEOMETRY;
 
 BEGIN
+  delete from placex where osm_type = 'W' and osm_id = wayid
+                                          and class = 'place' and type = 'address';
+
   IF interpolationtype = 'odd' OR interpolationtype = 'even' THEN
     stepsize := 2;
   ELSEIF interpolationtype = 'all' THEN
@@ -786,13 +857,7 @@ BEGIN
     RETURN 0;
   END IF;
 
-  select postcode, geometry from placex where osm_type = 'W' and osm_id = wayid 
-    INTO defpostalcode, linegeo;
-
-  IF ST_GeometryType(linegeo) != 'ST_LineString' THEN
-    RETURN 0;
-  END IF;
-
+  linegeo := geom;
   startnumber := NULL;
   newpoints := 0;
 
@@ -802,9 +867,10 @@ BEGIN
     -- it is guaranteed to be the original node. For place/house types use the
     -- one with the smallest id because the original node was created first.
     -- Ignore all nodes marked for deletion. (Might happen when the type changes.)
-    select place_id from placex where osm_type = 'N' and osm_id = waynodes[nodeidpos]::BIGINT and indexed_status < 100 order by (type = 'house'),place_id limit 1 INTO search_place_id;
-    IF search_place_id IS NOT NULL THEN
-      select * from placex where place_id = search_place_id INTO nextnode;
+    select * from placex where osm_type = 'N' and osm_id = waynodes[nodeidpos]::BIGINT
+                               and indexed_status < 100
+                         order by (type = 'address'),place_id limit 1 INTO nextnode;
+    IF nextnode.place_id IS NOT NULL THEN
 
         IF nodeidpos > 1 and nodeidpos < array_upper(waynodes, 1) THEN
           -- Make sure that the point is actually on the line. That might
@@ -833,23 +899,30 @@ BEGIN
 
           startnumber := startnumber + stepsize;
           -- correct for odd/even
-          IF (interpolationtype = 'odd' AND startnumber%2 = 0) OR (interpolationtype = 'even' AND startnumber%2 = 1) THEN
+          IF (interpolationtype = 'odd' AND startnumber%2 = 0)
+             OR (interpolationtype = 'even' AND startnumber%2 = 1) THEN
             startnumber := startnumber - 1;
           END IF;
           endnumber := endnumber - 1;
 
-          delete from placex where osm_type = 'N' and osm_id = prevnode.osm_id and type = 'house' and place_id != prevnode.place_id;
+          -- keep for compatibility with previous versions
+          delete from placex where osm_type = 'N' and osm_id = prevnode.osm_id
+                               and place_id != prevnode.place_id and class = 'place'
+                               and type = 'house';
           FOR housenum IN startnumber..endnumber BY stepsize LOOP
-            -- this should really copy postcodes but it puts a huge burden on
-            -- the system for no big benefit ideally postcodes should move up to the way
-            insert into placex (osm_type, osm_id, class, type, admin_level,
-              housenumber, street, addr_place, isin, postcode,
-              country_code, parent_place_id, rank_address, rank_search,
-              indexed_status, geometry)
-              values ('N', prevnode.osm_id, 'place', 'house', prevnode.admin_level,
-              housenum, prevnode.street, prevnode.addr_place, prevnode.isin, coalesce(prevnode.postcode, defpostalcode),
-              prevnode.country_code, prevnode.parent_place_id, prevnode.rank_address, prevnode.rank_search,
-              1, ST_LineInterpolatePoint(sectiongeo, (housenum::float-orginalstartnumber::float)/originalnumberrange::float));
+            pointgeo := ST_LineInterpolatePoint(sectiongeo, (housenum::float-orginalstartnumber::float)/originalnumberrange::float);
+            insert into placex (place_id, partition, osm_type, osm_id,
+                                class, type, admin_level, housenumber,
+                                postcode,
+                                country_code, parent_place_id, rank_address, rank_search,
+                                indexed_status, indexed_date, geometry_sector,
+                                calculated_country_code, centroid, geometry)
+              values (nextval('seq_place'), partition, 'W', wayid,
+                      'place', 'address', prevnode.admin_level, housenum,
+                      coalesce(prevnode.postcode, defpostalcode),
+                      prevnode.country_code, parent_id, 30, 30,
+                      0, now(), geometry_sector, country_code,
+                      pointgeo, pointgeo);
             newpoints := newpoints + 1;
 --RAISE WARNING 'interpolation number % % ',prevnode.place_id,housenum;
           END LOOP;
@@ -886,9 +959,9 @@ DECLARE
 BEGIN
   --DEBUG: RAISE WARNING '% %',NEW.osm_type,NEW.osm_id;
 
-  -- remove operator tag for most places, messes too much with search_name indexes
-  IF NEW.class not in ('amenity', 'shop') THEN
-    NEW.name := delete(NEW.name, 'operator');
+  -- ignore interpolated addresses
+  IF NEW.class = 'place' and NEW.type = 'address' THEN
+    RETURN NEW;
   END IF;
 
   -- just block these
@@ -1057,8 +1130,6 @@ BEGIN
         NEW.rank_address := NEW.rank_search;
       ELSEIF NEW.type in ('houses') THEN
         -- can't guarantee all required nodes loaded yet due to caching in osm2pgsql
-        -- insert new point into place for each derived building
-        --i := create_interpolation(NEW.osm_id, NEW.housenumber);
         NEW.rank_search := 28;
         NEW.rank_address := 0;
       END IF;
@@ -1197,6 +1268,7 @@ BEGIN
     END IF;
   END IF;
 
+
    -- add to tables for special search
    -- Note: won't work on initial import because the classtype tables
    -- do not yet exist. It won't hurt either.
@@ -1276,6 +1348,11 @@ BEGIN
     RETURN NEW;
   END IF;
 
+  -- ignore interpolated addresses
+  IF NEW.class = 'place' and NEW.type = 'address' THEN
+    RETURN NEW;
+  END IF;
+
   --DEBUG: RAISE WARNING 'placex_update % %',NEW.osm_type,NEW.osm_id;
 
 --RAISE WARNING '%',NEW.place_id;
@@ -1301,11 +1378,6 @@ BEGIN
       RETURN NEW;
     END IF;
 
-    IF NEW.class = 'place' AND NEW.type = 'houses' THEN
-      i := create_interpolation(NEW.osm_id, NEW.housenumber);
-      RETURN NEW;
-    END IF;
-
     -- Speed up searches - just use the centroid of the feature
     -- cheaper but less acurate
     place_centroid := ST_PointOnSurface(NEW.geometry);
@@ -1334,6 +1406,18 @@ BEGIN
     END IF;
     NEW.geometry_sector := geometry_sector(NEW.partition, place_centroid);
 
+    -- interpolations
+    IF NEW.class = 'place' AND NEW.type = 'houses'THEN
+      IF NEW.osm_type = 'W' and ST_GeometryType(NEW.geometry) = 'ST_LineString' THEN
+        NEW.parent_place_id := get_interpolation_parent(NEW.osm_id, NEW.street, NEW.addr_place,
+                                                        NEW.partition, place_centroid, NEW.geometry);
+        i := create_interpolation(NEW.osm_id, NEW.housenumber, NEW.parent_place_id,
+                                  NEW.partition, NEW.calculated_country_code,
+                                  NEW.geometry_sector, NEW.postcode, NEW.geometry);
+      END IF;
+      RETURN NEW;
+    END IF;
+
     -- waterway ways are linked when they are part of a relation and have the same class/type
     IF NEW.osm_type = 'R' and NEW.class = 'waterway' THEN
         FOR relation_members IN select members from planet_osm_rels r where r.id = NEW.osm_id and r.parts != array[]::bigint[]
@@ -1404,41 +1488,67 @@ BEGIN
 
       NEW.parent_place_id := null;
 
-      -- to do that we have to find our parent road
-      -- Copy data from linked items (points on ways, addr:street links, relations)
-      -- Note that addr:street links can only be indexed once the street itself is indexed
-      IF NEW.parent_place_id IS NULL AND NEW.osm_type = 'N' THEN
+      -- if we have a POI and there is no address information,
+      -- see if we can get it from a surrounding building
+      IF NEW.osm_type = 'N' AND NEW.street IS NULL AND NEW.addr_place IS NULL
+         AND NEW.housenumber IS NULL THEN
+        FOR location IN select * from placex where ST_Covers(geometry, place_centroid)
+              and (housenumber is not null or street is not null or addr_place is not null)
+              and rank_search > 28 AND ST_GeometryType(geometry) in ('ST_Polygon','ST_MultiPolygon')
+              limit 1
+        LOOP
+          NEW.housenumber := location.housenumber;
+          NEW.street := location.street;
+          NEW.addr_place := location.addr_place;
+        END LOOP;
+      END IF;
 
-        -- if there is no address information, see if we can get it from a surrounding building
-        IF NEW.street IS NULL AND NEW.addr_place IS NULL AND NEW.housenumber IS NULL THEN
-          FOR location IN select * from placex where ST_Covers(geometry, place_centroid) and rank_search > 28 and (housenumber is not null or street is not null or addr_place is not null) AND ST_GeometryType(geometry) in ('ST_Polygon','ST_MultiPolygon')
-          LOOP
-            NEW.housenumber := location.housenumber;
-            NEW.street := location.street;
-            NEW.addr_place := location.addr_place;
-          END LOOP;
-        END IF;
+      -- We have to find our parent road.
+      -- Copy data from linked items (points on ways, addr:street links, relations)
 
-        -- Is this node part of a relation?
-        FOR relation IN select * from planet_osm_rels where parts @> ARRAY[NEW.osm_id] and members @> ARRAY['n'||NEW.osm_id]
+      -- Is this object part of a relation?
+        FOR relation IN select * from planet_osm_rels where parts @> ARRAY[NEW.osm_id] and members @> ARRAY[lower(NEW.osm_type)||NEW.osm_id]
         LOOP
           -- At the moment we only process one type of relation - associatedStreet
-          IF relation.tags @> ARRAY['associatedStreet'] AND array_upper(relation.members, 1) IS NOT NULL THEN
+          IF relation.tags @> ARRAY['associatedStreet'] THEN
             FOR i IN 1..array_upper(relation.members, 1) BY 2 LOOP
               IF NEW.parent_place_id IS NULL AND relation.members[i+1] = 'street' THEN
 --RAISE WARNING 'node in relation %',relation;
-                SELECT place_id from placex where osm_type='W' and osm_id = substring(relation.members[i],2,200)::bigint 
+                SELECT place_id from placex where osm_type = 'W'
+                  and osm_id = substring(relation.members[i],2,200)::bigint
                   and rank_search = 26 and name is not null INTO NEW.parent_place_id;
               END IF;
             END LOOP;
           END IF;
-        END LOOP;      
+        END LOOP;
+
+
+      -- Note that addr:street links can only be indexed once the street itself is indexed
+       IF NEW.parent_place_id IS NULL AND NEW.street IS NOT NULL THEN
+        address_street_word_ids := get_name_ids(make_standard_name(NEW.street));
+        IF address_street_word_ids IS NOT NULL THEN
+          FOR location IN SELECT * from getNearestNamedRoadFeature(NEW.partition, place_centroid, address_street_word_ids) LOOP
+              NEW.parent_place_id := location.place_id;
+          END LOOP;
+        END IF;
+      END IF;
+
+      IF NEW.parent_place_id IS NULL AND NEW.addr_place IS NOT NULL THEN
+        address_street_word_ids := get_name_ids(make_standard_name(NEW.addr_place));
+        IF address_street_word_ids IS NOT NULL THEN
+          FOR location IN SELECT * from getNearestNamedPlaceFeature(NEW.partition, place_centroid, address_street_word_ids) LOOP
+            NEW.parent_place_id := location.place_id;
+          END LOOP;
+        END IF;
+      END IF;
+
+      IF NEW.parent_place_id IS NULL AND NEW.osm_type = 'N' THEN
 
 --RAISE WARNING 'x1';
         -- Is this node part of a way?
-        FOR way IN select id from planet_osm_ways where nodes @> ARRAY[NEW.osm_id] LOOP
---RAISE WARNING '%', way;
-        FOR location IN select * from placex where osm_type = 'W' and osm_id = way.id
+        FOR location IN select p.* from placex p, planet_osm_ways w
+           where p.osm_type = 'W' and p.rank_search >= 26
+             and p.geometry && NEW.geometry and p.osm_id = w.id and NEW.osm_id = any(w.nodes)
         LOOP
 --RAISE WARNING '%', location;
           -- Way IS a road then we are on it - that must be our road
@@ -1447,6 +1557,11 @@ BEGIN
             NEW.parent_place_id := location.place_id;
           END IF;
 
+          -- If this way is a street interpolation line then it is probably as good as we are going to get
+          IF NEW.parent_place_id IS NULL AND location.class = 'place' and location.type='houses' THEN
+            NEW.parent_place_id := location.parent_place_id;
+          END IF;
+
           -- Is the WAY part of a relation
           IF NEW.parent_place_id IS NULL THEN
               FOR relation IN select * from planet_osm_rels where parts @> ARRAY[location.osm_id] and members @> ARRAY['w'||location.osm_id]
@@ -1462,73 +1577,29 @@ BEGIN
                   END LOOP;
                 END IF;
               END LOOP;
-          END IF;    
-          
-          -- If the way contains an explicit name of a street copy it
-          -- Slightly less strict then above because data is copied from any object.
-          IF NEW.street IS NULL AND NEW.addr_place IS NULL THEN
---RAISE WARNING 'node in way that has a streetname %',location;
-            NEW.street := location.street;
-            NEW.addr_place := location.addr_place;
           END IF;
 
-          -- If this way is a street interpolation line then it is probably as good as we are going to get
-          IF NEW.parent_place_id IS NULL AND NEW.street IS NULL AND NEW.addr_place IS NULL AND location.class = 'place' and location.type='houses' THEN
-            -- Try and find a way that is close roughly parellel to this line
-            FOR relation IN SELECT place_id FROM placex
-              WHERE ST_DWithin(location.geometry, placex.geometry, 0.001) and placex.rank_search = 26
-                and st_geometrytype(location.geometry) in ('ST_LineString')
-              ORDER BY (ST_distance(placex.geometry, ST_LineInterpolatePoint(location.geometry,0))+
-                        ST_distance(placex.geometry, ST_LineInterpolatePoint(location.geometry,0.5))+
-                        ST_distance(placex.geometry, ST_LineInterpolatePoint(location.geometry,1))) ASC limit 1
-            LOOP
---RAISE WARNING 'using nearest street to address interpolation line,0.001 %',relation;
-              NEW.parent_place_id := relation.place_id;
-            END LOOP;
+          -- If the way mentions a street or place address, try that for parenting.
+          IF NEW.parent_place_id IS NULL AND location.street IS NOT NULL THEN
+            address_street_word_ids := get_name_ids(make_standard_name(location.street));
+            IF address_street_word_ids IS NOT NULL THEN
+              FOR linkedplacex IN SELECT place_id from getNearestNamedRoadFeature(NEW.partition, place_centroid, address_street_word_ids) LOOP
+                  NEW.parent_place_id := linkedplacex.place_id;
+              END LOOP;
+            END IF;
           END IF;
 
-        END LOOP;
-        END LOOP;
-                
-      END IF;
-
---RAISE WARNING 'x2';
-
-      IF NEW.parent_place_id IS NULL AND NEW.osm_type = 'W' THEN
-        -- Is this way part of a relation?
-        FOR relation IN select * from planet_osm_rels where parts @> ARRAY[NEW.osm_id] and members @> ARRAY['w'||NEW.osm_id]
-        LOOP
-          -- At the moment we only process one type of relation - associatedStreet
-          IF relation.tags @> ARRAY['associatedStreet'] AND array_upper(relation.members, 1) IS NOT NULL THEN
-            FOR i IN 1..array_upper(relation.members, 1) BY 2 LOOP
-              IF NEW.parent_place_id IS NULL AND relation.members[i+1] = 'street' THEN
---RAISE WARNING 'way that is in a relation %',relation;
-                SELECT place_id from placex where osm_type='W' and osm_id = substring(relation.members[i],2,200)::bigint
-                  and rank_search = 26 and name is not null INTO NEW.parent_place_id;
-              END IF;
-            END LOOP;
+          IF NEW.parent_place_id IS NULL AND location.addr_place IS NOT NULL THEN
+            address_street_word_ids := get_name_ids(make_standard_name(location.addr_place));
+            IF address_street_word_ids IS NOT NULL THEN
+              FOR linkedplacex IN SELECT place_id from getNearestNamedPlaceFeature(NEW.partition, place_centroid, address_street_word_ids) LOOP
+                NEW.parent_place_id := linkedplacex.place_id;
+              END LOOP;
+            END IF;
           END IF;
-        END LOOP;
-      END IF;
-      
---RAISE WARNING 'x3 %',NEW.parent_place_id;
 
-      IF NEW.parent_place_id IS NULL AND NEW.street IS NOT NULL THEN
-        address_street_word_ids := get_name_ids(make_standard_name(NEW.street));
-        IF address_street_word_ids IS NOT NULL THEN
-          FOR location IN SELECT * from getNearestNamedRoadFeature(NEW.partition, place_centroid, address_street_word_ids) LOOP
-              NEW.parent_place_id := location.place_id;
-          END LOOP;
-        END IF;
-      END IF;
+        END LOOP;
 
-      IF NEW.parent_place_id IS NULL AND NEW.addr_place IS NOT NULL THEN
-        address_street_word_ids := get_name_ids(make_standard_name(NEW.addr_place));
-        IF address_street_word_ids IS NOT NULL THEN
-          FOR location IN SELECT * from getNearestNamedPlaceFeature(NEW.partition, place_centroid, address_street_word_ids) LOOP
-            NEW.parent_place_id := location.place_id;
-          END LOOP;
-        END IF;
       END IF;
 
 --RAISE WARNING 'x4 %',NEW.parent_place_id;
@@ -2016,6 +2087,11 @@ BEGIN
   -- mark for delete
   UPDATE placex set indexed_status = 100 where osm_type = OLD.osm_type and osm_id = OLD.osm_id and class = OLD.class and type = OLD.type;
 
+  -- interpolations are special
+  IF OLD.class = 'place' and OLD.type = 'houses' THEN
+    UPDATE placex set indexed_status = 100 where osm_type = OLD.osm_type and osm_id = OLD.osm_id and class = 'place' and type = 'address';
+  END IF;
+
   RETURN OLD;
 
 END;
@@ -2295,6 +2371,11 @@ BEGIN
 
   END IF;
 
+  -- for interpolations invalidate all nodes on the line
+  IF NEW.class = 'place' and NEW.type = 'houses' and NEW.osm_type = 'W' THEN
+    update placex p set indexed_status = 2 from planet_osm_ways w where w.id = NEW.osm_id and p.osm_type = 'N' and p.osm_id = any(w.nodes);
+  END IF;
+
   -- Abort the add (we modified the existing place instead)
   RETURN NULL;
 
index 428eadc2d7c2c8d950532944fcd19b476afcad35..dcee40700036bcc07707a60e988f9e66fd1da444 100644 (file)
@@ -41,6 +41,8 @@ GRANT INSERT ON new_query_log TO "{www-user}" ;
 GRANT UPDATE ON new_query_log TO "{www-user}" ;
 GRANT SELECT ON new_query_log TO "{www-user}" ;
 
+GRANT SELECT ON TABLE country_name TO "{www-user}";
+GRANT SELECT ON TABLE gb_postcode TO "{www-user}";
 
 drop table IF EXISTS word;
 CREATE TABLE word (
index 0e4c269bf40083c540bfc894a251f065dfe99ba3..1b1663c3544c94b71102915d2ae9839a0db323e5 100644 (file)
@@ -15,13 +15,17 @@ Prerequisites
  * nose (https://nose.readthedocs.org)
  * pytidylib (http://countergram.com/open-source/pytidylib)
  * haversine (https://github.com/mapado/haversine)
+ * shapely (https://github.com/Toblerity/Shapely)
 
 Usage
 =====
 
  * get prerequisites
+     # on a fresh Ubuntu LTS 14.04 you'll also need these system-wide packages
+     [sudo] apt-get install python-dev python-pip python-Levenshtein tidy
 
-     [sudo] pip install lettuce nose pytidylib haversine psycopg2
+     [sudo] pip install lettuce nose pytidylib haversine psycopg2 shapely
 
  * run the tests
 
index ad4bdf851875c4b25b7d73d1d4c42502cbde8c41..d70bf18adc55715c2166d5b8512c74a74824daf6 100644 (file)
@@ -14,13 +14,9 @@ Feature: Import of address interpolations
           | id | nodes
           | 1  | 1,2
         When importing
-        Then node 1 expands to housenumbers
+        Then way 1 expands to housenumbers
           | housenumber | centroid
-          | 2           | 1,1
           | 4           | 1,1.0005
-        And node 2 expands to housenumbers
-          | housenumber | centroid
-          | 6           | 1,1.001
 
     Scenario: Simple even two point interpolation with zero beginning
         Given the place nodes
@@ -34,15 +30,11 @@ Feature: Import of address interpolations
           | id | nodes
           | 1  | 1,2
         When importing
-        Then node 1 expands to housenumbers
+        Then way 1 expands to housenumbers
           | housenumber | centroid
-          | 0           | 1,1
           | 2           | 1,1.00025
           | 4           | 1,1.0005
           | 6           | 1,1.00075
-        And node 2 expands to housenumbers
-          | housenumber | centroid
-          | 8           | 1,1.001
 
     Scenario: Backwards even two point interpolation
         Given the place nodes
@@ -56,13 +48,9 @@ Feature: Import of address interpolations
           | id | nodes
           | 1  | 2,1
         When importing
-        Then node 1 expands to housenumbers
-          | housenumber | centroid
-          | 2           | 1,1
-        And node 2 expands to housenumbers
+        Then way 1 expands to housenumbers
           | housenumber | centroid
           | 4           | 1,1.0005
-          | 6           | 1,1.001
 
     Scenario: Even two point interpolation with odd beginning
         Given the place nodes
@@ -76,14 +64,10 @@ Feature: Import of address interpolations
           | id | nodes
           | 1  | 1,2
         When importing
-        Then node 1 expands to housenumbers
+        Then way 1 expands to housenumbers
           | housenumber | centroid
-          | 11          | 1,1
           | 12          | 1,1.0002
           | 14          | 1,1.0006
-        And node 2 expands to housenumbers
-          | housenumber | centroid
-          | 16          | 1,1.001
 
     Scenario: Even two point interpolation with odd end
         Given the place nodes
@@ -97,14 +81,10 @@ Feature: Import of address interpolations
           | id | nodes
           | 1  | 1,2
         When importing
-        Then node 1 expands to housenumbers
+        Then way 1 expands to housenumbers
           | housenumber | centroid
-          | 10          | 1,1
           | 12          | 1,1.0004
           | 14          | 1,1.0008
-        And node 2 expands to housenumbers
-          | housenumber | centroid
-          | 15          | 1,1.001
 
     Scenario: Reverse even two point interpolation with odd beginning
         Given the place nodes
@@ -118,14 +98,10 @@ Feature: Import of address interpolations
           | id | nodes
           | 1  | 2,1
         When importing
-        Then node 1 expands to housenumbers
-          | housenumber | centroid
-          | 11          | 1,1
-        And node 2 expands to housenumbers
+        Then way 1 expands to housenumbers
           | housenumber | centroid
           | 12          | 1,1.0002
           | 14          | 1,1.0006
-          | 16          | 1,1.001
 
     Scenario: Reverse even two point interpolation with odd end
         Given the place nodes
@@ -139,14 +115,10 @@ Feature: Import of address interpolations
           | id | nodes
           | 1  | 2,1
         When importing
-        Then node 1 expands to housenumbers
-          | housenumber | centroid
-          | 10          | 1,1
-        And node 2 expands to housenumbers
+        Then way 1 expands to housenumbers
           | housenumber | centroid
           | 12          | 1,1.0004
           | 14          | 1,1.0008
-          | 15          | 1,1.001
 
       Scenario: Simple odd two point interpolation
         Given the place nodes
@@ -160,16 +132,12 @@ Feature: Import of address interpolations
           | id | nodes
           | 1  | 1,2
         When importing
-        Then node 1 expands to housenumbers
+        Then way 1 expands to housenumbers
           | housenumber | centroid
-          | 1           | 1,1
           | 3           | 1,1.0002
           | 5           | 1,1.0004
           | 7           | 1,1.0006
           | 9           | 1,1.0008
-        And node 2 expands to housenumbers
-          | housenumber | centroid
-          | 11           | 1,1.001
 
       Scenario: Odd two point interpolation with even beginning
         Given the place nodes
@@ -183,14 +151,10 @@ Feature: Import of address interpolations
           | id | nodes
           | 1  | 1,2
         When importing
-        Then node 1 expands to housenumbers
+        Then way 1 expands to housenumbers
           | housenumber | centroid
-          | 2           | 1,1
           | 3           | 1,1.0002
           | 5           | 1,1.0006
-        And node 2 expands to housenumbers
-          | housenumber | centroid
-          | 7           | 1,1.001
 
      Scenario: Simple all two point interpolation
         Given the place nodes
@@ -204,13 +168,9 @@ Feature: Import of address interpolations
           | id | nodes
           | 1  | 1,2
         When importing
-        Then node 1 expands to housenumbers
+        Then way 1 expands to housenumbers
           | housenumber | centroid
-          | 1           | 1,1
           | 2           | 1,1.0005
-        And node 2 expands to housenumbers
-          | housenumber | centroid
-          | 3           | 1,1.001
 
     Scenario: Simple numbered two point interpolation
         Given the place nodes
@@ -224,13 +184,9 @@ Feature: Import of address interpolations
           | id | nodes
           | 1  | 1,2
         When importing
-        Then node 1 expands to housenumbers
+        Then way 1 expands to housenumbers
           | housenumber | centroid
-          | 3           | 1,1
           | 6           | 1,1.0005
-        And node 2 expands to housenumbers
-          | housenumber | centroid
-          | 9           | 1,1.001
 
     Scenario: Even two point interpolation with intermediate empty node
         Given the place nodes
@@ -244,15 +200,11 @@ Feature: Import of address interpolations
           | id | nodes
           | 1  | 1,3,2
         When importing
-        Then node 1 expands to housenumbers
+        Then way 1 expands to housenumbers
           | housenumber | centroid
-          | 2           | 1,1
           | 4           | 1,1.0005
           | 6           | 1,1.001
           | 8           | 1.0005,1.001
-        And node 2 expands to housenumbers
-          | housenumber | centroid
-          | 10          | 1.001,1.001
 
 
     Scenario: Even two point interpolation with intermediate duplicated empty node
@@ -267,15 +219,11 @@ Feature: Import of address interpolations
           | id | nodes
           | 1  | 1,3,3,2
         When importing
-        Then node 1 expands to housenumbers
+        Then way 1 expands to housenumbers
           | housenumber | centroid
-          | 2           | 1,1
           | 4           | 1,1.0005
           | 6           | 1,1.001
           | 8           | 1.0005,1.001
-        And node 2 expands to housenumbers
-          | housenumber | centroid
-          | 10          | 1.001,1.001
 
     Scenario: Simple even three point interpolation
         Given the place nodes
@@ -290,16 +238,9 @@ Feature: Import of address interpolations
           | id | nodes
           | 1  | 1,3,2
         When importing
-        Then node 1 expands to housenumbers
-          | housenumber | centroid
-          | 2           | 1,1
-        Then node 3 expands to housenumbers
+        Then way 1 expands to housenumbers
           | housenumber | centroid
-          | 4           | 1,1.001
           | 6           | 1.0005,1.001
-        And node 2 expands to housenumbers
-          | housenumber | centroid
-          | 8           | 1.001,1.001
 
     Scenario: Even three point interpolation with odd center point
         Given the place nodes
@@ -314,17 +255,10 @@ Feature: Import of address interpolations
           | id | nodes
           | 1  | 1,3,2
         When importing
-        Then node 1 expands to housenumbers
+        Then way 1 expands to housenumbers
           | housenumber | centroid
-          | 2           | 1,1
           | 4           | 1,1.0004
           | 6           | 1,1.0008
-        Then node 3 expands to housenumbers
-          | housenumber | centroid
-          | 7           | 1,1.001
-        And node 2 expands to housenumbers
-          | housenumber | centroid
-          | 8           | 1.001,1.001
 
     Scenario: Interpolation on self-intersecting way
         Given the place nodes
@@ -339,17 +273,9 @@ Feature: Import of address interpolations
           | id | nodes
           | 1  | 1,2,3,2
         When importing
-        Then node 1 expands to housenumbers
+        Then way 1 expands to housenumbers
           | housenumber | centroid
-          | 2           | 0,0
           | 4           | 0,0.0005
-        Then node 2 expands to housenumbers
-          | housenumber | centroid
-          | 6           | 0,0.001
-          | 8           | 0,0.0015
-        Then node 3 expands to housenumbers
-          | housenumber | centroid
-          | 10          | 0,0.002
           | 8           | 0,0.0015
 
     Scenario: Interpolation on self-intersecting way II
@@ -364,12 +290,73 @@ Feature: Import of address interpolations
           | id | nodes
           | 1  | 1,2,3,2
         When importing
-        Then node 1 expands to housenumbers
+        Then way 1 expands to housenumbers
           | housenumber | centroid
-          | 2           | 0,0
           | 4           | 0,0.0005
-        Then node 2 expands to housenumbers
-          | housenumber | centroid
-          | 6           | 0,0.001
+
+
+     Scenario: addr:street on interpolation way
+       Given the scene parallel-road
+       And the place nodes
+          | osm_id | class | type  | housenumber | geometry
+          | 1      | place | house | 2           | :n-middle-w
+          | 2      | place | house | 6           | :n-middle-e
+          | 3      | place | house | 12          | :n-middle-w
+          | 4      | place | house | 16          | :n-middle-e
+       And the place ways
+          | osm_id | class   | type    | housenumber | street       | geometry
+          | 10     | place   | houses  | even        |              | :w-middle
+          | 11     | place   | houses  | even        | Cloud Street | :w-middle
+       And the place ways
+          | osm_id | class   | type     | name                    | geometry
+          | 2      | highway | tertiary | 'name' : 'Sun Way'      | :w-north
+          | 3      | highway | tertiary | 'name' : 'Cloud Street' | :w-south
+        And the ways
+          | id | nodes
+          | 10  | 1,100,101,102,2
+          | 11  | 3,200,201,202,4
+       When importing
+       Then table placex contains
+          | object | parent_place_id
+          | N1     | W2
+          | N2     | W2
+          | N3     | W3
+          | N4     | W3
+          | W10    | W2
+          | W11    | W3
+       And way 10 expands exactly to housenumbers 4
+       And way 11 expands exactly to housenumbers 14
+
+     Scenario: addr:street on housenumber way
+       Given the scene parallel-road
+       And the place nodes
+          | osm_id | class | type  | housenumber | street       | geometry
+          | 1      | place | house | 2           |              | :n-middle-w
+          | 2      | place | house | 6           |              | :n-middle-e
+          | 3      | place | house | 12          | Cloud Street | :n-middle-w
+          | 4      | place | house | 16          | Cloud Street | :n-middle-e
+       And the place ways
+          | osm_id | class   | type    | housenumber | geometry
+          | 10     | place   | houses  | even        | :w-middle
+          | 11     | place   | houses  | even        | :w-middle
+       And the place ways
+          | osm_id | class   | type     | name                    | geometry
+          | 2      | highway | tertiary | 'name' : 'Sun Way'      | :w-north
+          | 3      | highway | tertiary | 'name' : 'Cloud Street' | :w-south
+        And the ways
+          | id | nodes
+          | 10  | 1,100,101,102,2
+          | 11  | 3,200,201,202,4
+       When importing
+       Then table placex contains
+          | object | parent_place_id
+          | N1     | W2
+          | N2     | W2
+          | N3     | W3
+          | N4     | W3
+          | W10    | W2
+          | W11    | W3
+       And way 10 expands exactly to housenumbers 4
+       And way 11 expands exactly to housenumbers 14
 
 
index dd155c452466cd5d9f5f56281d75afe0a8ae5565..36754f844484ef843a36a5903effc2747aedf430 100644 (file)
@@ -389,7 +389,7 @@ Feature: Parenting of objects
          | N3     | W2              | None   | nowhere    | None
 
     ### Scenario 20
-    Scenario: POIs parent a road if and only if they are attached to it
+    Scenario: POIs parent a road if they are attached to it
         Given the scene points-on-roads
         And the named place nodes
          | osm_id | class   | type     | street   | geometry
@@ -408,8 +408,8 @@ Feature: Parenting of objects
         When importing
         Then table placex contains
          | object | parent_place_id
-         | N1     | W2
-         | N2     | W1
+         | N1     | W1
+         | N2     | W2
          | N3     | W1
          | N4     | W2
 
diff --git a/tests/features/db/update/interpolation.feature b/tests/features/db/update/interpolation.feature
new file mode 100644 (file)
index 0000000..bfc93b1
--- /dev/null
@@ -0,0 +1,167 @@
+@DB
+Feature: Update of address interpolations
+    Test the interpolated address are updated correctly
+
+    Scenario: addr:street added to interpolation
+      Given the scene parallel-road
+      And the place nodes
+          | osm_id | class | type  | housenumber | geometry
+          | 1      | place | house | 2           | :n-middle-w
+          | 2      | place | house | 6           | :n-middle-e
+      And the place ways
+          | osm_id | class   | type    | housenumber | geometry
+          | 10     | place   | houses  | even        | :w-middle
+      And the place ways
+          | osm_id | class   | type         | name                    | geometry
+          | 2      | highway | unclassified | 'name' : 'Sun Way'      | :w-north
+          | 3      | highway | unclassified | 'name' : 'Cloud Street' | :w-south
+      And the ways
+          | id  | nodes
+          | 10  | 1,100,101,102,2
+      When importing
+      Then table placex contains
+          | object | parent_place_id
+          | N1     | W2
+          | N2     | W2
+          | W10    | W2
+      And way 10 expands exactly to housenumbers 4
+      When updating place ways
+          | osm_id | class   | type    | housenumber | street       | geometry
+          | 10     | place   | houses  | even        | Cloud Street | :w-middle
+      Then way 10 expands exactly to housenumbers 4
+      And table placex contains
+          | object | parent_place_id
+          | N1     | W3
+          | N2     | W3
+          | W10    | W3
+
+    @Fail
+    Scenario: addr:street added to housenumbers
+      Given the scene parallel-road
+      And the place nodes
+          | osm_id | class | type  | housenumber | geometry
+          | 1      | place | house | 2           | :n-middle-w
+          | 2      | place | house | 6           | :n-middle-e
+      And the place ways
+          | osm_id | class   | type    | housenumber | geometry
+          | 10     | place   | houses  | even        | :w-middle
+      And the place ways
+          | osm_id | class   | type         | name                    | geometry
+          | 2      | highway | unclassified | 'name' : 'Sun Way'      | :w-north
+          | 3      | highway | unclassified | 'name' : 'Cloud Street' | :w-south
+      And the ways
+          | id  | nodes
+          | 10  | 1,100,101,102,2
+      When importing
+      Then table placex contains
+          | object | parent_place_id
+          | N1     | W2
+          | N2     | W2
+          | W10    | W2
+      And way 10 expands exactly to housenumbers 4
+      When updating place nodes
+          | osm_id | class | type  | street      | housenumber | geometry
+          | 1      | place | house | Cloud Street| 2           | :n-middle-w
+          | 2      | place | house | Cloud Street| 6           | :n-middle-e
+      Then way 10 expands exactly to housenumbers 4
+      And table placex contains
+          | object | parent_place_id
+          | N1     | W3
+          | N2     | W3
+          | W10    | W3
+
+
+    Scenario: interpolation tag removed
+      Given the scene parallel-road
+      And the place nodes
+          | osm_id | class | type  | housenumber | geometry
+          | 1      | place | house | 2           | :n-middle-w
+          | 2      | place | house | 6           | :n-middle-e
+      And the place ways
+          | osm_id | class   | type    | housenumber | geometry
+          | 10     | place   | houses  | even        | :w-middle
+      And the place ways
+          | osm_id | class   | type         | name                    | geometry
+          | 2      | highway | unclassified | 'name' : 'Sun Way'      | :w-north
+          | 3      | highway | unclassified | 'name' : 'Cloud Street' | :w-south
+      And the ways
+          | id  | nodes
+          | 10  | 1,100,101,102,2
+      When importing
+      Then table placex contains
+          | object | parent_place_id
+          | N1     | W2
+          | N2     | W2
+          | W10    | W2
+      And way 10 expands exactly to housenumbers 4
+      When marking for delete W10
+      Then way 10 expands to no housenumbers
+      And table placex contains
+          | object | parent_place_id
+          | N1     | W2
+          | N2     | W2
+
+
+    Scenario: referenced road added
+      Given the scene parallel-road
+      And the place nodes
+          | osm_id | class | type  | housenumber | geometry
+          | 1      | place | house | 2           | :n-middle-w
+          | 2      | place | house | 6           | :n-middle-e
+      And the place ways
+          | osm_id | class   | type    | housenumber | street      | geometry
+          | 10     | place   | houses  | even        | Cloud Street| :w-middle
+      And the place ways
+          | osm_id | class   | type         | name                    | geometry
+          | 2      | highway | unclassified | 'name' : 'Sun Way'      | :w-north
+      And the ways
+          | id  | nodes
+          | 10  | 1,100,101,102,2
+      When importing
+      Then table placex contains
+          | object | parent_place_id
+          | N1     | W2
+          | N2     | W2
+          | W10    | W2
+      And way 10 expands exactly to housenumbers 4
+      When updating place ways
+          | osm_id | class   | type         | name                    | geometry
+          | 3      | highway | unclassified | 'name' : 'Cloud Street' | :w-south
+      Then way 10 expands exactly to housenumbers 4
+      And table placex contains
+          | object | parent_place_id
+          | N1     | W3
+          | N2     | W3
+          | W10    | W3
+
+
+    Scenario: referenced road deleted
+      Given the scene parallel-road
+      And the place nodes
+          | osm_id | class | type  | housenumber | geometry
+          | 1      | place | house | 2           | :n-middle-w
+          | 2      | place | house | 6           | :n-middle-e
+      And the place ways
+          | osm_id | class   | type    | housenumber | street      | geometry
+          | 10     | place   | houses  | even        | Cloud Street| :w-middle
+      And the place ways
+          | osm_id | class   | type         | name                    | geometry
+          | 2      | highway | unclassified | 'name' : 'Sun Way'      | :w-north
+          | 3      | highway | unclassified | 'name' : 'Cloud Street' | :w-south
+      And the ways
+          | id  | nodes
+          | 10  | 1,100,101,102,2
+      When importing
+      Then table placex contains
+          | object | parent_place_id
+          | N1     | W3
+          | N2     | W3
+          | W10    | W3
+      And way 10 expands exactly to housenumbers 4
+      When marking for delete W3
+      Then way 10 expands exactly to housenumbers 4
+      And table placex contains
+          | object | parent_place_id
+          | N1     | W2
+          | N2     | W2
+          | W10    | W2
diff --git a/tests/scenes/data/parallel-road.wkt b/tests/scenes/data/parallel-road.wkt
new file mode 100644 (file)
index 0000000..355af30
--- /dev/null
@@ -0,0 +1,5 @@
+n-middle-w |  POINT(1.0065316 2.0003381)
+n-middle-e |  POINT(1.007236 2.0003408)
+w-south |  LINESTRING(1.0065324 2.0001892,1.006676 2.0002786,1.0068195 2.0002786,1.0069171 2.0002515,1.0070417 2.0001892,1.0072422 2.000173)
+w-middle |  LINESTRING(1.0065316 2.0003381,1.006686 2.0004248,1.0069 2.0004167,1.007236 2.0003408)
+w-north |  LINESTRING(1.0065397 2.000418,1.0066833 2.0005074,1.0068269 2.0005074,1.0069244 2.0004803,1.007049 2.000418,1.0072495 2.0004018)
index b642fa626a9a42e77ec73e60db722d933d14d954..ed7cd62a683880ec3e03b7bbd2b05366cb5faa6c 100644 (file)
 <?xml version='1.0' encoding='UTF-8'?>
 <osm version='0.6' upload='false' generator='JOSM'>
-  <node id='-204' action='modify' visible='true' lat='2.000651586300547' lon='1.005746444902722'>
+  <node id='-197' action='modify' visible='true' lat='2.0006515863' lon='1.0057464449'>
     <tag k='name' v='split-road' />
   </node>
-  <node id='-189' action='modify' visible='true' lat='2.0005350827634585' lon='1.0057490943252971' />
-  <node id='-187' action='modify' visible='true' lat='2.0005430261867043' lon='1.0058974619895207' />
-  <node id='-185' action='modify' visible='true' lat='2.0005430261867043' lon='1.0060511284988949' />
-  <node id='-183' action='modify' visible='true' lat='2.0005324349557014' lon='1.0061306111761574' />
-  <node id='-174' action='modify' visible='true' lat='2.0005244915324045' lon='1.00551064629351' />
-  <node id='-172' action='modify' visible='true' lat='2.0005668564562127' lon='1.0056086749288005' />
-  <node id='-170' action='modify' visible='true' lat='2.000561560840796' lon='1.0056855081834875' />
-  <node id='-168' action='modify' visible='true' lat='2.0005006612622807' lon='1.0057358472124205' />
-  <node id='-166' action='modify' visible='true' lat='2.000505956877894' lon='1.0059107091023978' />
-  <node id='-164' action='modify' visible='true' lat='2.0005112524934896' lon='1.0060537779214704' />
-  <node id='-162' action='modify' visible='true' lat='2.0004953656466506' lon='1.006135910021308' />
-  <node id='-160' action='modify' visible='true' lat='2.000513900301281' lon='1.0062842776855314' />
-  <node id='-158' action='modify' visible='true' lat='2.000471535376104' lon='1.0063717086305204' />
-  <node id='-156' action='modify' visible='true' lat='2.000296780048186' lon='1.0063584615176433' />
-  <node id='-154' action='modify' visible='true' lat='2.000262358542008' lon='1.006281628262956' />
-  <node id='-152' action='modify' visible='true' lat='2.000339144977876' lon='1.0061994961631182' />
-  <node id='-150' action='modify' visible='true' lat='2.0003576796342712' lon='1.0061041169504032' />
-  <node id='-148' action='modify' visible='true' lat='2.0003497362101275' lon='1.0060034388925374' />
-  <node id='-146' action='modify' visible='true' lat='2.000325905937466' lon='1.0058868642992191' />
-  <node id='-144' action='modify' visible='true' lat='2.000280893199271' lon='1.0057941345090795' />
-  <node id='-142' action='modify' visible='true' lat='2.0002782453911037' lon='1.0056351691545544' />
-  <node id='-141' action='modify' visible='true' lat='2.0003603274423103' lon='1.005470904954879' />
-  <node id='-139' action='modify' visible='true' lat='2.0007265421773432' lon='1.0047054313390744'>
+  <node id='-195' action='modify' visible='true' lat='2.00053508276' lon='1.00574909433' />
+  <node id='-193' action='modify' visible='true' lat='2.00054302619' lon='1.00589746199' />
+  <node id='-191' action='modify' visible='true' lat='2.00054302619' lon='1.0060511285' />
+  <node id='-189' action='modify' visible='true' lat='2.00053243496' lon='1.00613061118' />
+  <node id='-187' action='modify' visible='true' lat='2.00052449153' lon='1.00551064629' />
+  <node id='-185' action='modify' visible='true' lat='2.00056685646' lon='1.00560867493' />
+  <node id='-183' action='modify' visible='true' lat='2.00056156084' lon='1.00568550818' />
+  <node id='-181' action='modify' visible='true' lat='2.00050066126' lon='1.00573584721' />
+  <node id='-179' action='modify' visible='true' lat='2.00050595688' lon='1.0059107091' />
+  <node id='-177' action='modify' visible='true' lat='2.00051125249' lon='1.00605377792' />
+  <node id='-175' action='modify' visible='true' lat='2.00049536565' lon='1.00613591002' />
+  <node id='-173' action='modify' visible='true' lat='2.0005139003' lon='1.00628427769' />
+  <node id='-171' action='modify' visible='true' lat='2.00047153538' lon='1.00637170863' />
+  <node id='-169' action='modify' visible='true' lat='2.00029678005' lon='1.00635846152' />
+  <node id='-167' action='modify' visible='true' lat='2.00026235854' lon='1.00628162826' />
+  <node id='-165' action='modify' visible='true' lat='2.00033914498' lon='1.00619949616' />
+  <node id='-163' action='modify' visible='true' lat='2.00035767963' lon='1.00610411695' />
+  <node id='-161' action='modify' visible='true' lat='2.00034973621' lon='1.00600343889' />
+  <node id='-159' action='modify' visible='true' lat='2.00032590594' lon='1.0058868643' />
+  <node id='-157' action='modify' visible='true' lat='2.0002808932' lon='1.00579413451' />
+  <node id='-155' action='modify' visible='true' lat='2.00027824539' lon='1.00563516915' />
+  <node id='-153' action='modify' visible='true' lat='2.00036032744' lon='1.00547090495' />
+  <node id='-151' action='modify' visible='true' lat='2.00072654218' lon='1.00470543134'>
     <tag k='name' v='points-on-road' />
   </node>
-  <node id='-112' action='modify' visible='true' lat='2.0005155253763816' lon='1.0049220138358423' />
-  <node id='-110' action='modify' visible='true' lat='2.0005155253763816' lon='1.0049220138358423'>
+  <node id='-149' action='modify' visible='true' lat='2.00051552538' lon='1.00492201384' />
+  <node id='-147' action='modify' visible='true' lat='2.00051552538' lon='1.00492201384'>
     <tag k='test:id' v='n-N-unglued' />
     <tag k='test:section' v='points-on-roads' />
   </node>
-  <node id='-108' action='modify' visible='true' lat='2.0002948553437463' lon='1.0046258759080025'>
+  <node id='-145' action='modify' visible='true' lat='2.00029485534' lon='1.00462587591'>
     <tag k='test:id' v='n-S-unglued' />
     <tag k='test:section' v='points-on-roads' />
   </node>
-  <node id='-106' action='modify' visible='true' lat='2.0002948553437463' lon='1.0046258759080025' />
-  <node id='-104' action='modify' visible='true' lat='2.0006117740392657' lon='1.0050661381425037'>
+  <node id='-143' action='modify' visible='true' lat='2.00029485534' lon='1.00462587591' />
+  <node id='-141' action='modify' visible='true' lat='2.00061177404' lon='1.00506613814'>
     <tag k='test:id' v='n-NE' />
     <tag k='test:section' v='points-on-roads' />
   </node>
-  <node id='-102' action='modify' visible='true' lat='2.000334854794143' lon='1.0051338707939657'>
+  <node id='-139' action='modify' visible='true' lat='2.00033485479' lon='1.00513387079'>
     <tag k='test:id' v='n-SE' />
     <tag k='test:section' v='points-on-roads' />
   </node>
-  <node id='-100' action='modify' visible='true' lat='2.0006240815601832' lon='1.0053155174501582' />
-  <node id='-98' action='modify' visible='true' lat='2.0004086999307416' lon='1.0047582624540412'>
+  <node id='-137' action='modify' visible='true' lat='2.00062408156' lon='1.00531551745' />
+  <node id='-135' action='modify' visible='true' lat='2.00040869993' lon='1.00475826245'>
     <tag k='test:id' v='n-NW' />
     <tag k='test:section' v='points-on-roads' />
   </node>
-  <node id='-96' action='modify' visible='true' lat='2.0003840848855767' lon='1.0046258759080025' />
-  <node id='-94' action='modify' visible='true' lat='2.0004302380949586' lon='1.004499646875733' />
-  <node id='-92' action='modify' visible='true' lat='2.0003687004821606' lon='1.0053278324776966' />
-  <node id='-90' action='modify' visible='true' lat='2.0002640865351053' lon='1.0049368303533495' />
-  <node id='-88' action='modify' visible='true' lat='2.000291778462916' lon='1.004825995105503' />
-  <node id='-86' action='modify' visible='true' lat='2.0003563929593238' lon='1.004727474885195'>
+  <node id='-133' action='modify' visible='true' lat='2.00038408489' lon='1.00462587591' />
+  <node id='-131' action='modify' visible='true' lat='2.00043023809' lon='1.00449964688' />
+  <node id='-129' action='modify' visible='true' lat='2.00036870048' lon='1.00532783248' />
+  <node id='-127' action='modify' visible='true' lat='2.00026408654' lon='1.00493683035' />
+  <node id='-125' action='modify' visible='true' lat='2.00029177846' lon='1.00482599511' />
+  <node id='-123' action='modify' visible='true' lat='2.00035639296' lon='1.00472747489'>
     <tag k='test:id' v='n-SW' />
     <tag k='test:section' v='points-on-roads' />
   </node>
-  <node id='-84' action='modify' visible='true' lat='2.0002240870829975' lon='1.00452427693081' />
-  <node id='-82' action='modify' visible='true' lat='2.000715618411992' lon='1.0018322734314236'>
+  <node id='-121' action='modify' visible='true' lat='2.00022408708' lon='1.00452427693' />
+  <node id='-119' action='modify' visible='true' lat='2.00071561841' lon='1.00183227343'>
     <tag k='name' v='road-with-alley' />
   </node>
-  <node id='-80' action='modify' visible='true' lat='2.0007286441385155' lon='1.0004669962874884'>
+  <node id='-117' action='modify' visible='true' lat='2.00072864414' lon='1.00046699629'>
     <tag k='name' v='roads-with-pois' />
   </node>
-  <node id='-78' action='modify' visible='true' lat='2.000354154459697' lon='1.002448114434296'>
+  <node id='-115' action='modify' visible='true' lat='2.00035415446' lon='1.00244811443'>
     <tag k='test:id' v='n-main-east' />
     <tag k='test:section' v='road-with-alley' />
   </node>
-  <node id='-76' action='modify' visible='true' lat='2.000266230783582' lon='1.0015520494830263'>
+  <node id='-113' action='modify' visible='true' lat='2.00026623078' lon='1.00155204948'>
     <tag k='test:id' v='n-main-west' />
     <tag k='test:section' v='road-with-alley' />
   </node>
-  <node id='-74' action='modify' visible='true' lat='2.000546283957771' lon='1.0019235091355527'>
+  <node id='-111' action='modify' visible='true' lat='2.00054628396' lon='1.00192350914'>
     <tag k='test:id' v='n-alley' />
     <tag k='test:section' v='road-with-alley' />
   </node>
-  <node id='-72' action='modify' visible='true' lat='2.000354154459697' lon='1.0019235091355527'>
+  <node id='-109' action='modify' visible='true' lat='2.00035415446' lon='1.00192350914'>
     <tag k='test:id' v='n-corner' />
     <tag k='test:section' v='road-with-alley' />
   </node>
-  <node id='-70' action='modify' visible='true' lat='2.0005755918453296' lon='1.0019593517336036' />
-  <node id='-68' action='modify' visible='true' lat='2.000298795108618' lon='1.0026077769165225' />
-  <node id='-66' action='modify' visible='true' lat='2.000311820838452' lon='1.0023699124021854' />
-  <node id='-64' action='modify' visible='true' lat='2.0003150772708946' lon='1.0021255310518389' />
-  <node id='-62' action='modify' visible='true' lat='2.0003085644060037' lon='1.0019593517336036' />
-  <node id='-60' action='modify' visible='true' lat='2.000305307973548' lon='1.0016758693672019' />
-  <node id='-58' action='modify' visible='true' lat='2.000311820838452' lon='1.0013435107307307' />
-  <node id='-56' action='modify' visible='true' lat='2.0004054696330322' lon='1.0001173628501097'>
+  <node id='-107' action='modify' visible='true' lat='2.00057559185' lon='1.00195935173' />
+  <node id='-105' action='modify' visible='true' lat='2.00029879511' lon='1.00260777692' />
+  <node id='-103' action='modify' visible='true' lat='2.00031182084' lon='1.0023699124' />
+  <node id='-101' action='modify' visible='true' lat='2.00031507727' lon='1.00212553105' />
+  <node id='-99' action='modify' visible='true' lat='2.00030856441' lon='1.00195935173' />
+  <node id='-97' action='modify' visible='true' lat='2.00030530797' lon='1.00167586937' />
+  <node id='-95' action='modify' visible='true' lat='2.00031182084' lon='1.00134351073' />
+  <node id='-93' action='modify' visible='true' lat='2.00040546963' lon='1.00011736285'>
     <tag k='test:section' v='roads-with-pois' />
   </node>
-  <node id='-54' action='modify' visible='true' lat='2.000397598928471' lon='1.0004297578433892'>
+  <node id='-91' action='modify' visible='true' lat='2.00039759893' lon='1.00042975784'>
     <tag k='test:section' v='roads-with-pois' />
   </node>
-  <node id='-52' action='modify' visible='true' lat='2.0004579409958114' lon='1.0006607726283354'>
+  <node id='-89' action='modify' visible='true' lat='2.000457941' lon='1.00066077263'>
     <tag k='test:section' v='roads-with-pois' />
   </node>
-  <node id='-50' action='modify' visible='true' lat='2.0005418951727663' lon='1.0010624233339804'>
+  <node id='-87' action='modify' visible='true' lat='2.00054189517' lon='1.00106242333'>
     <tag k='test:section' v='roads-with-pois' />
   </node>
-  <node id='-48' action='modify' visible='true' lat='2.000190337028091' lon='1.0001383641941959'>
+  <node id='-85' action='modify' visible='true' lat='2.00019033703' lon='1.00013836419'>
     <tag k='test:section' v='roads-with-pois' />
   </node>
-  <node id='-46' action='modify' visible='true' lat='2.000198207733647' lon='1.000721151492583'>
+  <node id='-83' action='modify' visible='true' lat='2.00019820773' lon='1.00072115149'>
     <tag k='test:section' v='roads-with-pois' />
   </node>
-  <node id='-44' action='modify' visible='true' lat='2.000219196281612' lon='1.0010676736700022'>
+  <node id='-81' action='modify' visible='true' lat='2.00021919628' lon='1.00106767367'>
     <tag k='test:section' v='roads-with-pois' />
   </node>
-  <node id='-42' action='modify' visible='true' lat='2.000339880427198' lon='1.000390380323228'>
+  <node id='-79' action='modify' visible='true' lat='2.00033988043' lon='1.00039038032'>
     <tag k='test:id' v='p-N2' />
     <tag k='test:section' v='roads-with-pois' />
   </node>
-  <node id='-40' action='modify' visible='true' lat='2.000292656197374' lon='1.0008104072049482'>
+  <node id='-77' action='modify' visible='true' lat='2.0002926562' lon='1.0008104072'>
     <tag k='test:id' v='p-S1' />
     <tag k='test:section' v='roads-with-pois' />
   </node>
-  <node id='-38' action='modify' visible='true' lat='2.0005287773329004' lon='1.0005321393958087'>
+  <node id='-75' action='modify' visible='true' lat='2.00052877733' lon='1.0005321394'>
     <tag k='test:id' v='p-N1' />
     <tag k='test:section' v='roads-with-pois' />
   </node>
-  <node id='-36' action='modify' visible='true' lat='2.000106382833144' lon='1.0006397712842492'>
+  <node id='-73' action='modify' visible='true' lat='2.00010638283' lon='1.00063977128'>
     <tag k='test:id' v='p-S2' />
     <tag k='test:section' v='roads-with-pois' />
   </node>
-  <node id='-34' action='modify' visible='true' lat='2.0007211692424525' lon='1.0035828658185688'>
+  <node id='-71' action='modify' visible='true' lat='2.00072116924' lon='1.00358286582'>
     <tag k='name' v='building-on-street-corner' />
   </node>
-  <node id='-32' action='modify' visible='true' lat='2.000231635335803' lon='1.0031759205058477' />
-  <node id='-30' action='modify' visible='true' lat='2.000221087674047' lon='1.0040360790429201' />
-  <node id='-28' action='modify' visible='true' lat='2.0002263615049336' lon='1.0042735461237067' />
-  <node id='-26' action='modify' visible='true' lat='2.000105063390253' lon='1.0040413560891597' />
-  <node id='-24' action='modify' visible='true' lat='2.0006377202618473' lon='1.0040363991494512' />
-  <node id='-22' action='modify' visible='true' lat='2.0004388569487612' lon='1.0039042871025967' />
-  <node id='-20' action='modify' visible='true' lat='2.0004385547672516' lon='1.0040022536164286' />
-  <node id='-18' action='modify' visible='true' lat='2.0002343878022306' lon='1.0040016230872442' />
-  <node id='-16' action='modify' visible='true' lat='2.000234689983778' lon='1.0039036565734125' />
-  <node id='-14' action='modify' visible='true' lat='2.0003240388594246' lon='1.0040018999567464'>
+  <node id='-69' action='modify' visible='true' lat='2.00023163534' lon='1.00317592051' />
+  <node id='-67' action='modify' visible='true' lat='2.00022108767' lon='1.00403607904' />
+  <node id='-65' action='modify' visible='true' lat='2.0002263615' lon='1.00427354612' />
+  <node id='-63' action='modify' visible='true' lat='2.00010506339' lon='1.00404135609' />
+  <node id='-61' action='modify' visible='true' lat='2.00063772026' lon='1.00403639915' />
+  <node id='-59' action='modify' visible='true' lat='2.00043885695' lon='1.0039042871' />
+  <node id='-57' action='modify' visible='true' lat='2.00043855477' lon='1.00400225362' />
+  <node id='-55' action='modify' visible='true' lat='2.0002343878' lon='1.00400162309' />
+  <node id='-53' action='modify' visible='true' lat='2.00023468998' lon='1.00390365657' />
+  <node id='-51' action='modify' visible='true' lat='2.00032403886' lon='1.00400189996'>
     <tag k='test:id' v='n-edge-NS' />
     <tag k='test:section' v='building-on-street-corner' />
   </node>
-  <node id='-12' action='modify' visible='true' lat='2.000354798021768' lon='1.0039384858598128'>
+  <node id='-49' action='modify' visible='true' lat='2.00035479802' lon='1.00393848586'>
     <tag k='test:id' v='n-inner' />
     <tag k='test:section' v='building-on-street-corner' />
   </node>
-  <node id='-10' action='modify' visible='true' lat='2.0004676051467527' lon='1.0039478144477645'>
+  <node id='-47' action='modify' visible='true' lat='2.00046760515' lon='1.00394781445'>
     <tag k='test:id' v='n-outer' />
     <tag k='test:section' v='building-on-street-corner' />
   </node>
-  <node id='-8' action='modify' visible='true' lat='2.000234516370527' lon='1.0039599415620857'>
+  <node id='-45' action='modify' visible='true' lat='2.00023451637' lon='1.00395994156'>
     <tag k='test:id' v='n-edge-WE' />
     <tag k='test:section' v='building-on-street-corner' />
   </node>
+  <node id='-43' action='modify' visible='true' lat='2.0001892102' lon='1.00653236169' />
+  <node id='-41' action='modify' visible='true' lat='2.00027856164' lon='1.00667595302' />
+  <node id='-39' action='modify' visible='true' lat='2.00027856164' lon='1.00681954435' />
+  <node id='-37' action='modify' visible='true' lat='2.00025148545' lon='1.00691707809' />
+  <node id='-35' action='modify' visible='true' lat='2.0001892102' lon='1.00704170453' />
+  <node id='-33' action='modify' visible='true' lat='2.00017296448' lon='1.00724219054' />
+  <node id='-31' action='modify' visible='true' lat='2.00062243814' lon='1.00685396461'>
+    <tag k='name' v='parallel-road' />
+  </node>
+  <node id='-29' action='modify' visible='true' lat='2.00033813812' lon='1.00653156143'>
+    <tag k='test:id' v='n-middle-w' />
+    <tag k='test:section' v='parallel-road' />
+  </node>
+  <node id='-27' action='modify' visible='true' lat='2.00042478194' lon='1.00668598984' />
+  <node id='-25' action='modify' visible='true' lat='2.00041665908' lon='1.00690002221' />
+  <node id='-23' action='modify' visible='true' lat='2.00034084574' lon='1.00723597174'>
+    <tag k='test:id' v='n-middle-e' />
+    <tag k='test:section' v='parallel-road' />
+  </node>
+  <node id='-21' action='modify' visible='true' lat='2.00041801289' lon='1.00653968924' />
+  <node id='-19' action='modify' visible='true' lat='2.00050736432' lon='1.00668328057' />
+  <node id='-17' action='modify' visible='true' lat='2.00050736432' lon='1.00682687191' />
+  <node id='-15' action='modify' visible='true' lat='2.00048028813' lon='1.00692440564' />
+  <node id='-13' action='modify' visible='true' lat='2.00041801289' lon='1.00704903208' />
+  <node id='-11' action='modify' visible='true' lat='2.00040176717' lon='1.00724951809' />
   <node id='100000' timestamp='2014-01-01T00:00:00Z' uid='1' user='test' visible='true' version='1' changeset='1' lat='2.0' lon='1.0' />
   <node id='100001' timestamp='2014-01-01T00:00:00Z' uid='1' user='test' visible='true' version='1' changeset='1' lat='3.0' lon='1.0' />
   <node id='100002' timestamp='2014-01-01T00:00:00Z' uid='1' user='test' visible='true' version='1' changeset='1' lat='3.0' lon='2.0' />
   <node id='100003' timestamp='2014-01-01T00:00:00Z' uid='1' user='test' visible='true' version='1' changeset='1' lat='2.0' lon='2.0' />
-  <way id='-195' action='modify' visible='true'>
-    <nd ref='-170' />
-    <nd ref='-172' />
-    <nd ref='-174' />
+  <way id='-237' action='modify' visible='true'>
+    <nd ref='-183' />
+    <nd ref='-185' />
+    <nd ref='-187' />
     <tag k='test:id' v='w-5' />
     <tag k='test:section' v='split-road' />
   </way>
-  <way id='-194' action='modify' visible='true'>
-    <nd ref='-160' />
-    <nd ref='-162' />
-    <nd ref='-164' />
-    <nd ref='-166' />
-    <nd ref='-168' />
-    <nd ref='-170' />
+  <way id='-235' action='modify' visible='true'>
+    <nd ref='-173' />
+    <nd ref='-175' />
+    <nd ref='-177' />
+    <nd ref='-179' />
+    <nd ref='-181' />
+    <nd ref='-183' />
     <tag k='test:id' v='w-4a' />
     <tag k='test:section' v='split-road' />
   </way>
-  <way id='-193' action='modify' visible='true'>
-    <nd ref='-152' />
-    <nd ref='-154' />
-    <nd ref='-156' />
-    <nd ref='-158' />
-    <nd ref='-160' />
+  <way id='-233' action='modify' visible='true'>
+    <nd ref='-165' />
+    <nd ref='-167' />
+    <nd ref='-169' />
+    <nd ref='-171' />
+    <nd ref='-173' />
     <tag k='test:id' v='w-3' />
     <tag k='test:section' v='split-road' />
   </way>
-  <way id='-192' action='modify' visible='true'>
-    <nd ref='-144' />
-    <nd ref='-146' />
-    <nd ref='-148' />
-    <nd ref='-150' />
-    <nd ref='-152' />
+  <way id='-231' action='modify' visible='true'>
+    <nd ref='-157' />
+    <nd ref='-159' />
+    <nd ref='-161' />
+    <nd ref='-163' />
+    <nd ref='-165' />
     <tag k='test:id' v='w-2' />
     <tag k='test:section' v='split-road' />
   </way>
-  <way id='-184' action='modify' visible='true'>
-    <nd ref='-160' />
-    <nd ref='-183' />
-    <nd ref='-185' />
-    <nd ref='-187' />
+  <way id='-229' action='modify' visible='true'>
+    <nd ref='-173' />
     <nd ref='-189' />
-    <nd ref='-170' />
+    <nd ref='-191' />
+    <nd ref='-193' />
+    <nd ref='-195' />
+    <nd ref='-183' />
     <tag k='test:id' v='w-4b' />
     <tag k='test:section' v='split-road' />
   </way>
-  <way id='-143' action='modify' visible='true'>
-    <nd ref='-141' />
-    <nd ref='-142' />
-    <nd ref='-144' />
+  <way id='-227' action='modify' visible='true'>
+    <nd ref='-153' />
+    <nd ref='-155' />
+    <nd ref='-157' />
     <tag k='test:id' v='w-1' />
     <tag k='test:section' v='split-road' />
   </way>
-  <way id='-134' action='modify' visible='true'>
-    <nd ref='-94' />
-    <nd ref='-96' />
-    <nd ref='-98' />
-    <nd ref='-112' />
-    <nd ref='-104' />
-    <nd ref='-100' />
+  <way id='-225' action='modify' visible='true'>
+    <nd ref='-131' />
+    <nd ref='-133' />
+    <nd ref='-135' />
+    <nd ref='-149' />
+    <nd ref='-141' />
+    <nd ref='-137' />
     <tag k='test:id' v='w-north' />
     <tag k='test:section' v='points-on-roads' />
   </way>
-  <way id='-132' action='modify' visible='true'>
-    <nd ref='-84' />
-    <nd ref='-106' />
-    <nd ref='-86' />
-    <nd ref='-88' />
-    <nd ref='-90' />
-    <nd ref='-102' />
-    <nd ref='-92' />
+  <way id='-223' action='modify' visible='true'>
+    <nd ref='-121' />
+    <nd ref='-143' />
+    <nd ref='-123' />
+    <nd ref='-125' />
+    <nd ref='-127' />
+    <nd ref='-139' />
+    <nd ref='-129' />
     <tag k='test:id' v='w-south' />
     <tag k='test:section' v='points-on-roads' />
   </way>
-  <way id='-130' action='modify' visible='true'>
-    <nd ref='-62' />
-    <nd ref='-70' />
+  <way id='-221' action='modify' visible='true'>
+    <nd ref='-99' />
+    <nd ref='-107' />
     <tag k='test:id' v='w-alley' />
     <tag k='test:section' v='road-with-alley' />
   </way>
-  <way id='-128' action='modify' visible='true'>
-    <nd ref='-58' />
-    <nd ref='-60' />
-    <nd ref='-62' />
-    <nd ref='-64' />
-    <nd ref='-66' />
-    <nd ref='-68' />
+  <way id='-219' action='modify' visible='true'>
+    <nd ref='-95' />
+    <nd ref='-97' />
+    <nd ref='-99' />
+    <nd ref='-101' />
+    <nd ref='-103' />
+    <nd ref='-105' />
     <tag k='test:id' v='w-main' />
     <tag k='test:section' v='road-with-alley' />
   </way>
-  <way id='-126' action='modify' visible='true'>
-    <nd ref='-56' />
-    <nd ref='-54' />
-    <nd ref='-52' />
-    <nd ref='-50' />
+  <way id='-217' action='modify' visible='true'>
+    <nd ref='-93' />
+    <nd ref='-91' />
+    <nd ref='-89' />
+    <nd ref='-87' />
     <tag k='test:id' v='w-north' />
     <tag k='test:section' v='roads-with-pois' />
   </way>
-  <way id='-124' action='modify' visible='true'>
-    <nd ref='-48' />
-    <nd ref='-46' />
-    <nd ref='-44' />
+  <way id='-215' action='modify' visible='true'>
+    <nd ref='-85' />
+    <nd ref='-83' />
+    <nd ref='-81' />
     <tag k='test:id' v='w-south' />
     <tag k='test:section' v='roads-with-pois' />
   </way>
-  <way id='-122' action='modify' visible='true'>
-    <nd ref='-32' />
-    <nd ref='-30' />
-    <nd ref='-28' />
+  <way id='-213' action='modify' visible='true'>
+    <nd ref='-69' />
+    <nd ref='-67' />
+    <nd ref='-65' />
     <tag k='test:id' v='w-WE' />
     <tag k='test:section' v='building-on-street-corner' />
   </way>
-  <way id='-120' action='modify' visible='true'>
-    <nd ref='-26' />
-    <nd ref='-30' />
-    <nd ref='-24' />
+  <way id='-211' action='modify' visible='true'>
+    <nd ref='-63' />
+    <nd ref='-67' />
+    <nd ref='-61' />
     <tag k='test:id' v='w-NS' />
     <tag k='test:section' v='building-on-street-corner' />
   </way>
-  <way id='-118' action='modify' visible='true'>
-    <nd ref='-22' />
-    <nd ref='-20' />
-    <nd ref='-14' />
-    <nd ref='-18' />
-    <nd ref='-8' />
-    <nd ref='-16' />
-    <nd ref='-22' />
+  <way id='-209' action='modify' visible='true'>
+    <nd ref='-59' />
+    <nd ref='-57' />
+    <nd ref='-51' />
+    <nd ref='-55' />
+    <nd ref='-45' />
+    <nd ref='-53' />
+    <nd ref='-59' />
     <tag k='area' v='yes' />
     <tag k='test:id' v='w-building' />
     <tag k='test:section' v='building-on-street-corner' />
   </way>
+  <way id='-207' action='modify' visible='true'>
+    <nd ref='-43' />
+    <nd ref='-41' />
+    <nd ref='-39' />
+    <nd ref='-37' />
+    <nd ref='-35' />
+    <nd ref='-33' />
+    <tag k='test:id' v='w-south' />
+    <tag k='test:section' v='parallel-road' />
+  </way>
+  <way id='-205' action='modify' visible='true'>
+    <nd ref='-29' />
+    <nd ref='-27' />
+    <nd ref='-25' />
+    <nd ref='-23' />
+    <tag k='test:id' v='w-middle' />
+    <tag k='test:section' v='parallel-road' />
+  </way>
+  <way id='-203' action='modify' visible='true'>
+    <nd ref='-21' />
+    <nd ref='-19' />
+    <nd ref='-17' />
+    <nd ref='-15' />
+    <nd ref='-13' />
+    <nd ref='-11' />
+    <tag k='test:id' v='w-north' />
+    <tag k='test:section' v='parallel-road' />
+  </way>
   <way id='100000' timestamp='2014-01-01T00:00:00Z' uid='1' user='test' visible='true' version='1' changeset='1'>
     <nd ref='100000' />
     <nd ref='100001' />
index 2566418e39fdcd0c0fc4b8880dfe5a568bd90855..c3ac9445fe55738c8e87f9f78dc855c91c0c2ba8 100644 (file)
@@ -119,10 +119,10 @@ def check_search_name_content(step):
                 else:
                     raise Exception("Cannot handle field %s in search_name table" % (k, ))
 
-@step(u'node (\d+) expands to housenumbers')
+@step(u'way (\d+) expands to housenumbers')
 def check_interpolated_housenumbers(step, nodeid):
     """Check that the exact set of housenumbers has been entered in
-       placex for the given source node. Expected are tow columns:
+       placex for the given source node. Expected are two columns:
        housenumber and centroid
     """
     numbers = {}
@@ -132,7 +132,8 @@ def check_interpolated_housenumbers(step, nodeid):
     cur = world.conn.cursor(cursor_factory=psycopg2.extras.DictCursor)
     cur.execute("""SELECT DISTINCT housenumber,
                           ST_X(centroid) as clat, ST_Y(centroid) as clon
-                   FROM placex WHERE osm_type = 'N' and osm_id = %s""",
+                   FROM placex WHERE osm_type = 'W' and osm_id = %s
+                                 and class = 'place' and type = 'address'""",
                    (int(nodeid),))
     assert_equals(len(numbers), cur.rowcount)
     for r in cur:
@@ -140,6 +141,32 @@ def check_interpolated_housenumbers(step, nodeid):
         world.match_geometry((r['clat'], r['clon']), numbers[r["housenumber"]])
         del numbers[r["housenumber"]]
 
+@step(u'way (\d+) expands exactly to housenumbers ([0-9,]*)')
+def check_interpolated_housenumber_list(step, nodeid, numberlist):
+    """ Checks that the interpolated house numbers corresponds
+        to the given list.
+    """
+    expected = numberlist.split(',');
+    cur = world.conn.cursor()
+    cur.execute("""SELECT housenumber FROM placex
+                   WHERE osm_type = 'W' and osm_id = %s
+                     and class = 'place' and type = 'address'""", (int(nodeid),))
+    for r in cur:
+        assert_in(r[0], expected, "Unexpected house number %s for node %s." % (r[0], nodeid))
+        expected.remove(r[0])
+    assert_equals(0, len(expected), "Missing house numbers for way %s: %s" % (nodeid, expected))
+
+@step(u'way (\d+) expands to no housenumbers')
+def check_no_interpolated_housenumber_list(step, nodeid):
+    """ Checks that the interpolated house numbers corresponds
+        to the given list.
+    """
+    cur = world.conn.cursor()
+    cur.execute("""SELECT housenumber FROM placex
+                   WHERE osm_type = 'W' and osm_id = %s
+                     and class = 'place' and type = 'address'""", (int(nodeid),))
+    res = [r[0] for r in cur]
+    assert_equals(0, len(res), "Unexpected house numbers for way %s: %s" % (nodeid, res))
 
 @step(u'table search_name has no entry for (.*)')
 def check_placex_missing(step, osmid):
index 7d1ea8d3c11a59341d995ca3dfb1d1556d5377d0..14f17756b2a54d98648995fb3f7875a35ff69a46 100644 (file)
@@ -213,8 +213,8 @@ def import_database(step):
     world.run_nominatim_script('setup', 'create-functions', 'create-partition-functions')
     cur = world.conn.cursor()
     cur.execute("""insert into placex (osm_type, osm_id, class, type, name, admin_level,
-                              housenumber, street, addr_place, isin, postcode, country_code, extratags,
-                              geometry) select * from place""")
+                   housenumber, street, addr_place, isin, postcode, country_code, extratags,
+                   geometry) select * from place""")
     world.conn.commit()
     world.run_nominatim_script('setup', 'index', 'index-noanalyse')
     #world.db_dump_table('placex')
index 746485ac14b4bfb961e2e4d2274cf31cff2d9b04..e9561d1a9fd11b52653f8d383d7f5d9eb8872785 100644 (file)
@@ -94,7 +94,7 @@ def get_placeid(oid):
         q = 'SELECT place_id FROM placex where osm_type = %s and osm_id = %s and class = %s'
         params = (osmtype, osmid, cls)
     cur.execute(q, params)
-    assert_equals (cur.rowcount, 1)
+    assert_equals(cur.rowcount, 1, "%d rows found for place %s" % (cur.rowcount, oid))
     return cur.fetchone()[0]
 
 
index 13480695d5b806b69c6c9861b58e3991e208f20d..97b60dde39e974f15d24159061aadac2072bb1c9 100755 (executable)
                                echo " tablespace ".CONST_Tablespace_Aux_Index;
                        echo ";\n";
 
-            echo "GRANT SELECT ON place_classtype_".pg_escape_string($aPair[0])."_".pg_escape_string($aPair[1])." TO \"www-data\";\n";
+            echo "GRANT SELECT ON place_classtype_".pg_escape_string($aPair[0])."_".pg_escape_string($aPair[1]).' TO "'.CONST_Database_Web_User."\";\n";
 
                }