Commit b3373919 authored by Tim van der Lippe's avatar Tim van der Lippe Committed by Commit Bot

Convert ui/ARIAUtils.js to an ES module

ES modules allow files to explicitly import and export symbols [1].
This patch migrates ARIAUtils.js to an ES module, while maintaining
backwards compatibility with existing usages of `window.UI.ARIAUtils`.

The build system is updated to copy these modules verbatim, as it no
longer require pre-processing to be loaded. The `module.json` no longer
includes this file as a script, to make sure it is not double-bundled
into `shell.js`. Instead, it is added to the new field `modules`, which
contains all modules. By doing so, it becomes clear which files are
converted to modules already and which require the legacy references
to the global scope.

This module and future modules will be imported from `root.js`, which is
added to all existing HTML application files.

Design Doc: https://docs.google.com/document/d/1h9dOy3nNPNfZ2AtZXzB-DwJqG4Oo37WWvKLCuzCcPzo/edit?usp=sharing

[1]: https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Statements/import

TBR=jochen@chromium.org

Change-Id: Ie79c8f2fce3aff96fa28af0b575eae39bfe8e1a5
Reviewed-on: https://chromium-review.googlesource.com/c/chromium/src/+/1748949Reviewed-by: default avatarJochen Eisinger <jochen@chromium.org>
Reviewed-by: default avatarYang Guo <yangguo@chromium.org>
Commit-Queue: Tim van der Lippe <tvanderlippe@google.com>
Cr-Commit-Position: refs/heads/master@{#697238}
parent 2321e384
......@@ -57,6 +57,9 @@ std::string GetMimeTypeForPath(const std::string& path) {
} else if (base::EndsWith(filename, ".js",
base::CompareCase::INSENSITIVE_ASCII)) {
return "application/javascript";
} else if (base::EndsWith(filename, ".mjs",
base::CompareCase::INSENSITIVE_ASCII)) {
return "application/javascript";
} else if (base::EndsWith(filename, ".png",
base::CompareCase::INSENSITIVE_ASCII)) {
return "image/png";
......
......@@ -7,7 +7,8 @@ module.exports = {
},
"parserOptions": {
"ecmaVersion": 9
"ecmaVersion": 9,
"sourceType": "module"
},
/**
......
......@@ -786,7 +786,6 @@ all_devtools_files = [
"front_end/toolbox.js",
"front_end/toolbox.json",
"front_end/ui/ActionRegistry.js",
"front_end/ui/ARIAUtils.js",
"front_end/ui/checkboxTextLabel.css",
"front_end/ui/closeButton.css",
"front_end/ui/confirmDialog.css",
......@@ -958,6 +957,12 @@ lighthouse_locale_files = [
all_devtools_files += lighthouse_locale_files
all_devtools_modules = [
"front_end/root.js",
"front_end/ui/ARIAUtils.js",
"front_end/ui/UI.js",
]
devtools_test_files = [
"//third_party/axe-core/axe.js",
"front_end/accessibility_test_runner/AccessibilityPaneTestRunner.js",
......@@ -1149,6 +1154,12 @@ application_templates = [
"front_end/worker_app.html",
]
copied_devtools_modules = [
"$resources_out_dir/root.js",
"$resources_out_dir/ui/ARIAUtils.js",
"$resources_out_dir/ui/UI.js",
]
generated_applications = [
"$resources_out_dir/audits_worker.js",
"$resources_out_dir/devtools_app.html",
......@@ -1267,7 +1278,7 @@ devtools_applications = [
visibility = [ "//third_party/blink/*" ]
group("devtools_all_files") {
data = all_devtools_files
data = all_devtools_files + all_devtools_modules
deps = [
":devtools_frontend_resources_data",
]
......@@ -1284,6 +1295,7 @@ devtools_frontend_resources_deps = [
":devtools_extension_api",
":frontend_protocol_sources",
":supported_css_properties",
":copy_devtools_modules",
]
if (debug_devtools) {
......@@ -1348,8 +1360,8 @@ action("generate_devtools_grd") {
]
grd_files =
generated_applications + generated_non_autostart_non_remote_modules +
devtools_embedder_scripts +
all_devtools_modules + generated_applications +
generated_non_autostart_non_remote_modules + devtools_embedder_scripts +
[ "$resources_out_dir/devtools_extension_api.js" ]
# Bundle remote modules in ChromeOS.
......@@ -1468,6 +1480,24 @@ action("build_release_devtools") {
]
}
action("copy_devtools_modules") {
script = "scripts/build/copy_devtools_modules.py"
deps = [
":build_release_devtools",
]
inputs = all_devtools_modules
outputs = copied_devtools_modules
args = all_devtools_modules + [
"--input_path",
rebase_path(".", root_build_dir),
"--output_path",
rebase_path(resources_out_dir, root_build_dir),
]
}
if (debug_devtools) {
resources_out_debug_dir = "$root_out_dir/resources/inspector/debug"
......
......@@ -78,8 +78,8 @@ def _CheckFormat(input_api, output_api):
# Use eslint to autofix the braces.
# Also fix semicolon to avoid confusing clang-format.
eslint_process = popen([
local_node.node_path(), local_node.eslint_path(),
'--no-eslintrc', '--fix', '--env=es6', '--parser-options=ecmaVersion:9',
local_node.node_path(),
local_node.eslint_path(), '--no-eslintrc', '--fix', '--env=es6', '--parser-options=ecmaVersion:9,sourceType:module',
'--rule={"curly": [2, "multi-or-nest", "consistent"], "semi": 2}'
] + affected_files)
eslint_process.communicate()
......
......@@ -9,8 +9,9 @@
<meta charset="utf-8">
<meta http-equiv="Content-Security-Policy" content="object-src 'none'; script-src 'self' 'unsafe-eval' 'unsafe-inline' https://chrome-devtools-frontend.appspot.com">
<meta name="referrer" content="no-referrer">
<script src="Runtime.js"></script>
<script src="devtools_app.js"></script>
<script type="module" src="root.js"></script>
<script defer src="Runtime.js"></script>
<script defer src="devtools_app.js"></script>
</head>
<body class="undocked" id="-blink-dev-tools"></body>
</html>
......@@ -9,8 +9,9 @@
<meta charset="utf-8">
<meta http-equiv="Content-Security-Policy" content="object-src 'none'; script-src 'self' 'unsafe-eval' 'unsafe-inline' https://chrome-devtools-frontend.appspot.com">
<meta name="referrer" content="no-referrer">
<script src="Runtime.js"></script>
<script src="inspector.js"></script>
<script type="module" src="root.js"></script>
<script defer src="Runtime.js"></script>
<script defer src="inspector.js"></script>
</head>
<body class="undocked" id="-blink-dev-tools"></body>
</html>
......@@ -8,8 +8,9 @@
<head>
<meta charset="utf-8">
<meta http-equiv="Content-Security-Policy" content="object-src 'none'; script-src 'self' 'unsafe-eval' 'unsafe-inline' https://chrome-devtools-frontend.appspot.com">
<script src="Runtime.js"></script>
<script src="integration_test_runner.js"></script>
<script type="module" src="root.js"></script>
<script defer src="Runtime.js"></script>
<script defer src="integration_test_runner.js"></script>
</head>
<body id="-blink-dev-tools"></body>
</html>
......@@ -9,8 +9,9 @@
<meta charset="utf-8">
<meta http-equiv="Content-Security-Policy" content="object-src 'none'; script-src 'self' 'unsafe-eval' 'unsafe-inline' https://chrome-devtools-frontend.appspot.com">
<meta name="referrer" content="no-referrer">
<script src="Runtime.js"></script>
<script src="js_app.js"></script>
<script type="module" src="root.js"></script>
<script defer src="Runtime.js"></script>
<script defer src="js_app.js"></script>
</head>
<body class="undocked" id="-blink-dev-tools"></body>
</html>
......@@ -9,8 +9,9 @@
<meta charset="utf-8">
<meta http-equiv="Content-Security-Policy" content="object-src 'none'; script-src 'self' 'unsafe-eval' 'unsafe-inline' https://chrome-devtools-frontend.appspot.com">
<meta name="referrer" content="no-referrer">
<script src="Runtime.js"></script>
<script src="ndb_app.js"></script>
<script type="module" src="root.js"></script>
<script defer src="Runtime.js"></script>
<script defer src="ndb_app.js"></script>
</head>
<body class="undocked" id="-blink-dev-tools"></body>
</html>
......@@ -9,8 +9,9 @@
<meta charset="utf-8">
<meta http-equiv="Content-Security-Policy" content="object-src 'none'; script-src 'self' 'unsafe-eval' 'unsafe-inline' https://chrome-devtools-frontend.appspot.com">
<meta name="referrer" content="no-referrer">
<script src="Runtime.js"></script>
<script src="node_app.js"></script>
<script type="module" src="root.js"></script>
<script defer src="Runtime.js"></script>
<script defer src="node_app.js"></script>
</head>
<body class="undocked" id="-blink-dev-tools"></body>
</html>
// Copyright 2019 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
import './ui/UI.js';
\ No newline at end of file
......@@ -8,8 +8,9 @@
<head>
<meta charset="utf-8">
<meta http-equiv="Content-Security-Policy" content="object-src 'none'; script-src 'self' 'unsafe-eval' 'unsafe-inline' ">
<script src="Runtime.js"></script>
<script src="toolbox.js"></script>
<script type="module" src="root.js"></script>
<script defer src="Runtime.js"></script>
<script defer src="toolbox.js"></script>
</head>
<body class="undocked" id="-blink-dev-tools"></body>
</html>
......@@ -2,327 +2,326 @@
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
UI.ARIAUtils = {};
UI.ARIAUtils._id = 0;
let _id = 0;
/**
* @param {string} prefix
* @return {string}
*/
export function nextId(prefix) {
return (prefix || '') + ++_id;
}
/**
* @param {!Element} label
* @param {!Element} control
*/
UI.ARIAUtils.bindLabelToControl = function(label, control) {
const controlId = UI.ARIAUtils.nextId('labelledControl');
export function bindLabelToControl(label, control) {
const controlId = nextId('labelledControl');
control.id = controlId;
label.setAttribute('for', controlId);
};
}
/**
* @param {!Element} element
*/
UI.ARIAUtils.markAsAlert = function(element) {
export function markAsAlert(element) {
element.setAttribute('role', 'alert');
element.setAttribute('aria-live', 'polite');
};
}
/**
* @param {!Element} element
*/
UI.ARIAUtils.markAsButton = function(element) {
export function markAsButton(element) {
element.setAttribute('role', 'button');
};
}
/**
* @param {!Element} element
*/
UI.ARIAUtils.markAsCheckbox = function(element) {
export function markAsCheckbox(element) {
element.setAttribute('role', 'checkbox');
};
}
/**
* @param {!Element} element
* @param {boolean=} modal
*/
UI.ARIAUtils.markAsDialog = function(element, modal) {
export function markAsDialog(element, modal) {
element.setAttribute('role', 'dialog');
if (modal)
element.setAttribute('aria-modal', 'true');
};
}
/**
* @param {!Element} element
*/
UI.ARIAUtils.markAsGroup = function(element) {
export function markAsGroup(element) {
element.setAttribute('role', 'group');
};
}
/**
* @param {!Element} element
*/
UI.ARIAUtils.markAsLink = function(element) {
export function markAsLink(element) {
element.setAttribute('role', 'link');
};
}
/**
* @param {!Element} element
*/
UI.ARIAUtils.markAsMenuButton = function(element) {
UI.ARIAUtils.markAsButton(element);
export function markAsMenuButton(element) {
markAsButton(element);
element.setAttribute('aria-haspopup', true);
};
}
/**
* @param {!Element} element
*/
UI.ARIAUtils.markAsProgressBar = function(element) {
export function markAsProgressBar(element) {
element.setAttribute('role', 'progressbar');
element.setAttribute('aria-valuemin', 0);
element.setAttribute('aria-valuemax', 100);
};
}
/**
* @param {!Element} element
*/
UI.ARIAUtils.markAsTab = function(element) {
export function markAsTab(element) {
element.setAttribute('role', 'tab');
};
}
/**
* @param {!Element} element
*/
UI.ARIAUtils.markAsTree = function(element) {
export function markAsTree(element) {
element.setAttribute('role', 'tree');
};
}
/**
* @param {!Element} element
*/
UI.ARIAUtils.markAsTreeitem = function(element) {
export function markAsTreeitem(element) {
element.setAttribute('role', 'treeitem');
};
}
/**
* @param {!Element} element
*/
UI.ARIAUtils.markAsTextBox = function(element) {
export function markAsTextBox(element) {
element.setAttribute('role', 'textbox');
};
}
/**
* @param {!Element} element
*/
UI.ARIAUtils.markAsMenu = function(element) {
export function markAsMenu(element) {
element.setAttribute('role', 'menu');
};
}
/**
* @param {!Element} element
*/
UI.ARIAUtils.markAsMenuItem = function(element) {
export function markAsMenuItem(element) {
element.setAttribute('role', 'menuitem');
};
}
/**
* @param {!Element} element
*/
UI.ARIAUtils.markAsMenuItemSubMenu = function(element) {
UI.ARIAUtils.markAsMenuItem(element);
export function markAsMenuItemSubMenu(element) {
markAsMenuItem(element);
element.setAttribute('aria-haspopup', true);
};
}
/**
* Must contain children whose role is option.
* @param {!Element} element
*/
UI.ARIAUtils.markAsListBox = function(element) {
export function markAsListBox(element) {
element.setAttribute('role', 'listbox');
};
}
/**
* @param {!Element} element
*/
UI.ARIAUtils.markAsMultiSelectable = function(element) {
export function markAsMultiSelectable(element) {
element.setAttribute('aria-multiselectable', 'true');
};
}
/**
* Must be contained in, or owned by, an element with the role listbox.
* @param {!Element} element
*/
UI.ARIAUtils.markAsOption = function(element) {
export function markAsOption(element) {
element.setAttribute('role', 'option');
};
}
/**
* @param {!Element} element
*/
UI.ARIAUtils.markAsRadioGroup = function(element) {
export function markAsRadioGroup(element) {
element.setAttribute('role', 'radiogroup');
};
}
/**
* @param {!Element} element
*/
UI.ARIAUtils.markAsHidden = function(element) {
export function markAsHidden(element) {
element.setAttribute('aria-hidden', 'true');
};
}
/**
* @param {!Element} element
* @param {number} level
*/
UI.ARIAUtils.markAsHeading = function(element, level) {
export function markAsHeading(element, level) {
element.setAttribute('role', 'heading');
element.setAttribute('aria-level', level);
};
}
/**
* @param {!Element} element
*/
UI.ARIAUtils.markAsPoliteLiveRegion = function(element) {
export function markAsPoliteLiveRegion(element) {
element.setAttribute('aria-live', 'polite');
};
}
/**
* @param {!Element} element
* @param {?string} placeholder
*/
UI.ARIAUtils.setPlaceholder = function(element, placeholder) {
export function setPlaceholder(element, placeholder) {
if (placeholder)
element.setAttribute('aria-placeholder', placeholder);
else
element.removeAttribute('aria-placeholder');
};
}
/**
* @param {!Element} element
*/
UI.ARIAUtils.markAsPresentation = function(element) {
export function markAsPresentation(element) {
element.setAttribute('role', 'presentation');
};
}
/**
* @param {!Element} element
*/
UI.ARIAUtils.markAsStatus = function(element) {
export function markAsStatus(element) {
element.setAttribute('role', 'status');
};
}
/**
* @param {!Element} element
*/
UI.ARIAUtils.ensureId = function(element) {
export function ensureId(element) {
if (!element.id)
element.id = UI.ARIAUtils.nextId('ariaElement');
};
/**
* @param {string} prefix
* @return {string}
*/
UI.ARIAUtils.nextId = function(prefix) {
return (prefix || '') + ++UI.ARIAUtils._id;
};
element.id = nextId('ariaElement');
}
/**
* @param {!Element} element
* @param {?Element} controlledElement
*/
UI.ARIAUtils.setControls = function(element, controlledElement) {
export function setControls(element, controlledElement) {
if (!controlledElement) {
element.removeAttribute('aria-controls');
return;
}
UI.ARIAUtils.ensureId(controlledElement);
ensureId(controlledElement);
element.setAttribute('aria-controls', controlledElement.id);
};
}
/**
* @param {!Element} element
* @param {boolean} value
*/
UI.ARIAUtils.setChecked = function(element, value) {
export function setChecked(element, value) {
element.setAttribute('aria-checked', !!value);
};
}
/**
* @param {!Element} element
*/
UI.ARIAUtils.setCheckboxAsIndeterminate = function(element) {
export function setCheckboxAsIndeterminate(element) {
element.setAttribute('aria-checked', 'mixed');
};
}
/**
* @param {!Element} element
* @param {boolean} value
*/
UI.ARIAUtils.setExpanded = function(element, value) {
export function setExpanded(element, value) {
element.setAttribute('aria-expanded', !!value);
};
}
/**
* @param {!Element} element
*/
UI.ARIAUtils.unsetExpandable = function(element) {
export function unsetExpandable(element) {
element.removeAttribute('aria-expanded');
};
}
/**
* @param {!Element} element
* @param {boolean} value
*/
UI.ARIAUtils.setSelected = function(element, value) {
export function setSelected(element, value) {
// aria-selected behaves differently for false and undefined.
// Often times undefined values are unintentionally typed as booleans.
// Use !! to make sure this is true or false.
element.setAttribute('aria-selected', !!value);
};
}
/**
* @param {!Element} element
* @param {boolean} value
*/
UI.ARIAUtils.setInvalid = function(element, value) {
export function setInvalid(element, value) {
if (value)
element.setAttribute('aria-invalid', value);
else
element.removeAttribute('aria-invalid');
};
}
/**
* @param {!Element} element
* @param {boolean} value
*/
UI.ARIAUtils.setPressed = function(element, value) {
export function setPressed(element, value) {
// aria-pressed behaves differently for false and undefined.
// Often times undefined values are unintentionally typed as booleans.
// Use !! to make sure this is true or false.
element.setAttribute('aria-pressed', !!value);
};
}
/**
* @param {!Element} element
* @param {number} value
*/
UI.ARIAUtils.setProgressBarCurrentPercentage = function(element, value) {
export function setProgressBarCurrentPercentage(element, value) {
element.setAttribute('aria-valuenow', value);
};
}
/**
* @param {!Element} element
* @param {string} name
*/
UI.ARIAUtils.setAccessibleName = function(element, name) {
export function setAccessibleName(element, name) {
element.setAttribute('aria-label', name);
};
}
/** @type {!WeakMap<!Element, !Element>} */
UI.ARIAUtils._descriptionMap = new WeakMap();
const _descriptionMap = new WeakMap();
/**
* @param {!Element} element
* @param {string} description
*/
UI.ARIAUtils.setDescription = function(element, description) {
export function setDescription(element, description) {
// Nodes in the accesesibility tree are made up of a core
// triplet of "name", "value", "description"
// The "description" field is taken from either
......@@ -348,12 +347,12 @@ UI.ARIAUtils.setDescription = function(element, description) {
// The rest of DevTools shouldn't have to worry about this,
// so there is some unfortunate code below.
if (UI.ARIAUtils._descriptionMap.has(element))
UI.ARIAUtils._descriptionMap.get(element).remove();
if (_descriptionMap.has(element))
_descriptionMap.get(element).remove();
element.removeAttribute('data-aria-utils-animation-hack');
if (!description) {
UI.ARIAUtils._descriptionMap.delete(element);
_descriptionMap.delete(element);
element.removeAttribute('aria-describedby');
return;
}
......@@ -363,9 +362,9 @@ UI.ARIAUtils.setDescription = function(element, description) {
const descriptionElement = createElement('span');
descriptionElement.textContent = description;
descriptionElement.style.display = 'none';
UI.ARIAUtils.ensureId(descriptionElement);
ensureId(descriptionElement);
element.setAttribute('aria-describedby', descriptionElement.id);
UI.ARIAUtils._descriptionMap.set(element, descriptionElement);
_descriptionMap.set(element, descriptionElement);
// Now we have to actually put this description element
// somewhere in the DOM so that we can point to it.
......@@ -398,20 +397,20 @@ UI.ARIAUtils.setDescription = function(element, description) {
element.setAttribute('data-aria-utils-animation-hack', 'sorry');
element.addEventListener('animationend', () => {
// Someone might have made a new description in the meantime.
if (UI.ARIAUtils._descriptionMap.get(element) !== descriptionElement)
if (_descriptionMap.get(element) !== descriptionElement)
return;
element.removeAttribute('data-aria-utils-animation-hack');
// Try it again. This time we are in the DOM, so it *should* work.
element.insertAdjacentElement('afterend', descriptionElement);
}, {once: true});
};
}
/**
* @param {!Element} element
* @param {?Element} activedescendant
*/
UI.ARIAUtils.setActiveDescendant = function(element, activedescendant) {
export function setActiveDescendant(element, activedescendant) {
if (!activedescendant) {
element.removeAttribute('aria-activedescendant');
return;
......@@ -419,17 +418,19 @@ UI.ARIAUtils.setActiveDescendant = function(element, activedescendant) {
console.assert(element.hasSameShadowRoot(activedescendant), 'elements are not in the same shadow dom');
UI.ARIAUtils.ensureId(activedescendant);
ensureId(activedescendant);
element.setAttribute('aria-activedescendant', activedescendant.id);
};
}
const AlertElementSymbol = Symbol('AlertElementSybmol');
/**
* @param {string} message
* @param {!Element} element
*/
UI.ARIAUtils.alert = function(message, element) {
export function alert(message, element) {
const document = element.ownerDocument;
if (!document[UI.ARIAUtils.AlertElementSymbol]) {
if (!document[AlertElementSymbol]) {
const alertElement = document.body.createChild('div');
alertElement.style.position = 'absolute';
alertElement.style.left = '-999em';
......@@ -437,9 +438,54 @@ UI.ARIAUtils.alert = function(message, element) {
alertElement.style.overflow = 'hidden';
alertElement.setAttribute('role', 'alert');
alertElement.setAttribute('aria-atomic', 'true');
document[UI.ARIAUtils.AlertElementSymbol] = alertElement;
document[AlertElementSymbol] = alertElement;
}
document[UI.ARIAUtils.AlertElementSymbol].textContent = message.trimEndWithMaxLength(10000);
};
UI.ARIAUtils.AlertElementSymbol = Symbol('AlertElementSybmol');
document[AlertElementSymbol].textContent = message.trimEndWithMaxLength(10000);
}
/** Legacy exported object @suppress {const} */
self.UI = self.UI || {};
self.UI.ARIAUtils = {
nextId,
bindLabelToControl,
markAsAlert,
markAsButton,
markAsCheckbox,
markAsDialog,
markAsGroup,
markAsLink,
markAsMenuButton,
markAsProgressBar,
markAsTab,
markAsTree,
markAsTreeitem,
markAsTextBox,
markAsMenu,
markAsMenuItem,
markAsMenuItemSubMenu,
markAsListBox,
markAsMultiSelectable,
markAsOption,
markAsRadioGroup,
markAsHidden,
markAsHeading,
markAsPoliteLiveRegion,
setPlaceholder,
markAsPresentation,
markAsStatus,
ensureId,
setControls,
setChecked,
setCheckboxAsIndeterminate,
setExpanded,
unsetExpandable,
setSelected,
setInvalid,
setPressed,
setProgressBarCurrentPercentage,
setAccessibleName,
setDescription,
setActiveDescendant,
alert,
};
import * as ARIAUtils from './ARIAUtils.js';
export {
ARIAUtils,
};
\ No newline at end of file
......@@ -54,13 +54,16 @@
"SuggestBox.js",
"TabbedPane.js",
"UIUtils.js",
"ARIAUtils.js",
"ZoomManager.js",
"ShortcutsScreen.js",
"Geometry.js",
"XLink.js",
"XWidget.js"
],
"modules": [
"ARIAUtils.js",
"UI.js"
],
"resources": [
"checkboxTextLabel.css",
"closeButton.css",
......
......@@ -9,8 +9,9 @@
<meta charset="utf-8">
<meta http-equiv="Content-Security-Policy" content="object-src 'none'; script-src 'self' 'unsafe-eval' 'unsafe-inline' https://chrome-devtools-frontend.appspot.com">
<meta name="referrer" content="no-referrer">
<script src="Runtime.js"></script>
<script src="worker_app.js"></script>
<script type="module" src="root.js"></script>
<script defer src="Runtime.js"></script>
<script defer src="worker_app.js"></script>
</head>
<body class="undocked" id="-blink-dev-tools"></body>
</html>
......@@ -35,6 +35,10 @@
"bugs": {
"url": "https://bugs.chromium.org/p/chromium/issues/list?can=2&q=component:Platform%3EDevTools%20&sort=-opened&colspec=ID%20Stars%20Owner%20Summary%20Modified%20Opened"
},
"type": "module",
"files": [
"front_end/**/*.mjs"
],
"homepage": "https://devtools.chrome.com",
"devDependencies": {
"ajv": "^5.1.5"
......
......@@ -133,13 +133,13 @@ class ReleaseBuilder(object):
output = StringIO()
with open(join(self.application_dir, html_name), 'r') as app_input_html:
for line in app_input_html:
if '<script ' in line or '<link ' in line:
if ('<script ' in line and 'type="module"' not in line) or '<link ' in line:
continue
if '</head>' in line:
self._write_include_tags(self.descriptors, output)
js_file = join(self.application_dir, self.app_file('js'))
if path.exists(js_file):
output.write(' <script>%s</script>\n' % minify_js(read_file(js_file)))
output.write(' <script type="module">%s</script>\n' % minify_js(read_file(js_file)))
output.write(line)
write_file(join(self.output_dir, html_name), output.getvalue())
......@@ -154,7 +154,7 @@ class ReleaseBuilder(object):
def _generate_include_tag(self, resource_path):
if resource_path.endswith('.js'):
return ' <script type="text/javascript" src="%s"></script>\n' % resource_path
return ' <script defer src="%s"></script>\n' % resource_path
else:
assert resource_path
......
#!/usr/bin/env python
# -*- coding: UTF-8 -*-
#
# Copyright 2019 The Chromium Authors. All rights reserved.
# Use of this source code is governed by a BSD-style license that can be
# found in the LICENSE file.
"""
Copies the modules into the resources folder
"""
from os.path import join, relpath
import shutil
import sys
def main(argv):
try:
input_path_flag_index = argv.index('--input_path')
input_path = argv[input_path_flag_index + 1]
output_path_flag_index = argv.index('--output_path')
output_path = argv[output_path_flag_index + 1]
devtools_modules = argv[1:input_path_flag_index]
except:
print 'Usage: %s module_1 module_2 ... module_N --input_path <input_path> --output_path <output_path>' % argv[0]
raise
for file_name in devtools_modules:
shutil.copy(join(input_path, file_name), join(output_path, relpath(file_name, 'front_end')))
if __name__ == '__main__':
sys.exit(main(sys.argv))
......@@ -76,7 +76,7 @@ class Descriptors:
for name in self.sorted_modules():
module = self.modules[name]
skipped_files = set(module.get('skip_compilation', []))
for script in module.get('scripts', []):
for script in module.get('scripts', []) + module.get('modules', []):
if script not in skipped_files:
files[path.normpath(path.join(self.application_dir, name, script))] = True
return files.keys()
......
......@@ -284,7 +284,7 @@ async function auditFileForLocalizability(filePath, errors) {
if (path.extname(filePath) === '.grdp')
return auditGrdpFile(filePath, fileContent, errors);
const ast = esprima.parse(fileContent, {loc: true});
const ast = esprima.parseModule(fileContent, {loc: true});
const relativeFilePath = localizationUtils.getRelativeFilePathFromSrc(filePath);
for (const node of ast.body)
......
......@@ -32,6 +32,7 @@ async function main() {
else
await getErrors();
} catch (e) {
console.log(e.stack);
console.log(`Error: ${e.message}`);
process.exit(1);
}
......
......@@ -77,6 +77,7 @@ DEVTOOLS_FRONTEND_PATH = path.join(DEVTOOLS_PATH, 'front_end')
GLOBAL_EXTERNS_FILE = to_platform_path(path.join(DEVTOOLS_FRONTEND_PATH, 'externs.js'))
DEFAULT_PROTOCOL_EXTERNS_FILE = path.join(DEVTOOLS_FRONTEND_PATH, 'protocol_externs.js')
RUNTIME_FILE = to_platform_path(path.join(DEVTOOLS_FRONTEND_PATH, 'Runtime.js'))
ROOT_MODULE_FILE = to_platform_path(path.join(DEVTOOLS_FRONTEND_PATH, 'root.js'))
CLOSURE_COMPILER_JAR = to_platform_path(path.join(SCRIPTS_PATH, 'closure', 'compiler.jar'))
CLOSURE_RUNNER_JAR = to_platform_path(path.join(SCRIPTS_PATH, 'closure', 'closure_runner', 'closure_runner.jar'))
......@@ -279,6 +280,8 @@ def prepare_closure_frontend_compile(temp_devtools_path, descriptors, namespace_
namespace_externs_path,
'--js',
RUNTIME_FILE,
'--js',
ROOT_MODULE_FILE,
]
all_files = descriptors.all_compiled_files()
......
......@@ -93,7 +93,7 @@ async function parseLocalizableStringsFromFile(filePath) {
if (path.basename(filePath) === 'module.json')
return parseLocalizableStringFromModuleJson(fileContent, filePath);
const ast = esprima.parse(fileContent, {loc: true});
const ast = esprima.parseModule(fileContent, {loc: true});
for (const node of ast.body)
parseLocalizableStringFromNode(node, filePath);
}
......
{
"compilerOptions": {
"typeRoots": ["../../../devtools-node-modules/third_party/node_modules/@types"]
}
}
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment