Help me please for solve 'ListBlogPost' object has no attribute 'get_object' django

I am using forms in my list view. why I am getting this error 'ListBlogPost' object has no attribute 'get_object' ?. Here is my code:

views.py

class ListBlogPost(ListView,FormView):
       model = Blog
       template_name = 'approval-blog-post.html'
       form_class = AdminBlogFrom
       
       def get_success_url(self):
        return reverse('approval-blog')

       #def get_object(self,slug): #I aslo tried this  but didn't work 
          #blog = get_object_or_404(Blog,slug=slug)
          #return  blog
  
       def get_context_data(self, **kwargs):
          data = super(ListBlogPost, self).get_context_data(**kwargs)
          data['blog_admin_form'] = AdminBlogFrom()
          
          return data
      
       def post(self, request, *args, **kwargs):
        self.object = self.get_object()
        form = self.get_form()
        if form.is_valid():
            messages.add_message(self.request, messages.INFO, 'Your Comment pending for admin approval')
            return self.form_valid(form)
        else:
            messages.add_message(self.request, messages.INFO, 'Somethings Wrong. Please try again')
            return self.form_invalid(form)

       def form_valid(self, form):
        form.save()
        return super(ListBlogPost, self).form_valid(form)
    

froms.py

class AdminBlogFrom(ModelForm):
       class Meta:
        model = Blog
        fields = ['is_published','author','slug']

models.py

 author = models.ForeignKey(User,on_delete=models.CASCADE,max_length=100)
 title = models.CharField(max_length=300,unique=True)
 body = RichTextUploadingField()
 slug = models.SlugField(max_length=255,unique=True)
 created_at = models.DateTimeField(auto_now_add= True,blank=True,null=True)
 updated_at = models.DateTimeField(auto_now= True,blank=True,null=True)
 CHOICES = (
        ('published', 'published',),
        ('pending', 'pending',),
        ('rejected', 'rejected',),
        )
 is_published = models.CharField(
        max_length=10,
        choices=CHOICES,default='pending'
      )

#approve-post.html

<form  method="POST">
{% csrf_token %}
{{form}}
<button class="btn btn-info">Publish</button>
</form>

When I am clicking on publish button I am getting this errror

 File "P:\django\farhyn\blog\views.py", line 276, in post
    self.object = self.get_object()
AttributeError: 'ListBlogPost' object has no attribute 'get_object'
[12/Jun/2021 00:09:31] "POST /blog-admin/approval-blog-post/ HTTP/1.1" 500 83649

It seems to me the problems occurring for this line of code self.object = self.get_object() but not understanding what to do?

Because you’re using at ListVIew. self.get_object() returns the current instance for a DetailView - that makes sense, because a DetailView is about a single instance (object) in the database for that model. A ListView has not “object” - it’s a collection of object.

It’s not super clear to me why you want to use a ListView for that actually. ListView is good when you want to display/use all (or a subset of) the objects of a Model in your view. Seems to me you’re rather working with a single object there, no?

1 Like

In addition to @logikonabstractions’s answer, you’re trying to inherit from two different base views, ListView and FormView. Neither of those two views are Mixins and are not designed to be used in combination with each other.

If you’re looking for some better insight into how the generic CBVs work, take a look at:

Understanding how these CBVs work will help you resolve a lot of potential problems.

2 Likes

I can create an separate view for publish blog and redirect back to list view. But I want to know is it possible to use forms in listview? if yes then what I need to be do for solve this problem 'ListBlogPost' object has no attribute 'get_object' django. I also want to know is it good practice to use forms in ListView?

Well, as Ken mentioned, those views are not necessarily meant to be mixted this way. I have not idea if there are a good use case or not for a sort of List-FormView, and if those can be used toghether safely (e.g. without causing you weird bugs now or down the road).

I would suggest you read up on this section of the documentation, as well as this one, which discusses a related topic (corner cases of using a CBV with mixins). If you read this and you do not understand what they are saying, I would consider that an hint that you’re in over your head in this approach (of mixin list/form views).

You are not REQUIRED to use those List/Create/Form Views in your code. You could just as well inherit directly from View and just code the functionalities that they provide yourself. In some cases, the best approach may be to pick which classe provides you with the most functionalities (in the case of forms, I would suggest its the FormView). Then you inherit from that one, and code yourself in the view/templates the aspect of the list view that you would need.

For instance the listview readily provides your template with a list of objects that you can iterate on. But nothing prevents you, say in your def get(...): of your FormView, to add to the context those same objects your self (e.g. something like ctx = self.get_context_data(...)). Then ctx is a dictionnary, and you could do something like ctx["mylist"] = MyModel.objects.all(), then in your template you’ll be able to access all the instances of MyModel (e.g. your blog post I think) just as much as you would have been able with the ListView.

2 Likes

Thanks for your details explanations. It helps me lot. Thanks again

1 Like