def _pretty_name(self, ids, langs): """ This complicated method greatly speeds up getting the names of specified parent ids in order. It returns a dict of names in order of importance (admin_level). """ # We save each place name with its admin level (10 to 1). # The OSM admin level is sometimes set high for simple Nodes; we do not want that, so we define our own admin_level pp = {} al = 10 names = [(n.place_id, n.type_id, n.name, n.lang) for n in PlaceName.objects.prefetch_related('lang').only().filter(place__id__in=ids)] for i in ids: best = False for n in [n for n in names if n[0] == int(i)]: if n[3] in langs: pp[al] = n[2] break elif n[1] == get_type_id('name'): pp[al] = n[2] best = True elif not best: pp[al] = n[2] al -= 1 return pp
def _iter_country(self): if self.host_country is not None: # First of all, we try and do the search as if we're in the host country. This is to # catch cases where the name (possibly abbreviated) of an administrative area of the # country appears to be the same as another countries name. e.g. California as CA also # looks like CA for Canada. yield self.host_country, len(self.split) - 1 # Then see if the user has specified an ISO 2 code of a country name. if len(self.split[-1]) == 2: iso2_cnd = self.split[-1] if iso2_cnd == "uk": # As a bizarre special case, the ISO 2 code for the UK is GB, but people might # reasonably be expected to specify "UK" so we hack that in. iso2_cnd = "gb" country = Country.objects.filter(iso3166_2__iexact=iso2_cnd) if country.exists(): yield country[0], len(self.split) - 2 # Finally try and match a full country name. Note that we're agnostic over the language used to # specify the country name. sub_hash = _hash_wd(self.split[-1]) norm_hash = _hash_wd(unidecode(self.split[-1])) country_list = PlaceName.objects.prefetch_related('place').filter(Q(name_hash=sub_hash) | Q(name_hash=norm_hash), Q(type__id=get_type_id("country"))) done = set() for cnd in country_list: new_i = _match_end_split([unidecode(x) for x in self.split], len(self.split) - 1, unidecode(cnd.name)) country = cnd.place.country done_key = (country, new_i) if done_key in done: continue if new_i is not None: yield country, new_i done.add(done_key) # Apparently none of the above was a good enough match... yield None, len(self.split) - 1