2014-01-24 4 views
4

У меня две модели: поле и набор. И я хочу иметь гиперссылку на поля, которые составляют конкретный набор.
, например: URL: sets/ должен вернуть [{'title': 'dimensional', 'fieldsLink': '#url-to-enpoin'}]Django-Rest-Framework. Объекты гиперссылки через параметры запроса

Там нет ничего сложного, чтобы написать что-то вроде этого:

class Field(models.Model): 
    title = models.CharField(max_length=255, blank=True, null=True) 
    set = models.ForeignKey(Set, related_name='fields', blank=True, null=True) 

class Set(models.Model): 

    title = models.CharField(max_length=255, blank=True, null=True, unique=True) 
    slug = models.SlugField(unique=True) 


class SetSerializer(serializers.HyperlinkedModelSerializer): 
    field_list = serializers.HyperlinkedIdentityField(
     view_name='apiv1:setfields-list', 
     lookup_field='slug') 

    class Meta: 
     model = Set 
     fields = ('title', 'field_list') 

urlpatterns = patterns('', 
    url(r'^fields/$', views.FieldView.as_view(), name='fields-list'), 
    url(r'^sets/$', views.SetView.as_view(), name='sets-list'), 
    url(r'^sets/(?P<slug>[\d\w\-]+)/fields/$', views.SetFieldView.as_view(), name='setfields-list'), # this url should be removed 
) 

Но как я могу гиперссылку установить на поля через URL, как fields/?set=dimensional (запрос параметр) вместо sets/dimensional/fields/ (аргумент в url)?

Есть ли встроенный способ сделать это вместо переопределения HyperlinkedIdentityField?

+0

Там нет построен в пути, насколько я знаю, я использую подобные решения в своем коде – nemesisdesign

ответ

4

Вы можете сделать это двумя различными способами: с помощью настраиваемого HyperlinkedRelatedField или настраиваемого метода в вызываемом сериализаторе.

@kharandziuk при условии, что пользовательские поля первоначально в вопросе.

class CustomHyperlinkedIdentityField(HyperlinkedIdentityField): 

    def get_url(self, obj, view_name, request, format): 
     from rest_framework.reverse import reverse 
     lookup_field_value = getattr(obj, self.lookup_field, None) 
     result = '{}?{}'.format(
      reverse(view_name, kwargs={}, request=request, format=format), 
      urllib.urlencode({self.lookup_field: lookup_field_value}) 
     ) 
     return result 

Если вы не хотите, чтобы создать свое собственное поле, вы можете создать метод на вашем сериализаторе, который возвращает конкретный URL. Вы могли бы нужно использовать SerializerMethodField и метод на ваш сериализаторе аналогично

def get_the_url(self, obj): 
    return self.context["request"].build_absolute_url("/api/fields") + "?set=" + obj.title 
Смежные вопросы