Search code examples
javascriptmutation-observers

Do MutationObservers Only Listen To Local Changes?


I wanted to use MutationObservers to listen for a specific class addition (step_active) to elements with a class of (step), however this doesn't seem to be firing quite as expected.

If I add the class directly via element.classList.add() my event fires. When the site issues these class changes itself however - my events are not fired.

Why is this?

Here is the general format of my current code:

var target = document.querySelectorAll(".step");
for (var i = 0; i < target.length; i++) {
    var observer = new MutationObserver(function(mutations) {
        mutations.forEach(function(mutation) {
            var trigger = mutation.target;
            if(trigger.classList.contains('step_active')){
              window.dataLayer.push({
                event: 'Step: ' + mutation.id
              });
            }
        })
    });
    var config = {attributes: true, childList: true, subtree: true};
    observer.observe(target[i], config);
};

I expected this to push a unique event with the mutation.id as I progress through the steps on the page - This is not the case however. Instead doing something like this does produce the event I was expecting:

setTimeout(function(){
target[0].classList.add('step_active');
}, 1000);

Can anyone shed some light on what I'm missing/have misunderstood here?


Solution

  • As pointed out by wOxxOm this was caused by the elements that I was observing being replaced rather than manipulated, thus breaking my mutation observer.

    1. This scenario can be tested by artificially adding a class and observing whether it is retained as you progress.
    2. Or setting the MutationObserver to a higher level within the DOM and logging the mutationRecord.