django: raise an error similar to EmailField - django

When using an email field, attempting to submit a form with an invalid email address raises and error like this:
What I like about this:
doesn't reload the page, rather doesn't submit at all and instead displays an error
the look
Here is what I am able to accomplish currently with Name and Password (CharFields)
The "A name is needed!" and "This field is required" messages only display after the form is submitted, which is not as sleek as displaying without the form even needing to be submitted.

The popup that you see for the email it is not django validation. It is the build in in-browser html5 email field checking (and some older browsers will not do it for you).
And you can't get any kind of validation in html5, but for checking field presents you can add required attribute to the rendered input field.
There are several ways to add attibutes to widgets in django. take a look to the How do I get Django forms to show the html required attribute? and select appropriate for you.

kmmbvnr directed me to what I was looking for. To add the type of validation I was looking for, add code similar to that below:
class UserForm(forms.ModelForm):
...
username = forms.CharField(
widget=forms.TextInput(attrs={'required': 'true'}),#HERE
)
password = forms.CharField(
widget=forms.PasswordInput(attrs={'required': 'true'}),#OR HERE
)
...

Related

Django Emailfield fixed suffix

In my Contact model I use an EmailField to assure I'm saving a valid email address.
In my form however, I only want the user to be able to change the part before the #, the domain part is not user defined. (e.g. every email needs to end with #gmail.com)
I have looked at a lot of questions about modifying Django form field values before and after validation and display phase, but a lot of the answers are kind of 'hacky' or seem to much of a workaround for my case.
Is there some support of kind of a display filter, which manages a fixed prefix/suffix of a Django form field, without having to edit POST values or needing to suppress certain validations?
Use the clean method in your form to validate the email. It'll be something like this
def clean(self):
"""Check if valid email for institution."""
super().clean()
cleaned_data = self.cleaned_data
if not '#gmail.com' in cleaned_data['email']
msg = forms.ValidationError("Your email must be #gmail")
self.add_error('email', msg)

django - dynamic query on form field

Lets say I have a form with some fields. I was wondering if it is possible to do dynamic query where I could do a string match while the user is typing into a field. Like when typing into google it returns a list of choices when you type into the search bar. Can someone give me an example on how and where to implement it?
If what you're looking to achieve is fields for a ForeignKey then you can provide a Queryset on the form field then use an app like django_select2 which can then provide a widget which will allow a user to search for items in the Queryset for the field. e.g.
city = forms.ModelChoiceField(
queryset=City.objects.all(),
label=u"City",
widget=ModelSelect2Widget(
model=City,
search_fields=['name__icontains'],
dependent_fields={'country': 'country'},
max_results=500,
)
)
Then in the form, as you started to type into the city field it'd start to search on City.name using an icontains lookup. The docs for this are here.
If that's not what you're looking for then you could just write some Javascript which detected input to a field, then sent an ajax request to a view with the contents of your field. That could then return a response which displayed content in the page related to the input.

django formset - dont submit a single form if a checkbox is not true?

I have a formset displayed as a table, and I do not want to validate any of the forms that do not have a specific checkbox ticked. However when the formset is submitted they are getting validated.
Do I need to handle this at the clean_field() method level?
If so how do I stop the form at that point, without rendering the whole formset invalid??
class HILISForm(forms.ModelForm):
summary = forms.CharField(
widget=forms.Textarea(attrs={'rows':3, 'cols':70}),
label='',
required=False)
class Meta:
model = Report
fields = ('reported', 'summary', )
def clean_reported(self):
reported = self.cleaned_data['hilis']
if reported:
return(hilis_reported)
else:
raise(forms.ValidationError('Not checked...'))
if I 'pass' instead of raising the error- then this form still appears in my cleaned_dict which I do not want.
I'm sure there is a much easier and cleaner way to do it, but if you get stuck you could do it by creating an id for each input field, and then creating/saving the object with your logic in the view instead. It looks like you have a lot of things to check and wouldn't be ideal, but is one way to do it.
I had a tricky validation scheme for one of my projects and found it easier to just create the form, and then process it in the view on post. You can still add error messages to the form and do all of that from the view also.

Pre-populate password field in Django?

Is there a way to pre-populate a Django form password field so that it display something in the resulting <input type="password"> html element?
The default behavior seems to be not to display anything when the MyForm(initial = {'passfield':'something'}) is set.
I need this in order to implement an user edit form. I want to display a random string which if the user doesn't modify I will know that he does not want to change the password. So I don't think there is ANY security issue in what I'm trying to do.
It seems that using the render_value argument works not just for the case listed in the Django docs and can be used:
class MyForm(forms.Form):
password_field = forms.CharField(widget = forms.PasswordInput(render_value = True))
According to the docs, Django PasswordField does not support initial value. So even when you pass it, it would not render.
You can either subclass the field and make your own password widget which will allow you to do so or you can use HTML5 placeholder. HTML5 is much more secure bevause you can display something to the user, but not the password itself.
For HTML5 support, you can use https://github.com/adamcupial/django-html5-forms. Then you can do something like (not exact syntax but something along the lines of):
class FooForm(forms.Form):
...
password = forms.PasswordField(..., placeholder="Your password here")
I came across similar situation and I did the following:
class UserForm(forms.ModelForm):
password1 = PasswordField(label="Password")
In the PasswordField there is PasswordInput field you will need to set render_value = True as mentioned above which is by default False, then during initialization of UserForm I passed initial value for password.
UserForm(instance=user, initial={'password1': settings.dummy_password})
Now this initial value was predefined in settings file which I compare if the password is changed then update the password else leave the original as is.

Replace "this field is required" message in django admin

is there a way to replace the default error message in django admin. I'm using custom widget so I have the form and I was wondering is there something like:
field_1 = forms.Charfield(widget=X, error_messge='y')
I already tried to add claen_field_1 method but it looks that it is not called when the field is empty. Any ideas will be appreciated
yes there is and actually this is forms functionality and not admin functionality ;), you can use this anywhere.
field_1 = forms.Charfield(widget=X, error_messages={'required': 'y'})
for more information see the django docs