]> git.openstreetmap.org Git - nominatim.git/blob - lib/AddressDetails.php
traverse address list backwards when computing admin levels
[nominatim.git] / lib / AddressDetails.php
1 <?php
2
3 namespace Nominatim;
4
5 require_once(CONST_BasePath.'/lib/ClassTypes.php');
6
7 /**
8  * Detailed list of address parts for a single result
9  */
10 class AddressDetails
11 {
12     private $aAddressLines;
13
14     public function __construct(&$oDB, $iPlaceID, $sHousenumber, $mLangPref)
15     {
16         if (is_array($mLangPref)) {
17             $mLangPref = 'ARRAY['.join(',', array_map('getDBQuoted', $mLangPref)).']';
18         }
19
20         if (!$sHousenumber) {
21             $sHousenumber = -1;
22         }
23
24         $sSQL = 'SELECT *,';
25         $sSQL .= ' get_name_by_language(name,'.$mLangPref.') as localname';
26         $sSQL .= ' FROM get_addressdata('.$iPlaceID.','.$sHousenumber.')';
27         $sSQL .= ' ORDER BY rank_address DESC, isaddress DESC';
28
29         $this->aAddressLines = chksql($oDB->getAll($sSQL));
30     }
31
32     private static function isAddress($aLine)
33     {
34         return $aLine['isaddress'] == 't' || $aLine['type'] == 'country_code';
35     }
36
37     public function getAddressDetails($bAll = false)
38     {
39         if ($bAll) {
40             return $this->aAddressLines;
41         }
42
43         return array_filter($this->aAddressLines, array(__CLASS__, 'isAddress'));
44     }
45
46     public function getLocaleAddress()
47     {
48         $aParts = array();
49         $sPrevResult = '';
50
51         foreach ($this->aAddressLines as $aLine) {
52             if ($aLine['isaddress'] == 't' && $sPrevResult != $aLine['localname']) {
53                 $sPrevResult = $aLine['localname'];
54                 $aParts[] = $sPrevResult;
55             }
56         }
57
58         return join(', ', $aParts);
59     }
60
61     public function getAddressNames()
62     {
63         $aAddress = array();
64         $aFallback = array();
65
66         foreach ($this->aAddressLines as $aLine) {
67             if (!self::isAddress($aLine)) {
68                 continue;
69             }
70
71             $bFallback = false;
72             $aTypeLabel = ClassTypes\getInfo($aLine);
73
74             if ($aTypeLabel === false) {
75                 $aTypeLabel = ClassTypes\getFallbackInfo($aLine);
76                 $bFallback = true;
77             }
78
79             $sName = false;
80             if (isset($aLine['localname']) && $aLine['localname']) {
81                 $sName = $aLine['localname'];
82             } elseif (isset($aLine['housenumber']) && $aLine['housenumber']) {
83                 $sName = $aLine['housenumber'];
84             }
85
86             if ($sName) {
87                 $sTypeLabel = strtolower(isset($aTypeLabel['simplelabel']) ? $aTypeLabel['simplelabel'] : $aTypeLabel['label']);
88                 $sTypeLabel = str_replace(' ', '_', $sTypeLabel);
89                 if (!isset($aAddress[$sTypeLabel])
90                     || isset($aFallback[$sTypeLabel])
91                     || $aLine['class'] == 'place'
92                 ) {
93                     $aAddress[$sTypeLabel] = $sName;
94                     if ($bFallback) {
95                         $aFallback[$sTypeLabel] = $bFallback;
96                     }
97                 }
98             }
99         }
100         return $aAddress;
101     }
102
103     public function getAdminLevels()
104     {
105         $aAddress = array();
106         foreach (array_reverse($this->aAddressLines) as $aLine) {
107             if (self::isAddress($aLine)
108                 && isset($aLine['admin_level'])
109                 && $aLine['admin_level'] < 15
110                 && !isset($aAddress['level'.$aLine['admin_level']])
111             ) {
112                 $aAddress['level'.$aLine['admin_level']] = $aLine['localname'];
113             }
114         }
115         return $aAddress;
116     }
117
118     public function debugInfo()
119     {
120         return $this->aAddressLines;
121     }
122 }