From bd459525e54567c072bc2be507b6da4670526ca8 Mon Sep 17 00:00:00 2001 From: Ezzudin Alkotob Date: Thu, 28 Oct 2021 13:24:31 -0700 Subject: [PATCH 1/7] Devtools add open in vscode for fb --- .../react-devtools-core/webpack.standalone.js | 2 ++ .../webpack.config.js | 2 ++ .../src/devtools/views/ButtonIcon.js | 8 ++++++ .../views/Components/InspectedElement.js | 26 ++++++++++++++++++- 4 files changed, 37 insertions(+), 1 deletion(-) diff --git a/packages/react-devtools-core/webpack.standalone.js b/packages/react-devtools-core/webpack.standalone.js index 9d7c1fc34a685..f5866300b62df 100644 --- a/packages/react-devtools-core/webpack.standalone.js +++ b/packages/react-devtools-core/webpack.standalone.js @@ -30,6 +30,7 @@ const __DEV__ = NODE_ENV === 'development'; const DEVTOOLS_VERSION = getVersionString(); +const EDITOR_URL = process.env.EDITOR_URL || null; const LOGGING_URL = process.env.LOGGING_URL || null; const featureFlagTarget = @@ -83,6 +84,7 @@ module.exports = { __TEST__: NODE_ENV === 'test', 'process.env.DEVTOOLS_PACKAGE': `"react-devtools-core"`, 'process.env.DEVTOOLS_VERSION': `"${DEVTOOLS_VERSION}"`, + 'process.env.EDITOR_URL': `"${EDITOR_URL}"`, 'process.env.GITHUB_URL': `"${GITHUB_URL}"`, 'process.env.LOGGING_URL': `"${LOGGING_URL}"`, 'process.env.NODE_ENV': `"${NODE_ENV}"`, diff --git a/packages/react-devtools-extensions/webpack.config.js b/packages/react-devtools-extensions/webpack.config.js index 99b1d18d3a999..67bb309a0b5d2 100644 --- a/packages/react-devtools-extensions/webpack.config.js +++ b/packages/react-devtools-extensions/webpack.config.js @@ -32,6 +32,7 @@ const __DEV__ = NODE_ENV === 'development'; const DEVTOOLS_VERSION = getVersionString(process.env.DEVTOOLS_VERSION); +const EDITOR_URL = process.env.EDITOR_URL || null; const LOGGING_URL = process.env.LOGGING_URL || null; const featureFlagTarget = process.env.FEATURE_FLAG_TARGET || 'extension-oss'; @@ -92,6 +93,7 @@ module.exports = { __TEST__: NODE_ENV === 'test', 'process.env.DEVTOOLS_PACKAGE': `"react-devtools-extensions"`, 'process.env.DEVTOOLS_VERSION': `"${DEVTOOLS_VERSION}"`, + 'process.env.EDITOR_URL': `"${EDITOR_URL}"`, 'process.env.GITHUB_URL': `"${GITHUB_URL}"`, 'process.env.LOGGING_URL': `"${LOGGING_URL}"`, 'process.env.NODE_ENV': `"${NODE_ENV}"`, diff --git a/packages/react-devtools-shared/src/devtools/views/ButtonIcon.js b/packages/react-devtools-shared/src/devtools/views/ButtonIcon.js index 8239a765f90b6..2f4bc437848f6 100644 --- a/packages/react-devtools-shared/src/devtools/views/ButtonIcon.js +++ b/packages/react-devtools-shared/src/devtools/views/ButtonIcon.js @@ -19,6 +19,7 @@ export type IconType = | 'copy' | 'delete' | 'down' + | 'editor' | 'expanded' | 'export' | 'filter' @@ -72,6 +73,9 @@ export default function ButtonIcon({className = '', type}: Props) { case 'down': pathData = PATH_DOWN; break; + case 'editor': + pathData = PATH_VS_CODE; + break; case 'expanded': pathData = PATH_EXPANDED; break; @@ -268,3 +272,7 @@ const PATH_VIEW_DOM = ` const PATH_VIEW_SOURCE = ` M9.4 16.6L4.8 12l4.6-4.6L8 6l-6 6 6 6 1.4-1.4zm5.2 0l4.6-4.6-4.6-4.6L16 6l6 6-6 6-1.4-1.4z `; + +const PATH_VS_CODE = ` + M 17.488281 2.394531 L 9.058594 10.148438 L 4.34375 6.597656 L 2.394531 7.730469 L 7.042969 12 L 2.394531 16.269531 L 4.34375 17.40625 L 9.058594 13.851562 L 17.488281 21.605469 L 21.605469 19.605469 L 21.605469 4.394531 Z M 17.488281 7.496094 L 17.488281 16.503906 L 11.511719 12 Z M 17.488281 7.496094 +`; diff --git a/packages/react-devtools-shared/src/devtools/views/Components/InspectedElement.js b/packages/react-devtools-shared/src/devtools/views/Components/InspectedElement.js index f63da7b54a67d..39403fb0360ba 100644 --- a/packages/react-devtools-shared/src/devtools/views/Components/InspectedElement.js +++ b/packages/react-devtools-shared/src/devtools/views/Components/InspectedElement.js @@ -20,6 +20,7 @@ import {ElementTypeSuspense} from 'react-devtools-shared/src/types'; import CannotSuspendWarningMessage from './CannotSuspendWarningMessage'; import InspectedElementView from './InspectedElementView'; import {InspectedElementContext} from './InspectedElementContext'; +import {isInternalFacebookBuild} from 'react-devtools-feature-flags'; import styles from './InspectedElement.css'; @@ -198,6 +199,22 @@ export default function InspectedElementWrapper(_: Props) { } }, [bridge, dispatch, element, isSuspended, modalDialogDispatch, store]); + const onOpenInEditor = useCallback(() => { + const source = inspectedElement?.source; + if (source == null) { + return; + } + const editorURL = process.env.EDITOR_URL; + if (typeof editorURL !== 'string') { + return; + } + const url = new URL(editorURL); + url.searchParams.set('project', 'facebook-www'); + url.searchParams.append('paths[0]', source.fileName); + url.searchParams.append('lines[0]', String(source.lineNumber)); + window.open(url); + }, [inspectedElement]); + if (element === null) { return (
@@ -223,7 +240,14 @@ export default function InspectedElementWrapper(_: Props) { {element.displayName}
- + {isInternalFacebookBuild && ( + + )} {canToggleError && ( Date: Sun, 31 Oct 2021 22:35:04 -0700 Subject: [PATCH 2/7] configurable editor --- .../react-devtools-core/webpack.standalone.js | 2 +- .../webpack.config.js | 2 +- .../react-devtools-inline/webpack.config.js | 3 ++ .../react-devtools-shared/src/constants.js | 3 ++ .../src/devtools/views/ButtonIcon.js | 6 ++-- .../views/Components/InspectedElement.js | 29 ++++++++++--------- .../views/Settings/ComponentsSettings.js | 26 ++++++++++++++++- packages/react-devtools-shared/src/utils.js | 13 +++++++++ .../react-devtools-shell/webpack.config.js | 3 ++ 9 files changed, 68 insertions(+), 19 deletions(-) diff --git a/packages/react-devtools-core/webpack.standalone.js b/packages/react-devtools-core/webpack.standalone.js index f5866300b62df..508d485c6fb21 100644 --- a/packages/react-devtools-core/webpack.standalone.js +++ b/packages/react-devtools-core/webpack.standalone.js @@ -30,7 +30,7 @@ const __DEV__ = NODE_ENV === 'development'; const DEVTOOLS_VERSION = getVersionString(); -const EDITOR_URL = process.env.EDITOR_URL || null; +const EDITOR_URL = process.env.EDITOR_URL || 'vscode://file/{path}:{line}'; const LOGGING_URL = process.env.LOGGING_URL || null; const featureFlagTarget = diff --git a/packages/react-devtools-extensions/webpack.config.js b/packages/react-devtools-extensions/webpack.config.js index 67bb309a0b5d2..4a393b248f9b6 100644 --- a/packages/react-devtools-extensions/webpack.config.js +++ b/packages/react-devtools-extensions/webpack.config.js @@ -32,7 +32,7 @@ const __DEV__ = NODE_ENV === 'development'; const DEVTOOLS_VERSION = getVersionString(process.env.DEVTOOLS_VERSION); -const EDITOR_URL = process.env.EDITOR_URL || null; +const EDITOR_URL = process.env.EDITOR_URL || 'vscode://file/{path}:{line}'; const LOGGING_URL = process.env.LOGGING_URL || null; const featureFlagTarget = process.env.FEATURE_FLAG_TARGET || 'extension-oss'; diff --git a/packages/react-devtools-inline/webpack.config.js b/packages/react-devtools-inline/webpack.config.js index bc38a8792e4c4..950c2a4e689ea 100644 --- a/packages/react-devtools-inline/webpack.config.js +++ b/packages/react-devtools-inline/webpack.config.js @@ -20,6 +20,8 @@ if (!NODE_ENV) { const __DEV__ = NODE_ENV === 'development'; +const EDITOR_URL = process.env.EDITOR_URL || 'vscode://file/{path}:{line}'; + const DEVTOOLS_VERSION = getVersionString(); const babelOptions = { @@ -76,6 +78,7 @@ module.exports = { __TEST__: NODE_ENV === 'test', 'process.env.DEVTOOLS_PACKAGE': `"react-devtools-inline"`, 'process.env.DEVTOOLS_VERSION': `"${DEVTOOLS_VERSION}"`, + 'process.env.EDITOR_URL': `"${EDITOR_URL}"`, 'process.env.GITHUB_URL': `"${GITHUB_URL}"`, 'process.env.NODE_ENV': `"${NODE_ENV}"`, 'process.env.DARK_MODE_DIMMED_WARNING_COLOR': `"${DARK_MODE_DIMMED_WARNING_COLOR}"`, diff --git a/packages/react-devtools-shared/src/constants.js b/packages/react-devtools-shared/src/constants.js index 3c3aaae2fc461..798bdb9d900e3 100644 --- a/packages/react-devtools-shared/src/constants.js +++ b/packages/react-devtools-shared/src/constants.js @@ -32,6 +32,9 @@ export const LOCAL_STORAGE_FILTER_PREFERENCES_KEY = export const SESSION_STORAGE_LAST_SELECTION_KEY = 'React::DevTools::lastSelection'; +export const LOCAL_STORAGE_OPEN_IN_EDITOR_URL = + 'React::DevTools::openInEditorUrl'; + export const LOCAL_STORAGE_PARSE_HOOK_NAMES_KEY = 'React::DevTools::parseHookNames'; diff --git a/packages/react-devtools-shared/src/devtools/views/ButtonIcon.js b/packages/react-devtools-shared/src/devtools/views/ButtonIcon.js index 2f4bc437848f6..b384018671d92 100644 --- a/packages/react-devtools-shared/src/devtools/views/ButtonIcon.js +++ b/packages/react-devtools-shared/src/devtools/views/ButtonIcon.js @@ -74,7 +74,7 @@ export default function ButtonIcon({className = '', type}: Props) { pathData = PATH_DOWN; break; case 'editor': - pathData = PATH_VS_CODE; + pathData = PATH_EDITOR; break; case 'expanded': pathData = PATH_EXPANDED; @@ -273,6 +273,6 @@ const PATH_VIEW_SOURCE = ` M9.4 16.6L4.8 12l4.6-4.6L8 6l-6 6 6 6 1.4-1.4zm5.2 0l4.6-4.6-4.6-4.6L16 6l6 6-6 6-1.4-1.4z `; -const PATH_VS_CODE = ` - M 17.488281 2.394531 L 9.058594 10.148438 L 4.34375 6.597656 L 2.394531 7.730469 L 7.042969 12 L 2.394531 16.269531 L 4.34375 17.40625 L 9.058594 13.851562 L 17.488281 21.605469 L 21.605469 19.605469 L 21.605469 4.394531 Z M 17.488281 7.496094 L 17.488281 16.503906 L 11.511719 12 Z M 17.488281 7.496094 +const PATH_EDITOR = ` + M7 5h10v2h2V3c0-1.1-.9-1.99-2-1.99L7 1c-1.1 0-2 .9-2 2v4h2V5zm8.41 11.59L20 12l-4.59-4.59L14 8.83 17.17 12 14 15.17l1.41 1.42zM10 15.17L6.83 12 10 8.83 8.59 7.41 4 12l4.59 4.59L10 15.17zM17 19H7v-2H5v4c0 1.1.9 2 2 2h10c1.1 0 2-.9 2-2v-4h-2v2z `; diff --git a/packages/react-devtools-shared/src/devtools/views/Components/InspectedElement.js b/packages/react-devtools-shared/src/devtools/views/Components/InspectedElement.js index 39403fb0360ba..281cd58e68433 100644 --- a/packages/react-devtools-shared/src/devtools/views/Components/InspectedElement.js +++ b/packages/react-devtools-shared/src/devtools/views/Components/InspectedElement.js @@ -20,7 +20,7 @@ import {ElementTypeSuspense} from 'react-devtools-shared/src/types'; import CannotSuspendWarningMessage from './CannotSuspendWarningMessage'; import InspectedElementView from './InspectedElementView'; import {InspectedElementContext} from './InspectedElementContext'; -import {isInternalFacebookBuild} from 'react-devtools-feature-flags'; +import {getOpenInEditorURL} from '../../../utils'; import styles from './InspectedElement.css'; @@ -53,6 +53,7 @@ export default function InspectedElementWrapper(_: Props) { toggleParseHookNames, } = useContext(InspectedElementContext); + const element = inspectedElementID !== null ? store.getElementByID(inspectedElementID) @@ -124,6 +125,10 @@ export default function InspectedElementWrapper(_: Props) { inspectedElement != null && inspectedElement.canToggleSuspense; + const canOpenInEditor = + inspectedElement != null && + inspectedElement.source != null; + const toggleErrored = useCallback(() => { if (inspectedElement == null || targetErrorBoundaryID == null) { return; @@ -204,14 +209,14 @@ export default function InspectedElementWrapper(_: Props) { if (source == null) { return; } - const editorURL = process.env.EDITOR_URL; + + const editorURL = getOpenInEditorURL() ?? process.env.EDITOR_URL; if (typeof editorURL !== 'string') { return; } const url = new URL(editorURL); - url.searchParams.set('project', 'facebook-www'); - url.searchParams.append('paths[0]', source.fileName); - url.searchParams.append('lines[0]', String(source.lineNumber)); + url.href = url.href.replace('{path}', source.fileName); + url.href = url.href.replace('{line}', String(source.lineNumber)); window.open(url); }, [inspectedElement]); @@ -240,14 +245,12 @@ export default function InspectedElementWrapper(_: Props) { {element.displayName} - {isInternalFacebookBuild && ( - - )} + {canOpenInEditor && } {canToggleError && ( ( + LOCAL_STORAGE_OPEN_IN_EDITOR_URL, + null, + ); + const [componentFilters, setComponentFilters] = useState< Array, >(() => [...store.componentFilters]); @@ -271,6 +280,21 @@ export default function ComponentsSettings(_: {||}) { (may be slow) + +
Hide components where...
diff --git a/packages/react-devtools-shared/src/utils.js b/packages/react-devtools-shared/src/utils.js index 84c977f19d4e7..e0619030b82f8 100644 --- a/packages/react-devtools-shared/src/utils.js +++ b/packages/react-devtools-shared/src/utils.js @@ -34,6 +34,7 @@ import { import {ElementTypeRoot} from 'react-devtools-shared/src/types'; import { LOCAL_STORAGE_FILTER_PREFERENCES_KEY, + LOCAL_STORAGE_OPEN_IN_EDITOR_URL, LOCAL_STORAGE_SHOULD_BREAK_ON_CONSOLE_ERRORS, LOCAL_STORAGE_SHOULD_PATCH_CONSOLE_KEY, LOCAL_STORAGE_SHOW_INLINE_WARNINGS_AND_ERRORS_KEY, @@ -386,6 +387,18 @@ export function setShowInlineWarningsAndErrors(value: boolean): void { ); } +export function getOpenInEditorURL(): ?string { + try { + const url = localStorageGetItem( + LOCAL_STORAGE_OPEN_IN_EDITOR_URL, + ); + if (url != null) { + return JSON.parse(url); + } + } catch (error) {} + return null; +} + export function separateDisplayNameAndHOCs( displayName: string | null, type: ElementType, diff --git a/packages/react-devtools-shell/webpack.config.js b/packages/react-devtools-shell/webpack.config.js index 19f53f5d08b09..4a3f42ac85c3f 100644 --- a/packages/react-devtools-shell/webpack.config.js +++ b/packages/react-devtools-shell/webpack.config.js @@ -24,6 +24,8 @@ if (!TARGET) { process.exit(1); } +const EDITOR_URL = process.env.EDITOR_URL || 'vscode://file/{path}:{line}'; + const builtModulesDir = resolve( __dirname, '..', @@ -69,6 +71,7 @@ const config = { __PROFILE__: false, __TEST__: NODE_ENV === 'test', 'process.env.GITHUB_URL': `"${GITHUB_URL}"`, + 'process.env.EDITOR_URL': `"${EDITOR_URL}"`, 'process.env.DEVTOOLS_PACKAGE': `"react-devtools-shell"`, 'process.env.DEVTOOLS_VERSION': `"${DEVTOOLS_VERSION}"`, 'process.env.DARK_MODE_DIMMED_WARNING_COLOR': `"${DARK_MODE_DIMMED_WARNING_COLOR}"`, From e5b7dc146d40ee4c5308220aef3437533974ed99 Mon Sep 17 00:00:00 2001 From: Ezzudin Alkotob Date: Sun, 31 Oct 2021 22:35:04 -0700 Subject: [PATCH 3/7] configurable editor --- .../react-devtools-core/webpack.standalone.js | 2 +- .../webpack.config.js | 2 +- .../react-devtools-inline/webpack.config.js | 3 +++ .../react-devtools-shared/src/constants.js | 3 +++ .../src/devtools/views/ButtonIcon.js | 6 ++--- .../views/Components/InspectedElement.js | 15 +++++++----- .../views/Settings/ComponentsSettings.js | 23 ++++++++++++++++++- packages/react-devtools-shared/src/utils.js | 11 +++++++++ .../react-devtools-shell/webpack.config.js | 3 +++ 9 files changed, 56 insertions(+), 12 deletions(-) diff --git a/packages/react-devtools-core/webpack.standalone.js b/packages/react-devtools-core/webpack.standalone.js index f5866300b62df..508d485c6fb21 100644 --- a/packages/react-devtools-core/webpack.standalone.js +++ b/packages/react-devtools-core/webpack.standalone.js @@ -30,7 +30,7 @@ const __DEV__ = NODE_ENV === 'development'; const DEVTOOLS_VERSION = getVersionString(); -const EDITOR_URL = process.env.EDITOR_URL || null; +const EDITOR_URL = process.env.EDITOR_URL || 'vscode://file/{path}:{line}'; const LOGGING_URL = process.env.LOGGING_URL || null; const featureFlagTarget = diff --git a/packages/react-devtools-extensions/webpack.config.js b/packages/react-devtools-extensions/webpack.config.js index 67bb309a0b5d2..4a393b248f9b6 100644 --- a/packages/react-devtools-extensions/webpack.config.js +++ b/packages/react-devtools-extensions/webpack.config.js @@ -32,7 +32,7 @@ const __DEV__ = NODE_ENV === 'development'; const DEVTOOLS_VERSION = getVersionString(process.env.DEVTOOLS_VERSION); -const EDITOR_URL = process.env.EDITOR_URL || null; +const EDITOR_URL = process.env.EDITOR_URL || 'vscode://file/{path}:{line}'; const LOGGING_URL = process.env.LOGGING_URL || null; const featureFlagTarget = process.env.FEATURE_FLAG_TARGET || 'extension-oss'; diff --git a/packages/react-devtools-inline/webpack.config.js b/packages/react-devtools-inline/webpack.config.js index bc38a8792e4c4..950c2a4e689ea 100644 --- a/packages/react-devtools-inline/webpack.config.js +++ b/packages/react-devtools-inline/webpack.config.js @@ -20,6 +20,8 @@ if (!NODE_ENV) { const __DEV__ = NODE_ENV === 'development'; +const EDITOR_URL = process.env.EDITOR_URL || 'vscode://file/{path}:{line}'; + const DEVTOOLS_VERSION = getVersionString(); const babelOptions = { @@ -76,6 +78,7 @@ module.exports = { __TEST__: NODE_ENV === 'test', 'process.env.DEVTOOLS_PACKAGE': `"react-devtools-inline"`, 'process.env.DEVTOOLS_VERSION': `"${DEVTOOLS_VERSION}"`, + 'process.env.EDITOR_URL': `"${EDITOR_URL}"`, 'process.env.GITHUB_URL': `"${GITHUB_URL}"`, 'process.env.NODE_ENV': `"${NODE_ENV}"`, 'process.env.DARK_MODE_DIMMED_WARNING_COLOR': `"${DARK_MODE_DIMMED_WARNING_COLOR}"`, diff --git a/packages/react-devtools-shared/src/constants.js b/packages/react-devtools-shared/src/constants.js index 3c3aaae2fc461..798bdb9d900e3 100644 --- a/packages/react-devtools-shared/src/constants.js +++ b/packages/react-devtools-shared/src/constants.js @@ -32,6 +32,9 @@ export const LOCAL_STORAGE_FILTER_PREFERENCES_KEY = export const SESSION_STORAGE_LAST_SELECTION_KEY = 'React::DevTools::lastSelection'; +export const LOCAL_STORAGE_OPEN_IN_EDITOR_URL = + 'React::DevTools::openInEditorUrl'; + export const LOCAL_STORAGE_PARSE_HOOK_NAMES_KEY = 'React::DevTools::parseHookNames'; diff --git a/packages/react-devtools-shared/src/devtools/views/ButtonIcon.js b/packages/react-devtools-shared/src/devtools/views/ButtonIcon.js index 2f4bc437848f6..b384018671d92 100644 --- a/packages/react-devtools-shared/src/devtools/views/ButtonIcon.js +++ b/packages/react-devtools-shared/src/devtools/views/ButtonIcon.js @@ -74,7 +74,7 @@ export default function ButtonIcon({className = '', type}: Props) { pathData = PATH_DOWN; break; case 'editor': - pathData = PATH_VS_CODE; + pathData = PATH_EDITOR; break; case 'expanded': pathData = PATH_EXPANDED; @@ -273,6 +273,6 @@ const PATH_VIEW_SOURCE = ` M9.4 16.6L4.8 12l4.6-4.6L8 6l-6 6 6 6 1.4-1.4zm5.2 0l4.6-4.6-4.6-4.6L16 6l6 6-6 6-1.4-1.4z `; -const PATH_VS_CODE = ` - M 17.488281 2.394531 L 9.058594 10.148438 L 4.34375 6.597656 L 2.394531 7.730469 L 7.042969 12 L 2.394531 16.269531 L 4.34375 17.40625 L 9.058594 13.851562 L 17.488281 21.605469 L 21.605469 19.605469 L 21.605469 4.394531 Z M 17.488281 7.496094 L 17.488281 16.503906 L 11.511719 12 Z M 17.488281 7.496094 +const PATH_EDITOR = ` + M7 5h10v2h2V3c0-1.1-.9-1.99-2-1.99L7 1c-1.1 0-2 .9-2 2v4h2V5zm8.41 11.59L20 12l-4.59-4.59L14 8.83 17.17 12 14 15.17l1.41 1.42zM10 15.17L6.83 12 10 8.83 8.59 7.41 4 12l4.59 4.59L10 15.17zM17 19H7v-2H5v4c0 1.1.9 2 2 2h10c1.1 0 2-.9 2-2v-4h-2v2z `; diff --git a/packages/react-devtools-shared/src/devtools/views/Components/InspectedElement.js b/packages/react-devtools-shared/src/devtools/views/Components/InspectedElement.js index 39403fb0360ba..77818a10d9313 100644 --- a/packages/react-devtools-shared/src/devtools/views/Components/InspectedElement.js +++ b/packages/react-devtools-shared/src/devtools/views/Components/InspectedElement.js @@ -20,7 +20,7 @@ import {ElementTypeSuspense} from 'react-devtools-shared/src/types'; import CannotSuspendWarningMessage from './CannotSuspendWarningMessage'; import InspectedElementView from './InspectedElementView'; import {InspectedElementContext} from './InspectedElementContext'; -import {isInternalFacebookBuild} from 'react-devtools-feature-flags'; +import {getOpenInEditorURL} from '../../../utils'; import styles from './InspectedElement.css'; @@ -124,6 +124,9 @@ export default function InspectedElementWrapper(_: Props) { inspectedElement != null && inspectedElement.canToggleSuspense; + const canOpenInEditor = + inspectedElement != null && inspectedElement.source != null; + const toggleErrored = useCallback(() => { if (inspectedElement == null || targetErrorBoundaryID == null) { return; @@ -204,14 +207,14 @@ export default function InspectedElementWrapper(_: Props) { if (source == null) { return; } - const editorURL = process.env.EDITOR_URL; + + const editorURL = getOpenInEditorURL() ?? process.env.EDITOR_URL; if (typeof editorURL !== 'string') { return; } const url = new URL(editorURL); - url.searchParams.set('project', 'facebook-www'); - url.searchParams.append('paths[0]', source.fileName); - url.searchParams.append('lines[0]', String(source.lineNumber)); + url.href = url.href.replace('{path}', source.fileName); + url.href = url.href.replace('{line}', String(source.lineNumber)); window.open(url); }, [inspectedElement]); @@ -240,7 +243,7 @@ export default function InspectedElementWrapper(_: Props) { {element.displayName} - {isInternalFacebookBuild && ( + {canOpenInEditor && (
diff --git a/packages/react-devtools-shared/src/utils.js b/packages/react-devtools-shared/src/utils.js index 84c977f19d4e7..473afab2cbfed 100644 --- a/packages/react-devtools-shared/src/utils.js +++ b/packages/react-devtools-shared/src/utils.js @@ -34,6 +34,7 @@ import { import {ElementTypeRoot} from 'react-devtools-shared/src/types'; import { LOCAL_STORAGE_FILTER_PREFERENCES_KEY, + LOCAL_STORAGE_OPEN_IN_EDITOR_URL, LOCAL_STORAGE_SHOULD_BREAK_ON_CONSOLE_ERRORS, LOCAL_STORAGE_SHOULD_PATCH_CONSOLE_KEY, LOCAL_STORAGE_SHOW_INLINE_WARNINGS_AND_ERRORS_KEY, @@ -386,6 +387,16 @@ export function setShowInlineWarningsAndErrors(value: boolean): void { ); } +export function getOpenInEditorURL(): ?string { + try { + const url = localStorageGetItem(LOCAL_STORAGE_OPEN_IN_EDITOR_URL); + if (url != null) { + return JSON.parse(url); + } + } catch (error) {} + return null; +} + export function separateDisplayNameAndHOCs( displayName: string | null, type: ElementType, diff --git a/packages/react-devtools-shell/webpack.config.js b/packages/react-devtools-shell/webpack.config.js index 19f53f5d08b09..4a3f42ac85c3f 100644 --- a/packages/react-devtools-shell/webpack.config.js +++ b/packages/react-devtools-shell/webpack.config.js @@ -24,6 +24,8 @@ if (!TARGET) { process.exit(1); } +const EDITOR_URL = process.env.EDITOR_URL || 'vscode://file/{path}:{line}'; + const builtModulesDir = resolve( __dirname, '..', @@ -69,6 +71,7 @@ const config = { __PROFILE__: false, __TEST__: NODE_ENV === 'test', 'process.env.GITHUB_URL': `"${GITHUB_URL}"`, + 'process.env.EDITOR_URL': `"${EDITOR_URL}"`, 'process.env.DEVTOOLS_PACKAGE': `"react-devtools-shell"`, 'process.env.DEVTOOLS_VERSION': `"${DEVTOOLS_VERSION}"`, 'process.env.DARK_MODE_DIMMED_WARNING_COLOR': `"${DARK_MODE_DIMMED_WARNING_COLOR}"`, From 033da1248e967e6f820c57b2848c6fac930c5d05 Mon Sep 17 00:00:00 2001 From: Ezzudin Alkotob Date: Tue, 2 Nov 2021 11:24:59 -0700 Subject: [PATCH 4/7] Disable functionality by default, make local storage source of truth and default it to env variable if present --- .../react-devtools-core/webpack.standalone.js | 4 ++-- .../react-devtools-extensions/webpack.config.js | 4 ++-- packages/react-devtools-inline/webpack.config.js | 4 ++-- .../views/Components/InspectedElement.js | 16 ++++++++-------- .../views/Settings/ComponentsSettings.js | 11 +++++------ packages/react-devtools-shared/src/utils.js | 2 ++ packages/react-devtools-shell/webpack.config.js | 4 ++-- 7 files changed, 23 insertions(+), 22 deletions(-) diff --git a/packages/react-devtools-core/webpack.standalone.js b/packages/react-devtools-core/webpack.standalone.js index 508d485c6fb21..234d638353f43 100644 --- a/packages/react-devtools-core/webpack.standalone.js +++ b/packages/react-devtools-core/webpack.standalone.js @@ -30,7 +30,7 @@ const __DEV__ = NODE_ENV === 'development'; const DEVTOOLS_VERSION = getVersionString(); -const EDITOR_URL = process.env.EDITOR_URL || 'vscode://file/{path}:{line}'; +const EDITOR_URL = process.env.EDITOR_URL || null; const LOGGING_URL = process.env.LOGGING_URL || null; const featureFlagTarget = @@ -84,7 +84,7 @@ module.exports = { __TEST__: NODE_ENV === 'test', 'process.env.DEVTOOLS_PACKAGE': `"react-devtools-core"`, 'process.env.DEVTOOLS_VERSION': `"${DEVTOOLS_VERSION}"`, - 'process.env.EDITOR_URL': `"${EDITOR_URL}"`, + 'process.env.EDITOR_URL': EDITOR_URL != null ? `"${EDITOR_URL}"` : null, 'process.env.GITHUB_URL': `"${GITHUB_URL}"`, 'process.env.LOGGING_URL': `"${LOGGING_URL}"`, 'process.env.NODE_ENV': `"${NODE_ENV}"`, diff --git a/packages/react-devtools-extensions/webpack.config.js b/packages/react-devtools-extensions/webpack.config.js index 4a393b248f9b6..ac7c51f3bdc5e 100644 --- a/packages/react-devtools-extensions/webpack.config.js +++ b/packages/react-devtools-extensions/webpack.config.js @@ -32,7 +32,7 @@ const __DEV__ = NODE_ENV === 'development'; const DEVTOOLS_VERSION = getVersionString(process.env.DEVTOOLS_VERSION); -const EDITOR_URL = process.env.EDITOR_URL || 'vscode://file/{path}:{line}'; +const EDITOR_URL = process.env.EDITOR_URL || null; const LOGGING_URL = process.env.LOGGING_URL || null; const featureFlagTarget = process.env.FEATURE_FLAG_TARGET || 'extension-oss'; @@ -93,7 +93,7 @@ module.exports = { __TEST__: NODE_ENV === 'test', 'process.env.DEVTOOLS_PACKAGE': `"react-devtools-extensions"`, 'process.env.DEVTOOLS_VERSION': `"${DEVTOOLS_VERSION}"`, - 'process.env.EDITOR_URL': `"${EDITOR_URL}"`, + 'process.env.EDITOR_URL': EDITOR_URL != null ? `"${EDITOR_URL}"` : null, 'process.env.GITHUB_URL': `"${GITHUB_URL}"`, 'process.env.LOGGING_URL': `"${LOGGING_URL}"`, 'process.env.NODE_ENV': `"${NODE_ENV}"`, diff --git a/packages/react-devtools-inline/webpack.config.js b/packages/react-devtools-inline/webpack.config.js index 950c2a4e689ea..e24eb9091328d 100644 --- a/packages/react-devtools-inline/webpack.config.js +++ b/packages/react-devtools-inline/webpack.config.js @@ -20,7 +20,7 @@ if (!NODE_ENV) { const __DEV__ = NODE_ENV === 'development'; -const EDITOR_URL = process.env.EDITOR_URL || 'vscode://file/{path}:{line}'; +const EDITOR_URL = process.env.EDITOR_URL || null; const DEVTOOLS_VERSION = getVersionString(); @@ -78,7 +78,7 @@ module.exports = { __TEST__: NODE_ENV === 'test', 'process.env.DEVTOOLS_PACKAGE': `"react-devtools-inline"`, 'process.env.DEVTOOLS_VERSION': `"${DEVTOOLS_VERSION}"`, - 'process.env.EDITOR_URL': `"${EDITOR_URL}"`, + 'process.env.EDITOR_URL': EDITOR_URL != null ? `"${EDITOR_URL}"` : null, 'process.env.GITHUB_URL': `"${GITHUB_URL}"`, 'process.env.NODE_ENV': `"${NODE_ENV}"`, 'process.env.DARK_MODE_DIMMED_WARNING_COLOR': `"${DARK_MODE_DIMMED_WARNING_COLOR}"`, diff --git a/packages/react-devtools-shared/src/devtools/views/Components/InspectedElement.js b/packages/react-devtools-shared/src/devtools/views/Components/InspectedElement.js index 77818a10d9313..58717ddca5d7e 100644 --- a/packages/react-devtools-shared/src/devtools/views/Components/InspectedElement.js +++ b/packages/react-devtools-shared/src/devtools/views/Components/InspectedElement.js @@ -124,8 +124,12 @@ export default function InspectedElementWrapper(_: Props) { inspectedElement != null && inspectedElement.canToggleSuspense; + const editorURL = getOpenInEditorURL(); + const canOpenInEditor = - inspectedElement != null && inspectedElement.source != null; + editorURL && + inspectedElement != null && + inspectedElement.source != null; const toggleErrored = useCallback(() => { if (inspectedElement == null || targetErrorBoundaryID == null) { @@ -204,19 +208,15 @@ export default function InspectedElementWrapper(_: Props) { const onOpenInEditor = useCallback(() => { const source = inspectedElement?.source; - if (source == null) { - return; - } - - const editorURL = getOpenInEditorURL() ?? process.env.EDITOR_URL; - if (typeof editorURL !== 'string') { + if (source == null || editorURL == null) { return; } + console.log(editorURL); const url = new URL(editorURL); url.href = url.href.replace('{path}', source.fileName); url.href = url.href.replace('{line}', String(source.lineNumber)); window.open(url); - }, [inspectedElement]); + }, [inspectedElement, editorURL]); if (element === null) { return ( diff --git a/packages/react-devtools-shared/src/devtools/views/Settings/ComponentsSettings.js b/packages/react-devtools-shared/src/devtools/views/Settings/ComponentsSettings.js index 26609667ef4ee..f6dfe1017f87a 100644 --- a/packages/react-devtools-shared/src/devtools/views/Settings/ComponentsSettings.js +++ b/packages/react-devtools-shared/src/devtools/views/Settings/ComponentsSettings.js @@ -82,9 +82,9 @@ export default function ComponentsSettings(_: {||}) { [setParseHookNames], ); - const [openInEditorURL, setOpenInEditorURL] = useLocalStorage( + const [openInEditorURL, setOpenInEditorURL] = useLocalStorage( LOCAL_STORAGE_OPEN_IN_EDITOR_URL, - null, + typeof process.env.editorURL === 'string' ? process.env.editorURL : '', ); const [componentFilters, setComponentFilters] = useState< @@ -282,11 +282,10 @@ export default function ComponentsSettings(_: {||}) { { - const value = e.target.value; - setOpenInEditorURL(value !== '' ? value : null); + setOpenInEditorURL(e.target.value); }} /> (restart to take effect) diff --git a/packages/react-devtools-shared/src/utils.js b/packages/react-devtools-shared/src/utils.js index 473afab2cbfed..8630a2ca34154 100644 --- a/packages/react-devtools-shared/src/utils.js +++ b/packages/react-devtools-shared/src/utils.js @@ -392,6 +392,8 @@ export function getOpenInEditorURL(): ?string { const url = localStorageGetItem(LOCAL_STORAGE_OPEN_IN_EDITOR_URL); if (url != null) { return JSON.parse(url); + } else if (typeof process.env.EDITOR_URL === 'string') { + return process.env.EDITOR_URL; } } catch (error) {} return null; diff --git a/packages/react-devtools-shell/webpack.config.js b/packages/react-devtools-shell/webpack.config.js index 4a3f42ac85c3f..18c55d1d8b740 100644 --- a/packages/react-devtools-shell/webpack.config.js +++ b/packages/react-devtools-shell/webpack.config.js @@ -24,7 +24,7 @@ if (!TARGET) { process.exit(1); } -const EDITOR_URL = process.env.EDITOR_URL || 'vscode://file/{path}:{line}'; +const EDITOR_URL = process.env.EDITOR_URL || null; const builtModulesDir = resolve( __dirname, @@ -71,7 +71,7 @@ const config = { __PROFILE__: false, __TEST__: NODE_ENV === 'test', 'process.env.GITHUB_URL': `"${GITHUB_URL}"`, - 'process.env.EDITOR_URL': `"${EDITOR_URL}"`, + 'process.env.EDITOR_URL': EDITOR_URL != null ? `"${EDITOR_URL}"` : null, 'process.env.DEVTOOLS_PACKAGE': `"react-devtools-shell"`, 'process.env.DEVTOOLS_VERSION': `"${DEVTOOLS_VERSION}"`, 'process.env.DARK_MODE_DIMMED_WARNING_COLOR': `"${DARK_MODE_DIMMED_WARNING_COLOR}"`, From 6608106d6c3ae5bde85a9e378556d8d6222e7d71 Mon Sep 17 00:00:00 2001 From: Ezzudin Alkotob Date: Tue, 2 Nov 2021 11:31:33 -0700 Subject: [PATCH 5/7] fix prettier --- .../src/devtools/views/Components/InspectedElement.js | 4 +--- 1 file changed, 1 insertion(+), 3 deletions(-) diff --git a/packages/react-devtools-shared/src/devtools/views/Components/InspectedElement.js b/packages/react-devtools-shared/src/devtools/views/Components/InspectedElement.js index 58717ddca5d7e..d8e93b6d75240 100644 --- a/packages/react-devtools-shared/src/devtools/views/Components/InspectedElement.js +++ b/packages/react-devtools-shared/src/devtools/views/Components/InspectedElement.js @@ -127,9 +127,7 @@ export default function InspectedElementWrapper(_: Props) { const editorURL = getOpenInEditorURL(); const canOpenInEditor = - editorURL && - inspectedElement != null && - inspectedElement.source != null; + editorURL && inspectedElement != null && inspectedElement.source != null; const toggleErrored = useCallback(() => { if (inspectedElement == null || targetErrorBoundaryID == null) { From 555ad58901dcc8067ebac0ffd75f4fdd41aba41e Mon Sep 17 00:00:00 2001 From: Ezzudin Alkotob Date: Tue, 2 Nov 2021 11:35:22 -0700 Subject: [PATCH 6/7] fix bug in default value for env variable case --- .../src/devtools/views/Settings/ComponentsSettings.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/packages/react-devtools-shared/src/devtools/views/Settings/ComponentsSettings.js b/packages/react-devtools-shared/src/devtools/views/Settings/ComponentsSettings.js index f6dfe1017f87a..df38f65664212 100644 --- a/packages/react-devtools-shared/src/devtools/views/Settings/ComponentsSettings.js +++ b/packages/react-devtools-shared/src/devtools/views/Settings/ComponentsSettings.js @@ -84,7 +84,7 @@ export default function ComponentsSettings(_: {||}) { const [openInEditorURL, setOpenInEditorURL] = useLocalStorage( LOCAL_STORAGE_OPEN_IN_EDITOR_URL, - typeof process.env.editorURL === 'string' ? process.env.editorURL : '', + typeof process.env.EDITOR_URL === 'string' ? process.env.EDITOR_URL : '', ); const [componentFilters, setComponentFilters] = useState< From 9550c04483943589ffdf66dd0a8f86a25ed0c6f1 Mon Sep 17 00:00:00 2001 From: Brian Vaughn Date: Wed, 3 Nov 2021 11:11:14 -0400 Subject: [PATCH 7/7] Couple of minor tweaks: 1. Removed an unnecessary console.log 2. Added extra space/padding around new editor URL setting 3. Removed 'restart needed' label and updated setting to listen for change event --- .../views/Components/InspectedElement.js | 17 ++++++++++++++--- .../views/Settings/ComponentsSettings.js | 10 +++++----- .../devtools/views/Settings/SettingsShared.css | 8 ++++++++ .../src/devtools/views/hooks.js | 3 +++ packages/react-devtools-shared/src/utils.js | 18 +++++++++++------- 5 files changed, 41 insertions(+), 15 deletions(-) diff --git a/packages/react-devtools-shared/src/devtools/views/Components/InspectedElement.js b/packages/react-devtools-shared/src/devtools/views/Components/InspectedElement.js index d8e93b6d75240..9ebd30a6ec0b3 100644 --- a/packages/react-devtools-shared/src/devtools/views/Components/InspectedElement.js +++ b/packages/react-devtools-shared/src/devtools/views/Components/InspectedElement.js @@ -8,7 +8,7 @@ */ import * as React from 'react'; -import {useCallback, useContext} from 'react'; +import {useCallback, useContext, useSyncExternalStore} from 'react'; import {TreeDispatcherContext, TreeStateContext} from './TreeContext'; import {BridgeContext, StoreContext, OptionsContext} from '../context'; import Button from '../Button'; @@ -21,6 +21,7 @@ import CannotSuspendWarningMessage from './CannotSuspendWarningMessage'; import InspectedElementView from './InspectedElementView'; import {InspectedElementContext} from './InspectedElementContext'; import {getOpenInEditorURL} from '../../../utils'; +import {LOCAL_STORAGE_OPEN_IN_EDITOR_URL} from '../../../constants'; import styles from './InspectedElement.css'; @@ -124,7 +125,17 @@ export default function InspectedElementWrapper(_: Props) { inspectedElement != null && inspectedElement.canToggleSuspense; - const editorURL = getOpenInEditorURL(); + const editorURL = useSyncExternalStore( + function subscribe(callback) { + window.addEventListener(LOCAL_STORAGE_OPEN_IN_EDITOR_URL, callback); + return function unsubscribe() { + window.removeEventListener(LOCAL_STORAGE_OPEN_IN_EDITOR_URL, callback); + }; + }, + function getState() { + return getOpenInEditorURL(); + }, + ); const canOpenInEditor = editorURL && inspectedElement != null && inspectedElement.source != null; @@ -209,7 +220,7 @@ export default function InspectedElementWrapper(_: Props) { if (source == null || editorURL == null) { return; } - console.log(editorURL); + const url = new URL(editorURL); url.href = url.href.replace('{path}', source.fileName); url.href = url.href.replace('{line}', String(source.lineNumber)); diff --git a/packages/react-devtools-shared/src/devtools/views/Settings/ComponentsSettings.js b/packages/react-devtools-shared/src/devtools/views/Settings/ComponentsSettings.js index df38f65664212..83c3b2a612963 100644 --- a/packages/react-devtools-shared/src/devtools/views/Settings/ComponentsSettings.js +++ b/packages/react-devtools-shared/src/devtools/views/Settings/ComponentsSettings.js @@ -38,6 +38,7 @@ import { ElementTypeProfiler, ElementTypeSuspense, } from 'react-devtools-shared/src/types'; +import {getDefaultOpenInEditorURL} from 'react-devtools-shared/src/utils'; import styles from './SettingsShared.css'; @@ -84,7 +85,7 @@ export default function ComponentsSettings(_: {||}) { const [openInEditorURL, setOpenInEditorURL] = useLocalStorage( LOCAL_STORAGE_OPEN_IN_EDITOR_URL, - typeof process.env.EDITOR_URL === 'string' ? process.env.EDITOR_URL : '', + getDefaultOpenInEditorURL(), ); const [componentFilters, setComponentFilters] = useState< @@ -277,18 +278,17 @@ export default function ComponentsSettings(_: {||}) { (may be slow) -