1. from xml.dom import minidom
    
  2. 
    
  3. from django.conf import settings
    
  4. from django.contrib.sites.models import Site
    
  5. from django.test import TestCase, modify_settings, override_settings
    
  6. 
    
  7. from .models import City
    
  8. 
    
  9. 
    
  10. @modify_settings(INSTALLED_APPS={"append": "django.contrib.sites"})
    
  11. @override_settings(ROOT_URLCONF="gis_tests.geoapp.urls")
    
  12. class GeoFeedTest(TestCase):
    
  13.     fixtures = ["initial"]
    
  14. 
    
  15.     @classmethod
    
  16.     def setUpTestData(cls):
    
  17.         Site(id=settings.SITE_ID, domain="example.com", name="example.com").save()
    
  18. 
    
  19.     def assertChildNodes(self, elem, expected):
    
  20.         "Taken from syndication/tests.py."
    
  21.         actual = {n.nodeName for n in elem.childNodes}
    
  22.         expected = set(expected)
    
  23.         self.assertEqual(actual, expected)
    
  24. 
    
  25.     def test_geofeed_rss(self):
    
  26.         "Tests geographic feeds using GeoRSS over RSSv2."
    
  27.         # Uses `GEOSGeometry` in `item_geometry`
    
  28.         doc1 = minidom.parseString(self.client.get("/feeds/rss1/").content)
    
  29.         # Uses a 2-tuple in `item_geometry`
    
  30.         doc2 = minidom.parseString(self.client.get("/feeds/rss2/").content)
    
  31.         feed1, feed2 = doc1.firstChild, doc2.firstChild
    
  32. 
    
  33.         # Making sure the box got added to the second GeoRSS feed.
    
  34.         self.assertChildNodes(
    
  35.             feed2.getElementsByTagName("channel")[0],
    
  36.             [
    
  37.                 "title",
    
  38.                 "link",
    
  39.                 "description",
    
  40.                 "language",
    
  41.                 "lastBuildDate",
    
  42.                 "item",
    
  43.                 "georss:box",
    
  44.                 "atom:link",
    
  45.             ],
    
  46.         )
    
  47. 
    
  48.         # Incrementing through the feeds.
    
  49.         for feed in [feed1, feed2]:
    
  50.             # Ensuring the georss namespace was added to the <rss> element.
    
  51.             self.assertEqual(
    
  52.                 feed.getAttribute("xmlns:georss"), "http://www.georss.org/georss"
    
  53.             )
    
  54.             chan = feed.getElementsByTagName("channel")[0]
    
  55.             items = chan.getElementsByTagName("item")
    
  56.             self.assertEqual(len(items), City.objects.count())
    
  57. 
    
  58.             # Ensuring the georss element was added to each item in the feed.
    
  59.             for item in items:
    
  60.                 self.assertChildNodes(
    
  61.                     item, ["title", "link", "description", "guid", "georss:point"]
    
  62.                 )
    
  63. 
    
  64.     def test_geofeed_atom(self):
    
  65.         "Testing geographic feeds using GeoRSS over Atom."
    
  66.         doc1 = minidom.parseString(self.client.get("/feeds/atom1/").content)
    
  67.         doc2 = minidom.parseString(self.client.get("/feeds/atom2/").content)
    
  68.         feed1, feed2 = doc1.firstChild, doc2.firstChild
    
  69. 
    
  70.         # Making sure the box got added to the second GeoRSS feed.
    
  71.         self.assertChildNodes(
    
  72.             feed2, ["title", "link", "id", "updated", "entry", "georss:box"]
    
  73.         )
    
  74. 
    
  75.         for feed in [feed1, feed2]:
    
  76.             # Ensuring the georsss namespace was added to the <feed> element.
    
  77.             self.assertEqual(
    
  78.                 feed.getAttribute("xmlns:georss"), "http://www.georss.org/georss"
    
  79.             )
    
  80.             entries = feed.getElementsByTagName("entry")
    
  81.             self.assertEqual(len(entries), City.objects.count())
    
  82. 
    
  83.             # Ensuring the georss element was added to each entry in the feed.
    
  84.             for entry in entries:
    
  85.                 self.assertChildNodes(
    
  86.                     entry, ["title", "link", "id", "summary", "georss:point"]
    
  87.                 )
    
  88. 
    
  89.     def test_geofeed_w3c(self):
    
  90.         "Testing geographic feeds using W3C Geo."
    
  91.         doc = minidom.parseString(self.client.get("/feeds/w3cgeo1/").content)
    
  92.         feed = doc.firstChild
    
  93.         # Ensuring the geo namespace was added to the <feed> element.
    
  94.         self.assertEqual(
    
  95.             feed.getAttribute("xmlns:geo"), "http://www.w3.org/2003/01/geo/wgs84_pos#"
    
  96.         )
    
  97.         chan = feed.getElementsByTagName("channel")[0]
    
  98.         items = chan.getElementsByTagName("item")
    
  99.         self.assertEqual(len(items), City.objects.count())
    
  100. 
    
  101.         # Ensuring the geo:lat and geo:lon element was added to each item in the feed.
    
  102.         for item in items:
    
  103.             self.assertChildNodes(
    
  104.                 item, ["title", "link", "description", "guid", "geo:lat", "geo:lon"]
    
  105.             )
    
  106. 
    
  107.         # Boxes and Polygons aren't allowed in W3C Geo feeds.
    
  108.         with self.assertRaises(ValueError):  # Box in <channel>
    
  109.             self.client.get("/feeds/w3cgeo2/")
    
  110.         with self.assertRaises(ValueError):  # Polygons in <entry>
    
  111.             self.client.get("/feeds/w3cgeo3/")