Github: https://github.com/railsstudent/image-gallery-native-js
-
yarn add puppeteer mocha chai
yarn add puppeteer mocha chai
-
Create bootstrap.js file to share global variables among tests. Expose chai.expect, chai.assert and an instance of browser
'use strict';
const puppeteer = require(‘puppeteer’); const chai = require(‘chai’); const expect = chai.expect; const globalVariables = { browser: global.browser, expect: global.expect };
// puppeteer options const opts = { headless: true, slowMo: 150, timeout: 50000 };
// expose variables before (async function () { global.expect = expect; global.browser = await puppeteer.launch(opts); });
// close browser and reset global variables after (function () { global.browser.close();
global.browser = globalVariables.browser; global.expect = globalVariables.expect; });
-
Puppeteer creates a headless browser that timeout after 50 seconds and slow down operation by 150 milliseconds.
// puppeteer options const opts = { headless: true, slowMo: 150, timeout: 50000 }; -
Set up npm script commands in package.json to load the variables in bootstrap.js and execute all UI test cases in test/gallery.test.js directory
"scripts": { "serve:test": "gulp build && http-server dist/ -p 8000", "puppeteer": "rm ./test/*.png; SCREEN_SHOT=false mocha test/bootstrap.js test/gallery.test.js", "puppeteer-screenshot": "rm ./test/*.png; SCREEN_SHOT=true mocha test/bootstrap.js test/gallery.test.js" } -
Write mocha test case in test file.
describe('gallery test', function() { let page; this.timeout(TIMEOUT);
before(async () => { try { page = await browser.newPage(); await page.goto(‘http://localhost:8000/‘); } catch (e) { console.error(e); } });
after(async () => { await page.close(); });
it(‘Shows first image src is not blank and has correct caption and visible buttons’, async () => { try { await page.waitForSelector(‘.image:nth-child(1)’, { visible: true, timeout: 0 }); await page.screenshot( { path: ‘./test/test4.png’ });
const imageElement = await page.$('.image:nth-child(1)');
await imageElement.click();
await page.screenshot( {
path: './test/test5.png'
});
const modalHandle = await page.$('.modal.show');
const imageSrc = await page.evaluate((modal) =>
modal.querySelector('#modal-image').src, modalHandle);
const caption = await page.evaluate((modal) =>
modal.querySelector('#caption').innerText, modalHandle);
const [btnCloseDisplay, btnCloseOpacity,
btnLeftDisplay, btnLeftOpacity,
btnRightDisplay, btnRightOpacity
] = await page.evaluate((modal) => {
const { opacity: closeOpacity, display: closeDisplay }
= window.getComputedStyle(modal.querySelector('.close'));
const { opacity: leftOpacity, display: leftDisplay }
= window.getComputedStyle(modal.querySelector('.left-arrow'));
const { opacity: rightOpacity, display: rightDisplay }
= window.getComputedStyle(modal.querySelector('.right-arrow'));
return [
closeDisplay, closeOpacity,
leftDisplay, leftOpacity,
rightDisplay, rightOpacity
];
}, modalHandle);
expect(imageSrc).to.not.equal('');
expect(caption).to.equal(`1 of ${NUM_IMAGES}`);
expect(btnCloseDisplay).to.equal('inline-block');
expect(btnRightDisplay).to.equal('inline-block');
expect(btnLeftDisplay).to.be.equal('block');
expect(btnCloseOpacity).to.equal('1');
expect(btnRightOpacity).to.equal('1');
expect(btnLeftOpacity).to.equal('0');
const closeHandle = await page.$('.modal.show .close');
await closeHandle.click();
closeHandle.dispose();
modalHandle.dispose();
} catch (e) {
console.error(e);
throw e;
}
}); });
-
Build development version and serve website at http://localhost:8000
yarn serve:test
-
Run UI test cases without creating screen shots
yarn puppeteer
-
Run UI test cases that creates screen shots
yarn puppeteer-screenshot
Finally, we are done.