web-dev-qa-db-fra.com

Comment définir ForeignKey dans CreateView?

J'ai un modèle:

class Article(models.Model):
    text = models.CharField()
    author = models.ForeignKey(User)

Comment écrire une vue basée sur une classe qui crée une nouvelle instance de modèle et définit la clé étrangère author sur request.user?

Mise à jour:

Solution déplacée pour séparer réponse ci-dessous.

44
Vlad T.

J'ai résolu ce problème en remplaçant form_valid méthode. Voici un style bavard pour clarifier les choses:

class CreateArticle(CreateView):
    model = Article

    def form_valid(self, form):
        article = form.save(commit=False)
        article.author = self.request.user
        #article.save()  # This is redundant, see comments.
        return super(CreateArticle, self).form_valid(form)

Pourtant, nous pouvons faire court (merci dowjones123), ce cas est mentionné dans les documents .:

class CreateArticle(CreateView):
    model = Article

    def form_valid(self, form):
        form.instance.author = self.request.user
        return super(CreateArticle, self).form_valid(form)
40
Vlad T.

Je suis juste tombé sur ce problème et ce fil m'a conduit dans la bonne direction (merci!). Basé sur this Django page de documentation , nous pouvons éviter d'appeler la méthode save() du formulaire du tout:

class CreateArticle(LoginRequiredMixin, CreateView):
    model = Article

    def form_valid(self, form):
        form.instance.author = self.request.user
        return super(CreateArticle, self).form_valid(form)
11
Carlos Mermingas

Le code de Berislav dans views.py ne fonctionne pas pour moi. Le formulaire est rendu comme prévu, avec la valeur utilisateur dans une entrée masquée, mais le formulaire n'est pas enregistré (je ne sais pas pourquoi). J'ai essayé une approche légèrement différente, qui fonctionne pour moi:

views.py

from Django.views.generic import *
from myapp.forms import ArticleForm
from myapp.models import Article

class NewArticleView(CreateView):
    model = Article
    form_class = ArticleForm
    def get_initial(self):
        return {
            "user": self.request.user
        }
2
jantoniomartin

Vous devez configurer un CreateView en utilisant un ModelForm pour ce modèle. Dans la définition de formulaire, vous définissez le ForeignKey pour avoir le widget HiddenInput, puis utilisez le get_form méthode sur la vue pour définir la valeur de votre utilisateur:

forms.py:

from Django import forms

class ArticleForm(forms.ModelForm):
    class Meta:
        model = Article
        widgets = {"user": forms.HiddenInput()}

views.py:

from Django.views.generic import *
from myapp.forms import ArticleForm
from myapp.models import Article

class NewArticleView(CreateView):
    model = Article
    form_class = ArticleForm
    def get_form(self, form_class):
        initials = {
            "user": self.request.user
        }
        form = form_class(initial=initials)
        return form
1
Berislav Lopac