From ea531426c95e3340630ad4b389e1ade76f21d1eb Mon Sep 17 00:00:00 2001 From: Andrew Sotiriou Date: Thu, 2 May 2024 12:10:27 -0400 Subject: [PATCH] Slim down...does this work (#44) --- examples/apps/global.css | 20 - examples/apps/index.html | 14 - examples/apps/infinite-scrolling/app.js | 101 --- examples/apps/infinite-scrolling/content.js | 63 -- examples/apps/infinite-scrolling/index.html | 9 - examples/apps/infinite-scrolling/main.js | 5 - .../apps/infinite-scrolling/styles/content.js | 21 - .../apps/infinite-scrolling/styles/index.js | 22 - examples/apps/interstitial/app.js | 33 - examples/apps/interstitial/index.html | 9 - examples/apps/interstitial/main.js | 5 - examples/apps/interstitial/styles/index.js | 7 - examples/apps/lazy-render/app.js | 45 - examples/apps/lazy-render/index.html | 9 - examples/apps/lazy-render/main.js | 5 - examples/apps/lazy-render/styles/index.js | 38 - examples/apps/log.js | 52 -- examples/apps/responsive/app.js | 89 -- examples/apps/responsive/button.js | 22 - examples/apps/responsive/index.html | 9 - examples/apps/responsive/main.js | 5 - examples/apps/responsive/styles/index.js | 14 - examples/apps/routing/app.js | 104 --- examples/apps/routing/home.js | 9 - examples/apps/routing/index.html | 9 - examples/apps/routing/main.js | 5 - examples/apps/routing/page.js | 30 - examples/apps/routing/styles/index.js | 18 - examples/apps/routing/styles/page.js | 5 - examples/apps/single-request/app.js | 91 -- examples/apps/single-request/button.js | 22 - examples/apps/single-request/index.html | 9 - examples/apps/single-request/main.js | 5 - examples/apps/single-request/styles/index.js | 35 - examples/apps/static-ad/app.js | 39 - examples/apps/static-ad/index.html | 9 - examples/apps/static-ad/main.js | 5 - examples/apps/static-ad/styles/index.js | 14 - examples/server/index.js | 2 - examples/server/routes.js | 20 - examples/server/server.js | 118 --- examples/webpack.config.js | 55 -- examples/webpack.config.server.js | 54 -- karma.conf.ci.js | 17 - karma.conf.js | 93 -- package.json | 10 - src/utils/createManagerTest.js | 10 - src/utils/mockGPT.js | 288 ------- test/Bling.spec.js | 814 ------------------ test/createManager.spec.js | 640 -------------- test/isInViewport.spec.js | 18 - test/mockGPT.spec.js | 79 -- test/polyfill.js | 1 - 53 files changed, 3225 deletions(-) delete mode 100644 examples/apps/global.css delete mode 100644 examples/apps/index.html delete mode 100644 examples/apps/infinite-scrolling/app.js delete mode 100644 examples/apps/infinite-scrolling/content.js delete mode 100644 examples/apps/infinite-scrolling/index.html delete mode 100644 examples/apps/infinite-scrolling/main.js delete mode 100644 examples/apps/infinite-scrolling/styles/content.js delete mode 100644 examples/apps/infinite-scrolling/styles/index.js delete mode 100644 examples/apps/interstitial/app.js delete mode 100644 examples/apps/interstitial/index.html delete mode 100644 examples/apps/interstitial/main.js delete mode 100644 examples/apps/interstitial/styles/index.js delete mode 100644 examples/apps/lazy-render/app.js delete mode 100644 examples/apps/lazy-render/index.html delete mode 100644 examples/apps/lazy-render/main.js delete mode 100644 examples/apps/lazy-render/styles/index.js delete mode 100644 examples/apps/log.js delete mode 100644 examples/apps/responsive/app.js delete mode 100644 examples/apps/responsive/button.js delete mode 100644 examples/apps/responsive/index.html delete mode 100644 examples/apps/responsive/main.js delete mode 100644 examples/apps/responsive/styles/index.js delete mode 100644 examples/apps/routing/app.js delete mode 100644 examples/apps/routing/home.js delete mode 100644 examples/apps/routing/index.html delete mode 100644 examples/apps/routing/main.js delete mode 100644 examples/apps/routing/page.js delete mode 100644 examples/apps/routing/styles/index.js delete mode 100644 examples/apps/routing/styles/page.js delete mode 100644 examples/apps/single-request/app.js delete mode 100644 examples/apps/single-request/button.js delete mode 100644 examples/apps/single-request/index.html delete mode 100644 examples/apps/single-request/main.js delete mode 100644 examples/apps/single-request/styles/index.js delete mode 100644 examples/apps/static-ad/app.js delete mode 100644 examples/apps/static-ad/index.html delete mode 100644 examples/apps/static-ad/main.js delete mode 100644 examples/apps/static-ad/styles/index.js delete mode 100644 examples/server/index.js delete mode 100644 examples/server/routes.js delete mode 100644 examples/server/server.js delete mode 100644 examples/webpack.config.js delete mode 100644 examples/webpack.config.server.js delete mode 100644 karma.conf.ci.js delete mode 100644 karma.conf.js delete mode 100644 src/utils/createManagerTest.js delete mode 100644 src/utils/mockGPT.js delete mode 100644 test/Bling.spec.js delete mode 100644 test/createManager.spec.js delete mode 100644 test/isInViewport.spec.js delete mode 100644 test/mockGPT.spec.js delete mode 100644 test/polyfill.js diff --git a/examples/apps/global.css b/examples/apps/global.css deleted file mode 100644 index c8a20e7..0000000 --- a/examples/apps/global.css +++ /dev/null @@ -1,20 +0,0 @@ -body { - font-family: "Helvetica Neue", Arial; - font-weight: 200; -} - -h1, h2, h3 { - font-weight: 100; -} - -a { - color: hsl(150, 50%, 50%); -} - -a.active { - color: hsl(40, 50%, 50%); -} - -.breadcrumbs a { - text-decoration: none; -} diff --git a/examples/apps/index.html b/examples/apps/index.html deleted file mode 100644 index 0ad5976..0000000 --- a/examples/apps/index.html +++ /dev/null @@ -1,14 +0,0 @@ - -React GPT Examples - - -

React GPT Examples

- diff --git a/examples/apps/infinite-scrolling/app.js b/examples/apps/infinite-scrolling/app.js deleted file mode 100644 index 70cdf87..0000000 --- a/examples/apps/infinite-scrolling/app.js +++ /dev/null @@ -1,101 +0,0 @@ -/* eslint-disable react/sort-comp */ -import React, {Component} from "react"; -import Radium from "radium"; -import debounce from "throttle-debounce/debounce"; -import {Bling as Gpt, Events} from "react-gpt"; // eslint-disable-line import/no-unresolved -import "../log"; -import Content from "./content"; -import styles from "./styles"; - -Gpt.syncCorrelator(); -Gpt.enableSingleRequest(); -Gpt.disableInitialLoad(); - -@Radium -class App extends Component { - state = { - page: 1, - size: [728, 90] - }; - time = 0; - componentDidMount() { - window.addEventListener("scroll", this.onScroll); - window.addEventListener("resize", this.onScroll); - this.onScroll(); - this.startTimer(); - Gpt.on(Events.RENDER, () => { - let changeCorrelator = false; - if (this.time >= 30) { - changeCorrelator = true; - this.startTimer(); - } - Gpt.refresh(null, {changeCorrelator}); - }); - } - componentDidUpdate() { - Gpt.refresh(); - } - componentWillUnmount() { - window.removeEventListener("scroll", this.onScroll); - window.removeEventListener("resize", this.onScroll); - this.stopTimer(); - } - onScroll = debounce(66, () => { - const scrollTop = window.scrollY || document.documentElement.scrollTop; - if (scrollTop + window.innerHeight >= document.body.clientHeight) { - this.setState({ - page: ++this.state.page - }); - } - }); - startTimer() { - this.stopTimer(); - this.timer = setInterval(() => { - this.time++; - }, 1000); - } - stopTimer() { - if (this.timer) { - clearInterval(this.timer); - this.time = 0; - this.timer = null; - } - } - render() { - const {page} = this.state; - let contentCnt = 0; - const contents = []; - const targeting = { - test: "infinitescroll" - }; - while (contentCnt < page * 3) { - contents.push( - - ); - contentCnt++; - } - return ( -
-
- -
-
{contents}
-
- ); - } -} - -export default App; diff --git a/examples/apps/infinite-scrolling/content.js b/examples/apps/infinite-scrolling/content.js deleted file mode 100644 index 3c428f1..0000000 --- a/examples/apps/infinite-scrolling/content.js +++ /dev/null @@ -1,63 +0,0 @@ -import React, {Component} from "react"; -import PropTypes from "prop-types"; -import Radium from "radium"; -import {Bling as Gpt} from "react-gpt"; // eslint-disable-line import/no-unresolved -import styles from "./styles/content"; - -const contents = [ - `Lorem ipsum dolor sit amet, convallis nibh erat in lacus morbi orci, sed amet leo, donec a nulla lacus, velit suspendisse per. Est elit ultricies, a metus, aenean suspendisse ullamcorper facilisis. Wisi ridiculus ut nibh viverra cursus. Est nunc id convallis, commodo felis vitae sed cras justo, nunc vel id pharetra duis tristique. Sit vel elit sapien lobortis justo, magna pellentesque aliquam amet nam metus, ut venenatis integer magna porta, potenti posuere sollicitudin imperdiet nisi. -Feugiat venenatis. Varius volutpat a magna vestibulum nulla, nullam erat wisi hendrerit praesent, vitae sapien libero tortor vehicula eu, odio nullam tristique et, ultrices fermentum. Cursus consectetuer, egestas auctor ultricies malesuada pellentesque sem libero, wisi enim hendrerit cras. Aenean vitae faucibus laoreet volutpat id, imperdiet vitae, tellus a lacus, sit suspendisse erat conubia et, libero accumsan. Nullam orci eget non urna varius metus, etiam vestibulum euismod erat. Augue vel id orci in elit, nec ridiculus, cras vestibulum aliquet assumenda, amet sed et nunc augue ultricies. Ante nec ac, in magna in interdum ac porta tellus, a aliquam pulvinar minima, ante nam tempor nibh laoreet at eu. Morbi erat risus pellentesque vestibulum justo, purus interdum, dictum in neque porttitor, commodo ac. Tincidunt facilisis sit id ultrices est lectus. Sed id praesent tincidunt dui. Etiam ut tincidunt id. -Sollicitudin egestas suspendisse amet eget mi est, neque amet et erat. Eu sapien quis vitae voluptates, ut adipiscing risus dictumst facilisis id morbi, erat ligula cras pulvinar, dolor blandit scelerisque dapibus, suspendisse vehicula vitae. Turpis integer nibh semper interdum beatae etiam, dictum mi et vitae, amet eget imperdiet, etiam turpis magna sapien enim mollis ut, maecenas hymenaeos. Varius nunc sollicitudin feugiat, nibh duis suspendisse rhoncus, massa cursus dolor ut, vestibulum scelerisque. Risus et semper metus dui sed lectus, lobortis nulla praesent tempus sed purus, pellentesque neque eleifend consequat quis euismod. Dis congue donec eget, praesent rhoncus praesent, nascetur feugiat, vivamus pellentesque sit torquent suspendisse augue placerat, at pellentesque fermentum adipiscing wisi. Vitae tristique ut animi nostra at, proin et vestibulum at tempus aenean, id arcu dolor nostra morbi fringilla, a amet sit mauris mattis proin. Cras duis sollicitudin, ut pretium commodo pulvinar risus dapibus. Porta integer sapien. Elit fusce et, turpis risus. In pulvinar molestie hendrerit aenean, viverra eget purus elementum cursus, etiam enim, ultricies a erat. Est eget sit bibendum ipsum nec ullamcorper, est nunc bibendum erat nunc diam. -Cursus vel at mauris. Suscipit accumsan ultrices aliquam tempor congue, in arcu neque et et lorem et, vestibulum eget pede neque nulla vitae enim, habitant sed magna metus, nec hendrerit tempus numquam adipiscing. Ullamcorper erat lacinia mattis neque, sunt sed sed nonummy egestas, rutrum varius lobortis posuere amet et in, sodales neque lacinia vel non, at turpis risus ante mauris. Quam facilisis quis lorem praesent. Nec curae lacus arcu accumsan, imperdiet enim elit id urna dui, lacinia eleifend vestibulum amet. Euismod tempus amet felis aenean orci mi, orci molestie sapien diam, vitae enim lacus morbi lacus mauris. Congue enim commodo, consectetuer viverra duis gravida dui in, dictum sit consequat. Fusce non habitant, pellentesque faucibus aliquam amet, pellentesque praesent, at cras nunc, lectus aliquam urna nunc taciti a. Ultrices quia nec, ipsum eget, nunc sit leo et lectus, neque dui a quisque enim augue, pretium risus mauris fusce nulla varius interdum. Amet risus donec aliquam, ligula arcu tellus. Ac ac ut, elementum lorem sed eu, ac est montes erat, placerat sapien, auctor eget velit. Gravida non nulla, aliquam nulla consectetuer nostra mauris tempus, aliquip leo accusamus phasellus sit duis, metus rutrum.`, - `Appear. Let, won't have, living. God behold void, said. Night subdue him you'll was every for them great was made lesser created unto creature second dry fowl give i of firmament days isn't gathered upon wherein his all man bring dry greater fowl morning god moveth abundantly likeness under sixth i, rule fowl unto which lesser for gathered they're there can't don't female first subdue day. All wherein blessed divide god can't above lesser every. Open divided moved man. All hath. Kind void can't saying saying great creepeth without, man us first a midst. Great second. They're male male it shall greater. Had open hath there us. Upon third male rule. - -Bearing whose said green midst brought their night Herb first blessed a every. Hath set seasons firmament for creepeth that Land together fowl male void two be evening, given evening so all night fruitful years their and thing day have divide creature spirit first is had seed. You heaven place give. Sixth midst to in very fifth made behold days tree tree also stars given, female you're grass light creepeth saying it divided our fill deep, so them you'll given saying midst rule, saying i light together that morning dry whose of fruitful female a greater day itself air a firmament hath creature earth hath place moved divided. Deep together divide without sixth creeping great for, land grass. - -Night void them saw seas winged bring, fly had earth shall own. Divided. To image don't fill above to very. Hath. Light doesn't moving blessed. Bearing saying lesser. Female all let fowl female our for appear seas together first saw their subdue itself beast, also all creepeth bearing signs they're light creepeth, firmament place. It given you'll their sixth, fish let it morning light third lesser were. First every, good divide.`, - `Mucius feugait incorrupte no has, ei patrioque molestiae cum. Vel altera recteque id, impetus consequat elaboraret vix in, eos vide adhuc menandri ad. Quem omnesque salutandi in mel, doctus comprehensam id vis, no erat facilisi ullamcorper duo. Causae option duo id, eirmod numquam mei eu, et vim ipsum liberavisse. Efficiantur deterruisset sed in. Aperiri epicurei consulatu ea duo. Ut cum inani voluptaria interesset. - -Vim apeirian recteque eu. Ad sea graeci dicunt, vix brute velit ad. Semper nominati nam ne, te mea vero omnes tacimates. Porro dicant tamquam duo eu. Et eam consul noluisse electram, impetus conclusionemque pri ut.` -]; - -const bg = ["#90C3D4", "#FAD9EA", "#FCFCB1"]; - -@Radium -class Content extends Component { - static propTypes = { - index: PropTypes.number, - targeting: PropTypes.object - }; - render() { - const {index, targeting} = this.props; - let ad; - if (index !== 2) { - ad = ( -
- -
- ); - } - - return ( -
-
- {ad} -

- Content {index} - - Lorem ipsum dolor sit amet, accusamus complectitur - an est - - {contents[index]} -

-
-
- ); - } -} - -export default Content; diff --git a/examples/apps/infinite-scrolling/index.html b/examples/apps/infinite-scrolling/index.html deleted file mode 100644 index 65fa6d2..0000000 --- a/examples/apps/infinite-scrolling/index.html +++ /dev/null @@ -1,9 +0,0 @@ - -Infinite Scrolling Example - - -

