Created
February 5, 2020 03:40
-
-
Save thomasballinger/cae327bc5eb539398ea891facda9abed to your computer and use it in GitHub Desktop.
invalidation of Jupyter notebook cells
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
// Find deepest DOM ancestor that does not change on reexecute | |
const findParentOutputDiv = (el) => { | |
let candidate = el; | |
while (candidate) { | |
candidate = candidate.parentElement | |
if (candidate.className === 'output') { | |
return candidate; | |
} | |
} | |
throw Error("parent output div not found"); | |
} | |
// Find shallowest DOM ancestor that is removed on delete | |
const findParentCell = (el) => { | |
let candidate = el; | |
while (candidate) { | |
candidate = candidate.parentElement | |
if (candidate.classList.contains('cell')) { | |
return candidate; | |
} | |
} | |
throw Error("cell not found not found"); | |
} | |
const onCellReexecuteOrDelete = (element, cb) => { | |
const outputDiv = findParentOutputDiv(element); | |
const cellDiv = findParentCell(element); | |
const notebookContainer = cellDiv.parentElement; | |
let onEither = () => { throw Error('callback not initialized yet'); } | |
const reexecuteDetector = function(mutationsList, observer) { | |
for(let mutation of mutationsList) { | |
if (mutation.type === 'childList') { | |
onEither('cell reexecute'); | |
return; | |
} | |
} | |
}; | |
const cellDeleteDetector = function(mutationsList, observer) { | |
for (let mutation of mutationsList) { | |
if (mutation.type === 'childList') { | |
for (let node of mutation.removedNodes) { | |
if (node === cellDiv) { | |
onEither('cell delete') | |
return; | |
} | |
} | |
} | |
} | |
}; | |
const outputMutationObserver = new MutationObserver(reexecuteDetector); | |
const notebookMutationObserver = new MutationObserver(cellDeleteDetector); | |
onEither = (reason) => { | |
outputMutationObserver.disconnect(); | |
notebookMutationObserver.disconnect(); | |
cb(reason); | |
} | |
outputMutationObserver.observe(outputDiv, { childList: true }); | |
notebookMutationObserver.observe(notebookContainer, { childList: true }); | |
} | |
window.onCellReexecuteOrDelete = onCellReexecuteOrDelete; |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment