You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
 
 
 

78 lines
2.5 KiB

from django.apps import apps
from django.contrib.gis.db.models import GeometryField
from django.contrib.sitemaps import Sitemap
from django.db import models
from django.urls import reverse
class KMLSitemap(Sitemap):
"""
A minimal hook to produce KML sitemaps.
"""
geo_format = "kml"
def __init__(self, locations=None):
# If no locations specified, then we try to build for
# every model in installed applications.
self.locations = self._build_kml_sources(locations)
def _build_kml_sources(self, sources):
"""
Go through the given sources and return a 3-tuple of the application
label, module name, and field name of every GeometryField encountered
in the sources.
If no sources are provided, then all models.
"""
kml_sources = []
if sources is None:
sources = apps.get_models()
for source in sources:
if isinstance(source, models.base.ModelBase):
for field in source._meta.fields:
if isinstance(field, GeometryField):
kml_sources.append(
(
source._meta.app_label,
source._meta.model_name,
field.name,
)
)
elif isinstance(source, (list, tuple)):
if len(source) != 3:
raise ValueError(
"Must specify a 3-tuple of (app_label, module_name, "
"field_name)."
)
kml_sources.append(source)
else:
raise TypeError("KML Sources must be a model or a 3-tuple.")
return kml_sources
def get_urls(self, page=1, site=None, protocol=None):
"""
This method is overridden so the appropriate `geo_format` attribute
is placed on each URL element.
"""
urls = Sitemap.get_urls(self, page=page, site=site, protocol=protocol)
for url in urls:
url["geo_format"] = self.geo_format
return urls
def items(self):
return self.locations
def location(self, obj):
return reverse(
"django.contrib.gis.sitemaps.views.%s" % self.geo_format,
kwargs={
"label": obj[0],
"model": obj[1],
"field_name": obj[2],
},
)
class KMZSitemap(KMLSitemap):
geo_format = "kmz"