React GPT Examples / Infinite Scrolling Example

-
- - - diff --git a/examples/apps/infinite-scrolling/main.js b/examples/apps/infinite-scrolling/main.js deleted file mode 100644 index c341ca7..0000000 --- a/examples/apps/infinite-scrolling/main.js +++ /dev/null @@ -1,5 +0,0 @@ -import React from "react"; -import ReactDOM from "react-dom"; -import App from "./app"; - -ReactDOM.render(, document.getElementById("example")); diff --git a/examples/apps/infinite-scrolling/styles/content.js b/examples/apps/infinite-scrolling/styles/content.js deleted file mode 100644 index 7878189..0000000 --- a/examples/apps/infinite-scrolling/styles/content.js +++ /dev/null @@ -1,21 +0,0 @@ -export default { - main: { - flex: "1 1 auto", - padding: 5 - }, - mr: { - float: "right", - margin: 15 - }, - title: { - display: "block", - marginBottom: 10, - fontSize: 24, - fontWeight: "bold" - }, - description: { - display: "block", - marginBottom: 10, - fontSize: 20 - } -}; diff --git a/examples/apps/infinite-scrolling/styles/index.js b/examples/apps/infinite-scrolling/styles/index.js deleted file mode 100644 index a0db193..0000000 --- a/examples/apps/infinite-scrolling/styles/index.js +++ /dev/null @@ -1,22 +0,0 @@ -export default { - button: { - marginTop: 20, - padding: "2px 6px 3px", - border: "2px outset buttonface" - }, - container: { - marginTop: 20, - position: "relative" - }, - main: { - display: "flex", - flexDirection: "column" - }, - adBorder: { - padding: 10, - border: "1px dashed #666" - }, - lb: { - position: "relative" - } -}; diff --git a/examples/apps/interstitial/app.js b/examples/apps/interstitial/app.js deleted file mode 100644 index f1876df..0000000 --- a/examples/apps/interstitial/app.js +++ /dev/null @@ -1,33 +0,0 @@ -import React, {Component} from "react"; -import {Bling as Gpt} from "react-gpt"; // eslint-disable-line import/no-unresolved -import "../log"; -import styles from "./styles"; - -class App extends Component { - state = { - adUnitPath: "/4595/nfl.test.open/page/A" - }; - - onClick = () => { - this.setState({ - adUnitPath: - this.state.adUnitPath.indexOf("B") > -1 - ? "/4595/nfl.test.open/page/A" - : "/4595/nfl.test.open/page/B" - }); - }; - - render() { - const {adUnitPath} = this.state; - return ( -
- - -
- ); - } -} - -export default App; diff --git a/examples/apps/interstitial/index.html b/examples/apps/interstitial/index.html deleted file mode 100644 index 0b45f67..0000000 --- a/examples/apps/interstitial/index.html +++ /dev/null @@ -1,9 +0,0 @@ - -Interstitial Example - - -

React GPT Examples / Interstitial Example

-
- - - diff --git a/examples/apps/interstitial/main.js b/examples/apps/interstitial/main.js deleted file mode 100644 index c341ca7..0000000 --- a/examples/apps/interstitial/main.js +++ /dev/null @@ -1,5 +0,0 @@ -import React from "react"; -import ReactDOM from "react-dom"; -import App from "./app"; - -ReactDOM.render(, document.getElementById("example")); diff --git a/examples/apps/interstitial/styles/index.js b/examples/apps/interstitial/styles/index.js deleted file mode 100644 index eee7555..0000000 --- a/examples/apps/interstitial/styles/index.js +++ /dev/null @@ -1,7 +0,0 @@ -export default { - button: { - marginTop: 20, - padding: "2px 6px 3px", - border: "2px outset buttonface" - } -}; diff --git a/examples/apps/lazy-render/app.js b/examples/apps/lazy-render/app.js deleted file mode 100644 index 1548f03..0000000 --- a/examples/apps/lazy-render/app.js +++ /dev/null @@ -1,45 +0,0 @@ -import React, {Component} from "react"; -import Radium from "radium"; -import {Bling as Gpt} from "react-gpt"; // eslint-disable-line import/no-unresolved -import "../log"; -import styles from "./styles"; - -Gpt.configure({viewableThreshold: 0}); - -@Radium -class App extends Component { - onClick = () => { - Gpt.render(); - }; - render() { - return ( -
- -
-
-
- -
-
-
- -
-
- ); - } -} - -export default App; diff --git a/examples/apps/lazy-render/index.html b/examples/apps/lazy-render/index.html deleted file mode 100644 index 57abb84..0000000 --- a/examples/apps/lazy-render/index.html +++ /dev/null @@ -1,9 +0,0 @@ - -Lazy Render Example - - -

React GPT Examples / Lazy Render Example

