From 4933347fb4febbd52288556ff3c99b58da04b8d4 Mon Sep 17 00:00:00 2001 From: Nathan Bierema Date: Tue, 29 Sep 2020 08:27:04 -0400 Subject: [PATCH] progress --- .../.eslintrc.js | 16 ----- .../package.json | 1 + .../redux-devtools-trace-monitor/.babelrc | 13 ++-- .../redux-devtools-trace-monitor/package.json | 8 ++- .../src/StackTraceTab.tsx | 66 ++++++++++++------ .../src/openFile.ts | 64 +++++++++-------- .../components/CodeBlock.tsx | 13 ++-- .../components/Collapsible.tsx | 28 ++++---- .../containers/StackFrame.tsx | 49 ++++++------- .../containers/StackFrameCodeBlock.tsx | 39 ++++------- .../containers/StackTrace.tsx | 23 +++---- .../utils/dom/absolutifyCaret.ts | 5 +- .../src/react-error-overlay/utils/dom/css.ts | 10 +-- .../utils/generateAnsiHTML.ts | 26 ++++--- .../utils/getLinesAround.ts | 1 - .../react-error-overlay/utils/getPrettyURL.ts | 21 +++--- .../react-error-overlay/utils/getSourceMap.ts | 19 +++--- .../utils/getStackFrames.ts | 17 +++-- .../utils/isBultinErrorName.ts | 3 +- .../utils/isInternalFile.ts | 6 +- .../src/react-error-overlay/utils/mapper.ts | 5 +- .../utils/parseCompileError.ts | 27 ++++---- .../src/react-error-overlay/utils/parser.ts | 12 ++-- .../react-error-overlay/utils/pollyfills.ts | 1 + .../react-error-overlay/utils/stack-frame.ts | 8 +-- .../src/react-error-overlay/utils/unmapper.ts | 11 ++- .../src/settle-promise.ts | 3 + .../test/StackTraceTab.spec.js | 55 --------------- .../test/StackTraceTab.spec.tsx | 68 +++++++++++++++++++ tsconfig.base.json | 2 +- yarn.lock | 30 ++++++++ 31 files changed, 354 insertions(+), 296 deletions(-) create mode 100644 packages/redux-devtools-trace-monitor/src/settle-promise.ts delete mode 100644 packages/redux-devtools-trace-monitor/test/StackTraceTab.spec.js create mode 100644 packages/redux-devtools-trace-monitor/test/StackTraceTab.spec.tsx diff --git a/packages/redux-devtools-test-generator/.eslintrc.js b/packages/redux-devtools-test-generator/.eslintrc.js index 03a5a706..eca0de40 100644 --- a/packages/redux-devtools-test-generator/.eslintrc.js +++ b/packages/redux-devtools-test-generator/.eslintrc.js @@ -9,22 +9,6 @@ module.exports = { project: ['./tsconfig.json'], }, }, - { - files: ['demo/**/*.ts', 'demo/**/*.tsx'], - extends: '../../eslintrc.ts.react.base.json', - parserOptions: { - tsconfigRootDir: __dirname, - project: ['./demo/tsconfig.json'], - }, - }, - { - files: ['demo/config/webpack.config.ts'], - extends: '../../eslintrc.ts.base.json', - parserOptions: { - tsconfigRootDir: __dirname, - project: ['./demo/config/tsconfig.json'], - }, - }, { files: ['test/*.ts', 'test/*.tsx'], extends: '../../eslintrc.ts.react.jest.base.json', diff --git a/packages/redux-devtools-test-generator/package.json b/packages/redux-devtools-test-generator/package.json index 12fddd16..d87a8255 100644 --- a/packages/redux-devtools-test-generator/package.json +++ b/packages/redux-devtools-test-generator/package.json @@ -84,6 +84,7 @@ "peerDependencies": { "@types/react": "^16.3.18", "react": "^16.3.0", + "redux": "^3.4.0 || ^4.0.0", "redux-devtools-inspector-monitor": "^0.14.0" } } diff --git a/packages/redux-devtools-trace-monitor/.babelrc b/packages/redux-devtools-trace-monitor/.babelrc index 2a38a7b6..8cc520a8 100644 --- a/packages/redux-devtools-trace-monitor/.babelrc +++ b/packages/redux-devtools-trace-monitor/.babelrc @@ -1,13 +1,10 @@ { - "presets": ["@babel/preset-env", "@babel/preset-react", "@babel/preset-flow"], + "presets": [ + "@babel/preset-env", + "@babel/preset-react", + "@babel/preset-typescript" + ], "plugins": [ - [ - "@babel/plugin-transform-runtime", - { - "regenerator": true - } - ], - ["@babel/plugin-proposal-decorators", { "legacy": true }], "@babel/plugin-proposal-class-properties" ] } diff --git a/packages/redux-devtools-trace-monitor/package.json b/packages/redux-devtools-trace-monitor/package.json index 150d3cb8..591b66a4 100644 --- a/packages/redux-devtools-trace-monitor/package.json +++ b/packages/redux-devtools-trace-monitor/package.json @@ -29,6 +29,8 @@ }, "dependencies": { "@babel/code-frame": "^7.10.4", + "@types/babel__code-frame": "^7.0.2", + "@types/chrome": "^0.0.124", "@types/html-entities": "^1.2.16", "@types/redux-devtools-themes": "^1.0.0", "anser": "^1.4.9", @@ -45,12 +47,14 @@ "react-dom": "^16.13.1", "react-test-renderer": "^16.13.1", "redux": "^4.0.5", - "redux-devtools": "^3.7.0" + "redux-devtools": "^3.7.0", + "redux-devtools-inspector-monitor": "^0.14.0" }, "peerDependencies": { "@types/react": "^16.3.18", "react": "^16.3.0", "redux": "^3.4.0 || ^4.0.0", - "redux-devtools": "^3.0.0" + "redux-devtools": "^3.0.0", + "redux-devtools-inspector-monitor": "^0.14.0" } } diff --git a/packages/redux-devtools-trace-monitor/src/StackTraceTab.tsx b/packages/redux-devtools-trace-monitor/src/StackTraceTab.tsx index 17414b63..9d39ac14 100644 --- a/packages/redux-devtools-trace-monitor/src/StackTraceTab.tsx +++ b/packages/redux-devtools-trace-monitor/src/StackTraceTab.tsx @@ -3,26 +3,45 @@ import React, { Component } from 'react'; import { getStackFrames } from './react-error-overlay/utils/getStackFrames'; import StackTrace from './react-error-overlay/containers/StackTrace'; import openFile from './openFile'; +import { Action } from 'redux'; +import { TabComponentProps } from 'redux-devtools-inspector-monitor'; +import StackFrame from './react-error-overlay/utils/stack-frame'; +import { ErrorLocation } from './react-error-overlay/utils/parseCompileError'; const rootStyle = { padding: '5px 10px' }; -export default class StackTraceTab extends Component { +interface Props> extends TabComponentProps { + openFile: ( + fileName: string, + lineNumber: number, + stackFrame: StackFrame + ) => void; +} + +interface State { + stackFrames: StackFrame[]; + currentError?: Error; + showDocsLink?: boolean; +} + +export default class StackTraceTab< + S, + A extends Action +> extends Component, State> { static defaultProps = { openFile, }; - constructor(props) { - super(props); - this.state = { - stackFrames: [], - }; - } + state: State = { + stackFrames: [], + }; + componentDidMount() { // console.log("StackTraceTab mounted"); this.checkForStackTrace(); } - componentDidUpdate(prevProps) { + componentDidUpdate(prevProps: Props) { const { action, actions } = prevProps; if (action !== this.props.action || actions !== this.props.actions) { @@ -47,25 +66,32 @@ export default class StackTraceTab extends Component { stack: liftedAction.stack, }); - getStackFrames(deserializedError).then((stackFrames) => { - /* eslint-disable no-console */ - if (process.env.NODE_ENV === 'development') - console.log('Stack frames: ', stackFrames); - /* eslint-enable no-console */ - this.setState({ stackFrames, currentError: deserializedError }); - }); + getStackFrames(deserializedError) + .then((stackFrames) => { + /* eslint-disable no-console */ + if (process.env.NODE_ENV === 'development') + console.log('Stack frames: ', stackFrames); + /* eslint-enable no-console */ + this.setState({ + stackFrames: stackFrames!, + currentError: deserializedError, + }); + }) + .catch(() => { + // noop + }); } else { this.setState({ stackFrames: [], showDocsLink: - liftedAction.action && - liftedAction.action.type && - liftedAction.action.type !== '@@INIT', + liftedAction!.action && + liftedAction!.action.type && + liftedAction!.action.type !== '@@INIT', }); } } - onStackLocationClicked = (fileLocation = {}) => { + onStackLocationClicked = (fileLocation: Partial = {}) => { // console.log("Stack location args: ", ...args); const { fileName, lineNumber } = fileLocation; @@ -93,7 +119,7 @@ export default class StackTraceTab extends Component { } }; - openDocs = (e) => { + openDocs: React.MouseEventHandler = (e) => { e.stopPropagation(); window.open( 'https://github.com/zalmoxisus/redux-devtools-extension/blob/master/docs/Features/Trace.md' diff --git a/packages/redux-devtools-trace-monitor/src/openFile.ts b/packages/redux-devtools-trace-monitor/src/openFile.ts index 2e257edb..bbf11a91 100644 --- a/packages/redux-devtools-trace-monitor/src/openFile.ts +++ b/packages/redux-devtools-trace-monitor/src/openFile.ts @@ -1,31 +1,35 @@ +import StackFrame from './react-error-overlay/utils/stack-frame'; + const isFF = navigator.userAgent.indexOf('Firefox') !== -1; -function openResource(fileName, lineNumber, stackFrame) { +function openResource( + fileName: string, + lineNumber: number, + stackFrame: StackFrame +) { const adjustedLineNumber = Math.max(lineNumber - 1, 0); - chrome.devtools.panels.openResource( - fileName, - adjustedLineNumber, - (result) => { - //console.log("openResource callback args: ", callbackArgs); - if (result.isError) { - const { - fileName: finalFileName, - lineNumber: finalLineNumber, - } = stackFrame; - const adjustedLineNumber = Math.max(finalLineNumber - 1, 0); - chrome.devtools.panels.openResource( - finalFileName, - adjustedLineNumber, - (/* result */) => { - // console.log("openResource result: ", result); - } - ); - } + chrome.devtools.panels.openResource(fileName, adjustedLineNumber, ((result: { + isError?: boolean; + }) => { + //console.log("openResource callback args: ", callbackArgs); + if (result.isError) { + const { + fileName: finalFileName, + lineNumber: finalLineNumber, + } = stackFrame; + const adjustedLineNumber = Math.max(finalLineNumber! - 1, 0); + chrome.devtools.panels.openResource( + finalFileName!, + adjustedLineNumber, + (/* result */) => { + // console.log("openResource result: ", result); + } + ); } - ); + }) as () => void); } -function openAndCloseTab(url) { +function openAndCloseTab(url: string) { chrome.tabs.create({ url }, (tab) => { const removeTab = () => { chrome.windows.onFocusChanged.removeListener(removeTab); @@ -45,19 +49,19 @@ function openAndCloseTab(url) { }); } -function openInIframe(url) { +function openInIframe(url: string) { const iframe = document.createElement('iframe'); iframe.src = url; - iframe.style = 'display:none'; + iframe.style.display = 'none'; document.body.appendChild(iframe); - setTimeout(() => iframe.parentNode.removeChild(iframe), 3000); + setTimeout(() => iframe.parentNode!.removeChild(iframe), 3000); } -function openInEditor(editor, path, stackFrame) { +function openInEditor(editor: string, path: string, stackFrame: StackFrame) { const projectPath = path.replace(/\/$/, ''); const file = stackFrame._originalFileName || - stackFrame.finalFileName || + ((stackFrame as unknown) as { finalFileName: string }).finalFileName || stackFrame.fileName || ''; let filePath = /^https?:\/\//.test(file) @@ -95,7 +99,11 @@ function openInEditor(editor, path, stackFrame) { } } -export default function openFile(fileName, lineNumber, stackFrame) { +export default function openFile( + fileName: string, + lineNumber: number, + stackFrame: StackFrame +) { if (process.env.NODE_ENV === 'development') // eslint-disable-next-line no-console console.log(fileName, lineNumber, stackFrame); diff --git a/packages/redux-devtools-trace-monitor/src/react-error-overlay/components/CodeBlock.tsx b/packages/redux-devtools-trace-monitor/src/react-error-overlay/components/CodeBlock.tsx index f9058424..2c3a1b2c 100644 --- a/packages/redux-devtools-trace-monitor/src/react-error-overlay/components/CodeBlock.tsx +++ b/packages/redux-devtools-trace-monitor/src/react-error-overlay/components/CodeBlock.tsx @@ -5,10 +5,9 @@ * LICENSE file in the root directory of this source tree. */ -/* @flow */ -import React from 'react'; +import React, { CSSProperties } from 'react'; -const preStyle = { +const preStyle: CSSProperties = { position: 'relative', display: 'block', backgroundColor: '#000', @@ -24,10 +23,10 @@ const codeStyle = { fontFamily: 'Consolas, Menlo, monospace', }; -type CodeBlockPropsType = {| - main: boolean, - codeHTML: string, -|}; +interface CodeBlockPropsType { + main: boolean; + codeHTML: string; +} function CodeBlock(props: CodeBlockPropsType) { const codeBlock = { __html: props.codeHTML }; diff --git a/packages/redux-devtools-trace-monitor/src/react-error-overlay/components/Collapsible.tsx b/packages/redux-devtools-trace-monitor/src/react-error-overlay/components/Collapsible.tsx index 6f6f565c..07e81b64 100644 --- a/packages/redux-devtools-trace-monitor/src/react-error-overlay/components/Collapsible.tsx +++ b/packages/redux-devtools-trace-monitor/src/react-error-overlay/components/Collapsible.tsx @@ -5,13 +5,10 @@ * LICENSE file in the root directory of this source tree. */ -/* @flow */ -import React, { Component } from 'react'; +import React, { Component, CSSProperties, ReactNode } from 'react'; import { nicinabox as theme } from 'redux-devtools-themes'; -import type { Element as ReactElement } from 'react'; - -const _collapsibleStyle = { +const _collapsibleStyle: CSSProperties = { color: theme.base06, backgroundColor: theme.base01, cursor: 'pointer', @@ -24,26 +21,27 @@ const _collapsibleStyle = { lineHeight: '1.5', }; -const collapsibleCollapsedStyle = { +const collapsibleCollapsedStyle: CSSProperties = { ..._collapsibleStyle, marginBottom: '1.5em', }; -const collapsibleExpandedStyle = { +const collapsibleExpandedStyle: CSSProperties = { ..._collapsibleStyle, marginBottom: '0.6em', }; -type Props = {| - children: ReactElement[], -|}; +interface Props { + collapsedByDefault?: boolean; + children: ReactNode[]; +} -type State = {| - collapsed: boolean, -|}; +interface State { + collapsed: boolean | undefined; +} class Collapsible extends Component { - state = { + state: State = { collapsed: undefined, }; @@ -53,7 +51,7 @@ class Collapsible extends Component { })); }; - isCollapsed = (state) => + isCollapsed = (state: State) => state.collapsed === undefined ? this.props.collapsedByDefault : state.collapsed; diff --git a/packages/redux-devtools-trace-monitor/src/react-error-overlay/containers/StackFrame.tsx b/packages/redux-devtools-trace-monitor/src/react-error-overlay/containers/StackFrame.tsx index ba3cbf4b..9ef06708 100644 --- a/packages/redux-devtools-trace-monitor/src/react-error-overlay/containers/StackFrame.tsx +++ b/packages/redux-devtools-trace-monitor/src/react-error-overlay/containers/StackFrame.tsx @@ -5,8 +5,7 @@ * LICENSE file in the root directory of this source tree. */ -/* @flow */ -import React, { Component } from 'react'; +import React, { Component, CSSProperties } from 'react'; import CodeBlock from './StackFrameCodeBlock'; import { getPrettyURL } from '../utils/getPrettyURL'; import { nicinabox as theme } from 'redux-devtools-themes'; @@ -14,22 +13,22 @@ import { nicinabox as theme } from 'redux-devtools-themes'; import type { StackFrame as StackFrameType } from '../utils/stack-frame'; import type { ErrorLocation } from '../utils/parseCompileError'; -const linkStyle = { +const linkStyle: CSSProperties = { fontSize: '0.9em', marginBottom: '0.9em', }; -const anchorStyle = { +const anchorStyle: CSSProperties = { textDecoration: 'none', color: theme.base05, cursor: 'pointer', }; -const codeAnchorStyle = { +const codeAnchorStyle: CSSProperties = { cursor: 'pointer', }; -const toggleStyle = { +const toggleStyle: CSSProperties = { marginBottom: '1.5em', color: theme.base05, cursor: 'pointer', @@ -44,20 +43,20 @@ const toggleStyle = { lineHeight: '1.5', }; -type Props = {| - frame: StackFrameType, - contextSize: number, - critical: boolean, - showCode: boolean, - editorHandler: (errorLoc: ErrorLocation) => void, -|}; +interface Props { + frame: StackFrameType; + contextSize: number; + critical: boolean; + showCode: boolean; + editorHandler: (errorLoc: ErrorLocation) => void; +} -type State = {| - compiled: boolean, -|}; +interface State { + compiled: boolean; +} class StackFrame extends Component { - state = { + state: State = { compiled: false, }; @@ -93,7 +92,9 @@ class StackFrame extends Component { this.props.editorHandler(errorLoc); }; - onKeyDown = (e /* : SyntheticKeyboardEvent<> */) => { + onKeyDown: React.KeyboardEventHandler = ( + e /* : SyntheticKeyboardEvent<> */ + ) => { if (e.key === 'Enter') { this.editorHandler(); } @@ -162,10 +163,10 @@ class StackFrame extends Component {
{functionName}
{url} @@ -173,8 +174,8 @@ class StackFrame extends Component { {codeBlockProps && ( diff --git a/packages/redux-devtools-trace-monitor/src/react-error-overlay/containers/StackFrameCodeBlock.tsx b/packages/redux-devtools-trace-monitor/src/react-error-overlay/containers/StackFrameCodeBlock.tsx index 4045ab5e..753c2e06 100644 --- a/packages/redux-devtools-trace-monitor/src/react-error-overlay/containers/StackFrameCodeBlock.tsx +++ b/packages/redux-devtools-trace-monitor/src/react-error-overlay/containers/StackFrameCodeBlock.tsx @@ -5,40 +5,31 @@ * LICENSE file in the root directory of this source tree. */ -/* @flow */ import React from 'react'; import CodeBlock from '../components/CodeBlock'; import { applyStyles } from '../utils/dom/css'; import { absolutifyCaret } from '../utils/dom/absolutifyCaret'; -// import type { ScriptLine } from '../utils/stack-frame'; +import { ScriptLine } from '../utils/stack-frame'; import generateAnsiHTML from '../utils/generateAnsiHTML'; import { codeFrameColumns } from '@babel/code-frame'; import { nicinabox as theme } from 'redux-devtools-themes'; -/* -type StackFrameCodeBlockPropsType = {| - lines: ScriptLine[], - lineNum: number, - columnNum: ?number, - contextSize: number, - main: boolean, -|}; +interface StackFrameCodeBlockPropsType { + lines: ScriptLine[]; + lineNum: number; + columnNum: number | null | undefined; + contextSize: number; + main: boolean; +} -// Exact type workaround for spread operator. -// See: https://github.com/facebook/flow/issues/2405 -type Exact = $Shape; -*/ - -function StackFrameCodeBlock( - props /* : Exact */ -) { +function StackFrameCodeBlock(props: StackFrameCodeBlockPropsType) { const { lines, lineNum, columnNum, contextSize, main } = props; - const sourceCode = []; + const sourceCode: string[] = []; let whiteSpace = Infinity; lines.forEach(function (e) { const { content: text } = e; - const m = text.match(/^\s*/); + const m = /^\s*/.exec(text); if (text === '') { return; } @@ -86,16 +77,16 @@ function StackFrameCodeBlock( const ccn2 = node.childNodes; for (let index2 = 0; index2 < ccn2.length; ++index2) { const lineNode = ccn2[index2]; - const text = lineNode.innerText; + const text = (lineNode as HTMLElement).innerText; if (text == null) { continue; } - if (text.indexOf(' ' + lineNum + ' |') === -1) { + if (text.indexOf(` ${lineNum} |`) === -1) { continue; } // $FlowFixMe - applyStyles(node, { - 'background-color': main ? theme.base02 : theme.base01, + applyStyles(node as HTMLElement, { + backgroundColor: main ? theme.base02 : theme.base01, }); // eslint-disable-next-line break oLoop; diff --git a/packages/redux-devtools-trace-monitor/src/react-error-overlay/containers/StackTrace.tsx b/packages/redux-devtools-trace-monitor/src/react-error-overlay/containers/StackTrace.tsx index 35963caf..6369fe96 100644 --- a/packages/redux-devtools-trace-monitor/src/react-error-overlay/containers/StackTrace.tsx +++ b/packages/redux-devtools-trace-monitor/src/react-error-overlay/containers/StackTrace.tsx @@ -5,8 +5,7 @@ * LICENSE file in the root directory of this source tree. */ -/* @flow */ -import React, { Component } from 'react'; +import React, { Component, ReactElement } from 'react'; import StackFrame from './StackFrame'; import Collapsible from '../components/Collapsible'; import { isInternalFile } from '../utils/isInternalFile'; @@ -22,19 +21,19 @@ const traceStyle = { overflow: 'auto', }; -type Props = {| - stackFrames: StackFrameType[], - errorName: string, - contextSize: number, - editorHandler: (errorLoc: ErrorLocation) => void, -|}; +interface Props { + stackFrames: StackFrameType[]; + errorName: string; + contextSize: number; + editorHandler: (errorLoc: ErrorLocation) => void; +} class StackTrace extends Component { renderFrames() { const { stackFrames, errorName, contextSize, editorHandler } = this.props; - const renderedFrames = []; + const renderedFrames: ReactElement[] = []; let hasReachedAppCode = false, - currentBundle = [], + currentBundle: ReactElement[] = [], bundleCount = 0, anyNodeExpanded = false; @@ -55,7 +54,7 @@ class StackTrace extends Component { const frameEle = ( { renderedFrames.push( {currentBundle} diff --git a/packages/redux-devtools-trace-monitor/src/react-error-overlay/utils/dom/absolutifyCaret.ts b/packages/redux-devtools-trace-monitor/src/react-error-overlay/utils/dom/absolutifyCaret.ts index 9049069c..7bebf317 100644 --- a/packages/redux-devtools-trace-monitor/src/react-error-overlay/utils/dom/absolutifyCaret.ts +++ b/packages/redux-devtools-trace-monitor/src/react-error-overlay/utils/dom/absolutifyCaret.ts @@ -5,8 +5,7 @@ * LICENSE file in the root directory of this source tree. */ -/* @flow */ -function removeNextBr(parent, component: ?Element) { +function removeNextBr(parent: Node, component: Element | null | undefined) { while (component != null && component.tagName.toLowerCase() !== 'br') { component = component.nextElementSibling; } @@ -18,7 +17,7 @@ function removeNextBr(parent, component: ?Element) { function absolutifyCaret(component: Node) { const ccn = component.childNodes; for (let index = 0; index < ccn.length; ++index) { - const c = ccn[index]; + const c = ccn[index] as HTMLElement; // $FlowFixMe if (c.tagName.toLowerCase() !== 'span') { continue; diff --git a/packages/redux-devtools-trace-monitor/src/react-error-overlay/utils/dom/css.ts b/packages/redux-devtools-trace-monitor/src/react-error-overlay/utils/dom/css.ts index 3c71ba69..8791ecb2 100644 --- a/packages/redux-devtools-trace-monitor/src/react-error-overlay/utils/dom/css.ts +++ b/packages/redux-devtools-trace-monitor/src/react-error-overlay/utils/dom/css.ts @@ -5,9 +5,8 @@ * LICENSE file in the root directory of this source tree. */ -/* @flow */ let injectedCount = 0; -const injectedCache = {}; +const injectedCache: { [key: number]: HTMLStyleElement } = {}; function getHead(document: Document) { return document.head || document.getElementsByTagName('head')[0]; @@ -33,14 +32,17 @@ function removeCss(document: Document, ref: number) { delete injectedCache[ref]; } -function applyStyles(element: HTMLElement, styles: Object) { +function applyStyles( + element: HTMLElement, + styles: Partial +) { element.setAttribute('style', ''); for (const key in styles) { if (!Object.prototype.hasOwnProperty.call(styles, key)) { continue; } // $FlowFixMe - element.style[key] = styles[key]; + element.style[key] = styles[key]!; } } diff --git a/packages/redux-devtools-trace-monitor/src/react-error-overlay/utils/generateAnsiHTML.ts b/packages/redux-devtools-trace-monitor/src/react-error-overlay/utils/generateAnsiHTML.ts index 747845a4..e35d7a29 100644 --- a/packages/redux-devtools-trace-monitor/src/react-error-overlay/utils/generateAnsiHTML.ts +++ b/packages/redux-devtools-trace-monitor/src/react-error-overlay/utils/generateAnsiHTML.ts @@ -5,15 +5,13 @@ * LICENSE file in the root directory of this source tree. */ -/* @flow */ - import Anser from 'anser'; import { nicinabox as theme } from 'redux-devtools-themes'; import { AllHtmlEntities as Entities } from 'html-entities'; -var entities = new Entities(); +const entities = new Entities(); -var anserMap = { +const anserMap = { 'ansi-bright-black': theme.base03, 'ansi-bright-yellow': theme.base0A, 'ansi-yellow': theme.base0B, @@ -29,25 +27,25 @@ var anserMap = { }; function generateAnsiHTML(txt: string): string { - var arr = new Anser().ansiToJson(entities.encode(txt), { + const arr = new Anser().ansiToJson(entities.encode(txt), { use_classes: true, }); - var result = ''; - var open = false; - for (var index = 0; index < arr.length; ++index) { - var c = arr[index]; - var content = c.content, + let result = ''; + let open = false; + for (let index = 0; index < arr.length; ++index) { + const c = arr[index]; + const content = c.content, fg = c.fg; - var contentParts = content.split('\n'); - for (var _index = 0; _index < contentParts.length; ++_index) { + const contentParts = content.split('\n'); + for (let _index = 0; _index < contentParts.length; ++_index) { if (!open) { result += ''; open = true; } - var part = contentParts[_index].replace('\r', ''); - var color = anserMap[fg]; + const part = contentParts[_index].replace('\r', ''); + const color = anserMap[fg as keyof typeof anserMap]; if (color != null) { result += '' + part + ''; } else { diff --git a/packages/redux-devtools-trace-monitor/src/react-error-overlay/utils/getLinesAround.ts b/packages/redux-devtools-trace-monitor/src/react-error-overlay/utils/getLinesAround.ts index 4a7ffc34..dcaba0ce 100644 --- a/packages/redux-devtools-trace-monitor/src/react-error-overlay/utils/getLinesAround.ts +++ b/packages/redux-devtools-trace-monitor/src/react-error-overlay/utils/getLinesAround.ts @@ -5,7 +5,6 @@ * LICENSE file in the root directory of this source tree. */ -/* @flow */ import { ScriptLine } from './stack-frame'; /** diff --git a/packages/redux-devtools-trace-monitor/src/react-error-overlay/utils/getPrettyURL.ts b/packages/redux-devtools-trace-monitor/src/react-error-overlay/utils/getPrettyURL.ts index 1aa5dc77..894da6f3 100644 --- a/packages/redux-devtools-trace-monitor/src/react-error-overlay/utils/getPrettyURL.ts +++ b/packages/redux-devtools-trace-monitor/src/react-error-overlay/utils/getPrettyURL.ts @@ -5,14 +5,13 @@ * LICENSE file in the root directory of this source tree. */ -/* @flow */ function getPrettyURL( - sourceFileName: ?string, - sourceLineNumber: ?number, - sourceColumnNumber: ?number, - fileName: ?string, - lineNumber: ?number, - columnNumber: ?number, + sourceFileName: string | null | undefined, + sourceLineNumber: number | null | undefined, + sourceColumnNumber: number | null | undefined, + fileName: string | null | undefined, + lineNumber: number | null | undefined, + columnNumber: number | null | undefined, compiled: boolean ): string { let prettyURL; @@ -26,16 +25,16 @@ function getPrettyURL( } else { prettyURL = sourceFileName; } - prettyURL += ':' + sourceLineNumber; + prettyURL += `:${sourceLineNumber}`; // Note: we intentionally skip 0's because they're produced by cheap Webpack maps if (sourceColumnNumber) { - prettyURL += ':' + sourceColumnNumber; + prettyURL += `:${sourceColumnNumber}`; } } else if (fileName && typeof lineNumber === 'number') { - prettyURL = fileName + ':' + lineNumber; + prettyURL = `${fileName}:${lineNumber}`; // Note: we intentionally skip 0's because they're produced by cheap Webpack maps if (columnNumber) { - prettyURL += ':' + columnNumber; + prettyURL += `:${columnNumber}`; } } else { prettyURL = 'unknown'; diff --git a/packages/redux-devtools-trace-monitor/src/react-error-overlay/utils/getSourceMap.ts b/packages/redux-devtools-trace-monitor/src/react-error-overlay/utils/getSourceMap.ts index 644847bb..0157204a 100644 --- a/packages/redux-devtools-trace-monitor/src/react-error-overlay/utils/getSourceMap.ts +++ b/packages/redux-devtools-trace-monitor/src/react-error-overlay/utils/getSourceMap.ts @@ -5,8 +5,7 @@ * LICENSE file in the root directory of this source tree. */ -/* @flow */ -import { SourceMapConsumer } from 'source-map'; +import { RawSourceMap, SourceMapConsumer } from 'source-map'; /** * A wrapped instance of a {@link https://github.com/mozilla/source-map SourceMapConsumer}. @@ -16,7 +15,7 @@ import { SourceMapConsumer } from 'source-map'; class SourceMap { __source_map: SourceMapConsumer; - constructor(sourceMap) { + constructor(sourceMap: SourceMapConsumer) { this.__source_map = sourceMap; } @@ -28,7 +27,7 @@ class SourceMap { getOriginalPosition( line: number, column: number - ): { source: string, line: number, column: number } { + ): { source: string; line: number; column: number } { const { line: l, column: c, @@ -50,7 +49,7 @@ class SourceMap { source: string, line: number, column: number - ): { line: number, column: number } { + ): { line: number; column: number } { const { line: l, column: c } = this.__source_map.generatedPositionFor({ source, line, @@ -71,7 +70,7 @@ class SourceMap { } getSources(): string[] { - return this.__source_map.sources; + return ((this.__source_map as unknown) as { sources: string[] }).sources; } } @@ -82,7 +81,7 @@ function extractSourceMapUrl( const regex = /\/\/[#@] ?sourceMappingURL=([^\s'"]+)\s*$/gm; let match = null; for (;;) { - let next = regex.exec(fileContents); + const next = regex.exec(fileContents); if (next == null) { break; } @@ -107,7 +106,7 @@ async function getSourceMap( let sm = await extractSourceMapUrl(fileUri, fileContents); if (sm.indexOf('data:') === 0) { const base64 = /^data:application\/json;([\w=:"-]+;)*base64,/; - const match2 = sm.match(base64); + const match2 = base64.exec(sm); if (!match2) { throw new Error( 'Sorry, non-base64 inline source-map encoding is not supported.' @@ -116,7 +115,9 @@ async function getSourceMap( sm = sm.substring(match2[0].length); sm = window.atob(sm); sm = JSON.parse(sm); - return new SourceMap(new SourceMapConsumer(sm)); + return new SourceMap( + new SourceMapConsumer((sm as unknown) as RawSourceMap) + ); } else { const index = fileUri.lastIndexOf('/'); const url = fileUri.substring(0, index + 1) + sm; diff --git a/packages/redux-devtools-trace-monitor/src/react-error-overlay/utils/getStackFrames.ts b/packages/redux-devtools-trace-monitor/src/react-error-overlay/utils/getStackFrames.ts index f7d3984d..9021713a 100644 --- a/packages/redux-devtools-trace-monitor/src/react-error-overlay/utils/getStackFrames.ts +++ b/packages/redux-devtools-trace-monitor/src/react-error-overlay/utils/getStackFrames.ts @@ -5,7 +5,6 @@ * LICENSE file in the root directory of this source tree. */ -/* @flow */ import type { StackFrame } from './stack-frame'; import { parse } from './parser'; import { map } from './mapper'; @@ -14,15 +13,21 @@ import { toExclude } from '../../presets'; function getStackFrames( error: Error, - unhandledRejection: boolean = false, // eslint-disable-line no-unused-vars - contextSize: number = 3 + unhandledRejection = false, // eslint-disable-line no-unused-vars + contextSize = 3 ): Promise { const parsedFrames = parse(error); let enhancedFramesPromise; - if (error.__unmap_source) { + if ( + ((error as unknown) as { + __unmap_source: string | { uri: string; contents: string }; + }).__unmap_source + ) { enhancedFramesPromise = unmap( // $FlowFixMe - error.__unmap_source, + ((error as unknown) as { + __unmap_source: string | { uri: string; contents: string }; + }).__unmap_source, parsedFrames, contextSize ); @@ -44,7 +49,7 @@ function getStackFrames( (functionName == null || functionName.indexOf('__stack_frame_overlay_proxy_console__') === -1) && - !toExclude.test(fileName) + !toExclude.test(fileName!) ); }); } diff --git a/packages/redux-devtools-trace-monitor/src/react-error-overlay/utils/isBultinErrorName.ts b/packages/redux-devtools-trace-monitor/src/react-error-overlay/utils/isBultinErrorName.ts index 570f72cf..f7a82b3a 100644 --- a/packages/redux-devtools-trace-monitor/src/react-error-overlay/utils/isBultinErrorName.ts +++ b/packages/redux-devtools-trace-monitor/src/react-error-overlay/utils/isBultinErrorName.ts @@ -5,8 +5,7 @@ * LICENSE file in the root directory of this source tree. */ -/* @flow */ -function isBultinErrorName(errorName: ?string) { +function isBultinErrorName(errorName: string | null | undefined) { switch (errorName) { case 'EvalError': case 'InternalError': diff --git a/packages/redux-devtools-trace-monitor/src/react-error-overlay/utils/isInternalFile.ts b/packages/redux-devtools-trace-monitor/src/react-error-overlay/utils/isInternalFile.ts index 97dbeaae..9c916d4b 100644 --- a/packages/redux-devtools-trace-monitor/src/react-error-overlay/utils/isInternalFile.ts +++ b/packages/redux-devtools-trace-monitor/src/react-error-overlay/utils/isInternalFile.ts @@ -5,8 +5,10 @@ * LICENSE file in the root directory of this source tree. */ -/* @flow */ -function isInternalFile(sourceFileName: ?string, fileName: ?string) { +function isInternalFile( + sourceFileName: string | null | undefined, + fileName: string | null | undefined +) { return ( sourceFileName == null || sourceFileName === '' || diff --git a/packages/redux-devtools-trace-monitor/src/react-error-overlay/utils/mapper.ts b/packages/redux-devtools-trace-monitor/src/react-error-overlay/utils/mapper.ts index 3a20f538..d172e0c1 100644 --- a/packages/redux-devtools-trace-monitor/src/react-error-overlay/utils/mapper.ts +++ b/packages/redux-devtools-trace-monitor/src/react-error-overlay/utils/mapper.ts @@ -5,7 +5,6 @@ * LICENSE file in the root directory of this source tree. */ -/* @flow */ import StackFrame from './stack-frame'; import { getSourceMap } from './getSourceMap'; import { getLinesAround } from './getLinesAround'; @@ -18,7 +17,7 @@ import { settle } from 'settle-promise'; */ async function map( frames: StackFrame[], - contextLines: number = 3 + contextLines = 3 ): Promise { const cache: any = {}; const files: string[] = []; @@ -41,7 +40,7 @@ async function map( ); return frames.map((frame) => { const { functionName, fileName, lineNumber, columnNumber } = frame; - let { map, fileSource } = cache[fileName] || {}; + const { map, fileSource } = cache[fileName!] || {}; if (map == null || lineNumber == null) { return frame; } diff --git a/packages/redux-devtools-trace-monitor/src/react-error-overlay/utils/parseCompileError.ts b/packages/redux-devtools-trace-monitor/src/react-error-overlay/utils/parseCompileError.ts index e87c4562..e0bab04d 100644 --- a/packages/redux-devtools-trace-monitor/src/react-error-overlay/utils/parseCompileError.ts +++ b/packages/redux-devtools-trace-monitor/src/react-error-overlay/utils/parseCompileError.ts @@ -1,11 +1,10 @@ -// @flow import Anser from 'anser'; -export type ErrorLocation = {| - fileName: string, - lineNumber: number, - colNumber?: number, -|}; +export interface ErrorLocation { + fileName: string; + lineNumber: number; + colNumber?: number; +} const filePathRegex = /^\.(\/[^/\n ]+)+\.[^/\n ]+$/; @@ -22,11 +21,11 @@ const lineNumberRegexes = [ // Based on error formatting of webpack // https://github.com/webpack/webpack/blob/v3.5.5/lib/Stats.js#L183-L217 -function parseCompileError(message: string): ?ErrorLocation { - const lines: Array = message.split('\n'); - let fileName: string = ''; - let lineNumber: number = 0; - let colNumber: number = 0; +function parseCompileError(message: string): ErrorLocation | null | undefined { + const lines: string[] = message.split('\n'); + let fileName = ''; + let lineNumber = 0; + let colNumber = 0; for (let i = 0; i < lines.length; i++) { const line: string = Anser.ansiToText(lines[i]).trim(); @@ -34,13 +33,15 @@ function parseCompileError(message: string): ?ErrorLocation { continue; } - if (!fileName && line.match(filePathRegex)) { + if (!fileName && filePathRegex.exec(line)) { fileName = line; } let k = 0; while (k < lineNumberRegexes.length) { - const match: ?Array = line.match(lineNumberRegexes[k]); + const match: string[] | null | undefined = lineNumberRegexes[k].exec( + line + ); if (match) { lineNumber = parseInt(match[1], 10); // colNumber starts with 0 and hence add 1 diff --git a/packages/redux-devtools-trace-monitor/src/react-error-overlay/utils/parser.ts b/packages/redux-devtools-trace-monitor/src/react-error-overlay/utils/parser.ts index 5a8efd37..786d98e0 100644 --- a/packages/redux-devtools-trace-monitor/src/react-error-overlay/utils/parser.ts +++ b/packages/redux-devtools-trace-monitor/src/react-error-overlay/utils/parser.ts @@ -5,14 +5,13 @@ * LICENSE file in the root directory of this source tree. */ -/* @flow */ import StackFrame from './stack-frame'; const regexExtractLocation = /\(?(.+?)(?::(\d+))?(?::(\d+))?\)?$/; function extractLocation(token: string): [string, number, number] { return regexExtractLocation - .exec(token) + .exec(token)! .slice(1) .map((v) => { const p = Number(v); @@ -20,7 +19,7 @@ function extractLocation(token: string): [string, number, number] { return p; } return v; - }); + }) as [string, number, number]; } const regexValidFrame_Chrome = /^\s*(at|in)\s.+(:\d+)/; @@ -46,7 +45,7 @@ function parseStack(stack: string[]): StackFrame[] { const last = data.pop(); return new StackFrame( data.join('@') || (isEval ? 'eval' : null), - ...extractLocation(last) + ...extractLocation(last!) ); } else { // Strip eval, we don't care about it @@ -58,7 +57,10 @@ function parseStack(stack: string[]): StackFrame[] { } const data = e.trim().split(/\s+/g).slice(1); const last = data.pop(); - return new StackFrame(data.join(' ') || null, ...extractLocation(last)); + return new StackFrame( + data.join(' ') || null, + ...extractLocation(last!) + ); } }); return frames; diff --git a/packages/redux-devtools-trace-monitor/src/react-error-overlay/utils/pollyfills.ts b/packages/redux-devtools-trace-monitor/src/react-error-overlay/utils/pollyfills.ts index ddd5aeb9..d740eff1 100644 --- a/packages/redux-devtools-trace-monitor/src/react-error-overlay/utils/pollyfills.ts +++ b/packages/redux-devtools-trace-monitor/src/react-error-overlay/utils/pollyfills.ts @@ -9,6 +9,7 @@ if (typeof Promise === 'undefined') { // Rejection tracking prevents a common issue where React gets into an // inconsistent state due to an error, but it gets swallowed by a Promise, // and the user has no idea what causes React's erratic future behavior. + // eslint-disable-next-line @typescript-eslint/no-var-requires require('promise/lib/rejection-tracking').enable(); window.Promise = require('promise/lib/es6-extensions.js'); } diff --git a/packages/redux-devtools-trace-monitor/src/react-error-overlay/utils/stack-frame.ts b/packages/redux-devtools-trace-monitor/src/react-error-overlay/utils/stack-frame.ts index cbbea6a0..4406aa7d 100644 --- a/packages/redux-devtools-trace-monitor/src/react-error-overlay/utils/stack-frame.ts +++ b/packages/redux-devtools-trace-monitor/src/react-error-overlay/utils/stack-frame.ts @@ -5,8 +5,6 @@ * LICENSE file in the root directory of this source tree. */ -/* @flow */ - /** A container holding a script line. */ class ScriptLine { /** The line number of this line of source. */ @@ -16,7 +14,7 @@ class ScriptLine { /** Whether or not this line should be highlighted. Particularly useful for error reporting with context. */ highlight: boolean; - constructor(lineNumber: number, content: string, highlight: boolean = false) { + constructor(lineNumber: number, content: string, highlight = false) { this.lineNumber = lineNumber; this.content = content; this.highlight = highlight; @@ -98,10 +96,10 @@ class StackFrame { str += this.fileName + ':'; } if (this.lineNumber != null) { - str += this.lineNumber + ':'; + str += `${this.lineNumber}:`; } if (this.columnNumber != null) { - str += this.columnNumber + ':'; + str += `${this.columnNumber}:`; } return str.slice(0, -1); } diff --git a/packages/redux-devtools-trace-monitor/src/react-error-overlay/utils/unmapper.ts b/packages/redux-devtools-trace-monitor/src/react-error-overlay/utils/unmapper.ts index 7b8ab87a..72c9b4b5 100644 --- a/packages/redux-devtools-trace-monitor/src/react-error-overlay/utils/unmapper.ts +++ b/packages/redux-devtools-trace-monitor/src/react-error-overlay/utils/unmapper.ts @@ -5,7 +5,6 @@ * LICENSE file in the root directory of this source tree. */ -/* @flow */ import StackFrame from './stack-frame'; import { getSourceMap } from './getSourceMap'; import { getLinesAround } from './getLinesAround'; @@ -32,16 +31,16 @@ function count(search: string, string: string): number { * @param {number} [fileContents=3] The number of lines to provide before and after the line specified in the StackFrame. */ async function unmap( - _fileUri: string | { uri: string, contents: string }, + _fileUri: string | { uri: string; contents: string }, frames: StackFrame[], - contextLines: number = 3 + contextLines = 3 ): Promise { let fileContents = typeof _fileUri === 'object' ? _fileUri.contents : null; - let fileUri = typeof _fileUri === 'object' ? _fileUri.uri : _fileUri; + const fileUri = typeof _fileUri === 'object' ? _fileUri.uri : _fileUri; if (fileContents == null) { fileContents = await fetch(fileUri).then((res) => res.text()); } - const map = await getSourceMap(fileUri, fileContents); + const map = await getSourceMap(fileUri, fileContents!); return frames.map((frame) => { const { functionName, @@ -104,7 +103,7 @@ async function unmap( sourceT, lineNumber, // $FlowFixMe - columnNumber + columnNumber! ); const originalSource = map.getSource(sourceT); return new StackFrame( diff --git a/packages/redux-devtools-trace-monitor/src/settle-promise.ts b/packages/redux-devtools-trace-monitor/src/settle-promise.ts new file mode 100644 index 00000000..4168e22b --- /dev/null +++ b/packages/redux-devtools-trace-monitor/src/settle-promise.ts @@ -0,0 +1,3 @@ +declare module 'settle-promise' { + export function settle(promises: Promise[]): Promise; +} diff --git a/packages/redux-devtools-trace-monitor/test/StackTraceTab.spec.js b/packages/redux-devtools-trace-monitor/test/StackTraceTab.spec.js deleted file mode 100644 index d8f21163..00000000 --- a/packages/redux-devtools-trace-monitor/test/StackTraceTab.spec.js +++ /dev/null @@ -1,55 +0,0 @@ -import React from 'react'; -import { configure, mount } from 'enzyme'; -import toJson from 'enzyme-to-json'; -import StackTraceTab from '../src/StackTraceTab'; - -import Adapter from 'enzyme-adapter-react-16'; -configure({ adapter: new Adapter() }); - -function genAsyncSnapshot(component, done) { - setTimeout(() => { - component.update(); - expect(toJson(component)).toMatchSnapshot(); - done(); - }); -} - -const actions = { - 0: { type: 'PERFORM_ACTION', action: { type: '@@INIT' } }, - 1: { type: 'PERFORM_ACTION', action: { type: 'INCREMENT_COUNTER' } }, - 2: { - type: 'PERFORM_ACTION', - action: { type: 'INCREMENT_COUNTER' }, - stack: - 'Error\n at fn1 (app.js:72:24)\n at fn2 (app.js:84:31)\n ' + - 'at fn3 (chrome-extension://lmhkpmbekcpmknklioeibfkpmmfibljd/js/page.bundle.js:1269:80)', - }, -}; - -describe('StackTraceTab component', () => { - it('should render with no props', (done) => { - const component = mount(); - genAsyncSnapshot(component, done); - }); - - it('should render with props, but without stack', (done) => { - const component = mount( - - ); - genAsyncSnapshot(component, done); - }); - - it('should render the link to docs', (done) => { - const component = mount( - - ); - genAsyncSnapshot(component, done); - }); - - it('should render with trace stack', (done) => { - const component = mount( - - ); - genAsyncSnapshot(component, done); - }); -}); diff --git a/packages/redux-devtools-trace-monitor/test/StackTraceTab.spec.tsx b/packages/redux-devtools-trace-monitor/test/StackTraceTab.spec.tsx new file mode 100644 index 00000000..ba5cdc4a --- /dev/null +++ b/packages/redux-devtools-trace-monitor/test/StackTraceTab.spec.tsx @@ -0,0 +1,68 @@ +import React, { ReactComponentElement } from 'react'; +import { configure, mount } from 'enzyme'; +import toJson from 'enzyme-to-json'; +import StackTraceTab from '../src/StackTraceTab'; + +import Adapter from 'enzyme-adapter-react-16'; +configure({ adapter: new Adapter() }); + +function genAsyncSnapshot( + component: ReactComponentElement, + done: boolean +) { + setTimeout(() => { + component.update(); + expect(toJson(component)).toMatchSnapshot(); + done(); + }); +} + +const actions = { + 0: { type: 'PERFORM_ACTION', action: { type: '@@INIT' } }, + 1: { type: 'PERFORM_ACTION', action: { type: 'INCREMENT_COUNTER' } }, + 2: { + type: 'PERFORM_ACTION', + action: { type: 'INCREMENT_COUNTER' }, + stack: + 'Error\n at fn1 (app.js:72:24)\n at fn2 (app.js:84:31)\n ' + + 'at fn3 (chrome-extension://lmhkpmbekcpmknklioeibfkpmmfibljd/js/page.bundle.js:1269:80)', + }, +}; + +const StackTraceTabAsAny = StackTraceTab as any; + +describe('StackTraceTab component', () => { + it('should render with no props', () => { + return new Promise((done) => { + const component = mount(); + genAsyncSnapshot(component, done); + }); + }); + + it('should render with props, but without stack', () => { + return new Promise((done) => { + const component = mount( + + ); + genAsyncSnapshot(component, done); + }); + }); + + it('should render the link to docs', () => { + return new Promise((done) => { + const component = mount( + + ); + genAsyncSnapshot(component, done); + }); + }); + + it('should render with trace stack', () => { + return new Promise((done) => { + const component = mount( + + ); + genAsyncSnapshot(component, done); + }); + }); +}); diff --git a/tsconfig.base.json b/tsconfig.base.json index 2a17a794..55204414 100644 --- a/tsconfig.base.json +++ b/tsconfig.base.json @@ -8,6 +8,6 @@ "esModuleInterop": true, "forceConsistentCasingInFileNames": true, // See https://github.com/DefinitelyTyped/DefinitelyTyped/issues/33311 - "types": ["node", "jest", "webpack-env"] + "types": ["node", "jest", "webpack-env", "chrome"] } } diff --git a/yarn.lock b/yarn.lock index 22eab218..05fb37d5 100644 --- a/yarn.lock +++ b/yarn.lock @@ -3251,6 +3251,11 @@ resolved "https://registry.yarnpkg.com/@types/anymatch/-/anymatch-1.3.1.tgz#336badc1beecb9dacc38bea2cf32adf627a8421a" integrity sha512-/+CRPXpBDpo2RK9C68N3b2cOvO0Cf5B9aPijHsoDQTHivnGSObdOF2BRQOYjojWTDy6nQvMjmqRXIxH55VjxxA== +"@types/babel__code-frame@^7.0.2": + version "7.0.2" + resolved "https://registry.yarnpkg.com/@types/babel__code-frame/-/babel__code-frame-7.0.2.tgz#e0c0f1648cbc09a9d4e5b4ed2ae9a6f7c8f5aeb0" + integrity sha512-imO+jT/yjOKOAS5GQZ8SDtwiIloAGGr6OaZDKB0V5JVaSfGZLat5K5/ZRtyKW6R60XHV3RHYPTFfhYb+wDKyKg== + "@types/babel__core@^7.0.0", "@types/babel__core@^7.1.7": version "7.1.9" resolved "https://registry.yarnpkg.com/@types/babel__core/-/babel__core-7.1.9.tgz#77e59d438522a6fb898fa43dc3455c6e72f3963d" @@ -3309,6 +3314,14 @@ dependencies: "@types/node" "*" +"@types/chrome@^0.0.124": + version "0.0.124" + resolved "https://registry.yarnpkg.com/@types/chrome/-/chrome-0.0.124.tgz#1cdb8e1c1ddb04b15844f5a71b9907f73bbb84a2" + integrity sha512-0UmDQ6A9gaahvztKryIonSTyUMEhuhKNyyJAnBB7ZJN/YXP7YRkL4onPFSTxnIbXcMnYsQFo8TxsGP8jY2mdEw== + dependencies: + "@types/filesystem" "*" + "@types/har-format" "*" + "@types/classnames@^2.2.10": version "2.2.10" resolved "https://registry.yarnpkg.com/@types/classnames/-/classnames-2.2.10.tgz#cc658ca319b6355399efc1f5b9e818f1a24bf999" @@ -3419,6 +3432,18 @@ "@types/qs" "*" "@types/serve-static" "*" +"@types/filesystem@*": + version "0.0.29" + resolved "https://registry.yarnpkg.com/@types/filesystem/-/filesystem-0.0.29.tgz#ee3748eb5be140dcf980c3bd35f11aec5f7a3748" + integrity sha512-85/1KfRedmfPGsbK8YzeaQUyV1FQAvMPMTuWFQ5EkLd2w7szhNO96bk3Rh/SKmOfd9co2rCLf0Voy4o7ECBOvw== + dependencies: + "@types/filewriter" "*" + +"@types/filewriter@*": + version "0.0.28" + resolved "https://registry.yarnpkg.com/@types/filewriter/-/filewriter-0.0.28.tgz#c054e8af4d9dd75db4e63abc76f885168714d4b3" + integrity sha1-wFTor02d11205jq8dviFFocU1LM= + "@types/glob-base@^0.3.0": version "0.3.0" resolved "https://registry.yarnpkg.com/@types/glob-base/-/glob-base-0.3.0.tgz#a581d688347e10e50dd7c17d6f2880a10354319d" @@ -3439,6 +3464,11 @@ dependencies: "@types/node" "*" +"@types/har-format@*": + version "1.2.4" + resolved "https://registry.yarnpkg.com/@types/har-format/-/har-format-1.2.4.tgz#3275842095abb60d14b47fa798cc9ff708dab6d4" + integrity sha512-iUxzm1meBm3stxUMzRqgOVHjj4Kgpgu5w9fm4X7kPRfSgVRzythsucEN7/jtOo8SQzm+HfcxWWzJS0mJDH/3DQ== + "@types/hast@^2.0.0": version "2.3.1" resolved "https://registry.yarnpkg.com/@types/hast/-/hast-2.3.1.tgz#b16872f2a6144c7025f296fb9636a667ebb79cd9"