stats - know how many scripts, styles, and UI elements are used

This commit is contained in:
Johannes Rieken 2016-08-12 11:26:25 +02:00
parent 589b40315f
commit ffce4455b0
4 changed files with 44 additions and 16 deletions

View file

@ -173,15 +173,15 @@ export class ExtensionEditor extends BaseEditor {
.then<void>(body => {
const webview = new WebView(
this.body,
document.querySelector('.monaco-editor-background'),
link => shell.openExternal(link.toString())
document.querySelector('.monaco-editor-background')
);
webview.style(this.themeService.getTheme());
webview.contents = [renderBody(body)];
const listener = this.themeService.onDidThemeChange(themeId => webview.style(themeId));
this.transientDisposables.push(webview, listener);
const linkListener = webview.onDidClickLink(link => shell.openExternal(link.toString());
const themeListener = this.themeService.onDidThemeChange(themeId => webview.style(themeId));
this.transientDisposables.push(webview, linkListener, themeListener);
})
.then(null, () => null)
.then(() => removeClass(this.body, 'loading'));

View file

@ -10,7 +10,7 @@ import URI from 'vs/base/common/uri';
import {TPromise} from 'vs/base/common/winjs.base';
import {IModel} from 'vs/editor/common/editorCommon';
import {Dimension, Builder} from 'vs/base/browser/builder';
import {empty as EmptyDisposable} from 'vs/base/common/lifecycle';
import {empty as EmptyDisposable, IDisposable, dispose} from 'vs/base/common/lifecycle';
import {EditorOptions, EditorInput} from 'vs/workbench/common/editor';
import {BaseEditor} from 'vs/workbench/browser/parts/editor/baseEditor';
import {Position} from 'vs/platform/editor/common/editor';
@ -34,6 +34,7 @@ export class HtmlPreviewPart extends BaseEditor {
private _themeService: IThemeService;
private _openerService: IOpenerService;
private _webview: Webview;
private _webviewDisposables: IDisposable[];
private _container: HTMLDivElement;
private _baseUrl: URI;
@ -59,7 +60,7 @@ export class HtmlPreviewPart extends BaseEditor {
dispose(): void {
// remove from dom
this._webview.dispose();
this._webviewDisposables = dispose(this._webviewDisposables);
// unhook listeners
this._themeChangeSubscription.dispose();
@ -76,11 +77,14 @@ export class HtmlPreviewPart extends BaseEditor {
private get webview(): Webview {
if (!this._webview) {
this._webview = new Webview(this._container,
document.querySelector('.monaco-editor-background'),
uri => this._openerService.open(uri));
this._webview = new Webview(this._container, document.querySelector('.monaco-editor-background'));
this._webview.baseUrl = this._baseUrl && this._baseUrl.toString(true);
this._webviewDisposables = [
this._webview,
this._webview.onDidClickLink(uri => this._openerService.open(uri)),
this._webview.onDidLoadContent(data => this.telemetryService.publicLog('previewHtml', data.stats))
];
}
return this._webview;
}
@ -103,7 +107,7 @@ export class HtmlPreviewPart extends BaseEditor {
if (!visible) {
this._themeChangeSubscription.dispose();
this._modelChangeSubscription.dispose();
this._webview.dispose();
this._webviewDisposables = dispose(this._webviewDisposables);
this._webview = undefined;
} else {
this._themeChangeSubscription = this._themeService.onDidThemeChange(themeId => this.webview.style(themeId));

View file

@ -52,8 +52,17 @@
// update iframe-contents
ipcRenderer.on('content', function(event, value) {
const parser = new DOMParser();
const newDocument = parser.parseFromString(value.join('\n'), 'text/html');
const text = value.join('\n');
const newDocument = new DOMParser().parseFromString(text, 'text/html');
// know what happens here
const stats = {
scriptTags: newDocument.documentElement.querySelectorAll('script').length,
inputTags: newDocument.documentElement.querySelectorAll('input').length,
styleTags: newDocument.documentElement.querySelectorAll('style').length,
linkStyleSheetTags: newDocument.documentElement.querySelectorAll('link[rel=stylesheet]').length,
stringLen: text.length
};
// set base-url if applicable
if(initData.baseUrl && newDocument.head.getElementsByTagName('base').length === 0) {
@ -107,7 +116,7 @@
target.contentDocument.write(newDocument.documentElement.innerHTML);
target.contentDocument.close();
ipcRenderer.sendToHost('did-set-content');
ipcRenderer.sendToHost('did-set-content', stats);
});
// forward messages from the embedded iframe

View file

@ -8,6 +8,7 @@
import URI from 'vs/base/common/uri';
import {TPromise} from 'vs/base/common/winjs.base';
import {IDisposable, dispose} from 'vs/base/common/lifecycle';
import Event, {Emitter} from 'vs/base/common/event';
import {addDisposableListener, addClass} from 'vs/base/browser/dom';
import {isLightTheme, isDarkTheme} from 'vs/platform/theme/common/themes';
import {CommandsRegistry} from 'vs/platform/commands/common/commands';
@ -45,8 +46,10 @@ export default class Webview {
private _webview: WebviewElement;
private _ready: TPromise<this>;
private _disposables: IDisposable[];
private _onDidClickLink = new Emitter<URI>();
private _onDidLoadContent = new Emitter<{ stats: any }>();
constructor(private _parent: HTMLElement, private _styleElement: Element, onDidClickLink:(uri:URI)=>any) {
constructor(private _parent: HTMLElement, private _styleElement: Element) {
this._webview = <any>document.createElement('webview');
this._webview.style.width = '100%';
@ -80,12 +83,14 @@ export default class Webview {
addDisposableListener(this._webview, 'ipc-message', (event) => {
if (event.channel === 'did-click-link') {
let [uri] = event.args;
onDidClickLink(URI.parse(uri));
this._onDidClickLink.fire(URI.parse(uri));
return;
}
if (event.channel === 'did-set-content') {
this._webview.style.opacity = '';
let [stats] = event.args;
this._onDidLoadContent.fire({ stats });
return;
}
})
@ -95,10 +100,20 @@ export default class Webview {
}
dispose(): void {
this._onDidClickLink.dispose();
this._onDidLoadContent.dispose();
this._disposables = dispose(this._disposables);
this._webview.parentElement.removeChild(this._webview);
}
get onDidClickLink(): Event<URI> {
return this._onDidClickLink.event;
}
get onDidLoadContent(): Event<{ stats: any }> {
return this._onDidLoadContent.event;
}
private _send(channel: string, ...args: any[]): void {
this._ready
.then(() => this._webview.send(channel, ...args))