2015-02-11 1 views
0

Я хочу использовать ту же модель URL-адреса, что и SO. Поиск выполняется по номеру идентификатора, но если неправильный слизень находится в ссылке, а перенаправление выбрано на правильную страницу.Перенаправить URL-адрес, если slug не соответствует

пример: вопросы/4787731/все будет перенаправлено на вопросы/4787731/canonical-links-and-301-redirect-if-url-doesnt-match-slug. Мой текущий код выполняет поиск по идентификатору, но не перенаправляет его в случае плохой пули. пример: сущ./12786676/все, что нужно перенаправить в/сущ./12786676/yellow-and-green-tree /. Я правильно понимаю содержимое страницы, но хочу, чтобы URL-адрес перенаправлялся, чтобы избежать плохих ссылок. Вот код:

просмотров:

class EntityRedirectDetailView(RedirectView): 
    def get(self, request, *args, **kwargs): 
     pk = self.kwargs.get('pk', None) 
     slug=self.kwargs.get('slug', None) 
     entity = EntitiesNew.objects.get(pk=pk) 
     self.url = '/entities/%s/%s' % (entity.pk, entity.slug) 
     return super(EntityRedirectDetailView, self).get(request, *args, **kwargs) 

URLs:

urlpatterns = [ 
    url(r'^$', ListView.as_view(context_object_name = 'entities_list', queryset=EntitiesNew.objects.order_by('-id_number')[:500]), name='entities'), 
    url(r'^(?P<pk>\d+)/$', views.EntityRedirectDetailView.as_view(), name='entities-redirect'), 
    url(r'^(?P<pk>\d+)(?:/(?P<slug>[\w\d-]+))?/$', DetailView.as_view(model=EntitiesNew, context_object_name="entity"), name="entities-detail"), 
] 

благодаря

+0

Ваш второй шаблон совпадает, если в URL-адресе есть только pk, потому что за ним следует '$', поэтому он никогда не будет соответствовать ни одному URL-адресу с помощью slug, правильно или нет. То, что вы можете сделать, это переопределить 'get' в DetailView третьего шаблона и перенаправить, когда пул неверен. –

+0

спасибо Пауло, вы правы, второй шаблон перенаправляет только совпадение pk, поэтому нет перенаправления, если слизняк неправильный ... можете ли вы показать мне, что именно вы имеете в виду, переопределив метод get? Я попытался с этим, но без успеха ... если slug! = Entity.slug(): return redirect (entity, constant = True) ... что-то не так с этим кодом? – Torostar

+0

Это общая идея, но вы вызываете 'entity.slug', который, я полагаю, является опечаткой. Вы также перенаправляетесь на 'entity', и у меня недостаточно информации, чтобы знать, правильно ли это. У вас есть метод get_absolute_url в этой модели? Вы также можете перенаправить на «entity-detail» и передать аргументы. –

ответ

0

Хорошо мне удалось сделать то, что я хотел, переопределив метод получить в моем EntityDetailView (Detailview) согласно предложению Paulo Almeida. Вот окончательный код.

urls.py:

url(r'^(?P<pk>\d+)/$', views.EntityRedirectDetailView.as_view(), name='entities-redirect'), 
    url(r'^(?P<pk>\d+)/(?P<slug>[-\w\d]+)/$', views.EntityDetailView.as_view(), name="entities-detail"), 

views.py

class EntityRedirectDetailView(RedirectView): 
    def get(self, request, *args, **kwargs): 
     pk = self.kwargs.get('pk', None) 
     slug=self.kwargs.get('slug', None) 
     entity = EntitiesNew.objects.get(pk=pk) 
     self.url = '/entities/%s/%s' % (entity.pk, entity.slug) 
     return super(EntityRedirectDetailView, self).get(request, *args, **kwargs) 

class EntityDetailView(generic.DetailView): 
    """ 
     A DetailView which redirects to the absolute_url, if necessary. 
    """ 
    template_name = 'entities/entitiesnew_detail.html' 
    queryset = EntitiesNew.objects.get_queryset() 
    def get_object(self, *args, **kwargs): 
     # Return any previously-cached object 
     pk = self.kwargs.get('pk', None) 
     entity=EntitiesNew.objects.get(pk=pk) 
     if getattr(self, 'entity', None): 
      return self.entity 
     return super(EntityDetailView, self).get_object(*args, **kwargs) 
    def get(self, *args, **kwargs): 
     # Make sure to use the canonical URL 
     self.entity = self.get_object() 
     obj_url = self.entity.get_absolute_url() 
     if self.request.path != obj_url: 
      return http.HttpResponsePermanentRedirect(obj_url) 
     return super(EntityDetailView, self).get(*args, **kwargs); 

в models.py У меня есть get_absoulte_url:

def get_absolute_url(self): 
     return reverse('entities:entities-detail', kwargs={'pk':self.pk, 'slug':self.slug}) 

и в шаблоне: {% URL «Объекты: сущности-детали» entitynew.pk entitiesnew.slug%}