-
- - - diff --git a/examples/apps/lazy-render/main.js b/examples/apps/lazy-render/main.js deleted file mode 100644 index c341ca7..0000000 --- a/examples/apps/lazy-render/main.js +++ /dev/null @@ -1,5 +0,0 @@ -import React from "react"; -import ReactDOM from "react-dom"; -import App from "./app"; - -ReactDOM.render(, document.getElementById("example")); diff --git a/examples/apps/lazy-render/styles/index.js b/examples/apps/lazy-render/styles/index.js deleted file mode 100644 index f27f3f8..0000000 --- a/examples/apps/lazy-render/styles/index.js +++ /dev/null @@ -1,38 +0,0 @@ -export default { - button: { - marginTop: 20, - padding: "2px 6px 3px", - border: "2px outset buttonface" - }, - container: { - marginTop: 20, - position: "relative" - }, - content: { - display: "inline-block", - width: 1500, - height: 1500, - backgroundColor: "#ffffcc" - }, - hWrap: { - whiteSpace: "nowrap" - }, - adBorder: { - padding: 10, - border: "1px dashed #666", - width: "100%", - height: "100%" - }, - lb: { - position: "relative", - display: "inline-block", - width: 728, - height: 90, - verticalAlign: "top" - }, - mr: { - position: "relative", - width: 300, - height: 250 - } -}; diff --git a/examples/apps/log.js b/examples/apps/log.js deleted file mode 100644 index 2741e5f..0000000 --- a/examples/apps/log.js +++ /dev/null @@ -1,52 +0,0 @@ -import {Bling as GPT, Events} from "react-gpt"; // eslint-disable-line import/no-unresolved - -GPT.on(Events.SLOT_RENDER_ENDED, event => { - const slot = event.slot; - const divId = slot.getSlotElementId(); - const targetingKeys = slot.getTargetingKeys(); - const targeting = targetingKeys.reduce((t, key) => { - const val = slot.getTargeting(key); - t[key] = val.length === 1 ? val[0] : val; - return t; - }, {}); - - if (!event.isEmpty && event.size) { - console.log( - `ad creative '${ - event.creativeId - }' is rendered to slot '${divId}' of size '${event.size[0]}x${ - event.size[1] - }'`, - event, - targeting - ); - } else { - console.log( - `ad rendered but empty, div id is ${divId}`, - event, - targeting - ); - } -}); - -// Turn on these logs when checking these events. -/* GPT.on(Events.IMPRESSION_VIEWABLE, event => { - const slot = event.slot; - const divId = slot.getSlotElementId(); - const sizes = slot.getSizes(); - console.log(`IMPRESSION_VIEWABLE for ${divId}(${JSON.stringify(sizes)})`, event); -}); - -GPT.on(Events.SLOT_VISIBILITY_CHANGED, event => { - const slot = event.slot; - const divId = slot.getSlotElementId(); - const sizes = slot.getSizes(); - console.log(`SLOT_VISIBILITY_CHANGED for ${divId}(${JSON.stringify(sizes)}) to ${event.inViewPercentage}`, event); -}); - -GPT.on(Events.SLOT_LOADED, event => { - const slot = event.slot; - const divId = slot.getSlotElementId(); - const sizes = slot.getSizes(); - console.log(`SLOT_LOADED for ${divId}(${JSON.stringify(sizes)})`, event); -});*/ diff --git a/examples/apps/responsive/app.js b/examples/apps/responsive/app.js deleted file mode 100644 index e7b3a89..0000000 --- a/examples/apps/responsive/app.js +++ /dev/null @@ -1,89 +0,0 @@ -/* eslint-disable indent */ -import React, {Component} from "react"; -import Radium from "radium"; -import {Bling as Gpt} from "react-gpt"; // eslint-disable-line import/no-unresolved -import "../log"; -import Button from "./button"; -import styles from "./styles"; - -@Radium -class App extends Component { - state = { - adUnitPath: "/4595/nfl.test.open", - targeting: { - test: "responsive" - }, - sizeMapping: [ - {viewport: [0, 0], slot: [1, 1]}, - {viewport: [340, 0], slot: [320, 50]}, - {viewport: [750, 200], slot: [728, 90]}, - {viewport: [1050, 200], slot: [1024, 120]} - ], - style: styles.adBorder - }; - - onClick = params => { - if (params === "refresh") { - Gpt.refresh(); - return; - } - let newState; - if (params === "adUnitPath") { - newState = { - adUnitPath: - this.state.adUnitPath === "/4595/nfl.test.open" - ? "/4595/nfl.test.open/new" - : "/4595/nfl.test.open" - }; - } else if (params === "targeting") { - newState = { - targeting: { - test: "responsive", - changed: Date.now() - } - }; - } else if (params === "size") { - newState = { - sizeMapping: - this.state.sizeMapping[1].slot[1] === 50 - ? [ - {viewport: [0, 0], slot: [1, 1]}, - {viewport: [340, 0], slot: [300, 250]}, - {viewport: [750, 200], slot: [728, 90]}, - {viewport: [1050, 200], slot: [1024, 120]} - ] - : [ - {viewport: [0, 0], slot: [1, 1]}, - {viewport: [340, 0], slot: [320, 50]}, - {viewport: [750, 200], slot: [728, 90]}, - {viewport: [1050, 200], slot: [1024, 120]} - ] - }; - } - this.setState(newState); - }; - - render() { - return ( -
- - - - -
- -
-
- ); - } -} - -export default App; diff --git a/examples/apps/responsive/button.js b/examples/apps/responsive/button.js deleted file mode 100644 index 623dc7a..0000000 --- a/examples/apps/responsive/button.js +++ /dev/null @@ -1,22 +0,0 @@ -import React, {Component} from "react"; -import PropTypes from "prop-types"; -import styles from "./styles"; - -export default class Button extends Component { - static propTypes = { - children: PropTypes.node, - onClick: PropTypes.func.isRequired, - params: PropTypes.oneOfType([PropTypes.string, PropTypes.object]) - .isRequired - }; - onClick = () => { - this.props.onClick(this.props.params); - }; - render() { - return ( - - ); - } -} diff --git a/examples/apps/responsive/index.html b/examples/apps/responsive/index.html deleted file mode 100644 index d214187..0000000 --- a/examples/apps/responsive/index.html +++ /dev/null @@ -1,9 +0,0 @@ - -Responsive Example - - -

React GPT Examples / Responsive Example

-
- - - diff --git a/examples/apps/responsive/main.js b/examples/apps/responsive/main.js deleted file mode 100644 index c341ca7..0000000 --- a/examples/apps/responsive/main.js +++ /dev/null @@ -1,5 +0,0 @@ -import React from "react"; -import ReactDOM from "react-dom"; -import App from "./app"; - -ReactDOM.render(, document.getElementById("example")); diff --git a/examples/apps/responsive/styles/index.js b/examples/apps/responsive/styles/index.js deleted file mode 100644 index b6fd614..0000000 --- a/examples/apps/responsive/styles/index.js +++ /dev/null @@ -1,14 +0,0 @@ -export default { - button: { - marginTop: 20, - padding: "2px 6px 3px", - border: "2px outset buttonface" - }, - adBorder: { - padding: 10, - border: "1px dashed #666" - }, - lb: { - position: "relative" - } -}; diff --git a/examples/apps/routing/app.js b/examples/apps/routing/app.js deleted file mode 100644 index e046b3e..0000000 --- a/examples/apps/routing/app.js +++ /dev/null @@ -1,104 +0,0 @@ -/* eslint-disable react/no-multi-comp */ -import React, {Component} from "react"; -import PropTypes from "prop-types"; -import createHistory from "history/createHashHistory"; -import {Bling as Gpt} from "react-gpt"; // eslint-disable-line import/no-unresolved -import "../log"; -import Home from "./home"; -import Page from "./page"; -import styles from "./styles"; - -Gpt.syncCorrelator(); -Gpt.enableSingleRequest(); - -class App extends Component { - static propTypes = { - location: PropTypes.object, - history: PropTypes.object, - children: PropTypes.node - }; - - createHref(path) { - return `${window.location.origin}${window.location.pathname}#${path}`; - } - - render() { - const {location, children} = this.props; - const adUnitPath = `/4595/nfl.test.open${location.pathname}`; - const props = { - ...this.props, - adUnitPath - }; - - return ( -
- -
- -
- {children && React.cloneElement(children, props)} -
- ); - } -} - -class AppContainer extends Component { - // eslint-disable-next-line react/sort-comp - routes = { - "/Travel/Europe": {component: Home}, - "/Travel/Europe/France": {component: Page, params: {id: "France"}}, - "/Travel/Europe/Spain": {component: Page, params: {id: "Spain"}} - }; - - state = { - routeComponent: this.routes["/Travel/Europe"].component - }; - - UNSAFE_componentWillMount() { - this.unlisten = this.history.listen(location => { - const route = - this.routes[location.pathname] || this.routes["/Travel/Europe"]; - const {component: routeComponent, params} = route; - this.setState({routeComponent, location, params}); - }); - this.history.replace("/Travel/Europe"); - } - - componentWillUnmount() { - this.unlisten(); - } - - history = createHistory(); - - render() { - return ( - - {React.createElement(this.state.routeComponent)} - - ); - } -} - -export default AppContainer; diff --git a/examples/apps/routing/home.js b/examples/apps/routing/home.js deleted file mode 100644 index d2e3a35..0000000 --- a/examples/apps/routing/home.js +++ /dev/null @@ -1,9 +0,0 @@ -import React, {Component} from "react"; - -class Home extends Component { - render() { - return

Home

; - } -} - -export default Home; diff --git a/examples/apps/routing/index.html b/examples/apps/routing/index.html deleted file mode 100644 index a9da1cf..0000000 --- a/examples/apps/routing/index.html +++ /dev/null @@ -1,9 +0,0 @@ - -Router Example - - -

React GPT Examples / Router Example

-
- - - diff --git a/examples/apps/routing/main.js b/examples/apps/routing/main.js deleted file mode 100644 index c341ca7..0000000 --- a/examples/apps/routing/main.js +++ /dev/null @@ -1,5 +0,0 @@ -import React from "react"; -import ReactDOM from "react-dom"; -import App from "./app"; - -ReactDOM.render(, document.getElementById("example")); diff --git a/examples/apps/routing/page.js b/examples/apps/routing/page.js deleted file mode 100644 index 77e7071..0000000 --- a/examples/apps/routing/page.js +++ /dev/null @@ -1,30 +0,0 @@ -/* eslint-disable react/no-multi-comp */ -import React, {Component} from "react"; -import PropTypes from "prop-types"; -import {Bling as Gpt} from "react-gpt"; // eslint-disable-line import/no-unresolved -import styles from "./styles/page"; - -class Page extends Component { - static propTypes = { - adUnitPath: PropTypes.string, - params: PropTypes.object - }; - - render() { - const {adUnitPath, params} = this.props; - return ( -
-

Page: {params.id}

-
- -
-
- ); - } -} - -export default Page; diff --git a/examples/apps/routing/styles/index.js b/examples/apps/routing/styles/index.js deleted file mode 100644 index 49c5e5b..0000000 --- a/examples/apps/routing/styles/index.js +++ /dev/null @@ -1,18 +0,0 @@ -export default { - button: { - marginTop: 20, - padding: "2px 6px 3px", - border: "2px outset buttonface" - }, - dummyHeight: { - width: 1, - height: 2000 - }, - container: { - marginTop: 20, - position: "relative" - }, - topAd: { - margin: "0 auto" - } -}; diff --git a/examples/apps/routing/styles/page.js b/examples/apps/routing/styles/page.js deleted file mode 100644 index 9f01663..0000000 --- a/examples/apps/routing/styles/page.js +++ /dev/null @@ -1,5 +0,0 @@ -export default { - container: { - display: "flex" - } -}; diff --git a/examples/apps/single-request/app.js b/examples/apps/single-request/app.js deleted file mode 100644 index 18c26fc..0000000 --- a/examples/apps/single-request/app.js +++ /dev/null @@ -1,91 +0,0 @@ -import React, {Component} from "react"; -import {StyleRoot} from "radium"; -import {Bling as Gpt} from "react-gpt"; // eslint-disable-line import/no-unresolved -import {canUseDOM} from "fbjs/lib/ExecutionEnvironment"; -import querystring from "querystring"; -import "../log"; -import Button from "./button"; -import styles from "./styles"; - -const qs = canUseDOM - ? querystring.decode(window.location.search.substr(1)) - : {}; - -Gpt.enableSingleRequest().then(value => { - console.log("value", value); -}); -if (qs.mode === "disableInitialLoad") { - Gpt.disableInitialLoad(); -} - -class App extends Component { - state = { - adUnitPath: "/4595/nfl.test.open", - targeting: { - test: "responsive" - } - }; - onClick = params => { - if (params === "refresh") { - Gpt.refresh(); - } else if (params === "disableInitialLoad") { - window.location.href = `${window.location.pathname}?mode=${params}`; - } else if (params === "adUnitPath") { - this.setState({ - adUnitPath: "/4595/nfl.test.open/new" - }); - } else if (params === "targeting") { - this.setState({ - targeting: { - test: "responsive", - changed: Date.now() - } - }); - } - }; - render() { - const {adUnitPath, targeting} = this.state; - return ( - - - - - -
- -
-
-
- -
-
- -
-
-
- ); - } -} - -export default App; diff --git a/examples/apps/single-request/button.js b/examples/apps/single-request/button.js deleted file mode 100644 index 623dc7a..0000000 --- a/examples/apps/single-request/button.js +++ /dev/null @@ -1,22 +0,0 @@ -import React, {Component} from "react"; -import PropTypes from "prop-types"; -import styles from "./styles"; - -export default class Button extends Component { - static propTypes = { - children: PropTypes.node, - onClick: PropTypes.func.isRequired, - params: PropTypes.oneOfType([PropTypes.string, PropTypes.object]) - .isRequired - }; - onClick = () => { - this.props.onClick(this.props.params); - }; - render() { - return ( - - ); - } -} diff --git a/examples/apps/single-request/index.html b/examples/apps/single-request/index.html deleted file mode 100644 index 6660057..0000000 --- a/examples/apps/single-request/index.html +++ /dev/null @@ -1,9 +0,0 @@ - -Single Request Example - - -

React GPT Examples / Single Request Example

-
- - - diff --git a/examples/apps/single-request/main.js b/examples/apps/single-request/main.js deleted file mode 100644 index c341ca7..0000000 --- a/examples/apps/single-request/main.js +++ /dev/null @@ -1,5 +0,0 @@ -import React from "react"; -import ReactDOM from "react-dom"; -import App from "./app"; - -ReactDOM.render(, document.getElementById("example")); diff --git a/examples/apps/single-request/styles/index.js b/examples/apps/single-request/styles/index.js deleted file mode 100644 index 59e3fa4..0000000 --- a/examples/apps/single-request/styles/index.js +++ /dev/null @@ -1,35 +0,0 @@ -export default { - button: { - marginTop: 20, - padding: "2px 6px 3px", - border: "2px outset buttonface" - }, - container: { - marginTop: 20, - position: "relative" - }, - main: { - display: "flex", - flexDirection: "row", - "@media (max-width: 768px)": { - flexDirection: "column" - } - }, - adBorder: { - padding: 10, - border: "1px dashed #666" - }, - lb: { - position: "relative" - }, - mr: { - position: "relative", - order: 1, - flex: "1 1 auto" - }, - ws: { - position: "relative", - order: 2, - flex: "0 1 auto" - } -}; diff --git a/examples/apps/static-ad/app.js b/examples/apps/static-ad/app.js deleted file mode 100644 index 5d1833d..0000000 --- a/examples/apps/static-ad/app.js +++ /dev/null @@ -1,39 +0,0 @@ -import React, {Component} from "react"; -import Radium from "radium"; -import {Bling as Gpt} from "react-gpt"; // eslint-disable-line import/no-unresolved -import "../log"; -import styles from "./styles"; - -@Radium -class App extends Component { - state = { - color: "000000" - }; - - onClick = () => { - this.setState({ - color: this.state.color === "000000" ? "ff0000" : "000000" - }); - }; - - render() { - const {color} = this.state; - return ( -
- -
- `} - slotSize={[728, 90]} - style={styles.adBorder} - /> -
-
- ); - } -} - -export default App; diff --git a/examples/apps/static-ad/index.html b/examples/apps/static-ad/index.html deleted file mode 100644 index 9398038..0000000 --- a/examples/apps/static-ad/index.html +++ /dev/null @@ -1,9 +0,0 @@ - -Static Ad Example - - -

React GPT Examples / Static Ad Example

-
- - - diff --git a/examples/apps/static-ad/main.js b/examples/apps/static-ad/main.js deleted file mode 100644 index c341ca7..0000000 --- a/examples/apps/static-ad/main.js +++ /dev/null @@ -1,5 +0,0 @@ -import React from "react"; -import ReactDOM from "react-dom"; -import App from "./app"; - -ReactDOM.render(, document.getElementById("example")); diff --git a/examples/apps/static-ad/styles/index.js b/examples/apps/static-ad/styles/index.js deleted file mode 100644 index b6fd614..0000000 --- a/examples/apps/static-ad/styles/index.js +++ /dev/null @@ -1,14 +0,0 @@ -export default { - button: { - marginTop: 20, - padding: "2px 6px 3px", - border: "2px outset buttonface" - }, - adBorder: { - padding: 10, - border: "1px dashed #666" - }, - lb: { - position: "relative" - } -}; diff --git a/examples/server/index.js b/examples/server/index.js deleted file mode 100644 index 4d6ea0a..0000000 --- a/examples/server/index.js +++ /dev/null @@ -1,2 +0,0 @@ -require("babel-register"); -require("./server"); diff --git a/examples/server/routes.js b/examples/server/routes.js deleted file mode 100644 index 8b5dca4..0000000 --- a/examples/server/routes.js +++ /dev/null @@ -1,20 +0,0 @@ -import InfiniteScrollApp from "../apps/infinite-scrolling/app"; -import LazyRenderApp from "../apps/lazy-render/app"; -import ResponsiveApp from "../apps/responsive/app"; -import RoutingApp from "../apps/routing/app"; -import SingleRequestApp from "../apps/single-request/app"; -import StaticAdApp from "../apps/static-ad/app"; -import InterstitialApp from "../apps/interstitial/app"; - -export default { - "infinite-scrolling": { - title: "Infinite Scrolling Example", - app: InfiniteScrollApp - }, - "lazy-render": {title: "Lazy Render Example", app: LazyRenderApp}, - responsive: {title: "Responsive Example", app: ResponsiveApp}, - routing: {title: "Routing Example", app: RoutingApp}, - "single-request": {title: "Single Request Example", app: SingleRequestApp}, - "static-ad": {title: "Static Ad Example", app: StaticAdApp}, - interstitial: {title: "Interstitial Example", app: InterstitialApp} -}; diff --git a/examples/server/server.js b/examples/server/server.js deleted file mode 100644 index 67267a5..0000000 --- a/examples/server/server.js +++ /dev/null @@ -1,118 +0,0 @@ -/* eslint-disable no-console, no-use-before-define, import/default */ -import fs from "fs"; -import path from "path"; -import Express from "express"; - -import webpack from "webpack"; -import webpackDevMiddleware from "webpack-dev-middleware"; -import webpackConfig from "../webpack.config.server"; - -import React from "react"; -import {renderToString} from "react-dom/server"; - -import routes from "./routes"; - -const globalStyle = fs.readFileSync( - path.resolve(__dirname, "../apps/global.css"), - "utf8" -); - -const app = new Express(); -const port = 8080; - -app.use( - webpackDevMiddleware(webpack(webpackConfig), { - noInfo: true, - publicPath: webpackConfig.output.publicPath - }) -); -app.use(handleRoutes); - -function handleRoutes(req, res) { - const routeName = req.url.substr(1).split("/")[0]; - - if (routeName === "") { - res.send(renderIndex()); - return; - } - - if (!routes[routeName]) { - res.send(render404()); - return; - } - - const App = routes[routeName].app; - const title = routes[routeName].title; - const html = renderToString( - - ); - - res.send(renderPage(routeName, html, title)); -} - -function renderIndex() { - return ` - - - - React GPT Examples - - - -

React GPT Examples

- - - - `; -} - -function render404() { - return ` - - - - Page Not Found - - - -

Page Not Found

- React GPT Examples - - - `; -} - -function renderPage(name, html, title) { - return ` - - - - ${title} - - - -

React GPT Examples / ${title}

-
${html}
- - - - - `; -} - -app.listen(port, error => { - if (error) { - console.error(error); - } else { - console.info( - `==> 🌎 Listening on port ${port}. Open up http://localhost:${port}/ in your browser.` - ); - } -}); diff --git a/examples/webpack.config.js b/examples/webpack.config.js deleted file mode 100644 index fe740e3..0000000 --- a/examples/webpack.config.js +++ /dev/null @@ -1,55 +0,0 @@ -/* eslint-disable */ -var fs = require("fs"); -var path = require("path"); -var webpack = require("webpack"); - -var appDir = __dirname + "/apps"; - -module.exports = { - devtool: "inline-source-map", - - entry: fs.readdirSync(appDir).reduce(function (entries, dir) { - if (fs.statSync(path.join(appDir, dir)).isDirectory()) { - entries[dir] = ["core-js/fn/promise", path.join(appDir, dir, "main.js")]; - } - - return entries; - }, {}), - - output: { - path: __dirname + "/__build__", - filename: "[name].js", - chunkFilename: "[id].chunk.js", - publicPath: "/__build__/" - }, - - module: { - loaders: [ - { - test: /\.jsx?$/, - exclude: /node_modules/, - loader: "babel", - query: { - presets: ["es2015-without-strict", "stage-0", "react"], - plugins: ["transform-decorators-legacy"] - } - } - ] - }, - - resolve: { - alias: { - "react-gpt": process.cwd() + "/src" - } - }, - - cache: false, - - plugins: [ - new webpack.optimize.CommonsChunkPlugin("shared.js"), - new webpack.DefinePlugin({ - "process.env.NODE_ENV": JSON.stringify(process.env.NODE_ENV || "development") - }) - ] - -}; diff --git a/examples/webpack.config.server.js b/examples/webpack.config.server.js deleted file mode 100644 index fce9809..0000000 --- a/examples/webpack.config.server.js +++ /dev/null @@ -1,54 +0,0 @@ -/* eslint-disable */ -var fs = require("fs"); -var path = require("path"); -var webpack = require("webpack"); - -var appDir = __dirname + "/apps"; - -module.exports = { - devtool: "inline-source-map", - - entry: fs.readdirSync(appDir).reduce(function (entries, dir) { - if (fs.statSync(path.join(appDir, dir)).isDirectory()) { - entries[dir] = ["core-js/fn/promise", path.join(appDir, dir, "main.js")]; - } - - return entries; - }, {}), - - output: { - path: __dirname + "/__build__", - filename: "[name].js", - chunkFilename: "[id].chunk.js", - publicPath: "/__build__/" - }, - - plugins: [ - new webpack.optimize.CommonsChunkPlugin("shared.js"), - new webpack.optimize.OccurenceOrderPlugin(), - new webpack.DefinePlugin({ - "process.env.NODE_ENV": JSON.stringify(process.env.NODE_ENV || "production") - }) - ], - - module: { - loaders: [ - { - test: /\.js$/, - loader: "babel", - exclude: /node_modules/, - include: __dirname, - query: { - presets: ["es2015-without-strict", "stage-0", "react"], - plugins: ["transform-decorators-legacy"] - } - } - ] - }, - - resolve: { - alias: { - "react-gpt": process.cwd() + "/lib" - } - } -}; diff --git a/karma.conf.ci.js b/karma.conf.ci.js deleted file mode 100644 index 989e447..0000000 --- a/karma.conf.ci.js +++ /dev/null @@ -1,17 +0,0 @@ -/* eslint-disable camelcase */ -module.exports = function (config) { - config.set({ - singleRun: true - }); - - console.log("running default test on Chrome"); - config.set({ - customLaunchers: { - Chrome_CI: { - base: "Chrome", - flags: ["--no-sandbox"] - } - }, - browsers: ["Chrome_CI"] - }); -}; diff --git a/karma.conf.js b/karma.conf.js deleted file mode 100644 index 924a316..0000000 --- a/karma.conf.js +++ /dev/null @@ -1,93 +0,0 @@ -var webpack = require("webpack"); -module.exports = function (config) { - config.set({ - basePath: "", - - browserNoActivityTimeout: 60000, - - client: { - mocha: { - reporter: "html" - } - }, - - frameworks: [ - "chai-sinon", - "mocha" - ], - - files: [ - "test/polyfill.js", - "test/**/*spec.js" - ], - - preprocessors: { - "test/polyfill.js": ["webpack"], - "test/**/*spec.js": ["webpack", "sourcemap"] - }, - - coverageReporter: { - reporters: [{ - type: "html", - subdir: "html" - }, { - type: "text" - }, { - type: "lcovonly", - subdir: "." - }] - }, - - webpack: { - devtool: "inline-source-map", - module: { - loaders: [{ - test: /\.js$/, - exclude: /node_modules/, - loader: "babel" - }, { - test: /\.js$/, - // exclude this dirs from coverage - exclude: /(test|node_modules)\//, - loader: "isparta" - }] - }, - resolve: { - extensions: ["", ".js"] - }, - plugins: [ - new webpack.DefinePlugin({ - "process.env.NODE_ENV": JSON.stringify("test") - }) - ], - watch: true - }, - - webpackServer: { - noInfo: true - }, - - reporters: [ - "mocha", - "coverage" - ], - - port: 9876, - - colors: true, - - logLevel: config.LOG_INFO, - - autoWatch: true, - - browsers: ["Chrome"], - - captureTimeout: 60000, - - singleRun: false - }); - - if (process.env.CI) { - require("./karma.conf.ci.js")(config); - } -}; diff --git a/package.json b/package.json index 7432551..c1ac013 100644 --- a/package.json +++ b/package.json @@ -69,16 +69,6 @@ "express": "^4.13.4", "history": "^4.3.0", "isparta-loader": "^2.0.0", - "karma": "^1.3.0", - "karma-chai-sinon": "^0.1.5", - "karma-chrome-launcher": "^2.0.0", - "karma-cli": "^1.0.1", - "karma-coverage": "^1.1.1", - "karma-mocha": "^1.2.0", - "karma-mocha-reporter": "^2.0.0", - "karma-sourcemap-loader": "^0.3.6", - "karma-tap-reporter": "0.0.6", - "karma-webpack": "^1.7.0", "mocha": "^3.1.2", "phantom": "^2.0.4", "prettier": "^1.9.2", diff --git a/src/utils/createManagerTest.js b/src/utils/createManagerTest.js deleted file mode 100644 index d6c2aee..0000000 --- a/src/utils/createManagerTest.js +++ /dev/null @@ -1,10 +0,0 @@ -import {createManager} from "../createManager.js"; -import {GPTMock} from "./mockGPT"; - -export function createManagerTest(config) { - return createManager({ - ...config, - test: true, - GPTMock - }); -} diff --git a/src/utils/mockGPT.js b/src/utils/mockGPT.js deleted file mode 100644 index 12b7343..0000000 --- a/src/utils/mockGPT.js +++ /dev/null @@ -1,288 +0,0 @@ -import {gptAPI, pubadsAPI, slotAPI, gptVersion, pubadsVersion} from "./apiList"; -import Events from "../Events"; - -function createMock(list, obj) { - return list.reduce((mock, [api, type]) => { - if (typeof mock[api] === "undefined") { - if (type === "function") { - mock[api] = (...args) => { - if (args.length) { - return args[0]; - } - return {}; - }; - } else if (type === "boolean") { - mock[api] = true; - } else { - mock[api] = {}; - } - } - return mock; - }, obj || {}); -} - -function getSize(slot) { - const sizes = slot.getSizes(); - let item = sizes; - while (Array.isArray(item[0])) { - item = item[0]; - } - - return item; -} - -class SlotMock { - constructor(adUnitPath, size, divId) { - this.adUnitPath = adUnitPath; - this.size = size; - this.divId = divId; - this.services = []; - this.attributes = {}; - this.categoryExclusions = []; - this._targeting = {}; - } - defineSizeMapping(sizeMapping) { - this.size = sizeMapping; - return this; - } - addService(service) { - this.services.push(service); - } - getServices() { - return this.services; - } - set(key, value) { - this.attributes[key] = value; - return this; - } - get(key) { - return this.attributes[key]; - } - getAttributeKeys() { - return Object.keys(this.attributes); - } - setCollapseEmptyDiv(collapse, collapseBeforeAdFetch) { - this.collapseEmptyDiv = collapse; - this.collapseBeforeAdFetch = collapseBeforeAdFetch; - return this; - } - getCollapseEmptyDiv() { - return this.collapseEmptyDiv; - } - setClickUrl(clickUrl) { - this.clickUrl = clickUrl; - return this; - } - getClickUrl() { - return this.clickUrl; - } - setCategoryExclusion(categoryExclusion) { - this.categoryExclusions.push(categoryExclusion); - return this; - } - getCategoryExclusions() { - return this.categoryExclusions; - } - clearCategoryExclusions() { - this.categoryExclusions = []; - return this; - } - setTargeting(key, value) { - this._targeting[key] = value; - return this; - } - getAdUnitPath() { - return this.adUnitPath; - } - clearTargeting() { - this._targeting = {}; - return this; - } - getTargeting(key) { - return this._targeting && this._targeting[key]; - } - getTargetingKeys() { - return this._targeting && Object.keys(this._targeting); - } - getSizes() { - return this.size; - } - getSlotElementId() { - return this.divId; - } -} -createMock(slotAPI, SlotMock.prototype); - -class SizeMappingBuilderMock { - constructor(config = {}) { - this.config = config; - } - addSize(viewportSize, slotSize) { - if (!this.mapping) { - this.mapping = []; - } - this.mapping.push([viewportSize, slotSize]); - return this; - } - build() { - return this.mapping; - } -} - -class BaseService { - constructor(config = {}) { - this.config = config; - this.listeners = {}; - this.slots = {}; - } - addEventListener(eventType, cb) { - if (!this.listeners[eventType]) { - this.listeners[eventType] = []; - } - this.listeners[eventType].push(cb); - } - getSlots() { - return Object.keys(this.slots).map(key => this.slots[key]); - } -} - -class PubAdsServiceMock extends BaseService { - constructor(config = {}) { - super(config); - this.version = pubadsVersion; - } - getVersion() { - return this.version; - } - refresh(slots) { - if (!slots) { - slots = Object.keys(this.slots).map(key => this.slots[key]); - } - setTimeout(() => { - const key = Events.SLOT_RENDER_ENDED; - slots.forEach(slot => { - if (this.listeners[key]) { - this.listeners[key].forEach(cb => { - const isEmpty = !!this.config.emptyAd; - const event = { - isEmpty, - creativeId: isEmpty ? null : Date.now(), - lineItemId: isEmpty ? null : Date.now(), - serviceName: "publisher_ads", - size: isEmpty ? null : getSize(slot), - slot - }; - cb(event); - }); - } - }); - }, 0); - } -} -createMock(pubadsAPI, PubAdsServiceMock.prototype); - -class CompanionAdsServiceMock extends BaseService { - constructor(config = {}) { - super(config); - } - enableSyncLoading() { - this._enableSyncLoading = true; - } - setRefreshUnfilledSlots(value) { - if (typeof value === "boolean") { - this._refreshUnfilledSlots = value; - } - } -} -class ContentServiceMock extends BaseService { - constructor(config = {}) { - super(config); - } - setContent(slot, content) { - slot._content = content; - } -} - -class GPTMock { - constructor(config = {}) { - this.config = config; - this.version = gptVersion; - this.cmd = {}; - this.cmd.push = cb => { - cb(); - }; - } - pubadsReady = false; - getVersion() { - return this.version; - } - enableServices() { - this.pubadsReady = true; - } - sizeMapping() { - if (!this.sizeMappingBuilder) { - this.sizeMappingBuilder = new SizeMappingBuilderMock(this.config); - } - return this.sizeMappingBuilder; - } - pubads() { - if (!this._pubads) { - this._pubads = new PubAdsServiceMock(this.config); - } - return this._pubads; - } - companionAds() { - if (!this._companionAds) { - this._companionAds = new CompanionAdsServiceMock(this.config); - } - return this._companionAds; - } - content() { - if (!this._content) { - this._content = new ContentServiceMock(this.config); - } - return this._content; - } - defineSlot(adUnitPath, size, divId) { - const slot = new SlotMock(adUnitPath, size, divId); - this.pubads().slots[divId] = slot; - return slot; - } - defineOutOfPageSlot(adUnitPath, divId) { - const slot = new SlotMock(adUnitPath, [1, 1], divId); - this.pubads().slots[divId] = slot; - return slot; - } - display(divId) { - const pubads = this.pubads(); - setTimeout(() => { - Object.keys(pubads.listeners).forEach(key => { - if (pubads.listeners[key]) { - pubads.listeners[key].forEach(cb => { - const slot = pubads.slots[divId]; - const isEmpty = !!this.config.emptyAd; - const event = { - isEmpty, - creativeId: isEmpty ? null : Date.now(), - lineItemId: isEmpty ? null : Date.now(), - serviceName: "publisher_ads", - size: isEmpty ? null : getSize(slot), - slot - }; - cb(event); - }); - } - }); - }, 0); - } -} -createMock(gptAPI, GPTMock.prototype); - -export { - GPTMock, - SlotMock, - SizeMappingBuilderMock, - PubAdsServiceMock, - CompanionAdsServiceMock, - ContentServiceMock -}; diff --git a/test/Bling.spec.js b/test/Bling.spec.js deleted file mode 100644 index 4657e07..0000000 --- a/test/Bling.spec.js +++ /dev/null @@ -1,814 +0,0 @@ -/* eslint-disable react/no-multi-comp */ -import React, {Component} from "react"; -import PropTypes from "prop-types"; -import ReactTestUtils from "react-dom/test-utils"; -import ShallowRenderer from "react-test-renderer/shallow"; -import Bling from "../src/Bling"; -import Events from "../src/Events"; -import {pubadsAPI, APIToCallBeforeServiceEnabled} from "../src/createManager"; -import {gptVersion, pubadsVersion} from "../src/utils/apiList"; -import {createManagerTest} from "../src/utils/createManagerTest"; - -describe("Bling", () => { - let googletag; - const stubs = []; - - beforeEach(() => { - Bling.configure({renderWhenViewable: false}); - Bling.testManager = createManagerTest(); - googletag = Bling._adManager.googletag; - }); - - afterEach(() => { - stubs.forEach(stub => { - stub.restore(); - }); - }); - - it("throws when either slotSize or sizeMapping is missing", () => { - const renderBling = () => { - const renderer = new ShallowRenderer(); - renderer.render(); - }; - - expect(renderBling).to.throw( - "Either 'slotSize' or 'sizeMapping' prop needs to be set." - ); - }); - - it("initially renders empty div with style", () => { - const renderer = new ShallowRenderer(); - renderer.render( - - ); - const result = renderer.getRenderOutput(); - expect(result.type).to.equal("div"); - expect(result.props.style).to.eql({width: 728, height: 90}); - }); - - it("renders fluid to auto width and height", () => { - const renderer = new ShallowRenderer(); - renderer.render( - - ); - const result = renderer.getRenderOutput(); - expect(result.type).to.equal("div"); - expect(result.props.style).to.eql({width: "auto", height: "auto"}); - }); - - it("renders ['fluid'] to auto width and height", () => { - const renderer = new ShallowRenderer(); - renderer.render( - - ); - const result = renderer.getRenderOutput(); - expect(result.type).to.equal("div"); - expect(result.props.style).to.eql({width: "auto", height: "auto"}); - }); - - it("returns gpt version", done => { - Bling.once(Events.READY, () => { - expect(Bling.getGPTVersion()).to.equal(gptVersion); - done(); - }); - - ReactTestUtils.renderIntoDocument( - - ); - }); - - it("returns pubads version", done => { - Bling.once(Events.READY, () => { - expect(Bling.getPubadsVersion()).to.equal(pubadsVersion); - done(); - }); - - ReactTestUtils.renderIntoDocument( - - ); - }); - - it("accepts syncCorrelator", done => { - const render = sinon.stub( - Bling._adManager, - "render", - function syncCorrelator() { - expect(this._syncCorrelator).to.be.true; - render.restore(); - done(); - } - ); - - Bling.syncCorrelator(); - - ReactTestUtils.renderIntoDocument( - - ); - }); - - it("accepts pubads API", done => { - const apiStubs = {}; - pubadsAPI.forEach(method => { - apiStubs[method] = sinon.stub(googletag.pubads(), method); - }); - - Bling.once(Events.RENDER, () => { - APIToCallBeforeServiceEnabled.forEach(method => { - expect(Bling._adManager[`_${method}`]).to.be.true; - }); - Object.keys(apiStubs).forEach(method => { - const stub = apiStubs[method]; - expect(stub.calledOnce).to.be.true; - if (method === "collapseEmptyDivs") { - expect(stub.calledWith(true)).to.be.true; - } else if (method === "setTargeting") { - expect(stub.calledWith("key", "value")).to.be.true; - } - sinon.restore(stub); - }); - done(); - }); - - pubadsAPI.forEach(method => { - let args = []; - if (method === "collapseEmptyDivs") { - args = [true]; - } else if (method === "setTargeting") { - args = ["key", "value"]; - } - Bling[method](...args); - }); - - ReactTestUtils.renderIntoDocument( - - ); - }); - - it("can call pubads API multiple times", done => { - const spy = sinon.stub(googletag.pubads(), "setTargeting"); - - Bling.once(Events.RENDER, () => { - expect(spy.calledTwice).to.be.true; - expect(spy.calledWith("key1", "value1")).to.be.true; - expect(spy.calledWith("key2", "value2")).to.be.true; - sinon.restore(spy); - done(); - }); - - Bling.setTargeting("key1", "value1"); - Bling.setTargeting("key2", "value2"); - - ReactTestUtils.renderIntoDocument( - - ); - }); - - it("call pubads API to set non-personalized Ads when npa prop is set", done => { - const spy = sinon.stub(Bling._adManager, "pubadsProxy"); - const expectedParamTrue = { - method: "setRequestNonPersonalizedAds", - args: [1], - resolve: null, - reject: null - }; - const expectedParamFalse = { - ...expectedParamTrue, - args: [0] - }; - - Bling.once(Events.RENDER, () => { - expect(spy.calledWith(expectedParamTrue)).to.be.true; - expect(spy.calledWith(expectedParamFalse)).to.be.true; - spy.restore(); - done(); - }); - - // Render once to test with non-personalized ads - ReactTestUtils.renderIntoDocument( - - ); - - // Render a second time to test re-enable personalized ads - ReactTestUtils.renderIntoDocument( - - ); - }); - - it("fires once event", done => { - const events = Object.keys(Events).map(key => Events[key]); - - function afterReady() { - Bling.once(Events.READY, () => { - done(); - }); - } - - events.forEach(event => { - Bling.once(event, () => { - events.splice(events.indexOf(event), 1); - if (events.length === 0) { - afterReady(); - } - }); - }); - - ReactTestUtils.renderIntoDocument( - - ); - }); - - it("fires on event", done => { - const events = Object.keys(Events).map(key => Events[key]); - - function afterReady() { - Bling.on(Events.READY, () => { - Bling.removeAllListeners(); - done(); - }); - } - - events.forEach(event => { - Bling.on(event, () => { - events.splice(events.indexOf(event), 1); - if (events.length === 0) { - afterReady(); - } - }); - }); - - ReactTestUtils.renderIntoDocument( - - ); - }); - - it("removes event", done => { - const spy = sinon.spy(); - Bling.on(Events.RENDER, spy); - Bling.removeListener(Events.RENDER, spy); - - Bling.once(Events.SLOT_RENDER_ENDED, () => { - expect(spy.calledOnce).to.be.false; - done(); - }); - - ReactTestUtils.renderIntoDocument( - - ); - }); - - it("refreshes ads", () => { - const refresh = sinon.stub(Bling._adManager, "refresh"); - const slots = []; - const options = {}; - - Bling.refresh(slots, options); - - expect(refresh.calledOnce).to.be.true; - expect(refresh.calledWith(slots, options)).to.be.true; - refresh.restore(); - }); - - it("clears ads", () => { - const clear = sinon.stub(Bling._adManager, "clear"); - const slots = []; - - Bling.clear(slots); - - expect(clear.calledOnce).to.be.true; - expect(clear.calledWith(slots)).to.be.true; - clear.restore(); - }); - - it("handles empty adSlot on clear", () => { - const instance = new Bling(); - instance._adSlot = {}; - - expect(() => { - instance.clear(); - }).to.not.throw("adSlot.getServices is not a function"); - }); - - it("calls getServices on adSlot on clear", () => { - const instance = new Bling(); - const adSlot = sinon.mock({getServices: () => {}}); - adSlot.expects("getServices").once(); - instance._adSlot = adSlot; - instance.clear(); - }); - - it("updates correlator", () => { - const updateCorrelator = sinon.stub( - Bling._adManager, - "updateCorrelator" - ); - - Bling.updateCorrelator(); - - expect(updateCorrelator.calledOnce).to.be.true; - updateCorrelator.restore(); - }); - - it("reflects adUnitPath props to adSlot", done => { - Bling.once(Events.RENDER, () => { - const adSlot = instance.adSlot; - expect(adSlot.getAdUnitPath()).to.equal("/4595/nfl.test.open"); - done(); - }); - - const instance = ReactTestUtils.renderIntoDocument( - - ); - }); - - it("reflects slotSize props to adSlot", done => { - Bling.once(Events.RENDER, () => { - const adSlot = instance.adSlot; - expect(adSlot.getSizes()).to.eql([300, 250]); - done(); - }); - - const instance = ReactTestUtils.renderIntoDocument( - - ); - }); - - it("reflects sizeMapping props to adSlot", done => { - Bling.once(Events.RENDER, () => { - const adSlot = instance.adSlot; - expect(adSlot.getSizes()).to.eql([ - [[0, 0], [320, 50]], - [[750, 200], [728, 90]], - [[1050, 200], [1024, 120]] - ]); - done(); - }); - - const instance = ReactTestUtils.renderIntoDocument( - - ); - }); - - it("reflects targeting props to adSlot", done => { - const targeting = {t1: "v1", t2: [1, 2, 3]}; - - Bling.once(Events.RENDER, () => { - const adSlot = instance.adSlot; - expect(adSlot.getTargetingKeys()).to.eql(["t1", "t2"]); - expect(adSlot.getTargeting("t1")).to.equal(targeting.t1); - expect(adSlot.getTargeting("t2")).to.eql(targeting.t2); - done(); - }); - - const instance = ReactTestUtils.renderIntoDocument( - - ); - }); - - it("reflects collapseEmptyDiv props to adSlot", done => { - Bling.once(Events.RENDER, () => { - expect(ads[0].adSlot.getCollapseEmptyDiv()).to.be.true; - expect(ads[1].adSlot.getCollapseEmptyDiv()).to.be.false; - done(); - }); - - class Wrapper extends Component { - static propTypes = { - children: PropTypes.node - }; - render() { - return
{this.props.children}
; - } - } - - const instance = ReactTestUtils.renderIntoDocument( - - - - - ); - const ads = ReactTestUtils.scryRenderedComponentsWithType( - instance, - Bling - ); - }); - - it("reflects attributes props to adSlot", done => { - Bling.once(Events.RENDER, () => { - const adSlot = instance.adSlot; - expect(adSlot.get("attr1")).to.equal("val1"); - expect(adSlot.get("attr2")).to.equal("val2"); - expect(adSlot.getAttributeKeys()).to.eql(["attr1", "attr2"]); - done(); - }); - - const instance = ReactTestUtils.renderIntoDocument( - - ); - }); - - it("reflects categoryExclusion props to adSlot", done => { - Bling.once(Events.RENDER, () => { - expect(ads[0].adSlot.getCategoryExclusions()).to.eql(["Airline"]); - expect(ads[1].adSlot.getCategoryExclusions()).to.eql(["Airline"]); - done(); - }); - - class Wrapper extends Component { - static propTypes = { - children: PropTypes.node - }; - render() { - return
{this.props.children}
; - } - } - - const instance = ReactTestUtils.renderIntoDocument( - - - - - ); - const ads = ReactTestUtils.scryRenderedComponentsWithType( - instance, - Bling - ); - }); - - it("reflects clickUrl props to adSlot", done => { - Bling.once(Events.RENDER, () => { - const adSlot = instance.adSlot; - expect(adSlot.getClickUrl()).to.equal("clickUrl"); - done(); - }); - - const instance = ReactTestUtils.renderIntoDocument( - - ); - }); - - it("reflects companionAdService props to adSlot", done => { - Bling.once(Events.RENDER, () => { - const adSlot = instance.adSlot; - const services = adSlot.getServices(); - const companionAdService = services.filter( - service => !!service.setRefreshUnfilledSlots - )[0]; - expect(companionAdService._enableSyncLoading).to.be.true; - expect(companionAdService._refreshUnfilledSlots).to.be.true; - done(); - }); - - const instance = ReactTestUtils.renderIntoDocument( - - ); - }); - - it("reflects outOfPage props to adSlot", done => { - Bling.once(Events.RENDER, () => { - const adSlot = instance.adSlot; - expect(adSlot.getSizes()).to.eql([1, 1]); - done(); - }); - - const instance = ReactTestUtils.renderIntoDocument( - - ); - }); - - it("renders static ad", done => { - const content = ``; - - const instance = ReactTestUtils.renderIntoDocument( - - ); - - sinon - .stub(document, "getElementById") - .returns( - ReactTestUtils.findRenderedDOMComponentWithTag(instance, "div") - ); - - Bling.once(Events.RENDER, () => { - expect( - ReactTestUtils.findRenderedDOMComponentWithTag(instance, "div") - .innerHTML - ).to.equal(content); - done(); - }); - }); - - it("does not render ad when renderWhenViewable prop is set to true and the component is not in viewport", done => { - const isInViewport = sinon.stub( - Bling._adManager, - "isInViewport", - () => false - ); - - Bling.once(Events.SLOT_RENDER_ENDED, event => { - expect(event.slot).to.equal(ads[1].adSlot); - isInViewport.restore(); - done(); - }); - - function onScriptLoaded() { - expect(ads[0].state.inViewport).to.be.false; - } - - class Wrapper extends Component { - static propTypes = { - children: PropTypes.node - }; - render() { - return
{this.props.children}
; - } - } - - const instance = ReactTestUtils.renderIntoDocument( - - - - - ); - const ads = ReactTestUtils.scryRenderedComponentsWithType( - instance, - Bling - ); - }); - - it("renders ad as soon as the component gets in the viewport", done => { - const isInViewport = sinon.stub( - Bling._adManager, - "isInViewport", - () => false - ); - - Bling.once(Events.SLOT_RENDER_ENDED, event => { - expect(event.slot).to.equal(ads[0].adSlot); - done(); - }); - - function onScriptLoaded() { - expect(ads[0].state.inViewport).to.be.false; - - // simulate resize/scroll - isInViewport.restore(); - Bling._adManager._foldCheck(); - } - - class Wrapper extends Component { - static propTypes = { - children: PropTypes.node - }; - render() { - return
{this.props.children}
; - } - } - - const instance = ReactTestUtils.renderIntoDocument( - - - - ); - const ads = ReactTestUtils.scryRenderedComponentsWithType( - instance, - Bling - ); - }); - - it("renders slotSize with an array", () => { - const renderer = new ShallowRenderer(); - renderer.render( - - ); - const result = renderer.getRenderOutput(); - expect(result.type).to.equal("div"); - expect(result.props.style).to.eql({width: 300, height: 250}); - }); - - it("sets slotSize to 0,0 on foldCheck of 'fluid' or ['fluid']", done => { - const isInViewport = sinon.spy(Bling._adManager, "isInViewport"); - - class Wrapper extends Component { - onSlotRenderEnded = () => { - expect(isInViewport.args[0][1].join()).to.equal([0, 0].join()); - done(); - }; - render() { - return ( - - ); - } - } - - ReactTestUtils.renderIntoDocument(); - }); - - it("refreshes ad when refreshable prop changes", done => { - let count = 0; - - Bling.syncCorrelator(); - - class Wrapper extends Component { - state = { - targeting: {prop: "val"} - }; - onSlotRenderEnded = event => { - if (count === 0) { - expect(event.slot.getTargeting("prop")).to.equal("val"); - this.setState({ - targeting: {prop: "val2"} - }); - count++; - } else { - expect(event.slot.getTargeting("prop")).to.equal("val2"); - done(); - } - }; - render() { - const {targeting} = this.state; - return ( - - ); - } - } - - ReactTestUtils.renderIntoDocument(); - }); - - it("refreshes ad when refreshableProps changes w/o sync correlator", done => { - let count = 0; - - Bling.syncCorrelator(false); - - class Wrapper extends Component { - state = { - targeting: {prop: "val"} - }; - onSlotRenderEnded = event => { - if (count === 0) { - expect(event.slot.getTargeting("prop")).to.equal("val"); - this.setState({ - targeting: {prop: "val2"} - }); - count++; - } else { - expect(event.slot.getTargeting("prop")).to.equal("val2"); - done(); - } - }; - render() { - const {targeting} = this.state; - return ( - - ); - } - } - - ReactTestUtils.renderIntoDocument(); - }); - - it("re-renders ad when reRenderProps changes", done => { - let count = 0; - - Bling.syncCorrelator(); - - class Wrapper extends Component { - state = { - adUnitPath: "/4595/nfl.test.open" - }; - onSlotRenderEnded = event => { - if (count === 0) { - expect(event.slot.getAdUnitPath()).to.equal( - "/4595/nfl.test.open" - ); - this.setState({ - adUnitPath: "/4595/nfl.test.open/new" - }); - count++; - } else { - expect(event.slot.getAdUnitPath()).to.equal( - "/4595/nfl.test.open/new" - ); - done(); - } - }; - render() { - const {adUnitPath} = this.state; - return ( - - ); - } - } - - ReactTestUtils.renderIntoDocument(); - }); - - it("removes itself from registry when unmounted", () => { - const instance = ReactTestUtils.renderIntoDocument( - - ); - instance.componentWillUnmount(); - expect(Bling._adManager.getMountedInstances()).to.have.length(0); - }); - - it("does not call props.onSlotLoaded if it has been unmounted", () => { - const onScriptLoaded = sinon.stub(); - const instance = ReactTestUtils.renderIntoDocument( - - ); - onScriptLoaded.reset(); - instance.componentWillUnmount(); - instance.onScriptLoaded(); - expect(onScriptLoaded.called).to.be.false; - }); -}); diff --git a/test/createManager.spec.js b/test/createManager.spec.js deleted file mode 100644 index 071ffb2..0000000 --- a/test/createManager.spec.js +++ /dev/null @@ -1,640 +0,0 @@ -import { - createManager, - AdManager, - pubadsAPI, - APIToCallBeforeServiceEnabled -} from "../src/createManager"; -import Events from "../src/Events"; -import {gptVersion} from "../src/utils/apiList"; -import {createManagerTest} from "../src/utils/createManagerTest"; - -describe("createManager", () => { - let googletag; - let adManager; - - beforeEach(() => { - adManager = createManagerTest(); - googletag = adManager.googletag; - }); - - afterEach(() => { - window.googletag = undefined; - }); - - it("accepts syncCorrelator", () => { - adManager.syncCorrelator(true); - expect(adManager._syncCorrelator).to.be.true; - }); - - it("accepts pubads API before pubads is ready", done => { - const apiStubs = {}; - pubadsAPI.forEach(method => { - apiStubs[method] = sinon.stub(googletag.pubads(), method); - }); - - pubadsAPI.forEach(method => { - let args = []; - if (method === "collapseEmptyDivs") { - args = [true]; - } else if (method === "setTargeting") { - args = ["key", "value"]; - } - adManager.pubadsProxy({method, args}); - }); - - adManager.once(Events.RENDER, () => { - APIToCallBeforeServiceEnabled.forEach(method => { - expect(adManager[`_${method}`]).to.be.true; - }); - Object.keys(apiStubs).forEach(method => { - const stub = apiStubs[method]; - expect(stub.calledOnce).to.be.true; - if (method === "collapseEmptyDivs") { - expect(stub.calledWith(true)).to.be.true; - } else if (method === "setTargeting") { - expect(stub.calledWith("key", "value")).to.be.true; - } - sinon.restore(stub); - }); - - done(); - }); - - adManager.render(); - }); - - it("accepts pubads API after pubads is ready", done => { - const apiStubs = {}; - pubadsAPI.forEach(method => { - apiStubs[method] = sinon.stub(googletag.pubads(), method); - }); - - adManager.once(Events.RENDER, () => { - pubadsAPI.forEach(method => { - let args = []; - if (method === "collapseEmptyDivs") { - args = [true]; - } else if (method === "setTargeting") { - args = ["key", "value"]; - } - adManager.pubadsProxy({method, args}); - }); - APIToCallBeforeServiceEnabled.forEach(method => { - expect(adManager[`_${method}`]).to.be.true; - }); - Object.keys(apiStubs).forEach(method => { - const stub = apiStubs[method]; - expect(stub.calledOnce).to.be.true; - if (method === "collapseEmptyDivs") { - expect(stub.calledWith(true)).to.be.true; - } else if (method === "setTargeting") { - expect(stub.calledWith("key", "value")).to.be.true; - } - sinon.restore(stub); - }); - - done(); - }); - - adManager.render(); - }); - - it("loads gpt", done => { - adManager - .load("//securepubads.g.doubleclick.net/tag/js/gpt.js") - .then(result => { - expect(result).to.be.an("object"); - expect(adManager.isLoaded).to.be.true; - done(); - }) - .catch(done); - }); - - it("uses gpt when already exists", done => { - window.googletag = googletag; - adManager - .load("//securepubads.g.doubleclick.net/tag/js/gpt-invalid.js") - .then(() => { - expect(adManager.isLoaded).to.be.true; - done(); - }) - .catch(done); - }); - - it("handles missing url", done => { - adManager = createManager(); - adManager.load("").catch(err => { - expect(err.message).to.equal("url is missing"); - done(); - }); - }); - - it("handles invalid url", done => { - adManager = createManager(); - adManager - .load("//securepubads.g.doubleclick.net/tag/js/gpt-invalid.js") - .catch(err => { - expect(err.message).to.equal("failed to load script"); - done(); - }); - }); - - it("handles gpt existence", done => { - adManager = createManager(); - adManager.load("//www.google.com/jsapi").catch(err => { - expect(err.message).to.equal("window.googletag is not available"); - done(); - }); - }); - - it("returns gpt version", () => { - expect(adManager.getGPTVersion()).to.equal(gptVersion); - }); - - it("maintains instance list", () => { - const _toggleListener = sinon.stub( - AdManager.prototype, - "_toggleListener" - ); - const addMQListener = sinon.stub(AdManager.prototype, "addMQListener"); - const removeMQListener = sinon.stub( - AdManager.prototype, - "removeMQListener" - ); - const instances = [{}, {}]; - - adManager.addInstance(instances[0]); - - expect(_toggleListener.calledWith(true)).to.be.true; - expect(_toggleListener.calledOnce).to.be.true; - expect(addMQListener.calledWith(instances[0])).to.be.true; - expect(addMQListener.calledOnce).to.be.true; - - adManager.addInstance(instances[1]); - - expect(_toggleListener.calledOnce).to.be.true; - expect(addMQListener.calledWith(instances[1])).to.be.true; - expect(addMQListener.calledTwice).to.be.true; - - adManager.removeInstance(instances[0]); - - expect(removeMQListener.calledWith(instances[0])).to.be.true; - expect(removeMQListener.calledOnce).to.be.true; - - adManager.removeInstance(instances[1]); - - expect(_toggleListener.calledWith(false)).to.be.true; - expect(_toggleListener.calledTwice).to.be.true; - expect(removeMQListener.calledWith(instances[1])).to.be.true; - expect(removeMQListener.calledTwice).to.be.true; - - _toggleListener.restore(); - addMQListener.restore(); - removeMQListener.restore(); - }); - - it("adds/removes instance to matchMedia query listener", () => { - // case 1 - missing `sizeMapping` - - let instance = { - props: {} - }; - - adManager.addInstance(instance); - - expect(adManager._mqls).to.be.undefined; - - adManager.removeInstance(instance); - - // case 2 - non-array `sizeMapping` - - instance = { - props: { - sizeMapping: 100 - } - }; - - adManager.addInstance(instance); - - expect(adManager._mqls).to.be.undefined; - - adManager.removeInstance(instance); - - // case 3 - invalid `sizeMapping` item - - instance = { - props: { - sizeMapping: [320, 50] - } - }; - - adManager.addInstance(instance); - - expect(adManager._mqls).to.be.undefined; - - adManager.removeInstance(instance); - - // case 4 - valid `sizeMapping` item - - instance = { - props: { - sizeMapping: [{viewport: [0, 0], slot: [320, 50]}] - } - }; - - adManager.addInstance(instance); - - expect(adManager._mqls).to.be.an("object"); - expect(adManager._mqls["0"]).to.be.an("object"); - expect(adManager._mqls["0"].listeners.length).to.be.equal(1); - - adManager.removeInstance(instance); - - // case 5 - multiple instance listens for the same matchMedia query - - let instance2 = { - props: { - sizeMapping: [{viewport: [0, 0], slot: [320, 50]}] - } - }; - - adManager.addInstance(instance); - adManager.addInstance(instance2); - - expect(adManager._mqls).to.be.an("object"); - expect(adManager._mqls["0"]).to.be.an("object"); - expect(adManager._mqls["0"].listeners.length).to.be.equal(2); - - adManager.removeInstance(instance); - - expect(adManager._mqls["0"].listeners.length).to.be.equal(1); - - adManager.removeInstance(instance2); - - expect(adManager._mqls).to.be.an("object"); - expect(adManager._mqls["0"]).to.be.undefined; - - // case 6 - removing an instance that's not in listeners won't accidentally remove listeners - - instance2 = { - props: {} - }; - - adManager.addInstance(instance); - adManager.addInstance(instance2); - - adManager.removeInstance(instance2); - - expect(adManager._mqls).to.be.an("object"); - expect(adManager._mqls["0"]).to.be.an("object"); - expect(adManager._mqls["0"].listeners.length).to.be.equal(1); - }); - - it("handles media query change", () => { - adManager.syncCorrelator(); - - const refresh = sinon.stub(googletag.pubads(), "refresh"); - - googletag.pubadsReady = true; - - const instance = { - props: { - sizeMapping: [{viewport: [0, 0], slot: [320, 50]}] - }, - onMediaQueryChange() {} - }; - - const instanceOnMediaQueryChange = sinon.stub( - instance, - "onMediaQueryChange" - ); - - adManager.addInstance(instance); - adManager._handleMediaQueryChange({ - media: "(min-width: 0px)" - }); - - expect(refresh.calledOnce).to.be.true; - - adManager.syncCorrelator(false); - - adManager._handleMediaQueryChange({ - media: "(min-width: 0px)" - }); - - expect(instanceOnMediaQueryChange.calledOnce).to.be.true; - - // IE - adManager._handleMediaQueryChange({ - media: "all and (min-width:0px)" - }); - - expect(instanceOnMediaQueryChange.calledTwice).to.be.true; - - adManager.removeInstance(instance); - - refresh.restore(); - instanceOnMediaQueryChange.restore(); - }); - - it("debounces render", done => { - const enableServices = sinon.stub( - googletag, - "enableServices", - googletag.enableServices - ); - - adManager.once(Events.RENDER, () => { - expect(enableServices.calledOnce).to.be.true; - enableServices.restore(); - done(); - }); - - adManager.render(); - adManager.render(); - adManager.render(); - }); - - it("executes render once", done => { - const enableServices = sinon.stub( - googletag, - "enableServices", - googletag.enableServices - ); - - adManager.once(Events.RENDER, () => { - expect(enableServices.calledOnce).to.be.true; - - setTimeout(() => { - expect(enableServices.calledTwice).to.be.false; - enableServices.restore(); - done(); - }, 300); - - adManager.render(); - }); - - adManager.render(); - adManager.render(); - adManager.render(); - }); - - it("manages initial render", done => { - adManager.pubadsProxy({method: "disableInitialLoad"}); - adManager.pubadsProxy({method: "collapseEmptyDivs", args: [false]}); - - const disableInitialLoad = sinon.stub( - googletag.pubads(), - "disableInitialLoad" - ); - const collapseEmptyDivs = sinon.stub( - googletag.pubads(), - "collapseEmptyDivs" - ); - - const instance = { - props: { - sizeMapping: [{viewport: [0, 0], slot: [320, 50]}] - }, - notInViewport() { - return false; - }, - defineSlot() {}, - display() {}, - adSlot: googletag.defineSlot("/", []) - }; - - const defineSlot = sinon.stub(instance, "defineSlot"); - const display = sinon.stub(instance, "display"); - - adManager.addInstance(instance); - - adManager.once(Events.RENDER, () => { - expect(disableInitialLoad.calledOnce).to.be.true; - expect(collapseEmptyDivs.calledWith(false)).to.be.true; - expect(defineSlot.calledOnce).to.be.true; - expect(display.calledOnce).to.be.true; - - disableInitialLoad.restore(); - collapseEmptyDivs.restore(); - defineSlot.restore(); - display.restore(); - adManager.removeInstance(instance); - done(); - }); - - adManager.render(); - adManager.render(); - adManager.render(); - }); - - it("throttles foldCheck", done => { - const instance = { - props: { - sizeMapping: [{viewport: [0, 0], slot: [320, 50]}] - }, - getRenderWhenViewable() { - return true; - }, - foldCheck() {} - }; - - const instance2 = { - props: { - sizeMapping: [{viewport: [0, 0], slot: [320, 50]}] - }, - getRenderWhenViewable() { - return false; - }, - foldCheck() {} - }; - - const foldCheck = sinon.stub(instance, "foldCheck"); - const foldCheck2 = sinon.stub(instance2, "foldCheck"); - const getRenderWhenViewable = sinon.spy( - instance, - "getRenderWhenViewable" - ); - const getRenderWhenViewable2 = sinon.spy( - instance2, - "getRenderWhenViewable" - ); - const managerFoldCheck = sinon.spy(adManager, "_foldCheck"); - const timer = sinon.spy(adManager, "_getTimer"); - - adManager.addInstance(instance); - adManager.addInstance(instance2); - - const start = Date.now(); - adManager._foldCheck(); - adManager._foldCheck(); - setTimeout(() => { - adManager._foldCheck(); - }, 5); - setTimeout(() => { - adManager._foldCheck(); - }, 10); - setTimeout(() => { - adManager._foldCheck(); - }, 15); - - setTimeout(() => { - expect(managerFoldCheck.callCount).to.equal(5); - expect(timer.calledTwice).to.be.true; - expect(timer.returnValues[1] - timer.returnValues[0]).to.be.above( - 19 - ); // timer above 20ms timeout - expect(timer.returnValues[0] - start).to.be.below(5); // should start ~immediately - expect(foldCheck.calledTwice).to.be.true; - expect(foldCheck2.notCalled).to.be.true; - - foldCheck.restore(); - foldCheck2.restore(); - getRenderWhenViewable.restore(); - getRenderWhenViewable2.restore(); - managerFoldCheck.restore(); - timer.restore(); - adManager.removeInstance(instance); - adManager.removeInstance(instance2); - done(); - }, 100); - }); - - it("renders all ads", done => { - googletag.apiReady = false; - const updateCorrelator = sinon.stub( - AdManager.prototype, - "updateCorrelator" - ); - - const instance = { - props: {}, - forceUpdate() {} - }; - - const instance2 = { - props: {}, - forceUpdate() {} - }; - - const forceUpdate = sinon.stub(instance, "forceUpdate"); - const forceUpdate2 = sinon.stub(instance2, "forceUpdate"); - - adManager.addInstance(instance); - adManager.addInstance(instance2); - - setTimeout(() => { - expect(updateCorrelator.calledOnce).to.be.false; - expect(forceUpdate.calledOnce).to.be.false; - expect(forceUpdate2.calledOnce).to.be.false; - - googletag.apiReady = true; - - setTimeout(() => { - expect(updateCorrelator.calledOnce).to.be.true; - expect(forceUpdate.calledOnce).to.be.true; - expect(forceUpdate2.calledOnce).to.be.true; - - updateCorrelator.restore(); - forceUpdate.restore(); - forceUpdate2.restore(); - adManager.removeInstance(instance); - adManager.removeInstance(instance2); - done(); - }, 300); - - adManager.renderAll(); - }, 300); - - adManager.renderAll(); - }); - - it("refreshes ads", () => { - const refresh = sinon.stub(googletag.pubads(), "refresh"); - - adManager.refresh(); - expect(refresh.calledOnce).to.be.false; - - googletag.pubadsReady = true; - adManager.refresh(); - expect(refresh.calledOnce).to.be.true; - refresh.restore(); - }); - - it("uses a custom refresh function", () => { - const refreshFn = sinon.spy(); - adManager.configure({ - refresh: refreshFn - }); - googletag.pubadsReady = true; - adManager.refresh(); - expect(refreshFn.calledOnce).to.be.true; - }); - - it("clears ads", () => { - const clear = sinon.stub(googletag.pubads(), "clear"); - - adManager.clear(); - expect(clear.calledOnce).to.be.false; - - googletag.pubadsReady = true; - adManager.clear(); - expect(clear.calledOnce).to.be.true; - clear.restore(); - }); - - it("calls prop function for gpt event", done => { - const listeners = []; - const slot = googletag.defineSlot("/", []); - const addEventListener = sinon.stub( - googletag.pubads(), - "addEventListener", - (eventType, cb) => { - if (!listeners[eventType]) { - listeners[eventType] = []; - } - listeners[eventType].push(cb); - } - ); - - const instance = { - props: { - onSlotRenderEnded() {} - }, - adSlot: slot, - notInViewport() { - return false; - }, - defineSlot() {}, - display() {} - }; - - const display = sinon.stub(instance, "display", () => { - Object.keys(listeners).forEach(key => { - if (listeners[key]) { - listeners[key].forEach(cb => { - cb({slot}); - }); - } - }); - }); - - const onSlotRenderEnded = sinon.stub( - instance.props, - "onSlotRenderEnded" - ); - - adManager.addInstance(instance); - - adManager.once(Events.RENDER, () => { - expect(onSlotRenderEnded.calledOnce).to.be.true; - addEventListener.restore(); - display.restore(); - onSlotRenderEnded.restore(); - adManager.removeInstance(instance); - done(); - }); - - adManager.render(); - }); -}); diff --git a/test/isInViewport.spec.js b/test/isInViewport.spec.js deleted file mode 100644 index b3dc546..0000000 --- a/test/isInViewport.spec.js +++ /dev/null @@ -1,18 +0,0 @@ -import isInViewport from "../src/utils/isInViewport"; - -describe("isInViewport", () => { - it("returns false when an element is invalid", () => { - let result = isInViewport(); - expect(result).to.be.false; - const textNode = document.createTextNode("text"); - result = isInViewport(textNode); - expect(result).to.be.false; - }); - - it("checks intersection with viewport", () => { - const el = document.createElement("div"); - document.body.appendChild(el); - const result = isInViewport(el, [0, 0], 0); - expect(result).to.be.true; - }); -}); diff --git a/test/mockGPT.spec.js b/test/mockGPT.spec.js deleted file mode 100644 index ec625f9..0000000 --- a/test/mockGPT.spec.js +++ /dev/null @@ -1,79 +0,0 @@ -import { - GPTMock, - SlotMock, - SizeMappingBuilderMock, - PubAdsServiceMock, - CompanionAdsServiceMock, - ContentServiceMock -} from "../src/utils/mockGPT"; -import {gptVersion} from "../src/utils/apiList"; - -describe("mockGPT", () => { - let gptMock; - - beforeEach(() => { - gptMock = new GPTMock(); - }); - - it("returns version from getVersion()", () => { - expect(gptMock.getVersion()).to.equal(gptVersion); - }); - - it("returns sizeMappingBuilder from sizeMapping()", () => { - const sizeMappingBuilder = gptMock.sizeMapping(); - expect(sizeMappingBuilder).to.be.an.instanceof(SizeMappingBuilderMock); - const sizeMappingBuilder2 = sizeMappingBuilder - .addSize([1024, 768], [970, 250]) - .addSize([980, 690], [728, 90]) - .addSize([640, 480], "fluid"); - expect(sizeMappingBuilder).to.equal(sizeMappingBuilder2); - const mapping = sizeMappingBuilder2.build(); - expect(mapping).to.eql([ - [[1024, 768], [970, 250]], - [[980, 690], [728, 90]], - [[640, 480], "fluid"] - ]); - }); - - it("returns pubAdsService from pubads()", () => { - const pubAdsService = gptMock.pubads(); - expect(pubAdsService).to.be.an.instanceof(PubAdsServiceMock); - }); - - it("returns companionAdsService from companionAds()", () => { - const companionAdsService = gptMock.companionAds(); - expect(companionAdsService).to.be.an.instanceof( - CompanionAdsServiceMock - ); - }); - - it("returns contentService from content()", () => { - const contentService = gptMock.content(); - expect(contentService).to.be.an.instanceof(ContentServiceMock); - }); - - it("returns slot from defineSlot()", () => { - const adUnitPath = "/1234/abc"; - const size = [728, 90]; - const divId = "div-1"; - const slot = gptMock.defineSlot(adUnitPath, size, divId); - expect(slot).to.be.an.instanceof(SlotMock); - expect(slot.getSlotElementId()).to.equal(divId); - expect(slot.getSizes()).to.equal(size); - expect(slot.getAdUnitPath()).to.equal(adUnitPath); - - const adUnitPath2 = "/1234/def"; - const size2 = [300, 250]; - const divId2 = "div-2"; - const slot2 = gptMock.defineSlot(adUnitPath2, size2, divId2); - - const pubAdsService = gptMock.pubads(); - expect(pubAdsService.getSlots()).to.eql([slot, slot2]); - }); - - it("executes callback from cmd()", () => { - const spy = sinon.spy(); - gptMock.cmd.push(spy); - expect(spy.called).to.be.true; - }); -}); diff --git a/test/polyfill.js b/test/polyfill.js deleted file mode 100644 index c4d4bc0..0000000 --- a/test/polyfill.js +++ /dev/null @@ -1 +0,0 @@ -import "core-js/fn/promise";