Внешний ключ POST в Django - PullRequest
       4

Внешний ключ POST в Django

1 голос
/ 15 февраля 2020

У меня проблемы с приложением. Мне нужно сделать задачу с отношениями к пользователю.

Вот мой код:

ошибка

 ValueError at /
Cannot assign "(<SimpleLazyObject: <function AuthenticationMiddleware.process_request.<locals>.<lambda> at 0x04C54E38>>,)": "Task.usertask" must be a "UserMembership" instance.

models.py

class UserMembership(models.Model):
    user = models.OneToOneField(settings.AUTH_USER_MODEL, on_delete=models.PROTECT, null=True,blank=True)
    image=models.FileField(upload_to='photos/%Y/%m/%d/',null=True,blank=True)


class Task(models.Model):
    title=models.CharField(max_length=200)
    date = models.DateTimeField(default=datetime.now,blank=True)
    is_published=models.BooleanField(default=True)
    usertask=models.ForeignKey(UserMembership, on_delete=models.PROTECT, null=True, blank=True)

views.py

if request.method == 'POST':
    usertask = request.user,
    title = request.POST['title']
    task = Task(usertask=usertask,title=title)
    task.save()

task = Task.objects.order_by('-date').filter(is_published=True, usertask=request.user.id)

context={
    'task':task,
}
return render(request,'index.html',context)

html форма

<form action="" method="POST">
{% csrf_token %}

    <input name="title" type="text" class="form-control" id="usr">

<button type="submit" class="btn btn-primary">add</button>

Ответы [ 3 ]

2 голосов
/ 15 февраля 2020

Поле usertask вашей модели задачи, связанное с моделью UserMembership как ForeignKey. Поэтому вы должны предоставить объект UserMembership для создания объекта Task. Вы задали request.user как usertask, но request.user не является объектом UserMembership. Вы должны найти объект UserMembership раньше. Вы можете использовать следующий код:

user_member_ship = UserMemberShip.objects.get(user=request.user)
Task.objects.create(title=title,usertask=user_member_ship)
1 голос
/ 15 февраля 2020

Как говорит ошибка, ваше поле usertask вашей модели Task относится к UserMembership, а не к User объекту.

Вы можете использовать .get_or_create() [Django -doc] для извлечения или создания такого объекта, если он еще не существует. Например:

def myview(request):
    if request.method == 'POST':
        <b>usertask, __</b> = UserMembership.objects.get_or_create(
            user=request.user
        )
        title = request.POST['title']
        task = Task.objects.create(usertask=usertask, title=title)
    task = Task.objects.order_by('-date').filter(
        is_published=True,
        <b>usertask__user=request.user</b>
    )
    context={
        'task':task,
    }
    return render(request,'index.html',context)

Вам необходимо выполнить фильтрацию по usertask__user=request.user, поскольку снова usertask будет извлекать объект UserMembership, а не объект User.

I Настоятельно советуем работать с формами [Django -doc] и не пытаться обработать request.POST querydictionary самостоятельно. Например, возможно, что запрос POST не содержит какое-либо значение для title, что может вызвать ошибки. Форма справится с этим более элегантно.

1 голос
/ 15 февраля 2020

Несколько вещей:

1) в функции просмотра вы делаете это: usertask = request.user. Обратите внимание, что request.user вернет объект User.

2) Затем вы попытаетесь создать объект Task, выполнив это task = Task(usertask=usertask,title=title), но здесь вы установили usertask в User объект, когда вам действительно нужен UserMembership объект

Вы можете попробовать переписать свою функцию вида следующим образом:

def MyViewFunction(request):

    # unpack request:
    user = request.user
    title = request.POST['title']

    # create new UserMembership object:
    user_membership = UserMembership.objects.create(user=user)
    user_membership.save()

    # create new Task object:
    task = Task.objects.create(usetask=user_membership, title=title)
    task.save()

    # continue code here...
...