Code

Ticket #12733: extent-patch.diff

File extent-patch.diff, 2.7 KB (added by jann.kleen@…, 4 years ago)
Line 
1Index: django/contrib/gis/db/backends/mysql/operations.py
2===================================================================
3--- django/contrib/gis/db/backends/mysql/operations.py  (revision 12350)
4+++ django/contrib/gis/db/backends/mysql/operations.py  (working copy)
5@@ -11,7 +11,11 @@
6     select = 'AsText(%s)'
7     from_wkb = 'GeomFromWKB'
8     from_text = 'GeomFromText'
9+    valid_aggregates = dict([(k, None) for k in ('Extent',)])
10 
11+    extent_sql = '''CONCAT_WS(',', MAX(X(%(field)s)), MAX(Y(%(field)s)), MIN(X(%(field)s)), MIN(Y(%(field)s)))'''
12+    extent = 'Extent'
13+
14     Adapter = WKTAdapter
15 
16     geometry_functions = {
17@@ -31,6 +35,22 @@
18 
19     gis_terms = dict([(term, None) for term in geometry_functions.keys() + ['isnull']])
20 
21+    def convert_extent (self,box):
22+       """
23+       Returns a 4-tuple extent for the `Extent` aggregate, created by MIN/MAX
24+       queries on the dataset
25+        """
26+       xmax, ymax, xmin, ymin =  map(float, box.split(','))
27+       return (xmin, ymin, xmax, ymax)
28+
29+    def check_aggregate_support(self, aggregate):
30+        """
31+        Checks if the given aggregate name is supported (that is, if it's
32+        in `self.valid_aggregates`).
33+        """
34+        agg_name = aggregate.__class__.__name__
35+        return agg_name in self.valid_aggregates
36+
37     def geo_db_type(self, f):
38         return f.geom_type
39 
40@@ -46,6 +66,20 @@
41             placeholder = '%s(%%s)' % self.from_text
42         return placeholder
43 
44+
45+    def spatial_aggregate_sql(self, agg):
46+        """
47+        Returns the spatial aggregate SQL template and function for the
48+        given Aggregate instance.
49+        """
50+        agg_name = agg.__class__.__name__
51+        if not self.check_aggregate_support(agg):
52+            raise NotImplementedError('%s spatial aggregate is not implmented for this backend.' % agg_name)
53+        agg_name = agg_name.lower()
54+       sql_template = getattr(self, agg_name + '_sql')
55+        sql_function = getattr(self, agg_name)
56+        return sql_template, sql_function
57+
58     def spatial_lookup_sql(self, lvalue, lookup_type, value, field, qn):
59         alias, col, db_type = lvalue
60 
61Index: django/contrib/gis/tests/relatedapp/tests.py
62===================================================================
63--- django/contrib/gis/tests/relatedapp/tests.py        (revision 12350)
64+++ django/contrib/gis/tests/relatedapp/tests.py        (working copy)
65@@ -56,7 +56,6 @@
66             qs = list(City.objects.filter(name=name).transform(srid, field_name='location__point'))
67             check_pnt(GEOSGeometry(wkt, srid), qs[0].location.point)
68 
69-    @no_mysql
70     @no_spatialite
71     def test04a_related_extent_aggregate(self):
72         "Testing the `extent` GeoQuerySet aggregates on related geographic models."