首先你应该重新考虑你真的想要像 Tastypie 那样的 RESTful 类型的 API。因为拥有这种类型的接口是超级通用的,可以轻松快速地将您的数据公开给某些前端客户端,但需要您遵守不适合您当前问题的规则。
如果我理解正确,您只想为这个计算构建一个 API 端点。如果是的话,这不是您使用 RESTful 类型 API 的情况。
我建议你构建简单的 JSON 视图:
@csrf_exempt
def calculate_distance(request):
# Pass data in various ways
latitude = request.GET.get('latitude') or request.POST.get('latitude')
longitude = request.GET.get('longitude') or request.POST.get('longitude')
# Or pass data as JSON in request body
if request.method != 'POST':
return HttpResponseNotAllowed(permitted_methods=('POST',))
try:
data = json.loads(request.body)
except (AttributeError, ValueError):
return HttpResponseBadRequest(json.dumps({'message': 'json format incorrect'}),
content_type='application/json')
if data.get('latitude', None) and data.get('longitude', None):
within_range = []
for location in Location.objects.all():
distance_to_model = location.calculate_distance(data['latitude'], data['longitude'])
if distance_to_model <= 80:
within_range.append(location.name)
return HttpResponse(json.dumps({'success': True,
'within_range': within_range}),
content_type='application/json')
else:
return HttpResponseBadRequest(json.dumps({'message': 'offer_id is missing'}),
content_type='application/json')
您可以通过更多验证、授权、身份验证等来升级此视图。
已编辑:
但是,如果您出于某些原因决定坚持使用 Tastypie,请在模型资源类中使用 build_filters 方法:
def build_filters(self, filters=None):
if filters is None:
filters = {}
orm_filters = super(OfferResource, self).build_filters(filters)
if 'pk__in' not in orm_filters:
orm_filters['pk__in'] = []
if 'latitude' in filters and 'longitude' in filters:
for entity in Example.objects.all():
distance_to_model = entity.calculate_distance(
filters['latitude'], filters['longitude'])
if distance_to_model <= 80:
orm_filters['pk__in'].append(entity.pk)
return orm_filters
现在可以请求您的资源 ?latitude=xxx&longitude=yyyy。请记住,过滤器传递的值始终是字符串。确保 calculate_distance 可以处理它们。