зеркало из https://github.com/mozilla/gecko-dev.git
Bug 1464486 - Update Debugger Frontend v59. r=dwalsh
This commit is contained in:
Родитель
7d46f4bb8c
Коммит
15e1d86b8e
|
@ -1,13 +1,13 @@
|
|||
This is the debugger.html project output.
|
||||
See https://github.com/devtools-html/debugger.html
|
||||
|
||||
Version 58
|
||||
Version 59
|
||||
|
||||
Comparison: https://github.com/devtools-html/debugger.html/compare/release-57...release-58
|
||||
Comparison: https://github.com/devtools-html/debugger.html/compare/release-58...release-59
|
||||
|
||||
Packages:
|
||||
- babel-plugin-transform-es2015-modules-commonjs @6.26.2
|
||||
- babel-preset-react @6.24.1
|
||||
- react @16.2.0
|
||||
- react-dom @16.2.0
|
||||
- webpack @3.12.0
|
||||
- webpack @3.11.0
|
||||
|
|
|
@ -1108,7 +1108,10 @@ html .toggle-button.end.vertical svg {
|
|||
|
||||
.search-field i.magnifying-glass,
|
||||
.search-field i.sad-face {
|
||||
padding: 6px;
|
||||
padding-top: 5px;
|
||||
padding-bottom: 5px;
|
||||
padding-inline-end: 10px;
|
||||
padding-inline-start: 5px;
|
||||
width: 24px;
|
||||
}
|
||||
|
||||
|
@ -1118,6 +1121,11 @@ html .toggle-button.end.vertical svg {
|
|||
width: 40px;
|
||||
}
|
||||
|
||||
.search-field.big i.sad-face {
|
||||
padding-top: 4px;
|
||||
padding-inline-start: 4px;
|
||||
}
|
||||
|
||||
.search-field .magnifying-glass path,
|
||||
.search-field .magnifying-glass ellipse {
|
||||
stroke: var(--theme-comment);
|
||||
|
@ -1134,18 +1142,13 @@ html .toggle-button.end.vertical svg {
|
|||
.search-field .summary {
|
||||
line-height: 27px;
|
||||
text-align: center;
|
||||
padding-right: 10px;
|
||||
padding-inline-end: 10px;
|
||||
color: var(--theme-body-color-inactive);
|
||||
align-self: center;
|
||||
padding-top: 1px;
|
||||
white-space: nowrap;
|
||||
}
|
||||
|
||||
.search-field.big .summary {
|
||||
padding: 5px 0 5px 0;
|
||||
line-height: 2rem;
|
||||
}
|
||||
|
||||
.search-field .search-nav-buttons {
|
||||
display: flex;
|
||||
user-select: none;
|
||||
|
@ -1261,7 +1264,7 @@ html .toggle-button.end.vertical svg {
|
|||
}
|
||||
|
||||
.project-text-search .search-field .close-btn.big {
|
||||
margin-top: 6px;
|
||||
margin-top: 2px;
|
||||
}
|
||||
|
||||
.project-text-search .managed-tree {
|
||||
|
@ -3077,7 +3080,7 @@ html[dir="rtl"] .breakpoints-list .breakpoint .breakpoint-line {
|
|||
max-width: calc(100% - var(--breakpoint-expression-right-clear-space));
|
||||
display: inline-block;
|
||||
padding-inline-end: 8px;
|
||||
cursor: default;
|
||||
cursor: pointer;
|
||||
flex-grow: 1;
|
||||
text-overflow: ellipsis;
|
||||
overflow: hidden;
|
||||
|
@ -3261,7 +3264,7 @@ html[dir="rtl"] .breakpoints-list .breakpoint .breakpoint-line {
|
|||
.expression-container__close-btn {
|
||||
position: absolute;
|
||||
offset-inline-end: 0px;
|
||||
top: 0px;
|
||||
top: 1px;
|
||||
}
|
||||
|
||||
.expression-content {
|
||||
|
@ -4049,6 +4052,7 @@ html .welcomebox .toggle-button-end.collapsed {
|
|||
position: relative;
|
||||
transition: all 0.15s ease;
|
||||
min-width: 40px;
|
||||
max-width: 100%;
|
||||
overflow: hidden;
|
||||
padding: 5px;
|
||||
margin-inline-start: 3px;
|
||||
|
|
|
@ -22811,7 +22811,7 @@ function toParsedScopes(children, sourceId) {
|
|||
return {
|
||||
start: scope.loc.start,
|
||||
end: scope.loc.end,
|
||||
type: scope.type === "module" ? "block" : scope.type,
|
||||
type: scope.type === "module" || scope.type === "function-body" ? "block" : scope.type,
|
||||
displayName: scope.displayName,
|
||||
bindings: scope.bindings,
|
||||
children: toParsedScopes(scope.children, sourceId)
|
||||
|
@ -22906,9 +22906,18 @@ function isLetOrConst(node) {
|
|||
}
|
||||
|
||||
function hasLexicalDeclaration(node, parent) {
|
||||
const nodes = [];
|
||||
if (t.isSwitchStatement(node)) {
|
||||
for (const caseNode of node.cases) {
|
||||
nodes.push(...caseNode.consequent);
|
||||
}
|
||||
} else {
|
||||
nodes.push(...node.body);
|
||||
}
|
||||
|
||||
const isFunctionBody = t.isFunction(parent, { body: node });
|
||||
|
||||
return node.body.some(child => isLexicalVariable(child) || !isFunctionBody && child.type === "FunctionDeclaration" || child.type === "ClassDeclaration");
|
||||
return nodes.some(child => isLexicalVariable(child) || t.isClassDeclaration(child) || !isFunctionBody && t.isFunctionDeclaration(child));
|
||||
}
|
||||
function isLexicalVariable(node) {
|
||||
return isNode(node, "VariableDeclaration") && isLetOrConst(node);
|
||||
|
@ -22973,19 +22982,27 @@ const scopeCollectionVisitor = {
|
|||
// This ignores Annex B function declaration hoisting, which
|
||||
// is probably a fine assumption.
|
||||
state.declarationBindingIds.add(node.id);
|
||||
const fnScope = getVarScope(scope);
|
||||
scope.bindings[node.id.name] = {
|
||||
type: fnScope === scope ? "var" : "let",
|
||||
refs: [{
|
||||
type: "fn-decl",
|
||||
start: fromBabelLocation(node.id.loc.start, state.sourceId),
|
||||
end: fromBabelLocation(node.id.loc.end, state.sourceId),
|
||||
declaration: {
|
||||
start: fromBabelLocation(node.loc.start, state.sourceId),
|
||||
end: fromBabelLocation(node.loc.end, state.sourceId)
|
||||
}
|
||||
}]
|
||||
};
|
||||
const refs = [{
|
||||
type: "fn-decl",
|
||||
start: fromBabelLocation(node.id.loc.start, state.sourceId),
|
||||
end: fromBabelLocation(node.id.loc.end, state.sourceId),
|
||||
declaration: {
|
||||
start: fromBabelLocation(node.loc.start, state.sourceId),
|
||||
end: fromBabelLocation(node.loc.end, state.sourceId)
|
||||
}
|
||||
}];
|
||||
|
||||
if (scope.type === "block") {
|
||||
scope.bindings[node.id.name] = {
|
||||
type: "let",
|
||||
refs
|
||||
};
|
||||
} else {
|
||||
getVarScope(scope).bindings[node.id.name] = {
|
||||
type: "var",
|
||||
refs
|
||||
};
|
||||
}
|
||||
}
|
||||
|
||||
scope = pushTempScope(state, "function", (0, _getFunctionName2.default)(node, parentNode), {
|
||||
|
@ -23007,6 +23024,13 @@ const scopeCollectionVisitor = {
|
|||
refs: []
|
||||
};
|
||||
}
|
||||
|
||||
if (t.isBlockStatement(node.body) && hasLexicalDeclaration(node.body, node)) {
|
||||
scope = pushTempScope(state, "function-body", "Function Body", {
|
||||
start: fromBabelLocation(node.body.loc.start, state.sourceId),
|
||||
end: fromBabelLocation(node.body.loc.end, state.sourceId)
|
||||
});
|
||||
}
|
||||
} else if (t.isClass(node)) {
|
||||
if (t.isIdentifier(node.id)) {
|
||||
// For decorated classes, the AST considers the first the decorator
|
||||
|
@ -23075,7 +23099,9 @@ const scopeCollectionVisitor = {
|
|||
end: fromBabelLocation(node.loc.end, state.sourceId)
|
||||
});
|
||||
parseDeclarator(node.param, scope, "var", "catch", node, state);
|
||||
} else if (t.isBlockStatement(node) && hasLexicalDeclaration(node, parentNode)) {
|
||||
} else if (t.isBlockStatement(node) &&
|
||||
// Function body's are handled in the function logic above.
|
||||
!t.isFunction(parentNode) && hasLexicalDeclaration(node, parentNode)) {
|
||||
// Debugger will create new lexical environment for the block.
|
||||
pushTempScope(state, "block", "Block", {
|
||||
start: fromBabelLocation(node.loc.start, state.sourceId),
|
||||
|
@ -23199,7 +23225,7 @@ const scopeCollectionVisitor = {
|
|||
type: "implicit",
|
||||
refs: []
|
||||
};
|
||||
} else if (t.isSwitchStatement(node) && node.cases.some(caseNode => caseNode.consequent.some(child => isLexicalVariable(child)))) {
|
||||
} else if (t.isSwitchStatement(node) && hasLexicalDeclaration(node, parentNode)) {
|
||||
pushTempScope(state, "block", "Switch", {
|
||||
start: fromBabelLocation(node.loc.start, state.sourceId),
|
||||
end: fromBabelLocation(node.loc.end, state.sourceId)
|
||||
|
@ -25012,6 +25038,7 @@ const {
|
|||
const dispatcher = new WorkerDispatcher();
|
||||
|
||||
const getOriginalURLs = dispatcher.task("getOriginalURLs");
|
||||
const getOriginalRanges = dispatcher.task("getOriginalRanges");
|
||||
const getGeneratedRanges = dispatcher.task("getGeneratedRanges", {
|
||||
queue: true
|
||||
});
|
||||
|
@ -25035,6 +25062,7 @@ module.exports = {
|
|||
isOriginalId,
|
||||
hasMappedSource,
|
||||
getOriginalURLs,
|
||||
getOriginalRanges,
|
||||
getGeneratedRanges,
|
||||
getGeneratedLocation,
|
||||
getAllGeneratedLocations,
|
||||
|
|
|
@ -417,7 +417,7 @@ function toggleBreakpoint(line, column) {
|
|||
line,
|
||||
column
|
||||
});
|
||||
const isEmptyLine = (0, _ast.isEmptyLineInSource)(state, line, selectedSource);
|
||||
const isEmptyLine = (0, _ast.isEmptyLineInSource)(state, line, selectedSource.id);
|
||||
|
||||
if (!bp && isEmptyLine || bp && bp.loading) {
|
||||
return;
|
||||
|
@ -434,8 +434,8 @@ function toggleBreakpoint(line, column) {
|
|||
}
|
||||
|
||||
return dispatch(addBreakpoint({
|
||||
sourceId: selectedSource.get("id"),
|
||||
sourceUrl: selectedSource.get("url"),
|
||||
sourceId: selectedSource.id,
|
||||
sourceUrl: selectedSource.url,
|
||||
line: line,
|
||||
column: column
|
||||
}));
|
||||
|
|
|
@ -211,9 +211,9 @@ const mapStateToProps = state => {
|
|||
return {
|
||||
selectedLocation: (0, _selectors.getSelectedLocation)(state),
|
||||
selectedSource,
|
||||
hasPrettyPrint: !!(0, _selectors.getPrettySource)(state, selectedSource.get("id")),
|
||||
hasPrettyPrint: !!(0, _selectors.getPrettySource)(state, selectedSource.id),
|
||||
contextMenu: (0, _selectors.getContextMenu)(state),
|
||||
getFunctionText: line => (0, _function.findFunctionText)(line, selectedSource.toJS(), symbols),
|
||||
getFunctionText: line => (0, _function.findFunctionText)(line, selectedSource, symbols),
|
||||
getFunctionLocation: line => (0, _ast.findClosestFunction)(symbols, {
|
||||
line,
|
||||
column: Infinity
|
||||
|
|
|
@ -70,7 +70,7 @@ class EmptyLines extends _react.Component {
|
|||
|
||||
const mapStateToProps = state => {
|
||||
const selectedSource = (0, _selectors.getSelectedSource)(state);
|
||||
const foundEmptyLines = (0, _selectors.getEmptyLines)(state, selectedSource.toJS());
|
||||
const foundEmptyLines = (0, _selectors.getEmptyLines)(state, selectedSource.id);
|
||||
return {
|
||||
selectedSource,
|
||||
emptyLines: selectedSource ? foundEmptyLines : []
|
||||
|
|
|
@ -169,7 +169,7 @@ const mapStateToProps = state => {
|
|||
breakpoints: (0, _selectors.getVisibleBreakpoints)(state),
|
||||
isPaused: (0, _selectors.isPaused)(state),
|
||||
contextMenu: (0, _selectors.getContextMenu)(state),
|
||||
emptyLines: (0, _selectors.getEmptyLines)(state, selectedSource.toJS())
|
||||
emptyLines: (0, _selectors.getEmptyLines)(state, selectedSource.id)
|
||||
};
|
||||
};
|
||||
|
||||
|
|
|
@ -18,6 +18,8 @@ var _SourceIcon2 = _interopRequireDefault(_SourceIcon);
|
|||
|
||||
var _Button = require("../shared/Button/index");
|
||||
|
||||
var _text = require("../../utils/text");
|
||||
|
||||
var _actions = require("../../actions/index");
|
||||
|
||||
var _actions2 = _interopRequireDefault(_actions);
|
||||
|
@ -175,7 +177,7 @@ class Tab extends _react.PureComponent {
|
|||
shouldHide: icon => ["file", "javascript"].includes(icon)
|
||||
}), _react2.default.createElement("div", {
|
||||
className: "filename"
|
||||
}, (0, _devtoolsModules.getUnicodeUrlPath)(filename)), _react2.default.createElement(_Button.CloseButton, {
|
||||
}, (0, _text.truncateMiddleText)((0, _devtoolsModules.getUnicodeUrlPath)(filename), 30)), _react2.default.createElement(_Button.CloseButton, {
|
||||
handleClick: onClickClose,
|
||||
tooltip: L10N.getStr("sourceTabs.closeTabButtonTooltip")
|
||||
}));
|
||||
|
|
|
@ -16,14 +16,14 @@ var _classnames = require("devtools/client/debugger/new/dist/vendors").vendored[
|
|||
|
||||
var _classnames2 = _interopRequireDefault(_classnames);
|
||||
|
||||
var _devtoolsSourceMap = require("devtools/client/shared/source-map/index.js");
|
||||
|
||||
var _Button = require("../shared/Button/index");
|
||||
|
||||
var _breakpoint = require("../../utils/breakpoint/index");
|
||||
|
||||
var _prefs = require("../../utils/prefs");
|
||||
|
||||
var _pause = require("../../utils/pause/index");
|
||||
|
||||
function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
|
||||
|
||||
/* This Source Code Form is subject to the terms of the Mozilla Public
|
||||
|
@ -39,19 +39,19 @@ function getBreakpointLocation(source, line, column) {
|
|||
function getBreakpointText(selectedSource, breakpoint) {
|
||||
const {
|
||||
condition,
|
||||
text,
|
||||
originalText
|
||||
text
|
||||
} = breakpoint;
|
||||
return condition || text;
|
||||
}
|
||||
|
||||
if (condition) {
|
||||
return condition;
|
||||
function isCurrentlyPausedAtBreakpoint(breakpoint, frame, why) {
|
||||
if (!frame || (0, _pause.isInterrupted)(why)) {
|
||||
return false;
|
||||
}
|
||||
|
||||
if (!selectedSource || (0, _devtoolsSourceMap.isGeneratedId)(selectedSource.id) || originalText.length == 0) {
|
||||
return text;
|
||||
}
|
||||
|
||||
return originalText;
|
||||
const bpId = (0, _breakpoint.getLocationWithoutColumn)(breakpoint.location);
|
||||
const pausedId = (0, _breakpoint.getLocationWithoutColumn)(frame.location);
|
||||
return bpId === pausedId;
|
||||
}
|
||||
|
||||
class Breakpoint extends _react.Component {
|
||||
|
@ -74,7 +74,9 @@ class Breakpoint extends _react.Component {
|
|||
shouldComponentUpdate(nextProps) {
|
||||
const prevBreakpoint = this.props.breakpoint;
|
||||
const nextBreakpoint = nextProps.breakpoint;
|
||||
return !prevBreakpoint || this.props.selectedSource != nextProps.selectedSource || prevBreakpoint.text != nextBreakpoint.text || prevBreakpoint.disabled != nextBreakpoint.disabled || prevBreakpoint.condition != nextBreakpoint.condition || prevBreakpoint.hidden != nextBreakpoint.hidden || prevBreakpoint.isCurrentlyPaused != nextBreakpoint.isCurrentlyPaused;
|
||||
const wasPaused = isCurrentlyPausedAtBreakpoint(prevBreakpoint, this.props.frame, this.props.why);
|
||||
const isPaused = isCurrentlyPausedAtBreakpoint(nextBreakpoint, nextProps.frame, nextProps.why);
|
||||
return !prevBreakpoint || this.props.selectedSource != nextProps.selectedSource || prevBreakpoint.text != nextBreakpoint.text || prevBreakpoint.disabled != nextBreakpoint.disabled || prevBreakpoint.condition != nextBreakpoint.condition || prevBreakpoint.hidden != nextBreakpoint.hidden || prevBreakpoint.frame != nextBreakpoint.frame || wasPaused != isPaused;
|
||||
}
|
||||
|
||||
destroyEditor() {
|
||||
|
@ -144,22 +146,15 @@ class Breakpoint extends _react.Component {
|
|||
renderLineClose() {
|
||||
const {
|
||||
breakpoint,
|
||||
onCloseClick,
|
||||
selectedSource
|
||||
onCloseClick
|
||||
} = this.props;
|
||||
const {
|
||||
location
|
||||
} = breakpoint;
|
||||
let {
|
||||
const {
|
||||
line,
|
||||
column
|
||||
} = location;
|
||||
|
||||
if (selectedSource && (0, _devtoolsSourceMap.isGeneratedId)(selectedSource.id) && breakpoint.generatedLocation) {
|
||||
line = breakpoint.generatedLocation.line;
|
||||
column = breakpoint.generatedLocation.column;
|
||||
}
|
||||
|
||||
return _react2.default.createElement("div", {
|
||||
className: "breakpoint-line-close"
|
||||
}, _react2.default.createElement("div", {
|
||||
|
@ -174,10 +169,12 @@ class Breakpoint extends _react.Component {
|
|||
const {
|
||||
breakpoint,
|
||||
onClick,
|
||||
onContextMenu
|
||||
onContextMenu,
|
||||
frame,
|
||||
why
|
||||
} = this.props;
|
||||
const locationId = breakpoint.locationId;
|
||||
const isCurrentlyPaused = breakpoint.isCurrentlyPaused;
|
||||
const isCurrentlyPaused = isCurrentlyPausedAtBreakpoint(breakpoint, frame, why);
|
||||
const isDisabled = breakpoint.disabled;
|
||||
const isConditional = !!breakpoint.condition;
|
||||
return _react2.default.createElement("div", {
|
||||
|
|
|
@ -18,8 +18,6 @@ var _immutable = require("devtools/client/shared/vendor/immutable");
|
|||
|
||||
var I = _interopRequireWildcard(_immutable);
|
||||
|
||||
var _reselect = require("devtools/client/debugger/new/dist/vendors").vendored["reselect"];
|
||||
|
||||
var _lodash = require("devtools/client/shared/vendor/lodash");
|
||||
|
||||
var _Breakpoint = require("./Breakpoint");
|
||||
|
@ -38,10 +36,6 @@ var _source = require("../../utils/source");
|
|||
|
||||
var _selectors = require("../../selectors/index");
|
||||
|
||||
var _pause = require("../../utils/pause/index");
|
||||
|
||||
var _breakpoint = require("../../utils/breakpoint/index");
|
||||
|
||||
var _BreakpointsContextMenu = require("./BreakpointsContextMenu");
|
||||
|
||||
var _BreakpointsContextMenu2 = _interopRequireDefault(_BreakpointsContextMenu);
|
||||
|
@ -54,16 +48,6 @@ function _objectSpread(target) { for (var i = 1; i < arguments.length; i++) { va
|
|||
|
||||
function _defineProperty(obj, key, value) { if (key in obj) { Object.defineProperty(obj, key, { value: value, enumerable: true, configurable: true, writable: true }); } else { obj[key] = value; } return obj; }
|
||||
|
||||
function isCurrentlyPausedAtBreakpoint(frame, why, breakpoint) {
|
||||
if (!frame || !(0, _pause.isInterrupted)(why)) {
|
||||
return false;
|
||||
}
|
||||
|
||||
const bpId = (0, _breakpoint.makeLocationId)(breakpoint.location);
|
||||
const pausedId = (0, _breakpoint.makeLocationId)(frame.location);
|
||||
return bpId === pausedId;
|
||||
}
|
||||
|
||||
function createExceptionOption(label, value, onChange, className) {
|
||||
return _react2.default.createElement("div", {
|
||||
className: className,
|
||||
|
@ -106,7 +90,7 @@ class Breakpoints extends _react.Component {
|
|||
}
|
||||
|
||||
selectBreakpoint(breakpoint) {
|
||||
this.props.selectLocation(breakpoint.location);
|
||||
this.props.selectSpecificLocation(breakpoint.location);
|
||||
}
|
||||
|
||||
removeBreakpoint(event, breakpoint) {
|
||||
|
@ -116,12 +100,16 @@ class Breakpoints extends _react.Component {
|
|||
|
||||
renderBreakpoint(breakpoint) {
|
||||
const {
|
||||
selectedSource
|
||||
selectedSource,
|
||||
why,
|
||||
frame
|
||||
} = this.props;
|
||||
return _react2.default.createElement(_Breakpoint2.default, {
|
||||
key: breakpoint.locationId,
|
||||
breakpoint: breakpoint,
|
||||
selectedSource: selectedSource,
|
||||
why: why,
|
||||
frame: frame,
|
||||
onClick: () => this.selectBreakpoint(breakpoint),
|
||||
onContextMenu: e => (0, _BreakpointsContextMenu2.default)(_objectSpread({}, this.props, {
|
||||
breakpoint,
|
||||
|
@ -188,24 +176,10 @@ class Breakpoints extends _react.Component {
|
|||
|
||||
}
|
||||
|
||||
function updateLocation(sources, frame, why, bp) {
|
||||
const source = (0, _selectors.getSourceInSources)(sources, bp.location.sourceId);
|
||||
const isCurrentlyPaused = isCurrentlyPausedAtBreakpoint(frame, why, bp);
|
||||
const locationId = (0, _breakpoint.makeLocationId)(bp.location);
|
||||
|
||||
const localBP = _objectSpread({}, bp, {
|
||||
locationId,
|
||||
isCurrentlyPaused,
|
||||
source
|
||||
});
|
||||
|
||||
return localBP;
|
||||
}
|
||||
|
||||
const _getBreakpoints = (0, _reselect.createSelector)(_selectors.getBreakpoints, _selectors.getSources, _selectors.getTopFrame, _selectors.getPauseReason, (breakpoints, sources, frame, why) => breakpoints.map(bp => updateLocation(sources, frame, why, bp)).filter(bp => bp.source && !bp.source.isBlackBoxed));
|
||||
|
||||
const mapStateToProps = state => ({
|
||||
breakpoints: _getBreakpoints(state),
|
||||
breakpoints: (0, _selectors.getMappedBreakpoints)(state),
|
||||
frame: (0, _selectors.getTopFrame)(state),
|
||||
why: (0, _selectors.getPauseReason)(state),
|
||||
selectedSource: (0, _selectors.getSelectedSource)(state)
|
||||
});
|
||||
|
||||
|
|
|
@ -0,0 +1,196 @@
|
|||
"use strict";
|
||||
|
||||
Object.defineProperty(exports, "__esModule", {
|
||||
value: true
|
||||
});
|
||||
|
||||
var _react = require("devtools/client/shared/vendor/react");
|
||||
|
||||
var _react2 = _interopRequireDefault(_react);
|
||||
|
||||
var _reactRedux = require("devtools/client/shared/vendor/react-redux");
|
||||
|
||||
var _devtoolsSourceMap = require("devtools/client/shared/source-map/index.js");
|
||||
|
||||
var _classnames = require("devtools/client/debugger/new/dist/vendors").vendored["classnames"];
|
||||
|
||||
var _classnames2 = _interopRequireDefault(_classnames);
|
||||
|
||||
var _actions = require("../../../actions/index");
|
||||
|
||||
var _actions2 = _interopRequireDefault(_actions);
|
||||
|
||||
var _BreakpointsContextMenu = require("./BreakpointsContextMenu");
|
||||
|
||||
var _BreakpointsContextMenu2 = _interopRequireDefault(_BreakpointsContextMenu);
|
||||
|
||||
var _Button = require("../../shared/Button/index");
|
||||
|
||||
var _breakpoint = require("../../../utils/breakpoint/index");
|
||||
|
||||
var _prefs = require("../../../utils/prefs");
|
||||
|
||||
var _editor = require("../../../utils/editor/index");
|
||||
|
||||
var _selectors = require("../../../selectors/index");
|
||||
|
||||
function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
|
||||
|
||||
function _objectSpread(target) { for (var i = 1; i < arguments.length; i++) { var source = arguments[i] != null ? arguments[i] : {}; var ownKeys = Object.keys(source); if (typeof Object.getOwnPropertySymbols === 'function') { ownKeys = ownKeys.concat(Object.getOwnPropertySymbols(source).filter(function (sym) { return Object.getOwnPropertyDescriptor(source, sym).enumerable; })); } ownKeys.forEach(function (key) { _defineProperty(target, key, source[key]); }); } return target; }
|
||||
|
||||
function _defineProperty(obj, key, value) { if (key in obj) { Object.defineProperty(obj, key, { value: value, enumerable: true, configurable: true, writable: true }); } else { obj[key] = value; } return obj; }
|
||||
|
||||
function getMappedLocation(mappedLocation, selectedSource) {
|
||||
return selectedSource && (0, _devtoolsSourceMap.isGeneratedId)(selectedSource.id) ? mappedLocation.generatedLocation : mappedLocation.location;
|
||||
}
|
||||
|
||||
class Breakpoint extends _react.PureComponent {
|
||||
constructor(...args) {
|
||||
var _temp;
|
||||
|
||||
return _temp = super(...args), this.onContextMenu = e => {
|
||||
(0, _BreakpointsContextMenu2.default)(_objectSpread({}, this.props, {
|
||||
contextMenuEvent: e
|
||||
}));
|
||||
}, this.selectBreakpoint = () => {
|
||||
const {
|
||||
breakpoint,
|
||||
selectSpecificLocation
|
||||
} = this.props;
|
||||
selectSpecificLocation(breakpoint.location);
|
||||
}, this.removeBreakpoint = event => {
|
||||
const {
|
||||
breakpoint,
|
||||
removeBreakpoint
|
||||
} = this.props;
|
||||
event.stopPropagation();
|
||||
removeBreakpoint(breakpoint.location);
|
||||
}, this.handleBreakpointCheckbox = () => {
|
||||
const {
|
||||
breakpoint,
|
||||
enableBreakpoint,
|
||||
disableBreakpoint
|
||||
} = this.props;
|
||||
|
||||
if (breakpoint.loading) {
|
||||
return;
|
||||
}
|
||||
|
||||
if (breakpoint.disabled) {
|
||||
enableBreakpoint(breakpoint.location);
|
||||
} else {
|
||||
disableBreakpoint(breakpoint.location);
|
||||
}
|
||||
}, _temp;
|
||||
}
|
||||
|
||||
isCurrentlyPausedAtBreakpoint() {
|
||||
const {
|
||||
frame,
|
||||
breakpoint,
|
||||
selectedSource
|
||||
} = this.props;
|
||||
|
||||
if (!frame) {
|
||||
return false;
|
||||
}
|
||||
|
||||
const bpId = (0, _breakpoint.getLocationWithoutColumn)(getMappedLocation(breakpoint, selectedSource));
|
||||
const frameId = (0, _breakpoint.getLocationWithoutColumn)(getMappedLocation(frame, selectedSource));
|
||||
return bpId == frameId;
|
||||
}
|
||||
|
||||
getBreakpointLocation() {
|
||||
const {
|
||||
breakpoint,
|
||||
source,
|
||||
selectedSource
|
||||
} = this.props;
|
||||
const {
|
||||
column,
|
||||
line
|
||||
} = getMappedLocation(breakpoint, selectedSource);
|
||||
const isWasm = source && source.isWasm;
|
||||
const columnVal = _prefs.features.columnBreakpoints && column ? `:${column}` : "";
|
||||
const bpLocation = isWasm ? `0x${line.toString(16).toUpperCase()}` : `${line}${columnVal}`;
|
||||
return bpLocation;
|
||||
}
|
||||
|
||||
getBreakpointText() {
|
||||
const {
|
||||
selectedSource,
|
||||
breakpoint
|
||||
} = this.props;
|
||||
const {
|
||||
condition
|
||||
} = breakpoint;
|
||||
|
||||
if (condition) {
|
||||
return condition;
|
||||
}
|
||||
|
||||
if (selectedSource && (0, _devtoolsSourceMap.isGeneratedId)(selectedSource.id)) {
|
||||
return breakpoint.text;
|
||||
}
|
||||
|
||||
return breakpoint.originalText;
|
||||
}
|
||||
|
||||
highlightText() {
|
||||
const text = this.getBreakpointText();
|
||||
const sourceEditor = (0, _editor.getEditor)();
|
||||
|
||||
if (!text || !sourceEditor || !sourceEditor.editor) {
|
||||
return {
|
||||
__html: ""
|
||||
};
|
||||
}
|
||||
|
||||
const node = document.createElement("div");
|
||||
sourceEditor.editor.constructor.runMode(text, "application/javascript", node);
|
||||
return {
|
||||
__html: node.innerHTML
|
||||
};
|
||||
}
|
||||
|
||||
render() {
|
||||
const {
|
||||
breakpoint
|
||||
} = this.props;
|
||||
return _react2.default.createElement("div", {
|
||||
className: (0, _classnames2.default)({
|
||||
breakpoint,
|
||||
paused: this.isCurrentlyPausedAtBreakpoint(),
|
||||
disabled: breakpoint.disabled,
|
||||
"is-conditional": !!breakpoint.condition
|
||||
}),
|
||||
onClick: this.selectBreakpoint,
|
||||
onContextMenu: this.onContextMenu
|
||||
}, _react2.default.createElement("input", {
|
||||
type: "checkbox",
|
||||
className: "breakpoint-checkbox",
|
||||
checked: !breakpoint.disabled,
|
||||
onChange: this.handleBreakpointCheckbox,
|
||||
onClick: ev => ev.stopPropagation()
|
||||
}), _react2.default.createElement("label", {
|
||||
className: "breakpoint-label cm-s-mozilla",
|
||||
title: this.getBreakpointText(),
|
||||
dangerouslySetInnerHTML: this.highlightText()
|
||||
}), _react2.default.createElement("div", {
|
||||
className: "breakpoint-line-close"
|
||||
}, _react2.default.createElement("div", {
|
||||
className: "breakpoint-line"
|
||||
}, this.getBreakpointLocation()), _react2.default.createElement(_Button.CloseButton, {
|
||||
handleClick: e => this.removeBreakpoint(e),
|
||||
tooltip: L10N.getStr("breakpoints.removeBreakpointTooltip")
|
||||
})));
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
const mapStateToProps = state => ({
|
||||
frame: (0, _selectors.getTopFrame)(state),
|
||||
selectedSource: (0, _selectors.getSelectedSource)(state)
|
||||
});
|
||||
|
||||
exports.default = (0, _reactRedux.connect)(mapStateToProps, _actions2.default)(Breakpoint);
|
|
@ -0,0 +1,201 @@
|
|||
"use strict";
|
||||
|
||||
Object.defineProperty(exports, "__esModule", {
|
||||
value: true
|
||||
});
|
||||
exports.default = showContextMenu;
|
||||
|
||||
var _devtoolsContextmenu = require("devtools/client/debugger/new/dist/vendors").vendored["devtools-contextmenu"];
|
||||
|
||||
/* This Source Code Form is subject to the terms of the Mozilla Public
|
||||
* License, v. 2.0. If a copy of the MPL was not distributed with this
|
||||
* file, You can obtain one at <http://mozilla.org/MPL/2.0/>. */
|
||||
function showContextMenu(props) {
|
||||
const {
|
||||
removeBreakpoint,
|
||||
removeBreakpoints,
|
||||
removeAllBreakpoints,
|
||||
toggleBreakpoints,
|
||||
toggleAllBreakpoints,
|
||||
toggleDisabledBreakpoint,
|
||||
selectLocation,
|
||||
setBreakpointCondition,
|
||||
openConditionalPanel,
|
||||
breakpoints,
|
||||
breakpoint,
|
||||
contextMenuEvent
|
||||
} = props;
|
||||
contextMenuEvent.preventDefault();
|
||||
const deleteSelfLabel = L10N.getStr("breakpointMenuItem.deleteSelf2.label");
|
||||
const deleteAllLabel = L10N.getStr("breakpointMenuItem.deleteAll2.label");
|
||||
const deleteOthersLabel = L10N.getStr("breakpointMenuItem.deleteOthers2.label");
|
||||
const enableSelfLabel = L10N.getStr("breakpointMenuItem.enableSelf2.label");
|
||||
const enableAllLabel = L10N.getStr("breakpointMenuItem.enableAll2.label");
|
||||
const enableOthersLabel = L10N.getStr("breakpointMenuItem.enableOthers2.label");
|
||||
const disableSelfLabel = L10N.getStr("breakpointMenuItem.disableSelf2.label");
|
||||
const disableAllLabel = L10N.getStr("breakpointMenuItem.disableAll2.label");
|
||||
const disableOthersLabel = L10N.getStr("breakpointMenuItem.disableOthers2.label");
|
||||
const removeConditionLabel = L10N.getStr("breakpointMenuItem.removeCondition2.label");
|
||||
const addConditionLabel = L10N.getStr("breakpointMenuItem.addCondition2.label");
|
||||
const editConditionLabel = L10N.getStr("breakpointMenuItem.editCondition2.label");
|
||||
const deleteSelfKey = L10N.getStr("breakpointMenuItem.deleteSelf2.accesskey");
|
||||
const deleteAllKey = L10N.getStr("breakpointMenuItem.deleteAll2.accesskey");
|
||||
const deleteOthersKey = L10N.getStr("breakpointMenuItem.deleteOthers2.accesskey");
|
||||
const enableSelfKey = L10N.getStr("breakpointMenuItem.enableSelf2.accesskey");
|
||||
const enableAllKey = L10N.getStr("breakpointMenuItem.enableAll2.accesskey");
|
||||
const enableOthersKey = L10N.getStr("breakpointMenuItem.enableOthers2.accesskey");
|
||||
const disableSelfKey = L10N.getStr("breakpointMenuItem.disableSelf2.accesskey");
|
||||
const disableAllKey = L10N.getStr("breakpointMenuItem.disableAll2.accesskey");
|
||||
const disableOthersKey = L10N.getStr("breakpointMenuItem.disableOthers2.accesskey");
|
||||
const removeConditionKey = L10N.getStr("breakpointMenuItem.removeCondition2.accesskey");
|
||||
const editConditionKey = L10N.getStr("breakpointMenuItem.editCondition2.accesskey");
|
||||
const addConditionKey = L10N.getStr("breakpointMenuItem.addCondition2.accesskey");
|
||||
const otherBreakpoints = breakpoints.filter(b => b !== breakpoint);
|
||||
const enabledBreakpoints = breakpoints.filter(b => !b.disabled);
|
||||
const disabledBreakpoints = breakpoints.filter(b => b.disabled);
|
||||
const otherEnabledBreakpoints = breakpoints.filter(b => !b.disabled && b !== breakpoint);
|
||||
const otherDisabledBreakpoints = breakpoints.filter(b => b.disabled && b !== breakpoint);
|
||||
const deleteSelfItem = {
|
||||
id: "node-menu-delete-self",
|
||||
label: deleteSelfLabel,
|
||||
accesskey: deleteSelfKey,
|
||||
disabled: false,
|
||||
click: () => removeBreakpoint(breakpoint.location)
|
||||
};
|
||||
const deleteAllItem = {
|
||||
id: "node-menu-delete-all",
|
||||
label: deleteAllLabel,
|
||||
accesskey: deleteAllKey,
|
||||
disabled: false,
|
||||
click: () => removeAllBreakpoints()
|
||||
};
|
||||
const deleteOthersItem = {
|
||||
id: "node-menu-delete-other",
|
||||
label: deleteOthersLabel,
|
||||
accesskey: deleteOthersKey,
|
||||
disabled: false,
|
||||
click: () => removeBreakpoints(otherBreakpoints)
|
||||
};
|
||||
const enableSelfItem = {
|
||||
id: "node-menu-enable-self",
|
||||
label: enableSelfLabel,
|
||||
accesskey: enableSelfKey,
|
||||
disabled: false,
|
||||
click: () => toggleDisabledBreakpoint(breakpoint.location.line)
|
||||
};
|
||||
const enableAllItem = {
|
||||
id: "node-menu-enable-all",
|
||||
label: enableAllLabel,
|
||||
accesskey: enableAllKey,
|
||||
disabled: false,
|
||||
click: () => toggleAllBreakpoints(false)
|
||||
};
|
||||
const enableOthersItem = {
|
||||
id: "node-menu-enable-others",
|
||||
label: enableOthersLabel,
|
||||
accesskey: enableOthersKey,
|
||||
disabled: false,
|
||||
click: () => toggleBreakpoints(false, otherDisabledBreakpoints)
|
||||
};
|
||||
const disableSelfItem = {
|
||||
id: "node-menu-disable-self",
|
||||
label: disableSelfLabel,
|
||||
accesskey: disableSelfKey,
|
||||
disabled: false,
|
||||
click: () => toggleDisabledBreakpoint(breakpoint.location.line)
|
||||
};
|
||||
const disableAllItem = {
|
||||
id: "node-menu-disable-all",
|
||||
label: disableAllLabel,
|
||||
accesskey: disableAllKey,
|
||||
disabled: false,
|
||||
click: () => toggleAllBreakpoints(true)
|
||||
};
|
||||
const disableOthersItem = {
|
||||
id: "node-menu-disable-others",
|
||||
label: disableOthersLabel,
|
||||
accesskey: disableOthersKey,
|
||||
click: () => toggleBreakpoints(true, otherEnabledBreakpoints)
|
||||
};
|
||||
const removeConditionItem = {
|
||||
id: "node-menu-remove-condition",
|
||||
label: removeConditionLabel,
|
||||
accesskey: removeConditionKey,
|
||||
disabled: false,
|
||||
click: () => setBreakpointCondition(breakpoint.location)
|
||||
};
|
||||
const addConditionItem = {
|
||||
id: "node-menu-add-condition",
|
||||
label: addConditionLabel,
|
||||
accesskey: addConditionKey,
|
||||
click: () => {
|
||||
selectLocation(breakpoint.location);
|
||||
openConditionalPanel(breakpoint.location.line);
|
||||
}
|
||||
};
|
||||
const editConditionItem = {
|
||||
id: "node-menu-edit-condition",
|
||||
label: editConditionLabel,
|
||||
accesskey: editConditionKey,
|
||||
click: () => {
|
||||
selectLocation(breakpoint.location);
|
||||
openConditionalPanel(breakpoint.location.line);
|
||||
}
|
||||
};
|
||||
const hideEnableSelfItem = !breakpoint.disabled;
|
||||
const hideEnableAllItem = disabledBreakpoints.size === 0;
|
||||
const hideEnableOthersItem = otherDisabledBreakpoints.size === 0;
|
||||
const hideDisableAllItem = enabledBreakpoints.size === 0;
|
||||
const hideDisableOthersItem = otherEnabledBreakpoints.size === 0;
|
||||
const hideDisableSelfItem = breakpoint.disabled;
|
||||
const items = [{
|
||||
item: enableSelfItem,
|
||||
hidden: () => hideEnableSelfItem
|
||||
}, {
|
||||
item: enableAllItem,
|
||||
hidden: () => hideEnableAllItem
|
||||
}, {
|
||||
item: enableOthersItem,
|
||||
hidden: () => hideEnableOthersItem
|
||||
}, {
|
||||
item: {
|
||||
type: "separator"
|
||||
},
|
||||
hidden: () => hideEnableSelfItem && hideEnableAllItem && hideEnableOthersItem
|
||||
}, {
|
||||
item: deleteSelfItem
|
||||
}, {
|
||||
item: deleteAllItem
|
||||
}, {
|
||||
item: deleteOthersItem,
|
||||
hidden: () => breakpoints.size === 1
|
||||
}, {
|
||||
item: {
|
||||
type: "separator"
|
||||
},
|
||||
hidden: () => hideDisableSelfItem && hideDisableAllItem && hideDisableOthersItem
|
||||
}, {
|
||||
item: disableSelfItem,
|
||||
hidden: () => hideDisableSelfItem
|
||||
}, {
|
||||
item: disableAllItem,
|
||||
hidden: () => hideDisableAllItem
|
||||
}, {
|
||||
item: disableOthersItem,
|
||||
hidden: () => hideDisableOthersItem
|
||||
}, {
|
||||
item: {
|
||||
type: "separator"
|
||||
}
|
||||
}, {
|
||||
item: addConditionItem,
|
||||
hidden: () => breakpoint.condition
|
||||
}, {
|
||||
item: editConditionItem,
|
||||
hidden: () => !breakpoint.condition
|
||||
}, {
|
||||
item: removeConditionItem,
|
||||
hidden: () => !breakpoint.condition
|
||||
}];
|
||||
(0, _devtoolsContextmenu.showMenu)(contextMenuEvent, (0, _devtoolsContextmenu.buildMenu)(items));
|
||||
}
|
|
@ -0,0 +1,105 @@
|
|||
"use strict";
|
||||
|
||||
Object.defineProperty(exports, "__esModule", {
|
||||
value: true
|
||||
});
|
||||
|
||||
var _react = require("devtools/client/shared/vendor/react");
|
||||
|
||||
var _react2 = _interopRequireDefault(_react);
|
||||
|
||||
var _classnames = require("devtools/client/debugger/new/dist/vendors").vendored["classnames"];
|
||||
|
||||
var _classnames2 = _interopRequireDefault(_classnames);
|
||||
|
||||
var _reactRedux = require("devtools/client/shared/vendor/react-redux");
|
||||
|
||||
var _Breakpoint = require("./Breakpoint");
|
||||
|
||||
var _Breakpoint2 = _interopRequireDefault(_Breakpoint);
|
||||
|
||||
var _SourceIcon = require("../../shared/SourceIcon");
|
||||
|
||||
var _SourceIcon2 = _interopRequireDefault(_SourceIcon);
|
||||
|
||||
var _actions = require("../../../actions/index");
|
||||
|
||||
var _actions2 = _interopRequireDefault(_actions);
|
||||
|
||||
var _source = require("../../../utils/source");
|
||||
|
||||
var _breakpoint = require("../../../utils/breakpoint/index");
|
||||
|
||||
var _selectors = require("../../../selectors/index");
|
||||
|
||||
function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
|
||||
|
||||
/* This Source Code Form is subject to the terms of the Mozilla Public
|
||||
* License, v. 2.0. If a copy of the MPL was not distributed with this
|
||||
* file, You can obtain one at <http://mozilla.org/MPL/2.0/>. */
|
||||
function createExceptionOption(label, value, onChange, className) {
|
||||
return _react2.default.createElement("div", {
|
||||
className: className,
|
||||
onClick: onChange
|
||||
}, _react2.default.createElement("input", {
|
||||
type: "checkbox",
|
||||
checked: value ? "checked" : "",
|
||||
onChange: e => e.stopPropagation() && onChange()
|
||||
}), _react2.default.createElement("div", {
|
||||
className: "breakpoint-exceptions-label"
|
||||
}, label));
|
||||
}
|
||||
|
||||
class Breakpoints extends _react.Component {
|
||||
renderExceptionsOptions() {
|
||||
const {
|
||||
breakpointSources,
|
||||
shouldPauseOnExceptions,
|
||||
shouldPauseOnCaughtExceptions,
|
||||
pauseOnExceptions
|
||||
} = this.props;
|
||||
const isEmpty = breakpointSources.length == 0;
|
||||
const exceptionsBox = createExceptionOption(L10N.getStr("pauseOnExceptionsItem2"), shouldPauseOnExceptions, () => pauseOnExceptions(!shouldPauseOnExceptions, false), "breakpoints-exceptions");
|
||||
const ignoreCaughtBox = createExceptionOption(L10N.getStr("pauseOnCaughtExceptionsItem"), shouldPauseOnCaughtExceptions, () => pauseOnExceptions(true, !shouldPauseOnCaughtExceptions), "breakpoints-exceptions-caught");
|
||||
return _react2.default.createElement("div", {
|
||||
className: (0, _classnames2.default)("breakpoints-exceptions-options", {
|
||||
empty: isEmpty
|
||||
})
|
||||
}, exceptionsBox, shouldPauseOnExceptions ? ignoreCaughtBox : null);
|
||||
}
|
||||
|
||||
renderBreakpoints() {
|
||||
const {
|
||||
breakpointSources
|
||||
} = this.props;
|
||||
return [...breakpointSources.map(({
|
||||
source,
|
||||
breakpoints
|
||||
}) => [_react2.default.createElement("div", {
|
||||
className: "breakpoint-heading",
|
||||
title: source.url,
|
||||
key: source.url,
|
||||
onClick: () => this.props.selectSource(source.id)
|
||||
}, _react2.default.createElement(_SourceIcon2.default, {
|
||||
source: source
|
||||
}), (0, _source.getFilename)(source)), ...breakpoints.map(breakpoint => _react2.default.createElement(_Breakpoint2.default, {
|
||||
breakpoint: breakpoint,
|
||||
source: source,
|
||||
key: (0, _breakpoint.makeLocationId)(breakpoint.location)
|
||||
}))])];
|
||||
}
|
||||
|
||||
render() {
|
||||
return _react2.default.createElement("div", {
|
||||
className: "pane breakpoints-list"
|
||||
}, this.renderExceptionsOptions(), this.renderBreakpoints());
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
const mapStateToProps = state => ({
|
||||
breakpointSources: (0, _selectors.getBreakpointSources)(state),
|
||||
selectedSource: (0, _selectors.getSelectedSource)(state)
|
||||
});
|
||||
|
||||
exports.default = (0, _reactRedux.connect)(mapStateToProps, _actions2.default)(Breakpoints);
|
|
@ -0,0 +1,14 @@
|
|||
# vim: set filetype=python:
|
||||
# This Source Code Form is subject to the terms of the Mozilla Public
|
||||
# License, v. 2.0. If a copy of the MPL was not distributed with this
|
||||
# file, You can obtain one at http://mozilla.org/MPL/2.0/.
|
||||
|
||||
DIRS += [
|
||||
|
||||
]
|
||||
|
||||
DevToolsModules(
|
||||
'Breakpoint.js',
|
||||
'BreakpointsContextMenu.js',
|
||||
'index.js',
|
||||
)
|
|
@ -162,17 +162,17 @@ function isSymbolsLoading(state, source) {
|
|||
return symbols.hasOwnProperty("loading");
|
||||
}
|
||||
|
||||
function isEmptyLineInSource(state, line, selectedSource) {
|
||||
const emptyLines = getEmptyLines(state, selectedSource);
|
||||
function isEmptyLineInSource(state, line, selectedSourceId) {
|
||||
const emptyLines = getEmptyLines(state, selectedSourceId);
|
||||
return emptyLines && emptyLines.includes(line);
|
||||
}
|
||||
|
||||
function getEmptyLines(state, source) {
|
||||
if (!source) {
|
||||
function getEmptyLines(state, sourceId) {
|
||||
if (!sourceId) {
|
||||
return null;
|
||||
}
|
||||
|
||||
return state.ast.emptyLines.get(source.id);
|
||||
return state.ast.emptyLines.get(sourceId);
|
||||
}
|
||||
|
||||
function getPausePoints(state, sourceId) {
|
||||
|
|
|
@ -0,0 +1,37 @@
|
|||
"use strict";
|
||||
|
||||
Object.defineProperty(exports, "__esModule", {
|
||||
value: true
|
||||
});
|
||||
exports.getBreakpointSources = undefined;
|
||||
|
||||
var _lodash = require("devtools/client/shared/vendor/lodash");
|
||||
|
||||
var _reselect = require("devtools/client/debugger/new/dist/vendors").vendored["reselect"];
|
||||
|
||||
var _selectors = require("../selectors/index");
|
||||
|
||||
var _source = require("../utils/source");
|
||||
|
||||
/* This Source Code Form is subject to the terms of the Mozilla Public
|
||||
* License, v. 2.0. If a copy of the MPL was not distributed with this
|
||||
* file, You can obtain one at <http://mozilla.org/MPL/2.0/>. */
|
||||
function getBreakpointsForSource(source, breakpoints) {
|
||||
return breakpoints.valueSeq().filter(bp => bp.location.sourceId == source.id && !bp.hidden && (bp.text || bp.condition)).sortBy(bp => bp.location.line).toJS();
|
||||
}
|
||||
|
||||
function findBreakpointSources(sources, breakpoints) {
|
||||
const sourceIds = (0, _lodash.uniq)(breakpoints.valueSeq().filter(bp => !bp.hidden).map(bp => bp.location.sourceId).toJS());
|
||||
const breakpointSources = sourceIds.map(id => (0, _selectors.getSourceInSources)(sources, id)).filter(source => source && !source.isBlackBoxed);
|
||||
return (0, _lodash.sortBy)(breakpointSources, source => (0, _source.getFilenameFromURL)(source.url));
|
||||
}
|
||||
|
||||
function _getBreakpointSources(breakpoints, sources, selectedSource) {
|
||||
const breakpointSources = findBreakpointSources(sources, breakpoints);
|
||||
return breakpointSources.map(source => ({
|
||||
source,
|
||||
breakpoints: getBreakpointsForSource(source, breakpoints)
|
||||
}));
|
||||
}
|
||||
|
||||
const getBreakpointSources = exports.getBreakpointSources = (0, _reselect.createSelector)(_selectors.getBreakpoints, _selectors.getSources, _getBreakpointSources);
|
|
@ -251,4 +251,13 @@ Object.defineProperty(exports, "getRelativeSources", {
|
|||
get: function () {
|
||||
return _getRelativeSources.getRelativeSources;
|
||||
}
|
||||
});
|
||||
|
||||
var _mappedBreakpoints = require("./mappedBreakpoints");
|
||||
|
||||
Object.defineProperty(exports, "getMappedBreakpoints", {
|
||||
enumerable: true,
|
||||
get: function () {
|
||||
return _mappedBreakpoints.getMappedBreakpoints;
|
||||
}
|
||||
});
|
|
@ -0,0 +1,57 @@
|
|||
"use strict";
|
||||
|
||||
Object.defineProperty(exports, "__esModule", {
|
||||
value: true
|
||||
});
|
||||
exports.getMappedBreakpoints = undefined;
|
||||
|
||||
var _breakpoint = require("../utils/breakpoint/index");
|
||||
|
||||
var _immutable = require("devtools/client/shared/vendor/immutable");
|
||||
|
||||
var _immutable2 = _interopRequireDefault(_immutable);
|
||||
|
||||
var _selectors = require("../selectors/index");
|
||||
|
||||
var _devtoolsSourceMap = require("devtools/client/shared/source-map/index.js");
|
||||
|
||||
var _reselect = require("devtools/client/debugger/new/dist/vendors").vendored["reselect"];
|
||||
|
||||
function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
|
||||
|
||||
/* This Source Code Form is subject to the terms of the Mozilla Public
|
||||
* License, v. 2.0. If a copy of the MPL was not distributed with this
|
||||
* file, You can obtain one at <http://mozilla.org/MPL/2.0/>. */
|
||||
function formatBreakpoint(sources, selectedSource, breakpoint) {
|
||||
let location = breakpoint.location;
|
||||
let text = breakpoint.originalText;
|
||||
const condition = breakpoint.condition;
|
||||
const disabled = breakpoint.disabled;
|
||||
const locationId = (0, _breakpoint.makeLocationId)(location);
|
||||
const source = (0, _selectors.getSourceInSources)(sources, location.sourceId);
|
||||
|
||||
if ((0, _devtoolsSourceMap.isGeneratedId)(selectedSource.id)) {
|
||||
location = breakpoint.generatedLocation || breakpoint.location;
|
||||
text = breakpoint.text;
|
||||
}
|
||||
|
||||
const localBP = {
|
||||
locationId,
|
||||
location,
|
||||
text,
|
||||
source,
|
||||
condition,
|
||||
disabled
|
||||
};
|
||||
return localBP;
|
||||
}
|
||||
|
||||
function _getMappedBreakpoints(breakpoints, sources, selectedSource) {
|
||||
if (!selectedSource) {
|
||||
return _immutable2.default.Map();
|
||||
}
|
||||
|
||||
return breakpoints.map(bp => formatBreakpoint(sources, selectedSource, bp)).filter(bp => bp.source && !bp.source.isBlackBoxed);
|
||||
}
|
||||
|
||||
const getMappedBreakpoints = exports.getMappedBreakpoints = (0, _reselect.createSelector)(_selectors.getBreakpoints, _selectors.getSources, _selectors.getSelectedSource, _selectors.getTopFrame, _selectors.getPauseReason, _getMappedBreakpoints);
|
|
@ -14,6 +14,7 @@ DevToolsModules(
|
|||
'inComponent.js',
|
||||
'index.js',
|
||||
'isSelectedFrameVisible.js',
|
||||
'mappedBreakpoints.js',
|
||||
'visibleBreakpoints.js',
|
||||
'visibleSelectedFrame.js',
|
||||
)
|
||||
|
|
|
@ -31,6 +31,7 @@ Object.defineProperty(exports, "findScopeByName", {
|
|||
exports.firstString = firstString;
|
||||
exports.locationMoved = locationMoved;
|
||||
exports.makeLocationId = makeLocationId;
|
||||
exports.getLocationWithoutColumn = getLocationWithoutColumn;
|
||||
exports.makePendingLocationId = makePendingLocationId;
|
||||
exports.assertBreakpoint = assertBreakpoint;
|
||||
exports.assertPendingBreakpoint = assertPendingBreakpoint;
|
||||
|
@ -77,6 +78,14 @@ function makeLocationId(location) {
|
|||
return `${sourceId}:${line}:${columnString}`;
|
||||
}
|
||||
|
||||
function getLocationWithoutColumn(location) {
|
||||
const {
|
||||
sourceId,
|
||||
line
|
||||
} = location;
|
||||
return `${sourceId}:${line}`;
|
||||
}
|
||||
|
||||
function makePendingLocationId(location) {
|
||||
assertPendingLocation(location);
|
||||
const {
|
||||
|
|
|
@ -9,6 +9,8 @@ var _parser = require("../../../workers/parser/index");
|
|||
|
||||
var _locColumn = require("./locColumn");
|
||||
|
||||
var _rangeMetadata = require("./rangeMetadata");
|
||||
|
||||
var _findGeneratedBindingFromPosition = require("./findGeneratedBindingFromPosition");
|
||||
|
||||
var _buildGeneratedBindingList = require("./buildGeneratedBindingList");
|
||||
|
@ -30,10 +32,11 @@ async function buildMappedScopes(source, frame, scopes, sourceMaps, client) {
|
|||
}
|
||||
|
||||
const generatedAstBindings = (0, _buildGeneratedBindingList.buildGeneratedBindingList)(scopes, generatedAstScopes, frame.this);
|
||||
const originalRanges = await (0, _rangeMetadata.loadRangeMetadata)(source, frame, originalAstScopes, sourceMaps);
|
||||
const {
|
||||
mappedOriginalScopes,
|
||||
expressionLookup
|
||||
} = await mapOriginalBindingsToGenerated(source, originalAstScopes, generatedAstBindings, client, sourceMaps);
|
||||
} = await mapOriginalBindingsToGenerated(source, originalRanges, originalAstScopes, generatedAstBindings, client, sourceMaps);
|
||||
const mappedGeneratedScopes = generateClientScope(scopes, mappedOriginalScopes);
|
||||
return isReliableScope(mappedGeneratedScopes) ? {
|
||||
mappings: expressionLookup,
|
||||
|
@ -41,7 +44,7 @@ async function buildMappedScopes(source, frame, scopes, sourceMaps, client) {
|
|||
} : null;
|
||||
}
|
||||
|
||||
async function mapOriginalBindingsToGenerated(source, originalAstScopes, generatedAstBindings, client, sourceMaps) {
|
||||
async function mapOriginalBindingsToGenerated(source, originalRanges, originalAstScopes, generatedAstBindings, client, sourceMaps) {
|
||||
const expressionLookup = {};
|
||||
const mappedOriginalScopes = [];
|
||||
const cachedSourceMaps = batchScopeMappings(originalAstScopes, source, sourceMaps);
|
||||
|
@ -51,7 +54,7 @@ async function mapOriginalBindingsToGenerated(source, originalAstScopes, generat
|
|||
|
||||
for (const name of Object.keys(item.bindings)) {
|
||||
const binding = item.bindings[name];
|
||||
const result = await findGeneratedBinding(cachedSourceMaps, client, source, name, binding, generatedAstBindings);
|
||||
const result = await findGeneratedBinding(cachedSourceMaps, client, source, name, binding, originalRanges, generatedAstBindings);
|
||||
|
||||
if (result) {
|
||||
generatedBindings[name] = result.grip;
|
||||
|
@ -213,7 +216,14 @@ function generateClientScope(scopes, originalScopes) {
|
|||
return result;
|
||||
}
|
||||
|
||||
async function findGeneratedBinding(sourceMaps, client, source, name, originalBinding, generatedAstBindings) {
|
||||
function hasValidIdent(range, pos) {
|
||||
return range.type === "match" || // For declarations, we allow the range on the identifier to be a
|
||||
// more general "contains" to increase the chances of a match.
|
||||
pos.type !== "ref" && range.type === "contains";
|
||||
} // eslint-disable-next-line complexity
|
||||
|
||||
|
||||
async function findGeneratedBinding(sourceMaps, client, source, name, originalBinding, originalRanges, generatedAstBindings) {
|
||||
// If there are no references to the implicits, then we have no way to
|
||||
// even attempt to map it back to the original since there is no location
|
||||
// data to use. Bail out instead of just showing it as unmapped.
|
||||
|
@ -227,27 +237,43 @@ async function findGeneratedBinding(sourceMaps, client, source, name, originalBi
|
|||
let genContent = null;
|
||||
|
||||
for (const pos of refs) {
|
||||
if (originalBinding.type === "import") {
|
||||
genContent = await (0, _findGeneratedBindingFromPosition.findGeneratedBindingForImportBinding)(sourceMaps, client, source, pos, name, originalBinding.type, generatedAstBindings);
|
||||
} else {
|
||||
genContent = await (0, _findGeneratedBindingFromPosition.findGeneratedBindingForStandardBinding)(sourceMaps, client, source, pos, name, originalBinding.type, generatedAstBindings);
|
||||
const range = (0, _rangeMetadata.findMatchingRange)(originalRanges, pos);
|
||||
|
||||
if (range && hasValidIdent(range, pos)) {
|
||||
if (originalBinding.type === "import") {
|
||||
genContent = await (0, _findGeneratedBindingFromPosition.findGeneratedBindingForImportBinding)(sourceMaps, client, source, pos, name, originalBinding.type, generatedAstBindings);
|
||||
} else {
|
||||
genContent = await (0, _findGeneratedBindingFromPosition.findGeneratedBindingForStandardBinding)(sourceMaps, client, source, pos, name, originalBinding.type, generatedAstBindings);
|
||||
}
|
||||
}
|
||||
|
||||
if ((pos.type === "class-decl" || pos.type === "class-inner") && source.contentType && source.contentType.match(/\/typescript/)) {
|
||||
// Resolve to first binding in the range
|
||||
const declContent = await (0, _findGeneratedBindingFromPosition.findGeneratedBindingForNormalDeclaration)(sourceMaps, client, source, pos, name, originalBinding.type, generatedAstBindings);
|
||||
const declRange = (0, _rangeMetadata.findMatchingRange)(originalRanges, pos.declaration);
|
||||
|
||||
if (declContent) {
|
||||
// Prefer the declaration mapping in this case because TS sometimes
|
||||
// maps class declaration names to "export.Foo = Foo;" or to
|
||||
// the decorator logic itself
|
||||
genContent = declContent;
|
||||
if (declRange && declRange.type !== "multiple") {
|
||||
// Resolve to first binding in the range
|
||||
const declContent = await (0, _findGeneratedBindingFromPosition.findGeneratedBindingForNormalDeclaration)(sourceMaps, client, source, pos, name, originalBinding.type, generatedAstBindings);
|
||||
|
||||
if (declContent) {
|
||||
// Prefer the declaration mapping in this case because TS sometimes
|
||||
// maps class declaration names to "export.Foo = Foo;" or to
|
||||
// the decorator logic itself
|
||||
genContent = declContent;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (!genContent && (pos.type === "import-decl" || pos.type === "import-ns-decl")) {
|
||||
// match the import declaration location
|
||||
genContent = await (0, _findGeneratedBindingFromPosition.findGeneratedBindingForImportDeclaration)(sourceMaps, client, source, pos, name, originalBinding.type, generatedAstBindings);
|
||||
const declRange = (0, _rangeMetadata.findMatchingRange)(originalRanges, pos.declaration); // The import declaration should have an original position mapping,
|
||||
// but otherwise we don't really have preferences on the range type
|
||||
// because it can have multiple bindings, but we do want to make sure
|
||||
// that all of the bindings that match the range are part of the same
|
||||
// import declaration.
|
||||
|
||||
if (declRange && declRange.singleDeclaration) {
|
||||
// match the import declaration location
|
||||
genContent = await (0, _findGeneratedBindingFromPosition.findGeneratedBindingForImportDeclaration)(sourceMaps, client, source, pos, name, originalBinding.type, generatedAstBindings);
|
||||
}
|
||||
}
|
||||
|
||||
if (genContent) {
|
||||
|
|
|
@ -16,4 +16,5 @@ DevToolsModules(
|
|||
'locColumn.js',
|
||||
'mappingContains.js',
|
||||
'positionCmp.js',
|
||||
'rangeMetadata.js',
|
||||
)
|
||||
|
|
|
@ -0,0 +1,92 @@
|
|||
"use strict";
|
||||
|
||||
Object.defineProperty(exports, "__esModule", {
|
||||
value: true
|
||||
});
|
||||
exports.loadRangeMetadata = loadRangeMetadata;
|
||||
exports.findMatchingRange = findMatchingRange;
|
||||
|
||||
var _locColumn = require("./locColumn");
|
||||
|
||||
var _positionCmp = require("./positionCmp");
|
||||
|
||||
var _filtering = require("./filtering");
|
||||
|
||||
function _objectSpread(target) { for (var i = 1; i < arguments.length; i++) { var source = arguments[i] != null ? arguments[i] : {}; var ownKeys = Object.keys(source); if (typeof Object.getOwnPropertySymbols === 'function') { ownKeys = ownKeys.concat(Object.getOwnPropertySymbols(source).filter(function (sym) { return Object.getOwnPropertyDescriptor(source, sym).enumerable; })); } ownKeys.forEach(function (key) { _defineProperty(target, key, source[key]); }); } return target; }
|
||||
|
||||
function _defineProperty(obj, key, value) { if (key in obj) { Object.defineProperty(obj, key, { value: value, enumerable: true, configurable: true, writable: true }); } else { obj[key] = value; } return obj; }
|
||||
|
||||
async function loadRangeMetadata(source, frame, originalAstScopes, sourceMaps) {
|
||||
const originalRanges = await sourceMaps.getOriginalRanges(frame.location.sourceId, source.url);
|
||||
const sortedOriginalAstBindings = [];
|
||||
|
||||
for (const item of originalAstScopes) {
|
||||
for (const name of Object.keys(item.bindings)) {
|
||||
for (const ref of item.bindings[name].refs) {
|
||||
sortedOriginalAstBindings.push(ref);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
sortedOriginalAstBindings.sort((a, b) => (0, _positionCmp.positionCmp)(a.start, b.start));
|
||||
let i = 0;
|
||||
return originalRanges.map(range => {
|
||||
const bindings = [];
|
||||
|
||||
while (i < sortedOriginalAstBindings.length && (sortedOriginalAstBindings[i].start.line < range.line || sortedOriginalAstBindings[i].start.line === range.line && (0, _locColumn.locColumn)(sortedOriginalAstBindings[i].start) < range.columnStart)) {
|
||||
i++;
|
||||
}
|
||||
|
||||
while (i < sortedOriginalAstBindings.length && sortedOriginalAstBindings[i].start.line === range.line && (0, _locColumn.locColumn)(sortedOriginalAstBindings[i].start) >= range.columnStart && (0, _locColumn.locColumn)(sortedOriginalAstBindings[i].start) < range.columnEnd) {
|
||||
bindings.push(sortedOriginalAstBindings[i]);
|
||||
i++;
|
||||
}
|
||||
|
||||
let type = "empty";
|
||||
let singleDeclaration = true;
|
||||
|
||||
if (bindings.length === 1) {
|
||||
const binding = bindings[0];
|
||||
|
||||
if (binding.start.line === range.line && binding.start.column === range.columnStart) {
|
||||
type = "match";
|
||||
} else {
|
||||
type = "contains";
|
||||
}
|
||||
} else if (bindings.length > 1) {
|
||||
type = "multiple";
|
||||
const binding = bindings[0];
|
||||
const declStart = binding.type !== "ref" ? binding.declaration.start : null;
|
||||
singleDeclaration = bindings.every(b => {
|
||||
return declStart && b.type !== "ref" && (0, _positionCmp.positionCmp)(declStart, b.declaration.start) === 0;
|
||||
});
|
||||
}
|
||||
|
||||
return _objectSpread({
|
||||
type,
|
||||
singleDeclaration
|
||||
}, range);
|
||||
});
|
||||
}
|
||||
|
||||
function findMatchingRange(sortedOriginalRanges, bindingRange) {
|
||||
return (0, _filtering.filterSortedArray)(sortedOriginalRanges, range => {
|
||||
if (range.line < bindingRange.start.line) {
|
||||
return -1;
|
||||
}
|
||||
|
||||
if (range.line > bindingRange.start.line) {
|
||||
return 1;
|
||||
}
|
||||
|
||||
if (range.columnEnd <= (0, _locColumn.locColumn)(bindingRange.start)) {
|
||||
return -1;
|
||||
}
|
||||
|
||||
if (range.columnStart > (0, _locColumn.locColumn)(bindingRange.start)) {
|
||||
return 1;
|
||||
}
|
||||
|
||||
return 0;
|
||||
}).pop();
|
||||
}
|
|
@ -466,5 +466,5 @@ function getSourceClassnames(source, sourceMetaData) {
|
|||
return "blackBox";
|
||||
}
|
||||
|
||||
return sourceTypes[(0, _sourcesTree.getExtension)(source)] || defaultClassName;
|
||||
return sourceTypes[(0, _sourcesTree.getExtension)(source.url)] || defaultClassName;
|
||||
}
|
|
@ -47,8 +47,7 @@ function isDirectory(url) {
|
|||
return (parts.length === 0 || url.path.slice(-1) === "/" || nodeHasChildren(url)) && url.name != "(index)";
|
||||
}
|
||||
|
||||
function getExtension(source) {
|
||||
const url = source.get ? source.get("url") : source.url;
|
||||
function getExtension(url = "") {
|
||||
const parsedUrl = (0, _url.parse)(url).pathname;
|
||||
|
||||
if (!parsedUrl) {
|
||||
|
@ -59,7 +58,7 @@ function getExtension(source) {
|
|||
}
|
||||
|
||||
function isNotJavaScript(source) {
|
||||
return ["css", "svg", "png"].includes(getExtension(source));
|
||||
return ["css", "svg", "png"].includes(getExtension(source.url));
|
||||
}
|
||||
|
||||
function isInvalidUrl(url, source) {
|
||||
|
|
|
@ -3,7 +3,7 @@
|
|||
Object.defineProperty(exports, "__esModule", {
|
||||
value: true
|
||||
});
|
||||
exports.formatKeyShortcut = undefined;
|
||||
exports.truncateMiddleText = exports.formatKeyShortcut = undefined;
|
||||
|
||||
var _devtoolsModules = require("devtools/client/debugger/new/dist/vendors").vendored["devtools-modules"];
|
||||
|
||||
|
@ -40,5 +40,26 @@ function formatKeyShortcut(shortcut) {
|
|||
|
||||
return shortcut.replace(/CommandOrControl\+|CmdOrCtrl\+/g, `${L10N.getStr("ctrl")} `).replace(/Shift\+/g, "Shift ");
|
||||
}
|
||||
/**
|
||||
* Truncates the received text to the maxLength in the format:
|
||||
* Original: 'this is a very long text and ends here'
|
||||
* Truncated: 'this is a ver...and ends here'
|
||||
* @param {String} sourceText - Source text
|
||||
* @param {Number} maxLength - Max allowed length
|
||||
* @memberof utils/text
|
||||
* @static
|
||||
*/
|
||||
|
||||
exports.formatKeyShortcut = formatKeyShortcut;
|
||||
|
||||
function truncateMiddleText(sourceText, maxLength) {
|
||||
let truncatedText = sourceText;
|
||||
|
||||
if (sourceText.length > maxLength) {
|
||||
truncatedText = `${sourceText.substring(0, Math.round(maxLength / 2) - 2)}...${sourceText.substring(sourceText.length - Math.round(maxLength / 2 - 1))}`;
|
||||
}
|
||||
|
||||
return truncatedText;
|
||||
}
|
||||
|
||||
exports.formatKeyShortcut = formatKeyShortcut;
|
||||
exports.truncateMiddleText = truncateMiddleText;
|
|
@ -89,7 +89,7 @@ function toParsedScopes(children, sourceId) {
|
|||
return {
|
||||
start: scope.loc.start,
|
||||
end: scope.loc.end,
|
||||
type: scope.type === "module" ? "block" : scope.type,
|
||||
type: scope.type === "module" || scope.type === "function-body" ? "block" : scope.type,
|
||||
displayName: scope.displayName,
|
||||
bindings: scope.bindings,
|
||||
children: toParsedScopes(scope.children, sourceId)
|
||||
|
@ -190,10 +190,20 @@ function isLetOrConst(node) {
|
|||
}
|
||||
|
||||
function hasLexicalDeclaration(node, parent) {
|
||||
const nodes = [];
|
||||
|
||||
if (t.isSwitchStatement(node)) {
|
||||
for (const caseNode of node.cases) {
|
||||
nodes.push(...caseNode.consequent);
|
||||
}
|
||||
} else {
|
||||
nodes.push(...node.body);
|
||||
}
|
||||
|
||||
const isFunctionBody = t.isFunction(parent, {
|
||||
body: node
|
||||
});
|
||||
return node.body.some(child => isLexicalVariable(child) || !isFunctionBody && child.type === "FunctionDeclaration" || child.type === "ClassDeclaration");
|
||||
return nodes.some(child => isLexicalVariable(child) || t.isClassDeclaration(child) || !isFunctionBody && t.isFunctionDeclaration(child));
|
||||
}
|
||||
|
||||
function isLexicalVariable(node) {
|
||||
|
@ -257,19 +267,27 @@ const scopeCollectionVisitor = {
|
|||
// This ignores Annex B function declaration hoisting, which
|
||||
// is probably a fine assumption.
|
||||
state.declarationBindingIds.add(node.id);
|
||||
const fnScope = getVarScope(scope);
|
||||
scope.bindings[node.id.name] = {
|
||||
type: fnScope === scope ? "var" : "let",
|
||||
refs: [{
|
||||
type: "fn-decl",
|
||||
start: fromBabelLocation(node.id.loc.start, state.sourceId),
|
||||
end: fromBabelLocation(node.id.loc.end, state.sourceId),
|
||||
declaration: {
|
||||
start: fromBabelLocation(node.loc.start, state.sourceId),
|
||||
end: fromBabelLocation(node.loc.end, state.sourceId)
|
||||
}
|
||||
}]
|
||||
};
|
||||
const refs = [{
|
||||
type: "fn-decl",
|
||||
start: fromBabelLocation(node.id.loc.start, state.sourceId),
|
||||
end: fromBabelLocation(node.id.loc.end, state.sourceId),
|
||||
declaration: {
|
||||
start: fromBabelLocation(node.loc.start, state.sourceId),
|
||||
end: fromBabelLocation(node.loc.end, state.sourceId)
|
||||
}
|
||||
}];
|
||||
|
||||
if (scope.type === "block") {
|
||||
scope.bindings[node.id.name] = {
|
||||
type: "let",
|
||||
refs
|
||||
};
|
||||
} else {
|
||||
getVarScope(scope).bindings[node.id.name] = {
|
||||
type: "var",
|
||||
refs
|
||||
};
|
||||
}
|
||||
}
|
||||
|
||||
scope = pushTempScope(state, "function", (0, _getFunctionName2.default)(node, parentNode), {
|
||||
|
@ -290,6 +308,13 @@ const scopeCollectionVisitor = {
|
|||
refs: []
|
||||
};
|
||||
}
|
||||
|
||||
if (t.isBlockStatement(node.body) && hasLexicalDeclaration(node.body, node)) {
|
||||
scope = pushTempScope(state, "function-body", "Function Body", {
|
||||
start: fromBabelLocation(node.body.loc.start, state.sourceId),
|
||||
end: fromBabelLocation(node.body.loc.end, state.sourceId)
|
||||
});
|
||||
}
|
||||
} else if (t.isClass(node)) {
|
||||
if (t.isIdentifier(node.id)) {
|
||||
// For decorated classes, the AST considers the first the decorator
|
||||
|
@ -359,7 +384,8 @@ const scopeCollectionVisitor = {
|
|||
end: fromBabelLocation(node.loc.end, state.sourceId)
|
||||
});
|
||||
parseDeclarator(node.param, scope, "var", "catch", node, state);
|
||||
} else if (t.isBlockStatement(node) && hasLexicalDeclaration(node, parentNode)) {
|
||||
} else if (t.isBlockStatement(node) && // Function body's are handled in the function logic above.
|
||||
!t.isFunction(parentNode) && hasLexicalDeclaration(node, parentNode)) {
|
||||
// Debugger will create new lexical environment for the block.
|
||||
pushTempScope(state, "block", "Block", {
|
||||
start: fromBabelLocation(node.loc.start, state.sourceId),
|
||||
|
@ -489,7 +515,7 @@ const scopeCollectionVisitor = {
|
|||
type: "implicit",
|
||||
refs: []
|
||||
};
|
||||
} else if (t.isSwitchStatement(node) && node.cases.some(caseNode => caseNode.consequent.some(child => isLexicalVariable(child)))) {
|
||||
} else if (t.isSwitchStatement(node) && hasLexicalDeclaration(node, parentNode)) {
|
||||
pushTempScope(state, "block", "Switch", {
|
||||
start: fromBabelLocation(node.loc.start, state.sourceId),
|
||||
end: fromBabelLocation(node.loc.end, state.sourceId)
|
||||
|
|
|
@ -31,6 +31,8 @@ support-files =
|
|||
examples/sourcemapped/fixtures/babel-for-loops/output.js.map
|
||||
examples/sourcemapped/fixtures/babel-functions/output.js
|
||||
examples/sourcemapped/fixtures/babel-functions/output.js.map
|
||||
examples/sourcemapped/fixtures/babel-lex-and-nonlex/output.js
|
||||
examples/sourcemapped/fixtures/babel-lex-and-nonlex/output.js.map
|
||||
examples/sourcemapped/fixtures/babel-type-module/output.js
|
||||
examples/sourcemapped/fixtures/babel-type-module/output.js.map
|
||||
examples/sourcemapped/fixtures/babel-type-script/output.js
|
||||
|
|
|
@ -25,7 +25,7 @@ add_task(async function() {
|
|||
let onPaused = waitForPaused(dbg);
|
||||
invokeInTab("mutate");
|
||||
await onPaused;
|
||||
await waitForLoadedSource(dbg, "script-mutate");
|
||||
await waitForSelectedSource(dbg, "script-mutate");
|
||||
|
||||
is(
|
||||
getScopeNodeLabel(dbg, 2),
|
||||
|
|
|
@ -46,7 +46,7 @@ add_task(async function() {
|
|||
"Block",
|
||||
["three", "5"],
|
||||
["two", "4"],
|
||||
"Block",
|
||||
"Function Body",
|
||||
["three", "3"],
|
||||
["two", "2"],
|
||||
"root",
|
||||
|
@ -73,7 +73,7 @@ add_task(async function() {
|
|||
["aConst", '"const2"'],
|
||||
["aLet", '"let2"'],
|
||||
"Outer:_Outer()",
|
||||
"Block",
|
||||
"Function Body",
|
||||
["aConst", '"const1"'],
|
||||
["aLet", '"let1"'],
|
||||
"Outer()",
|
||||
|
@ -86,7 +86,7 @@ add_task(async function() {
|
|||
"babel-line-start-bindings-es6",
|
||||
{ line: 19, column: 4 },
|
||||
[
|
||||
"Block",
|
||||
"Function Body",
|
||||
["<this>", "{\u2026}"],
|
||||
["one", "1"],
|
||||
["two", "2"],
|
||||
|
@ -102,7 +102,7 @@ add_task(async function() {
|
|||
"babel-this-arguments-bindings",
|
||||
{ line: 4, column: 4 },
|
||||
[
|
||||
"Block",
|
||||
"Function Body",
|
||||
["<this>", '"this-value"'],
|
||||
["arrow", "undefined"],
|
||||
"fn",
|
||||
|
@ -123,7 +123,7 @@ add_task(async function() {
|
|||
"arrow",
|
||||
["<this>", '"this-value"'],
|
||||
["argArrow", '"arrow-arg"'],
|
||||
"Block",
|
||||
"Function Body",
|
||||
"arrow()",
|
||||
"fn",
|
||||
["arg", '"arg-value"'],
|
||||
|
@ -158,12 +158,12 @@ add_task(async function() {
|
|||
]);
|
||||
|
||||
await breakpointScopes(dbg, "babel-classes", { line: 12, column: 6 }, [
|
||||
"Block",
|
||||
"Function Body",
|
||||
["three", "3"],
|
||||
["two", "2"],
|
||||
"Class",
|
||||
"Another()",
|
||||
"Block",
|
||||
"Function Body",
|
||||
"Another()",
|
||||
["one", "1"],
|
||||
"Thing()",
|
||||
|
@ -174,7 +174,7 @@ add_task(async function() {
|
|||
await breakpointScopes(dbg, "babel-for-loops", { line: 5, column: 4 }, [
|
||||
"For",
|
||||
["i", "1"],
|
||||
"Block",
|
||||
"Function Body",
|
||||
["i", "0"],
|
||||
"Module",
|
||||
"root()"
|
||||
|
@ -183,7 +183,7 @@ add_task(async function() {
|
|||
await breakpointScopes(dbg, "babel-for-loops", { line: 9, column: 4 }, [
|
||||
"For",
|
||||
["i", '"2"'],
|
||||
"Block",
|
||||
"Function Body",
|
||||
["i", "0"],
|
||||
"Module",
|
||||
"root()"
|
||||
|
@ -192,7 +192,7 @@ add_task(async function() {
|
|||
await breakpointScopes(dbg, "babel-for-loops", { line: 13, column: 4 }, [
|
||||
"For",
|
||||
["i", "3"],
|
||||
"Block",
|
||||
"Function Body",
|
||||
["i", "0"],
|
||||
"Module",
|
||||
"root()"
|
||||
|
@ -201,13 +201,13 @@ add_task(async function() {
|
|||
await breakpointScopes(dbg, "babel-functions", { line: 6, column: 8 }, [
|
||||
"arrow",
|
||||
["p3", "undefined"],
|
||||
"Block",
|
||||
"Function Body",
|
||||
"arrow()",
|
||||
"inner",
|
||||
["p2", "undefined"],
|
||||
"Function Expression",
|
||||
"inner()",
|
||||
"Block",
|
||||
"Function Body",
|
||||
"inner()",
|
||||
"decl",
|
||||
["p1", "undefined"],
|
||||
|
@ -268,7 +268,7 @@ add_task(async function() {
|
|||
await breakpointScopes(dbg, "babel-switches", { line: 7, column: 6 }, [
|
||||
"Switch",
|
||||
["val", "2"],
|
||||
"Block",
|
||||
"Function Body",
|
||||
["val", "1"],
|
||||
"Module",
|
||||
"root()"
|
||||
|
@ -279,7 +279,7 @@ add_task(async function() {
|
|||
["val", "3"],
|
||||
"Switch",
|
||||
["val", "2"],
|
||||
"Block",
|
||||
"Function Body",
|
||||
["val", "1"],
|
||||
"Module",
|
||||
"root()"
|
||||
|
@ -290,12 +290,21 @@ add_task(async function() {
|
|||
["two", "2"],
|
||||
"Catch",
|
||||
["err", '"AnError"'],
|
||||
"Block",
|
||||
"Function Body",
|
||||
["one", "1"],
|
||||
"Module",
|
||||
"root()"
|
||||
]);
|
||||
|
||||
await breakpointScopes(dbg, "babel-lex-and-nonlex", { line: 3, column: 4 }, [
|
||||
"Function Body",
|
||||
"Thing()",
|
||||
"root",
|
||||
"someHelper()",
|
||||
"Module",
|
||||
"root()"
|
||||
]);
|
||||
|
||||
await breakpointScopes(
|
||||
dbg,
|
||||
"babel-modules-webpack",
|
||||
|
|
|
@ -40,7 +40,7 @@ add_task(async function() {
|
|||
is(getScopeLabel(dbg, 2), "na");
|
||||
is(getScopeLabel(dbg, 3), "nb");
|
||||
|
||||
is(getScopeLabel(dbg, 4), "Block");
|
||||
is(getScopeLabel(dbg, 4), "Function Body");
|
||||
|
||||
await toggleScopeNode(dbg, 4);
|
||||
|
||||
|
|
|
@ -27,6 +27,8 @@
|
|||
<button onclick="babelForOf()">Run babel-for-of</button>
|
||||
<script src="sourcemapped/fixtures/babel-functions/output.js"></script>
|
||||
<button onclick="babelFunctions()">Run babel-functions</button>
|
||||
<script src="sourcemapped/fixtures/babel-lex-and-nonlex/output.js"></script>
|
||||
<button onclick="babelLexAndNonlex()">Run babel-lex-and-nonlex</button>
|
||||
<script src="sourcemapped/fixtures/babel-line-start-bindings-es6/output.js"></script>
|
||||
<button onclick="babelLineStartBindingsEs6()">Run babel-line-start-bindings-es6</button>
|
||||
<script src="sourcemapped/fixtures/babel-modules-cjs/output.js"></script>
|
||||
|
|
|
@ -0,0 +1,9 @@
|
|||
export default function root() {
|
||||
function someHelper(){
|
||||
console.log("pause here", root, Thing);
|
||||
}
|
||||
|
||||
class Thing {}
|
||||
|
||||
someHelper();
|
||||
}
|
|
@ -0,0 +1,90 @@
|
|||
var babelLexAndNonlex =
|
||||
/******/ (function(modules) { // webpackBootstrap
|
||||
/******/ // The module cache
|
||||
/******/ var installedModules = {};
|
||||
/******/
|
||||
/******/ // The require function
|
||||
/******/ function __webpack_require__(moduleId) {
|
||||
/******/
|
||||
/******/ // Check if module is in cache
|
||||
/******/ if(installedModules[moduleId]) {
|
||||
/******/ return installedModules[moduleId].exports;
|
||||
/******/ }
|
||||
/******/ // Create a new module (and put it into the cache)
|
||||
/******/ var module = installedModules[moduleId] = {
|
||||
/******/ i: moduleId,
|
||||
/******/ l: false,
|
||||
/******/ exports: {}
|
||||
/******/ };
|
||||
/******/
|
||||
/******/ // Execute the module function
|
||||
/******/ modules[moduleId].call(module.exports, module, module.exports, __webpack_require__);
|
||||
/******/
|
||||
/******/ // Flag the module as loaded
|
||||
/******/ module.l = true;
|
||||
/******/
|
||||
/******/ // Return the exports of the module
|
||||
/******/ return module.exports;
|
||||
/******/ }
|
||||
/******/
|
||||
/******/
|
||||
/******/ // expose the modules object (__webpack_modules__)
|
||||
/******/ __webpack_require__.m = modules;
|
||||
/******/
|
||||
/******/ // expose the module cache
|
||||
/******/ __webpack_require__.c = installedModules;
|
||||
/******/
|
||||
/******/ // define getter function for harmony exports
|
||||
/******/ __webpack_require__.d = function(exports, name, getter) {
|
||||
/******/ if(!__webpack_require__.o(exports, name)) {
|
||||
/******/ Object.defineProperty(exports, name, {
|
||||
/******/ configurable: false,
|
||||
/******/ enumerable: true,
|
||||
/******/ get: getter
|
||||
/******/ });
|
||||
/******/ }
|
||||
/******/ };
|
||||
/******/
|
||||
/******/ // getDefaultExport function for compatibility with non-harmony modules
|
||||
/******/ __webpack_require__.n = function(module) {
|
||||
/******/ var getter = module && module.__esModule ?
|
||||
/******/ function getDefault() { return module['default']; } :
|
||||
/******/ function getModuleExports() { return module; };
|
||||
/******/ __webpack_require__.d(getter, 'a', getter);
|
||||
/******/ return getter;
|
||||
/******/ };
|
||||
/******/
|
||||
/******/ // Object.prototype.hasOwnProperty.call
|
||||
/******/ __webpack_require__.o = function(object, property) { return Object.prototype.hasOwnProperty.call(object, property); };
|
||||
/******/
|
||||
/******/ // __webpack_public_path__
|
||||
/******/ __webpack_require__.p = "";
|
||||
/******/
|
||||
/******/ // Load entry module and return exports
|
||||
/******/ return __webpack_require__(__webpack_require__.s = 0);
|
||||
/******/ })
|
||||
/************************************************************************/
|
||||
/******/ ([
|
||||
/* 0 */
|
||||
/***/ (function(module, __webpack_exports__, __webpack_require__) {
|
||||
|
||||
"use strict";
|
||||
Object.defineProperty(__webpack_exports__, "__esModule", { value: true });
|
||||
/* harmony export (immutable) */ __webpack_exports__["default"] = root;
|
||||
function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
|
||||
|
||||
function root() {
|
||||
function someHelper() {
|
||||
console.log("pause here", root, Thing);
|
||||
}
|
||||
|
||||
var Thing = function Thing() {
|
||||
_classCallCheck(this, Thing);
|
||||
};
|
||||
|
||||
someHelper();
|
||||
}
|
||||
|
||||
/***/ })
|
||||
/******/ ])["default"];
|
||||
//# sourceMappingURL=output.js.map
|
|
@ -0,0 +1 @@
|
|||
{"version":3,"sources":["webpack:///webpack/bootstrap 683415abc3361bb5ff85","webpack:///./fixtures/babel-lex-and-nonlex/input.js"],"names":["root","someHelper","console","log","Thing"],"mappings":";;AAAA;AACA;;AAEA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA;;AAEA;AACA;;AAEA;AACA;AACA;;;AAGA;AACA;;AAEA;AACA;;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA,aAAK;AACL;AACA;;AAEA;AACA;AACA;AACA,mCAA2B,0BAA0B,EAAE;AACvD,yCAAiC,eAAe;AAChD;AACA;AACA;;AAEA;AACA,8DAAsD,+DAA+D;;AAErH;AACA;;AAEA;AACA;;;;;;;;;;;;AC7De,SAASA,IAAT,GAAgB;AAC7B,WAASC,UAAT,GAAqB;AACnBC,YAAQC,GAAR,CAAY,YAAZ,EAA0BH,IAA1B,EAAgCI,KAAhC;AACD;;AAH4B,MAKvBA,KALuB;AAAA;AAAA;;AAO7BH;AACD,C","file":"fixtures/babel-lex-and-nonlex/output.js","sourcesContent":[" \t// The module cache\n \tvar installedModules = {};\n\n \t// The require function\n \tfunction __webpack_require__(moduleId) {\n\n \t\t// Check if module is in cache\n \t\tif(installedModules[moduleId]) {\n \t\t\treturn installedModules[moduleId].exports;\n \t\t}\n \t\t// Create a new module (and put it into the cache)\n \t\tvar module = installedModules[moduleId] = {\n \t\t\ti: moduleId,\n \t\t\tl: false,\n \t\t\texports: {}\n \t\t};\n\n \t\t// Execute the module function\n \t\tmodules[moduleId].call(module.exports, module, module.exports, __webpack_require__);\n\n \t\t// Flag the module as loaded\n \t\tmodule.l = true;\n\n \t\t// Return the exports of the module\n \t\treturn module.exports;\n \t}\n\n\n \t// expose the modules object (__webpack_modules__)\n \t__webpack_require__.m = modules;\n\n \t// expose the module cache\n \t__webpack_require__.c = installedModules;\n\n \t// define getter function for harmony exports\n \t__webpack_require__.d = function(exports, name, getter) {\n \t\tif(!__webpack_require__.o(exports, name)) {\n \t\t\tObject.defineProperty(exports, name, {\n \t\t\t\tconfigurable: false,\n \t\t\t\tenumerable: true,\n \t\t\t\tget: getter\n \t\t\t});\n \t\t}\n \t};\n\n \t// getDefaultExport function for compatibility with non-harmony modules\n \t__webpack_require__.n = function(module) {\n \t\tvar getter = module && module.__esModule ?\n \t\t\tfunction getDefault() { return module['default']; } :\n \t\t\tfunction getModuleExports() { return module; };\n \t\t__webpack_require__.d(getter, 'a', getter);\n \t\treturn getter;\n \t};\n\n \t// Object.prototype.hasOwnProperty.call\n \t__webpack_require__.o = function(object, property) { return Object.prototype.hasOwnProperty.call(object, property); };\n\n \t// __webpack_public_path__\n \t__webpack_require__.p = \"\";\n\n \t// Load entry module and return exports\n \treturn __webpack_require__(__webpack_require__.s = 0);\n\n\n\n// WEBPACK FOOTER //\n// webpack/bootstrap 683415abc3361bb5ff85","export default function root() {\n function someHelper(){\n console.log(\"pause here\", root, Thing);\n }\n\n class Thing {}\n\n someHelper();\n}\n\n\n\n// WEBPACK FOOTER //\n// ./fixtures/babel-lex-and-nonlex/input.js"],"sourceRoot":""}
|
|
@ -437,6 +437,7 @@ const {
|
|||
const dispatcher = new WorkerDispatcher();
|
||||
|
||||
const getOriginalURLs = dispatcher.task("getOriginalURLs");
|
||||
const getOriginalRanges = dispatcher.task("getOriginalRanges");
|
||||
const getGeneratedRanges = dispatcher.task("getGeneratedRanges", {
|
||||
queue: true
|
||||
});
|
||||
|
@ -460,6 +461,7 @@ module.exports = {
|
|||
isOriginalId,
|
||||
hasMappedSource,
|
||||
getOriginalURLs,
|
||||
getOriginalRanges,
|
||||
getGeneratedRanges,
|
||||
getGeneratedLocation,
|
||||
getAllGeneratedLocations,
|
||||
|
|
|
@ -1973,6 +1973,7 @@ exports.ArraySet = ArraySet;
|
|||
|
||||
const {
|
||||
getOriginalURLs,
|
||||
getOriginalRanges,
|
||||
getGeneratedRanges,
|
||||
getGeneratedLocation,
|
||||
getAllGeneratedLocations,
|
||||
|
@ -1993,6 +1994,7 @@ const {
|
|||
// easier to unit test.
|
||||
self.onmessage = workerHandler({
|
||||
getOriginalURLs,
|
||||
getOriginalRanges,
|
||||
getGeneratedRanges,
|
||||
getGeneratedLocation,
|
||||
getAllGeneratedLocations,
|
||||
|
@ -2046,6 +2048,57 @@ async function getOriginalURLs(generatedSource) {
|
|||
|
||||
const COMPUTED_SPANS = new WeakSet();
|
||||
|
||||
const SOURCE_MAPPINGS = new WeakMap();
|
||||
async function getOriginalRanges(sourceId, url) {
|
||||
if (!isOriginalId(sourceId)) {
|
||||
return [];
|
||||
}
|
||||
|
||||
const generatedSourceId = originalToGeneratedId(sourceId);
|
||||
const map = await getSourceMap(generatedSourceId);
|
||||
if (!map) {
|
||||
return [];
|
||||
}
|
||||
|
||||
let mappings = SOURCE_MAPPINGS.get(map);
|
||||
if (!mappings) {
|
||||
mappings = new Map();
|
||||
SOURCE_MAPPINGS.set(map, mappings);
|
||||
}
|
||||
|
||||
let fileMappings = mappings.get(url);
|
||||
if (!fileMappings) {
|
||||
fileMappings = [];
|
||||
mappings.set(url, fileMappings);
|
||||
|
||||
const originalMappings = fileMappings;
|
||||
map.eachMapping(mapping => {
|
||||
if (mapping.source !== url) {
|
||||
return;
|
||||
}
|
||||
|
||||
const last = originalMappings[originalMappings.length - 1];
|
||||
|
||||
if (last && last.line === mapping.originalLine) {
|
||||
if (last.columnStart < mapping.originalColumn) {
|
||||
last.columnEnd = mapping.originalColumn;
|
||||
} else {
|
||||
// Skip this duplicate original location,
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
originalMappings.push({
|
||||
line: mapping.originalLine,
|
||||
columnStart: mapping.originalColumn,
|
||||
columnEnd: Infinity
|
||||
});
|
||||
}, null, SourceMapConsumer.ORIGINAL_ORDER);
|
||||
}
|
||||
|
||||
return fileMappings;
|
||||
}
|
||||
|
||||
/**
|
||||
* Given an original location, find the ranges on the generated file that
|
||||
* are mapped from the original range containing the location.
|
||||
|
@ -2234,6 +2287,7 @@ function applySourceMap(generatedId, url, code, mappings) {
|
|||
|
||||
module.exports = {
|
||||
getOriginalURLs,
|
||||
getOriginalRanges,
|
||||
getGeneratedRanges,
|
||||
getGeneratedLocation,
|
||||
getAllGeneratedLocations,
|
||||
|
|
|
@ -956,7 +956,9 @@ var WasmDisassembler = /** @class */ (function () {
|
|||
case 30 /* CODE_OPERATOR */:
|
||||
var operator = reader.result;
|
||||
if (operator.code == 11 /* end */ && this._indentLevel == 0) {
|
||||
// reached of the function, skipping the operator
|
||||
// reached of the function, closing function body
|
||||
this.appendBuffer(" )");
|
||||
this.newLine();
|
||||
break;
|
||||
}
|
||||
switch (operator.code) {
|
||||
|
@ -980,8 +982,7 @@ var WasmDisassembler = /** @class */ (function () {
|
|||
case 31 /* END_FUNCTION_BODY */:
|
||||
this._funcIndex++;
|
||||
this._backrefLabels = null;
|
||||
this.appendBuffer(" )");
|
||||
this.newLine();
|
||||
// See case BinaryReaderState.CODE_OPERATOR for closing of body
|
||||
break;
|
||||
default:
|
||||
throw new Error("Expectected state: " + reader.state);
|
||||
|
|
Загрузка…
Ссылка в новой задаче