OLD | NEW |
1 // Copyright (c) 2016 The Chromium Authors. All rights reserved. | 1 // Copyright (c) 2016 The Chromium Authors. All rights reserved. |
2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
4 | 4 |
5 /** | 5 /** |
6 * @unrestricted | 6 * @unrestricted |
7 */ | 7 */ |
8 Audits2.Audits2Panel = class extends UI.PanelWithSidebar { | 8 Audits2.Audits2Panel = class extends UI.PanelWithSidebar { |
9 constructor() { | 9 constructor() { |
10 super('audits2'); | 10 super('audits2'); |
(...skipping 137 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
148 } | 148 } |
149 | 149 |
150 return Promise.resolve() | 150 return Promise.resolve() |
151 .then(_ => this._protocolService.attach()) | 151 .then(_ => this._protocolService.attach()) |
152 .then(_ => { | 152 .then(_ => { |
153 this._auditRunning = true; | 153 this._auditRunning = true; |
154 this._updateButton(); | 154 this._updateButton(); |
155 this._updateStatus(Common.UIString('Loading\u2026')); | 155 this._updateStatus(Common.UIString('Loading\u2026')); |
156 }) | 156 }) |
157 .then(_ => this._protocolService.startLighthouse(this._inspectedURL, cat
egoryIDs)) | 157 .then(_ => this._protocolService.startLighthouse(this._inspectedURL, cat
egoryIDs)) |
158 .then(lighthouseResult => | 158 .then(lighthouseResult => { |
159 this._stopAndReattach().then(() => this._buildReportUI(lighthouseResul
t)) | 159 if (lighthouseResult && lighthouseResult.fatal) { |
160 ).catch(err => { | 160 const error = new Error(lighthouseResult.message); |
| 161 error.stack = lighthouseResult.stack; |
| 162 throw error; |
| 163 } |
| 164 |
| 165 return this._stopAndReattach().then(() => this._buildReportUI(lighthou
seResult)); |
| 166 }) |
| 167 .catch(err => { |
161 if (err instanceof Error) | 168 if (err instanceof Error) |
162 this._renderBugReport(err); | 169 this._renderBugReport(err); |
163 }); | 170 }); |
164 } | 171 } |
165 | 172 |
166 _hideDialog() { | 173 _hideDialog() { |
167 if (!this._dialog) | 174 if (!this._dialog) |
168 return; | 175 return; |
169 this._dialog.hide(); | 176 this._dialog.hide(); |
170 | 177 |
171 var emulationModel = self.singleton(Emulation.DeviceModeModel); | 178 var emulationModel = self.singleton(Emulation.DeviceModeModel); |
172 emulationModel.enabledSetting().set(this._emulationEnabledBefore); | 179 emulationModel.enabledSetting().set(this._emulationEnabledBefore); |
173 emulationModel.deviceOutlineSetting().set(this._emulationOutlineEnabledBefor
e); | 180 emulationModel.deviceOutlineSetting().set(this._emulationOutlineEnabledBefor
e); |
(...skipping 85 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
259 | 266 |
260 /** | 267 /** |
261 * @param {!Error} err | 268 * @param {!Error} err |
262 * @param {!Element} parentElem | 269 * @param {!Element} parentElem |
263 */ | 270 */ |
264 _createBugReportLink(err, parentElem) { | 271 _createBugReportLink(err, parentElem) { |
265 var baseURI = 'https://github.com/GoogleChrome/lighthouse/issues/new?'; | 272 var baseURI = 'https://github.com/GoogleChrome/lighthouse/issues/new?'; |
266 var title = encodeURI('title=DevTools Error: ' + err.message.substring(0, 60
)); | 273 var title = encodeURI('title=DevTools Error: ' + err.message.substring(0, 60
)); |
267 | 274 |
268 var qsBody = ''; | 275 var qsBody = ''; |
| 276 qsBody += '**Initial URL**: ' + this._inspectedURL + '\n'; |
| 277 qsBody += '**Chrome Version**: ' + navigator.userAgent.match(/Chrome\/(\S+)/
)[1] + '\n'; |
269 qsBody += '**Error Message**: ' + err.message + '\n'; | 278 qsBody += '**Error Message**: ' + err.message + '\n'; |
270 qsBody += '**Stack Trace**:\n ```' + err.stack + '```'; | 279 qsBody += '**Stack Trace**:\n ```' + err.stack + '```'; |
271 var body = '&body=' + encodeURI(qsBody); | 280 var body = '&body=' + encodeURI(qsBody); |
272 | 281 |
273 var reportErrorEl = parentElem.createChild('a', 'audits2-link audits2-report
-error'); | 282 var reportErrorEl = parentElem.createChild('a', 'audits2-link audits2-report
-error'); |
274 reportErrorEl.href = baseURI + title + body; | 283 reportErrorEl.href = baseURI + title + body; |
275 reportErrorEl.textContent = Common.UIString('Report this bug'); | 284 reportErrorEl.textContent = Common.UIString('Report this bug'); |
276 reportErrorEl.target = '_blank'; | 285 reportErrorEl.target = '_blank'; |
277 } | 286 } |
278 | 287 |
(...skipping 254 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
533 this._reportContainer.remove(); | 542 this._reportContainer.remove(); |
534 } | 543 } |
535 | 544 |
536 _renderReport() { | 545 _renderReport() { |
537 this._resultsView.removeChildren(); | 546 this._resultsView.removeChildren(); |
538 if (this._reportContainer) { | 547 if (this._reportContainer) { |
539 this._resultsView.appendChild(this._reportContainer); | 548 this._resultsView.appendChild(this._reportContainer); |
540 return; | 549 return; |
541 } | 550 } |
542 | 551 |
543 this._reportContainer = this._resultsView.createChild('div', 'report-contain
er lh-vars lh-root'); | 552 this._reportContainer = this._resultsView.createChild('div', 'report-contain
er lh-vars lh-root lh-devtools'); |
544 | 553 |
545 var dom = new DOM(/** @type {!Document} */ (this._resultsView.ownerDocument)
); | 554 var dom = new DOM(/** @type {!Document} */ (this._resultsView.ownerDocument)
); |
546 var detailsRenderer = new Audits2.DetailsRenderer(dom); | 555 var detailsRenderer = new Audits2.DetailsRenderer(dom); |
547 var categoryRenderer = new CategoryRenderer(dom, detailsRenderer); | 556 var categoryRenderer = new CategoryRenderer(dom, detailsRenderer); |
548 var renderer = new Audits2.Audits2Panel.ReportRenderer(dom, categoryRenderer
); | 557 var renderer = new Audits2.Audits2Panel.ReportRenderer(dom, categoryRenderer
); |
549 | 558 |
550 var templatesHTML = Runtime.cachedResources['audits2/lighthouse/templates.ht
ml']; | 559 var templatesHTML = Runtime.cachedResources['audits2/lighthouse/templates.ht
ml']; |
551 var templatesDOM = new DOMParser().parseFromString(templatesHTML, 'text/html
'); | 560 var templatesDOM = new DOMParser().parseFromString(templatesHTML, 'text/html
'); |
552 if (!templatesDOM) | 561 if (!templatesDOM) |
553 return; | 562 return; |
554 | 563 |
555 renderer.setTemplateContext(templatesDOM); | 564 renderer.setTemplateContext(templatesDOM); |
556 renderer.renderReport(this._lighthouseResult, this._reportContainer); | 565 renderer.renderReport(this._lighthouseResult, this._reportContainer); |
557 | |
558 var performanceScoreElement = this._reportContainer.querySelector('.lh-categ
ory[id=performance] .lh-score'); | |
559 var artifacts = this._lighthouseResult['artifacts']; | |
560 if (!performanceScoreElement || !artifacts) | |
561 return; | |
562 var tracePass = artifacts['traces'] ? artifacts['traces']['defaultPass'] : n
ull; | |
563 if (!tracePass) | |
564 return; | |
565 | |
566 var fmp = this._lighthouseResult['audits']['first-meaningful-paint']; | |
567 if (!fmp || !fmp['extendedInfo']) | |
568 return; | |
569 | |
570 var tti = this._lighthouseResult['audits']['time-to-interactive']; | |
571 if (!tti || !tti['extendedInfo']) | |
572 return; | |
573 | |
574 var navStart = fmp['extendedInfo']['value']['timestamps']['navStart']; | |
575 var markers = [ | |
576 { | |
577 title: Common.UIString('First contentful paint'), | |
578 value: (fmp['extendedInfo']['value']['timestamps']['fCP'] - navStart) /
1000 | |
579 }, | |
580 { | |
581 title: Common.UIString('First meaningful paint'), | |
582 value: (fmp['extendedInfo']['value']['timestamps']['fMP'] - navStart) /
1000 | |
583 }, | |
584 { | |
585 title: Common.UIString('Time to interactive'), | |
586 value: (tti['extendedInfo']['value']['timestamps']['timeToInteractive']
- navStart) / 1000 | |
587 }, | |
588 { | |
589 title: Common.UIString('Visually ready'), | |
590 value: (tti['extendedInfo']['value']['timestamps']['visuallyReady'] - na
vStart) / 1000 | |
591 } | |
592 ]; | |
593 | |
594 var timeSpan = Math.max(...markers.map(marker => marker.value)); | |
595 var screenshots = tracePass.traceEvents.filter(e => e.cat === 'disabled-by-d
efault-devtools.screenshot'); | |
596 var timelineElement = createElementWithClass('div', 'audits2-timeline'); | |
597 var filmStripElement = timelineElement.createChild('div', 'audits2-filmstrip
'); | |
598 | |
599 var numberOfFrames = 8; | |
600 var roundToMs = 100; | |
601 var timeStep = (Math.ceil(timeSpan / numberOfFrames / roundToMs)) * roundToM
s; | |
602 | |
603 for (var time = 0; time < timeSpan; time += timeStep) { | |
604 var frameForTime = null; | |
605 for (var e of screenshots) { | |
606 if ((e.ts - navStart) / 1000 < time + timeStep) | |
607 frameForTime = e.args.snapshot; | |
608 } | |
609 var frame = filmStripElement.createChild('div', 'frame'); | |
610 frame.createChild('div', 'time').textContent = Number.millisToString(time
+ timeStep); | |
611 | |
612 var thumbnail = frame.createChild('div', 'thumbnail'); | |
613 if (frameForTime) { | |
614 var img = thumbnail.createChild('img'); | |
615 img.src = 'data:image/jpg;base64,' + frameForTime; | |
616 } | |
617 } | |
618 | |
619 for (var marker of markers) { | |
620 var markerElement = timelineElement.createChild('div', 'audits2-timeline-m
arker'); | |
621 markerElement.createChild('div', 'audits2-timeline-bar').style.width = | |
622 (100 * (marker.value / timeSpan) | 0) + '%'; | |
623 markerElement.createChild('span').textContent = Common.UIString('%s: ', ma
rker.title); | |
624 markerElement.createChild('span', 'audits2-timeline-subtitle').textContent
= Number.millisToString(marker.value); | |
625 } | |
626 | |
627 performanceScoreElement.parentElement.insertBefore(timelineElement, performa
nceScoreElement.nextSibling); | |
628 } | 566 } |
629 }; | 567 }; |
630 | 568 |
631 Audits2.Audits2Panel.TreeSubElement = class extends UI.TreeElement { | 569 Audits2.Audits2Panel.TreeSubElement = class extends UI.TreeElement { |
632 /** | 570 /** |
633 * @param {string} id | 571 * @param {string} id |
634 * @param {string} name | 572 * @param {string} name |
635 * @param {number} score | 573 * @param {number} score |
636 */ | 574 */ |
637 constructor(id, name, score) { | 575 constructor(id, name, score) { |
(...skipping 66 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
704 return; | 642 return; |
705 | 643 |
706 var element = Components.DOMPresentationUtils.linkifyNodeReference(node,
undefined, detailsItem.snippet); | 644 var element = Components.DOMPresentationUtils.linkifyNodeReference(node,
undefined, detailsItem.snippet); |
707 origElement.title = ''; | 645 origElement.title = ''; |
708 origElement.textContent = ''; | 646 origElement.textContent = ''; |
709 origElement.appendChild(element); | 647 origElement.appendChild(element); |
710 }); | 648 }); |
711 }); | 649 }); |
712 } | 650 } |
713 }; | 651 }; |
OLD | NEW |