user8463989
user8463989

Reputation: 2459

click event listener only works on first list item generated from mongoDB and node.js

I am fetching records from mongoDB and showing them in an unordered list. I have given the delete link a data-id which holds the product ID. For now I am just alerting the id when I click on the button. But for some reason the alert only pops up if I click on the first item. If I click on any item after that nothing happens and I get no error in console.

<% for (const products of pending) { %>
 <li>
    <a href="#" class="button gray delete" data-id="<%= products._id %>"><i class="sl sl-icon-close"></i> Delete</a>
 </li>
<% } %>

<script>
    const deleteBtn = document.querySelector('.delete');
    const productId = deleteBtn.getAttribute('data-id');
    document.querySelector('.delete').addEventListener('click', e => {
        e.preventDefault();
        alert(productId);
    });
</script>

Upvotes: 1

Views: 85

Answers (1)

Patrick Roberts
Patrick Roberts

Reputation: 51886

If you're going to create an event listener for a lot of dynamically generated elements, you should use a delegated event listener:

document.body.addEventListener('click', event => {
  if (!event.target.matches('.delete')) return;

  const btn = event.target;
  const productId = btn.dataset.id;

  event.preventDefault();
  alert(productId);
});

Instead of body you should use the most direct ancestor of all the elements that match .delete so you're not wasting time running a handler for a lot of irrelevant click events.

References:

Upvotes: 1

Related Questions