#32318: Collect on annotated values causes error
-------------------------------------+-------------------------------------
               Reporter:             |          Owner:  nobody
  adrianmrit                         |
                   Type:  Bug        |         Status:  new
              Component:  GIS        |        Version:  3.1
               Severity:  Normal     |       Keywords:  Collect, annotate,
           Triage Stage:             |  aggregate
  Unreviewed                         |      Has patch:  0
    Needs documentation:  0          |    Needs tests:  0
Patch needs improvement:  0          |  Easy pickings:  0
                  UI/UX:  0          |
-------------------------------------+-------------------------------------
 django.contrib.gis.db.models.Collect does not work on annotated values

 Steps to reproduce:

 {{{
 # create models
 class SampleItem(models.Model):
     name = models.CharField(max_length=250)


 class SampleLocation(models.Model):
     point = PointField()
     item = models.OneToOneField(SampleItem, on_delete=models.CASCADE)


 def run_this():
     # import models
     from django.db.models.expressions import Subquery
     from django.contrib.gis.geos.point import Point
     from django.contrib.gis.db.models import Collect
     from django.db.models import OuterRef
     item = SampleItem.objects.create(name="Sample Item")
     SampleLocation.objects.create(item=item, point=Point(50, 50))

     sub =
 
Subquery(SampleLocation.objects.filter(item=OuterRef("pk")).values("point")[:1])
     locations =
 
SampleItem.objects.annotate(location=sub).aggregate(locations=Collect("location"))
 # Throws error
 }}}


 Last line will trhow the following error:

 {{{
 /usr/local/lib/python3.6/site-packages/django/db/models/query.py in
 aggregate(self, *args, **kwargs)
     396             if not query.annotations[alias].contains_aggregate:
     397                 raise TypeError("%s is not an aggregate
 expression" % alias)
 --> 398         return query.get_aggregation(self.db, kwargs)
     399
     400     def count(self):

 /usr/local/lib/python3.6/site-packages/django/db/models/sql/query.py in
 get_aggregation(self, using, added_aggregate_names)
     503
     504         converters =
 compiler.get_converters(outer_query.annotation_select.values())
 --> 505         result = next(compiler.apply_converters((result,),
 converters))
     506
     507         return dict(zip(outer_query.annotation_select, result))

 /usr/local/lib/python3.6/site-packages/django/db/models/sql/compiler.py in
 apply_converters(self, rows, converters)
    1098                 value = row[pos]
    1099                 for converter in convs:
 -> 1100                     value = converter(value, expression,
 connection)
    1101                 row[pos] = value
    1102             yield row

 /usr/local/lib/python3.6/site-
 packages/django/contrib/gis/db/backends/postgis/operations.py in
 converter(value, expression, connection)
     385
     386         def converter(value, expression, connection):
 --> 387             return None if value is None else
 GEOSGeometryBase(read(value), geom_class)
     388         return converter
     389

 /usr/local/lib/python3.6/site-
 packages/django/contrib/gis/geos/prototypes/io.py in read(self, wkb)
     151             return wkb_reader_read(self.ptr, wkb_s, len(wkb_s))
     152         elif isinstance(wkb, (bytes, str)):
 --> 153             return wkb_reader_read_hex(self.ptr, wkb, len(wkb))
     154         else:
     155             raise TypeError

 /usr/local/lib/python3.6/site-packages/django/contrib/gis/geos/libgeos.py
 in __call__(self, *args)
     150
     151     def __call__(self, *args):
 --> 152         return self.func(*args)
     153
     154     @cached_property

 /usr/local/lib/python3.6/site-
 packages/django/contrib/gis/geos/prototypes/threadsafe.py in
 __call__(self, *args)
      45         # Call the threaded GEOS routine with the pointer of the
 context handle
      46         # as the first argument.
 ---> 47         return self.cfunc(self.thread_context.handle.ptr, *args)
      48
      49     def __str__(self):

 ArgumentError: argument 3: <class 'TypeError'>: wrong type

 }}}

 Tested with Django-3.1, PostgreSQL-9.6.12, POSTGIS-2.5.2, GEOS-3.7.1,
 GDAL-2.4.0

-- 
Ticket URL: <https://code.djangoproject.com/ticket/32318>
Django <https://code.djangoproject.com/>
The Web framework for perfectionists with deadlines.

-- 
You received this message because you are subscribed to the Google Groups 
"Django updates" group.
To unsubscribe from this group and stop receiving emails from it, send an email 
to [email protected].
To view this discussion on the web visit 
https://groups.google.com/d/msgid/django-updates/053.197610695251a568d747204068b285ad%40djangoproject.com.

Reply via email to