web-dev-qa-db-ja.com

Djangoのオブジェクトを削除する

ミニブログアプリで、ブログの所有者が自分のエントリ(および自分のエントリのみ)を削除できるように、削除機能を作成したいと考えています。そうするための唯一の方法は、フォームを使用することだと思います。私の削除コードは明確で正しいようですが、機能しません。私のコード:

def delete_new(request,id):
   u = New.objects.get(pk=id).delete()
   if request.method == 'POST':
       form = DeleteNewForm(request.POST)    
       form.u.delete()             
       form.save()   
   return render_to_response('news/deleteNew.html', {
           'form': form,
           }, 
        context_instance=RequestContext(request)) 

テンプレートで:

<a href='/news/delete_new/{{object.id}}/'> Delete</a> <br /> 

これは正しいアプローチですか?つまり、このためのフォームを作成していますか?また、削除リンクに関連付けられたブログ投稿を取得する唯一の方法は、パラメーターとしてIDを持つことです。正しいですか?つまり、おそらくユーザーは別のIDをURLに入力して、別のエントリを削除することができます(最終的には自分のエントリではありません)

22
dana

一般に、オブジェクトを削除するには、POST(またはDELETE) HTTPメソッド を使用する必要があります。

例として本当にHTTP GETを使用したい場合は、次の修正が必要です。

あなたのようないくつかのURLを指しているURLがある場合:_<a href='/news/delete_new/{{object.id}}/'> Delete</a>_次に、すでに記述したコードのように、オブジェクトがログインしているユーザーに属しているかどうかをチェックし、はいの場合はこのエントリを削除するビューを書くだけです:

_def delete_new(request,id):
   #+some code to check if New belongs to logged in user
   u = New.objects.get(pk=id).delete()
_

新しいオブジェクトが一部のユーザーに嘆願するかどうかを確認するには、UserNewの間にリアレーションを作成する必要があります(Newモデルのcreated_by = models.ForeignKey(User)など)。

次の方法でユーザーをログインさせることができます:_request.user_

私はあなたのポイントが正しく得られたことを願っていますが、私の答えはどういうわけかあなたを助けます。

PS:テンプレートに直接URLを記述する代わりに、_{% url %}_タグの使用を検討することもできます。

20
dzida

フォームを使用する必要があるか、または CSRF攻撃 に対して脆弱です。また、リクエストがGETであるかPOSTであるかを確認する前に、モデルを削除しています。

単純なModelFormを作成します。

from Django import forms

from .models import New

class DeleteNewForm(forms.ModelForm):
    class Meta:
        model = New
        fields = []

同じDjangoアプリ内のviews.pyで:

from Django.shortcuts import render, get_object_or_404

from .forms import DeleteNewForm
from .models import New

def delete_new(request, new_id):
    new_to_delete = get_object_or_404(New, id=new_id)
    #+some code to check if this object belongs to the logged in user

    if request.method == 'POST':
        form = DeleteNewForm(request.POST, instance=new_to_delete)

        if form.is_valid(): # checks CSRF
            new_to_delete.delete()
            return HttpResponseRedirect("/") # wherever to go after deleting

    else:
        form = DeleteNewForm(instance=new_to_delete)

    template_vars = {'form': form}
    return render(request, 'news/deleteNew.html', template_vars)
32
Wilfred Hughes