/* eslint-disable no-console */ const puppeteer = require('puppeteer'); const pa11y = require('pa11y'); const shitlistCheck = require('./pa11y-utilities.js').shitlistCheck; const shitlist = require('./../a11y_shitlist.json'); const NUMBER_OF_BROWSERS = 5; async function runPa11y() { const browsers = [ { browser: await puppeteer.launch(), taken: new Promise((resolve) => { resolve(); }), }, { browser: await puppeteer.launch(), taken: new Promise((resolve) => { resolve(); }), }, { browser: await puppeteer.launch(), taken: new Promise((resolve) => { resolve(); }), }, { browser: await puppeteer.launch(), taken: new Promise((resolve) => { resolve(); }), }, { browser: await puppeteer.launch(), taken: new Promise((resolve) => { resolve(); }), }, ]; await browsers.forEach(async (instance) => { instance.page = await instance.browser.newPage(); }); let browserIndex = 0; const results = []; const setupBrowser = browsers[0].browser; const page = await setupBrowser.newPage(); const iframePath = `file://${__dirname}/../build/storybook/static/iframe.html`; const stories = await page .goto(iframePath) .then(() => page.evaluate(() => window.__STORYBOOK_CLIENT_API__.raw())); const storyIDs = stories.reduce((memo, story) => { // There is no need to test the Playground, or the "All Examples" stories const isSkippedStory = story.kind === 'Playground|Playground' || story.name === 'All Examples'; if (!isSkippedStory) { memo.push(`${encodeURIComponent(story.id)}`); } return memo; }, []); storyIDs.forEach((queryString) => { const currentBrowser = browsers[browserIndex % NUMBER_OF_BROWSERS]; browserIndex++; currentBrowser.taken = currentBrowser.taken.then(async () => { console.log('Testing ', queryString); const result = await pa11y(`${iframePath}?id=${queryString}`, { browser: currentBrowser.browser, ignore: [ // Missing lang attribute on tag // Storybook does not include this property so ignore it 'WCAG2AA.Principle3.Guideline3_1.3_1_1.H57.2', ], }); result.exampleID = queryString; delete result.pageUrl; results.push(result); }); }); await Promise.all(browsers.map((instance) => instance.taken)); await Promise.all(browsers.map((instance) => instance.browser.close())); return results; } (async () => { let rawResults; try { rawResults = await runPa11y(); if (rawResults.length === 0) { throw new Error('Component URLs could not be crawled'); } } catch (error) { console.log(error); process.exit(1); } const {results, remainingIssues} = shitlistCheck(rawResults, shitlist); if (remainingIssues) { console.log( ` ======================================================================== The following items were fixed, and therefore should be removed from the shitlist. Please edit the file a11y_shitlist.json to remove them and run these tests again.', ======================================================================== `, ); remainingIssues.forEach((issue) => { console.log( '------------------------------------------------------------------------', ); console.log(issue.exampleID); console.log( '------------------------------------------------------------------------', ); console.log(JSON.stringify(issue.issues, null, 2)); }); } console.log( ` ======================================================================== The following issues were discovered and need to be fixed before this code can be merged ======================================================================== `, ); if (results.length) { results.forEach((result) => { console.log( '------------------------------------------------------------------------', ); console.log(result.exampleID); console.log( '------------------------------------------------------------------------', ); console.log(JSON.stringify(result.issues, null, 2)); }); } else { console.log('No issues!'); } if (results.length || remainingIssues) { process.exit(1); } process.exit(0); })();