Django is not updating my database after submitting my form - python

I have created a model and a form, both are working correctly, and I have added data to the database using the admin module
models.py
class Client(models.Model):
firstname = models.CharField(blank=True, max_length=30)
lastname = models.CharField(blank=True, max_length=15)
company = models.ForeignKey(Company, on_delete=models.CASCADE, default="company")
position = models.CharField(blank=True, max_length=15)
country = CountryField(blank_label='(select country)')
email = models.EmailField(blank=True, max_length=100, default="this_is#n_example.com")
created_at = models.DateTimeField(auto_now_add=True)
updated_at = models.DateTimeField(auto_now=True)
phone = PhoneField(default="(XX)-XXX-XXX")
def __str__(self):
return f'{self.firstname}'
forms.py
class ClientForm(forms.ModelForm):
class Meta:
model = Client
fields = ('firstname', 'lastname',"position",'country','email','phone')
views.py
#login_required
def add_client(request):
if request.method == "POST":
client_form = ClientForm(instance=request.user, data=request.POST)
if client_form.is_valid():
client_form.save()
messages.success(request, 'You have successfully added a client')
else:
messages.success(request, "Error Updating your form")
else:
client_form = ClientForm(instance=request.user)
return render(request,
"account/add_client.html",
{'client_form':client_form})
add_client.html
{% extends "base.html" %}
{% block title %}Client Information {% endblock %}
{% block content %}
<h1> Client Form</h1>
<p>Please use the form below to add a new client to the database:</p>
<form method="post" enctype="multipart/form-data">
{{ client_form.as_p }}
{% csrf_token %}
<p><input type="submit" value="Save changes"></p>
</form>
{% endblock %}
Everything seems to be working fine, I can submit data in the website and I get a message stating that the the submission when fine, however, when I check the admin website and inspect the database, I can't see the new data added, essentially the form is not submitting data and I don't get an error
[10/Jul/2021 18:36:24] "GET /account/add_client/ HTTP/1.1" 200 12385
[10/Jul/2021 18:36:36] "POST /account/add_client/ HTTP/1.1" 200 12616
Does anyone knows what am I doing wrong?

I notice my mistake is in the form, I should have not use the request.user in the instance, the #login_required is enough informtion.
Please see amended code:
#login_required
def add_client(request):
if request.method == "POST":
client_form = ClientForm(request.POST)
if client_form.is_valid():
client_form.save()
messages.success(request, 'You have successfully added a client')
return HttpResponseRedirect(reverse('add_client'))
else:
messages.error(request, "Error Updating your form")
else:
client_form = ClientForm()
return render(request,
"account/add_client.html",
{'client_form':client_form})

Related

image not saved while updating userprofile in django

I am trying to update a userprofile model that i used to save additional information over the inbuilt User model, now when i am trying to update it , the image does not gets saved. I need help to resolve this issue
# In views.py
#login_required(login_url=LOGIN_REDIRECT_URL)
def update_user_profile(request):
userobj = get_object_or_404(UserProfile, user=request.user)
form = UserProfileForm(data = request.POST or None,files= request.FILES or None, instance=userobj)
if request.method=='POST':
print(form.is_valid())
if form.is_valid():
profile = form.save(commit=False)
profile.picture = form.cleaned_data['picture']
profile.about = form.cleaned_data['about']
profile.save()
else:
print("NO picure")
return HttpResponseRedirect("/blog/profile/")
return render(request, "blog/post_update.html", {'form':form})
#models.py
class UserProfile(models.Model):
user = models.OneToOneField(User, on_delete=models.CASCADE)
about = models.CharField(max_length=200, null=True, blank=True)
picture = models.ImageField(upload_to="profile_images/", blank=True)
def __str__(self):
return str(self.user)
#In forms.py
class UserProfileForm(forms.ModelForm):
def __init__(self, *args, **kwargs):
super(UserProfileForm, self).__init__(*args, **kwargs)
self.fields['about'].widget.attrs.update({'class': 'form-control '})
self.fields['picture'].widget.attrs.update({'class': 'form-control-file'})
class Meta:
model = UserProfile
fields = ('about', 'picture')
# userprofileform.html
{% extends 'base.html' %}
{% block content %}
<form method="POST" enctype="multipart/form-data">
{% csrf_token %}
{{ form.as_p }}
<input type="submit" class="btn btn-primary" value="Create Profile">
</form>
{% endblock %}
please take a look at the code and help. while registering if the image was uploaded it get's saved , but when i try to update the userprofile directly in profile section image does not get changed and shows the same as one saved while user registration else it shows None.
I did some changes on templates in settings.py and got my project runnning. Issue was that i was not mentioning the Templates directory properly

Django ModelForm not saving data to database, Form.save is not working?

List item
Hello I am django beginner having tough time could someone please help me I don't know what am I doing wrong ?
I am trying to create a form and saving some data through it by using form.save(). And I am new to here also so don't mind any mistakes.
Here is my model:
from django.db import models
from stores.models import Store
class Category(models.Model):
id = models.AutoField(primary_key=True)
name = models.CharField(max_length=30)
def __str__(self):
return self.name
class Product(models.Model):
id = models.AutoField(primary_key=True)
name = models.CharField(max_length=30)
price = models.DecimalField(max_digits=5, decimal_places=5)
image = models.ImageField(upload_to='upload_to/')
category = models.ForeignKey(Category, default='Default', on_delete=models.CASCADE, blank=False, null=False)
store = models.ForeignKey(Store, on_delete=models.CASCADE, blank=False, null=False)
Here is my view:
from django.shortcuts import render, redirect
from .forms import NewPro
def pro(request):
if request.method == 'POST':
form = NewPro(request.POST)
if form.is_valid():
form.save()
return redirect('stores_list')
else:
form = NewPro()
return render(request, "default/add_product.html", {'form': form})
def product_list(request):
return render(request, 'default/product_list.html')
Here is my form:
from django import forms
from .models import Product
class NewPro(forms.ModelForm):
class Meta:
model = Product
fields = ('name', 'price', 'image','category', 'store',)
default/add_product.html :
{% extends 'default/base.html' %}
<html>
<head><title>E-Commerce App</title></head>
{% block content %}
<h1>Add Product details</h1>
<form method="post">
{% csrf_token %}
{{ form.as_p }}
<button type="submit">Add Product</button>
</form>{% endblock %}
</html>
Settings.py settings
MEDIA_ROOT = '/home/saifi/Saif_project/final_project/MEDIA_ROOT/upload_to'
I can see some indentation issues in the view - but I'll guess that's just formatting when copying into Stackoverflow.
the form.is_valid() check will validate all your form fields and will only write to the database if all the input fields are valid. If it's not saving, the first place I'd check would be for form errors.
In your template you can render the errors with {{form.errors}} and it will list each field and error.
You forgot request.FILES in your pro view function, you have an image file after all.
def pro(request):
if request.method == 'POST':
form = NewPro(request.POST, request.FILES)
if form.is_valid():
form.save()
return redirect('stores_list')
else:
form = NewPro()
return render(request, "default/add_product.html", {'form': form})
Try using the form this way:
<form action="YOUR_URL_HERE" method="post" enctype="multipart/form-data">
{% csrf_token %}
{{ form.as_p }}
<button type="submit">Add Product</button>
</form>
I hope this will help. Welcome aboard ;)
Your indentation is wrong, the else should be for first 'if'
def pro(request):
form = NewPro()
if request.method == 'POST':
form = NewPro(request.POST)
if form.is_valid():
form.save()
return redirect('stores_list')
else:
form = NewPro()
return render(request, "default/add_product.html", {'form': form})

Django - Tango With Django upload picture

