0

I am working on a website that has a feature to add and remove friend I wanted to make AJAX requests to add & remove a friend from user DB

here is my client-side JS code

window.addEventListener('DOMContentLoaded', (event) => {

    var username = document.getElementById("profileUsername").innerHTML;
    
    if(document.getElementById("addFriend")!= null){
        document.getElementById("addFriend").onclick = () => {
            $.ajax(
                {
                url : '/add_friend_JSON/'+username ,
                method : 'GET' ,
                processData: false,
                contentType: false,
                success: function(status) {
                    if ( status["status"] == 0 ) {
                        document.getElementById("addFriend").innerHTML  = "Unfriend";
                        
                        document.getElementById("addFriend").setAttribute("id" , "unFriend" );
                    }
                }
                })
            return false;
        }
    }
    else {
        document.getElementById("unFriend").onclick = () => {
        
            $.ajax(
                {
                url : '/remove_friend_JSON/'+username ,
                method : 'GET' ,
                processData: false,
                contentType: false,
                success: function(status) {
                    if ( status["status"] == 0 ) {
                        document.getElementById("unFriend").innerHTML  = "Add Friend";
                        
                        document.getElementById("unFriend").setAttribute("id", "addFriend");
                    }
                }
                })
            return false;
        }
    }

});

the above basically is like a switch which flips when we click it be 'add friend' and 'unfriend'

but the problem is it working only one time like if id changes from and friend to unFriend The next time when I click it without reloading the page, I got the following error in the log window

Uncaught TypeError: Cannot set property 'innerHTML' of null
    at Object.success (profile.js:36)
    at c (jquery.min.js:2)
    at Object.fireWith [as resolveWith] (jquery.min.js:2)
    at l (jquery.min.js:2)
    at XMLHttpRequest.<anonymous> (jquery.min.js:2)

here my HTML for reference

<button type="submit" class="btn btn-warning d-btn" id = "addFriend">
        Add Friend
</button>

The backend code just updates the DB based on the request Thank you!

Jaya Shankar B
  • 121
  • 2
  • 8
  • 1
    You never reassign the `onclick` callback so when you click it again it is still using the prior callback and querying the DOM for a no longer existing id. But changing `id` is not the way to go about this, and you are better off using `addEventListener()` for better control of the listeners attached to each element or even event delegation. see: [I am trying to make a simple toggle button in javascript](https://stackoverflow.com/questions/3047755/i-am-trying-to-make-a-simple-toggle-button-in-javascript) for a basic starting place. – pilchard Jun 05 '21 at 17:45

1 Answers1

1

The problem is that the if statement only executes 1 time, so you are only adding the event listener to add friend to the button, when you click it for the first time it changes it's id, but the button itself mantains the event listener, so when you click the button again, the same event happens and it tries to access the element with id "addFriend" but you changed that id so that's why you are getting that error.

Solution:

window.addEventListener("DOMContentLoaded", (event) => {
var username = document.getElementById("profileUsername").innerHTML;

const button = document.getElementById("addFriend");

if (document.getElementById("addFriend") != null) {
    document.getElementById("addFriend").onclick = (e) => {
        if (e.target.name === "addFriend") {
            $.ajax({
                url: "/add_friend_JSON/" + username,
                method: "GET",
                processData: false,
                contentType: false,
                success: function (status) {
                    if (status["status"] == 0) {
                        document.getElementById("addFriend").innerHTML =
                            "Unfriend";

                        e.target.name = "unfriend";
                    }
                },
            });
        } else if (e.target.name === "unfriend") {
            $.ajax({
                url: "/remove_friend_JSON/" + username,
                method: "GET",
                processData: false,
                contentType: false,
                success: function (status) {
                    if (status["status"] == 0) {
                        document.getElementById("addFriend").innerHTML =
                            "Add Friend";

                        e.target.name = "addFriend";
                    }
                },
            });
        }

        return false;
    };
}});

Add name="addFriend" to the button html

  • @JayaShankarB I would add only 1 event listener to the button, the inside the event listener check for the name property of the button, you need to add name="addFriend" to the button in the html, look the anwser again I posted you the code – Pablo Valverde Llamas Jun 05 '21 at 18:13