Something is wrong with variables typeManyToManyField

0

For my project I have created in my project a new model called displacement, which will be related to the animal model by means of a variable type manytomanyfield :

class desplazamiento(models.Model):
    nombre=models.CharField(max_length=15)
    descripcion=models.CharField(max_length=150)
    foto=models.ImageField(null=True)
    def __str__(self):
        return self.nombre

class animal(models.Model):
    ncomun=models.CharField(max_length=50)
    ncientifico=models.CharField(max_length=50)
    foto=models.ImageField()
    categoria=models.ForeignKey(categoria,null=True)
    alimentacion=models.ForeignKey(alimentacion,null=True)
    desplazamiento=models.ManyToManyField(desplazamiento)
    def __str__(self):
        return self.ncomun

The next thing is that the form to make a new animal fits the new variable:

class nue_animal(forms.ModelForm):
    class Meta:
        model = animal
        fields = ('ncomun', 'ncientifico', 'foto', 'categoria', 'alimentacion', 'desplazamiento')

Code views.py :

def nuevo_animal(request):
    if request.method == "POST":
        form = nue_animal(request.POST, request.FILES)
        if form.is_valid():
            com = form.cleaned_data['ncomun']
            cie = form.cleaned_data['ncientifico']
            fot = form.cleaned_data['foto']
            cat = form.cleaned_data['categoria']
            ali = form.cleaned_data['alimentacion']
            des = form.cleaned_data['desplazamiento']
            an = animal(ncomun=com, ncientifico=cie, foto=fot, categoria=cat, alimentacion=ali, desplazamiento=des)
            an.save()
            return HttpResponseRedirect('/')
    else:
        form=nue_animal()
    return render(request,'bestias.html',{'forma':form})

So I can add the variable to the form, but when I give insertar , I get this:

  

needs to have a value for field "animal" before this many-to-many relationship can be used.

PS: The Jabali is the name ( ncomun ) of the new animal. On the contrary, if I insert the animal through the administrator, everything goes well.

    
asked by Miguel Alparez 17.05.2017 в 23:59
source

2 answers

3

The error is simple, but I recommend you always first look for the documentation of the software you use, here I'll leave you with ManyToManyFields .

The first thing is more a recommendation, when you use ModelForm in your forms, remember that they come a method called save with which you would not have to worry about the saved fields ManyToMany since it does it automatically , an example for your case would be to do the following:

form = nue_animal(request.POST, request.FILES)
if form.is_valid():
    animal = form.save()
    return HttpResponseRedirect('/')

And now, solved the problem, now, if you want to manipulate the instance with your own data and this model contains fields ManyToMany , then you would do so:

form = nue_animal(request.POST, request.FILES)
if form.is_valid():
    animal = form.save(commit=False)
    # hago algo con mi instancia
    animal.owner = request.user  # un ejemplo
    animal.save()
    form.save_m2m()  # importante esta linea para guardar los *ManyToManyFields*
return HttpResponseRedirect('/')

And another option is to continue as you are doing, create the instance manually, you just have to follow this order:

form = nue_animal(request.POST, request.FILES)
if form.is_valid():
    com = form.cleaned_data['ncomun']
    cie = form.cleaned_data['ncientifico']
    fot = form.cleaned_data['foto']
    cat = form.cleaned_data['categoria']
    ali = form.cleaned_data['alimentacion']
    des = form.cleaned_data['desplazamiento']
    an = animal(
       ncomun=com, ncientifico=cie, foto=fot,
       categoria=cat, alimentacion=ali
    )
    an.save()
    for desplazamiento in des:
        an.desplazamiento.add(desplazamiento)  # esta es la forma de agregar objetos manualmente a un ManyToMany
    return HttpResponseRedirect('/')

Any questions or doubts, comment, I hope I have helped you

    
answered by 18.05.2017 / 16:18
source
0

Good, you have the option to allow the displacement field to have null values, in the model it would be like this.

desplazamiento=models.ManyToManyField(desplazamiento, blank=True)
    
answered by 18.05.2017 в 11:50