I'm on chapter 9 in Tango With Django - creating user authentication. In the registration page I have the option of uploading a picture. In my admin file everything looks good after I register myself. I show up in the User Profiles, and it even shows the image I uploaded:
Picture: Currently: profile_images/earth.jpeg Clear. However when I click on that picture this is the error message I get:
Page not found (404)
Request Method: GET
Request URL: http://localhost:8000/admin/rango/userprofile/1/change/profile_images/earth.jpeg/change/
Raised by: django.contrib.admin.options.change_view
user profile object with primary key u'1/change/profile_images/earth.jpeg' does not exist.
You're seeing this error because you have DEBUG = True in your Django settings file. Change that to False, and Django will display a standard 404 page.
models.py:
from __future__ import unicode_literals
from django.db import models
from django.template.defaultfilters import slugify
from django.contrib.auth.models import User
class Category(models.Model):
name = models.CharField(max_length=128, unique=True)
views = models.IntegerField(default=0)
likes = models.IntegerField(default=0)
slug = models.SlugField(unique=True)
def save(self, *args, **kwargs):
self.slug = slugify(self.name)
super(Category, self).save(*args, **kwargs)
class Meta:
verbose_name_plural = 'categories'
def __str__(self):
return self.name
class Page(models.Model):
category = models.ForeignKey(Category)
title = models.CharField(max_length=128)
url = models.URLField()
views = models.IntegerField(default=0)
def __str__(self):
return self.title
class UserProfile(models.Model):
user = models.OneToOneField(User)
website = models.URLField(blank=True)
picture = models.ImageField(upload_to='profile_images', blank=True)
def __str__(self):
return self.user.username
views.py - only the register():
def register(request):
registered = False
if request.method == 'POST':
user_form = UserForm(data=request.POST)
profile_form = UserProfileForm(data=request.POST)
if user_form.is_valid() and profile_form.is_valid():
user = user_form.save()
user.set_password(user.password)
user.save()
profile = profile_form.save(commit=False)
profile.user = user
if 'picture' in request.FILES:
profile.picture = request.FILES['picture']
profile.save()
registered = True
else:
print user_form.errors, profile_form.errors
else:
user_form = UserForm()
profile_form = UserProfileForm()
return render(request, 'rango/register.html',
{'user_form': user_form,
'profile_form': profile_form,
'registered': registered}
)
finally, my register.html file:
{% extends 'rango/base.html' %}
{% load staticfiles %}
{% block title_block %}
Register
{% endblock %}
{% block body_block %}
<h1>Register with Rango</h1>
{% if registered %}
Rango says: <strong>thank you for registering!</strong>
Return to the homepage<br/>
{% else %}
Rango says: <strong>register here!</strong>
Click here to go to the homepage<br/>
<form id="user_form" method="post" action="/rango/register/" enctype="multipart/form-data">
{% csrf_token %}
{{ user_form.as_p }}
{{ profile_form.as_p }}
<input type="submit" name="submit" value="Register" />
</form>
{% endif %}
{% endblock %}
user profile object with primary key u'1/change/profile_images/earth.jpeg' does not exist.
It looks like one of your URL patterns may be off; it probably just wants to capture that 1 to use as the PK for a lookup, but instead is capturing 1/change/profile_images/earth.jpeg.

Validation Error Django Form

Hey so I set up a input form for users to share projects they are working on on a website I have been developing in Django 1.5, I created model, view and Form Model, to allow users who are logged in to add links to projects they are working on.
The Model works and when I enter a text through the admin panel it creates a new object, the views all seem to work, the form loads, and seems to take input however, the Project Name field keeps throwing me a invalid input error when I attempt to fill out the form, not sure why because I am inputing a string, and the field is designated as a CharField in both the Model, and Form Model.
Model:
class Project(models.Model):
creator = models.ForeignKey(User)
project_name = models.CharField(max_length=128)
website = models.URLField(blank=True)
github = models.URLField(blank=True)
description = models.CharField(max_length=255, unique=True)
likes = models.IntegerField(default=0)
def __unicode__(self):
return self.nam
View for adding a project:
#login_required
def add_project(request):
context = RequestContext(request)
if request.method == 'POST':
form = ProjectForm(request.POST)
if form.is_valid():
form.save(commit=False)
project.creator = request.user
project.save()
return index(request)
else:
print form.errors
else:
form = ProjectForm()
return render_to_response('rango/add_project.html', {'form' : form}, context)
The Form Model:
class ProjectForm(forms.ModelForm):
project_name = forms.CharField(max_length=128, help_text="What is the name of your project?")
website = forms.CharField(max_length=200, help_text="Enter the project website:")
github = forms.CharField(max_length=200, help_text="Enter the project github:")
description = forms.CharField(widget=forms.Textarea, help_text="Description:")
likes = forms.IntegerField(widget=forms.HiddenInput(), initial=0)
class Meta:
model = Project
exclude = ('creator')
def clean(self):
cleaned_data = self.cleaned_data
website = cleaned_data.get('website')
#If Url is not empty and dont start with 'http://' prepend 'http://'
if website and not website.startswith('http://'):
website = 'http://' + website
cleaned_data['website'] = website
return cleaned_data
def clean(self):
cleaned_data = self.cleaned_data
github = cleaned_data.get('github')
#If Url is not empty and dont start with 'http://' prepend 'http://'
if github and not github.startswith('http://'):
github = 'http://' + github
cleaned_data['github'] = github
return cleaned_data
and lastly the html template:
{% extends 'rango/base.html' %}
{% block title %} Add Project {% endblock %}
{% block body_block %}
<H1>Add a new Project</H1>
<form id="project_form" method="post" action="/rango/add_project/">
{% csrf_token %}
{% for hidden in form.hidden_fields %}
{{hidden}}
{% endfor %}
{% for field in form.visible_fields %}
{{field.errors}}
{{field.help_text}}
{{field}}
{% endfor %}
<input type="submit" name="submit" value="Create Project" />
</form>
{% endblock %}
The Page loads fine but when I attempt to submit i get this for project name:
Enter a valid value.
the value I entered was test for project name.
In the view function, I do not understand from where project comes from.
I would expect instead:
project = form.save(commit=False)
project.creator = request.user
project.save()

