В многопользовательском приложении необходимо проверить, принадлежит ли текущая запись в блоге зарегистрированному пользователю, и необходимо указать URL-адрес. - PullRequest
1 голос
/ 24 марта 2011

Предупреждение новичка: у меня есть следующий код.Мой блог-приложение является многопользовательским.Как только любой пользователь создает сообщение и посещает его / ее профиль, он должен видеть только свое сообщение, что очень просто.

post_id - это первичный ключ модели Post, который увеличивается сам по себе.Проблема с многопользовательским приложением состоит в том, что пользователи могут попытаться поместить /<post_id>/ того, что им не принадлежит.Я пытаюсь уловить эту проблему здесь.Через некоторое время им станет очевидно, что их post_id не увеличиваются, а некоторые «отсутствуют», потому что они принадлежат кому-то другому.

  • Это хорошая идея показать ПКсообщения в URL, чтобы захватить его и проверить в представлении edit_post, принадлежит ли оно пользователю?
  • Есть ли лучшее предложение, чем показ первичного ключа в URL?
  • Как еще можно получить текущий post_id, если его нет в URL, и я считаю, что мне нужно post_id, чтобы получить текущее сообщение, которое пользователь хочет отредактировать.

urls.py

(r'^create/$', create_post),
(r'^post/(?P<post_id>\d+)/edit/$', edit_post),

models.py:

class Post (models.Model): 
    name = models.CharField(max_length=1000, help_text="required, name of the post") 
    user = models.ForeignKey(User, unique=False, help_text="user this post belongs to") 

    def __unicode__(self): 
        return self.name 

class PostForm(ModelForm): 
    class Meta: 
            model = Post 

views.py

#----------------------------View-------------------------------------- 
@login_required 
def create_post (request): 
    if request.method == 'POST': 
        post_form = PostForm(request.POST) 
        if post_form.is_valid(): 
            post.save() 
            return render_to_response('home.html') 
        else: 
            return HttpResponse('not working') 
    else: 
        post_form = PostForm() 
        return render_to_response('create.html', {'post_form':post_form })

@login_required 
def edit_post (request, post_id): 
    if request.method == 'POST': 
        post_form = PostForm(request.POST) 
        """
        Stuff to check whether the 
        current logged in user owns 
        this post.
        like 
        if post_user = Post(pk=post_id).user:
            show the post here.
        """
       else: 
            return HttpResponse('not working') 
    else: 
        post_form = PostForm() 
        return render_to_response('create.html', {'post_form':post_form })\

Ответы [ 3 ]

3 голосов
/ 24 марта 2011

Это хорошая идея, чтобы показать pk сообщения в URL, чтобы захватить его и проверить в представлении edit_post, принадлежит ли он пользователю?

Вы обязательно должны проверитьправо собственности на сообщение в представлении редактирования.

Есть ли лучшее предложение, чем показ первичного ключа в URL-адресе?

Есть и другие варианты: например,идентификаторы на самом деле не должны быть уникальными - просто уникальными для каждого пользователя.Вы можете иметь идентификатор, который увеличивается для каждого пользователя, а не глобально.Лично я не знаю, стоит ли это хлопот.Я думаю, что использование первичного ключа - это нормально, если вы сделаете его безопасным, и вам все равно, смогут ли люди определить ваш объем, посмотрев на него.

Как еще можно получить текущий post_id, еслиего нет в url, и я считаю, что мне нужен post_id для получения текущего сообщения, которое пользователь хочет отредактировать.

Как я уже сказал, вы можете выполнить поиск другого столбца вместе с пользователем, иливы можете даже создать случайные идентификаторы (например, усеченный UUID) для каждого сообщения.

Для представления редактирования вы можете защитить его, просто выполнив что-то вроде:

from django.shortcuts import get_object_or_404

@login_required 
def edit_post (request, post_id):
    post = get_object_or_404(Post, pk=post_id, user=request.user)
...
1 голос
/ 25 сентября 2012

Ваш вариант использования просто идеален для Джанго-Страж . Этот пакет уже реализует разрешения для каждого объекта, и есть функция с именем get_objects_for_user, которая работает следующим образом:

from django.shortcuts import render_to_response
from django.template import RequestContext
from projects.models import Project
from guardian.shortcuts import get_objects_for_user

def user_dashboard(request, template_name='projects/dashboard.html'):
 projects = get_objects_for_user(request.user, 'projects.view_project')
 return render_to_response(template_name, {'projects': projects},
    RequestContext(request))

Как видите, пример - почти то, что вам нужно, но для постов.

1 голос
/ 24 марта 2011

в вашем views.py вы можете использовать что-то вроде:

@login_required 
def edit_post (request, post_id):
    post = None
    if post_id:
        post = get_object_or_404(Post, pk=post_id)
        if post.user != request.user:
            return HttpResponse("You can only edit your own posts")

    if request.method == 'POST': 
        post_form = PostForm(request.POST, instance=post) 
        if post_form.is_valid():
            post_form.save()
            return HttpResponse("Sucess")
    else: 
        post_form = PostForm(instance=post) 

    return render_to_response('edit.html', {'post_form':post_form })  
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...