Required field modification if checkbox is selected in Django

0

I need to check if a "checkbox" button, called yes_no, was selected on my html page and change the "name" field to mandatory when this checkbox is triggered. My code is as follows:

In the models.py file:

from django.db import models

# Create your models here.


class RandomModel(models.Model):
    name = models.CharField(max_length=200)
    shirt_size = models.IntegerField()
    yes_no = models.BooleanField()

In the forms.py file:

from django import forms
from .models import RandomModel


class RandomForm(forms.ModelForm):
    name = forms.CharField(required=False)

    class Meta:
        model = RandomModel
        fields = ['name', 'shirt_size', 'yes_no']

In the views.py file:

from django.shortcuts import render
from .forms import *
from django.shortcuts import redirect

# Create your views here.


def random_view(request):
    if request.method == 'POST':
        form = RandomForm(request.POST)
        if form.is_valid():
            form.save()
            return redirect('learn:random')

    else:
        form = RandomForm()
    return render(request, 'learn/index.html', {'form': form})

In the index.html file:

{% load staticfiles %}
<form action="{% url 'learn:random' %}" method="post">
    {% csrf_token %}
    {{ form.name }}
    {{ form.shirt_size }}
    {{ form.yes_no }}
    <input type="submit" value="Enviar">
</form>
    
asked by anonymous 29.07.2018 / 15:34

3 answers

1

On your form, the name field is not mandatory, but your template will not be able to be saved with the blank name field, if you want to allow this, set it in the name field of your% / p>

When you inherit from blank=True or forms.Form as it is in your case, this allows you to define some methods on your form that will do a validation let's say forms.ModelForm than those "personalizada" already does in the defined fields, as if the entry is valid or its size.

To do this, simply define methods on your form with the following signature:

def clean_<field_name>(self):
    field = self.cleaned_data['<field_name'>]
    ... # Faça aqui sua validações
    return field

Where Django is the field name of your form, you have a few steps to follow in your validation that is to get the field you want to validate, validate it in case of failure raise a <field_name> exception in case of In this case, you want to check if the forms.ValidationError field is selected, the name field becomes mandatory soon we can do something like this. :

from django import forms
from .models import RandomModel


class RandomForm(forms.ModelForm):

    name = forms.CharField(required=False)

    def clean_yes_no(self):
        yes_no = self.cleaned_data['yes_no']
        if yes_no:
            if not self.cleaned_data['name']:
                raise forms.ValidationError('O campo nome é obrigatório')
        return yes_no

    class Meta:
        model = RandomModel
        fields = ['name', 'shirt_size', 'yes_no']

Basic form template example:

<form action="{% learn:random %}" method="post" novalidate>{% csrf_token %}
    {% for error in form.non_field_errors %}
        <div>
            {{ error }}
        </div>
    {% endfor %}
    {% for field in form %}
        {% for error in field.errors %}
            <div>
                {{ error }}
            </div>
        {% endfor %}
        <div>
            {{ field.label_tag }}
            {{ field }}
        </div>
    {% endfor %}
</form> 
    
29.07.2018 / 18:19
0

Now I have the following forms.py file:

class SellsForm(forms.ModelForm):
    client = forms.CharField(widget=forms.TextInput(
        attrs={'type': 'hidden'}))
    yn_choices = (('Sim', 'Sim'),
                  ('Não, emissão fiscal sem ERP', 'Não, emissão ERP'))
    yn = forms.CharField(widget=forms.RadioSelect(choices=required=False)

def clean_b2c_active(self):
    b2c_active = self.cleaned_data['b2c_active']
    b2c_platform = self.cleaned_data['b2c_platform']
    print(b2c_platform)
    if b2c_active:
        if not b2c_platform:
            raise forms.ValidationError('O campo é obrigatório')
    return b2c_active

class Meta:
    model = Sells
    fields = '__all__'

def __init__(self, *args, **kwargs):
    super(SellsForm, self).__init__(*args, **kwargs)
    self.fields['b2c_platform'].required = False
    self.fields['b2b_platform'].required = False
    self.fields['b2b_platform2'].required = False
    self.fields['market_platform_1'].required = False
    self.fields['market_platform_2'].required = False

With the associated error:

KeyError at /profile/config
'b2c_active'
Request Method: POST
Request URL:    http://192.168.25.192:8000/profile/config
Django Version: 2.0.7
Exception Type: KeyError
Exception Value:    
'b2c_active'
Exception Location: C:\Users\checkstore\Desktop\Checkstore\Clientes\forms.py 
in 
clean, line 62
Python Executable:  C:\Python36\python.exe
Python Version: 3.6.5
Python Path:    
['C:\Users\checkstore\Desktop\Checkstore',
 'C:\Users\checkstore\Desktop\Checkstore',
 'C:\Python36\python36.zip',
 'C:\Python36\DLLs',
 'C:\Python36\lib',
 'C:\Python36',
 'C:\Users\checkstore\AppData\Roaming\Python\Python36\site-packages',
 'C:\Python36\lib\site-packages',
 'c:\users\checkstore\src\django-extra-views',
 'C:\Program Files\JetBrains\PyCharm '
 '2018.1.4\helpers\pycharm_matplotlib_backend']
Server time:    Seg, 30 Jul 2018 17:06:07 +0000
    
30.07.2018 / 19:12
0

The views.py file looks like this:

def config_view(request):
    if request.method == "POST":
        form = SellsForm(request.POST, initial={'client': request.user.username})
        if form.is_valid():
            form.save()
            return redirect('/profile')
    else:
        form = SellsForm(initial={'client': request.user.username})
    return render(request, 'Clientes/config.html', {'form': form})
    
30.07.2018 / 20:33