Amsterdam / django-gisserver

Django speaking WFS 2.0 to expose geo data
Mozilla Public License 2.0
42 stars 10 forks source link

GetCapabilities does not work with dotted model_attribute value #24

Closed jforsman closed 3 months ago

jforsman commented 7 months ago

If a FeatureField has reference to a different model via FK reference, GetCapabilities query is not working. eg.

FeatureField( "not_working", model_attribute="some_fk.field_name", abstract="does not work", )

Result from eg. http://localhost:8000/wfs/?SERVICE=WFS&VERSION=2.0.0&REQUEST=GetCapabilities Now would be 500 internal server error. Reason would be that " has no attribute field_name"

This is because FeatureType.get_bounding_box function uses self.get_query_set() that does not check any feature relations.

Suggested fix: Change function FeatureType.get_bounding_box not to use get_query_set() as such but add a .only(self.geometry_field.name)

so line: bbox = self.get_queryset().aggregate(a=Extent(geo_expression))["a"] to: bbox = self.get_queryset().only(self.geometry_field.name).aggregate(a=Extent(geo_expression))["a"] or even: bbox = self.queryset.only(self.geometry_field.name).aggregate(a=Extent(geo_expression))["a"]

I am not so familiar with the codebase that really not sure if this is the way to go here, maybe someone who actually is doing dev on this will do the actual fix in a different way. Atleast this way there would be no need for any prefetches.

sposs commented 5 months ago

Actually, the issue is a little more profound: the bind method of FeatureField makes a mistake I think. It puts in the self.model_field the related field directly, losing the fact that it's from a related model. Then in _local_model_field_names, the name of the field is added to the list, because it's not a related field as it's the actual related model's field, not the relation field. I don't think there is a way currently to fix this issue properly, except by adding a new attribute to FeatureField, like 'related' and exclude that from the _local_model_field_names.

Your fix solves the problem, but only temporarily.