adding bookmarklet

This commit is contained in:
Benjamin Boudreau
2018-06-03 16:01:32 -04:00
parent 5a2184062e
commit 799221f411
11 changed files with 60 additions and 15 deletions

View File

@@ -0,0 +1,12 @@
import React from 'react';
import ReactDOM from 'react-dom';
import Widget from '../components/widget';
const component = <Widget />;
const el = document.createElement('div');
document.body.appendChild(el);
console.log('running bookmarklet');
ReactDOM.render(
component,
el,
);

View File

@@ -0,0 +1,15 @@
import './bookmarklet';
import ReactDOM from 'react-dom';
describe('bookmarklet', () => {
afterEach(() => {
const el = document.querySelectorAll('body > div');
ReactDOM.unmountComponentAtNode(el[0]);
el[0].parentNode.removeChild(el[0]);
});
test('#mount document becomes ready', async () => {
const el = document.querySelectorAll('body > div');
expect(el).toHaveLength(1);
});
});

View File

@@ -0,0 +1,40 @@
import React from 'react';
import ReactDOM from 'react-dom';
import Widget from '../components/widget';
export default class EmbeddableWidget {
static el;
static mount() {
const component = <Widget />;
function doRender() {
if (EmbeddableWidget.el) {
throw new Error('EmbeddableWidget is already mounted, unmount first');
}
const el = document.createElement('div');
document.body.appendChild(el);
ReactDOM.render(
component,
el,
);
EmbeddableWidget.el = el;
}
if (document.readyState === 'complete') {
doRender();
} else {
window.addEventListener('load', () => {
doRender();
});
}
}
static unmount() {
if (!EmbeddableWidget.el) {
throw new Error('EmbeddableWidget is not mounted, mount first');
}
ReactDOM.unmountComponentAtNode(EmbeddableWidget.el);
EmbeddableWidget.el.parentNode.removeChild(EmbeddableWidget.el);
EmbeddableWidget.el = null;
}
}

View File

@@ -0,0 +1,44 @@
import EmbeddableWidget from './embeddable-widget';
import { waitForSelection } from '../test-helpers';
describe('EmbeddableWidget', () => {
afterEach(() => {
document.readyState = 'complete';
if (EmbeddableWidget.el) {
EmbeddableWidget.unmount();
}
});
test('#mount document becomes ready', async () => {
document.readyState = 'loading';
EmbeddableWidget.mount();
window.dispatchEvent(new Event('load', {}));
await waitForSelection(document, 'div');
});
test('#mount document complete', async () => {
EmbeddableWidget.mount();
await waitForSelection(document, 'div');
});
test('#mount twice', async () => {
EmbeddableWidget.mount();
expect(() => EmbeddableWidget.mount()).toThrow('already mounted');
});
test('#unmount', async () => {
const el = document.createElement('div');
document.body.appendChild(el);
expect(document.querySelectorAll('div')).toHaveLength(1);
EmbeddableWidget.el = el;
EmbeddableWidget.unmount();
expect(document.querySelectorAll('div')).toHaveLength(0);
});
test('#unmount without mounting', async () => {
expect(() => EmbeddableWidget.unmount()).toThrow('not mounted');
});
});