Can't find out why UpdateView in django wasn't saving form data upon being saved. Instead, it saved the data in a url when it redirected me back to an un-edited object detail view.
I'm sharing the same template for CreateView and UpdateView
Here's my Views.py
from django.shortcuts import render, redirect, get_object_or_404
from django.urls import reverse
from django.views import View
from .models import Blog
from .forms import BlogForm
from django.views.generic import (
CreateView,
ListView,
DetailView,
UpdateView,
DeleteView
)
class BlogListView(ListView):
template_name = 'blogtemplates/blogs.html'
queryset = Blog.objects.all()
model = Blog
paginate_by = 4
def get_context_data(self, **kwargs):
context = super().get_context_data(**kwargs)
# Add in a QuerySet of all the books
context['object_list'] = Blog.objects.all()
return context
class BlogDetailView(DetailView):
model = Blog
template_name = 'blogview.html'
queryset = Blog.objects.all()
def get_object(self):
id_ = self.kwargs.get("pk")
return get_object_or_404(Blog, id=id_)
def get_context_data(self, **kwargs):
context = super().get_context_data(**kwargs)
# Add in a QuerySet of all the books
context['object_list'] = Blog.objects.all()
return context
class BlogCreateView(CreateView):
template_name = 'blogpost.html'
form_class = BlogForm
queryset = Blog.objects.all()
def get_context_data(self, **kwargs):
# Call the base implementation first to get a context
context = super().get_context_data(**kwargs)
# Add in a QuerySet of all the books
context['object_list'] = Blog.objects.all()
return context
class BlogUpdateView(UpdateView):
template_name = 'blogpost.html'
form_class = BlogForm
def get_object(self):
id_ = self.kwargs.get("pk")
return get_object_or_404(Blog, id=id_)
def get_context_data(self, **kwargs):
# Call the base implementation first to get a context
context = super().get_context_data(**kwargs)
# Add in a QuerySet of all the books
context['object'] = self.get_object()
context['object_list'] = Blog.objects.all()
print(context['object'])
return context
Here's my urls.py (in-app urls.py)
from django.urls import path
from .views import (
BlogListView,
BlogCreateView,
BlogDetailView,
BlogUpdateView,
#BlogDeleteView
)
app_name = 'blogs'
urlpatterns = [
path('', BlogListView.as_view(), name='blog-list'),
path('<int:pk>/', BlogDetailView.as_view(), name="blog-detail"),
path('post/', BlogCreateView.as_view(), name="blogs-post"),
path('<int:pk>/update', BlogUpdateView.as_view(), name='blogs-update')
#path('<int:pk>/delete', BlogDeleteView.as_view(), name="blog-delete"),
]
Here's The HTML Template that is rendered blogpost.html
{% extends 'base.html' %}
{% block content %}
{% if request.user.username == 'Thorba' %}
<div class="container-fluid bg-5 text-center">
{% if "update" in request.get_full_path %}
<form action="." method="PUT">
{% csrf_token %}
{{ form.as_p }}
<input type="submit" value="Save"/>
</form>
{% else %}
<form action="." method="POST">
{% csrf_token %}
{{ form.as_p }}
<input type="submit" value="Save"/>
</form>
{% endif %}
</div>
{% else %}
<div class="container-fluid bg-5 text-center">
<h1 class="box li">Permission Denied</h1>
</div>
{% endif %}
{% endblock %}
Here's the GET request I get after hitting Save on the UpdateView
HTTP GET /11/?csrfmiddlewaretoken=F4syRqsTW8X8JtPPSpzpu6qsCf7lryMOlGAnqHFelFt2XuzWCVQaeHEeoINOLnvR&title=And+Yet+%E2%80%A6+Another+Blog&description=POST+METHOD+CHECK&blog=After+a+LOT+of+research+about+UpdateView%2C+I+still+haven%27t+found+a+way+to+SAVE+THE+DATA.+The+url+is+routing+the+UpdateView+correctly+but+after+hitting+save+it+redirects+me+to+the+same%2C+previous%2C+unedited+object+First+Edit 200 [0.01, 192.168.29.226:51360]
Here, the 'first+edit' in the get request is what I had tried to save in the UpdateView form but instead went into the url and the object came out unchanged.
How do I Save the edits I make to the blog after I save it?
in your form the value of method="PUT"
is not valid, see method attribute docs , so it fallbacks to method="GET"
, which is why you are getting GET request after hitting save, and UpdateView
does not save any data when it's dispatching GET
request.
To fix this, change method
value in your form to POST
.
Then you have to change the logic of form. Don't use things like {% if "update" in request.get_full_path %}
it seems like an ureliable hack - if you'd change the path in your urls.py
this will stop working. Or if someone would put ?update=foolyou
into the url arbitrarily, it will also misbehave. Rather than that you should rely on abesnce/presence of object
in your template context, ie. something like this:
{% if object %} # existing object, do update
<form action="{% url "blogs-update" pk=object.pk %}" method="POST">
{% else %} # object not present, creating new one
<form action="." method="POST">
{%e endif %}
The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.