Skip to content

Commit

Permalink
feat: remove mutationobserver shim
Browse files Browse the repository at this point in the history
Closes #413

BREAKING CHANGE: MutationObserver is supported by all major browsers and recent versions of JSDOM. If you need, you can create your own shim (using @sheerun/mutationobserver-shim) and attach it to the window.
  • Loading branch information
kentcdodds committed Mar 4, 2020
1 parent 5aa6386 commit 53ec1bf
Show file tree
Hide file tree
Showing 6 changed files with 28 additions and 63 deletions.
1 change: 0 additions & 1 deletion package.json
Original file line number Diff line number Diff line change
Expand Up @@ -41,7 +41,6 @@
],
"dependencies": {
"@babel/runtime": "^7.8.4",
"@sheerun/mutationobserver-shim": "^0.3.2",
"@types/testing-library__dom": "^6.12.1",
"aria-query": "^4.0.2",
"dom-accessibility-api": "^0.3.0",
Expand Down
27 changes: 1 addition & 26 deletions src/__tests__/helpers.js
Original file line number Diff line number Diff line change
@@ -1,30 +1,5 @@
import {getDocument, newMutationObserver} from '../helpers'
import {getDocument} from '../helpers'

test('returns global document if exists', () => {
expect(getDocument()).toBe(document)
})

class DummyClass {
constructor(args) {
this.args = args
}
}

describe('newMutationObserver', () => {
if (typeof window === 'undefined') {
it('instantiates mock MutationObserver if not availble on window', () => {
expect(newMutationObserver(() => {}).observe).toBeDefined()
})
} else {
it('instantiates from global MutationObserver if available', () => {
const oldMutationObserver = window.MutationObserver
window.MutationObserver = DummyClass

try {
expect(newMutationObserver('foobar').args).toEqual('foobar')
} finally {
window.MutationObserver = oldMutationObserver
}
})
}
})
20 changes: 1 addition & 19 deletions src/events.js
Original file line number Diff line number Diff line change
@@ -1,3 +1,4 @@
import {getWindowFromNode} from './helpers'
const eventMap = {
// Clipboard Events
copy: {
Expand Down Expand Up @@ -410,25 +411,6 @@ Object.keys(eventMap).forEach(key => {
fireEvent[key] = (node, init) => fireEvent(node, createEvent[key](node, init))
})

function getWindowFromNode(node) {
// istanbul ignore next I'm not sure what could cause the final else so we'll leave it uncovered.
if (node.defaultView) {
// node is document
return node.defaultView
} else if (node.ownerDocument && node.ownerDocument.defaultView) {
// node is a DOM node
return node.ownerDocument.defaultView
} else if (node.window) {
// node is window
return node.window
} else {
// no idea...
throw new Error(
`Unable to find the "window" object for the given node. fireEvent currently supports firing events on DOM nodes, document, and window. Please file an issue with the code that's causing you to see this error: https://github.com/testing-library/dom-testing-library/issues/new`,
)
}
}

// function written after some investigation here:
// https://github.com/facebook/react/issues/10135#issuecomment-401496776
function setNativeValue(element, value) {
Expand Down
33 changes: 20 additions & 13 deletions src/helpers.js
Original file line number Diff line number Diff line change
@@ -1,5 +1,3 @@
import MutationObserver from '@sheerun/mutationobserver-shim'

const globalObj = typeof window === 'undefined' ? global : window

// Currently this fn only supports jest timers, but it could support other test runners in the future.
Expand Down Expand Up @@ -41,16 +39,6 @@ const {clearTimeoutFn, setImmediateFn, setTimeoutFn} = runWithRealTimers(
getTimeFunctions,
)

function newMutationObserver(onMutation) {
const MutationObserverConstructor =
typeof window !== 'undefined' &&
typeof window.MutationObserver !== 'undefined'
? window.MutationObserver
: MutationObserver

return new MutationObserverConstructor(onMutation)
}

function getDocument() {
/* istanbul ignore if */
if (typeof window === 'undefined') {
Expand All @@ -59,9 +47,28 @@ function getDocument() {
return window.document
}

function getWindowFromNode(node) {
// istanbul ignore next I'm not sure what could cause the final else so we'll leave it uncovered.
if (node.defaultView) {
// node is document
return node.defaultView
} else if (node.ownerDocument && node.ownerDocument.defaultView) {
// node is a DOM node
return node.ownerDocument.defaultView
} else if (node.window) {
// node is window
return node.window
} else {
// no idea...
throw new Error(
`Unable to find the "window" object for the given node. fireEvent currently supports firing events on DOM nodes, document, and window. Please file an issue with the code that's causing you to see this error: https://github.com/testing-library/dom-testing-library/issues/new`,
)
}
}

export {
getWindowFromNode,
getDocument,
newMutationObserver,
clearTimeoutFn as clearTimeout,
setImmediateFn as setImmediate,
setTimeoutFn as setTimeout,
Expand Down
5 changes: 3 additions & 2 deletions src/wait-for-dom-change.js
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
import {
newMutationObserver,
getWindowFromNode,
getDocument,
setImmediate,
setTimeout,
Expand Down Expand Up @@ -31,7 +31,8 @@ function waitForDomChange({
}
return new Promise((resolve, reject) => {
const timer = setTimeout(onTimeout, timeout)
const observer = newMutationObserver(onMutation)
const {MutationObserver} = getWindowFromNode(container)
const observer = new MutationObserver(onMutation)
runWithRealTimers(() =>
observer.observe(container, mutationObserverOptions),
)
Expand Down
5 changes: 3 additions & 2 deletions src/wait.js
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
import {
newMutationObserver,
getWindowFromNode,
getDocument,
setImmediate,
setTimeout,
Expand Down Expand Up @@ -28,7 +28,8 @@ function wait(
const overallTimeoutTimer = setTimeout(onTimeout, timeout)
const intervalId = setInterval(checkCallback, interval)

const observer = newMutationObserver(checkCallback)
const {MutationObserver} = getWindowFromNode(container)
const observer = new MutationObserver(checkCallback)
runWithRealTimers(() =>
observer.observe(container, mutationObserverOptions),
)
Expand Down

0 comments on commit 53ec1bf

Please sign in to comment.