]> git.openstreetmap.org Git - nominatim.git/commitdiff
Merge remote-tracking branch 'upstream/master'
authorSarah Hoffmann <lonvia@denofr.de>
Fri, 4 May 2018 20:04:56 +0000 (22:04 +0200)
committerSarah Hoffmann <lonvia@denofr.de>
Fri, 4 May 2018 20:04:56 +0000 (22:04 +0200)
lib/DebugHtml.php
sql/functions.sql
sql/indices.src.sql
test/php/Nominatim/DebugTest.php [new file with mode: 0644]

index ce2b8361c3fa5bf211846bfe5cc347c9eea1e2bb..0f5af241022c9fd8b5252e99635719b6cab85ce7 100644 (file)
@@ -39,73 +39,75 @@ class Debug
     public static function printDebugTable($sHeading, $aVar)
     {
         echo '<b>'.$sHeading.":</b>\n";
-        echo '<table border="1">';
+        echo "<table border='1'>\n";
         if (!empty($aVar)) {
-            echo '<tr>';
+            echo "  <tr>\n";
             $aKeys = array();
             $aInfo = reset($aVar);
             if (!is_array($aInfo)) {
                 $aInfo = $aInfo->debugInfo();
             }
             foreach ($aInfo as $sKey => $mVal) {
-                echo '<th><small>'.$sKey.'</small></th>';
+                echo '    <th><small>'.$sKey.'</small></th>'."\n";
                 $aKeys[] = $sKey;
             }
-            echo '</tr>';
+            echo "  </tr>\n";
             foreach ($aVar as $oRow) {
                 $aInfo = $oRow;
                 if (!is_array($oRow)) {
                     $aInfo = $oRow->debugInfo();
                 }
-                echo '<tr>';
+                echo "  <tr>\n";
                 foreach ($aKeys as $sKey) {
-                    echo '<td><pre>';
+                    echo '    <td><pre>';
                     if (isset($aInfo[$sKey])) {
                         Debug::outputVar($aInfo[$sKey], '');
                     }
-                    echo '</pre></td>';
+                    echo '</pre></td>'."\n";
                 }
-                echo '<tr>';
+                echo "  </tr>\n";
             }
         }
-        echo '</table>';
+        echo "</table>\n";
     }
 
     public static function printGroupTable($sHeading, $aVar)
     {
         echo '<b>'.$sHeading.":</b>\n";
-        echo '<table border="1">';
+        echo "<table border='1'>\n";
         if (!empty($aVar)) {
-            echo '<tr><th><small>Group</small></th>';
+            echo "  <tr>\n";
+            echo '    <th><small>Group</small></th>'."\n";
             $aKeys = array();
-            $aInfo = reset(reset($aVar));
+            $aInfo = reset($aVar)[0];
             if (!is_array($aInfo)) {
                 $aInfo = $aInfo->debugInfo();
             }
             foreach ($aInfo as $sKey => $mVal) {
-                echo '<th><small>'.$sKey.'</small></th>';
+                echo '    <th><small>'.$sKey.'</small></th>'."\n";
                 $aKeys[] = $sKey;
             }
-            echo '</tr>';
+            echo "  </tr>\n";
             foreach ($aVar as $sGrpKey => $aGroup) {
                 foreach ($aGroup as $oRow) {
                     $aInfo = $oRow;
                     if (!is_array($oRow)) {
                         $aInfo = $oRow->debugInfo();
                     }
-                    echo '<tr><td><pre>'.$sGrpKey.'</pre></td>';
+                    echo "  <tr>\n";
+                    echo '    <td><pre>'.$sGrpKey.'</pre></td>'."\n";
                     foreach ($aKeys as $sKey) {
-                        echo '<td><pre>';
+                        echo '    <td><pre>';
                         if (!empty($aInfo[$sKey])) {
                             Debug::outputVar($aInfo[$sKey], '');
                         }
-                        echo '</pre></td>';
+                        echo '</pre></td>'."\n";
                     }
-                    echo '<tr>';
+                    echo "  </tr>\n";
                 }
             }
         }
-        echo '</table>';
+        echo "</table>\n";
     }
 
     public static function printSQL($sSQL)
@@ -128,9 +130,9 @@ class Debug
                 $sPre = "\n".$sPreNL;
             }
         } elseif (is_array($mVar) && isset($mVar['__debug_format'])) {
-            if (!empty($mVar[data])) {
+            if (!empty($mVar['data'])) {
                 $sPre = '';
-                foreach ($mVar[data] as $mValue) {
+                foreach ($mVar['data'] as $mValue) {
                     echo $sPre;
                     Debug::outputSimpleVar($mValue);
                     $sPre = ', ';
index 305365d1b612878d292df21f7d436f02ce3c808f..c9797a5c93eef9ad66a85c2fb4c69e6e5a903c1d 100644 (file)
@@ -1311,8 +1311,8 @@ BEGIN
         i := getorcreate_housenumber_id(make_standard_name(NEW.housenumber));
       END IF;
 
-      addr_street = NEW.address->'street';
-      addr_place = NEW.address->'place';
+      addr_street := NEW.address->'street';
+      addr_place := NEW.address->'place';
 
       IF NEW.address ? 'postcode' and NEW.address->'postcode' not similar to '%(,|;)%' THEN
         i := getorcreate_postcode_id(NEW.address->'postcode');
@@ -1419,7 +1419,7 @@ BEGIN
     -- see if we can get it from a surrounding building
     IF NEW.osm_type = 'N' AND addr_street IS NULL AND addr_place IS NULL
        AND NEW.housenumber IS NULL THEN
-      FOR location IN select * from placex where ST_Covers(geometry, place_centroid)
+      FOR location IN select address from placex where ST_Covers(geometry, place_centroid)
             and address is not null
             and (address ? 'housenumber' or address ? 'street' or address ? 'place')
             and rank_search > 28 AND ST_GeometryType(geometry) in ('ST_Polygon','ST_MultiPolygon')
@@ -1456,9 +1456,7 @@ BEGIN
     IF NEW.parent_place_id IS NULL AND 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 * from getNearestNamedRoadFeature(NEW.partition, place_centroid, address_street_word_ids) LOOP
-            NEW.parent_place_id := location.place_id;
-        END LOOP;
+        SELECT place_id from getNearestNamedRoadFeature(NEW.partition, place_centroid, address_street_word_ids) INTO NEW.parent_place_id;
       END IF;
     END IF;
     --DEBUG: RAISE WARNING 'Checked for addr:street (%)', NEW.parent_place_id;
@@ -1466,88 +1464,80 @@ BEGIN
     IF NEW.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 * from getNearestNamedPlaceFeature(NEW.partition, place_centroid, address_street_word_ids) LOOP
-          NEW.parent_place_id := location.place_id;
-        END LOOP;
+        SELECT place_id from getNearestNamedPlaceFeature(NEW.partition, place_centroid, address_street_word_ids) INTO NEW.parent_place_id;
       END IF;
     END IF;
     --DEBUG: RAISE WARNING 'Checked for addr:place (%)', NEW.parent_place_id;
 
     -- Is this node part of an interpolation?
     IF NEW.parent_place_id IS NULL AND NEW.osm_type = 'N' THEN
-      FOR location IN
-        SELECT q.parent_place_id FROM location_property_osmline q, planet_osm_ways x
-         WHERE q.linegeo && NEW.geometry and x.id = q.osm_id and NEW.osm_id = any(x.nodes)
-         LIMIT 1
-      LOOP
-         NEW.parent_place_id := location.parent_place_id;
-      END LOOP;
+      SELECT q.parent_place_id FROM location_property_osmline q, planet_osm_ways x
+        WHERE q.linegeo && NEW.geometry and x.id = q.osm_id and NEW.osm_id = any(x.nodes)
+        LIMIT 1 INTO NEW.parent_place_id;
     END IF;
     --DEBUG: RAISE WARNING 'Checked for interpolation (%)', NEW.parent_place_id;
 
     -- Is this node part of a way?
     IF NEW.parent_place_id IS NULL AND NEW.osm_type = 'N' THEN
 
-      FOR location IN select p.place_id, p.osm_id, p.parent_place_id, p.rank_search, p.address from placex p, planet_osm_ways w
-         where p.osm_type = 'W' and p.rank_search >= 26 and p.geometry && NEW.geometry and w.id = p.osm_id and NEW.osm_id = any(w.nodes) 
+      FOR location IN
+        SELECT p.place_id, p.osm_id, p.rank_search, p.address from placex p, planet_osm_ways w
+         WHERE p.osm_type = 'W' and p.rank_search >= 26 and p.geometry && NEW.geometry and w.id = p.osm_id and NEW.osm_id = any(w.nodes)
       LOOP
         --DEBUG: RAISE WARNING 'Node is part of way % ', location.osm_id;
 
         -- Way IS a road then we are on it - that must be our road
-        IF location.rank_search < 28 AND NEW.parent_place_id IS NULL THEN
+        IF location.rank_search < 28 THEN
 --RAISE WARNING 'node in way that is a street %',location;
           NEW.parent_place_id := location.place_id;
+          EXIT;
         END IF;
         --DEBUG: RAISE WARNING 'Checked if way is street (%)', NEW.parent_place_id;
 
         -- If the way mentions a street or place address, try that for parenting.
-        IF NEW.parent_place_id IS NULL AND location.address ? 'street' THEN
-          address_street_word_ids := get_name_ids(make_standard_name(location.address->'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;
+        IF location.address is not null THEN
+          IF location.address ? 'street' THEN
+            address_street_word_ids := get_name_ids(make_standard_name(location.address->'street'));
+            IF address_street_word_ids IS NOT NULL THEN
+              SELECT place_id from getNearestNamedRoadFeature(NEW.partition, place_centroid, address_street_word_ids) INTO NEW.parent_place_id;
+              EXIT WHEN NEW.parent_place_id is not NULL;
+            END IF;
           END IF;
-        END IF;
-        --DEBUG: RAISE WARNING 'Checked for addr:street in way (%)', NEW.parent_place_id;
+          --DEBUG: RAISE WARNING 'Checked for addr:street in way (%)', NEW.parent_place_id;
 
-        IF NEW.parent_place_id IS NULL AND location.address ? 'place' THEN
-          address_street_word_ids := get_name_ids(make_standard_name(location.address->'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;
+          IF location.address ? 'place' THEN
+            address_street_word_ids := get_name_ids(make_standard_name(location.address->'place'));
+            IF address_street_word_ids IS NOT NULL THEN
+              SELECT place_id from getNearestNamedPlaceFeature(NEW.partition, place_centroid, address_street_word_ids) INTO NEW.parent_place_id;
+              EXIT WHEN NEW.parent_place_id is not NULL;
+            END IF;
           END IF;
-        END IF;
         --DEBUG: RAISE WARNING 'Checked for addr:place in way (%)', NEW.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]
-            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 'node in 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;
+        FOR relation IN select * from planet_osm_rels where parts @> ARRAY[location.osm_id] and members @> ARRAY['w'||location.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 'node in 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;
-        END IF;
+          END IF;
+        END LOOP;
+        EXIT WHEN NEW.parent_place_id is not null;
         --DEBUG: RAISE WARNING 'Checked for street relation in way (%)', NEW.parent_place_id;
 
       END LOOP;
-
     END IF;
 
     -- Still nothing, just use the nearest road
     IF NEW.parent_place_id IS NULL THEN
-      FOR location IN SELECT place_id FROM getNearestRoadFeature(NEW.partition, place_centroid) LOOP
-        NEW.parent_place_id := location.place_id;
-      END LOOP;
+      SELECT place_id FROM getNearestRoadFeature(NEW.partition, place_centroid) INTO NEW.parent_place_id;
     END IF;
     --DEBUG: RAISE WARNING 'Checked for nearest way (%)', NEW.parent_place_id;
 
@@ -1556,7 +1546,8 @@ BEGIN
     IF NEW.parent_place_id IS NOT NULL THEN
 
       -- Get the details of the parent road
-      select * from search_name where place_id = NEW.parent_place_id INTO location;
+      select s.country_code, s.name_vector, s.nameaddress_vector from search_name s
+       where s.place_id = NEW.parent_place_id INTO location;
       NEW.country_code := location.country_code;
       --DEBUG: RAISE WARNING 'Got parent details from search name';
 
index 61af89002b81762be8835b7b7170e73bcdfae880..8f6b7b51c4380a438ebfdfebb0722d13624bdf48 100644 (file)
@@ -14,7 +14,7 @@ CREATE INDEX idx_placex_rank_search ON placex USING BTREE (rank_search) {ts:sear
 CREATE INDEX idx_placex_rank_address ON placex USING BTREE (rank_address) {ts:search-index};
 CREATE INDEX idx_placex_pendingsector ON placex USING BTREE (rank_search,geometry_sector) {ts:address-index} where indexed_status > 0;
 CREATE INDEX idx_placex_parent_place_id ON placex USING BTREE (parent_place_id) {ts:search-index} where parent_place_id IS NOT NULL;
-CREATE INDEX idx_placex_reverse_geometry ON placex USING gist (geometry) {ts:search-index} where rank_search != 28 and (name is not null or housenumber is not null) and class not in ('waterway','railway','tunnel','bridge','man_made');
+CREATE INDEX idx_placex_reverse_geometry ON placex USING gist (geometry) {ts:search-index} where rank_search != 28 and (name is not null or housenumber is not null or rank_search between 26 and 27) and class not in ('waterway','railway','tunnel','bridge','man_made');
 CREATE INDEX idx_location_area_country_place_id ON location_area_country USING BTREE (place_id) {ts:address-index};
 
 CREATE INDEX idx_osmline_parent_place_id ON location_property_osmline USING BTREE (parent_place_id) {ts:search-index};
diff --git a/test/php/Nominatim/DebugTest.php b/test/php/Nominatim/DebugTest.php
new file mode 100644 (file)
index 0000000..7ed0812
--- /dev/null
@@ -0,0 +1,197 @@
+<?php
+
+namespace Nominatim;
+
+use Exception;
+
+require_once('../../lib/DebugHtml.php');
+
+class DebugTest extends \PHPUnit_Framework_TestCase
+{
+    protected function setUp()
+    {
+        $this->oWithDebuginfo = $this->getMock(Geocode::class, array('debugInfo'));
+        $this->oWithDebuginfo->method('debugInfo')
+                  ->willReturn(array('key1' => 'val1', 'key2' => 'val2', 'key3' => 'val3'));
+
+        $this->oWithToString = $this->getMock(Geocode::class, array('__toString'));
+        $this->oWithToString->method('__toString')->willReturn('me as string');
+    }
+
+    public function testPrintVar()
+    {
+        $this->expectOutputString(<<<EOT
+<pre><b>Var0:</b>  </pre>
+<pre><b>Var1:</b>  <i>True</i></pre>
+<pre><b>Var2:</b>  <i>False</i></pre>
+<pre><b>Var3:</b>  0</pre>
+<pre><b>Var4:</b>  'String'</pre>
+<pre><b>Var5:</b>  0 => 'one'
+       1 => 'two'
+       2 => 'three'</pre>
+<pre><b>Var6:</b>  'key' => 'value'
+       'key2' => 'value2'</pre>
+<pre><b>Var7:</b>  me as string</pre>
+<pre><b>Var8:</b>  'value', 'value2'</pre>
+
+EOT
+        );
+    
+        Debug::printVar('Var0', null);
+        Debug::printVar('Var1', true);
+        Debug::printVar('Var2', false);
+        Debug::printVar('Var3', 0);
+        Debug::printVar('Var4', 'String');
+        Debug::printVar('Var5', array('one', 'two', 'three'));
+        Debug::printVar('Var6', array('key' => 'value', 'key2' => 'value2'));
+        Debug::printVar('Var7', $this->oWithToString);
+        Debug::printVar('Var8', Debug::fmtArrayVals(array('key' => 'value', 'key2' => 'value2')));
+    }
+
+
+    public function testDebugArray()
+    {
+        $this->expectOutputString(<<<EOT
+<pre><b>Arr0:</b>  'null'</pre>
+<pre><b>Arr1:</b>  'key1' => 'val1'
+       'key2' => 'val2'
+       'key3' => 'val3'</pre>
+
+EOT
+        );
+    
+        Debug::printDebugArray('Arr0', null);
+        Debug::printDebugArray('Arr1', $this->oWithDebuginfo);
+    }
+
+
+    public function testPrintDebugTable()
+    {
+        $this->expectOutputString(<<<EOT
+<b>Table1:</b>
+<table border='1'>
+</table>
+<b>Table2:</b>
+<table border='1'>
+</table>
+<b>Table3:</b>
+<table border='1'>
+  <tr>
+    <th><small>0</small></th>
+    <th><small>1</small></th>
+  </tr>
+  <tr>
+    <td><pre>'one'</pre></td>
+    <td><pre>'two'</pre></td>
+  </tr>
+  <tr>
+    <td><pre>'three'</pre></td>
+    <td><pre>'four'</pre></td>
+  </tr>
+</table>
+<b>Table4:</b>
+<table border='1'>
+  <tr>
+    <th><small>key1</small></th>
+    <th><small>key2</small></th>
+    <th><small>key3</small></th>
+  </tr>
+  <tr>
+    <td><pre>'val1'</pre></td>
+    <td><pre>'val2'</pre></td>
+    <td><pre>'val3'</pre></td>
+  </tr>
+</table>
+
+EOT
+        );
+    
+        Debug::printDebugTable('Table1', null);
+
+        Debug::printDebugTable('Table2', array());
+
+        // Numeric headers
+        Debug::printDebugTable('Table3', array(array('one', 'two'), array('three', 'four')));
+
+        // Associate array
+        Debug::printDebugTable('Table4', array($this->oWithDebuginfo));
+    }
+
+    public function testPrintGroupTable()
+    {
+        $this->expectOutputString(<<<EOT
+<b>Table1:</b>
+<table border='1'>
+</table>
+<b>Table2:</b>
+<table border='1'>
+</table>
+<b>Table3:</b>
+<table border='1'>
+  <tr>
+    <th><small>Group</small></th>
+    <th><small>key1</small></th>
+    <th><small>key2</small></th>
+  </tr>
+  <tr>
+    <td><pre>group1</pre></td>
+    <td><pre>'val1'</pre></td>
+    <td><pre>'val2'</pre></td>
+  </tr>
+  <tr>
+    <td><pre>group1</pre></td>
+    <td><pre>'one'</pre></td>
+    <td><pre>'two'</pre></td>
+  </tr>
+  <tr>
+    <td><pre>group2</pre></td>
+    <td><pre>'val1'</pre></td>
+    <td><pre>'val2'</pre></td>
+  </tr>
+</table>
+<b>Table4:</b>
+<table border='1'>
+  <tr>
+    <th><small>Group</small></th>
+    <th><small>key1</small></th>
+    <th><small>key2</small></th>
+    <th><small>key3</small></th>
+  </tr>
+  <tr>
+    <td><pre>group1</pre></td>
+    <td><pre>'val1'</pre></td>
+    <td><pre>'val2'</pre></td>
+    <td><pre>'val3'</pre></td>
+  </tr>
+  <tr>
+    <td><pre>group1</pre></td>
+    <td><pre>'val1'</pre></td>
+    <td><pre>'val2'</pre></td>
+    <td><pre>'val3'</pre></td>
+  </tr>
+</table>
+
+EOT
+        );
+    
+        Debug::printGroupTable('Table1', null);
+        Debug::printGroupTable('Table2', array());
+
+        // header are taken from first group item, thus no key3 gets printed
+        $aGroups = array(
+            'group1' => array(
+                array('key1' => 'val1', 'key2' => 'val2'),
+                array('key1' => 'one', 'key2' => 'two', 'unknown' => 1),
+            ),
+            'group2' => array(
+                array('key1' => 'val1', 'key2' => 'val2', 'key3' => 'val3'),
+            )
+        );
+        Debug::printGroupTable('Table3', $aGroups);
+
+        $aGroups = array(
+            'group1' => array($this->oWithDebuginfo, $this->oWithDebuginfo),
+        );
+        Debug::printGroupTable('Table4', $aGroups);
+    }
+}