Как фильтровать результаты API связанным атрибутом модели с помощью Tastypie?

Учитывая следующее определение API, я должен иметь возможность фильтровать события по псевдониму продукта.

Учитывая, что событие принадлежит заданию и заданию принадлежит к продукту, я не уверен, как это специфицировать.

api.py:

class ProductResource(ModelResource):
 class Meta:
 queryset = Product.objects.all()
 resource_name = 'product'
 allowed_methods = ['get']
 excludes = ['created_at','updated_at']
 filtering = {
 'alias': ALL
 }
class EnvironmentResource(ModelResource):
 class Meta:
 queryset = Environment.objects.all()
 resource_name = 'environment'
 allowed_methods = ['get']
 excludes = ['created_at','updated_at']
class JobResource(ModelResource):
 product = fields.ForeignKey(ProductResource, 'product')
 class Meta:
 queryset = Job.objects.all()
 resource_name = 'job'
 allowed_methods = ['get']
 excludes = ['created_at','updated_at']
class EventResource(ModelResource):
 environment = fields.ForeignKey(EnvironmentResource, 'environment',full=True)
 job = fields.ForeignKey(JobResource, 'job',full=True)
 class Meta:
 queryset = Event.objects.all()
 resource_name = 'event'
 allowed_methods = ['get']
 excludes = ['created_at','updated_at']
 filtering = {
 HOW DO I FILTER BY PRODUCT ALIAS????
 }
2 ответа

Учитывая следующие характеристики фильтрации:

# In EventResource
filtering = { 
 'job' : ALL_WITH_RELATIONS
}
# In JobResource
filtering = { 
 'product' : ALL_WITH_RELATIONS
}
# In ProductResource
filtering = {
 'alias' : ALL
}

Вы должны уметь:

/api/events/job__product__alias=something


Простым способом достижения этого является Расширенная фильтрация. Это позволяет избежать многих запросов, генерируемых полями tastypie ForeignKey. Для обеспечения безопасности не забудьте вручную проверить или очистить входные данные фильтра, прежде чем добавлять данные в orm_filters.

class EventResource(ModelResource):
 class Meta:
 queryset = Event.objects.all()
 resource_name = 'event'
 allowed_methods = ['get']
 def build_filters(self, filters=None):
 if filters is None:
 filters = {}
 orm_filters = super(EventResource, self).build_filters(filters)
 # Your filtering
 if 'job__product__alias' in filters:
 orm_filters['job__product__alias'] = filters.get(
 'job__product__alias')
 return orm_filters

Им вы сможете получить отфильтрованные результаты:

/api/events/?job__product__alias=something

licensed under cc by-sa 3.0 with attribution.