Django form saving issue AttributeError 'tuple' object has no attribute 'get'

I've been tried many different things to solve this issue and none seem to work.
Essentially I am just trying to create a registiration page which contains 2 forms built from 2 models, the User model and my restaurant model (profile model). Every time I submit my form, I keep getting AttributeError 'tuple' object has no attribute 'get'. I thought it may have been my cuisine many to many field causing the issue as its the only thing that is a tuple I think. So I tried removing the cuisine aspect altogether but that didn't work. Heres my code. I can provide additional information if necessary. Appreciate any help very much
Traceback - dpaste.com/2CXS7MZ
Additional Information
Request Method: POST
Request URL: http://127.0.0.1:8000/auth/register/
Django Version: 1.6.5
Exception Type: AttributeError
Exception Value:
'tuple' object has no attribute 'get'
Exception Location: C:\Python34\testapps\lib\site-packages\django\middleware\clickjacking.py in process_response, line 30
Python Executable: C:\Python34\testapps\Scripts\python.EXE
Python Version: 3.4.1
Models
class Cuisine(models.Model):
name = models.CharField(max_length=15, blank=False)
def __str__(self):
return self.name
#User Profile (The restaurant)
class Restaurant(models.Model):
#Main Test Field
name = models.CharField(max_length=25, blank=False)
user = models.OneToOneField(User)
cuisine = models.ManyToManyField(Cuisine, blank=True)
approved = models.BooleanField(default=False)
#Non Essential Fields
created_at = models.DateTimeField(auto_now_add=True)
updated_at = models.DateTimeField(auto_now=True)
def __str__(self):
return self.name
Forms
class UserSignUpForm(forms.ModelForm):
password = forms.CharField(widget=forms.PasswordInput())
class Meta:
model = User
fields = ('username', 'password', 'first_name', 'last_name', 'email',)
class RestaurantForm(forms.ModelForm):
cuisine = forms.ChoiceField(queryset=Cuisine.name.all())
name = forms.CharField(max_length=25)
class Meta:
model = Restaurant
exclude = ('user', 'approved',)
Views
def restaurant_register(request):
if request.user.is_authenticated():
return HttpResponse('Thank you for registering.')
if request.method == 'POST':
user_form = UserSignUpForm(request.POST)
restaurant_form = RestaurantForm(request.POST)
if user_form.is_valid() and restaurant_form.is_valid():
user = user_form.save()
user.set_password(user.password)
user.save()
profile = restaurant_form.save(commit=False)
profile.user = user
profile.save()
profile.save_m2m()
return render(request, '/auth/login.html')
else:
return user_form.errors, restaurant_form.errors
else:
user_form = UserSignUpForm()
restaurant_form = RestaurantForm()
return render(request, 'auth/register.html', {'restaurant_form':restaurant_form, 'user_form': user_form})
Template
{% extends "base.html" %}
{% block content %}
<form id="user_form" method="post" action="/auth/register/" enctype="multipart/form-data">
{{ user_form.errors }}
{{ restaurant_form.errors }}
{% csrf_token %}
{{ user_form.as_p }}
{{ restaurant_form.as_p }}
<input type="submit" name="submit" value="Register" />
</form>
{% endblock %}
URL
url(r'^register/$', views.restaurant_register, name='register'),
You are not returning a HttpResponse here:
return user_form.errors, restaurant_form.errors
return this instead:
render(request, 'auth/register.html', {'restaurant_form':restaurant_form, 'user_form': user_form})
or rather, you should skip that whole else and return.
Here is your problem:
return user_form.errors, restaurant_form.errors
You returning tuple instead of a response

Categories