添加子项时,什么可能导致整个文档和子树上的 Mutation Observer 不触发?

Das*_*uss 7 javascript twitter mutation-observers

有时,突变观察者回调不会在我期望的时候触发。

如果我在开发人员工具控制台中运行此代码:

// callback for mutations observer
 callbackForAllChanges = function (mutationsList, observer) {
  console.log("mutations: ", mutationsList);
};

// create mutation observer
 allChanges = new MutationObserver(callbackForAllChanges);


// attach mutation observer to document
  allChanges.observe(document, {
    childList: true,
      subtree:true
  });

// create new child
document.body.appendChild(document.createElement("div"));
Run Code Online (Sandbox Code Playgroud)

我希望当我创建一个新的孩子时回调会触发。但有时会,有时不会。

当我在 stackoverflow 上的 devtools 控制台中运行代码时,它可以工作:我看到mutations: [MutationRecord]已记录到控制台。

当我在twitter上并在 devtools 控制台中运行上述代码时,它似乎不起作用:mutations: [MutationRecord]未记录到控制台。

什么可能导致 Mutation Observer 在 Twitter 上无法工作?

重现问题

  1. 转到推特
  2. 打开开发者工具控制台
  3. 粘贴上面的代码,看mutations: [MutationRecord]没有日志

更新

现在它在推特上对我有用,所以似乎是断断续续的。

更新2

Twitter 又停止工作了。我还发现,如果我将突变观察器添加到我创建的 div 中,这也不起作用,但可以在其他网站上使用。
const newDiv = document.createElement('div')
newDiv.setAttribute('id','newDiv')
// callback for mutations observer
 callbackForAllChanges = function (mutationsList, observer) {
  console.log("mutations: ", mutationsList);
};

// create mutation observer
 allChanges = new MutationObserver(callbackForAllChanges);


// attach mutation observer to document
  allChanges.observe(newDiv, {
    childList: true,
      subtree:true
  });

// create new child
newDiv.appendChild(document.createElement("div"));
Run Code Online (Sandbox Code Playgroud)

更新3

  • 突变观察者并没有停止隐姓埋名的工作
  • 关闭所有扩展并不能修复突变观察器不工作的情况
  • 退出并重新启动 chrome 似乎可以修复突变​​观察器停止工作时的问题
  • 清除 cookie并不能解决问题

更新4

它可能与无限循环有关,当观察到突变时,会添加一个节点。这会导致观察到突变(新添加的节点)。等等...

例子

  const callbackForAllChanges = function (mutationsList, observer) {
    if (mutationsList.find((record) => record.type === "childList")) {      
  document.body.appendChild(document.createElement("div"));
    }
  };
Run Code Online (Sandbox Code Playgroud)

我认为如果发生这种情况,可能会触发突变工作停止工作。

小智 1

我面临着同样的问题,现在我通过使用循环并检查是否手动进行了一些更改来修补回调。

setInterval(() => {
  const recs = allChanges.takeRecords()
  if (recs.length === ) return
  yourcallback(recs)
}, 30)
Run Code Online (Sandbox Code Playgroud)