2

All the examples I have seen for generating sitemaps in Django seem to iterate over a model, to generate URLs that way.

For example, from the Django documentation:

class BlogSitemap(Sitemap):
    changefreq = "never"
    priority = 0.5

    def items(self):
        return Entry.objects.filter(is_draft=False)

    def lastmod(self, obj):
        return obj.pub_date

I can't do this with my web application. I have thousands of URLs that correspond to product pages, that are generated using django, based on data retrieved from an API that was directly inserted into a postgres database.

So, I am using django to retrieve records from the database and shape how they are presented, but the URLs I have do not correspond to any django model (this is something that will be improved and changed in the future).

Is there a way then, that I can specify specific URLs in a sitemap without iterating over a model?

Jake Rankin
  • 714
  • 6
  • 22

1 Answers1

2

items() can return any python object, it doesn't need to be a Django model. By default each object gets passed to the location method, which should return the URL for the object (on a Django model, it uses the get_absolute_url() method).

So basically, if you have a python class that defines each "page" you want to show in your sitemap (it could be just a string, or a tuple of strings), and you define a method to return the URL of that page, you just need to call that method in location() to override the default behaviour.

items can also be just a list of strings that you would use in the url path. Then location() would use reverse() with each of these strings. Say for example your product page url uses a regex like this:

path('products/<str:category>/<str:name>', name='product')

and in items() you return a list of dictionaries:

return [{'category': cat, 'name': name} for cat, name in product_searches]

then your location(item) function would need to return:

return reverse('product', kwargs={'category': item.category, 'name': item.name}) 

For more details, refer to the docs

dirkgroten
  • 20,112
  • 2
  • 29
  • 42
  • The problem is that I don't have a python class that defines my pages. I have a url that uses regexp, passes what is in the url to the view, and then the view retrieves the relevant data from the db. – Jake Rankin Mar 29 '19 at 10:14
  • But if you have the urls, why use the Sitemap framework? Just generate the list of urls directly and add it to the sitemap.xml – dirkgroten Mar 29 '19 at 10:20
  • or reconstruct your urls as I added to the answer. – dirkgroten Mar 29 '19 at 10:28
  • because the URL's will change every few months, if there is a way to do it more automatically via django I would rather do it that way. – Jake Rankin Mar 30 '19 at 17:43
  • I'm having trouble understanding your answer, I was wondering if you could clarify? At the moment, I have a page listing 'collections', which retrieves all products with a collection name, then each 'collection page' returns all products from the database that correspond to the collection name. There are no models for collections, only products. I'm not sure how I would generate the links for connection pages based on your answer? – Jake Rankin Mar 30 '19 at 17:54
  • Additionally I have all the products in one table. A messy design but it is working at the moment and will be improved in later months, but had a deadline to meet. So there is no model for product categories like bedroom, dining etc. These are matched by regex in the url and then records from the db matching where category matches the regexp are pulled. – Jake Rankin Mar 30 '19 at 17:55