1

I have a POST request that passes data to my database when the form is submitted.

Photo of what I mean:

][

home.html

 <script type="text/javascript">
        $(document).ready(function(){
            var postForm = $(".form-post")

            //POSTING DATA INTO DATABASE
            postForm.submit(function(event){
                event.preventDefault();
                var thisForm =$(this)
                var actionEndPoint = thisForm.attr("action");
                var httpMethod = thisForm.attr("method");
                var formData = thisForm.serialize();

                $.ajax({
                    url: actionEndPoint,
                    method: httpMethod,
                    data: formData,
                    success:function(data){
                        console.log(data)
                        $(".form-post")[0].reset();

                        //I WANT TO PASS THE NEWLY ADDED DATA TO DISPLAY WITHOUT REFRESH
                        $.ajax({
                        type: 'GET',
                        url: '{% url "postInfo" %}',
                        dataType : 'json',
                        success: function(cdata){
                            $.each(cdata, function(id,posts){
                            $('#cb').append('<li>' +posts['fields'].title+ '  ' +posts['fields'].body+ '</li>');
                        });
                    }
                    });

                    },
                    error:function(errData){

                    }

                })
            })

        })
    </script>

As it is now it shows multiple of the same posts every time I add a post.

This is my views

views.py

def postInfo(request): # GET REQUEST
    if request.method == 'GET' and request.is_ajax():
        mytitle = Post.objects.all().order_by('-date_posted')
        response = serializers.serialize("json", mytitle)
        return HttpResponse(response, content_type='application/json')



def posting(request):  # POST REQUEST
    if request.method == 'POST' and request.is_ajax():
        title = request.POST.get('postTitle')
        content = request.POST.get('postContent')
        post = Post()
        post.title = title
        post.body = content
        post.author = request.user
        post.save()
        return HttpResponse('') 

models.py

class Post(models.Model):
    title = models.CharField(max_length=50)
    body = models.TextField()
    date_posted = models.DateTimeField(default=timezone.now)
    author = models.ForeignKey(User, on_delete=models.CASCADE)

    def __str__(self):
        return self.title

How can I make it so it just shows the post that I have added + what's in the database without showing multiple of the same posts? Thanks for any help.

Michal
  • 2,078
  • 23
  • 36
BadHabits
  • 13
  • 4

2 Answers2

0

You could have the POST view return the serialized instance as follows. It may not be entirely correct as I don't know what you're using for serialization, but it should give you an idea.

If you don't like that, you could inject the id's of the post as a data-post-id attribute in html, then only append it to $('#cb') if it doesn't exist.

def posting(request):  # POST REQUEST
    if request.method == 'POST' and request.is_ajax():
        title = request.POST.get('postTitle')
        content = request.POST.get('postContent')
        post = Post()
        post.title = title
        post.body = content
        post.author = request.user
        post.save()
        response = serializers.serialize("json", post)
        return HttpResponse(response, content_type='application/json')

$.ajax({
    url: actionEndPoint,
    method: httpMethod,
    data: formData,
    success:function(data){
        console.log(data)
        $(".form-post")[0].reset();
        $('#cb').append('<li>' +data['fields'].title+ '  ' +data['fields'].body+ '</li>');
    }
    });

    },
    error:function(errData){

    }

})
schillingt
  • 13,493
  • 2
  • 32
  • 34
  • Thanks for reply, I have same problem as I stated below. I now get TypeError: 'Post' object is not iterable. – BadHabits Mar 25 '19 at 03:58
0

You are getting multiples because you are asking for every post in the database to be sent upon the success of the POST request.

Assuming cdata is an array, you could do something like

let innerHtml;
cdata.forEach(function(obj) {
    innerHtml.append(`<li>${data['fields'].title} ${data['fields'].body}</li>`);
});

$('#cb').html(innerHtml);

$('#cb').html(...) will replace the HTML content of the element rather than add to it so you will not get any duplicate entries. Also using a template literal in the append method can make things a little cleaner.

Or you could simply send only the post you have just created in your posting view in it's HttpResponse. This will also be faster as you reduce the number of requests made when the form is submitted.

views.py

# Other endpoints
...

def posting(request):  # POST REQUEST
    if request.method == 'POST' and request.is_ajax():
        title = request.POST.get('postTitle')
        content = request.POST.get('postContent')
        post = Post()
        post.title = title
        post.body = content
        post.author = request.user
        post.save()

        # Send new post as response
        response = serializers.serialize('json', post)
        return HttpResponse(response, content_type='application/json') 

home.html

<script type="text/javascript">
  $(document).ready(function(){
    var postForm = $(".form-post");

    // POSTING DATA INTO DATABASE
    postForm.submit(function(event){
      event.preventDefault();
      var thisForm = $(this);
      var actionEndPoint = thisForm.attr("action");
      var httpMethod = thisForm.attr("method");
      var formData = thisForm.serialize();

      $.ajax({
        url: actionEndPoint,
        method: httpMethod,
        data: formData,
        success: function(data) {
          console.log(data);
          $(".form-post")[0].reset();

          // Add the new post to $('#cb')
          $('#cb')
            .append(`<li>${data['fields'].title} ${data['fields'].body}</li>`);         
        },
        error: function(errData){
          // Do something
        }
      })
    })

  })
</script>
Jamie Williams
  • 347
  • 4
  • 12
  • Thanks for the reply I changed to what you recommended sending the post in the HttpResponse but I am now getting TypeError: 'Post' object is not iterable. I am using - from django.core import serializers for the serialize. Same applies to @schillingt – BadHabits Mar 25 '19 at 03:44
  • Looking at the docs for the serializer you are using, `serialize` takes an iterator as its second argument, this is why you are seeing that error. If you have a look at this question https://stackoverflow.com/questions/2391002/django-serializer-for-one-object someone suggests that `serialize('json', [post])` should work. Remember that you will now get an array as a response. – Jamie Williams Mar 25 '19 at 13:21
  • Also, you might want to look into using Django Rest Framework to build your API https://www.django-rest-framework.org/. – Jamie Williams Mar 25 '19 at 13:26
  • Thanks finally got it to work! Using ` post_arr = serializers.serialize('json', [post]) response = post_arr[1:-1]` – BadHabits Mar 25 '19 at 13:40