I know that this question have been asked many times and I already checked many solutions but can not find an explanation to the weird behavior of saving form in this case
as in production saving image is working on my pc and not in my colleagues, in local as well it is working if I change the position of the form save (more below, if more up it does not work)
here the related forms to the template I am working with:
class ProfilePageTitleForm(ModelForm):
class Meta:
model = ProfilePage
fields = [
"title",
]
class ProfilePageDetailsForm(ModelForm):
intro = forms.CharField(
required=True,
widget=forms.Textarea(
attrs={
"class": "max-w-md w-full bg-gray-100 border border-gray-200 "
"rounded-lg text-base outline-none focus:border-blue-600 p-4"
}
),
label=_("Personal introduction"),
help_text=_("maximum number of characters: 80 characters"),
max_length=80,
)
class Meta:
model = ProfilePage
fields = [
"avatar",
"school",
"location",
"intro",
]
here they are separated as I used the title in another template separately
related views
#login_required
def profile_details(request: HttpRequest, pk: int = None) -> HttpResponse:
profile = ProfilePage.objects.get(pk=pk)
user = profile.user
titleprofilepage_form = ProfilePageTitleForm(instance=profile)
profilepage_form = ProfilePageDetailsForm(instance=profile)
if user == request.user or request.user.has_perm("userprofile.manager_permissions"):
if request.method == "POST":
profilepage_form = ProfilePageDetailsForm(
request.POST, request.FILES, instance=profile
)
titleprofilepage_form = ProfilePageTitleForm(request.POST, instance=profile)
if (
profilepage_form.is_valid()
and titleprofilepage_form.is_valid()
):
titleprofilepage_form.save()
profilepage_form.save()
return redirect(profile.get_full_url())
else:
messages.error(
request,
_("You have no permissions to edit this page"),
)
return redirect("/")
context = {
"user": user,
"profilepage_form": profilepage_form,
"titleprofilepage_form": titleprofilepage_form,
}
return render(request, "account/profile_details.html", context)
here if I put profilepage_form.save() in the line upper, the image do not save
the related template
{% extends "base.html" %}
{% load i18n wagtailcore_tags static %}
{% block content %}
<h1 class="text-3xl font-bold mt-7 mb-9 lg:mt-14">{% translate "edit profile" %}</h1>
<form action="" method="post" enctype="multipart/form-data" novalidate>
{# using novalidate to cancel the browser validation and use our form validations #}
{% csrf_token %}
<label for="id_avatar" class="block text-sm font-bold mb-2">
{% translate "profile picture" %}
<span class="pl-2 text-pink-repeat">*</span>
</label>
<div class="flex items-center w-68 overflow-hidden">
<div id="avatar_image" class="w-24 h-24 rounded-half bg-cover bg-center flex-shrink-0" style="background-image:url({{ user.get_user_avatar }})"></div>
<label for="id_avatar" class="flex items-center h-8 px-4 mx-6 text-xs bg-gray-200 rounded-full text-blue-400 cursor-pointer hover:bg-gray-400 flex-shrink-0 w-34 text-center">
{% translate "upload image" %}
</label>
{{ profilepage_form.avatar }}
{% if profilepage_form.avatar.errors %}
<div class="text-red-700 px-4 py-3" role="alert">
<strong>{{ profilepage_form.avatar.errors|escape }}</strong>
</div>
{% endif %}
</div>
<label for="id_title" class="block text-sm font-bold mb-2 mt-10">
{% translate "nick name" %}
<span class="pl-2 text-pink-repeat">*</span>
</label>
{{ titleprofilepage_form.title }}
{% if titleprofilepage_form.title.errors %}
<div class="text-red-700 px-4 py-3" role="alert">
<strong>{{ titleprofilepage_form.title.errors|escape }}</strong>
</div>
{% endif %}
<label for="id_location" class="block text-sm font-bold mb-2 mt-10">
{% translate "address" %}
</label>
{{ profilepage_form.location }}
{% if profilepage_form.location.errors %}
<div class="text-red-700 px-4 py-3" role="alert">
<strong>{{ profilepage_form.location.errors|escape }}</strong>
</div>
{% endif %}
<label for="id_school" class="block text-sm font-bold mb-2 mt-10">
{% translate "what you want to do" %}
</label>
{{ profilepage_form.school }}
{% if profilepage_form.school.errors %}
<div class="text-red-700 px-4 py-3" role="alert">
<strong>{{ profilepage_form.school.errors|escape }}</strong>
</div>
{% endif %}
<label for="id_intro" class="block text-sm font-bold mb-2 mt-10">
{% translate "self introduction" %}
<span class="pl-2 text-pink-repeat">*</span>
</label>
{{ profilepage_form.intro }}
{% if profilepage_form.intro.errors %}
<div class="text-red-700 px-4 py-3" role="alert">
<strong>{{ profilepage_form.intro.errors|escape }}</strong>
</div>
{% endif %}
<span class="helptext block text-sm mt-2">{% translate "Maximum number of characters : 80" %}</span>
<input type="submit" class="button mt-8 flex items-center justify-center text-sm font-bold shadow-md btn-goblue hover:bg-blue-499 active:bg-blue-800 active:shadow-none h-10 w-32 cursor-pointer" value="{% translate 'save' %}" data-button="load">
</form>
{% block footer %}
{% include "footer.html" %}
{% endblock %}
{% endblock %}
{% block extra_js %}
{{ block.super }}
<script type="text/javascript" src="{% static 'js/account_registration.js' %}"></script>
{% endblock %}
my questions are:
1- why changing the order between titleprofilepage_form.save() and profilepage_form.save() in views.py affects the behavior of saving picture (as written now in the file, it saves the image in local)
2- why I was able to save the image on local, in production on my computer but not in my colleague's computer (already cleaned cache)
New Update:
through the comment of Iain Shelvington was able to understand the importance of order as the title form is overriding the profilepage form and used a unique form for the same model
about the difference in production it is because using a user who has a different picture in the different village which is the problem in profile.user.get_user_avatar, I am closing this issue as it has been resolved
Related
I built a simple signup form that will take data as the user will click submit it and will save it in the database. But for some reason, I am able to validate it. I removed all the validations and added them again too. Not sure where I am missing?
it is not saving and giving the error Error Processing Your Request. which is in the else block of the code
Forms.py:
class RegisterForm(UserCreationForm):
email = forms.EmailField(max_length=100,help_text='Enter Email Address', required=True,widget=forms.TextInput(attrs={'class': 'form-control', 'placeholder': 'Email'}))
first_name = forms.CharField(max_length=100,help_text='Enter First Name', required=True,widget=forms.TextInput(attrs={'class': 'form-control', 'placeholder': 'First Name'}))
last_name = forms.CharField(max_length=100,help_text='Enter Last Name', required=True,widget=forms.TextInput(attrs={'class': 'form-control', 'placeholder': 'Last Name'}))
username = forms.CharField(max_length=100,help_text='Enter Username', required=True,widget=forms.TextInput(attrs={'class': 'form-control', 'placeholder': 'Username'}))
password = forms.CharField(max_length=200,help_text='Enter Password', required=True,widget=forms.PasswordInput(attrs={'class': 'form-control', 'placeholder': 'Password'}))
password2 = forms.CharField(max_length=200,help_text='Enter your Password again', required=True,widget=forms.PasswordInput(attrs={'class': 'form-control', 'placeholder': 'Password'}))
#check = forms.BooleanField(required = True)
class Meta:
model = User
fields = [
'username', 'email', 'first_name', 'last_name', 'password', 'password2' #, 'check'
]
Views.py:
def register(request):
if request.method == 'GET': #when you request a form it is in a get request
form = RegisterForm()
context = {'form' : form} #this creates a object which you want to send to the front end
return render(request, 'signup-login.html', context) # here we pushing that form to the html page
if request.method == 'POST': #when you submit a form it is POST request
form = RegisterForm(request.POST)
if form.is_valid():
form.save()
user = form.cleaned_data.get('username')
messages.success(request, 'Account was created for' + user)
return redirect('home_page')
else:
messages.error(request, 'Error Processing Your Request')
context = {'form' : form}
return render(request, 'signup-login.html', context)
return render(request, 'signup-login.html', {})
form HTML(added just the HTML part):
<form action="#" class="p-4 border rounded" method = 'POST'>
{% csrf_token %}
<div class="row form-group">
<div class="col-md-12 mb-3 mb-md-0">
<label class="text-black" for="fname">Email</label>
{{ form.email }} {% comment %}removed the input and added this do for all {% endcomment %}
</div>
{% if form.email.errors %}
{% for error in form.email.errors %}
<div class "alert">
{{ error|escape }}
</div>
{% endfor %}
{% endif %} {% comment %} do this for all {% endcomment %}
</div>
<div class="row form-group">
<div class="col-md-12 mb-3 mb-md-0">
<label class="text-black" for="fname">Password</label>
{{ form.password }}
</div>
{% if form.email.password %}
{% for error in form.password.errors %}
<div class "alert">
{{ error|escape }}
</div>
{% endfor %}
{% endif %}
</div>
<div class="row form-group mb-4">
<div class="col-md-12 mb-3 mb-md-0">
<label class="text-black" for="fname">Re-Type Password</label>
{{ form.password2 }}
</div>
{% if form.password2.errors %}
{% for error in form.password.errors %}
<div class "alert">
{{ error|escape }}
</div>
{% endfor %}
{% endif %}
</div>
<div class="row form-group">
<div class="col-md-12 mb-3 mb-md-0">
<label class="text-black" for="fname">First Name</label>
{{ form.first_name}}
</div>
{% if form.first_name.errors %}
{% for error in form.first_name.errors %}
<div class "alert">
{{ error|escape }}
</div>
{% endfor %}
{% endif %}
</div>
<div class="row form-group">
<div class="col-md-12 mb-3 mb-md-0">
<label class="text-black" for="fname">Last Name</label>
{{ form.last_name}}
</div>
{% if form.last_name.errors %}
{% for error in form.last_name.errors %}
<div class "alert">
{{ error|escape }}
</div>
{% endfor %}
{% endif %}
</div>
<div class="row form-group">
<div class="col-md-12">
<input type="submit" value="Sign Up" class="btn px-4 btn-primary text-white">
</div>
</div>
</form>
The code is displaying so I am assuming there is no error in the html side of it
What I have tried:
I tried several different values again and again but it is not validating.
Thank you so much for helping!!
Updated Answer
Try adding the non-field-errors to your form HTML template and check if there is any message printed.
<form action="." class="p-4 border rounded" method="POST">
{% csrf_token %}
{{ form.non_field_errors }}
<!-- DEBUG -->
{% for field in form %}
{% if field.errors %}{{ field.html_name }}: {{ field.errors }}{% endif %}
{% endfor %}
<!-- DEBUG -->
<!-- ... your markup ... -->
</form>
Docs: https://docs.djangoproject.com/en/4.0/topics/forms/#looping-over-the-form-s-fields
Error in your markup
There is a error in your template code. You are checking for the errors of password2 but printing only the errors for password
{% if form.password2.errors %}
{% for error in form.password.errors %}
<div class "alert">
{{ error|escape }}
</div>
{% endfor %}
{% endif %}
should be
{% if form.password2.errors %}
{% for error in form.password2.errors %}
<div class "alert">
{{ error|escape }}
</div>
{% endfor %}
{% endif %}
I am trying to use a for loop in my Django template to show the data stored in the models of a table but for some reason , the data does not show up in the template.
Views.py
def add_part(request):
parts = Parts.objects.all()
context = {
"parts": parts
}
return render(request, 'admintemplate/add_parts_template.html', context)
def add_part_save(request):
if request.method != "POST":
messages.error(request, "Method Not Allowed!")
return redirect('add_part')
else:
part_name = request.POST.get('part_name')
part_type = request.POST.get('part_type')
supplier_id = request.POST.get('suppliers')
suppliers = Suppliers.objects.get(id=supplier_id)
try:
part = Parts(part_name=part_name, part_type=part_type, supplier_id=supplier)
part.save()
messages.success(request, "Part Added Successfully!")
return redirect('add_part')
except:
messages.error(request, "Failed to Add Part!")
return redirect('add_part')
models.py
The parts and the services model are exactly the same with different column names, so I think the functionality for both should be the same.
Suppliers models
class Suppliers(models.Model):
id = models.AutoField(primary_key=True)
name = models.CharField(max_length=20)
Parts model
class Parts(models.Model):
id = models.AutoField(primary_key=True)
name = models.CharField(max_length=20)
part_type = models.CharField(max_length=20)
supplier_id = models.ForeignKey(Suppliers, on_delete=models.CASCADE)
Services model
class Services(models.Model):
id = models.AutoField(primary_key=True)
name = models.CharField(max_length=20)
service_type = models.CharField(max_length=20)
supplier_id = models.ForeignKey(Suppliers, on_delete=models.CASCADE)
Part template
{% extends 'admintemplate/base_template.html' %}
{% block page_title %}
Add Parts
{% endblock page_title %}
{% block main_content %}
{% load static %}
<section class="content">
<div class="container-fluid">
<div class="row">
<div class="col-md-12">
<!-- general form elements -->
<div class="card card-primary">
<div class="card-header">
<h3 class="card-title">Add Parts</h3>
</div>
<!-- /.card-header -->
<!-- form start -->
<form role="form" method="POST" action="{% url 'add_part_save' %}">
{% csrf_token %}
{% comment %} Display Messages {% endcomment %}
{% if messages %}
<div class="form-group">
<div class="col-12">
{% for message in messages %}
{% if message.tags == "error" %}
<div class="alert alert-danger alert-dismissible fade show" role="alert" style="margin-top: 10px;">
{{ message }}
<button type="button" class="close" data-dismiss="alert" aria-label="Close">
<span aria-hidden="true">×</span>
</button>
</div>
{% elif message.tags == "success" %}
<div class="alert alert-success alert-dismissible fade show" role="alert" style="margin-top: 10px;">
{{ message }}
<button type="button" class="close" data-dismiss="alert" aria-label="Close">
<span aria-hidden="true">×</span>
</button>
</div>
{% endif %}
{% endfor %}
</div>
</div>
{% endif %}
<div class="card-body">
<div class="form-group">
<label>Part Name </label>
<input type="text" class="form-control" name="part_name" placeholder="Part Name">
</div>
<div class="form-group">
<label>Part Type </label>
<input type="text" class="form-control" name="part_type" placeholder="Part Type">
</div>
<div class="form-group">
<label>Supplier Name</label>
<select class="form-control" name="suppliers">
{% for supplier in suppliers %}
<option value="{{ supplier.id }}">{{ supplier.name }}</option>
{% endfor %}
</select>
</div>
</div>
<!-- /.card-body -->
<div class="card-footer">
<button type="submit" class="btn btn-primary">Add Part</button>
</div>
</form>
</div>
<!-- /.card -->
</div>
</div>
</div><!-- /.container-fluid -->
</section>
{% endblock main_content %}
Now the services in parts template does not show up at all. There is no choices on the form. But, for the add services template, it does populate. I have no idea why this happens because I have used the exact same code for both templates.
Changing the view to this solved the issue
def add_part(request):
parts = Parts.objects.all()
context = {
"suppliers": suppliers
}
return render(request, 'admintemplate/add_parts_template.html', context)
I have created a template for displaying a photo gallery and giving users the ability to add photos to that gallery:
{% extends 'nowandthen/base.html' %}
{% block body_block %}
<br>
<br>
{% if pictures %}
<ul>
{% for p in pictures %}
<div class="container">
<div class="row">
<div class="col-md-8 card mb-4 mt-3 ">
<!-- Card -->
<!-- Card content -->
<div class="card-body d-flex flex-row">
<!-- Content -->
<div>
<!-- Title -->
<h4 class="card-title font-weight-bold mb-2">{{ p.title }}</h4>
<!-- Subtitle -->
<p class="card-text"><i class="far fa-clock pr-2"></i>{{ p.when_added }}</p>
</div>
</div>
<!-- Card image -->
<div class="view overlay">
<img class="card-img-top rounded-0" src="{{ p.image.url }}" alt="Card image cap">
<a href="#!">
<div class="mask rgba-white-slight"></div>
</a>
</div>
<!-- Card content -->
<div class="card-body">
<div class="collapse-content">
<!-- Text -->
<p class="card-text collapse" id="collapseContent">{{ p.description }}</p>
<!-- Button -->
<a class="btn btn-flat red-text p-1 my-1 mr-0 mml-1 collapsed" data-toggle="collapse" href="#collapseContent" aria-expanded="false" aria-controls="collapseContent">Click for description</a>
<i class="fas fa-share-alt text-muted float-right p-1 my-1" data-toggle="tooltip" data-placement="top" title="Share this post"></i>
<i class="fas fa-heart text-muted float-right p-1 my-1 mr-3" data-toggle="tooltip" data-placement="top" title="I like it"></i>
</div>
</div>
<div class="card-body">
<!-- comments -->
<h2>comments</h2>
{% if not p.comments %}
No comments
{% endif %}
{% for x in p.comment %}
<div class="comments" style="padding: 10px;">
<p class="font-weight-bold">
<h4>Comment by</h4> {{ x.user }}
<span class=" text-muted font-weight-normal">
{{ x.created_on }}
</span>
</p>
{{ x.body | linebreaks }}
</div>
{% endfor %}
</div>
<div class="card-body">
{% if new_comment %}
<h2>Your comment has been posted.</h2>
{% else %}
<h3>Leave a comment</h3>
<form action="{% url 'nowandthen:add_comment' p.image_id %}" method="POST">
{{ comment_form.as_p }}
{% csrf_token %}
<button type="submit" class="btn btn-primary btn-lg">Submit</button>
{% endif %}
</div>
</div>
</div>
</div>
<!-- Card -->
{% endfor %}
</ul>
{% else %}
<li><strong>There are no photographs present.</strong></li>
{% endif %}
{% endblock %}
The idea is that there is an image associated with each comment - there is a for loop of {% for p in pictures %} at the start of the page, and I use variations of p. (e.g. p.image_id) to associate particular pictures with particular comments.
In addition, the urls.py contains the following:
path('add_comment/<int:p.image_id>', views.add_comment, name='add_comment')
However, when I run the code, I get an error message that suggests that image ids aren't being created (even though image is a field in he Pictures model I created):
Reverse for 'add_comment' with arguments '('',)' not found. 1 pattern(s) tried: ['add_comment/$']
What do you suggest, please?
EDIT: This is my view:
#login_required
def add_comment(request, image_id):
new_comment = None
template_name = 'add_comment.html'
image = get_object_or_404(Picture, id=image_id)
comment = image.comments.filter(active=True)
new_comment = None
# Comment posted
if request.method == 'POST':
comment_form = CommentForm(data=request.POST)
if comment_form.is_valid():
# Create Comment object and don't save to database yet
new_comment = comment_form.save(commit=False)
# Assign the current post to the comment
new_comment.post = post
# Save the comment to the database
new_comment.save()
else:
comment_form = CommentForm()
context = {'image': image,'comment': comment, 'new_comment': new_comment,'comment_form': comment_form}
return render(request, template_name, context)
And this is my add_comment.html template:
{% extends 'nowandthen/base.html' %}
{% load staticfiles %}
{% block title_block %}
Add self
{% endblock %}
{% block body_block %}
<h1>Add a Comment</h1>
<div>
<form id="comment_form" method="post" action="{% url 'nowandthen:add_comment' comment_id%}" enctype="multipart/form-data" >
{% csrf_token %}
{{ form.as_p }}
<input type="submit" name="submit" value="Add Comment" />
</form>
</div>
{% endblock %}
Since you pictures variable is a Queryset, when you loop through it in your template, to access its ID, you just need to do it that way. instance.id
Based on your case, you will have:
{% url 'nowandthen:add_comment' p.id %}
And you will be able to access the id in your view with image_id
After Create moneylog, I want to got back to moneybook_detail, so I made a moneylog/view.py:
class moneylog_create(CreateView):
form_class = forms.CreateMoneylogForm
template_name = "moneylogs/create.html"
def form_valid(self, form):
moneylog = form.save()
moneybook = moneybook_models.Moneybook.objects.get(
pk=self.kwargs["pk"])
form.instance.moneybook = moneybook
moneylog.save()
form.save_m2m()
return redirect(reverse("moneybooks:detail", kwargs={'pk': moneybook.pk}))
and this is moneybook/urls.py
app_name = "moneybooks"
urlpatterns = [
path("create/", views.moneybook_create.as_view(), name="create"),
path("update/<int:pk>/",
views.moneybook_update.as_view(), name="update"),
path("<int:pk>/", views.moneybook_detail, name="detail")
]
moneylogs/urls.py
app_name = "moneylogs"
urlpatterns = [
path("create/<int:pk>/", views.moneylog_create.as_view(), name="create"),
path("update/<int:pk>/", views.moneylog_update.as_view(), name="update")
]
here is my detail.html
<a style="display:scroll;position:fixed;bottom:50px;right:30px;" href="{% url 'moneylogs:create' pk %}">
<div class="rounded-full h-16 w-16 flex items-center justify-center bg-red-400 text-bold font-bold text-white">+</div>
</a>
here is my moneylogs/forms.py
class CreateMoneylogForm(forms.ModelForm):
class Meta:
model = models.Moneylog
fields = (
"pay_day",
"payer",
"dutch_payer",
"price",
"category",
"memo",
)
widgets = {
"payer": forms.RadioSelect(attrs={"style": "width: 100 %"}),
"dutch_payer": forms.CheckboxSelectMultiple,
"memo": forms.Textarea(attrs={"rows": 3})
}
def save(self, *args, **kwargs):
moneylog = super().save(commit=False)
return moneylog
and moneylog_form.html
<form method="POST" class="w-full" enctype="multipart/form-data">
{% csrf_token %}
{% if form.non_field_errors %}
{% for error in form.non_field_errors %}
<span class="text-red-700 font-medium text-sm">{{error}}</span>
{% endfor %}
{% endif %}
<div class="input {% if field.errors %}has_error{% endif %}">
<div class="flex">
<div class="w-1/4">
{{form.name.label}}
</div>
<div class="w-3/4 border-b my-2 py-3">
{{form.name}}
</div>
</div>
{% if form.name.errors %}
{% for error in form.name.errors %}
<span class="text-red-700 font-medium text-sm">{{error}}</span>
{% endfor %}
{% endif %}
</div>
<div class="input {% if field.errors %}has_error{% endif %}">
<div class="flex">
<div class="w-1/4">
{{form.companion.label}}
</div>
<div class="w-3/4 flex inline border-b my-2 py-3">
<div class="w-3/4">
{{form.companion}}
</div>
<div class= "w-1/4 flex justify-center ">
<i class="fas fa-plus-circle"></i>
</div>
</div>
</div>
{% if form.companion.errors %}
{% for error in form.companion.errors %}
><span class="text-red-700 font-medium text-sm">{{error}}</span>
{% endfor %}
{% endif %}
</div>
<div class="input {% if field.errors %}has_error{% endif %}">
<div class="flex">
<div class="w-1/4">
{{form.country.label}}
</div>
<div class="w-3/4 border-b my-2 py-3">
{{form.country}}
</div>
</div>
{% if form.country.errors %}
{% for error in form.country.errors %}
<span class="text-red-700 font-medium text-sm">{{error}}</span>
{% endfor %}
{% endif %}
</div>
<div class="input {% if field.errors %}has_error{% endif %}">
<div class="flex">
<div class="w-1/4">
{{form.location.label}}
</div>
<div class="w-3/4 border-b my-2 py-3">
{{form.location}}
</div>
</div>
{% if form.location.errors %}
{% for error in form.location.errors %}
<span class="text-red-700 font-medium text-sm">{{error}}</span>
{% endfor %}
{% endif %}
</div>
<div class="input {% if field.errors %}has_error{% endif %}">
<div class="flex">
<div class="w-1/4">
{{form.start_date.label}}
</div>
<div class="w-3/4 border-b my-2 py-3">
{{form.start_date}}
</div>
</div>
{% if form.start_date.errors %}
{% for error in form.start_date.errors %}
<span class="text-red-700 font-medium text-sm">{{error}}</span>
{% endfor %}
{% endif %}
</div>
<div class="input {% if field.errors %}has_error{% endif %}">
<div class="flex">
<div class="w-1/4">
{{form.end_date.label}}
</div>
<div class="w-3/4 border-b my-2 py-3">
{{form.end_date}}
</div>
</div>
{% if form.end_date.errors %}
{% for error in form.end_date.errors %}
<span class="text-red-700 font-medium text-sm">{{error}}</span>
{% endfor %}
{% endif %}
</div>
<button class="px-2 py-1 rounded bg-red-500 text-white">{{cta}}</button>
</form>
there is no page redirect. no move, it print just log
"POST /moneylogs/create/1/ HTTP/1.1" 200 5275
How can I return to moneybook_detail after create moneylog?? why my redirect doesn't work?
The generic CreateView has two possible return paths when receiving a POST request:
form_valid() which in your case redirects. This is a HTTP status 302.
form_invalid() which renders the template again with the bound form in its context, in order to display the errors. This is a HTTP status 200.
Since your request returns status 200, we can conclude that the view went into the form_invalid() method, meaning your form has errors. It seems you're rendering the various field errors (although the template you're showing is for the wrong form, I assume this is a copy & paste error) but the easiest to debug is add {{ form.errors }} at the top of your template to display all errors. Or set a breakpoint in your form_invalid() method (override it to return super().form_invalid(form)).
either change the app_name or change the href in details.html. Because in one place you mentioned moneylogs and in another place, you mentioned moneybooks.
When I access the update page it doesn't populate the fields with the existing entry data (which is there, and print statements I've placed in parts of the view show that it's accessible and exists), I'm not really sure why it's not populating.
This is my view:
#login_required
def sites_update_view(request, place_id=None):
if place_id:
place = get_object_or_404(SiteMeta, pk=place_id)
else:
return redirect('sites-index')
if request.POST:
form = SitesAddForm(request.POST, instance=place)
if form.is_valid():
form.save()
return redirect('sites-index')
else:
form = SitesAddForm(instance=place)
return render(request, 'sites-update.html', {
'form': form,
'site': place,
'place_id': place_id
})
My template:
{% extends "newbase.html" %}
{% load url from future %}
{% load floppyforms %}
{% load staticfiles %}
{% block title %} - Update Site {% endblock %}
{% block content %}
<div class="row">
<div class="col-sm-6 col-md-6">
<h3 class="heading">Update Surveillance Site</h3>
<form method="post" action={% url 'sites-update' place_id=site.pk %}>
{% csrf_token %}
<div class="formSep">
<div class="row">
<div class="col-sm6 col-md-6">
<label for="id_name">Site Name:<span class="f_req">*</span></label>
{{ form.name }}
<span class="help-block">What is the site name?</span>
</div>
<div class="col-sm-6 col-md-6">
<label for="id_lga">LGA:<span class="f_req">*</span></label>
{{ form.lga }}
<span class="help-block">What is the LGA?</span>
</div>
<div class="col-sm-6 col-md-6">
<label for="id_site_type">Site Type:<span class="f_req">*</span></label>
{{ form.site_type }}
<span class="help-block">What type of site is this?</span>
</div>
<div class="col-sm-6 col-md-6">
<label for="id_site_priority">Site Priority:<span class="f_req">*</span></label>
{{ form.site_priority }}
<span class="help-block">What is the priority of this site?</span>
</div>
<div class="col-sm-6 col-md-6">
<label for="id_site_category">Site Category:<span class="f_req">*</span></label>
{{ form.site_category }}
<span class="help-block">What category should the site be in?</span>
</div>
</div>
</div>
<div class="row">
<input class="btn btn-default" type="submit" value="Save" />
<a class="btn btn-default" href={% url "sites-index" %}>Cancel</a>
</div>
</form>
</div>
</div>
{{ form.errors }}
{% endblock %}
{% block sidebar %}
{% include "afp-sidebar.html" %}
{% endblock %}
if request.POST: should be if request.method == 'POST':