From cd8078c4df2df28aef6c194b255568579884df75 Mon Sep 17 00:00:00 2001 From: francis-andrade Date: Sun, 3 Dec 2017 16:40:15 +0000 Subject: [PATCH 01/63] Fixes issue #16228 --- .../bracketMatching/bracketMatching.ts | 20 ++++++++++++++++--- 1 file changed, 17 insertions(+), 3 deletions(-) diff --git a/src/vs/editor/contrib/bracketMatching/bracketMatching.ts b/src/vs/editor/contrib/bracketMatching/bracketMatching.ts index fbd1a37d39c..5df1f747a6f 100644 --- a/src/vs/editor/contrib/bracketMatching/bracketMatching.ts +++ b/src/vs/editor/contrib/bracketMatching/bracketMatching.ts @@ -16,10 +16,19 @@ import { RunOnceScheduler } from 'vs/base/common/async'; import * as editorCommon from 'vs/editor/common/editorCommon'; import { registerEditorAction, registerEditorContribution, ServicesAccessor, EditorAction } from 'vs/editor/browser/editorExtensions'; import { EditorContextKeys } from 'vs/editor/common/editorContextKeys'; -import { registerThemingParticipant } from 'vs/platform/theme/common/themeService'; -import { editorBracketMatchBackground, editorBracketMatchBorder } from 'vs/editor/common/view/editorColorRegistry'; +import { registerThemingParticipant, themeColorFromId} from 'vs/platform/theme/common/themeService'; +import { editorBracketMatchBackground, editorBracketMatchBorder} from 'vs/editor/common/view/editorColorRegistry'; import { ModelDecorationOptions } from 'vs/editor/common/model/textModelWithDecorations'; import { ICodeEditor } from 'vs/editor/browser/editorBrowser'; +import { registerColor, overviewRulerSelectionHighlightForeground } from 'vs/platform/theme/common/colorRegistry'; + + +export const editorWordHighlight = registerColor('editor.wordHighlightBackground', { dark: '#575757B8', light: '#57575740', hc: null }, nls.localize('wordHighlight', 'Background color of a symbol during read-access, like reading a variable.')); +export const editorWordHighlightStrong = registerColor('editor.wordHighlightStrongBackground', { dark: '#004972B8', light: '#0e639c40', hc: null }, nls.localize('wordHighlightStrong', 'Background color of a symbol during write-access, like writing to a variable.')); + +export const overviewRulerWordHighlightForeground = registerColor('editorOverviewRuler.wordHighlightForeground', { dark: '#A0A0A0', light: '#A0A0A0', hc: '#A0A0A0' }, nls.localize('overviewRulerWordHighlightForeground', 'Overview ruler marker color for symbol highlights.')); +export const overviewRulerWordHighlightStrongForeground = registerColor('editorOverviewRuler.wordHighlightStrongForeground', { dark: '#C0A0C0', light: '#C0A0C0', hc: '#C0A0C0' }, nls.localize('overviewRulerWordHighlightStrongForeground', 'Overview ruler marker color for write-access symbol highlights.')); + class SelectBracketAction extends EditorAction { constructor() { @@ -150,7 +159,12 @@ export class BracketMatchingController extends Disposable implements editorCommo private static readonly _DECORATION_OPTIONS = ModelDecorationOptions.register({ stickiness: editorCommon.TrackedRangeStickiness.NeverGrowsWhenTypingAtEdges, - className: 'bracket-match' + className: 'bracket-match', + overviewRuler: { + color: themeColorFromId(overviewRulerSelectionHighlightForeground), + darkColor: themeColorFromId(overviewRulerSelectionHighlightForeground), + position: editorCommon.OverviewRulerLane.Center + } }); private _updateBrackets(): void { From 8e93e7e47b632d0cbc91637720a4e6b034747087 Mon Sep 17 00:00:00 2001 From: francis-andrade Date: Wed, 6 Dec 2017 13:08:45 +0000 Subject: [PATCH 02/63] Fixed Identation --- src/vs/editor/contrib/bracketMatching/bracketMatching.ts | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/src/vs/editor/contrib/bracketMatching/bracketMatching.ts b/src/vs/editor/contrib/bracketMatching/bracketMatching.ts index 5df1f747a6f..5e6d3e66eed 100644 --- a/src/vs/editor/contrib/bracketMatching/bracketMatching.ts +++ b/src/vs/editor/contrib/bracketMatching/bracketMatching.ts @@ -16,11 +16,11 @@ import { RunOnceScheduler } from 'vs/base/common/async'; import * as editorCommon from 'vs/editor/common/editorCommon'; import { registerEditorAction, registerEditorContribution, ServicesAccessor, EditorAction } from 'vs/editor/browser/editorExtensions'; import { EditorContextKeys } from 'vs/editor/common/editorContextKeys'; -import { registerThemingParticipant, themeColorFromId} from 'vs/platform/theme/common/themeService'; -import { editorBracketMatchBackground, editorBracketMatchBorder} from 'vs/editor/common/view/editorColorRegistry'; +import { registerThemingParticipant, themeColorFromId } from 'vs/platform/theme/common/themeService'; +import { editorBracketMatchBackground, editorBracketMatchBorder } from 'vs/editor/common/view/editorColorRegistry'; import { ModelDecorationOptions } from 'vs/editor/common/model/textModelWithDecorations'; import { ICodeEditor } from 'vs/editor/browser/editorBrowser'; -import { registerColor, overviewRulerSelectionHighlightForeground } from 'vs/platform/theme/common/colorRegistry'; +import { registerColor, overviewRulerSelectionHighlightForeground } from 'vs/platform/theme/common/colorRegistry'; export const editorWordHighlight = registerColor('editor.wordHighlightBackground', { dark: '#575757B8', light: '#57575740', hc: null }, nls.localize('wordHighlight', 'Background color of a symbol during read-access, like reading a variable.')); From e932b8ad9cf1c70762d89cdcbf66fcf5776a157a Mon Sep 17 00:00:00 2001 From: Matt Bierner Date: Wed, 10 Jan 2018 14:26:43 -0800 Subject: [PATCH 03/63] Add rename/create/delete file to workspaced edit Fixes #10659 Allows workspace edits to also change files in the workspace --- .../vscode-api-tests/src/workspace.test.ts | 14 ++++ src/vs/editor/browser/services/bulkEdit.ts | 71 ++++++++++++++++--- src/vs/editor/common/modes.ts | 14 ++++ .../contrib/quickFix/quickFixCommands.ts | 11 +-- src/vs/monaco.d.ts | 13 ++++ src/vs/vscode.d.ts | 38 ++++++++++ .../api/electron-browser/mainThreadEditors.ts | 17 +++-- src/vs/workbench/api/node/extHost.protocol.ts | 8 ++- .../workbench/api/node/extHostTextEditors.ts | 2 +- .../api/node/extHostTypeConverters.ts | 7 +- src/vs/workbench/api/node/extHostTypes.ts | 53 +++++++++++++- .../electron-browser/api/extHostTypes.test.ts | 13 ++++ .../api/mainThreadEditors.test.ts | 66 ++++++++++++++++- 13 files changed, 304 insertions(+), 23 deletions(-) diff --git a/extensions/vscode-api-tests/src/workspace.test.ts b/extensions/vscode-api-tests/src/workspace.test.ts index d4c4ae7013c..4fccf98385b 100644 --- a/extensions/vscode-api-tests/src/workspace.test.ts +++ b/extensions/vscode-api-tests/src/workspace.test.ts @@ -505,4 +505,18 @@ suite('workspace-namespace', () => { return vscode.workspace.applyEdit(edit); }); }); + + + test('applyEdit should fail when editing deleted resource', async () => { + const resource = await createRandomFile(); + + let edit = new vscode.WorkspaceEdit(); + edit.deleteResource(resource); + try { + edit.insert(resource, new vscode.Position(0, 0), ''); + assert.fail(false, 'Should disallow edit of deleted resource'); + } catch { + // noop + } + }); }); diff --git a/src/vs/editor/browser/services/bulkEdit.ts b/src/vs/editor/browser/services/bulkEdit.ts index bfe4d9c4df3..d5052d8c706 100644 --- a/src/vs/editor/browser/services/bulkEdit.ts +++ b/src/vs/editor/browser/services/bulkEdit.ts @@ -18,6 +18,13 @@ import { Selection, ISelection } from 'vs/editor/common/core/selection'; import { IIdentifiedSingleEditOperation, ITextModel, EndOfLineSequence } from 'vs/editor/common/model'; import { IProgressRunner } from 'vs/platform/progress/common/progress'; import { ICodeEditor } from 'vs/editor/browser/editorBrowser'; +import { IResourceRename, IResourceCreate } from 'vs/editor/common/modes'; + +export interface IResourceFileEdit { + readonly renamedResources: { from: URI, to }[]; + readonly createdResources: { uri: URI, contents: string }[]; + readonly deletedResources: URI[]; +} export interface IResourceEdit { resource: URI; @@ -196,12 +203,24 @@ class BulkEditModel implements IDisposable { private _sourceSelections: Selection[]; private _sourceModelTask: SourceModelEditTask; - constructor(textModelResolverService: ITextModelService, sourceModel: URI, sourceSelections: Selection[], edits: IResourceEdit[], private progress: IProgressRunner = null) { + constructor( + textModelResolverService: ITextModelService, + sourceModel: URI, + sourceSelections: Selection[], + edits: IResourceEdit[], + private progress: IProgressRunner, + private renames: IResourceRename[], + private creates: IResourceCreate[], + private deletes: URI[], + private fileService: IFileService + ) { this._textModelResolverService = textModelResolverService; this._sourceModel = sourceModel; this._sourceSelections = sourceSelections; this._sourceModelTask = null; + this._numberOfResourcesToModify += this.renames.length + this.deletes.length + this.creates.length; + for (let edit of edits) { this._addEdit(edit); } @@ -216,7 +235,7 @@ class BulkEditModel implements IDisposable { array.push(edit); } - public prepare(): TPromise { + public async prepare(): TPromise { if (this._tasks) { throw new Error('illegal state - already prepared'); @@ -229,6 +248,15 @@ class BulkEditModel implements IDisposable { this.progress.total(this._numberOfResourcesToModify * 2); } + await TPromise.join(this.renames.map(rename => + this.fileService.moveFile(rename.from, rename.to))); + + await TPromise.join(this.creates.map(create => + this.fileService.createFile(create.uri, create.contents))); + + await TPromise.join(this.deletes.map(uri => + this.fileService.del(uri))); + forEach(this._edits, entry => { const promise = this._textModelResolverService.createModelReference(URI.parse(entry.key)).then(ref => { const model = ref.object; @@ -256,8 +284,9 @@ class BulkEditModel implements IDisposable { promises.push(promise); }); + await TPromise.join(promises); - return TPromise.join(promises).then(_ => this); + return this; } public apply(): Selection { @@ -284,20 +313,29 @@ class BulkEditModel implements IDisposable { export interface BulkEdit { progress(progress: IProgressRunner): void; add(edit: IResourceEdit[]): void; + addRename(edit: IResourceRename[]): void; + addCreate(edit: IResourceCreate[]): void; + addDelete(edit: URI[]): void; finish(): TPromise; ariaMessage(): string; } -export function bulkEdit(textModelResolverService: ITextModelService, editor: ICodeEditor, edits: IResourceEdit[], fileService?: IFileService, progress: IProgressRunner = null): TPromise { +export function bulkEdit(textModelResolverService: ITextModelService, editor: ICodeEditor, edits: IResourceEdit[], fileService: IFileService, resourceFileEdits?: IResourceFileEdit): TPromise { let bulk = createBulkEdit(textModelResolverService, editor, fileService); bulk.add(edits); - bulk.progress(progress); + bulk.addRename(resourceFileEdits.renamedResources); + bulk.addCreate(resourceFileEdits.createdResources); + bulk.addDelete(resourceFileEdits.deletedResources); + bulk.progress(null); return bulk.finish(); } export function createBulkEdit(textModelResolverService: ITextModelService, editor?: ICodeEditor, fileService?: IFileService): BulkEdit { let all: IResourceEdit[] = []; + const renames: IResourceRename[] = []; + const creates: IResourceCreate[] = []; + const deletes: URI[] = []; let recording = new ChangeRecorder(fileService).start(); let progressRunner: IProgressRunner; @@ -309,6 +347,18 @@ export function createBulkEdit(textModelResolverService: ITextModelService, edit all.push(...edits); } + function addRename(edits: IResourceRename[]): void { + renames.push(...edits); + } + + function addCreate(edits: IResourceCreate[]): void { + creates.push(...edits); + } + + function addDelete(edits: URI[]): void { + deletes.push(...edits); + } + function getConcurrentEdits() { let names: string[]; for (let edit of all) { @@ -327,7 +377,7 @@ export function createBulkEdit(textModelResolverService: ITextModelService, edit function finish(): TPromise { - if (all.length === 0) { + if (all.length === 0 && renames.length === 0 && creates.length === 0 && deletes.length === 0) { return TPromise.as(undefined); } @@ -344,9 +394,9 @@ export function createBulkEdit(textModelResolverService: ITextModelService, edit selections = editor.getSelections(); } - const model = new BulkEditModel(textModelResolverService, uri, selections, all, progressRunner); + const model = new BulkEditModel(textModelResolverService, uri, selections, all, progressRunner, renames, creates, deletes, fileService); - return model.prepare().then(_ => { + return model.prepare().then(async _ => { let concurrentEdits = getConcurrentEdits(); if (concurrentEdits) { @@ -355,7 +405,7 @@ export function createBulkEdit(textModelResolverService: ITextModelService, edit recording.stop(); - const result = model.apply(); + const result = await model.apply(); model.dispose(); return result; }); @@ -376,6 +426,9 @@ export function createBulkEdit(textModelResolverService: ITextModelService, edit return { progress, add, + addRename, + addCreate, + addDelete, finish, ariaMessage }; diff --git a/src/vs/editor/common/modes.ts b/src/vs/editor/common/modes.ts index 1693993e6db..9aa2e6ae1ba 100644 --- a/src/vs/editor/common/modes.ts +++ b/src/vs/editor/common/modes.ts @@ -821,8 +821,22 @@ export interface IResourceEdit { range: IRange; newText: string; } + +export interface IResourceRename { + readonly from: URI; + readonly to: URI; +} + +export interface IResourceCreate { + readonly uri: URI; + readonly contents: string; +} + export interface WorkspaceEdit { edits: IResourceEdit[]; + renamedResources?: IResourceRename[]; + createdResources?: IResourceCreate[]; + deletedResources?: URI[]; rejectReason?: string; } export interface RenameProvider { diff --git a/src/vs/editor/contrib/quickFix/quickFixCommands.ts b/src/vs/editor/contrib/quickFix/quickFixCommands.ts index 2d067db0bf0..f012b11a4ca 100644 --- a/src/vs/editor/contrib/quickFix/quickFixCommands.ts +++ b/src/vs/editor/contrib/quickFix/quickFixCommands.ts @@ -22,9 +22,10 @@ import { LightBulbWidget } from './lightBulbWidget'; import { QuickFixModel, QuickFixComputeEvent } from './quickFixModel'; import { TPromise } from 'vs/base/common/winjs.base'; import { CodeAction } from 'vs/editor/common/modes'; -import { createBulkEdit } from 'vs/editor/browser/services/bulkEdit'; +import { bulkEdit } from 'vs/editor/browser/services/bulkEdit'; import { IFileService } from 'vs/platform/files/common/files'; import { ITextModelService } from 'vs/editor/common/services/resolverService'; +import URI from 'vs/base/common/uri'; export class QuickFixController implements IEditorContribution { @@ -112,9 +113,11 @@ export class QuickFixController implements IEditorContribution { private async _onApplyCodeAction(action: CodeAction): TPromise { if (action.edit) { - const edit = createBulkEdit(this._textModelService, this._editor, this._fileService); - edit.add(action.edit.edits); - await edit.finish(); + await bulkEdit(this._textModelService, this._editor, action.edit.edits, this._fileService, { + createdResources: action.edit.createdResources.map(create => ({ uri: URI.revive(create.uri), contents: create.contents })), + renamedResources: action.edit.renamedResources.map(rename => ({ from: URI.revive(rename.from), to: URI.revive(rename.to) })), + deletedResources: action.edit.deletedResources.map(URI.revive) + }); } if (action.command) { diff --git a/src/vs/monaco.d.ts b/src/vs/monaco.d.ts index 81d3e99523b..58eb60dd225 100644 --- a/src/vs/monaco.d.ts +++ b/src/vs/monaco.d.ts @@ -4913,8 +4913,21 @@ declare module monaco.languages { newText: string; } + export interface IResourceRename { + readonly from: Uri; + readonly to: Uri; + } + + export interface IResourceCreate { + readonly uri: Uri; + readonly contents: string; + } + export interface WorkspaceEdit { edits: IResourceEdit[]; + renamedResources?: IResourceRename[]; + createdResources?: IResourceCreate[]; + deletedResources?: Uri[]; rejectReason?: string; } diff --git a/src/vs/vscode.d.ts b/src/vs/vscode.d.ts index 0920acba747..ad5cb36dc8c 100644 --- a/src/vs/vscode.d.ts +++ b/src/vs/vscode.d.ts @@ -2430,6 +2430,29 @@ declare module 'vscode' { */ readonly size: number; + /** + * Renames a given resource in the workspace. + * + * @param from Uri of current resource. + * @param to Uri of renamed resource. + */ + renameResource(from: Uri, to: Uri): void; + + /** + * Create a new resource in the workspace. + * + * @param uri Uri of resource to create. + * @param contents New file contents. + */ + createResource(uri: Uri, contents: String): void; + + /** + * Delete a given resource in the workspace. + * + * @param uri Uri of resource to delete. + */ + deleteResource(uri: Uri): void; + /** * Replace the given range with given text for the given resource. * @@ -2485,6 +2508,21 @@ declare module 'vscode' { * @return An array of `[Uri, TextEdit[]]`-tuples. */ entries(): [Uri, TextEdit[]][]; + + /** + * Get all resource rename edits. + */ + readonly renamedResources: { from: Uri, to: Uri }[]; + + /** + * Get all resource create edits. + */ + readonly createdResources: { uri: Uri, contents: string }[]; + + /** + * Get all resource delete edits. + */ + readonly deletedResources: Uri[]; } /** diff --git a/src/vs/workbench/api/electron-browser/mainThreadEditors.ts b/src/vs/workbench/api/electron-browser/mainThreadEditors.ts index 0952ff3985f..1af196d2491 100644 --- a/src/vs/workbench/api/electron-browser/mainThreadEditors.ts +++ b/src/vs/workbench/api/electron-browser/mainThreadEditors.ts @@ -15,7 +15,7 @@ import { IWorkbenchEditorService } from 'vs/workbench/services/editor/common/edi import { IEditorGroupService } from 'vs/workbench/services/group/common/groupService'; import { Position as EditorPosition, ITextEditorOptions } from 'vs/platform/editor/common/editor'; import { MainThreadTextEditor } from './mainThreadEditor'; -import { ITextEditorConfigurationUpdate, TextEditorRevealType, IApplyEditsOptions, IUndoStopOptions } from 'vs/workbench/api/node/extHost.protocol'; +import { ITextEditorConfigurationUpdate, TextEditorRevealType, IApplyEditsOptions, IUndoStopOptions, IResourceFileEdit } from 'vs/workbench/api/node/extHost.protocol'; import { MainThreadDocumentsAndEditors } from './mainThreadDocumentsAndEditors'; import { equals as objectEquals } from 'vs/base/common/objects'; import { ExtHostContext, MainThreadEditorsShape, ExtHostEditorsShape, ITextDocumentShowOptions, ITextEditorPositionData, IExtHostContext, IWorkspaceResourceEdit } from '../node/extHost.protocol'; @@ -210,7 +210,7 @@ export class MainThreadEditors implements MainThreadEditorsShape { return TPromise.as(this._documentsAndEditors.getEditor(id).applyEdits(modelVersionId, edits, opts)); } - $tryApplyWorkspaceEdit(workspaceResourceEdits: IWorkspaceResourceEdit[]): TPromise { + $tryApplyWorkspaceEdit(workspaceResourceEdits: IWorkspaceResourceEdit[], resourceFileEdits?: IResourceFileEdit): TPromise { // First check if loaded models were not changed in the meantime for (let i = 0, len = workspaceResourceEdits.length; i < len; i++) { @@ -253,8 +253,17 @@ export class MainThreadEditors implements MainThreadEditorsShape { } } - return bulkEdit(this._textModelResolverService, codeEditor, resourceEdits, this._fileService) - .then(() => true); + return bulkEdit( + this._textModelResolverService, + codeEditor, + resourceEdits, + this._fileService, + resourceFileEdits ? { + renamedResources: resourceFileEdits.renamedResources.map(entry => ({ from: URI.revive(entry.from), to: URI.revive(entry.to) })), + createdResources: resourceFileEdits.createdResources.map(entry => ({ uri: URI.revive(entry.uri), contents: entry.contents })), + deletedResources: resourceFileEdits.deletedResources.map(URI.revive) + } : undefined + ).then(() => true); } $tryInsertSnippet(id: string, template: string, ranges: IRange[], opts: IUndoStopOptions): TPromise { diff --git a/src/vs/workbench/api/node/extHost.protocol.ts b/src/vs/workbench/api/node/extHost.protocol.ts index d189f463f6b..0d3ad1d8df1 100644 --- a/src/vs/workbench/api/node/extHost.protocol.ts +++ b/src/vs/workbench/api/node/extHost.protocol.ts @@ -210,6 +210,12 @@ export interface IWorkspaceResourceEdit { }[]; } +export interface IResourceFileEdit { + renamedResources: { from: UriComponents, to: UriComponents }[]; + createdResources: { uri: UriComponents, contents: string }[]; + deletedResources: UriComponents[]; +} + export interface MainThreadEditorsShape extends IDisposable { $tryShowTextDocument(resource: UriComponents, options: ITextDocumentShowOptions): TPromise; $registerTextEditorDecorationType(key: string, options: editorCommon.IDecorationRenderOptions): void; @@ -222,7 +228,7 @@ export interface MainThreadEditorsShape extends IDisposable { $tryRevealRange(id: string, range: IRange, revealType: TextEditorRevealType): TPromise; $trySetSelections(id: string, selections: ISelection[]): TPromise; $tryApplyEdits(id: string, modelVersionId: number, edits: ISingleEditOperation[], opts: IApplyEditsOptions): TPromise; - $tryApplyWorkspaceEdit(workspaceResourceEdits: IWorkspaceResourceEdit[]): TPromise; + $tryApplyWorkspaceEdit(workspaceResourceEdits: IWorkspaceResourceEdit[], resourceFileEdits?: IResourceFileEdit): TPromise; $tryInsertSnippet(id: string, template: string, selections: IRange[], opts: IUndoStopOptions): TPromise; $getDiffInformation(id: string): TPromise; } diff --git a/src/vs/workbench/api/node/extHostTextEditors.ts b/src/vs/workbench/api/node/extHostTextEditors.ts index 35ad03c3a49..79e50c129a2 100644 --- a/src/vs/workbench/api/node/extHostTextEditors.ts +++ b/src/vs/workbench/api/node/extHostTextEditors.ts @@ -121,7 +121,7 @@ export class ExtHostEditors implements ExtHostEditorsShape { workspaceResourceEdits.push(workspaceResourceEdit); } - return this._proxy.$tryApplyWorkspaceEdit(workspaceResourceEdits); + return this._proxy.$tryApplyWorkspaceEdit(workspaceResourceEdits, edit); } // --- called from main thread diff --git a/src/vs/workbench/api/node/extHostTypeConverters.ts b/src/vs/workbench/api/node/extHostTypeConverters.ts index 46b71714596..f1379708459 100644 --- a/src/vs/workbench/api/node/extHostTypeConverters.ts +++ b/src/vs/workbench/api/node/extHostTypeConverters.ts @@ -228,7 +228,12 @@ export const TextEdit = { export namespace WorkspaceEdit { export function from(value: vscode.WorkspaceEdit): modes.WorkspaceEdit { - const result: modes.WorkspaceEdit = { edits: [] }; + const result: modes.WorkspaceEdit = { + edits: [], + renamedResources: value.renamedResources, + createdResources: value.createdResources, + deletedResources: value.deletedResources + }; for (let entry of value.entries()) { let [uri, textEdits] = entry; for (let textEdit of textEdits) { diff --git a/src/vs/workbench/api/node/extHostTypes.ts b/src/vs/workbench/api/node/extHostTypes.ts index 154012715bf..a7b250b6d69 100644 --- a/src/vs/workbench/api/node/extHostTypes.ts +++ b/src/vs/workbench/api/node/extHostTypes.ts @@ -494,8 +494,43 @@ export class TextEdit { export class WorkspaceEdit { private _values: [URI, TextEdit[]][] = []; + private readonly _resourcesCreated: { uri: URI, contents: string }[] = []; + private readonly _resourcesDeleted: URI[] = []; + private readonly _resourcesRenamed: { from: URI, to: URI }[] = []; private _index = new Map(); + private _validResources = new Set(); + private _invalidResources = new Set(); + + + createResource(uri: URI, contents: string): void { + if (this._invalidResources.has(uri)) { + throw illegalArgument('Cannot create already deleted resource'); + } + this._resourcesCreated.push({ uri: uri, contents: contents }); + this._validResources.add(uri); + } + + deleteResource(uri: URI): void { + if (this._validResources.has(uri)) { + throw illegalArgument('Cannot delete newly created resource'); + } + this._resourcesDeleted.push(uri); + this._invalidResources.add(uri); + } + + renameResource(uri: URI, newUri: URI): void { + if (this._validResources.has(uri)) { + throw illegalArgument('Cannot delete newly created resource'); + } + if (this._invalidResources.has(newUri)) { + throw illegalArgument('Cannot create already deleted resource'); + } + this._resourcesRenamed.push({ from: uri, to: newUri }); + this._invalidResources.add(uri); + this._validResources.add(newUri); + } + replace(uri: URI, range: Range, newText: string): void { let edit = new TextEdit(range, newText); let array = this.get(uri); @@ -519,6 +554,10 @@ export class WorkspaceEdit { } set(uri: URI, edits: TextEdit[]): void { + if (this._invalidResources.has(uri)) { + throw illegalArgument('Cannot modify already deleted resource'); + } + this._validResources.add(uri); const idx = this._index.get(uri.toString()); if (typeof idx === 'undefined') { let newLen = this._values.push([uri, edits]); @@ -537,8 +576,20 @@ export class WorkspaceEdit { return this._values; } + get createdResources(): { uri: URI, contents: string }[] { + return this._resourcesCreated; + } + + get deletedResources(): URI[] { + return this._resourcesDeleted; + } + + get renamedResources(): { from: URI, to: URI }[] { + return this._resourcesRenamed; + } + get size(): number { - return this._values.length; + return this._values.length + this._resourcesCreated.length + this._resourcesRenamed.length + this._resourcesDeleted.length; } toJSON(): any { diff --git a/src/vs/workbench/test/electron-browser/api/extHostTypes.test.ts b/src/vs/workbench/test/electron-browser/api/extHostTypes.test.ts index 3cd1208f264..3e99b175fc7 100644 --- a/src/vs/workbench/test/electron-browser/api/extHostTypes.test.ts +++ b/src/vs/workbench/test/electron-browser/api/extHostTypes.test.ts @@ -362,6 +362,19 @@ suite('ExtHostTypes', function () { }); + test('WorkspaceEdit should fail when editing deleted resource', () => { + const resource = URI.parse('file:///a.ts'); + + const edit = new types.WorkspaceEdit(); + edit.deleteResource(resource); + try { + edit.insert(resource, new types.Position(0, 0), ''); + assert.fail(false, 'Should disallow edit of deleted resource'); + } catch { + // expected + } + }); + test('DocumentLink', function () { assert.throws(() => new types.DocumentLink(null, null)); assert.throws(() => new types.DocumentLink(new types.Range(1, 1, 1, 1), null)); diff --git a/src/vs/workbench/test/electron-browser/api/mainThreadEditors.test.ts b/src/vs/workbench/test/electron-browser/api/mainThreadEditors.test.ts index 73887be8ea3..b725c6163bd 100644 --- a/src/vs/workbench/test/electron-browser/api/mainThreadEditors.test.ts +++ b/src/vs/workbench/test/electron-browser/api/mainThreadEditors.test.ts @@ -23,6 +23,9 @@ import { Range } from 'vs/editor/common/core/range'; import { Position } from 'vs/editor/common/core/position'; import { IModelService } from 'vs/editor/common/services/modelService'; import { EditOperation } from 'vs/editor/common/core/editOperation'; +import { TestFileService } from 'vs/workbench/test/workbenchTestServices'; +import { TPromise } from 'vs/base/common/winjs.base'; +import { IFileStat } from 'vs/platform/files/common/files'; suite('MainThreadEditors', () => { @@ -31,10 +34,35 @@ suite('MainThreadEditors', () => { let modelService: IModelService; let editors: MainThreadEditors; + const movedResources = new Map(); + const createdResources = new Map(); + const deletedResources = new Set(); + setup(() => { const configService = new TestConfigurationService(); modelService = new ModelServiceImpl(null, configService); const codeEditorService = new TestCodeEditorService(); + + movedResources.clear(); + createdResources.clear(); + deletedResources.clear(); + const fileService = new TestFileService(); + + fileService.moveFile = async (from, target): TPromise => { + assert(!movedResources.has(from)); + movedResources.set(from, target); + return createMockFileStat(target); + }; + fileService.createFile = async (uri, contents): TPromise => { + assert(!createdResources.has(uri)); + createdResources.set(uri, contents); + return createMockFileStat(uri); + }; + fileService.del = async (uri): TPromise => { + assert(!deletedResources.has(uri)); + deletedResources.add(uri); + }; + const textFileService = new class extends mock() { isDirty() { return false; } models = { @@ -69,7 +97,7 @@ suite('MainThreadEditors', () => { workbenchEditorService, codeEditorService, null, - null, + fileService, null, null, editorGroupService, @@ -82,7 +110,7 @@ suite('MainThreadEditors', () => { workbenchEditorService, editorGroupService, null, - null, + fileService, modelService ); }); @@ -107,4 +135,38 @@ suite('MainThreadEditors', () => { assert.equal(result, false); }); }); + + test(`applyWorkspaceEdit with only resource edit`, () => { + let model = modelService.createModel('something', null, resource); + + let workspaceResourceEdit: IWorkspaceResourceEdit = { + resource: resource, + modelVersionId: model.getVersionId(), + edits: [] + }; + + return editors.$tryApplyWorkspaceEdit([workspaceResourceEdit], { + renamedResources: [{ from: resource, to: resource }], + createdResources: [{ uri: resource, contents: 'foo' }], + deletedResources: [resource] + }).then((result) => { + assert.equal(result, true); + assert.equal(movedResources.get(resource), resource); + assert.equal(createdResources.get(resource), 'foo'); + assert.equal(deletedResources.has(resource), true); + }); + }); }); + + +function createMockFileStat(target: URI): IFileStat { + return { + etag: '', + hasChildren: false, + isDirectory: false, + name: target.path, + mtime: 0, + resource: target + }; +} + From 519b4723d586d364cf4b34afea3c5c759ba1ef23 Mon Sep 17 00:00:00 2001 From: Matt Bierner Date: Fri, 12 Jan 2018 14:12:52 -0800 Subject: [PATCH 04/63] Fix potentiall undefined ref --- .../vscode-api-tests/src/workspace.test.ts | 29 ++++++++++++++++++- .../workbench/api/node/extHostTextEditors.ts | 6 +++- 2 files changed, 33 insertions(+), 2 deletions(-) diff --git a/extensions/vscode-api-tests/src/workspace.test.ts b/extensions/vscode-api-tests/src/workspace.test.ts index 4fccf98385b..d698bba1eab 100644 --- a/extensions/vscode-api-tests/src/workspace.test.ts +++ b/extensions/vscode-api-tests/src/workspace.test.ts @@ -10,6 +10,7 @@ import * as vscode from 'vscode'; import { createRandomFile, deleteFile, closeAllEditors, pathEquals } from './utils'; import { join, basename } from 'path'; import * as fs from 'fs'; +import { Uri } from 'vscode'; suite('workspace-namespace', () => { @@ -510,7 +511,7 @@ suite('workspace-namespace', () => { test('applyEdit should fail when editing deleted resource', async () => { const resource = await createRandomFile(); - let edit = new vscode.WorkspaceEdit(); + const edit = new vscode.WorkspaceEdit(); edit.deleteResource(resource); try { edit.insert(resource, new vscode.Position(0, 0), ''); @@ -519,4 +520,30 @@ suite('workspace-namespace', () => { // noop } }); + + test('applyEdit should fail when renaming deleted resource', async () => { + const resource = await createRandomFile(); + + const edit = new vscode.WorkspaceEdit(); + edit.deleteResource(resource); + try { + edit.renameResource(resource, resource); + assert.fail(false, 'Should disallow rename of deleted resource'); + } catch { + // noop + } + }); + + test('applyEdit should fail when editing renamed from resource', async () => { + const resource = await createRandomFile(); + const newResource = Uri.parse(resource.fsPath + '.1'); + const edit = new vscode.WorkspaceEdit(); + edit.renameResource(resource, newResource); + try { + edit.insert(resource, new vscode.Position(0, 0), ''); + assert.fail(false, 'Should disallow editing renamed file'); + } catch { + // noop + } + }); }); diff --git a/src/vs/workbench/api/node/extHostTextEditors.ts b/src/vs/workbench/api/node/extHostTextEditors.ts index 79e50c129a2..2b3738a27f3 100644 --- a/src/vs/workbench/api/node/extHostTextEditors.ts +++ b/src/vs/workbench/api/node/extHostTextEditors.ts @@ -121,7 +121,11 @@ export class ExtHostEditors implements ExtHostEditorsShape { workspaceResourceEdits.push(workspaceResourceEdit); } - return this._proxy.$tryApplyWorkspaceEdit(workspaceResourceEdits, edit); + return this._proxy.$tryApplyWorkspaceEdit(workspaceResourceEdits, { + createdResources: edit.createdResources, + renamedResources: edit.renamedResources, + deletedResources: edit.deletedResources + }); } // --- called from main thread From dc31fa213be87c0c937324ec608e42157dbb4418 Mon Sep 17 00:00:00 2001 From: Johannes Rieken Date: Fri, 19 Jan 2018 17:54:54 +0100 Subject: [PATCH 05/63] support interleaving file and text changes, basically rewrite bulk edit... --- src/vs/editor/browser/services/bulkEdit.ts | 423 ++++++++---------- src/vs/editor/common/modes.ts | 44 +- .../contrib/quickFix/quickFixCommands.ts | 9 +- .../contrib/quickFix/test/quickFix.test.ts | 4 +- src/vs/editor/contrib/rename/rename.ts | 8 +- src/vs/monaco.d.ts | 26 +- src/vs/platform/progress/common/progress.ts | 6 + src/vs/vscode.d.ts | 56 ++- .../api/electron-browser/mainThreadEditors.ts | 53 +-- .../mainThreadLanguageFeatures.ts | 18 +- src/vs/workbench/api/node/extHost.protocol.ts | 53 +-- .../workbench/api/node/extHostApiCommands.ts | 6 +- .../node/extHostDocumentSaveParticipant.ts | 14 +- .../api/node/extHostLanguageFeatures.ts | 8 +- .../workbench/api/node/extHostTextEditors.ts | 43 +- .../api/node/extHostTypeConverters.ts | 36 +- src/vs/workbench/api/node/extHostTypes.ts | 100 ++--- .../parts/search/browser/replaceService.ts | 18 +- .../extHostDocumentSaveParticipant.test.ts | 30 +- .../api/extHostLanguageFeatures.test.ts | 5 +- .../api/extHostTextEditors.test.ts | 15 +- .../electron-browser/api/extHostTypes.test.ts | 50 ++- .../api/mainThreadEditors.test.ts | 58 ++- 23 files changed, 499 insertions(+), 584 deletions(-) diff --git a/src/vs/editor/browser/services/bulkEdit.ts b/src/vs/editor/browser/services/bulkEdit.ts index d5052d8c706..2be87d824bf 100644 --- a/src/vs/editor/browser/services/bulkEdit.ts +++ b/src/vs/editor/browser/services/bulkEdit.ts @@ -5,75 +5,46 @@ 'use strict'; import * as nls from 'vs/nls'; -import { flatten } from 'vs/base/common/arrays'; -import { IStringDictionary, forEach, values, groupBy, size } from 'vs/base/common/collections'; import { IDisposable, dispose, IReference } from 'vs/base/common/lifecycle'; import URI from 'vs/base/common/uri'; import { TPromise } from 'vs/base/common/winjs.base'; import { ITextModelService, ITextEditorModel } from 'vs/editor/common/services/resolverService'; -import { IFileService, IFileChange } from 'vs/platform/files/common/files'; +import { IFileService } from 'vs/platform/files/common/files'; import { EditOperation } from 'vs/editor/common/core/editOperation'; -import { Range, IRange } from 'vs/editor/common/core/range'; -import { Selection, ISelection } from 'vs/editor/common/core/selection'; +import { Range } from 'vs/editor/common/core/range'; +import { Selection } from 'vs/editor/common/core/selection'; import { IIdentifiedSingleEditOperation, ITextModel, EndOfLineSequence } from 'vs/editor/common/model'; -import { IProgressRunner } from 'vs/platform/progress/common/progress'; +import { IProgressRunner, emptyProgressRunner, IProgress } from 'vs/platform/progress/common/progress'; import { ICodeEditor } from 'vs/editor/browser/editorBrowser'; -import { IResourceRename, IResourceCreate } from 'vs/editor/common/modes'; +import { optional } from 'vs/platform/instantiation/common/instantiation'; +import { ResourceTextEdit, ResourceFileEdit, isResourceFileEdit } from 'vs/editor/common/modes'; +import { getPathLabel } from 'vs/base/common/labels'; -export interface IResourceFileEdit { - readonly renamedResources: { from: URI, to }[]; - readonly createdResources: { uri: URI, contents: string }[]; - readonly deletedResources: URI[]; -} -export interface IResourceEdit { - resource: URI; - range?: IRange; - newText: string; - newEol?: EndOfLineSequence; -} +abstract class IRecording { -interface IRecording { - stop(): void; - hasChanged(resource: URI): boolean; - allChanges(): IFileChange[]; -} - -class ChangeRecorder { - - private _fileService: IFileService; - - constructor(fileService?: IFileService) { - this._fileService = fileService; - } - - public start(): IRecording { - - const changes: IStringDictionary = Object.create(null); + static start(fileService: IFileService): IRecording { + const _changes = new Set(); let stop: IDisposable; - if (this._fileService) { - stop = this._fileService.onFileChanges((event) => { - event.changes.forEach(change => { - const key = String(change.resource); - let array = changes[key]; - - if (!array) { - changes[key] = array = []; - } - - array.push(change); - }); + if (fileService) { + // watch only when there is a fileservice available + stop = fileService.onFileChanges(event => { + for (const change of event.changes) { + _changes.add(change.resource.toString()); + } }); } return { - stop: () => { return stop && stop.dispose(); }, - hasChanged: (resource: URI) => !!changes[resource.toString()], - allChanges: () => flatten(values(changes)) + stop() { return dispose(stop); }, + hasChanged(resource) { return _changes.has(resource.toString()); } }; } + + abstract stop(): void; + abstract hasChanged(resource: URI): boolean; } class EditTask implements IDisposable { @@ -91,26 +62,34 @@ class EditTask implements IDisposable { this._edits = []; } - public addEdit(edit: IResourceEdit): void { - - if (typeof edit.newEol === 'number') { - // honor eol-change - this._newEol = edit.newEol; - } - - if (edit.range || edit.newText) { - // create edit operation - let range: Range; - if (!edit.range) { - range = this._model.getFullModelRange(); - } else { - range = Range.lift(edit.range); - } - this._edits.push(EditOperation.replaceMove(range, edit.newText)); + dispose() { + if (this._model) { + this._modelReference.dispose(); + this._modelReference = null; } } - public apply(): void { + addEdit(resourceEdit: ResourceTextEdit): void { + + for (const edit of resourceEdit.edits) { + if (typeof edit.eol === 'number') { + // honor eol-change + this._newEol = edit.eol; + } + if (edit.range || edit.text) { + // create edit operation + let range: Range; + if (!edit.range) { + range = this._model.getFullModelRange(); + } else { + range = Range.lift(edit.range); + } + this._edits.push(EditOperation.replaceMove(range, edit.text)); + } + } + } + + apply(): void { if (this._edits.length > 0) { this._edits = this._edits.map((value, index) => ({ value, index })).sort((a, b) => { @@ -167,16 +146,10 @@ class EditTask implements IDisposable { return [this._endCursorSelection]; } - public getEndCursorSelection(): Selection { + getEndCursorSelection(): Selection { return this._endCursorSelection; } - dispose() { - if (this._model) { - this._modelReference.dispose(); - this._modelReference = null; - } - } } class SourceModelEditTask extends EditTask { @@ -196,46 +169,42 @@ class SourceModelEditTask extends EditTask { class BulkEditModel implements IDisposable { private _textModelResolverService: ITextModelService; - private _numberOfResourcesToModify: number = 0; - private _edits: IStringDictionary = Object.create(null); + private _edits = new Map(); private _tasks: EditTask[]; private _sourceModel: URI; private _sourceSelections: Selection[]; private _sourceModelTask: SourceModelEditTask; + private _progress: IProgress; constructor( textModelResolverService: ITextModelService, - sourceModel: URI, - sourceSelections: Selection[], - edits: IResourceEdit[], - private progress: IProgressRunner, - private renames: IResourceRename[], - private creates: IResourceCreate[], - private deletes: URI[], - private fileService: IFileService + editor: ICodeEditor, + edits: ResourceTextEdit[], + progress: IProgress ) { this._textModelResolverService = textModelResolverService; - this._sourceModel = sourceModel; - this._sourceSelections = sourceSelections; - this._sourceModelTask = null; + this._sourceModel = editor ? editor.getModel().uri : undefined; + this._sourceSelections = editor ? editor.getSelections() : undefined; + this._sourceModelTask = undefined; + this._progress = progress; - this._numberOfResourcesToModify += this.renames.length + this.deletes.length + this.creates.length; - - for (let edit of edits) { - this._addEdit(edit); - } + edits.forEach(this.addEdit, this); } - private _addEdit(edit: IResourceEdit): void { - let array = this._edits[edit.resource.toString()]; + dispose(): void { + this._tasks = dispose(this._tasks); + } + + addEdit(edit: ResourceTextEdit): void { + let array = this._edits.get(edit.resource.toString()); if (!array) { - this._edits[edit.resource.toString()] = array = []; - this._numberOfResourcesToModify += 1; + array = []; + this._edits.set(edit.resource.toString(), array); } array.push(edit); } - public async prepare(): TPromise { + async prepare(): TPromise { if (this._tasks) { throw new Error('illegal state - already prepared'); @@ -244,42 +213,25 @@ class BulkEditModel implements IDisposable { this._tasks = []; const promises: TPromise[] = []; - if (this.progress) { - this.progress.total(this._numberOfResourcesToModify * 2); - } - - await TPromise.join(this.renames.map(rename => - this.fileService.moveFile(rename.from, rename.to))); - - await TPromise.join(this.creates.map(create => - this.fileService.createFile(create.uri, create.contents))); - - await TPromise.join(this.deletes.map(uri => - this.fileService.del(uri))); - - forEach(this._edits, entry => { - const promise = this._textModelResolverService.createModelReference(URI.parse(entry.key)).then(ref => { + this._edits.forEach((value, key) => { + const promise = this._textModelResolverService.createModelReference(URI.parse(key)).then(ref => { const model = ref.object; if (!model || !model.textEditorModel) { - throw new Error(`Cannot load file ${entry.key}`); + throw new Error(`Cannot load file ${key}`); } - const textEditorModel = model.textEditorModel; let task: EditTask; - - if (this._sourceModel && textEditorModel.uri.toString() === this._sourceModel.toString()) { + if (this._sourceModel && model.textEditorModel.uri.toString() === this._sourceModel.toString()) { this._sourceModelTask = new SourceModelEditTask(ref, this._sourceSelections); task = this._sourceModelTask; } else { task = new EditTask(ref); } - entry.value.forEach(edit => task.addEdit(edit)); + value.forEach(edit => task.addEdit(edit)); this._tasks.push(task); - if (this.progress) { - this.progress.worked(1); - } + this._progress.report(undefined); }); promises.push(promise); }); @@ -289,131 +241,52 @@ class BulkEditModel implements IDisposable { return this; } - public apply(): Selection { - this._tasks.forEach(task => this.applyTask(task)); - let r: Selection = null; - if (this._sourceModelTask) { - r = this._sourceModelTask.getEndCursorSelection(); + apply(): Selection { + for (const task of this._tasks) { + task.apply(); + this._progress.report(undefined); } - return r; - } - - private applyTask(task: EditTask): void { - task.apply(); - if (this.progress) { - this.progress.worked(1); - } - } - - dispose(): void { - this._tasks = dispose(this._tasks); + return this._sourceModelTask + ? this._sourceModelTask.getEndCursorSelection() + : undefined; } } -export interface BulkEdit { - progress(progress: IProgressRunner): void; - add(edit: IResourceEdit[]): void; - addRename(edit: IResourceRename[]): void; - addCreate(edit: IResourceCreate[]): void; - addDelete(edit: URI[]): void; - finish(): TPromise; - ariaMessage(): string; -} +export type Edit = ResourceFileEdit | ResourceTextEdit; -export function bulkEdit(textModelResolverService: ITextModelService, editor: ICodeEditor, edits: IResourceEdit[], fileService: IFileService, resourceFileEdits?: IResourceFileEdit): TPromise { - let bulk = createBulkEdit(textModelResolverService, editor, fileService); - bulk.add(edits); - bulk.addRename(resourceFileEdits.renamedResources); - bulk.addCreate(resourceFileEdits.createdResources); - bulk.addDelete(resourceFileEdits.deletedResources); - bulk.progress(null); - return bulk.finish(); -} +export class BulkEdit { -export function createBulkEdit(textModelResolverService: ITextModelService, editor?: ICodeEditor, fileService?: IFileService): BulkEdit { - - let all: IResourceEdit[] = []; - const renames: IResourceRename[] = []; - const creates: IResourceCreate[] = []; - const deletes: URI[] = []; - let recording = new ChangeRecorder(fileService).start(); - let progressRunner: IProgressRunner; - - function progress(progress: IProgressRunner) { - progressRunner = progress; + static perform(edits: Edit[], textModelService: ITextModelService, fileService: IFileService, editor: ICodeEditor): TPromise { + const edit = new BulkEdit(editor, null, textModelService, fileService); + edit.add(edits); + return edit.perform(); } - function add(edits: IResourceEdit[]): void { - all.push(...edits); + private _edits: Edit[] = []; + private _editor: ICodeEditor; + private _progress: IProgressRunner; + + constructor( + editor: ICodeEditor, + progress: IProgressRunner, + @ITextModelService private _textModelService: ITextModelService, + @optional(IFileService) private _fileService: IFileService + ) { + this._editor = editor; + this._progress = progress || emptyProgressRunner; } - function addRename(edits: IResourceRename[]): void { - renames.push(...edits); - } - - function addCreate(edits: IResourceCreate[]): void { - creates.push(...edits); - } - - function addDelete(edits: URI[]): void { - deletes.push(...edits); - } - - function getConcurrentEdits() { - let names: string[]; - for (let edit of all) { - if (recording.hasChanged(edit.resource)) { - if (!names) { - names = []; - } - names.push(edit.resource.fsPath); - } + add(edits: Edit[] | Edit): void { + if (Array.isArray(edits)) { + this._edits.push(...edits); + } else { + this._edits.push(edits); } - if (names) { - return nls.localize('conflict', "These files have changed in the meantime: {0}", names.join(', ')); - } - return undefined; } - function finish(): TPromise { - - if (all.length === 0 && renames.length === 0 && creates.length === 0 && deletes.length === 0) { - return TPromise.as(undefined); - } - - let concurrentEdits = getConcurrentEdits(); - if (concurrentEdits) { - return TPromise.wrapError(new Error(concurrentEdits)); - } - - let uri: URI; - let selections: Selection[]; - - if (editor && editor.getModel()) { - uri = editor.getModel().uri; - selections = editor.getSelections(); - } - - const model = new BulkEditModel(textModelResolverService, uri, selections, all, progressRunner, renames, creates, deletes, fileService); - - return model.prepare().then(async _ => { - - let concurrentEdits = getConcurrentEdits(); - if (concurrentEdits) { - throw new Error(concurrentEdits); - } - - recording.stop(); - - const result = await model.apply(); - model.dispose(); - return result; - }); - } - - function ariaMessage(): string { - let editCount = all.length; - let resourceCount = size(groupBy(all, edit => edit.resource.toString())); + ariaMessage(): string { + const editCount = this._edits.reduce((prev, cur) => isResourceFileEdit(cur) ? prev : prev + cur.edits.length, 0); + const resourceCount = this._edits.length; if (editCount === 0) { return nls.localize('summary.0', "Made no edits"); } else if (editCount > 1 && resourceCount > 1) { @@ -423,13 +296,81 @@ export function createBulkEdit(textModelResolverService: ITextModelService, edit } } - return { - progress, - add, - addRename, - addCreate, - addDelete, - finish, - ariaMessage - }; + async perform(): TPromise { + + let seen = new Set(); + let total = 0; + + const groups: Edit[][] = []; + let group: Edit[]; + for (const edit of this._edits) { + if (!group || isResourceFileEdit(group[0]) === isResourceFileEdit(edit)) { + group = []; + groups.push(group); + } + group.push(edit); + + if (isResourceFileEdit(edit)) { + total += 1; + } else if (!seen.has(edit.resource.toString())) { + seen.add(edit.resource.toString()); + total += 2; + } + } + + // define total work and progress callback + // for child operations + this._progress.total(total); + let progress: IProgress = { report: _ => this._progress.worked(1) }; + + // do it. return the last selection computed + // by a text change (can be undefined then) + let res: Selection = undefined; + for (const group of groups) { + if (isResourceFileEdit(group[0])) { + await this._performFileEdits(group, progress); + } else { + res = await this._performTextEdits(group, progress) || res; + } + } + return res; + } + + private async _performFileEdits(edits: ResourceFileEdit[], progress: IProgress) { + for (const edit of edits) { + + progress.report(undefined); + + if (edit.newUri && edit.oldUri) { + await this._fileService.moveFile(edit.oldUri, edit.newUri, false); + } else if (!edit.newUri && edit.oldUri) { + await this._fileService.del(edit.oldUri, true); + } else if (edit.newUri && !edit.oldUri) { + await this._fileService.createFile(edit.newUri, undefined, { overwrite: false }); + } + } + } + + private async _performTextEdits(edits: ResourceTextEdit[], progress: IProgress): TPromise { + + const recording = IRecording.start(this._fileService); + const model = new BulkEditModel(this._textModelService, this._editor, edits, progress); + + await model.prepare(); + + const conflicts = edits + .filter(edit => recording.hasChanged(edit.resource)) + .map(edit => getPathLabel(edit.resource)); + + recording.stop(); + + if (conflicts.length > 0) { + model.dispose(); + throw new Error(nls.localize('conflict', "These files have changed in the meantime: {0}", conflicts.join(', '))); + } + + const selection = await model.apply(); + model.dispose(); + return selection; + } } diff --git a/src/vs/editor/common/modes.ts b/src/vs/editor/common/modes.ts index 9aa2e6ae1ba..e822789ab01 100644 --- a/src/vs/editor/common/modes.ts +++ b/src/vs/editor/common/modes.ts @@ -17,6 +17,7 @@ import { TokenizationRegistryImpl } from 'vs/editor/common/modes/tokenizationReg import { Color } from 'vs/base/common/color'; import { IMarkerData } from 'vs/platform/markers/common/markers'; import * as model from 'vs/editor/common/model'; +import { isObject } from 'vs/base/common/types'; /** * Open ended enum at runtime @@ -816,29 +817,36 @@ export interface DocumentColorProvider { provideColorPresentations(model: model.ITextModel, colorInfo: IColorInformation, token: CancellationToken): IColorPresentation[] | Thenable; } -export interface IResourceEdit { +/** + * @internal + */ +export function isResourceFileEdit(thing: any): thing is ResourceFileEdit { + return isObject(thing) && (Boolean((thing).newUri) || Boolean((thing).oldUri)); +} + +/** + * @internal + */ +export function isResourceTextEdit(thing: any): thing is ResourceTextEdit { + return isObject(thing) && (thing).resource && Array.isArray((thing).edits); +} + +export interface ResourceFileEdit { + oldUri: URI; + newUri: URI; +} + +export interface ResourceTextEdit { resource: URI; - range: IRange; - newText: string; -} - -export interface IResourceRename { - readonly from: URI; - readonly to: URI; -} - -export interface IResourceCreate { - readonly uri: URI; - readonly contents: string; + modelVersionId?: number; + edits: TextEdit[]; } export interface WorkspaceEdit { - edits: IResourceEdit[]; - renamedResources?: IResourceRename[]; - createdResources?: IResourceCreate[]; - deletedResources?: URI[]; - rejectReason?: string; + edits: Array; + rejectReason?: string; // TODO@joh, move to rename } + export interface RenameProvider { provideRenameEdits(model: model.ITextModel, position: Position, newName: string, token: CancellationToken): WorkspaceEdit | Thenable; } diff --git a/src/vs/editor/contrib/quickFix/quickFixCommands.ts b/src/vs/editor/contrib/quickFix/quickFixCommands.ts index f012b11a4ca..1345f72935b 100644 --- a/src/vs/editor/contrib/quickFix/quickFixCommands.ts +++ b/src/vs/editor/contrib/quickFix/quickFixCommands.ts @@ -22,10 +22,9 @@ import { LightBulbWidget } from './lightBulbWidget'; import { QuickFixModel, QuickFixComputeEvent } from './quickFixModel'; import { TPromise } from 'vs/base/common/winjs.base'; import { CodeAction } from 'vs/editor/common/modes'; -import { bulkEdit } from 'vs/editor/browser/services/bulkEdit'; +import { BulkEdit } from 'vs/editor/browser/services/bulkEdit'; import { IFileService } from 'vs/platform/files/common/files'; import { ITextModelService } from 'vs/editor/common/services/resolverService'; -import URI from 'vs/base/common/uri'; export class QuickFixController implements IEditorContribution { @@ -113,11 +112,7 @@ export class QuickFixController implements IEditorContribution { private async _onApplyCodeAction(action: CodeAction): TPromise { if (action.edit) { - await bulkEdit(this._textModelService, this._editor, action.edit.edits, this._fileService, { - createdResources: action.edit.createdResources.map(create => ({ uri: URI.revive(create.uri), contents: create.contents })), - renamedResources: action.edit.renamedResources.map(rename => ({ from: URI.revive(rename.from), to: URI.revive(rename.to) })), - deletedResources: action.edit.deletedResources.map(URI.revive) - }); + await BulkEdit.perform(action.edit.edits, this._textModelService, this._fileService, this._editor); } if (action.command) { diff --git a/src/vs/editor/contrib/quickFix/test/quickFix.test.ts b/src/vs/editor/contrib/quickFix/test/quickFix.test.ts index 8e1fdc79473..0a598114488 100644 --- a/src/vs/editor/contrib/quickFix/test/quickFix.test.ts +++ b/src/vs/editor/contrib/quickFix/test/quickFix.test.ts @@ -8,7 +8,7 @@ import * as assert from 'assert'; import URI from 'vs/base/common/uri'; import Severity from 'vs/base/common/severity'; import { TextModel } from 'vs/editor/common/model/textModel'; -import { CodeActionProviderRegistry, LanguageIdentifier, CodeActionProvider, Command, WorkspaceEdit, IResourceEdit } from 'vs/editor/common/modes'; +import { CodeActionProviderRegistry, LanguageIdentifier, CodeActionProvider, Command, WorkspaceEdit, ResourceTextEdit } from 'vs/editor/common/modes'; import { IDisposable, dispose } from 'vs/base/common/lifecycle'; import { Range } from 'vs/editor/common/core/range'; import { getCodeActions } from 'vs/editor/contrib/quickFix/quickFix'; @@ -57,7 +57,7 @@ suite('QuickFix', () => { bcd: { diagnostics: [], edit: new class implements WorkspaceEdit { - edits: IResourceEdit[]; + edits: ResourceTextEdit[]; }, title: 'abc' } diff --git a/src/vs/editor/contrib/rename/rename.ts b/src/vs/editor/contrib/rename/rename.ts index 0fbe5db81f9..b25b9b3f74b 100644 --- a/src/vs/editor/contrib/rename/rename.ts +++ b/src/vs/editor/contrib/rename/rename.ts @@ -18,7 +18,7 @@ import { registerEditorAction, registerEditorContribution, ServicesAccessor, Edi import { IEditorContribution } from 'vs/editor/common/editorCommon'; import { ITextModel } from 'vs/editor/common/model'; import { EditorContextKeys } from 'vs/editor/common/editorContextKeys'; -import { createBulkEdit } from 'vs/editor/browser/services/bulkEdit'; +import { BulkEdit } from 'vs/editor/browser/services/bulkEdit'; import { ICodeEditor } from 'vs/editor/browser/editorBrowser'; import RenameInputField from './renameInputField'; import { ITextModelService } from 'vs/editor/common/services/resolverService'; @@ -147,9 +147,7 @@ class RenameController implements IEditorContribution { this._renameInputVisible.reset(); this.editor.focus(); - // start recording of file changes so that we can figure out if a file that - // is to be renamed conflicts with another (concurrent) modification - const edit = createBulkEdit(this._textModelResolverService, this.editor, this._fileService); + const edit = new BulkEdit(this.editor, null, this._textModelResolverService, this._fileService); const state = new EditorState(this.editor, CodeEditorStateFlag.Position | CodeEditorStateFlag.Value | CodeEditorStateFlag.Selection | CodeEditorStateFlag.Scroll); const renameOperation = rename(this.editor.getModel(), this.editor.getPosition(), newName).then(result => { @@ -163,7 +161,7 @@ class RenameController implements IEditorContribution { } edit.add(result.edits); - return edit.finish().then(selection => { + return edit.perform().then(selection => { if (selection) { this.editor.setSelection(selection); } diff --git a/src/vs/monaco.d.ts b/src/vs/monaco.d.ts index 58eb60dd225..ea436add39c 100644 --- a/src/vs/monaco.d.ts +++ b/src/vs/monaco.d.ts @@ -4907,27 +4907,19 @@ declare module monaco.languages { provideColorPresentations(model: editor.ITextModel, colorInfo: IColorInformation, token: CancellationToken): IColorPresentation[] | Thenable; } - export interface IResourceEdit { + export interface ResourceFileEdit { + oldUri: Uri; + newUri: Uri; + } + + export interface ResourceTextEdit { resource: Uri; - range: IRange; - newText: string; - } - - export interface IResourceRename { - readonly from: Uri; - readonly to: Uri; - } - - export interface IResourceCreate { - readonly uri: Uri; - readonly contents: string; + modelVersionId?: number; + edits: TextEdit[]; } export interface WorkspaceEdit { - edits: IResourceEdit[]; - renamedResources?: IResourceRename[]; - createdResources?: IResourceCreate[]; - deletedResources?: Uri[]; + edits: Array; rejectReason?: string; } diff --git a/src/vs/platform/progress/common/progress.ts b/src/vs/platform/progress/common/progress.ts index 75addbff74d..97fc957c02b 100644 --- a/src/vs/platform/progress/common/progress.ts +++ b/src/vs/platform/progress/common/progress.ts @@ -31,6 +31,12 @@ export interface IProgressRunner { done(): void; } +export const emptyProgressRunner: IProgressRunner = Object.freeze({ + total() { }, + worked() { }, + done() { } +}); + export interface IProgress { report(item: T): void; } diff --git a/src/vs/vscode.d.ts b/src/vs/vscode.d.ts index ad5cb36dc8c..1529b850f59 100644 --- a/src/vs/vscode.d.ts +++ b/src/vs/vscode.d.ts @@ -2430,29 +2430,6 @@ declare module 'vscode' { */ readonly size: number; - /** - * Renames a given resource in the workspace. - * - * @param from Uri of current resource. - * @param to Uri of renamed resource. - */ - renameResource(from: Uri, to: Uri): void; - - /** - * Create a new resource in the workspace. - * - * @param uri Uri of resource to create. - * @param contents New file contents. - */ - createResource(uri: Uri, contents: String): void; - - /** - * Delete a given resource in the workspace. - * - * @param uri Uri of resource to delete. - */ - deleteResource(uri: Uri): void; - /** * Replace the given range with given text for the given resource. * @@ -2510,19 +2487,40 @@ declare module 'vscode' { entries(): [Uri, TextEdit[]][]; /** - * Get all resource rename edits. + * Renames a given resource in the workspace. + * + * @param from Uri of current resource. + * @param to Uri of renamed resource. */ - readonly renamedResources: { from: Uri, to: Uri }[]; + renameResource(from: Uri, to: Uri): void; /** - * Get all resource create edits. + * Create a new resource in the workspace. + * + * @param uri Uri of resource to create. */ - readonly createdResources: { uri: Uri, contents: string }[]; + createResource(uri: Uri): void; /** - * Get all resource delete edits. + * Delete a given resource in the workspace. + * + * @param uri Uri of resource to delete. */ - readonly deletedResources: Uri[]; + deleteResource(uri: Uri): void; + + /** + * Get the resource edits for this workspace edit. + * + * @returns A array of uri-tuples in which a rename-edit + * is represented as `[from, to]`, a delete-operation as `[from, null]`, + * and a create-operation as `[null, to]`; + */ + resourceEdits(): [Uri, Uri][]; + + /** + * + */ + allEntries(): ([Uri, TextEdit[]] | [Uri, Uri])[]; } /** diff --git a/src/vs/workbench/api/electron-browser/mainThreadEditors.ts b/src/vs/workbench/api/electron-browser/mainThreadEditors.ts index 1af196d2491..409e9df963d 100644 --- a/src/vs/workbench/api/electron-browser/mainThreadEditors.ts +++ b/src/vs/workbench/api/electron-browser/mainThreadEditors.ts @@ -15,17 +15,18 @@ import { IWorkbenchEditorService } from 'vs/workbench/services/editor/common/edi import { IEditorGroupService } from 'vs/workbench/services/group/common/groupService'; import { Position as EditorPosition, ITextEditorOptions } from 'vs/platform/editor/common/editor'; import { MainThreadTextEditor } from './mainThreadEditor'; -import { ITextEditorConfigurationUpdate, TextEditorRevealType, IApplyEditsOptions, IUndoStopOptions, IResourceFileEdit } from 'vs/workbench/api/node/extHost.protocol'; +import { ITextEditorConfigurationUpdate, TextEditorRevealType, IApplyEditsOptions, IUndoStopOptions, WorkspaceEditDto, reviveWorkspaceEditDto } from 'vs/workbench/api/node/extHost.protocol'; import { MainThreadDocumentsAndEditors } from './mainThreadDocumentsAndEditors'; import { equals as objectEquals } from 'vs/base/common/objects'; -import { ExtHostContext, MainThreadEditorsShape, ExtHostEditorsShape, ITextDocumentShowOptions, ITextEditorPositionData, IExtHostContext, IWorkspaceResourceEdit } from '../node/extHost.protocol'; +import { ExtHostContext, MainThreadEditorsShape, ExtHostEditorsShape, ITextDocumentShowOptions, ITextEditorPositionData, IExtHostContext } from '../node/extHost.protocol'; import { IRange } from 'vs/editor/common/core/range'; import { ISelection } from 'vs/editor/common/core/selection'; import { ITextModelService } from 'vs/editor/common/services/resolverService'; import { IFileService } from 'vs/platform/files/common/files'; -import { bulkEdit, IResourceEdit } from 'vs/editor/browser/services/bulkEdit'; +import { BulkEdit } from 'vs/editor/browser/services/bulkEdit'; import { IModelService } from 'vs/editor/common/services/modelService'; import { isCodeEditor, ICodeEditor } from 'vs/editor/browser/editorBrowser'; +import { isResourceFileEdit } from 'vs/editor/common/modes'; export class MainThreadEditors implements MainThreadEditorsShape { @@ -210,40 +211,22 @@ export class MainThreadEditors implements MainThreadEditorsShape { return TPromise.as(this._documentsAndEditors.getEditor(id).applyEdits(modelVersionId, edits, opts)); } - $tryApplyWorkspaceEdit(workspaceResourceEdits: IWorkspaceResourceEdit[], resourceFileEdits?: IResourceFileEdit): TPromise { + $tryApplyWorkspaceEdit(dto: WorkspaceEditDto): TPromise { + + const { edits } = reviveWorkspaceEditDto(dto); // First check if loaded models were not changed in the meantime - for (let i = 0, len = workspaceResourceEdits.length; i < len; i++) { - const workspaceResourceEdit = workspaceResourceEdits[i]; - if (workspaceResourceEdit.modelVersionId) { - const uri = URI.revive(workspaceResourceEdit.resource); - let model = this._modelService.getModel(uri); - if (model && model.getVersionId() !== workspaceResourceEdit.modelVersionId) { + for (let i = 0, len = edits.length; i < len; i++) { + const edit = edits[i]; + if (!isResourceFileEdit(edit) && edit.modelVersionId) { + let model = this._modelService.getModel(edit.resource); + if (model && model.getVersionId() !== edit.modelVersionId) { // model changed in the meantime return TPromise.as(false); } } } - // Convert to shape expected by bulkEdit below - let resourceEdits: IResourceEdit[] = []; - for (let i = 0, len = workspaceResourceEdits.length; i < len; i++) { - const workspaceResourceEdit = workspaceResourceEdits[i]; - const uri = URI.revive(workspaceResourceEdit.resource); - const edits = workspaceResourceEdit.edits; - - for (let j = 0, lenJ = edits.length; j < lenJ; j++) { - const edit = edits[j]; - - resourceEdits.push({ - resource: uri, - newText: edit.newText, - newEol: edit.newEol, - range: edit.range - }); - } - } - let codeEditor: ICodeEditor; let editor = this._workbenchEditorService.getActiveEditor(); if (editor) { @@ -253,17 +236,7 @@ export class MainThreadEditors implements MainThreadEditorsShape { } } - return bulkEdit( - this._textModelResolverService, - codeEditor, - resourceEdits, - this._fileService, - resourceFileEdits ? { - renamedResources: resourceFileEdits.renamedResources.map(entry => ({ from: URI.revive(entry.from), to: URI.revive(entry.to) })), - createdResources: resourceFileEdits.createdResources.map(entry => ({ uri: URI.revive(entry.uri), contents: entry.contents })), - deletedResources: resourceFileEdits.deletedResources.map(URI.revive) - } : undefined - ).then(() => true); + return BulkEdit.perform(edits, this._textModelResolverService, this._fileService, codeEditor).then(() => true); } $tryInsertSnippet(id: string, template: string, ranges: IRange[], opts: IUndoStopOptions): TPromise { diff --git a/src/vs/workbench/api/electron-browser/mainThreadLanguageFeatures.ts b/src/vs/workbench/api/electron-browser/mainThreadLanguageFeatures.ts index d60034d69a2..77ff222bd12 100644 --- a/src/vs/workbench/api/electron-browser/mainThreadLanguageFeatures.ts +++ b/src/vs/workbench/api/electron-browser/mainThreadLanguageFeatures.ts @@ -15,7 +15,7 @@ import { wireCancellationToken } from 'vs/base/common/async'; import { CancellationToken } from 'vs/base/common/cancellation'; import { Position as EditorPosition } from 'vs/editor/common/core/position'; import { Range as EditorRange } from 'vs/editor/common/core/range'; -import { ExtHostContext, MainThreadLanguageFeaturesShape, ExtHostLanguageFeaturesShape, MainContext, IExtHostContext, ISerializedLanguageConfiguration, ISerializedRegExp, ISerializedIndentationRule, ISerializedOnEnterRule, LocationDto, SymbolInformationDto, WorkspaceEditDto, ResourceEditDto, CodeActionDto } from '../node/extHost.protocol'; +import { ExtHostContext, MainThreadLanguageFeaturesShape, ExtHostLanguageFeaturesShape, MainContext, IExtHostContext, ISerializedLanguageConfiguration, ISerializedRegExp, ISerializedIndentationRule, ISerializedOnEnterRule, LocationDto, SymbolInformationDto, CodeActionDto, reviveWorkspaceEditDto } from '../node/extHost.protocol'; import { LanguageConfigurationRegistry } from 'vs/editor/common/modes/languageConfigurationRegistry'; import { LanguageConfiguration, IndentationRule, OnEnterRule } from 'vs/editor/common/modes/languageConfiguration'; import { IHeapService } from './mainThreadHeapService'; @@ -86,21 +86,9 @@ export class MainThreadLanguageFeatures implements MainThreadLanguageFeaturesSha } } - private static _reviveResourceEditDto(data: ResourceEditDto): modes.IResourceEdit { - data.resource = URI.revive(data.resource); - return data; - } - - private static _reviveWorkspaceEditDto(data: WorkspaceEditDto): modes.WorkspaceEdit { - if (data && data.edits) { - data.edits.forEach(MainThreadLanguageFeatures._reviveResourceEditDto); - } - return data; - } - private static _reviveCodeActionDto(data: CodeActionDto[]): modes.CodeAction[] { if (data) { - data.forEach(code => MainThreadLanguageFeatures._reviveWorkspaceEditDto(code.edit)); + data.forEach(code => reviveWorkspaceEditDto(code.edit)); } return data; } @@ -266,7 +254,7 @@ export class MainThreadLanguageFeatures implements MainThreadLanguageFeaturesSha $registerRenameSupport(handle: number, selector: vscode.DocumentSelector): void { this._registrations[handle] = modes.RenameProviderRegistry.register(toLanguageSelector(selector), { provideRenameEdits: (model: ITextModel, position: EditorPosition, newName: string, token: CancellationToken): Thenable => { - return wireCancellationToken(token, this._proxy.$provideRenameEdits(handle, model.uri, position, newName)).then(MainThreadLanguageFeatures._reviveWorkspaceEditDto); + return wireCancellationToken(token, this._proxy.$provideRenameEdits(handle, model.uri, position, newName)).then(reviveWorkspaceEditDto); } }); } diff --git a/src/vs/workbench/api/node/extHost.protocol.ts b/src/vs/workbench/api/node/extHost.protocol.ts index 0d3ad1d8df1..dad2c493041 100644 --- a/src/vs/workbench/api/node/extHost.protocol.ts +++ b/src/vs/workbench/api/node/extHost.protocol.ts @@ -14,7 +14,7 @@ import { import * as vscode from 'vscode'; -import { UriComponents } from 'vs/base/common/uri'; +import URI, { UriComponents } from 'vs/base/common/uri'; import Severity from 'vs/base/common/severity'; import { TPromise } from 'vs/base/common/winjs.base'; @@ -52,7 +52,7 @@ import { IStat, IFileChange } from 'vs/platform/files/common/files'; import { ConfigurationScope } from 'vs/platform/configuration/common/configurationRegistry'; import { ParsedArgs } from 'vs/platform/environment/common/environment'; import { CommentRule, CharacterPair, EnterAction } from 'vs/editor/common/modes/languageConfiguration'; -import { EndOfLineSequence, ISingleEditOperation } from 'vs/editor/common/model'; +import { ISingleEditOperation } from 'vs/editor/common/model'; export interface IEnvironment { isExtensionDevelopmentDebug: boolean; @@ -191,8 +191,6 @@ export interface IApplyEditsOptions extends IUndoStopOptions { setEndOfLine: EndOfLine; } - - export interface ITextDocumentShowOptions { position?: EditorPosition; preserveFocus?: boolean; @@ -200,22 +198,6 @@ export interface ITextDocumentShowOptions { selection?: IRange; } -export interface IWorkspaceResourceEdit { - resource: UriComponents; - modelVersionId?: number; - edits: { - range?: IRange; - newText: string; - newEol?: EndOfLineSequence; - }[]; -} - -export interface IResourceFileEdit { - renamedResources: { from: UriComponents, to: UriComponents }[]; - createdResources: { uri: UriComponents, contents: string }[]; - deletedResources: UriComponents[]; -} - export interface MainThreadEditorsShape extends IDisposable { $tryShowTextDocument(resource: UriComponents, options: ITextDocumentShowOptions): TPromise; $registerTextEditorDecorationType(key: string, options: editorCommon.IDecorationRenderOptions): void; @@ -228,7 +210,7 @@ export interface MainThreadEditorsShape extends IDisposable { $tryRevealRange(id: string, range: IRange, revealType: TextEditorRevealType): TPromise; $trySetSelections(id: string, selections: ISelection[]): TPromise; $tryApplyEdits(id: string, modelVersionId: number, edits: ISingleEditOperation[], opts: IApplyEditsOptions): TPromise; - $tryApplyWorkspaceEdit(workspaceResourceEdits: IWorkspaceResourceEdit[], resourceFileEdits?: IResourceFileEdit): TPromise; + $tryApplyWorkspaceEdit(workspaceEditDto: WorkspaceEditDto): TPromise; $tryInsertSnippet(id: string, template: string, selections: IRange[], opts: IUndoStopOptions): TPromise; $getDiffInformation(id: string): TPromise; } @@ -622,17 +604,38 @@ export interface WorkspaceSymbolsDto extends IdObject { symbols: SymbolInformationDto[]; } -export interface ResourceEditDto { +export interface ResourceFileEditDto { + oldUri: UriComponents; + newUri: UriComponents; +} + +export interface ResourceTextEditDto { resource: UriComponents; - range: IRange; - newText: string; + modelVersionId?: number; + edits: modes.TextEdit[]; } export interface WorkspaceEditDto { - edits: ResourceEditDto[]; + edits: (ResourceFileEditDto | ResourceTextEditDto)[]; + + // todo@joh reject should go into rename rejectReason?: string; } +export function reviveWorkspaceEditDto(data: WorkspaceEditDto): modes.WorkspaceEdit { + if (data && data.edits) { + for (const edit of data.edits) { + if (typeof (edit).resource === 'object') { + (edit).resource = URI.revive((edit).resource); + } else { + (edit).newUri = URI.revive((edit).newUri); + (edit).oldUri = URI.revive((edit).oldUri); + } + } + } + return data; +} + export interface CodeActionDto { title: string; edit?: WorkspaceEditDto; diff --git a/src/vs/workbench/api/node/extHostApiCommands.ts b/src/vs/workbench/api/node/extHostApiCommands.ts index 62652183f85..d29bab7425a 100644 --- a/src/vs/workbench/api/node/extHostApiCommands.ts +++ b/src/vs/workbench/api/node/extHostApiCommands.ts @@ -344,11 +344,7 @@ export class ExtHostApiCommands { if (value.rejectReason) { return TPromise.wrapError(new Error(value.rejectReason)); } - let workspaceEdit = new types.WorkspaceEdit(); - for (let edit of value.edits) { - workspaceEdit.replace(edit.resource, typeConverters.toRange(edit.range), edit.newText); - } - return workspaceEdit; + return typeConverters.WorkspaceEdit.to(value); }); } diff --git a/src/vs/workbench/api/node/extHostDocumentSaveParticipant.ts b/src/vs/workbench/api/node/extHostDocumentSaveParticipant.ts index 3733a20adbc..d6edc95eb20 100644 --- a/src/vs/workbench/api/node/extHostDocumentSaveParticipant.ts +++ b/src/vs/workbench/api/node/extHostDocumentSaveParticipant.ts @@ -8,7 +8,7 @@ import Event from 'vs/base/common/event'; import URI, { UriComponents } from 'vs/base/common/uri'; import { sequence, always } from 'vs/base/common/async'; import { illegalState } from 'vs/base/common/errors'; -import { ExtHostDocumentSaveParticipantShape, MainThreadEditorsShape, IWorkspaceResourceEdit } from 'vs/workbench/api/node/extHost.protocol'; +import { ExtHostDocumentSaveParticipantShape, MainThreadEditorsShape, ResourceTextEditDto } from 'vs/workbench/api/node/extHost.protocol'; import { TextEdit } from 'vs/workbench/api/node/extHostTypes'; import { fromRange, TextDocumentSaveReason, EndOfLine } from 'vs/workbench/api/node/extHostTypeConverters'; import { ExtHostDocuments } from 'vs/workbench/api/node/extHostDocuments'; @@ -142,7 +142,7 @@ export class ExtHostDocumentSaveParticipant implements ExtHostDocumentSavePartic }).then(values => { - let workspaceResourceEdit: IWorkspaceResourceEdit = { + const resourceEdit: ResourceTextEditDto = { resource: document.uri, edits: [] }; @@ -150,10 +150,10 @@ export class ExtHostDocumentSaveParticipant implements ExtHostDocumentSavePartic for (const value of values) { if (Array.isArray(value) && (value).every(e => e instanceof TextEdit)) { for (const { newText, newEol, range } of value) { - workspaceResourceEdit.edits.push({ + resourceEdit.edits.push({ range: range && fromRange(range), - newText, - newEol: EndOfLine.from(newEol) + text: newText, + eol: EndOfLine.from(newEol) }); } } @@ -161,12 +161,12 @@ export class ExtHostDocumentSaveParticipant implements ExtHostDocumentSavePartic // apply edits if any and if document // didn't change somehow in the meantime - if (workspaceResourceEdit.edits.length === 0) { + if (resourceEdit.edits.length === 0) { return undefined; } if (version === document.version) { - return this._mainThreadEditors.$tryApplyWorkspaceEdit([workspaceResourceEdit]); + return this._mainThreadEditors.$tryApplyWorkspaceEdit({ edits: [resourceEdit] }); } // TODO@joh bubble this to listener? diff --git a/src/vs/workbench/api/node/extHostLanguageFeatures.ts b/src/vs/workbench/api/node/extHostLanguageFeatures.ts index 37ac8015683..731fccd8492 100644 --- a/src/vs/workbench/api/node/extHostLanguageFeatures.ts +++ b/src/vs/workbench/api/node/extHostLanguageFeatures.ts @@ -17,7 +17,7 @@ import { ExtHostDocuments } from 'vs/workbench/api/node/extHostDocuments'; import { ExtHostCommands, CommandsConverter } from 'vs/workbench/api/node/extHostCommands'; import { ExtHostDiagnostics, DiagnosticCollection } from 'vs/workbench/api/node/extHostDiagnostics'; import { asWinJsPromise } from 'vs/base/common/async'; -import { MainContext, MainThreadLanguageFeaturesShape, ExtHostLanguageFeaturesShape, ObjectIdentifier, IRawColorInfo, IMainContext, IdObject, ISerializedRegExp, ISerializedIndentationRule, ISerializedOnEnterRule, ISerializedLanguageConfiguration, SymbolInformationDto, SuggestResultDto, WorkspaceSymbolsDto, SuggestionDto } from './extHost.protocol'; +import { MainContext, MainThreadLanguageFeaturesShape, ExtHostLanguageFeaturesShape, ObjectIdentifier, IRawColorInfo, IMainContext, IdObject, ISerializedRegExp, ISerializedIndentationRule, ISerializedOnEnterRule, ISerializedLanguageConfiguration, SymbolInformationDto, SuggestResultDto, WorkspaceSymbolsDto, SuggestionDto, CodeActionDto } from './extHost.protocol'; import { regExpLeadsToEndlessLoop } from 'vs/base/common/strings'; import { IPosition } from 'vs/editor/common/core/position'; import { IRange } from 'vs/editor/common/core/range'; @@ -255,7 +255,7 @@ class ReferenceAdapter { } } -export interface CustomCodeAction extends modes.CodeAction { +export interface CustomCodeAction extends CodeActionDto { _isSynthetic?: boolean; } @@ -273,7 +273,7 @@ class CodeActionAdapter { this._provider = provider; } - provideCodeActions(resource: URI, range: IRange): TPromise { + provideCodeActions(resource: URI, range: IRange): TPromise { const doc = this._documents.getDocumentData(resource).document; const ran = TypeConverters.toRange(range); @@ -943,7 +943,7 @@ export class ExtHostLanguageFeatures implements ExtHostLanguageFeaturesShape { return this._createDisposable(handle); } - $provideCodeActions(handle: number, resource: UriComponents, range: IRange): TPromise { + $provideCodeActions(handle: number, resource: UriComponents, range: IRange): TPromise { return this._withAdapter(handle, CodeActionAdapter, adapter => adapter.provideCodeActions(URI.revive(resource), range)); } diff --git a/src/vs/workbench/api/node/extHostTextEditors.ts b/src/vs/workbench/api/node/extHostTextEditors.ts index 2b3738a27f3..ea973d68b22 100644 --- a/src/vs/workbench/api/node/extHostTextEditors.ts +++ b/src/vs/workbench/api/node/extHostTextEditors.ts @@ -12,7 +12,7 @@ import * as TypeConverters from './extHostTypeConverters'; import { TextEditorDecorationType, ExtHostTextEditor } from './extHostTextEditor'; import { ExtHostDocumentsAndEditors } from './extHostDocumentsAndEditors'; import { Position as EditorPosition } from 'vs/platform/editor/common/editor'; -import { MainContext, MainThreadEditorsShape, ExtHostEditorsShape, ITextDocumentShowOptions, ITextEditorPositionData, IResolvedTextEditorConfiguration, ISelectionChangeEvent, IMainContext, IWorkspaceResourceEdit } from './extHost.protocol'; +import { MainContext, MainThreadEditorsShape, ExtHostEditorsShape, ITextDocumentShowOptions, ITextEditorPositionData, IResolvedTextEditorConfiguration, ISelectionChangeEvent, IMainContext, WorkspaceEditDto } from './extHost.protocol'; import * as vscode from 'vscode'; export class ExtHostEditors implements ExtHostEditorsShape { @@ -92,40 +92,23 @@ export class ExtHostEditors implements ExtHostEditorsShape { applyWorkspaceEdit(edit: vscode.WorkspaceEdit): TPromise { - let workspaceResourceEdits: IWorkspaceResourceEdit[] = []; + const dto: WorkspaceEditDto = { edits: [] }; - let entries = edit.entries(); - for (let entry of entries) { - let [uri, edits] = entry; - - let doc = this._extHostDocumentsAndEditors.getDocument(uri.toString()); - let docVersion: number = undefined; - if (doc) { - docVersion = doc.version; - } - - let workspaceResourceEdit: IWorkspaceResourceEdit = { - resource: uri, - modelVersionId: docVersion, - edits: [] - }; - - for (let edit of edits) { - workspaceResourceEdit.edits.push({ - newText: edit.newText, - newEol: TypeConverters.EndOfLine.from(edit.newEol), - range: edit.range && TypeConverters.fromRange(edit.range) + for (let entry of edit.allEntries()) { + let [uri, uriOrEdits] = entry; + if (Array.isArray(uriOrEdits)) { + let doc = this._extHostDocumentsAndEditors.getDocument(uri.toString()); + dto.edits.push({ + resource: uri, + modelVersionId: doc && doc.version, + edits: uriOrEdits.map(TypeConverters.TextEdit.from) }); + } else { + dto.edits.push({ oldUri: uri, newUri: uriOrEdits }); } - - workspaceResourceEdits.push(workspaceResourceEdit); } - return this._proxy.$tryApplyWorkspaceEdit(workspaceResourceEdits, { - createdResources: edit.createdResources, - renamedResources: edit.renamedResources, - deletedResources: edit.deletedResources - }); + return this._proxy.$tryApplyWorkspaceEdit(dto); } // --- called from main thread diff --git a/src/vs/workbench/api/node/extHostTypeConverters.ts b/src/vs/workbench/api/node/extHostTypeConverters.ts index f1379708459..af3ba6607cd 100644 --- a/src/vs/workbench/api/node/extHostTypeConverters.ts +++ b/src/vs/workbench/api/node/extHostTypeConverters.ts @@ -20,6 +20,7 @@ import { ISelection } from 'vs/editor/common/core/selection'; import * as htmlContent from 'vs/base/common/htmlContent'; import { IRelativePattern } from 'vs/base/common/glob'; import { LanguageSelector, LanguageFilter } from 'vs/editor/common/modes/languageSelector'; +import { WorkspaceEditDto, ResourceTextEditDto, ResourceFileEditDto } from 'vs/workbench/api/node/extHost.protocol'; export interface PositionLike { line: number; @@ -229,28 +230,35 @@ export const TextEdit = { export namespace WorkspaceEdit { export function from(value: vscode.WorkspaceEdit): modes.WorkspaceEdit { const result: modes.WorkspaceEdit = { - edits: [], - renamedResources: value.renamedResources, - createdResources: value.createdResources, - deletedResources: value.deletedResources + edits: [] }; - for (let entry of value.entries()) { - let [uri, textEdits] = entry; - for (let textEdit of textEdits) { - result.edits.push({ - resource: uri, - newText: textEdit.newText, - range: fromRange(textEdit.range) - }); + for (const entry of value.allEntries()) { + const [uri, uriOrEdits] = entry; + if (Array.isArray(uriOrEdits)) { + // text edits + result.edits.push({ resource: uri, edits: uriOrEdits.map(TextEdit.from) }); + } else { + // resource edits + result.edits.push({ oldUri: uri, newUri: uriOrEdits }); } } return result; } - export function to(value: modes.WorkspaceEdit) { + export function to(value: WorkspaceEditDto) { const result = new types.WorkspaceEdit(); for (const edit of value.edits) { - result.replace(edit.resource, toRange(edit.range), edit.newText); + if (Array.isArray((edit).edits)) { + result.set( + URI.revive((edit).resource), + (edit).edits.map(TextEdit.to) + ); + } else { + result.renameResource( + URI.revive((edit).oldUri), + URI.revive((edit).newUri) + ); + } } return result; } diff --git a/src/vs/workbench/api/node/extHostTypes.ts b/src/vs/workbench/api/node/extHostTypes.ts index a7b250b6d69..b7351530c0c 100644 --- a/src/vs/workbench/api/node/extHostTypes.ts +++ b/src/vs/workbench/api/node/extHostTypes.ts @@ -491,44 +491,28 @@ export class TextEdit { } } -export class WorkspaceEdit { +export class WorkspaceEdit implements vscode.WorkspaceEdit { - private _values: [URI, TextEdit[]][] = []; - private readonly _resourcesCreated: { uri: URI, contents: string }[] = []; - private readonly _resourcesDeleted: URI[] = []; - private readonly _resourcesRenamed: { from: URI, to: URI }[] = []; - private _index = new Map(); + private _clock: number = 0; - private _validResources = new Set(); - private _invalidResources = new Set(); + private _resourceEdits: [number/*time*/, URI, URI][] = []; + private _textEdits: [URI, TextEdit[]][] = []; + private _textEditsIndex = new Map(); - - createResource(uri: URI, contents: string): void { - if (this._invalidResources.has(uri)) { - throw illegalArgument('Cannot create already deleted resource'); - } - this._resourcesCreated.push({ uri: uri, contents: contents }); - this._validResources.add(uri); + createResource(uri: vscode.Uri): void { + this.renameResource(undefined, uri); } - deleteResource(uri: URI): void { - if (this._validResources.has(uri)) { - throw illegalArgument('Cannot delete newly created resource'); - } - this._resourcesDeleted.push(uri); - this._invalidResources.add(uri); + deleteResource(uri: vscode.Uri): void { + this.renameResource(uri, undefined); } - renameResource(uri: URI, newUri: URI): void { - if (this._validResources.has(uri)) { - throw illegalArgument('Cannot delete newly created resource'); - } - if (this._invalidResources.has(newUri)) { - throw illegalArgument('Cannot create already deleted resource'); - } - this._resourcesRenamed.push({ from: uri, to: newUri }); - this._invalidResources.add(uri); - this._validResources.add(newUri); + renameResource(from: vscode.Uri, to: vscode.Uri): void { + this._resourceEdits.push([this._clock++, from, to]); + } + + resourceEdits(): [vscode.Uri, vscode.Uri][] { + return this._resourceEdits.map(([, oldUri, newUri]) => (<[vscode.Uri, vscode.Uri]>[oldUri, newUri])); } replace(uri: URI, range: Range, newText: string): void { @@ -550,50 +534,54 @@ export class WorkspaceEdit { } has(uri: URI): boolean { - return this._index.has(uri.toString()); + return this._textEditsIndex.has(uri.toString()); } set(uri: URI, edits: TextEdit[]): void { - if (this._invalidResources.has(uri)) { - throw illegalArgument('Cannot modify already deleted resource'); - } - this._validResources.add(uri); - const idx = this._index.get(uri.toString()); - if (typeof idx === 'undefined') { - let newLen = this._values.push([uri, edits]); - this._index.set(uri.toString(), newLen - 1); + if (!this._textEditsIndex.has(uri.toString())) { + let newLen = this._textEdits.push([uri, edits]); + this._textEditsIndex.set(uri.toString(), [newLen - 1, this._clock++]); } else { - this._values[idx][1] = edits; + const [idx] = this._textEditsIndex.get(uri.toString()); + this._textEdits[idx][1] = edits; } } get(uri: URI): TextEdit[] { - let idx = this._index.get(uri.toString()); - return typeof idx !== 'undefined' && this._values[idx][1]; + if (!this._textEditsIndex.has(uri.toString())) { + return undefined; + } + const [idx] = this._textEditsIndex.get(uri.toString()); + return this._textEdits[idx][1]; } entries(): [URI, TextEdit[]][] { - return this._values; + // todo@joh - make this immutable + return this._textEdits; } - get createdResources(): { uri: URI, contents: string }[] { - return this._resourcesCreated; - } - - get deletedResources(): URI[] { - return this._resourcesDeleted; - } - - get renamedResources(): { from: URI, to: URI }[] { - return this._resourcesRenamed; + allEntries(): ([URI, TextEdit[]] | [URI, URI])[] { + // use the 'time' the we have assigned when inserting + // the operation and use that order in the resulting + // array + const res: ([URI, TextEdit[]] | [URI, URI])[] = []; + this._textEditsIndex.forEach(value => { + const [index, time] = value; + res[time] = this._textEdits[index]; + }); + this._resourceEdits.forEach(value => { + const [time, oldUri, newUri] = value; + res[time] = [oldUri, newUri]; + }); + return res; } get size(): number { - return this._values.length + this._resourcesCreated.length + this._resourcesRenamed.length + this._resourcesDeleted.length; + return this._textEdits.length + this._resourceEdits.length; } toJSON(): any { - return this._values; + return this._textEdits; } } diff --git a/src/vs/workbench/parts/search/browser/replaceService.ts b/src/vs/workbench/parts/search/browser/replaceService.ts index c93549e85dd..82bbc09d363 100644 --- a/src/vs/workbench/parts/search/browser/replaceService.ts +++ b/src/vs/workbench/parts/search/browser/replaceService.ts @@ -15,7 +15,7 @@ import { IWorkbenchEditorService } from 'vs/workbench/services/editor/common/edi import { IModelService } from 'vs/editor/common/services/modelService'; import { IModeService } from 'vs/editor/common/services/modeService'; import { Match, FileMatch, FileMatchOrMatch, ISearchWorkbenchService } from 'vs/workbench/parts/search/common/searchModel'; -import { BulkEdit, IResourceEdit, createBulkEdit } from 'vs/editor/browser/services/bulkEdit'; +import { BulkEdit } from 'vs/editor/browser/services/bulkEdit'; import { IProgressRunner } from 'vs/platform/progress/common/progress'; import { IDiffEditor } from 'vs/editor/browser/editorBrowser'; import { ITextModelService, ITextModelContentProvider } from 'vs/editor/common/services/resolverService'; @@ -24,6 +24,7 @@ import { ScrollType } from 'vs/editor/common/editorCommon'; import { ITextModel } from 'vs/editor/common/model'; import { IInstantiationService } from 'vs/platform/instantiation/common/instantiation'; import { IFileService } from 'vs/platform/files/common/files'; +import { ResourceTextEdit } from 'vs/editor/common/modes'; const REPLACE_PREVIEW = 'replacePreview'; @@ -103,8 +104,7 @@ export class ReplaceService implements IReplaceService { public replace(match: FileMatchOrMatch, progress?: IProgressRunner, resource?: URI): TPromise; public replace(arg: any, progress: IProgressRunner = null, resource: URI = null): TPromise { - let bulkEdit: BulkEdit = createBulkEdit(this.textModelResolverService, null, this.fileService); - bulkEdit.progress(progress); + let bulkEdit = new BulkEdit(null, progress, this.textModelResolverService, this.fileService); if (arg instanceof Match) { let match = arg; @@ -126,7 +126,7 @@ export class ReplaceService implements IReplaceService { }); } - return bulkEdit.finish(); + return bulkEdit.perform(); } public openReplacePreview(element: FileMatchOrMatch, preserveFocus?: boolean, sideBySide?: boolean, pinned?: boolean): TPromise { @@ -174,12 +174,14 @@ export class ReplaceService implements IReplaceService { }); } - private createEdit(match: Match, text: string, resource: URI = null): IResourceEdit { + private createEdit(match: Match, text: string, resource: URI = null): ResourceTextEdit { let fileMatch: FileMatch = match.parent(); - let resourceEdit: IResourceEdit = { + let resourceEdit: ResourceTextEdit = { resource: resource !== null ? resource : fileMatch.resource(), - range: match.range(), - newText: text + edits: [{ + range: match.range(), + text: text + }] }; return resourceEdit; } diff --git a/src/vs/workbench/test/electron-browser/api/extHostDocumentSaveParticipant.test.ts b/src/vs/workbench/test/electron-browser/api/extHostDocumentSaveParticipant.test.ts index a4c0366b6e4..8ec74bfb073 100644 --- a/src/vs/workbench/test/electron-browser/api/extHostDocumentSaveParticipant.test.ts +++ b/src/vs/workbench/test/electron-browser/api/extHostDocumentSaveParticipant.test.ts @@ -10,7 +10,7 @@ import { TPromise } from 'vs/base/common/winjs.base'; import { ExtHostDocuments } from 'vs/workbench/api/node/extHostDocuments'; import { ExtHostDocumentsAndEditors } from 'vs/workbench/api/node/extHostDocumentsAndEditors'; import { TextDocumentSaveReason, TextEdit, Position, EndOfLine } from 'vs/workbench/api/node/extHostTypes'; -import { MainThreadEditorsShape, IWorkspaceResourceEdit } from 'vs/workbench/api/node/extHost.protocol'; +import { MainThreadEditorsShape, WorkspaceEditDto } from 'vs/workbench/api/node/extHost.protocol'; import { ExtHostDocumentSaveParticipant } from 'vs/workbench/api/node/extHostDocumentSaveParticipant'; import { SingleProxyRPCProtocol } from './testRPCProtocol'; import { SaveReason } from 'vs/workbench/services/textfile/common/textfiles'; @@ -18,6 +18,7 @@ import * as vscode from 'vscode'; import { mock } from 'vs/workbench/test/electron-browser/api/mock'; import { IExtensionDescription } from 'vs/platform/extensions/common/extensions'; import { NullLogService } from 'vs/platform/log/common/log'; +import { isResourceTextEdit, ResourceTextEdit } from 'vs/editor/common/modes'; suite('ExtHostDocumentSaveParticipant', () => { @@ -262,10 +263,10 @@ suite('ExtHostDocumentSaveParticipant', () => { test('event delivery, pushEdits sync', () => { - let edits: IWorkspaceResourceEdit[]; + let dto: WorkspaceEditDto; const participant = new ExtHostDocumentSaveParticipant(nullLogService, documents, new class extends mock() { - $tryApplyWorkspaceEdit(_edits: IWorkspaceResourceEdit[]) { - edits = _edits; + $tryApplyWorkspaceEdit(_edits: WorkspaceEditDto) { + dto = _edits; return TPromise.as(true); } }); @@ -278,16 +279,17 @@ suite('ExtHostDocumentSaveParticipant', () => { return participant.$participateInSave(resource, SaveReason.EXPLICIT).then(() => { sub.dispose(); - assert.equal(edits.length, 1); - assert.equal(edits[0].edits.length, 2); + assert.equal(dto.edits.length, 1); + assert.ok(isResourceTextEdit(dto.edits[0])); + assert.equal((dto.edits[0]).edits.length, 2); }); }); test('event delivery, concurrent change', () => { - let edits: IWorkspaceResourceEdit[]; + let edits: WorkspaceEditDto; const participant = new ExtHostDocumentSaveParticipant(nullLogService, documents, new class extends mock() { - $tryApplyWorkspaceEdit(_edits: IWorkspaceResourceEdit[]) { + $tryApplyWorkspaceEdit(_edits: WorkspaceEditDto) { edits = _edits; return TPromise.as(true); } @@ -321,16 +323,20 @@ suite('ExtHostDocumentSaveParticipant', () => { test('event delivery, two listeners -> two document states', () => { const participant = new ExtHostDocumentSaveParticipant(nullLogService, documents, new class extends mock() { - $tryApplyWorkspaceEdit(_edits: IWorkspaceResourceEdit[]) { + $tryApplyWorkspaceEdit(dto: WorkspaceEditDto) { - for (const { resource, edits } of _edits) { + for (const edit of dto.edits) { + if (!isResourceTextEdit(edit)) { + continue; + } + const { resource, edits } = edit; const uri = URI.revive(resource); - for (const { newText, range } of edits) { + for (const { text, range } of edits) { documents.$acceptModelChanged(uri.toString(), { changes: [{ range, + text, rangeLength: undefined, - text: newText }], eol: undefined, versionId: documents.getDocumentData(uri).version + 1 diff --git a/src/vs/workbench/test/electron-browser/api/extHostLanguageFeatures.test.ts b/src/vs/workbench/test/electron-browser/api/extHostLanguageFeatures.test.ts index 256ebb6879f..f85ee97b9cb 100644 --- a/src/vs/workbench/test/electron-browser/api/extHostLanguageFeatures.test.ts +++ b/src/vs/workbench/test/electron-browser/api/extHostLanguageFeatures.test.ts @@ -24,7 +24,7 @@ import { IHeapService } from 'vs/workbench/api/electron-browser/mainThreadHeapSe import { ExtHostDocuments } from 'vs/workbench/api/node/extHostDocuments'; import { ExtHostDocumentsAndEditors } from 'vs/workbench/api/node/extHostDocumentsAndEditors'; import { getDocumentSymbols } from 'vs/editor/contrib/quickOpen/quickOpen'; -import { DocumentSymbolProviderRegistry, DocumentHighlightKind, Hover } from 'vs/editor/common/modes'; +import { DocumentSymbolProviderRegistry, DocumentHighlightKind, Hover, ResourceTextEdit } from 'vs/editor/common/modes'; import { getCodeLensData } from 'vs/editor/contrib/codelens/codelens'; import { getDefinitionsAtPosition, getImplementationsAtPosition, getTypeDefinitionsAtPosition } from 'vs/editor/contrib/goToDeclaration/goToDeclaration'; import { getHover } from 'vs/editor/contrib/hover/getHover'; @@ -812,7 +812,8 @@ suite('ExtHostLanguageFeatures', function () { return rpcProtocol.sync().then(() => { return rename(model, new EditorPosition(1, 1), 'newName').then(value => { - assert.equal(value.edits.length, 2); // least relevant renamer + assert.equal(value.edits.length, 1); // least relevant renamer + assert.equal((value.edits)[0].edits.length, 2); // least relevant renamer }); }); }); diff --git a/src/vs/workbench/test/electron-browser/api/extHostTextEditors.test.ts b/src/vs/workbench/test/electron-browser/api/extHostTextEditors.test.ts index b5ec3f55274..41663d277ef 100644 --- a/src/vs/workbench/test/electron-browser/api/extHostTextEditors.test.ts +++ b/src/vs/workbench/test/electron-browser/api/extHostTextEditors.test.ts @@ -7,25 +7,26 @@ import * as assert from 'assert'; import { TPromise } from 'vs/base/common/winjs.base'; import * as extHostTypes from 'vs/workbench/api/node/extHostTypes'; -import { MainContext, MainThreadEditorsShape, IWorkspaceResourceEdit } from 'vs/workbench/api/node/extHost.protocol'; +import { MainContext, MainThreadEditorsShape, WorkspaceEditDto } from 'vs/workbench/api/node/extHost.protocol'; import URI from 'vs/base/common/uri'; import { mock } from 'vs/workbench/test/electron-browser/api/mock'; import { ExtHostDocumentsAndEditors } from 'vs/workbench/api/node/extHostDocumentsAndEditors'; import { SingleProxyRPCProtocol, TestRPCProtocol } from 'vs/workbench/test/electron-browser/api/testRPCProtocol'; import { ExtHostEditors } from 'vs/workbench/api/node/extHostTextEditors'; +import { ResourceTextEdit } from 'vs/editor/common/modes'; suite('ExtHostTextEditors.applyWorkspaceEdit', () => { const resource = URI.parse('foo:bar'); let editors: ExtHostEditors; - let workspaceResourceEdits: IWorkspaceResourceEdit[]; + let workspaceResourceEdits: WorkspaceEditDto; setup(() => { workspaceResourceEdits = null; let rpcProtocol = new TestRPCProtocol(); rpcProtocol.set(MainContext.MainThreadEditors, new class extends mock() { - $tryApplyWorkspaceEdit(_workspaceResourceEdits: IWorkspaceResourceEdit[]): TPromise { + $tryApplyWorkspaceEdit(_workspaceResourceEdits: WorkspaceEditDto): TPromise { workspaceResourceEdits = _workspaceResourceEdits; return TPromise.as(true); } @@ -48,8 +49,8 @@ suite('ExtHostTextEditors.applyWorkspaceEdit', () => { let edit = new extHostTypes.WorkspaceEdit(); edit.replace(resource, new extHostTypes.Range(0, 0, 0, 0), 'hello'); return editors.applyWorkspaceEdit(edit).then((result) => { - assert.equal(workspaceResourceEdits.length, 1); - assert.equal(workspaceResourceEdits[0].modelVersionId, 1337); + assert.equal(workspaceResourceEdits.edits.length, 1); + assert.equal((workspaceResourceEdits.edits[0]).modelVersionId, 1337); }); }); @@ -57,8 +58,8 @@ suite('ExtHostTextEditors.applyWorkspaceEdit', () => { let edit = new extHostTypes.WorkspaceEdit(); edit.replace(URI.parse('foo:bar2'), new extHostTypes.Range(0, 0, 0, 0), 'hello'); return editors.applyWorkspaceEdit(edit).then((result) => { - assert.equal(workspaceResourceEdits.length, 1); - assert.ok(typeof workspaceResourceEdits[0].modelVersionId === 'undefined'); + assert.equal(workspaceResourceEdits.edits.length, 1); + assert.ok(typeof (workspaceResourceEdits.edits[0]).modelVersionId === 'undefined'); }); }); diff --git a/src/vs/workbench/test/electron-browser/api/extHostTypes.test.ts b/src/vs/workbench/test/electron-browser/api/extHostTypes.test.ts index 3e99b175fc7..478b506e60f 100644 --- a/src/vs/workbench/test/electron-browser/api/extHostTypes.test.ts +++ b/src/vs/workbench/test/electron-browser/api/extHostTypes.test.ts @@ -362,17 +362,51 @@ suite('ExtHostTypes', function () { }); - test('WorkspaceEdit should fail when editing deleted resource', () => { - const resource = URI.parse('file:///a.ts'); + // test('WorkspaceEdit should fail when editing deleted resource', () => { + // const resource = URI.parse('file:///a.ts'); + + // const edit = new types.WorkspaceEdit(); + // edit.deleteResource(resource); + // try { + // edit.insert(resource, new types.Position(0, 0), ''); + // assert.fail(false, 'Should disallow edit of deleted resource'); + // } catch { + // // expected + // } + // }); + + test('WorkspaceEdit - keep order of text and file changes', function () { const edit = new types.WorkspaceEdit(); - edit.deleteResource(resource); - try { - edit.insert(resource, new types.Position(0, 0), ''); - assert.fail(false, 'Should disallow edit of deleted resource'); - } catch { - // expected + edit.replace(URI.parse('foo:a'), new types.Range(1, 1, 1, 1), 'foo'); + edit.renameResource(URI.parse('foo:a'), URI.parse('foo:b')); + edit.replace(URI.parse('foo:a'), new types.Range(2, 1, 2, 1), 'bar'); + edit.replace(URI.parse('foo:b'), new types.Range(3, 1, 3, 1), 'bazz'); + + const all = edit.allEntries(); + assert.equal(all.length, 3); + + function isFileChange(thing: [URI, types.TextEdit[]] | [URI, URI]): thing is [URI, URI] { + const [f, s] = thing; + return URI.isUri(f) && URI.isUri(s); } + + function isTextChange(thing: [URI, types.TextEdit[]] | [URI, URI]): thing is [URI, types.TextEdit[]] { + const [f, s] = thing; + return URI.isUri(f) && Array.isArray(s); + } + + const [first, second, third] = all; + assert.equal(first[0].toString(), 'foo:a'); + assert.ok(!isFileChange(first)); + assert.ok(isTextChange(first) && first[1].length === 2); + + assert.equal(second[0].toString(), 'foo:a'); + assert.ok(isFileChange(second)); + + assert.equal(third[0].toString(), 'foo:b'); + assert.ok(!isFileChange(third)); + assert.ok(isTextChange(third) && third[1].length === 1); }); test('DocumentLink', function () { diff --git a/src/vs/workbench/test/electron-browser/api/mainThreadEditors.test.ts b/src/vs/workbench/test/electron-browser/api/mainThreadEditors.test.ts index b725c6163bd..da8f3fb2498 100644 --- a/src/vs/workbench/test/electron-browser/api/mainThreadEditors.test.ts +++ b/src/vs/workbench/test/electron-browser/api/mainThreadEditors.test.ts @@ -13,7 +13,7 @@ import { ModelServiceImpl } from 'vs/editor/common/services/modelServiceImpl'; import { TestCodeEditorService } from 'vs/editor/test/browser/testCodeEditorService'; import { ITextFileService } from 'vs/workbench/services/textfile/common/textfiles'; import { IWorkbenchEditorService } from 'vs/workbench/services/editor/common/editorService'; -import { ExtHostDocumentsAndEditorsShape, IWorkspaceResourceEdit, ExtHostContext, ExtHostDocumentsShape } from 'vs/workbench/api/node/extHost.protocol'; +import { ExtHostDocumentsAndEditorsShape, ExtHostContext, ExtHostDocumentsShape } from 'vs/workbench/api/node/extHost.protocol'; import { mock } from 'vs/workbench/test/electron-browser/api/mock'; import { IEditorGroupService } from 'vs/workbench/services/group/common/groupService'; import Event from 'vs/base/common/event'; @@ -26,6 +26,7 @@ import { EditOperation } from 'vs/editor/common/core/editOperation'; import { TestFileService } from 'vs/workbench/test/workbenchTestServices'; import { TPromise } from 'vs/base/common/winjs.base'; import { IFileStat } from 'vs/platform/files/common/files'; +import { ResourceTextEdit } from 'vs/editor/common/modes'; suite('MainThreadEditors', () => { @@ -35,7 +36,7 @@ suite('MainThreadEditors', () => { let editors: MainThreadEditors; const movedResources = new Map(); - const createdResources = new Map(); + const createdResources = new Set(); const deletedResources = new Set(); setup(() => { @@ -46,23 +47,22 @@ suite('MainThreadEditors', () => { movedResources.clear(); createdResources.clear(); deletedResources.clear(); - const fileService = new TestFileService(); - fileService.moveFile = async (from, target): TPromise => { - assert(!movedResources.has(from)); - movedResources.set(from, target); - return createMockFileStat(target); - }; - fileService.createFile = async (uri, contents): TPromise => { - assert(!createdResources.has(uri)); - createdResources.set(uri, contents); - return createMockFileStat(uri); - }; - fileService.del = async (uri): TPromise => { - assert(!deletedResources.has(uri)); - deletedResources.add(uri); + const fileService = new class extends TestFileService { + async moveFile(from, target): TPromise { + movedResources.set(from, target); + return createMockFileStat(target); + } + async createFile(uri): TPromise { + createdResources.add(uri); + return createMockFileStat(uri); + } + async del(uri): TPromise { + deletedResources.add(uri); + } }; + const textFileService = new class extends mock() { isDirty() { return false; } models = { @@ -119,11 +119,11 @@ suite('MainThreadEditors', () => { let model = modelService.createModel('something', null, resource); - let workspaceResourceEdit: IWorkspaceResourceEdit = { + let workspaceResourceEdit: ResourceTextEdit = { resource: resource, modelVersionId: model.getVersionId(), edits: [{ - newText: 'asdfg', + text: 'asdfg', range: new Range(1, 1, 1, 1) }] }; @@ -131,28 +131,22 @@ suite('MainThreadEditors', () => { // Act as if the user edited the model model.applyEdits([EditOperation.insert(new Position(0, 0), 'something')]); - return editors.$tryApplyWorkspaceEdit([workspaceResourceEdit]).then((result) => { + return editors.$tryApplyWorkspaceEdit({ edits: [workspaceResourceEdit] }).then((result) => { assert.equal(result, false); }); }); test(`applyWorkspaceEdit with only resource edit`, () => { - let model = modelService.createModel('something', null, resource); - - let workspaceResourceEdit: IWorkspaceResourceEdit = { - resource: resource, - modelVersionId: model.getVersionId(), - edits: [] - }; - - return editors.$tryApplyWorkspaceEdit([workspaceResourceEdit], { - renamedResources: [{ from: resource, to: resource }], - createdResources: [{ uri: resource, contents: 'foo' }], - deletedResources: [resource] + return editors.$tryApplyWorkspaceEdit({ + edits: [ + { oldUri: resource, newUri: resource }, + { oldUri: undefined, newUri: resource }, + { oldUri: resource, newUri: undefined } + ] }).then((result) => { assert.equal(result, true); assert.equal(movedResources.get(resource), resource); - assert.equal(createdResources.get(resource), 'foo'); + assert.equal(createdResources.has(resource), true); assert.equal(deletedResources.has(resource), true); }); }); From 155b0662667fd090b73f4dbeab0a018dc60bf38c Mon Sep 17 00:00:00 2001 From: Johannes Rieken Date: Mon, 22 Jan 2018 10:38:44 +0100 Subject: [PATCH 06/63] post merge fixes --- src/vs/workbench/api/node/extHost.protocol.ts | 2 +- .../test/electron-browser/api/mainThreadEditors.test.ts | 1 - 2 files changed, 1 insertion(+), 2 deletions(-) diff --git a/src/vs/workbench/api/node/extHost.protocol.ts b/src/vs/workbench/api/node/extHost.protocol.ts index 347ab9e9328..4b2f6b6a404 100644 --- a/src/vs/workbench/api/node/extHost.protocol.ts +++ b/src/vs/workbench/api/node/extHost.protocol.ts @@ -52,7 +52,7 @@ import { IStat, FileChangeType } from 'vs/platform/files/common/files'; import { ConfigurationScope } from 'vs/platform/configuration/common/configurationRegistry'; import { ParsedArgs } from 'vs/platform/environment/common/environment'; import { CommentRule, CharacterPair, EnterAction } from 'vs/editor/common/modes/languageConfiguration'; -import { EndOfLineSequence, ISingleEditOperation } from 'vs/editor/common/model'; +import { ISingleEditOperation } from 'vs/editor/common/model'; import { ILineMatch, IPatternInfo } from 'vs/platform/search/common/search'; export interface IEnvironment { diff --git a/src/vs/workbench/test/electron-browser/api/mainThreadEditors.test.ts b/src/vs/workbench/test/electron-browser/api/mainThreadEditors.test.ts index da8f3fb2498..03ad3ac7926 100644 --- a/src/vs/workbench/test/electron-browser/api/mainThreadEditors.test.ts +++ b/src/vs/workbench/test/electron-browser/api/mainThreadEditors.test.ts @@ -156,7 +156,6 @@ suite('MainThreadEditors', () => { function createMockFileStat(target: URI): IFileStat { return { etag: '', - hasChildren: false, isDirectory: false, name: target.path, mtime: 0, From 54616a8ffebc5204de72648a0d4d12f2897f5c89 Mon Sep 17 00:00:00 2001 From: Johannes Rieken Date: Mon, 22 Jan 2018 15:57:49 +0100 Subject: [PATCH 07/63] fixes in bulk edit --- src/vs/editor/browser/services/bulkEdit.ts | 13 +++++++++---- 1 file changed, 9 insertions(+), 4 deletions(-) diff --git a/src/vs/editor/browser/services/bulkEdit.ts b/src/vs/editor/browser/services/bulkEdit.ts index 2be87d824bf..cded7ca6be5 100644 --- a/src/vs/editor/browser/services/bulkEdit.ts +++ b/src/vs/editor/browser/services/bulkEdit.ts @@ -9,7 +9,7 @@ import { IDisposable, dispose, IReference } from 'vs/base/common/lifecycle'; import URI from 'vs/base/common/uri'; import { TPromise } from 'vs/base/common/winjs.base'; import { ITextModelService, ITextEditorModel } from 'vs/editor/common/services/resolverService'; -import { IFileService } from 'vs/platform/files/common/files'; +import { IFileService, FileChangeType } from 'vs/platform/files/common/files'; import { EditOperation } from 'vs/editor/common/core/editOperation'; import { Range } from 'vs/editor/common/core/range'; import { Selection } from 'vs/editor/common/core/selection'; @@ -17,7 +17,7 @@ import { IIdentifiedSingleEditOperation, ITextModel, EndOfLineSequence } from 'v import { IProgressRunner, emptyProgressRunner, IProgress } from 'vs/platform/progress/common/progress'; import { ICodeEditor } from 'vs/editor/browser/editorBrowser'; import { optional } from 'vs/platform/instantiation/common/instantiation'; -import { ResourceTextEdit, ResourceFileEdit, isResourceFileEdit } from 'vs/editor/common/modes'; +import { ResourceTextEdit, ResourceFileEdit, isResourceFileEdit, isResourceTextEdit } from 'vs/editor/common/modes'; import { getPathLabel } from 'vs/base/common/labels'; @@ -32,7 +32,9 @@ abstract class IRecording { // watch only when there is a fileservice available stop = fileService.onFileChanges(event => { for (const change of event.changes) { - _changes.add(change.resource.toString()); + if (change.type === FileChangeType.UPDATED) { + _changes.add(change.resource.toString()); + } } }); } @@ -304,7 +306,10 @@ export class BulkEdit { const groups: Edit[][] = []; let group: Edit[]; for (const edit of this._edits) { - if (!group || isResourceFileEdit(group[0]) === isResourceFileEdit(edit)) { + if (!group + || (isResourceFileEdit(group[0]) && !isResourceFileEdit(edit)) + || (isResourceTextEdit(group[0]) && !isResourceTextEdit(edit)) + ) { group = []; groups.push(group); } From 2835524c71808dc60e0318aba088f7e1524e3f4c Mon Sep 17 00:00:00 2001 From: Johannes Rieken Date: Mon, 22 Jan 2018 17:28:54 +0100 Subject: [PATCH 08/63] less tuple type usage --- src/vs/workbench/api/node/extHostTypes.ts | 26 +++++++++++------------ 1 file changed, 13 insertions(+), 13 deletions(-) diff --git a/src/vs/workbench/api/node/extHostTypes.ts b/src/vs/workbench/api/node/extHostTypes.ts index 59416044954..b62d6592c54 100644 --- a/src/vs/workbench/api/node/extHostTypes.ts +++ b/src/vs/workbench/api/node/extHostTypes.ts @@ -493,11 +493,11 @@ export class TextEdit { export class WorkspaceEdit implements vscode.WorkspaceEdit { - private _clock: number = 0; + private _seqPool: number = 0; - private _resourceEdits: [number/*time*/, URI, URI][] = []; + private _resourceEdits: { seq: number, from: URI, to: URI }[] = []; private _textEdits: [URI, TextEdit[]][] = []; - private _textEditsIndex = new Map(); + private _textEditsIndex = new Map(); createResource(uri: vscode.Uri): void { this.renameResource(undefined, uri); @@ -508,11 +508,11 @@ export class WorkspaceEdit implements vscode.WorkspaceEdit { } renameResource(from: vscode.Uri, to: vscode.Uri): void { - this._resourceEdits.push([this._clock++, from, to]); + this._resourceEdits.push({ seq: this._seqPool++, from, to }); } resourceEdits(): [vscode.Uri, vscode.Uri][] { - return this._resourceEdits.map(([, oldUri, newUri]) => (<[vscode.Uri, vscode.Uri]>[oldUri, newUri])); + return this._resourceEdits.map(({ from, to }) => (<[vscode.Uri, vscode.Uri]>[from, to])); } replace(uri: URI, range: Range, newText: string): void { @@ -540,9 +540,9 @@ export class WorkspaceEdit implements vscode.WorkspaceEdit { set(uri: URI, edits: TextEdit[]): void { if (!this._textEditsIndex.has(uri.toString())) { let newLen = this._textEdits.push([uri, edits]); - this._textEditsIndex.set(uri.toString(), [newLen - 1, this._clock++]); + this._textEditsIndex.set(uri.toString(), { idx: newLen - 1, seq: this._seqPool++ }); } else { - const [idx] = this._textEditsIndex.get(uri.toString()); + const { idx } = this._textEditsIndex.get(uri.toString()); this._textEdits[idx][1] = edits; } } @@ -551,7 +551,7 @@ export class WorkspaceEdit implements vscode.WorkspaceEdit { if (!this._textEditsIndex.has(uri.toString())) { return undefined; } - const [idx] = this._textEditsIndex.get(uri.toString()); + const { idx } = this._textEditsIndex.get(uri.toString()); return this._textEdits[idx][1]; } @@ -561,17 +561,17 @@ export class WorkspaceEdit implements vscode.WorkspaceEdit { } allEntries(): ([URI, TextEdit[]] | [URI, URI])[] { - // use the 'time' the we have assigned when inserting + // use the 'seq' the we have assigned when inserting // the operation and use that order in the resulting // array const res: ([URI, TextEdit[]] | [URI, URI])[] = []; this._textEditsIndex.forEach(value => { - const [index, time] = value; - res[time] = this._textEdits[index]; + const { idx, seq } = value; + res[seq] = this._textEdits[idx]; }); this._resourceEdits.forEach(value => { - const [time, oldUri, newUri] = value; - res[time] = [oldUri, newUri]; + const { seq, from, to } = value; + res[seq] = [from, to]; }); return res; } From 5bdb90de36863ae2fdfbc424e34800f4e4eb484a Mon Sep 17 00:00:00 2001 From: Alex Dima Date: Tue, 23 Jan 2018 16:40:41 +0100 Subject: [PATCH 09/63] scripts/code.sh picks up marketplace built-in extensions automatically --- build/builtInExtensions.json | 4 +++ build/gulpfile.vscode.js | 26 ++++++++++++--- build/lib/builtInExtensions.js | 32 ++++++++++++++++++ extensions/ms-vscode.node-debug/package.json | 4 +-- extensions/ms-vscode.node-debug2/package.json | 4 +-- scripts/code.sh | 3 ++ .../electron-browser/extensionPoints.ts | 4 +++ .../electron-browser/extensionService.ts | 33 ++++++++++++++++++- 8 files changed, 100 insertions(+), 10 deletions(-) create mode 100644 build/builtInExtensions.json create mode 100644 build/lib/builtInExtensions.js diff --git a/build/builtInExtensions.json b/build/builtInExtensions.json new file mode 100644 index 00000000000..4921d2a27c7 --- /dev/null +++ b/build/builtInExtensions.json @@ -0,0 +1,4 @@ +[ + { "name": "ms-vscode.node-debug", "version": "1.20.3" }, + { "name": "ms-vscode.node-debug2", "version": "1.20.1" } +] \ No newline at end of file diff --git a/build/gulpfile.vscode.js b/build/gulpfile.vscode.js index 15b95986668..b0ff0a2a732 100644 --- a/build/gulpfile.vscode.js +++ b/build/gulpfile.vscode.js @@ -44,14 +44,13 @@ const nodeModules = ['electron', 'original-fs'] // Build -const builtInExtensions = [ - { name: 'ms-vscode.node-debug', version: '1.20.3' }, - { name: 'ms-vscode.node-debug2', version: '1.20.1' } -]; +const builtInExtensions = require('./builtInExtensions'); const excludedExtensions = [ 'vscode-api-tests', - 'vscode-colorize-tests' + 'vscode-colorize-tests', + 'ms-vscode.node-debug', + 'ms-vscode.node-debug2', ]; const vscodeEntryPoints = _.flatten([ @@ -584,3 +583,20 @@ gulp.task('generate-vscode-configuration', () => { console.error(e.toString()); }); }); + +//#region Built-In Extensions +gulp.task('clean-builtInExtensions', util.rimraf('.build/builtInExtensions')); + +gulp.task('builtInExtensions', ['clean-builtInExtensions'], function() { + const marketplaceExtensions = es.merge(...builtInExtensions.map(extension => { + return ext.fromMarketplace(extension.name, extension.version) + .pipe(rename(p => p.dirname = `${extension.name}/${p.dirname}`)); + })); + + return ( + marketplaceExtensions + .pipe(util.setExecutableBit(['**/*.sh'])) + .pipe(vfs.dest('.build/builtInExtensions')) + ); +}); +//#endregion diff --git a/build/lib/builtInExtensions.js b/build/lib/builtInExtensions.js new file mode 100644 index 00000000000..0a78f4ccffd --- /dev/null +++ b/build/lib/builtInExtensions.js @@ -0,0 +1,32 @@ +/*--------------------------------------------------------------------------------------------- + * Copyright (c) Microsoft Corporation. All rights reserved. + * Licensed under the MIT License. See License.txt in the project root for license information. + *--------------------------------------------------------------------------------------------*/ + +'use strict'; + +const fs = require('fs'); +const path = require('path'); +const root = path.dirname(path.dirname(__dirname)); + +function isUpToDate(extension) { + const packagePath = path.join(root, '.build', 'builtInExtensions', extension.name, 'package.json'); + if (!fs.existsSync(packagePath)) { + return false; + } + const packageContents = fs.readFileSync(packagePath); + try { + const diskVersion = JSON.parse(packageContents).version; + return (diskVersion === extension.version); + } catch(err) { + return false; + } +} + +const builtInExtensions = require('../builtInExtensions'); +builtInExtensions.forEach((extension) => { + if (!isUpToDate(extension)) { + process.exit(1); + } +}); +process.exit(0); diff --git a/extensions/ms-vscode.node-debug/package.json b/extensions/ms-vscode.node-debug/package.json index 87569809e43..9d065dd4a5c 100644 --- a/extensions/ms-vscode.node-debug/package.json +++ b/extensions/ms-vscode.node-debug/package.json @@ -1,7 +1,7 @@ { - "name": "node-debug-placeholder", + "name": "node-debug", "version": "1.6.0", - "publisher": "vscode", + "publisher": "ms-vscode", "engines": { "vscode": "1.6.x" } diff --git a/extensions/ms-vscode.node-debug2/package.json b/extensions/ms-vscode.node-debug2/package.json index 26777f7dae6..96c454263b3 100644 --- a/extensions/ms-vscode.node-debug2/package.json +++ b/extensions/ms-vscode.node-debug2/package.json @@ -1,7 +1,7 @@ { - "name": "node-debug2-placeholder", + "name": "node-debug2", "version": "0.0.3", - "publisher": "vscode", + "publisher": "ms-vscode", "engines": { "vscode": "1.6.x" } diff --git a/scripts/code.sh b/scripts/code.sh index 6339ad06bd4..089d380c1b5 100755 --- a/scripts/code.sh +++ b/scripts/code.sh @@ -24,6 +24,9 @@ function code() { # Get electron node build/lib/electron.js || ./node_modules/.bin/gulp electron + # Get built-in extensions + node build/lib/builtInExtensions.js || ./node_modules/.bin/gulp builtInExtensions + # Build test -d out || ./node_modules/.bin/gulp compile diff --git a/src/vs/workbench/services/extensions/electron-browser/extensionPoints.ts b/src/vs/workbench/services/extensions/electron-browser/extensionPoints.ts index b0b0f300177..1ce6fdca2c2 100644 --- a/src/vs/workbench/services/extensions/electron-browser/extensionPoints.ts +++ b/src/vs/workbench/services/extensions/electron-browser/extensionPoints.ts @@ -334,6 +334,10 @@ export class ExtensionScanner { } const rawFolders = await pfs.readDirsInDir(absoluteFolderPath); + + // Ensure the same extension order + rawFolders.sort(); + let folders: string[] = null; if (isBuiltin) { folders = rawFolders; diff --git a/src/vs/workbench/services/extensions/electron-browser/extensionService.ts b/src/vs/workbench/services/extensions/electron-browser/extensionService.ts index 8abc3ff6140..4d51f56bd85 100644 --- a/src/vs/workbench/services/extensions/electron-browser/extensionService.ts +++ b/src/vs/workbench/services/extensions/electron-browser/extensionService.ts @@ -44,6 +44,7 @@ import * as strings from 'vs/base/common/strings'; import { RPCProtocol } from 'vs/workbench/services/extensions/node/rpcProtocol'; const SystemExtensionsRoot = path.normalize(path.join(URI.parse(require.toUrl('')).fsPath, '..', 'extensions')); +const ExtraDevSystemExtensionsRoot = path.normalize(path.join(URI.parse(require.toUrl('')).fsPath, '..', '.build', 'builtInExtensions')); // Enable to see detailed message communication between window and extension host const logExtensionHostCommunication = false; @@ -624,6 +625,36 @@ export class ExtensionService extends Disposable implements IExtensionService { log ); + let finalBuiltinExtensions: TPromise = builtinExtensions; + + if (devMode) { + const extraBuiltinExtensions = ExtensionScanner.scanExtensions(new ExtensionScannerInput(version, commit, locale, devMode, ExtraDevSystemExtensionsRoot, true), log); + finalBuiltinExtensions = TPromise.join([builtinExtensions, extraBuiltinExtensions]).then(([builtinExtensions, extraBuiltinExtensions]) => { + let resultMap: { [id: string]: IExtensionDescription; } = Object.create(null); + for (let i = 0, len = builtinExtensions.length; i < len; i++) { + resultMap[builtinExtensions[i].id] = builtinExtensions[i]; + } + // Overwrite with extensions found in extra + for (let i = 0, len = extraBuiltinExtensions.length; i < len; i++) { + resultMap[extraBuiltinExtensions[i].id] = extraBuiltinExtensions[i]; + } + + let resultArr = Object.keys(resultMap).map((id) => resultMap[id]); + resultArr.sort((a, b) => { + const aLastSegment = path.basename(a.extensionFolderPath); + const bLastSegment = path.basename(b.extensionFolderPath); + if (aLastSegment < bLastSegment) { + return -1; + } + if (aLastSegment > bLastSegment) { + return 1; + } + return 0; + }); + return resultArr; + }); + } + const userExtensions = ( environmentService.disableExtensions || !environmentService.extensionsPath ? TPromise.as([]) @@ -646,7 +677,7 @@ export class ExtensionService extends Disposable implements IExtensionService { : TPromise.as([]) ); - return TPromise.join([builtinExtensions, userExtensions, developedExtensions]) + return TPromise.join([finalBuiltinExtensions, userExtensions, developedExtensions]) .then((extensionDescriptions: IExtensionDescription[][]) => { const system = extensionDescriptions[0]; const user = extensionDescriptions[1]; From 018cc146a786cf3adf04ab5d56b6a0f301e5ea3e Mon Sep 17 00:00:00 2001 From: Joao Moreno Date: Tue, 23 Jan 2018 16:33:06 +0100 Subject: [PATCH 10/63] use 32 bit version of inno_updater --- build/win32/inno_updater.exe | Bin 181248 -> 147456 bytes 1 file changed, 0 insertions(+), 0 deletions(-) diff --git a/build/win32/inno_updater.exe b/build/win32/inno_updater.exe index 6b8c7a981423d8c8c8cd66b1389b5864d2731d41..c83bcd48cacd90aaa9e5e0a2fda90ae0f568e210 100644 GIT binary patch literal 147456 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%0Ati%`MS+43hdoZ2gUTyL`> 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%0D!hP36)m2 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 ieUbal?F-vK7U{MiWlndSmg}W8fo72K Date: Tue, 23 Jan 2018 16:59:23 +0100 Subject: [PATCH 11/63] make WorkspaceEdit more sane --- src/vs/workbench/api/node/extHostTypes.ts | 42 +++++++++++++---------- 1 file changed, 23 insertions(+), 19 deletions(-) diff --git a/src/vs/workbench/api/node/extHostTypes.ts b/src/vs/workbench/api/node/extHostTypes.ts index b62d6592c54..5a230349a39 100644 --- a/src/vs/workbench/api/node/extHostTypes.ts +++ b/src/vs/workbench/api/node/extHostTypes.ts @@ -496,8 +496,7 @@ export class WorkspaceEdit implements vscode.WorkspaceEdit { private _seqPool: number = 0; private _resourceEdits: { seq: number, from: URI, to: URI }[] = []; - private _textEdits: [URI, TextEdit[]][] = []; - private _textEditsIndex = new Map(); + private _textEdits = new Map(); createResource(uri: vscode.Uri): void { this.renameResource(undefined, uri); @@ -521,8 +520,9 @@ export class WorkspaceEdit implements vscode.WorkspaceEdit { if (array) { array.push(edit); } else { - this.set(uri, [edit]); + array = [edit]; } + this.set(uri, array); } insert(resource: URI, position: Position, newText: string): void { @@ -534,30 +534,34 @@ export class WorkspaceEdit implements vscode.WorkspaceEdit { } has(uri: URI): boolean { - return this._textEditsIndex.has(uri.toString()); + return this._textEdits.has(uri.toString()); } set(uri: URI, edits: TextEdit[]): void { - if (!this._textEditsIndex.has(uri.toString())) { - let newLen = this._textEdits.push([uri, edits]); - this._textEditsIndex.set(uri.toString(), { idx: newLen - 1, seq: this._seqPool++ }); + let data = this._textEdits.get(uri.toString()); + if (!data) { + data = { seq: this._seqPool++, uri, edits: [] }; + this._textEdits.set(uri.toString(), data); + } + if (!edits) { + data.edits = undefined; } else { - const { idx } = this._textEditsIndex.get(uri.toString()); - this._textEdits[idx][1] = edits; + data.edits = edits.slice(0); } } get(uri: URI): TextEdit[] { - if (!this._textEditsIndex.has(uri.toString())) { + if (!this._textEdits.has(uri.toString())) { return undefined; } - const { idx } = this._textEditsIndex.get(uri.toString()); - return this._textEdits[idx][1]; + const { edits } = this._textEdits.get(uri.toString()); + return edits ? edits.slice() : undefined; } entries(): [URI, TextEdit[]][] { - // todo@joh - make this immutable - return this._textEdits; + const res: [URI, TextEdit[]][] = []; + this._textEdits.forEach(value => res.push([value.uri, value.edits])); + return res.slice(); } allEntries(): ([URI, TextEdit[]] | [URI, URI])[] { @@ -565,9 +569,9 @@ export class WorkspaceEdit implements vscode.WorkspaceEdit { // the operation and use that order in the resulting // array const res: ([URI, TextEdit[]] | [URI, URI])[] = []; - this._textEditsIndex.forEach(value => { - const { idx, seq } = value; - res[seq] = this._textEdits[idx]; + this._textEdits.forEach(value => { + const { seq, uri, edits } = value; + res[seq] = [uri, edits]; }); this._resourceEdits.forEach(value => { const { seq, from, to } = value; @@ -577,11 +581,11 @@ export class WorkspaceEdit implements vscode.WorkspaceEdit { } get size(): number { - return this._textEdits.length + this._resourceEdits.length; + return this._textEdits.size + this._resourceEdits.length; } toJSON(): any { - return this._textEdits; + return this.entries(); } } From 1ccfbe4024aa6eb439c8f4d93d64e9789712af64 Mon Sep 17 00:00:00 2001 From: Johannes Rieken Date: Tue, 23 Jan 2018 17:21:43 +0100 Subject: [PATCH 12/63] missing merge change --- src/vs/workbench/api/node/extHost.protocol.ts | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/vs/workbench/api/node/extHost.protocol.ts b/src/vs/workbench/api/node/extHost.protocol.ts index 8827d4cf011..b6272b1f035 100644 --- a/src/vs/workbench/api/node/extHost.protocol.ts +++ b/src/vs/workbench/api/node/extHost.protocol.ts @@ -648,7 +648,7 @@ export interface CodeActionDto { edit?: WorkspaceEditDto; diagnostics?: IMarkerData[]; command?: modes.Command; - scope?: string; + kind?: string; } export interface ExtHostLanguageFeaturesShape { From de24732aa964197104c0e8a3b4ddd2aeb3b383b7 Mon Sep 17 00:00:00 2001 From: Sandeep Somavarapu Date: Tue, 23 Jan 2018 17:16:08 +0100 Subject: [PATCH 13/63] Implement #39574 --- .../sharedProcess/sharedProcessMain.ts | 6 ++- src/vs/code/electron-main/app.ts | 6 +++ src/vs/platform/log/common/bufferLog.ts | 19 ++------ src/vs/platform/log/common/logIpc.ts | 43 ++++++++++++++++++ src/vs/platform/log/node/spdlogService.ts | 28 +++++------- .../electron-browser/mainThreadLogService.ts | 24 ++++++++++ src/vs/workbench/api/node/extHost.protocol.ts | 7 ++- .../api/node/extHostExtensionService.ts | 2 +- .../workbench/api/node/extHostLogService.ts | 44 ++++++++++++------- src/vs/workbench/electron-browser/main.ts | 16 ++++--- 10 files changed, 137 insertions(+), 58 deletions(-) create mode 100644 src/vs/platform/log/common/logIpc.ts create mode 100644 src/vs/workbench/api/electron-browser/mainThreadLogService.ts diff --git a/src/vs/code/electron-browser/sharedProcess/sharedProcessMain.ts b/src/vs/code/electron-browser/sharedProcess/sharedProcessMain.ts index 2f0521cf00e..17fdc47c3e7 100644 --- a/src/vs/code/electron-browser/sharedProcess/sharedProcessMain.ts +++ b/src/vs/code/electron-browser/sharedProcess/sharedProcessMain.ts @@ -38,7 +38,8 @@ import { ipcRenderer } from 'electron'; import { IDisposable, dispose } from 'vs/base/common/lifecycle'; import { createSharedProcessContributions } from 'vs/code/electron-browser/sharedProcess/contrib/contributions'; import { createSpdLogService } from 'vs/platform/log/node/spdlogService'; -import { ILogService } from 'vs/platform/log/common/log'; +import { ILogService, FollowerLogService } from 'vs/platform/log/common/log'; +import { LogLevelChannelClient } from 'vs/platform/log/common/logIpc'; export interface ISharedProcessConfiguration { readonly machineId: string; @@ -81,7 +82,8 @@ function main(server: Server, initData: ISharedProcessInitData, configuration: I const services = new ServiceCollection(); const environmentService = new EnvironmentService(initData.args, process.execPath); - const logService = createSpdLogService('sharedprocess', environmentService); + const logLevelClient = new LogLevelChannelClient(server.getChannel('loglevel', { route: () => 'main' })); + const logService = new FollowerLogService(logLevelClient, createSpdLogService('sharedprocess', environmentService)); process.once('exit', () => logService.dispose()); logService.info('main', JSON.stringify(configuration)); diff --git a/src/vs/code/electron-main/app.ts b/src/vs/code/electron-main/app.ts index 24fb6d6ca51..eec6c2bae9b 100644 --- a/src/vs/code/electron-main/app.ts +++ b/src/vs/code/electron-main/app.ts @@ -57,6 +57,7 @@ import { DarwinUpdateService } from 'vs/platform/update/electron-main/updateServ import { IIssueService } from 'vs/platform/issue/common/issue'; import { IssueChannel } from 'vs/platform/issue/common/issueIpc'; import { IssueService } from 'vs/platform/issue/electron-main/issueService'; +import { LogLevelChannel } from 'vs/platform/log/common/logIpc'; export class CodeApplication { @@ -378,6 +379,11 @@ export class CodeApplication { this.electronIpcServer.registerChannel('windows', windowsChannel); this.sharedProcessClient.done(client => client.registerChannel('windows', windowsChannel)); + // Log level management + const logLevelChannel = new LogLevelChannel(accessor.get(ILogService)); + this.electronIpcServer.registerChannel('loglevel', logLevelChannel); + this.sharedProcessClient.done(client => client.registerChannel('loglevel', logLevelChannel)); + // Lifecycle this.lifecycleService.ready(); diff --git a/src/vs/platform/log/common/bufferLog.ts b/src/vs/platform/log/common/bufferLog.ts index caa628e51da..65fa32adb0e 100644 --- a/src/vs/platform/log/common/bufferLog.ts +++ b/src/vs/platform/log/common/bufferLog.ts @@ -5,7 +5,7 @@ 'use strict'; -import { ILogService, LogLevel } from 'vs/platform/log/common/log'; +import { ILogService, LogLevel, AbstractLogService } from 'vs/platform/log/common/log'; interface ILog { level: LogLevel; @@ -24,17 +24,12 @@ function getLogFunction(logger: ILogService, level: LogLevel): Function { } } -export class BufferLogService implements ILogService { +export class BufferLogService extends AbstractLogService implements ILogService { _serviceBrand: any; private buffer: ILog[] = []; private _logger: ILogService | undefined = undefined; - constructor( - private level: LogLevel = LogLevel.Error - ) { - } - set logger(logger: ILogService) { this._logger = logger; @@ -46,19 +41,11 @@ export class BufferLogService implements ILogService { this.buffer = []; } - setLevel(logLevel: LogLevel): void { - this.level = logLevel; - } - - getLevel(): LogLevel { - return this.level; - } - private _log(level: LogLevel, args: IArguments): void { if (this._logger) { const fn = getLogFunction(this._logger, level); fn.apply(this._logger, args); - } else if (this.level <= level) { + } else if (this.getLevel() <= level) { this.buffer.push({ level, args }); } } diff --git a/src/vs/platform/log/common/logIpc.ts b/src/vs/platform/log/common/logIpc.ts new file mode 100644 index 00000000000..9eb0764c54e --- /dev/null +++ b/src/vs/platform/log/common/logIpc.ts @@ -0,0 +1,43 @@ +/*--------------------------------------------------------------------------------------------- + * Copyright (c) Microsoft Corporation. All rights reserved. + * Licensed under the MIT License. See License.txt in the project root for license information. + *--------------------------------------------------------------------------------------------*/ + +import { IChannel, eventToCall, eventFromCall } from 'vs/base/parts/ipc/common/ipc'; +import { TPromise } from 'vs/base/common/winjs.base'; +import { LogLevel, ILogService } from 'vs/platform/log/common/log'; +import Event, { buffer } from 'vs/base/common/event'; + +export interface ILogLevelManagementChannel extends IChannel { + call(command: 'event:onDidChangeLogLevel'): TPromise; + call(command: 'setLogLevel', logLevel: LogLevel): TPromise; +} + +export class LogLevelChannel implements ILogLevelManagementChannel { + + onDidChangeLogLevel: Event; + + constructor(private service: ILogService) { + this.onDidChangeLogLevel = buffer(service.onDidChangeLogLevel, true); + } + + call(command: string, arg?: any): TPromise { + switch (command) { + case 'event:onDidChangeLogLevel': return eventToCall(this.onDidChangeLogLevel); + case 'setLogLevel': this.service.setLevel(arg); return TPromise.as(null); + } + return undefined; + } +} + +export class LogLevelChannelClient { + + constructor(private channel: ILogLevelManagementChannel) { } + + private _onDidChangeLogLevel = eventFromCall(this.channel, 'event:onDidChangeLogLevel'); + get onDidChangeLogLevel(): Event { return this._onDidChangeLogLevel; } + + setLogLevel(level: LogLevel): TPromise { + return this.channel.call('setLogLevel', level); + } +} \ No newline at end of file diff --git a/src/vs/platform/log/node/spdlogService.ts b/src/vs/platform/log/node/spdlogService.ts index 6493d6e1c8d..9df00ce99f6 100644 --- a/src/vs/platform/log/node/spdlogService.ts +++ b/src/vs/platform/log/node/spdlogService.ts @@ -6,7 +6,7 @@ 'use strict'; import * as path from 'path'; -import { ILogService, LogLevel, NullLogService } from 'vs/platform/log/common/log'; +import { ILogService, LogLevel, NullLogService, AbstractLogService } from 'vs/platform/log/common/log'; import { IEnvironmentService } from 'vs/platform/environment/common/environment'; import { RotatingLogger, setAsyncMode } from 'spdlog'; @@ -25,50 +25,44 @@ export function createSpdLogService(processName: string, environmentService: IEn return new NullLogService(); } -class SpdLogService implements ILogService { +class SpdLogService extends AbstractLogService implements ILogService { _serviceBrand: any; constructor( private readonly logger: RotatingLogger, - private level: LogLevel = LogLevel.Error + level: LogLevel ) { - } - - setLevel(logLevel: LogLevel): void { - this.level = logLevel; - } - - getLevel(): LogLevel { - return this.level; + super(); + this.setLevel(level); } trace(): void { - if (this.level <= LogLevel.Trace) { + if (this.getLevel() <= LogLevel.Trace) { this.logger.trace(this.format(arguments)); } } debug(): void { - if (this.level <= LogLevel.Debug) { + if (this.getLevel() <= LogLevel.Debug) { this.logger.debug(this.format(arguments)); } } info(): void { - if (this.level <= LogLevel.Info) { + if (this.getLevel() <= LogLevel.Info) { this.logger.info(this.format(arguments)); } } warn(): void { - if (this.level <= LogLevel.Warning) { + if (this.getLevel() <= LogLevel.Warning) { this.logger.warn(this.format(arguments)); } } error(): void { - if (this.level <= LogLevel.Error) { + if (this.getLevel() <= LogLevel.Error) { const arg = arguments[0]; if (arg instanceof Error) { @@ -82,7 +76,7 @@ class SpdLogService implements ILogService { } critical(): void { - if (this.level <= LogLevel.Critical) { + if (this.getLevel() <= LogLevel.Critical) { this.logger.critical(this.format(arguments)); } } diff --git a/src/vs/workbench/api/electron-browser/mainThreadLogService.ts b/src/vs/workbench/api/electron-browser/mainThreadLogService.ts new file mode 100644 index 00000000000..c24b24c619a --- /dev/null +++ b/src/vs/workbench/api/electron-browser/mainThreadLogService.ts @@ -0,0 +1,24 @@ +/*--------------------------------------------------------------------------------------------- + * Copyright (c) Microsoft Corporation. All rights reserved. + * Licensed under the MIT License. See License.txt in the project root for license information. + *--------------------------------------------------------------------------------------------*/ + +'use strict'; + +import { ExtHostContext, IExtHostContext } from '../node/extHost.protocol'; +import { extHostCustomer } from 'vs/workbench/api/electron-browser/extHostCustomers'; +import { ILogService } from 'vs/platform/log/common/log'; +import { Disposable } from 'vs/base/common/lifecycle'; + +@extHostCustomer +export class MainThreadLogLevelManagementChannel extends Disposable { + + constructor( + extHostContext: IExtHostContext, + @ILogService logService: ILogService, + ) { + super(); + this._register(logService.onDidChangeLogLevel(level => extHostContext.getProxy(ExtHostContext.ExtHostLogService).$setLogLevel(level))); + } + +} \ No newline at end of file diff --git a/src/vs/workbench/api/node/extHost.protocol.ts b/src/vs/workbench/api/node/extHost.protocol.ts index d4dcd03d363..955e29ee3fc 100644 --- a/src/vs/workbench/api/node/extHost.protocol.ts +++ b/src/vs/workbench/api/node/extHost.protocol.ts @@ -54,6 +54,7 @@ import { ParsedArgs } from 'vs/platform/environment/common/environment'; import { CommentRule, CharacterPair, EnterAction } from 'vs/editor/common/modes/languageConfiguration'; import { EndOfLineSequence, ISingleEditOperation } from 'vs/editor/common/model'; import { ILineMatch, IPatternInfo } from 'vs/platform/search/common/search'; +import { LogLevel } from 'vs/platform/log/common/log'; export interface IEnvironment { isExtensionDevelopmentDebug: boolean; @@ -744,6 +745,10 @@ export interface ExtHostWindowShape { $onDidChangeWindowFocus(value: boolean): void; } +export interface ExtHostLogServiceShape { + $setLogLevel(level: LogLevel); +} + // --- proxy identifiers export const MainContext = { @@ -794,7 +799,7 @@ export const ExtHostContext = { ExtHostLanguageFeatures: createExtId('ExtHostLanguageFeatures'), ExtHostQuickOpen: createExtId('ExtHostQuickOpen'), ExtHostExtensionService: createExtId('ExtHostExtensionService'), - // ExtHostLogService: createExtId('ExtHostLogService'), + ExtHostLogService: createExtId('ExtHostLogService'), ExtHostTerminalService: createExtId('ExtHostTerminalService'), ExtHostSCM: createExtId('ExtHostSCM'), ExtHostTask: createExtId('ExtHostTask', ProxyType.CustomMarshaller), diff --git a/src/vs/workbench/api/node/extHostExtensionService.ts b/src/vs/workbench/api/node/extHostExtensionService.ts index d39a58a432e..fb50ec716d8 100644 --- a/src/vs/workbench/api/node/extHostExtensionService.ts +++ b/src/vs/workbench/api/node/extHostExtensionService.ts @@ -150,7 +150,7 @@ export class ExtHostExtensionService implements ExtHostExtensionServiceShape { this._storagePath = new ExtensionStoragePath(initData.workspace, initData.environment); this._proxy = extHostContext.getProxy(MainContext.MainThreadExtensionService); this._activator = null; - this._extHostLogService = new ExtHostLogService(environmentService); + this._extHostLogService = new ExtHostLogService(environmentService, this._logService); // initialize API first (i.e. do not release barrier until the API is initialized) const apiFactory = createApiFactory(initData, extHostContext, extHostWorkspace, extHostConfiguration, this, logService); diff --git a/src/vs/workbench/api/node/extHostLogService.ts b/src/vs/workbench/api/node/extHostLogService.ts index fff0755018d..4689e038ae8 100644 --- a/src/vs/workbench/api/node/extHostLogService.ts +++ b/src/vs/workbench/api/node/extHostLogService.ts @@ -8,47 +8,59 @@ import * as path from 'path'; import * as vscode from 'vscode'; import { TPromise } from 'vs/base/common/winjs.base'; import { mkdirp, dirExists } from 'vs/base/node/pfs'; -import Event, { Emitter } from 'vs/base/common/event'; +import Event from 'vs/base/common/event'; import { LogLevel } from 'vs/workbench/api/node/extHostTypes'; import { ILogService } from 'vs/platform/log/common/log'; import { createSpdLogService } from 'vs/platform/log/node/spdlogService'; import { IEnvironmentService } from 'vs/platform/environment/common/environment'; import { memoize } from 'vs/base/common/decorators'; +import { ExtHostLogServiceShape } from 'vs/workbench/api/node/extHost.protocol'; +import { Disposable } from 'vs/base/common/lifecycle'; -export class ExtHostLogService { +export class ExtHostLogService extends Disposable implements ExtHostLogServiceShape { private _loggers: Map = new Map(); - constructor(private _environmentService: IEnvironmentService) { + constructor( + private _environmentService: IEnvironmentService, + private _logService: ILogService + ) { + super(); + } + + $setLogLevel(level: LogLevel) { + this._logService.setLevel(level); } getExtLogger(extensionID: string): ExtHostLogger { - if (!this._loggers.has(extensionID)) { - const logService = createSpdLogService(extensionID, this._environmentService, extensionID); - const logsDirPath = path.join(this._environmentService.logsPath, extensionID); - this._loggers.set(extensionID, new ExtHostLogger(logService, logsDirPath)); + let logger = this._loggers.get(extensionID); + if (!logger) { + logger = this.createLogger(extensionID); + this._loggers.set(extensionID, logger); } + return logger; + } - return this._loggers.get(extensionID); + private createLogger(extensionID: string): ExtHostLogger { + const logService = createSpdLogService(extensionID, this._environmentService, extensionID); + const logsDirPath = path.join(this._environmentService.logsPath, extensionID); + this._register(this._logService.onDidChangeLogLevel(level => logService.setLevel(level))); + return new ExtHostLogger(logService, logsDirPath); } } export class ExtHostLogger implements vscode.Logger { - private _currentLevel: LogLevel; - private _onDidChangeLogLevel: Emitter; constructor( private readonly _logService: ILogService, private readonly _logDirectory: string ) { - this._currentLevel = this._logService.getLevel(); - this._onDidChangeLogLevel = new Emitter(); - this.onDidChangeLogLevel = this._onDidChangeLogLevel.event; } - // TODO - readonly onDidChangeLogLevel: Event; + get onDidChangeLogLevel(): Event { + return this._logService.onDidChangeLogLevel; + } - get currentLevel(): LogLevel { return this._currentLevel; } + get currentLevel(): LogLevel { return this._logService.getLevel(); } @memoize get logDirectory(): TPromise { diff --git a/src/vs/workbench/electron-browser/main.ts b/src/vs/workbench/electron-browser/main.ts index 9f6e912a251..f40edbae3fc 100644 --- a/src/vs/workbench/electron-browser/main.ts +++ b/src/vs/workbench/electron-browser/main.ts @@ -43,9 +43,10 @@ import { IWorkspacesService } from 'vs/platform/workspaces/common/workspaces'; import { createSpdLogService } from 'vs/platform/log/node/spdlogService'; import fs = require('fs'); -import { ConsoleLogService, MultiplexLogService } from 'vs/platform/log/common/log'; +import { ConsoleLogService, MultiplexLogService, ILogService, FollowerLogService } from 'vs/platform/log/common/log'; import { IssueChannelClient } from 'vs/platform/issue/common/issueIpc'; import { IIssueService } from 'vs/platform/issue/common/issue'; +import { LogLevelChannelClient } from 'vs/platform/log/common/logIpc'; gracefulFs.gracefulify(fs); // enable gracefulFs export function startup(configuration: IWindowConfiguration): TPromise { @@ -75,10 +76,7 @@ function openWorkbench(configuration: IWindowConfiguration): TPromise { const mainServices = createMainProcessServices(mainProcessClient, configuration); const environmentService = new EnvironmentService(configuration, configuration.execPath); - const spdlogService = createSpdLogService(`renderer${configuration.windowId}`, environmentService); - const consoleLogService = new ConsoleLogService(environmentService); - const logService = new MultiplexLogService([consoleLogService, spdlogService]); - + const logService = createLogService(mainProcessClient, configuration, environmentService); logService.trace('openWorkbench configuration', JSON.stringify(configuration)); // Since the configuration service is one of the core services that is used in so many places, we initialize it @@ -200,6 +198,14 @@ function createStorageService(workspaceService: IWorkspaceContextService, enviro return new StorageService(storage, storage, workspaceId, secondaryWorkspaceId); } +function createLogService(mainProcessClient: ElectronIPCClient, configuration: IWindowConfiguration, environmentService: IEnvironmentService): ILogService { + const spdlogService = createSpdLogService(`renderer${configuration.windowId}`, environmentService); + const consoleLogService = new ConsoleLogService(environmentService); + const logService = new MultiplexLogService([consoleLogService, spdlogService]); + const logLevelClient = new LogLevelChannelClient(mainProcessClient.getChannel('loglevel')); + return new FollowerLogService(logLevelClient, logService); +} + function createMainProcessServices(mainProcessClient: ElectronIPCClient, configuration: IWindowConfiguration): ServiceCollection { const serviceCollection = new ServiceCollection(); From b0cd8f8481e12d221374fa39ebd344e74cdec5ac Mon Sep 17 00:00:00 2001 From: Sandeep Somavarapu Date: Tue, 23 Jan 2018 17:28:43 +0100 Subject: [PATCH 14/63] #39574 --- src/vs/platform/log/common/log.ts | 125 ++++++++++++++++++++---------- 1 file changed, 84 insertions(+), 41 deletions(-) diff --git a/src/vs/platform/log/common/log.ts b/src/vs/platform/log/common/log.ts index 823ec1cd2e0..f7019d95418 100644 --- a/src/vs/platform/log/common/log.ts +++ b/src/vs/platform/log/common/log.ts @@ -7,8 +7,10 @@ import { IEnvironmentService } from 'vs/platform/environment/common/environment'; import { createDecorator as createServiceDecorator } from 'vs/platform/instantiation/common/instantiation'; -import { IDisposable } from 'vs/base/common/lifecycle'; +import { IDisposable, Disposable } from 'vs/base/common/lifecycle'; import { isWindows } from 'vs/base/common/platform'; +import Event, { Emitter } from 'vs/base/common/event'; +import { LogLevelChannelClient } from 'vs/platform/log/common/logIpc'; export const ILogService = createServiceDecorator('logService'); @@ -25,6 +27,7 @@ export enum LogLevel { export interface ILogService extends IDisposable { _serviceBrand: any; + onDidChangeLogLevel: Event; setLevel(level: LogLevel): void; getLevel(): LogLevel; trace(message: string, ...args: any[]): void; @@ -35,27 +38,37 @@ export interface ILogService extends IDisposable { critical(message: string | Error, ...args: any[]): void; } -export class ConsoleLogMainService implements ILogService { +export abstract class AbstractLogService extends Disposable { - _serviceBrand: any; private level: LogLevel = LogLevel.Error; - private useColors: boolean; - - constructor( @IEnvironmentService environmentService: IEnvironmentService) { - this.setLevel(environmentService.logLevel); - this.useColors = !isWindows; - } + private readonly _onDidChangeLogLevel: Emitter = this._register(new Emitter()); + readonly onDidChangeLogLevel: Event = this._onDidChangeLogLevel.event; setLevel(level: LogLevel): void { - this.level = level; + if (this.level !== level) { + this.level = level; + this._onDidChangeLogLevel.fire(this.level); + } } getLevel(): LogLevel { return this.level; } +} + +export class ConsoleLogMainService extends AbstractLogService implements ILogService { + + _serviceBrand: any; + private useColors: boolean; + + constructor( @IEnvironmentService environmentService: IEnvironmentService) { + super(); + this.setLevel(environmentService.logLevel); + this.useColors = !isWindows; + } trace(message: string, ...args: any[]): void { - if (this.level <= LogLevel.Trace) { + if (this.getLevel() <= LogLevel.Trace) { if (this.useColors) { console.log(`\x1b[90m[main ${new Date().toLocaleTimeString()}]\x1b[0m`, message, ...args); } else { @@ -65,7 +78,7 @@ export class ConsoleLogMainService implements ILogService { } debug(message: string, ...args: any[]): void { - if (this.level <= LogLevel.Debug) { + if (this.getLevel() <= LogLevel.Debug) { if (this.useColors) { console.log(`\x1b[90m[main ${new Date().toLocaleTimeString()}]\x1b[0m`, message, ...args); } else { @@ -75,7 +88,7 @@ export class ConsoleLogMainService implements ILogService { } info(message: string, ...args: any[]): void { - if (this.level <= LogLevel.Info) { + if (this.getLevel() <= LogLevel.Info) { if (this.useColors) { console.log(`\x1b[90m[main ${new Date().toLocaleTimeString()}]\x1b[0m`, message, ...args); } else { @@ -85,7 +98,7 @@ export class ConsoleLogMainService implements ILogService { } warn(message: string | Error, ...args: any[]): void { - if (this.level <= LogLevel.Warning) { + if (this.getLevel() <= LogLevel.Warning) { if (this.useColors) { console.warn(`\x1b[93m[main ${new Date().toLocaleTimeString()}]\x1b[0m`, message, ...args); } else { @@ -95,7 +108,7 @@ export class ConsoleLogMainService implements ILogService { } error(message: string, ...args: any[]): void { - if (this.level <= LogLevel.Error) { + if (this.getLevel() <= LogLevel.Error) { if (this.useColors) { console.error(`\x1b[91m[main ${new Date().toLocaleTimeString()}]\x1b[0m`, message, ...args); } else { @@ -105,7 +118,7 @@ export class ConsoleLogMainService implements ILogService { } critical(message: string, ...args: any[]): void { - if (this.level <= LogLevel.Critical) { + if (this.getLevel() <= LogLevel.Critical) { if (this.useColors) { console.error(`\x1b[90m[main ${new Date().toLocaleTimeString()}]\x1b[0m`, message, ...args); } else { @@ -119,55 +132,47 @@ export class ConsoleLogMainService implements ILogService { } } -export class ConsoleLogService implements ILogService { +export class ConsoleLogService extends AbstractLogService implements ILogService { _serviceBrand: any; - private level: LogLevel = LogLevel.Error; constructor( @IEnvironmentService environmentService: IEnvironmentService) { + super(); this.setLevel(environmentService.logLevel); } - setLevel(level: LogLevel): void { - this.level = level; - } - - getLevel(): LogLevel { - return this.level; - } - trace(message: string, ...args: any[]): void { - if (this.level <= LogLevel.Trace) { + if (this.getLevel() <= LogLevel.Trace) { console.log('%cTRACE', 'color: #888', message, ...args); } } debug(message: string, ...args: any[]): void { - if (this.level <= LogLevel.Debug) { + if (this.getLevel() <= LogLevel.Debug) { console.log('%cDEBUG', 'background: #eee; color: #888', message, ...args); } } info(message: string, ...args: any[]): void { - if (this.level <= LogLevel.Info) { + if (this.getLevel() <= LogLevel.Info) { console.log('%c INFO', 'color: #33f', message, ...args); } } warn(message: string | Error, ...args: any[]): void { - if (this.level <= LogLevel.Warning) { + if (this.getLevel() <= LogLevel.Warning) { console.log('%c WARN', 'color: #993', message, ...args); } } error(message: string, ...args: any[]): void { - if (this.level <= LogLevel.Error) { + if (this.getLevel() <= LogLevel.Error) { console.log('%c ERR', 'color: #f33', message, ...args); } } critical(message: string, ...args: any[]): void { - if (this.level <= LogLevel.Critical) { + if (this.getLevel() <= LogLevel.Critical) { console.log('%cCRITI', 'background: #f33; color: white', message, ...args); } } @@ -175,22 +180,18 @@ export class ConsoleLogService implements ILogService { dispose(): void { } } -export class MultiplexLogService implements ILogService { +export class MultiplexLogService extends AbstractLogService implements ILogService { _serviceBrand: any; - constructor(private logServices: ILogService[]) { } + constructor(private logServices: ILogService[]) { + super(); + } setLevel(level: LogLevel): void { for (const logService of this.logServices) { logService.setLevel(level); } - } - - getLevel(): LogLevel { - for (const logService of this.logServices) { - return logService.getLevel(); - } - return LogLevel.Info; + super.setLevel(level); } trace(message: string, ...args: any[]): void { @@ -236,8 +237,50 @@ export class MultiplexLogService implements ILogService { } } +export class FollowerLogService extends AbstractLogService implements ILogService { + _serviceBrand: any; + + constructor(private client: LogLevelChannelClient, private logService: ILogService) { + super(); + this._register(client.onDidChangeLogLevel(level => logService.setLevel(level))); + } + + setLevel(level: LogLevel): void { + this.client.setLogLevel(level); + } + + trace(message: string, ...args: any[]): void { + this.logService.trace(message, ...args); + } + + debug(message: string, ...args: any[]): void { + this.logService.debug(message, ...args); + } + + info(message: string, ...args: any[]): void { + this.logService.info(message, ...args); + } + + warn(message: string, ...args: any[]): void { + this.logService.warn(message, ...args); + } + + error(message: string | Error, ...args: any[]): void { + this.logService.error(message, ...args); + } + + critical(message: string | Error, ...args: any[]): void { + this.logService.critical(message, ...args); + } + + dispose(): void { + this.logService.dispose(); + } +} + export class NullLogService implements ILogService { _serviceBrand: any; + readonly onDidChangeLogLevel: Event = new Emitter().event; setLevel(level: LogLevel): void { } getLevel(): LogLevel { return LogLevel.Info; } trace(message: string, ...args: any[]): void { } From c5ea1cf551379b5df8a64140844c4e577fa811ac Mon Sep 17 00:00:00 2001 From: Alex Dima Date: Tue, 23 Jan 2018 17:35:26 +0100 Subject: [PATCH 15/63] builtInExtensions.json keeps pointer to repo --- build/builtInExtensions.json | 12 ++++++++++-- 1 file changed, 10 insertions(+), 2 deletions(-) diff --git a/build/builtInExtensions.json b/build/builtInExtensions.json index 4921d2a27c7..f03be115d34 100644 --- a/build/builtInExtensions.json +++ b/build/builtInExtensions.json @@ -1,4 +1,12 @@ [ - { "name": "ms-vscode.node-debug", "version": "1.20.3" }, - { "name": "ms-vscode.node-debug2", "version": "1.20.1" } + { + "name": "ms-vscode.node-debug", + "version": "1.20.3", + "repo": "https://github.com/Microsoft/vscode-node-debug" + }, + { + "name": "ms-vscode.node-debug2", + "version": "1.20.1", + "repo": "https://github.com/Microsoft/vscode-node-debug2" + } ] \ No newline at end of file From 7af951014b83dbc5b217ed2a7a7d57ad1b9a9423 Mon Sep 17 00:00:00 2001 From: Alex Dima Date: Tue, 23 Jan 2018 17:46:13 +0100 Subject: [PATCH 16/63] Remove node-debug and node-debug2 obsolete marker files --- .../ms-vscode.node-debug/package-lock.json | 7087 ----------------- extensions/ms-vscode.node-debug/package.json | 8 - .../ms-vscode.node-debug2/package-lock.json | 5106 ------------ extensions/ms-vscode.node-debug2/package.json | 8 - 4 files changed, 12209 deletions(-) delete mode 100644 extensions/ms-vscode.node-debug/package-lock.json delete mode 100644 extensions/ms-vscode.node-debug/package.json delete mode 100644 extensions/ms-vscode.node-debug2/package-lock.json delete mode 100644 extensions/ms-vscode.node-debug2/package.json diff --git a/extensions/ms-vscode.node-debug/package-lock.json b/extensions/ms-vscode.node-debug/package-lock.json deleted file mode 100644 index 526e856f483..00000000000 --- a/extensions/ms-vscode.node-debug/package-lock.json +++ /dev/null @@ -1,7087 +0,0 @@ -{ - "name": "node-debug", - "version": "1.19.7", - "lockfileVersion": 1, - "requires": true, - "dependencies": { - "@gulp-sourcemaps/identity-map": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/@gulp-sourcemaps/identity-map/-/identity-map-1.0.1.tgz", - "integrity": "sha1-z6I7xYQPkQTOMqZedNt+epdLvuE=", - "dev": true, - "requires": { - "acorn": "5.2.1", - "css": "2.2.1", - "normalize-path": "2.1.1", - "source-map": "0.5.7", - "through2": "2.0.3" - }, - "dependencies": { - "acorn": { - "version": "5.2.1", - "resolved": "https://registry.npmjs.org/acorn/-/acorn-5.2.1.tgz", - "integrity": "sha512-jG0u7c4Ly+3QkkW18V+NRDN+4bWHdln30NL1ZL2AvFZZmQe/BfopYCtghCKKVBUSetZ4QKcyA0pY6/4Gw8Pv8w==", - "dev": true - }, - "source-map": { - "version": "0.5.7", - "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.5.7.tgz", - "integrity": "sha1-igOdLRAh0i0eoUyA2OpGi6LvP8w=", - "dev": true - } - } - }, - "@gulp-sourcemaps/map-sources": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/@gulp-sourcemaps/map-sources/-/map-sources-1.0.0.tgz", - "integrity": "sha1-iQrnxdjId/bThIYCFazp1+yUW9o=", - "dev": true, - "requires": { - "normalize-path": "2.1.1", - "through2": "2.0.3" - } - }, - "@types/mocha": { - "version": "2.2.44", - "resolved": "https://registry.npmjs.org/@types/mocha/-/mocha-2.2.44.tgz", - "integrity": "sha512-k2tWTQU8G4+iSMvqKi0Q9IIsWAp/n8xzdZS4Q4YVIltApoMA00wFBFdlJnmoaK1/z7B0Cy0yPe6GgXteSmdUNw==", - "dev": true - }, - "@types/node": { - "version": "7.0.43", - "resolved": "https://registry.npmjs.org/@types/node/-/node-7.0.43.tgz", - "integrity": "sha512-7scYwwfHNppXvH/9JzakbVxk0o0QUILVk1Lv64GRaxwPuGpnF1QBiwdvhDpLcymb8BpomQL3KYoWKq3wUdDMhQ==", - "dev": true - }, - "@types/source-map": { - "version": "0.5.2", - "resolved": "https://registry.npmjs.org/@types/source-map/-/source-map-0.5.2.tgz", - "integrity": "sha512-++w4WmMbk3dS3UeHGzAG+xJOSz5Xqtjys/TBkqG3qp3SeWE7Wwezqe5eB7B51cxUyh4PW7bwVotpsLdBK0D8cw==", - "dev": true - }, - "abbrev": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/abbrev/-/abbrev-1.1.1.tgz", - "integrity": "sha512-nne9/IiQ/hzIhY6pdDnbBtz7DjPTKrY00P/zvPSm5pOFkl6xuGrGnXn/VtTNNfNtAfZ9/1RtehkszU9qcTii0Q==", - "dev": true - }, - "acorn": { - "version": "4.0.13", - "resolved": "https://registry.npmjs.org/acorn/-/acorn-4.0.13.tgz", - "integrity": "sha1-EFSVrlNh1pe9GVyCUZLhrX8lN4c=", - "dev": true - }, - "agent-base": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/agent-base/-/agent-base-1.0.2.tgz", - "integrity": "sha1-aJDT+yFwBLYrcPiSjg+uX4lSpwY=" - }, - "ajv": { - "version": "5.4.0", - "resolved": "https://registry.npmjs.org/ajv/-/ajv-5.4.0.tgz", - "integrity": "sha1-MtHPCNvIDEMvQm8S4QslEfa0ZHQ=", - "dev": true, - "requires": { - "co": "4.6.0", - "fast-deep-equal": "1.0.0", - "fast-json-stable-stringify": "2.0.0", - "json-schema-traverse": "0.3.1" - } - }, - "align-text": { - "version": "0.1.4", - "resolved": "https://registry.npmjs.org/align-text/-/align-text-0.1.4.tgz", - "integrity": "sha1-DNkKVhCT810KmSVsIrcGlDP60Rc=", - "dev": true, - "requires": { - "kind-of": "3.2.2", - "longest": "1.0.1", - "repeat-string": "1.6.1" - } - }, - "amdefine": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/amdefine/-/amdefine-1.0.1.tgz", - "integrity": "sha1-SlKCrBZHKek2Gbz9OtFR+BfOkfU=", - "dev": true - }, - "ansi-align": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/ansi-align/-/ansi-align-2.0.0.tgz", - "integrity": "sha1-w2rsy6VjuJzrVW82kPCx2eNUf38=", - "dev": true, - "requires": { - "string-width": "2.1.1" - } - }, - "ansi-regex": { - "version": "2.1.1", - "resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-2.1.1.tgz", - "integrity": "sha1-w7M6te42DYbg5ijwRorn7yfWVN8=", - "dev": true - }, - "ansi-styles": { - "version": "2.2.1", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-2.2.1.tgz", - "integrity": "sha1-tDLdM1i2NM914eRmQ2gkBTPB3b4=", - "dev": true - }, - "anymatch": { - "version": "1.3.2", - "resolved": "https://registry.npmjs.org/anymatch/-/anymatch-1.3.2.tgz", - "integrity": "sha512-0XNayC8lTHQ2OI8aljNCN3sSx6hsr/1+rlcDAotXJR7C1oZZHCNsfpbKwMjRA3Uqb5tF1Rae2oloTr4xpq+WjA==", - "dev": true, - "requires": { - "micromatch": "2.3.11", - "normalize-path": "2.1.1" - } - }, - "archy": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/archy/-/archy-1.0.0.tgz", - "integrity": "sha1-+cjBN1fMHde8N5rHeyxipcKGjEA=", - "dev": true - }, - "argparse": { - "version": "1.0.9", - "resolved": "https://registry.npmjs.org/argparse/-/argparse-1.0.9.tgz", - "integrity": "sha1-c9g7wmP4bpf4zE9rrhsOkKfSLIY=", - "dev": true, - "requires": { - "sprintf-js": "1.0.3" - } - }, - "arr-diff": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/arr-diff/-/arr-diff-2.0.0.tgz", - "integrity": "sha1-jzuCf5Vai9ZpaX5KQlasPOrjVs8=", - "dev": true, - "requires": { - "arr-flatten": "1.1.0" - } - }, - "arr-flatten": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/arr-flatten/-/arr-flatten-1.1.0.tgz", - "integrity": "sha512-L3hKV5R/p5o81R7O02IGnwpDmkp6E982XhtbuwSe3O4qOtMMMtodicASA1Cny2U+aCXcNpml+m4dPsvsJ3jatg==", - "dev": true - }, - "array-differ": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/array-differ/-/array-differ-1.0.0.tgz", - "integrity": "sha1-7/UuN1gknTO+QCuLuOVkuytdQDE=", - "dev": true - }, - "array-each": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/array-each/-/array-each-1.0.1.tgz", - "integrity": "sha1-p5SvDAWrF1KEbudTofIRoFugxE8=", - "dev": true - }, - "array-slice": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/array-slice/-/array-slice-1.0.0.tgz", - "integrity": "sha1-5zA08A3MH0CHYAj9IP6ud71LfC8=", - "dev": true - }, - "array-union": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/array-union/-/array-union-1.0.2.tgz", - "integrity": "sha1-mjRBDk9OPaI96jdb5b5w8kd47Dk=", - "dev": true, - "requires": { - "array-uniq": "1.0.3" - } - }, - "array-uniq": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/array-uniq/-/array-uniq-1.0.3.tgz", - "integrity": "sha1-r2rId6Jcx/dOBYiUdThY39sk/bY=", - "dev": true - }, - "array-unique": { - "version": "0.2.1", - "resolved": "https://registry.npmjs.org/array-unique/-/array-unique-0.2.1.tgz", - "integrity": "sha1-odl8yvy8JiXMcPrc6zalDFiwGlM=", - "dev": true - }, - "arrify": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/arrify/-/arrify-1.0.1.tgz", - "integrity": "sha1-iYUI2iIm84DfkEcoRWhJwVAaSw0=", - "dev": true - }, - "asn1": { - "version": "0.2.3", - "resolved": "https://registry.npmjs.org/asn1/-/asn1-0.2.3.tgz", - "integrity": "sha1-2sh4dxPJlmhJ/IGAd36+nB3fO4Y=", - "dev": true - }, - "assert-plus": { - "version": "0.2.0", - "resolved": "https://registry.npmjs.org/assert-plus/-/assert-plus-0.2.0.tgz", - "integrity": "sha1-104bh+ev/A24qttwIfP+SBAasjQ=", - "dev": true - }, - "async": { - "version": "0.2.10", - "resolved": "https://registry.npmjs.org/async/-/async-0.2.10.tgz", - "integrity": "sha1-trvgsGdLnXGXCMo43owjfLUmw9E=", - "dev": true - }, - "async-each": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/async-each/-/async-each-1.0.1.tgz", - "integrity": "sha1-GdOGodntxufByF04iu28xW0zYC0=", - "dev": true - }, - "asynckit": { - "version": "0.4.0", - "resolved": "https://registry.npmjs.org/asynckit/-/asynckit-0.4.0.tgz", - "integrity": "sha1-x57Zf380y48robyXkLzDZkdLS3k=", - "dev": true - }, - "atob": { - "version": "1.1.3", - "resolved": "https://registry.npmjs.org/atob/-/atob-1.1.3.tgz", - "integrity": "sha1-lfE2KbEsOlGl0hWr3OKqnzL4B3M=", - "dev": true - }, - "aws-sign2": { - "version": "0.6.0", - "resolved": "https://registry.npmjs.org/aws-sign2/-/aws-sign2-0.6.0.tgz", - "integrity": "sha1-FDQt0428yU0OW4fXY81jYSwOeU8=", - "dev": true - }, - "aws4": { - "version": "1.6.0", - "resolved": "https://registry.npmjs.org/aws4/-/aws4-1.6.0.tgz", - "integrity": "sha1-g+9cqGCysy5KDe7e6MdxudtXRx4=", - "dev": true - }, - "babel-code-frame": { - "version": "6.26.0", - "resolved": "https://registry.npmjs.org/babel-code-frame/-/babel-code-frame-6.26.0.tgz", - "integrity": "sha1-Y/1D99weO7fONZR9uP42mj9Yx0s=", - "dev": true, - "requires": { - "chalk": "1.1.3", - "esutils": "2.0.2", - "js-tokens": "3.0.2" - } - }, - "balanced-match": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/balanced-match/-/balanced-match-1.0.0.tgz", - "integrity": "sha1-ibTRmasr7kneFk6gK4nORi1xt2c=" - }, - "bcrypt-pbkdf": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/bcrypt-pbkdf/-/bcrypt-pbkdf-1.0.1.tgz", - "integrity": "sha1-Y7xdy2EzG5K8Bf1SiVPDNGKgb40=", - "dev": true, - "optional": true, - "requires": { - "tweetnacl": "0.14.5" - } - }, - "beeper": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/beeper/-/beeper-1.1.1.tgz", - "integrity": "sha1-5tXqjF2tABMEpwsiY4RH9pyy+Ak=", - "dev": true - }, - "binary-extensions": { - "version": "1.11.0", - "resolved": "https://registry.npmjs.org/binary-extensions/-/binary-extensions-1.11.0.tgz", - "integrity": "sha1-RqoXUftqL5PuXmibsQh9SxTGwgU=", - "dev": true - }, - "block-stream": { - "version": "0.0.9", - "resolved": "https://registry.npmjs.org/block-stream/-/block-stream-0.0.9.tgz", - "integrity": "sha1-E+v+d4oDIFz+A3UUgeu0szAMEmo=", - "dev": true, - "requires": { - "inherits": "2.0.3" - } - }, - "boolbase": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/boolbase/-/boolbase-1.0.0.tgz", - "integrity": "sha1-aN/1++YMUes3cl6p4+0xDcwed24=", - "dev": true - }, - "boom": { - "version": "2.10.1", - "resolved": "https://registry.npmjs.org/boom/-/boom-2.10.1.tgz", - "integrity": "sha1-OciRjO/1eZ+D+UkqhI9iWt0Mdm8=", - "dev": true, - "requires": { - "hoek": "2.16.3" - } - }, - "boxen": { - "version": "1.2.2", - "resolved": "https://registry.npmjs.org/boxen/-/boxen-1.2.2.tgz", - "integrity": "sha1-Px1AMsMP/qnUsCwyLq8up0HcvOU=", - "dev": true, - "requires": { - "ansi-align": "2.0.0", - "camelcase": "4.1.0", - "chalk": "2.3.0", - "cli-boxes": "1.0.0", - "string-width": "2.1.1", - "term-size": "1.2.0", - "widest-line": "1.0.0" - }, - "dependencies": { - "ansi-styles": { - "version": "3.2.0", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-3.2.0.tgz", - "integrity": "sha512-NnSOmMEYtVR2JVMIGTzynRkkaxtiq1xnFBcdQD/DnNCYPoEPsVJhM98BDyaoNOQIi7p4okdi3E27eN7GQbsUug==", - "dev": true, - "requires": { - "color-convert": "1.9.1" - } - }, - "camelcase": { - "version": "4.1.0", - "resolved": "https://registry.npmjs.org/camelcase/-/camelcase-4.1.0.tgz", - "integrity": "sha1-1UVjW+HjPFQmScaRc+Xeas+uNN0=", - "dev": true - }, - "chalk": { - "version": "2.3.0", - "resolved": "https://registry.npmjs.org/chalk/-/chalk-2.3.0.tgz", - "integrity": "sha512-Az5zJR2CBujap2rqXGaJKaPHyJ0IrUimvYNX+ncCy8PJP4ltOGTrHUIo097ZaL2zMeKYpiCdqDvS6zdrTFok3Q==", - "dev": true, - "requires": { - "ansi-styles": "3.2.0", - "escape-string-regexp": "1.0.5", - "supports-color": "4.5.0" - } - }, - "supports-color": { - "version": "4.5.0", - "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-4.5.0.tgz", - "integrity": "sha1-vnoN5ITexcXN34s9WRJQRJEvY1s=", - "dev": true, - "requires": { - "has-flag": "2.0.0" - } - } - } - }, - "brace-expansion": { - "version": "1.1.8", - "resolved": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-1.1.8.tgz", - "integrity": "sha1-wHshHHyVLsH479Uad+8NHTmQopI=", - "requires": { - "balanced-match": "1.0.0", - "concat-map": "0.0.1" - } - }, - "braces": { - "version": "1.8.5", - "resolved": "https://registry.npmjs.org/braces/-/braces-1.8.5.tgz", - "integrity": "sha1-uneWLhLf+WnWt2cR6RS3N4V79qc=", - "dev": true, - "requires": { - "expand-range": "1.8.2", - "preserve": "0.2.0", - "repeat-element": "1.1.2" - } - }, - "browser-stdout": { - "version": "1.3.0", - "resolved": "https://registry.npmjs.org/browser-stdout/-/browser-stdout-1.3.0.tgz", - "integrity": "sha1-81HTKWnTL6XXpVZxVCY9korjvR8=", - "dev": true - }, - "buffer-crc32": { - "version": "0.2.13", - "resolved": "https://registry.npmjs.org/buffer-crc32/-/buffer-crc32-0.2.13.tgz", - "integrity": "sha1-DTM+PwDqxQqhRUq9MO+MKl2ackI=", - "dev": true - }, - "builtin-modules": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/builtin-modules/-/builtin-modules-1.1.1.tgz", - "integrity": "sha1-Jw8HbFpywC9bZaR9+Uxf46J4iS8=", - "dev": true - }, - "camelcase": { - "version": "1.2.1", - "resolved": "https://registry.npmjs.org/camelcase/-/camelcase-1.2.1.tgz", - "integrity": "sha1-m7UwTS4LVmmLLHWLCKPqqdqlijk=", - "dev": true - }, - "capture-stack-trace": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/capture-stack-trace/-/capture-stack-trace-1.0.0.tgz", - "integrity": "sha1-Sm+gc5nCa7pH8LJJa00PtAjFVQ0=", - "dev": true - }, - "caseless": { - "version": "0.11.0", - "resolved": "https://registry.npmjs.org/caseless/-/caseless-0.11.0.tgz", - "integrity": "sha1-cVuW6phBWTzDMGeSP17GDr2k99c=", - "dev": true - }, - "center-align": { - "version": "0.1.3", - "resolved": "https://registry.npmjs.org/center-align/-/center-align-0.1.3.tgz", - "integrity": "sha1-qg0yYptu6XIgBBHL1EYckHvCt60=", - "dev": true, - "requires": { - "align-text": "0.1.4", - "lazy-cache": "1.0.4" - } - }, - "chalk": { - "version": "1.1.3", - "resolved": "https://registry.npmjs.org/chalk/-/chalk-1.1.3.tgz", - "integrity": "sha1-qBFcVeSnAv5NFQq9OHKCKn4J/Jg=", - "dev": true, - "requires": { - "ansi-styles": "2.2.1", - "escape-string-regexp": "1.0.5", - "has-ansi": "2.0.0", - "strip-ansi": "3.0.1", - "supports-color": "2.0.0" - } - }, - "cheerio": { - "version": "1.0.0-rc.2", - "resolved": "https://registry.npmjs.org/cheerio/-/cheerio-1.0.0-rc.2.tgz", - "integrity": "sha1-S59TqBsn5NXawxwP/Qz6A8xoMNs=", - "dev": true, - "requires": { - "css-select": "1.2.0", - "dom-serializer": "0.1.0", - "entities": "1.1.1", - "htmlparser2": "3.9.2", - "lodash": "4.17.4", - "parse5": "3.0.3" - }, - "dependencies": { - "lodash": { - "version": "4.17.4", - "resolved": "https://registry.npmjs.org/lodash/-/lodash-4.17.4.tgz", - "integrity": "sha1-eCA6TRwyiuHYbcpkYONptX9AVa4=", - "dev": true - } - } - }, - "chokidar": { - "version": "1.7.0", - "resolved": "https://registry.npmjs.org/chokidar/-/chokidar-1.7.0.tgz", - "integrity": "sha1-eY5ol3gVHIB2tLNg5e3SjNortGg=", - "dev": true, - "requires": { - "anymatch": "1.3.2", - "async-each": "1.0.1", - "fsevents": "1.1.3", - "glob-parent": "2.0.0", - "inherits": "2.0.3", - "is-binary-path": "1.0.1", - "is-glob": "2.0.1", - "path-is-absolute": "1.0.1", - "readdirp": "2.1.0" - } - }, - "cli-boxes": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/cli-boxes/-/cli-boxes-1.0.0.tgz", - "integrity": "sha1-T6kXw+WclKAEzWH47lCdplFocUM=", - "dev": true - }, - "cliui": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/cliui/-/cliui-2.1.0.tgz", - "integrity": "sha1-S0dXYP+AJkx2LDoXGQMukcf+oNE=", - "dev": true, - "requires": { - "center-align": "0.1.3", - "right-align": "0.1.3", - "wordwrap": "0.0.2" - } - }, - "clone": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/clone/-/clone-1.0.3.tgz", - "integrity": "sha1-KY1+IjFmD0DAA8LtMUDezz9TCF8=", - "dev": true - }, - "clone-buffer": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/clone-buffer/-/clone-buffer-1.0.0.tgz", - "integrity": "sha1-4+JbIHrE5wGvch4staFnksrD3Fg=", - "dev": true - }, - "clone-stats": { - "version": "0.0.1", - "resolved": "https://registry.npmjs.org/clone-stats/-/clone-stats-0.0.1.tgz", - "integrity": "sha1-uI+UqCzzi4eR1YBG6kAprYjKmdE=", - "dev": true - }, - "cloneable-readable": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/cloneable-readable/-/cloneable-readable-1.0.0.tgz", - "integrity": "sha1-pikNQT8hemEjL5XkWP84QYz7ARc=", - "dev": true, - "requires": { - "inherits": "2.0.3", - "process-nextick-args": "1.0.7", - "through2": "2.0.3" - } - }, - "co": { - "version": "4.6.0", - "resolved": "https://registry.npmjs.org/co/-/co-4.6.0.tgz", - "integrity": "sha1-bqa989hTrlTMuOR7+gvz+QMfsYQ=", - "dev": true - }, - "code-point-at": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/code-point-at/-/code-point-at-1.1.0.tgz", - "integrity": "sha1-DQcLTQQ6W+ozovGkDi7bPZpMz3c=", - "dev": true - }, - "color-convert": { - "version": "1.9.1", - "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-1.9.1.tgz", - "integrity": "sha512-mjGanIiwQJskCC18rPR6OmrZ6fm2Lc7PeGFYwCmy5J34wC6F1PzdGL6xeMfmgicfYcNLGuVFA3WzXtIDCQSZxQ==", - "dev": true, - "requires": { - "color-name": "1.1.3" - } - }, - "color-name": { - "version": "1.1.3", - "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.3.tgz", - "integrity": "sha1-p9BVi9icQveV3UIyj3QIMcpTvCU=", - "dev": true - }, - "combined-stream": { - "version": "1.0.5", - "resolved": "https://registry.npmjs.org/combined-stream/-/combined-stream-1.0.5.tgz", - "integrity": "sha1-k4NwpXtKUd6ix3wV1cX9+JUWQAk=", - "dev": true, - "requires": { - "delayed-stream": "1.0.0" - } - }, - "commander": { - "version": "2.11.0", - "resolved": "https://registry.npmjs.org/commander/-/commander-2.11.0.tgz", - "integrity": "sha512-b0553uYA5YAEGgyYIGYROzKQ7X5RAqedkfjiZxwi0kL1g3bOaBNNZfYkzt/CL0umgD5wc9Jec2FbB98CjkMRvQ==", - "dev": true - }, - "concat-map": { - "version": "0.0.1", - "resolved": "https://registry.npmjs.org/concat-map/-/concat-map-0.0.1.tgz", - "integrity": "sha1-2Klr13/Wjfd5OnMDajug1UBdR3s=" - }, - "configstore": { - "version": "3.1.1", - "resolved": "https://registry.npmjs.org/configstore/-/configstore-3.1.1.tgz", - "integrity": "sha512-5oNkD/L++l0O6xGXxb1EWS7SivtjfGQlRyxJsYgE0Z495/L81e2h4/d3r969hoPXuFItzNOKMtsXgYG4c7dYvw==", - "dev": true, - "requires": { - "dot-prop": "4.2.0", - "graceful-fs": "4.1.11", - "make-dir": "1.1.0", - "unique-string": "1.0.0", - "write-file-atomic": "2.3.0", - "xdg-basedir": "3.0.0" - }, - "dependencies": { - "graceful-fs": { - "version": "4.1.11", - "resolved": "https://registry.npmjs.org/graceful-fs/-/graceful-fs-4.1.11.tgz", - "integrity": "sha1-Dovf5NHduIVNZOBOp8AOKgJuVlg=", - "dev": true - } - } - }, - "convert-source-map": { - "version": "1.5.0", - "resolved": "https://registry.npmjs.org/convert-source-map/-/convert-source-map-1.5.0.tgz", - "integrity": "sha1-ms1whRxtXf3ZPZKC5e35SgP/RrU=", - "dev": true - }, - "core-util-is": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/core-util-is/-/core-util-is-1.0.2.tgz", - "integrity": "sha1-tf1UIgqivFq1eqtxQMlAdUUDwac=", - "dev": true - }, - "create-error-class": { - "version": "3.0.2", - "resolved": "https://registry.npmjs.org/create-error-class/-/create-error-class-3.0.2.tgz", - "integrity": "sha1-Br56vvlHo/FKMP1hBnHUAbyot7Y=", - "dev": true, - "requires": { - "capture-stack-trace": "1.0.0" - } - }, - "cross-spawn": { - "version": "5.1.0", - "resolved": "https://registry.npmjs.org/cross-spawn/-/cross-spawn-5.1.0.tgz", - "integrity": "sha1-6L0O/uWPz/b4+UUQoKVUu/ojVEk=", - "dev": true, - "requires": { - "lru-cache": "4.1.1", - "shebang-command": "1.2.0", - "which": "1.3.0" - } - }, - "cryptiles": { - "version": "2.0.5", - "resolved": "https://registry.npmjs.org/cryptiles/-/cryptiles-2.0.5.tgz", - "integrity": "sha1-O9/s3GCBR8HGcgL6KR59ylnqo7g=", - "dev": true, - "requires": { - "boom": "2.10.1" - } - }, - "crypto-random-string": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/crypto-random-string/-/crypto-random-string-1.0.0.tgz", - "integrity": "sha1-ojD2T1aDEOFJgAmUB5DsmVRbyn4=", - "dev": true - }, - "css": { - "version": "2.2.1", - "resolved": "https://registry.npmjs.org/css/-/css-2.2.1.tgz", - "integrity": "sha1-c6TIHehdtmTU7mdPfUcIXjstVdw=", - "dev": true, - "requires": { - "inherits": "2.0.3", - "source-map": "0.1.43", - "source-map-resolve": "0.3.1", - "urix": "0.1.0" - }, - "dependencies": { - "source-map": { - "version": "0.1.43", - "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.1.43.tgz", - "integrity": "sha1-wkvBRspRfBRx9drL4lcbK3+eM0Y=", - "dev": true, - "requires": { - "amdefine": "1.0.1" - } - } - } - }, - "css-select": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/css-select/-/css-select-1.2.0.tgz", - "integrity": "sha1-KzoRBTnFNV8c2NMUYj6HCxIeyFg=", - "dev": true, - "requires": { - "boolbase": "1.0.0", - "css-what": "2.1.0", - "domutils": "1.5.1", - "nth-check": "1.0.1" - } - }, - "css-what": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/css-what/-/css-what-2.1.0.tgz", - "integrity": "sha1-lGfQMsOM+u+58teVASUwYvh/ob0=", - "dev": true - }, - "d": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/d/-/d-1.0.0.tgz", - "integrity": "sha1-dUu1v+VUUdpppYuU1F9MWwRi1Y8=", - "dev": true, - "requires": { - "es5-ext": "0.10.35" - } - }, - "dashdash": { - "version": "1.14.1", - "resolved": "https://registry.npmjs.org/dashdash/-/dashdash-1.14.1.tgz", - "integrity": "sha1-hTz6D3y+L+1d4gMmuN1YEDX24vA=", - "dev": true, - "requires": { - "assert-plus": "1.0.0" - }, - "dependencies": { - "assert-plus": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/assert-plus/-/assert-plus-1.0.0.tgz", - "integrity": "sha1-8S4PPF13sLHN2RRpQuTpbB5N1SU=", - "dev": true - } - } - }, - "dateformat": { - "version": "2.2.0", - "resolved": "https://registry.npmjs.org/dateformat/-/dateformat-2.2.0.tgz", - "integrity": "sha1-QGXiATz5+5Ft39gu+1Bq1MZ2kGI=", - "dev": true - }, - "debug": { - "version": "2.6.9", - "resolved": "https://registry.npmjs.org/debug/-/debug-2.6.9.tgz", - "integrity": "sha512-bC7ElrdJaJnPbAP+1EotYvqZsb3ecl5wi6Bfi6BJTUcNowp6cvspg0jXznRTKDjm/E7AdgFBVeAPVMNcKGsHMA==", - "requires": { - "ms": "2.0.0" - } - }, - "debug-fabulous": { - "version": "0.2.1", - "resolved": "https://registry.npmjs.org/debug-fabulous/-/debug-fabulous-0.2.1.tgz", - "integrity": "sha512-u0TV6HcfLsZ03xLBhdhSViQMldaiQ2o+8/nSILaXkuNSWvxkx66vYJUAam0Eu7gAilJRX/69J4kKdqajQPaPyw==", - "dev": true, - "requires": { - "debug": "3.1.0", - "memoizee": "0.4.11", - "object-assign": "4.1.1" - }, - "dependencies": { - "debug": { - "version": "3.1.0", - "resolved": "https://registry.npmjs.org/debug/-/debug-3.1.0.tgz", - "integrity": "sha512-OX8XqP7/1a9cqkxYw2yXss15f26NKWBpDXQd0/uK/KPqdQhxbPa994hnzjcE2VqQpDslf55723cKPUOGSmMY3g==", - "dev": true, - "requires": { - "ms": "2.0.0" - } - } - } - }, - "decamelize": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/decamelize/-/decamelize-1.2.0.tgz", - "integrity": "sha1-9lNNFRSCabIDUue+4m9QH5oZEpA=", - "dev": true - }, - "deep-assign": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/deep-assign/-/deep-assign-1.0.0.tgz", - "integrity": "sha1-sJJ0O+hCfcYh6gBnzex+cN0Z83s=", - "dev": true, - "requires": { - "is-obj": "1.0.1" - } - }, - "deep-extend": { - "version": "0.4.2", - "resolved": "https://registry.npmjs.org/deep-extend/-/deep-extend-0.4.2.tgz", - "integrity": "sha1-SLaZwn4zS/ifEIkr5DL25MfTSn8=", - "dev": true - }, - "defaults": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/defaults/-/defaults-1.0.3.tgz", - "integrity": "sha1-xlYFHpgX2f8I7YgUd/P+QBnz730=", - "dev": true, - "requires": { - "clone": "1.0.3" - } - }, - "del": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/del/-/del-3.0.0.tgz", - "integrity": "sha1-U+z2mf/LyzljdpGrE7rxYIGXZuU=", - "dev": true, - "requires": { - "globby": "6.1.0", - "is-path-cwd": "1.0.0", - "is-path-in-cwd": "1.0.0", - "p-map": "1.2.0", - "pify": "3.0.0", - "rimraf": "2.6.2" - } - }, - "delayed-stream": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/delayed-stream/-/delayed-stream-1.0.0.tgz", - "integrity": "sha1-3zrhmayt+31ECqrgsp4icrJOxhk=", - "dev": true - }, - "denodeify": { - "version": "1.2.1", - "resolved": "https://registry.npmjs.org/denodeify/-/denodeify-1.2.1.tgz", - "integrity": "sha1-OjYof1A05pnnV3kBBSwubJQlFjE=", - "dev": true - }, - "deprecated": { - "version": "0.0.1", - "resolved": "https://registry.npmjs.org/deprecated/-/deprecated-0.0.1.tgz", - "integrity": "sha1-+cmvVGSvoeepcUWKi97yqpTVuxk=", - "dev": true - }, - "detect-file": { - "version": "0.1.0", - "resolved": "https://registry.npmjs.org/detect-file/-/detect-file-0.1.0.tgz", - "integrity": "sha1-STXe39lIhkjgBrASlWbpOGcR6mM=", - "dev": true, - "requires": { - "fs-exists-sync": "0.1.0" - } - }, - "detect-newline": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/detect-newline/-/detect-newline-2.1.0.tgz", - "integrity": "sha1-9B8cEL5LAOh7XxPaaAdZ8sW/0+I=", - "dev": true - }, - "diff": { - "version": "3.3.1", - "resolved": "https://registry.npmjs.org/diff/-/diff-3.3.1.tgz", - "integrity": "sha512-MKPHZDMB0o6yHyDryUOScqZibp914ksXwAMYMTHj6KO8UeKsRYNJD3oNCKjTqZon+V488P7N/HzXF8t7ZR95ww==", - "dev": true - }, - "dom-serializer": { - "version": "0.1.0", - "resolved": "https://registry.npmjs.org/dom-serializer/-/dom-serializer-0.1.0.tgz", - "integrity": "sha1-BzxpdUbOB4DOI75KKOKT5AvDDII=", - "dev": true, - "requires": { - "domelementtype": "1.1.3", - "entities": "1.1.1" - }, - "dependencies": { - "domelementtype": { - "version": "1.1.3", - "resolved": "https://registry.npmjs.org/domelementtype/-/domelementtype-1.1.3.tgz", - "integrity": "sha1-vSh3PiZCiBrsUVRJJCmcXNgiGFs=", - "dev": true - } - } - }, - "domelementtype": { - "version": "1.3.0", - "resolved": "https://registry.npmjs.org/domelementtype/-/domelementtype-1.3.0.tgz", - "integrity": "sha1-sXrtguirWeUt2cGbF1bg/BhyBMI=", - "dev": true - }, - "domhandler": { - "version": "2.4.1", - "resolved": "https://registry.npmjs.org/domhandler/-/domhandler-2.4.1.tgz", - "integrity": "sha1-iS5HAAqZvlW783dP/qBWHYh5wlk=", - "dev": true, - "requires": { - "domelementtype": "1.3.0" - } - }, - "domutils": { - "version": "1.5.1", - "resolved": "https://registry.npmjs.org/domutils/-/domutils-1.5.1.tgz", - "integrity": "sha1-3NhIiib1Y9YQeeSMn3t+Mjc2gs8=", - "dev": true, - "requires": { - "dom-serializer": "0.1.0", - "domelementtype": "1.3.0" - } - }, - "dot-prop": { - "version": "4.2.0", - "resolved": "https://registry.npmjs.org/dot-prop/-/dot-prop-4.2.0.tgz", - "integrity": "sha512-tUMXrxlExSW6U2EXiiKGSBVdYgtV8qlHL+C10TsW4PURY/ic+eaysnSkwB4kA/mBlCyy/IKDJ+Lc3wbWeaXtuQ==", - "dev": true, - "requires": { - "is-obj": "1.0.1" - } - }, - "duplexer": { - "version": "0.1.1", - "resolved": "https://registry.npmjs.org/duplexer/-/duplexer-0.1.1.tgz", - "integrity": "sha1-rOb/gIwc5mtX0ev5eXessCM0z8E=", - "dev": true - }, - "duplexer2": { - "version": "0.0.2", - "resolved": "https://registry.npmjs.org/duplexer2/-/duplexer2-0.0.2.tgz", - "integrity": "sha1-xhTc9n4vsUmVqRcR5aYX6KYKMds=", - "dev": true, - "requires": { - "readable-stream": "1.1.14" - } - }, - "duplexer3": { - "version": "0.1.4", - "resolved": "https://registry.npmjs.org/duplexer3/-/duplexer3-0.1.4.tgz", - "integrity": "sha1-7gHdHKwO08vH/b6jfcCo8c4ALOI=", - "dev": true - }, - "duplexify": { - "version": "3.5.1", - "resolved": "https://registry.npmjs.org/duplexify/-/duplexify-3.5.1.tgz", - "integrity": "sha512-j5goxHTwVED1Fpe5hh3q9R93Kip0Bg2KVAt4f8CEYM3UEwYcPSvWbXaUQOzdX/HtiNomipv+gU7ASQPDbV7pGQ==", - "dev": true, - "requires": { - "end-of-stream": "1.4.0", - "inherits": "2.0.3", - "readable-stream": "2.3.3", - "stream-shift": "1.0.0" - }, - "dependencies": { - "end-of-stream": { - "version": "1.4.0", - "resolved": "https://registry.npmjs.org/end-of-stream/-/end-of-stream-1.4.0.tgz", - "integrity": "sha1-epDYM+/abPpurA9JSduw+tOmMgY=", - "dev": true, - "requires": { - "once": "1.4.0" - } - }, - "isarray": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/isarray/-/isarray-1.0.0.tgz", - "integrity": "sha1-u5NdSFgsuhaMBoNJV6VKPgcSTxE=", - "dev": true - }, - "readable-stream": { - "version": "2.3.3", - "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-2.3.3.tgz", - "integrity": "sha512-m+qzzcn7KUxEmd1gMbchF+Y2eIUbieUaxkWtptyHywrX0rE8QEYqPC07Vuy4Wm32/xE16NcdBctb8S0Xe/5IeQ==", - "dev": true, - "requires": { - "core-util-is": "1.0.2", - "inherits": "2.0.3", - "isarray": "1.0.0", - "process-nextick-args": "1.0.7", - "safe-buffer": "5.1.1", - "string_decoder": "1.0.3", - "util-deprecate": "1.0.2" - } - }, - "string_decoder": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/string_decoder/-/string_decoder-1.0.3.tgz", - "integrity": "sha512-4AH6Z5fzNNBcH+6XDMfA/BTt87skxqJlO0lAh3Dker5zThcAxG6mKz+iGu308UKoPPQ8Dcqx/4JhujzltRa+hQ==", - "dev": true, - "requires": { - "safe-buffer": "5.1.1" - } - } - } - }, - "ecc-jsbn": { - "version": "0.1.1", - "resolved": "https://registry.npmjs.org/ecc-jsbn/-/ecc-jsbn-0.1.1.tgz", - "integrity": "sha1-D8c6ntXw1Tw4GTOYUj735UN3dQU=", - "dev": true, - "optional": true, - "requires": { - "jsbn": "0.1.1" - } - }, - "end-of-stream": { - "version": "0.1.5", - "resolved": "https://registry.npmjs.org/end-of-stream/-/end-of-stream-0.1.5.tgz", - "integrity": "sha1-jhdyBsPICDfYVjLouTWd/osvbq8=", - "dev": true, - "requires": { - "once": "1.3.3" - }, - "dependencies": { - "once": { - "version": "1.3.3", - "resolved": "https://registry.npmjs.org/once/-/once-1.3.3.tgz", - "integrity": "sha1-suJhVXzkwxTsgwTz+oJmPkKXyiA=", - "dev": true, - "requires": { - "wrappy": "1.0.2" - } - } - } - }, - "entities": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/entities/-/entities-1.1.1.tgz", - "integrity": "sha1-blwtClYhtdra7O+AuQ7ftc13cvA=", - "dev": true - }, - "es5-ext": { - "version": "0.10.35", - "resolved": "https://registry.npmjs.org/es5-ext/-/es5-ext-0.10.35.tgz", - "integrity": "sha1-GO6FjOajxFx9eekcFfzKnsVoSU8=", - "dev": true, - "requires": { - "es6-iterator": "2.0.3", - "es6-symbol": "3.1.1" - } - }, - "es6-iterator": { - "version": "2.0.3", - "resolved": "https://registry.npmjs.org/es6-iterator/-/es6-iterator-2.0.3.tgz", - "integrity": "sha1-p96IkUGgWpSwhUQDstCg+/qY87c=", - "dev": true, - "requires": { - "d": "1.0.0", - "es5-ext": "0.10.35", - "es6-symbol": "3.1.1" - } - }, - "es6-promise": { - "version": "3.3.1", - "resolved": "https://registry.npmjs.org/es6-promise/-/es6-promise-3.3.1.tgz", - "integrity": "sha1-oIzd6EzNvzTQJ6FFG8kdS80ophM=", - "dev": true - }, - "es6-symbol": { - "version": "3.1.1", - "resolved": "https://registry.npmjs.org/es6-symbol/-/es6-symbol-3.1.1.tgz", - "integrity": "sha1-vwDvT9q2uhtG7Le2KbTH7VcVzHc=", - "dev": true, - "requires": { - "d": "1.0.0", - "es5-ext": "0.10.35" - } - }, - "es6-weak-map": { - "version": "2.0.2", - "resolved": "https://registry.npmjs.org/es6-weak-map/-/es6-weak-map-2.0.2.tgz", - "integrity": "sha1-XjqzIlH/0VOKH45f+hNXdy+S2W8=", - "dev": true, - "requires": { - "d": "1.0.0", - "es5-ext": "0.10.35", - "es6-iterator": "2.0.3", - "es6-symbol": "3.1.1" - } - }, - "escape-string-regexp": { - "version": "1.0.5", - "resolved": "https://registry.npmjs.org/escape-string-regexp/-/escape-string-regexp-1.0.5.tgz", - "integrity": "sha1-G2HAViGQqN/2rjuyzwIAyhMLhtQ=", - "dev": true - }, - "esutils": { - "version": "2.0.2", - "resolved": "https://registry.npmjs.org/esutils/-/esutils-2.0.2.tgz", - "integrity": "sha1-Cr9PHKpbyx96nYrMbepPqqBLrJs=", - "dev": true - }, - "event-emitter": { - "version": "0.3.5", - "resolved": "https://registry.npmjs.org/event-emitter/-/event-emitter-0.3.5.tgz", - "integrity": "sha1-34xp7vFkeSPHFXuc6DhAYQsCzDk=", - "dev": true, - "requires": { - "d": "1.0.0", - "es5-ext": "0.10.35" - } - }, - "event-stream": { - "version": "3.3.4", - "resolved": "https://registry.npmjs.org/event-stream/-/event-stream-3.3.4.tgz", - "integrity": "sha1-SrTJoPWlTbkzi0w02Gv86PSzVXE=", - "dev": true, - "requires": { - "duplexer": "0.1.1", - "from": "0.1.7", - "map-stream": "0.1.0", - "pause-stream": "0.0.11", - "split": "0.3.3", - "stream-combiner": "0.0.4", - "through": "2.3.8" - } - }, - "execa": { - "version": "0.7.0", - "resolved": "https://registry.npmjs.org/execa/-/execa-0.7.0.tgz", - "integrity": "sha1-lEvs00zEHuMqY6n68nrVpl/Fl3c=", - "dev": true, - "requires": { - "cross-spawn": "5.1.0", - "get-stream": "3.0.0", - "is-stream": "1.1.0", - "npm-run-path": "2.0.2", - "p-finally": "1.0.0", - "signal-exit": "3.0.2", - "strip-eof": "1.0.0" - } - }, - "expand-brackets": { - "version": "0.1.5", - "resolved": "https://registry.npmjs.org/expand-brackets/-/expand-brackets-0.1.5.tgz", - "integrity": "sha1-3wcoTjQqgHzXM6xa9yQR5YHRF3s=", - "dev": true, - "requires": { - "is-posix-bracket": "0.1.1" - } - }, - "expand-range": { - "version": "1.8.2", - "resolved": "https://registry.npmjs.org/expand-range/-/expand-range-1.8.2.tgz", - "integrity": "sha1-opnv/TNf4nIeuujiV+x5ZE/IUzc=", - "dev": true, - "requires": { - "fill-range": "2.2.3" - } - }, - "expand-tilde": { - "version": "1.2.2", - "resolved": "https://registry.npmjs.org/expand-tilde/-/expand-tilde-1.2.2.tgz", - "integrity": "sha1-C4HrqJflo9MdHD0QL48BRB5VlEk=", - "dev": true, - "requires": { - "os-homedir": "1.0.2" - } - }, - "extend": { - "version": "3.0.1", - "resolved": "https://registry.npmjs.org/extend/-/extend-3.0.1.tgz", - "integrity": "sha1-p1Xqe8Gt/MWjHOfnYtuq3F5jZEQ=" - }, - "extend-shallow": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/extend-shallow/-/extend-shallow-2.0.1.tgz", - "integrity": "sha1-Ua99YUrZqfYQ6huvu5idaxxWiQ8=", - "dev": true, - "requires": { - "is-extendable": "0.1.1" - } - }, - "extglob": { - "version": "0.3.2", - "resolved": "https://registry.npmjs.org/extglob/-/extglob-0.3.2.tgz", - "integrity": "sha1-Lhj/PS9JqydlzskCPwEdqo2DSaE=", - "dev": true, - "requires": { - "is-extglob": "1.0.0" - } - }, - "extsprintf": { - "version": "1.3.0", - "resolved": "https://registry.npmjs.org/extsprintf/-/extsprintf-1.3.0.tgz", - "integrity": "sha1-lpGEQOMEGnpBT4xS48V06zw+HgU=", - "dev": true - }, - "fancy-log": { - "version": "1.3.0", - "resolved": "https://registry.npmjs.org/fancy-log/-/fancy-log-1.3.0.tgz", - "integrity": "sha1-Rb4X0Cu5kX1gzP/UmVyZnmyMmUg=", - "dev": true, - "requires": { - "chalk": "1.1.3", - "time-stamp": "1.1.0" - } - }, - "fast-deep-equal": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/fast-deep-equal/-/fast-deep-equal-1.0.0.tgz", - "integrity": "sha1-liVqO8l1WV6zbYLpkp0GDYk0Of8=", - "dev": true - }, - "fast-json-stable-stringify": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/fast-json-stable-stringify/-/fast-json-stable-stringify-2.0.0.tgz", - "integrity": "sha1-1RQsDK7msRifh9OnYREGT4bIu/I=", - "dev": true - }, - "fd-slicer": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/fd-slicer/-/fd-slicer-1.0.1.tgz", - "integrity": "sha1-i1vL2ewyfFBBv5qwI/1nUPEXfmU=", - "dev": true, - "requires": { - "pend": "1.2.0" - } - }, - "filename-regex": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/filename-regex/-/filename-regex-2.0.1.tgz", - "integrity": "sha1-wcS5vuPglyXdsQa3XB4wH+LxiyY=", - "dev": true - }, - "fill-range": { - "version": "2.2.3", - "resolved": "https://registry.npmjs.org/fill-range/-/fill-range-2.2.3.tgz", - "integrity": "sha1-ULd9/X5Gm8dJJHCWNpn+eoSFpyM=", - "dev": true, - "requires": { - "is-number": "2.1.0", - "isobject": "2.1.0", - "randomatic": "1.1.7", - "repeat-element": "1.1.2", - "repeat-string": "1.6.1" - } - }, - "find-index": { - "version": "0.1.1", - "resolved": "https://registry.npmjs.org/find-index/-/find-index-0.1.1.tgz", - "integrity": "sha1-Z101iyyjiS15Whq0cjL4tuLg3eQ=", - "dev": true - }, - "findup-sync": { - "version": "0.4.3", - "resolved": "https://registry.npmjs.org/findup-sync/-/findup-sync-0.4.3.tgz", - "integrity": "sha1-QAQ5Kee8YK3wt/SCfExudaDeyhI=", - "dev": true, - "requires": { - "detect-file": "0.1.0", - "is-glob": "2.0.1", - "micromatch": "2.3.11", - "resolve-dir": "0.1.1" - } - }, - "fined": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/fined/-/fined-1.1.0.tgz", - "integrity": "sha1-s33IRLdqL15wgeiE98CuNE8VNHY=", - "dev": true, - "requires": { - "expand-tilde": "2.0.2", - "is-plain-object": "2.0.4", - "object.defaults": "1.1.0", - "object.pick": "1.3.0", - "parse-filepath": "1.0.1" - }, - "dependencies": { - "expand-tilde": { - "version": "2.0.2", - "resolved": "https://registry.npmjs.org/expand-tilde/-/expand-tilde-2.0.2.tgz", - "integrity": "sha1-l+gBqgUt8CRU3kawK/YhZCzchQI=", - "dev": true, - "requires": { - "homedir-polyfill": "1.0.1" - } - } - } - }, - "first-chunk-stream": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/first-chunk-stream/-/first-chunk-stream-1.0.0.tgz", - "integrity": "sha1-Wb+1DNkF9g18OUzT2ayqtOatk04=", - "dev": true - }, - "flagged-respawn": { - "version": "0.3.2", - "resolved": "https://registry.npmjs.org/flagged-respawn/-/flagged-respawn-0.3.2.tgz", - "integrity": "sha1-/xke3c1wiKZ1smEP/8l2vpuAdLU=", - "dev": true - }, - "for-in": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/for-in/-/for-in-1.0.2.tgz", - "integrity": "sha1-gQaNKVqBQuwKxybG4iAMMPttXoA=", - "dev": true - }, - "for-own": { - "version": "0.1.5", - "resolved": "https://registry.npmjs.org/for-own/-/for-own-0.1.5.tgz", - "integrity": "sha1-UmXGgaTylNq78XyVCbZ2OqhFEM4=", - "dev": true, - "requires": { - "for-in": "1.0.2" - } - }, - "forever-agent": { - "version": "0.6.1", - "resolved": "https://registry.npmjs.org/forever-agent/-/forever-agent-0.6.1.tgz", - "integrity": "sha1-+8cfDEGt6zf5bFd60e1C2P2sypE=", - "dev": true - }, - "form-data": { - "version": "2.1.4", - "resolved": "https://registry.npmjs.org/form-data/-/form-data-2.1.4.tgz", - "integrity": "sha1-M8GDrPGTJ27KqYFDpp6Uv+4XUNE=", - "dev": true, - "requires": { - "asynckit": "0.4.0", - "combined-stream": "1.0.5", - "mime-types": "2.1.17" - } - }, - "from": { - "version": "0.1.7", - "resolved": "https://registry.npmjs.org/from/-/from-0.1.7.tgz", - "integrity": "sha1-g8YK/Fi5xWmXAH7Rp2izqzA6RP4=", - "dev": true - }, - "fs-exists-sync": { - "version": "0.1.0", - "resolved": "https://registry.npmjs.org/fs-exists-sync/-/fs-exists-sync-0.1.0.tgz", - "integrity": "sha1-mC1ok6+RjnLQjeyehnP/K1qNat0=", - "dev": true - }, - "fs.realpath": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/fs.realpath/-/fs.realpath-1.0.0.tgz", - "integrity": "sha1-FQStJSMVjKpA20onh8sBQRmU6k8=" - }, - "fsevents": { - "version": "1.1.3", - "resolved": "https://registry.npmjs.org/fsevents/-/fsevents-1.1.3.tgz", - "integrity": "sha512-WIr7iDkdmdbxu/Gh6eKEZJL6KPE74/5MEsf2whTOFNxbIoIixogroLdKYqB6FDav4Wavh/lZdzzd3b2KxIXC5Q==", - "dev": true, - "optional": true, - "requires": { - "nan": "2.8.0", - "node-pre-gyp": "0.6.39" - }, - "dependencies": { - "abbrev": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/abbrev/-/abbrev-1.1.0.tgz", - "integrity": "sha1-0FVMIlZjbi9W58LlrRg/hZQo2B8=", - "dev": true, - "optional": true - }, - "ajv": { - "version": "4.11.8", - "resolved": "https://registry.npmjs.org/ajv/-/ajv-4.11.8.tgz", - "integrity": "sha1-gv+wKynmYq5TvcIK8VlHcGc5xTY=", - "dev": true, - "optional": true, - "requires": { - "co": "4.6.0", - "json-stable-stringify": "1.0.1" - } - }, - "ansi-regex": { - "version": "2.1.1", - "resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-2.1.1.tgz", - "integrity": "sha1-w7M6te42DYbg5ijwRorn7yfWVN8=", - "dev": true - }, - "aproba": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/aproba/-/aproba-1.1.1.tgz", - "integrity": "sha1-ldNgDwdxCqDpKYxyatXs8urLq6s=", - "dev": true, - "optional": true - }, - "are-we-there-yet": { - "version": "1.1.4", - "resolved": "https://registry.npmjs.org/are-we-there-yet/-/are-we-there-yet-1.1.4.tgz", - "integrity": "sha1-u13KOCu5TwXhUZQ3PRb9O6HKEQ0=", - "dev": true, - "optional": true, - "requires": { - "delegates": "1.0.0", - "readable-stream": "2.2.9" - } - }, - "asn1": { - "version": "0.2.3", - "resolved": "https://registry.npmjs.org/asn1/-/asn1-0.2.3.tgz", - "integrity": "sha1-2sh4dxPJlmhJ/IGAd36+nB3fO4Y=", - "dev": true, - "optional": true - }, - "assert-plus": { - "version": "0.2.0", - "resolved": "https://registry.npmjs.org/assert-plus/-/assert-plus-0.2.0.tgz", - "integrity": "sha1-104bh+ev/A24qttwIfP+SBAasjQ=", - "dev": true, - "optional": true - }, - "asynckit": { - "version": "0.4.0", - "resolved": "https://registry.npmjs.org/asynckit/-/asynckit-0.4.0.tgz", - "integrity": "sha1-x57Zf380y48robyXkLzDZkdLS3k=", - "dev": true, - "optional": true - }, - "aws-sign2": { - "version": "0.6.0", - "resolved": "https://registry.npmjs.org/aws-sign2/-/aws-sign2-0.6.0.tgz", - "integrity": "sha1-FDQt0428yU0OW4fXY81jYSwOeU8=", - "dev": true, - "optional": true - }, - "aws4": { - "version": "1.6.0", - "resolved": "https://registry.npmjs.org/aws4/-/aws4-1.6.0.tgz", - "integrity": "sha1-g+9cqGCysy5KDe7e6MdxudtXRx4=", - "dev": true, - "optional": true - }, - "balanced-match": { - "version": "0.4.2", - "resolved": "https://registry.npmjs.org/balanced-match/-/balanced-match-0.4.2.tgz", - "integrity": "sha1-yz8+PHMtwPAe5wtAPzAuYddwmDg=", - "dev": true - }, - "bcrypt-pbkdf": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/bcrypt-pbkdf/-/bcrypt-pbkdf-1.0.1.tgz", - "integrity": "sha1-Y7xdy2EzG5K8Bf1SiVPDNGKgb40=", - "dev": true, - "optional": true, - "requires": { - "tweetnacl": "0.14.5" - } - }, - "block-stream": { - "version": "0.0.9", - "resolved": "https://registry.npmjs.org/block-stream/-/block-stream-0.0.9.tgz", - "integrity": "sha1-E+v+d4oDIFz+A3UUgeu0szAMEmo=", - "dev": true, - "requires": { - "inherits": "2.0.3" - } - }, - "boom": { - "version": "2.10.1", - "resolved": "https://registry.npmjs.org/boom/-/boom-2.10.1.tgz", - "integrity": "sha1-OciRjO/1eZ+D+UkqhI9iWt0Mdm8=", - "dev": true, - "requires": { - "hoek": "2.16.3" - } - }, - "brace-expansion": { - "version": "1.1.7", - "resolved": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-1.1.7.tgz", - "integrity": "sha1-Pv/DxQ4ABTH7cg6v+A8K6O8jz1k=", - "dev": true, - "requires": { - "balanced-match": "0.4.2", - "concat-map": "0.0.1" - } - }, - "buffer-shims": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/buffer-shims/-/buffer-shims-1.0.0.tgz", - "integrity": "sha1-mXjOMXOIxkmth5MCjDR37wRKi1E=", - "dev": true - }, - "caseless": { - "version": "0.12.0", - "resolved": "https://registry.npmjs.org/caseless/-/caseless-0.12.0.tgz", - "integrity": "sha1-G2gcIf+EAzyCZUMJBolCDRhxUdw=", - "dev": true, - "optional": true - }, - "co": { - "version": "4.6.0", - "resolved": "https://registry.npmjs.org/co/-/co-4.6.0.tgz", - "integrity": "sha1-bqa989hTrlTMuOR7+gvz+QMfsYQ=", - "dev": true, - "optional": true - }, - "code-point-at": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/code-point-at/-/code-point-at-1.1.0.tgz", - "integrity": "sha1-DQcLTQQ6W+ozovGkDi7bPZpMz3c=", - "dev": true - }, - "combined-stream": { - "version": "1.0.5", - "resolved": "https://registry.npmjs.org/combined-stream/-/combined-stream-1.0.5.tgz", - "integrity": "sha1-k4NwpXtKUd6ix3wV1cX9+JUWQAk=", - "dev": true, - "requires": { - "delayed-stream": "1.0.0" - } - }, - "concat-map": { - "version": "0.0.1", - "resolved": "https://registry.npmjs.org/concat-map/-/concat-map-0.0.1.tgz", - "integrity": "sha1-2Klr13/Wjfd5OnMDajug1UBdR3s=", - "dev": true - }, - "console-control-strings": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/console-control-strings/-/console-control-strings-1.1.0.tgz", - "integrity": "sha1-PXz0Rk22RG6mRL9LOVB/mFEAjo4=", - "dev": true - }, - "core-util-is": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/core-util-is/-/core-util-is-1.0.2.tgz", - "integrity": "sha1-tf1UIgqivFq1eqtxQMlAdUUDwac=", - "dev": true - }, - "cryptiles": { - "version": "2.0.5", - "resolved": "https://registry.npmjs.org/cryptiles/-/cryptiles-2.0.5.tgz", - "integrity": "sha1-O9/s3GCBR8HGcgL6KR59ylnqo7g=", - "dev": true, - "requires": { - "boom": "2.10.1" - } - }, - "dashdash": { - "version": "1.14.1", - "resolved": "https://registry.npmjs.org/dashdash/-/dashdash-1.14.1.tgz", - "integrity": "sha1-hTz6D3y+L+1d4gMmuN1YEDX24vA=", - "dev": true, - "optional": true, - "requires": { - "assert-plus": "1.0.0" - }, - "dependencies": { - "assert-plus": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/assert-plus/-/assert-plus-1.0.0.tgz", - "integrity": "sha1-8S4PPF13sLHN2RRpQuTpbB5N1SU=", - "dev": true, - "optional": true - } - } - }, - "debug": { - "version": "2.6.8", - "resolved": "https://registry.npmjs.org/debug/-/debug-2.6.8.tgz", - "integrity": "sha1-5zFTHKLt4n0YgiJCfaF4IdaP9Pw=", - "dev": true, - "optional": true, - "requires": { - "ms": "2.0.0" - } - }, - "deep-extend": { - "version": "0.4.2", - "resolved": "https://registry.npmjs.org/deep-extend/-/deep-extend-0.4.2.tgz", - "integrity": "sha1-SLaZwn4zS/ifEIkr5DL25MfTSn8=", - "dev": true, - "optional": true - }, - "delayed-stream": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/delayed-stream/-/delayed-stream-1.0.0.tgz", - "integrity": "sha1-3zrhmayt+31ECqrgsp4icrJOxhk=", - "dev": true - }, - "delegates": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/delegates/-/delegates-1.0.0.tgz", - "integrity": "sha1-hMbhWbgZBP3KWaDvRM2HDTElD5o=", - "dev": true, - "optional": true - }, - "detect-libc": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/detect-libc/-/detect-libc-1.0.2.tgz", - "integrity": "sha1-ca1dIEvxempsqPRQxhRUBm70YeE=", - "dev": true, - "optional": true - }, - "ecc-jsbn": { - "version": "0.1.1", - "resolved": "https://registry.npmjs.org/ecc-jsbn/-/ecc-jsbn-0.1.1.tgz", - "integrity": "sha1-D8c6ntXw1Tw4GTOYUj735UN3dQU=", - "dev": true, - "optional": true, - "requires": { - "jsbn": "0.1.1" - } - }, - "extend": { - "version": "3.0.1", - "resolved": "https://registry.npmjs.org/extend/-/extend-3.0.1.tgz", - "integrity": "sha1-p1Xqe8Gt/MWjHOfnYtuq3F5jZEQ=", - "dev": true, - "optional": true - }, - "extsprintf": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/extsprintf/-/extsprintf-1.0.2.tgz", - "integrity": "sha1-4QgOBljjALBilJkMxw4VAiNf1VA=", - "dev": true - }, - "forever-agent": { - "version": "0.6.1", - "resolved": "https://registry.npmjs.org/forever-agent/-/forever-agent-0.6.1.tgz", - "integrity": "sha1-+8cfDEGt6zf5bFd60e1C2P2sypE=", - "dev": true, - "optional": true - }, - "form-data": { - "version": "2.1.4", - "resolved": "https://registry.npmjs.org/form-data/-/form-data-2.1.4.tgz", - "integrity": "sha1-M8GDrPGTJ27KqYFDpp6Uv+4XUNE=", - "dev": true, - "optional": true, - "requires": { - "asynckit": "0.4.0", - "combined-stream": "1.0.5", - "mime-types": "2.1.15" - } - }, - "fs.realpath": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/fs.realpath/-/fs.realpath-1.0.0.tgz", - "integrity": "sha1-FQStJSMVjKpA20onh8sBQRmU6k8=", - "dev": true - }, - "fstream": { - "version": "1.0.11", - "resolved": "https://registry.npmjs.org/fstream/-/fstream-1.0.11.tgz", - "integrity": "sha1-XB+x8RdHcRTwYyoOtLcbPLD9MXE=", - "dev": true, - "requires": { - "graceful-fs": "4.1.11", - "inherits": "2.0.3", - "mkdirp": "0.5.1", - "rimraf": "2.6.1" - } - }, - "fstream-ignore": { - "version": "1.0.5", - "resolved": "https://registry.npmjs.org/fstream-ignore/-/fstream-ignore-1.0.5.tgz", - "integrity": "sha1-nDHa40dnAY/h0kmyTa2mfQktoQU=", - "dev": true, - "optional": true, - "requires": { - "fstream": "1.0.11", - "inherits": "2.0.3", - "minimatch": "3.0.4" - } - }, - "gauge": { - "version": "2.7.4", - "resolved": "https://registry.npmjs.org/gauge/-/gauge-2.7.4.tgz", - "integrity": "sha1-LANAXHU4w51+s3sxcCLjJfsBi/c=", - "dev": true, - "optional": true, - "requires": { - "aproba": "1.1.1", - "console-control-strings": "1.1.0", - "has-unicode": "2.0.1", - "object-assign": "4.1.1", - "signal-exit": "3.0.2", - "string-width": "1.0.2", - "strip-ansi": "3.0.1", - "wide-align": "1.1.2" - } - }, - "getpass": { - "version": "0.1.7", - "resolved": "https://registry.npmjs.org/getpass/-/getpass-0.1.7.tgz", - "integrity": "sha1-Xv+OPmhNVprkyysSgmBOi6YhSfo=", - "dev": true, - "optional": true, - "requires": { - "assert-plus": "1.0.0" - }, - "dependencies": { - "assert-plus": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/assert-plus/-/assert-plus-1.0.0.tgz", - "integrity": "sha1-8S4PPF13sLHN2RRpQuTpbB5N1SU=", - "dev": true, - "optional": true - } - } - }, - "glob": { - "version": "7.1.2", - "resolved": "https://registry.npmjs.org/glob/-/glob-7.1.2.tgz", - "integrity": "sha512-MJTUg1kjuLeQCJ+ccE4Vpa6kKVXkPYJ2mOCQyUuKLcLQsdrMCpBPUi8qVE6+YuaJkozeA9NusTAw3hLr8Xe5EQ==", - "dev": true, - "requires": { - "fs.realpath": "1.0.0", - "inflight": "1.0.6", - "inherits": "2.0.3", - "minimatch": "3.0.4", - "once": "1.4.0", - "path-is-absolute": "1.0.1" - } - }, - "graceful-fs": { - "version": "4.1.11", - "resolved": "https://registry.npmjs.org/graceful-fs/-/graceful-fs-4.1.11.tgz", - "integrity": "sha1-Dovf5NHduIVNZOBOp8AOKgJuVlg=", - "dev": true - }, - "har-schema": { - "version": "1.0.5", - "resolved": "https://registry.npmjs.org/har-schema/-/har-schema-1.0.5.tgz", - "integrity": "sha1-0mMTX0MwfALGAq/I/pWXDAFRNp4=", - "dev": true, - "optional": true - }, - "har-validator": { - "version": "4.2.1", - "resolved": "https://registry.npmjs.org/har-validator/-/har-validator-4.2.1.tgz", - "integrity": "sha1-M0gdDxu/9gDdID11gSpqX7oALio=", - "dev": true, - "optional": true, - "requires": { - "ajv": "4.11.8", - "har-schema": "1.0.5" - } - }, - "has-unicode": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/has-unicode/-/has-unicode-2.0.1.tgz", - "integrity": "sha1-4Ob+aijPUROIVeCG0Wkedx3iqLk=", - "dev": true, - "optional": true - }, - "hawk": { - "version": "3.1.3", - "resolved": "https://registry.npmjs.org/hawk/-/hawk-3.1.3.tgz", - "integrity": "sha1-B4REvXwWQLD+VA0sm3PVlnjo4cQ=", - "dev": true, - "requires": { - "boom": "2.10.1", - "cryptiles": "2.0.5", - "hoek": "2.16.3", - "sntp": "1.0.9" - } - }, - "hoek": { - "version": "2.16.3", - "resolved": "https://registry.npmjs.org/hoek/-/hoek-2.16.3.tgz", - "integrity": "sha1-ILt0A9POo5jpHcRxCo/xuCdKJe0=", - "dev": true - }, - "http-signature": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/http-signature/-/http-signature-1.1.1.tgz", - "integrity": "sha1-33LiZwZs0Kxn+3at+OE0qPvPkb8=", - "dev": true, - "optional": true, - "requires": { - "assert-plus": "0.2.0", - "jsprim": "1.4.0", - "sshpk": "1.13.0" - } - }, - "inflight": { - "version": "1.0.6", - "resolved": "https://registry.npmjs.org/inflight/-/inflight-1.0.6.tgz", - "integrity": "sha1-Sb1jMdfQLQwJvJEKEHW6gWW1bfk=", - "dev": true, - "requires": { - "once": "1.4.0", - "wrappy": "1.0.2" - } - }, - "inherits": { - "version": "2.0.3", - "resolved": "https://registry.npmjs.org/inherits/-/inherits-2.0.3.tgz", - "integrity": "sha1-Yzwsg+PaQqUC9SRmAiSA9CCCYd4=", - "dev": true - }, - "ini": { - "version": "1.3.4", - "resolved": "https://registry.npmjs.org/ini/-/ini-1.3.4.tgz", - "integrity": "sha1-BTfLedr1m1mhpRff9wbIbsA5Fi4=", - "dev": true, - "optional": true - }, - "is-fullwidth-code-point": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/is-fullwidth-code-point/-/is-fullwidth-code-point-1.0.0.tgz", - "integrity": "sha1-754xOG8DGn8NZDr4L95QxFfvAMs=", - "dev": true, - "requires": { - "number-is-nan": "1.0.1" - } - }, - "is-typedarray": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/is-typedarray/-/is-typedarray-1.0.0.tgz", - "integrity": "sha1-5HnICFjfDBsR3dppQPlgEfzaSpo=", - "dev": true, - "optional": true - }, - "isarray": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/isarray/-/isarray-1.0.0.tgz", - "integrity": "sha1-u5NdSFgsuhaMBoNJV6VKPgcSTxE=", - "dev": true - }, - "isstream": { - "version": "0.1.2", - "resolved": "https://registry.npmjs.org/isstream/-/isstream-0.1.2.tgz", - "integrity": "sha1-R+Y/evVa+m+S4VAOaQ64uFKcCZo=", - "dev": true, - "optional": true - }, - "jodid25519": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/jodid25519/-/jodid25519-1.0.2.tgz", - "integrity": "sha1-BtSRIlUJNBlHfUJWM2BuDpB4KWc=", - "dev": true, - "optional": true, - "requires": { - "jsbn": "0.1.1" - } - }, - "jsbn": { - "version": "0.1.1", - "resolved": "https://registry.npmjs.org/jsbn/-/jsbn-0.1.1.tgz", - "integrity": "sha1-peZUwuWi3rXyAdls77yoDA7y9RM=", - "dev": true, - "optional": true - }, - "json-schema": { - "version": "0.2.3", - "resolved": "https://registry.npmjs.org/json-schema/-/json-schema-0.2.3.tgz", - "integrity": "sha1-tIDIkuWaLwWVTOcnvT8qTogvnhM=", - "dev": true, - "optional": true - }, - "json-stable-stringify": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/json-stable-stringify/-/json-stable-stringify-1.0.1.tgz", - "integrity": "sha1-mnWdOcXy/1A/1TAGRu1EX4jE+a8=", - "dev": true, - "optional": true, - "requires": { - "jsonify": "0.0.0" - } - }, - "json-stringify-safe": { - "version": "5.0.1", - "resolved": "https://registry.npmjs.org/json-stringify-safe/-/json-stringify-safe-5.0.1.tgz", - "integrity": "sha1-Epai1Y/UXxmg9s4B1lcB4sc1tus=", - "dev": true, - "optional": true - }, - "jsonify": { - "version": "0.0.0", - "resolved": "https://registry.npmjs.org/jsonify/-/jsonify-0.0.0.tgz", - "integrity": "sha1-LHS27kHZPKUbe1qu6PUDYx0lKnM=", - "dev": true, - "optional": true - }, - "jsprim": { - "version": "1.4.0", - "resolved": "https://registry.npmjs.org/jsprim/-/jsprim-1.4.0.tgz", - "integrity": "sha1-o7h+QCmNjDgFUtjMdiigu5WiKRg=", - "dev": true, - "optional": true, - "requires": { - "assert-plus": "1.0.0", - "extsprintf": "1.0.2", - "json-schema": "0.2.3", - "verror": "1.3.6" - }, - "dependencies": { - "assert-plus": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/assert-plus/-/assert-plus-1.0.0.tgz", - "integrity": "sha1-8S4PPF13sLHN2RRpQuTpbB5N1SU=", - "dev": true, - "optional": true - } - } - }, - "mime-db": { - "version": "1.27.0", - "resolved": "https://registry.npmjs.org/mime-db/-/mime-db-1.27.0.tgz", - "integrity": "sha1-gg9XIpa70g7CXtVeW13oaeVDbrE=", - "dev": true - }, - "mime-types": { - "version": "2.1.15", - "resolved": "https://registry.npmjs.org/mime-types/-/mime-types-2.1.15.tgz", - "integrity": "sha1-pOv1BkCUVpI3uM9wBGd20J/JKu0=", - "dev": true, - "requires": { - "mime-db": "1.27.0" - } - }, - "minimatch": { - "version": "3.0.4", - "resolved": "https://registry.npmjs.org/minimatch/-/minimatch-3.0.4.tgz", - "integrity": "sha512-yJHVQEhyqPLUTgt9B83PXu6W3rx4MvvHvSUvToogpwoGDOUQ+yDrR0HRot+yOCdCO7u4hX3pWft6kWBBcqh0UA==", - "dev": true, - "requires": { - "brace-expansion": "1.1.7" - } - }, - "minimist": { - "version": "0.0.8", - "resolved": "https://registry.npmjs.org/minimist/-/minimist-0.0.8.tgz", - "integrity": "sha1-hX/Kv8M5fSYluCKCYuhqp6ARsF0=", - "dev": true - }, - "mkdirp": { - "version": "0.5.1", - "resolved": "https://registry.npmjs.org/mkdirp/-/mkdirp-0.5.1.tgz", - "integrity": "sha1-MAV0OOrGz3+MR2fzhkjWaX11yQM=", - "dev": true, - "requires": { - "minimist": "0.0.8" - } - }, - "ms": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/ms/-/ms-2.0.0.tgz", - "integrity": "sha1-VgiurfwAvmwpAd9fmGF4jeDVl8g=", - "dev": true, - "optional": true - }, - "node-pre-gyp": { - "version": "0.6.39", - "resolved": "https://registry.npmjs.org/node-pre-gyp/-/node-pre-gyp-0.6.39.tgz", - "integrity": "sha512-OsJV74qxnvz/AMGgcfZoDaeDXKD3oY3QVIbBmwszTFkRisTSXbMQyn4UWzUMOtA5SVhrBZOTp0wcoSBgfMfMmQ==", - "dev": true, - "optional": true, - "requires": { - "detect-libc": "1.0.2", - "hawk": "3.1.3", - "mkdirp": "0.5.1", - "nopt": "4.0.1", - "npmlog": "4.1.0", - "rc": "1.2.1", - "request": "2.81.0", - "rimraf": "2.6.1", - "semver": "5.3.0", - "tar": "2.2.1", - "tar-pack": "3.4.0" - } - }, - "nopt": { - "version": "4.0.1", - "resolved": "https://registry.npmjs.org/nopt/-/nopt-4.0.1.tgz", - "integrity": "sha1-0NRoWv1UFRk8jHUFYC0NF81kR00=", - "dev": true, - "optional": true, - "requires": { - "abbrev": "1.1.0", - "osenv": "0.1.4" - } - }, - "npmlog": { - "version": "4.1.0", - "resolved": "https://registry.npmjs.org/npmlog/-/npmlog-4.1.0.tgz", - "integrity": "sha512-ocolIkZYZt8UveuiDS0yAkkIjid1o7lPG8cYm05yNYzBn8ykQtaiPMEGp8fY9tKdDgm8okpdKzkvu1y9hUYugA==", - "dev": true, - "optional": true, - "requires": { - "are-we-there-yet": "1.1.4", - "console-control-strings": "1.1.0", - "gauge": "2.7.4", - "set-blocking": "2.0.0" - } - }, - "number-is-nan": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/number-is-nan/-/number-is-nan-1.0.1.tgz", - "integrity": "sha1-CXtgK1NCKlIsGvuHkDGDNpQaAR0=", - "dev": true - }, - "oauth-sign": { - "version": "0.8.2", - "resolved": "https://registry.npmjs.org/oauth-sign/-/oauth-sign-0.8.2.tgz", - "integrity": "sha1-Rqarfwrq2N6unsBWV4C31O/rnUM=", - "dev": true, - "optional": true - }, - "object-assign": { - "version": "4.1.1", - "resolved": "https://registry.npmjs.org/object-assign/-/object-assign-4.1.1.tgz", - "integrity": "sha1-IQmtx5ZYh8/AXLvUQsrIv7s2CGM=", - "dev": true, - "optional": true - }, - "once": { - "version": "1.4.0", - "resolved": "https://registry.npmjs.org/once/-/once-1.4.0.tgz", - "integrity": "sha1-WDsap3WWHUsROsF9nFC6753Xa9E=", - "dev": true, - "requires": { - "wrappy": "1.0.2" - } - }, - "os-homedir": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/os-homedir/-/os-homedir-1.0.2.tgz", - "integrity": "sha1-/7xJiDNuDoM94MFox+8VISGqf7M=", - "dev": true, - "optional": true - }, - "os-tmpdir": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/os-tmpdir/-/os-tmpdir-1.0.2.tgz", - "integrity": "sha1-u+Z0BseaqFxc/sdm/lc0VV36EnQ=", - "dev": true, - "optional": true - }, - "osenv": { - "version": "0.1.4", - "resolved": "https://registry.npmjs.org/osenv/-/osenv-0.1.4.tgz", - "integrity": "sha1-Qv5tWVPfBsgGS+bxdsPQWqqjRkQ=", - "dev": true, - "optional": true, - "requires": { - "os-homedir": "1.0.2", - "os-tmpdir": "1.0.2" - } - }, - "path-is-absolute": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/path-is-absolute/-/path-is-absolute-1.0.1.tgz", - "integrity": "sha1-F0uSaHNVNP+8es5r9TpanhtcX18=", - "dev": true - }, - "performance-now": { - "version": "0.2.0", - "resolved": "https://registry.npmjs.org/performance-now/-/performance-now-0.2.0.tgz", - "integrity": "sha1-M+8wxcd9TqIcWlOGnZG1bY8lVeU=", - "dev": true, - "optional": true - }, - "process-nextick-args": { - "version": "1.0.7", - "resolved": "https://registry.npmjs.org/process-nextick-args/-/process-nextick-args-1.0.7.tgz", - "integrity": "sha1-FQ4gt1ZZCtP5EJPyWk8q2L/zC6M=", - "dev": true - }, - "punycode": { - "version": "1.4.1", - "resolved": "https://registry.npmjs.org/punycode/-/punycode-1.4.1.tgz", - "integrity": "sha1-wNWmOycYgArY4esPpSachN1BhF4=", - "dev": true, - "optional": true - }, - "qs": { - "version": "6.4.0", - "resolved": "https://registry.npmjs.org/qs/-/qs-6.4.0.tgz", - "integrity": "sha1-E+JtKK1rD/qpExLNO/cI7TUecjM=", - "dev": true, - "optional": true - }, - "rc": { - "version": "1.2.1", - "resolved": "https://registry.npmjs.org/rc/-/rc-1.2.1.tgz", - "integrity": "sha1-LgPo5C7kULjLPc5lvhv4l04d/ZU=", - "dev": true, - "optional": true, - "requires": { - "deep-extend": "0.4.2", - "ini": "1.3.4", - "minimist": "1.2.0", - "strip-json-comments": "2.0.1" - }, - "dependencies": { - "minimist": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/minimist/-/minimist-1.2.0.tgz", - "integrity": "sha1-o1AIsg9BOD7sH7kU9M1d95omQoQ=", - "dev": true, - "optional": true - } - } - }, - "readable-stream": { - "version": "2.2.9", - "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-2.2.9.tgz", - "integrity": "sha1-z3jsb0ptHrQ9JkiMrJfwQudLf8g=", - "dev": true, - "requires": { - "buffer-shims": "1.0.0", - "core-util-is": "1.0.2", - "inherits": "2.0.3", - "isarray": "1.0.0", - "process-nextick-args": "1.0.7", - "string_decoder": "1.0.1", - "util-deprecate": "1.0.2" - } - }, - "request": { - "version": "2.81.0", - "resolved": "https://registry.npmjs.org/request/-/request-2.81.0.tgz", - "integrity": "sha1-xpKJRqDgbF+Nb4qTM0af/aRimKA=", - "dev": true, - "optional": true, - "requires": { - "aws-sign2": "0.6.0", - "aws4": "1.6.0", - "caseless": "0.12.0", - "combined-stream": "1.0.5", - "extend": "3.0.1", - "forever-agent": "0.6.1", - "form-data": "2.1.4", - "har-validator": "4.2.1", - "hawk": "3.1.3", - "http-signature": "1.1.1", - "is-typedarray": "1.0.0", - "isstream": "0.1.2", - "json-stringify-safe": "5.0.1", - "mime-types": "2.1.15", - "oauth-sign": "0.8.2", - "performance-now": "0.2.0", - "qs": "6.4.0", - "safe-buffer": "5.0.1", - "stringstream": "0.0.5", - "tough-cookie": "2.3.2", - "tunnel-agent": "0.6.0", - "uuid": "3.0.1" - } - }, - "rimraf": { - "version": "2.6.1", - "resolved": "https://registry.npmjs.org/rimraf/-/rimraf-2.6.1.tgz", - "integrity": "sha1-wjOOxkPfeht/5cVPqG9XQopV8z0=", - "dev": true, - "requires": { - "glob": "7.1.2" - } - }, - "safe-buffer": { - "version": "5.0.1", - "resolved": "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.0.1.tgz", - "integrity": "sha1-0mPKVGls2KMGtcplUekt5XkY++c=", - "dev": true - }, - "semver": { - "version": "5.3.0", - "resolved": "https://registry.npmjs.org/semver/-/semver-5.3.0.tgz", - "integrity": "sha1-myzl094C0XxgEq0yaqa00M9U+U8=", - "dev": true, - "optional": true - }, - "set-blocking": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/set-blocking/-/set-blocking-2.0.0.tgz", - "integrity": "sha1-BF+XgtARrppoA93TgrJDkrPYkPc=", - "dev": true, - "optional": true - }, - "signal-exit": { - "version": "3.0.2", - "resolved": "https://registry.npmjs.org/signal-exit/-/signal-exit-3.0.2.tgz", - "integrity": "sha1-tf3AjxKH6hF4Yo5BXiUTK3NkbG0=", - "dev": true, - "optional": true - }, - "sntp": { - "version": "1.0.9", - "resolved": "https://registry.npmjs.org/sntp/-/sntp-1.0.9.tgz", - "integrity": "sha1-ZUEYTMkK7qbG57NeJlkIJEPGYZg=", - "dev": true, - "requires": { - "hoek": "2.16.3" - } - }, - "sshpk": { - "version": "1.13.0", - "resolved": "https://registry.npmjs.org/sshpk/-/sshpk-1.13.0.tgz", - "integrity": "sha1-/yo+T9BEl1Vf7Zezmg/YL6+zozw=", - "dev": true, - "optional": true, - "requires": { - "asn1": "0.2.3", - "assert-plus": "1.0.0", - "bcrypt-pbkdf": "1.0.1", - "dashdash": "1.14.1", - "ecc-jsbn": "0.1.1", - "getpass": "0.1.7", - "jodid25519": "1.0.2", - "jsbn": "0.1.1", - "tweetnacl": "0.14.5" - }, - "dependencies": { - "assert-plus": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/assert-plus/-/assert-plus-1.0.0.tgz", - "integrity": "sha1-8S4PPF13sLHN2RRpQuTpbB5N1SU=", - "dev": true, - "optional": true - } - } - }, - "string-width": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/string-width/-/string-width-1.0.2.tgz", - "integrity": "sha1-EYvfW4zcUaKn5w0hHgfisLmxB9M=", - "dev": true, - "requires": { - "code-point-at": "1.1.0", - "is-fullwidth-code-point": "1.0.0", - "strip-ansi": "3.0.1" - } - }, - "string_decoder": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/string_decoder/-/string_decoder-1.0.1.tgz", - "integrity": "sha1-YuIA8DmVWmgQ2N8KM//A8BNmLZg=", - "dev": true, - "requires": { - "safe-buffer": "5.0.1" - } - }, - "stringstream": { - "version": "0.0.5", - "resolved": "https://registry.npmjs.org/stringstream/-/stringstream-0.0.5.tgz", - "integrity": "sha1-TkhM1N5aC7vuGORjB3EKioFiGHg=", - "dev": true, - "optional": true - }, - "strip-ansi": { - "version": "3.0.1", - "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-3.0.1.tgz", - "integrity": "sha1-ajhfuIU9lS1f8F0Oiq+UJ43GPc8=", - "dev": true, - "requires": { - "ansi-regex": "2.1.1" - } - }, - "strip-json-comments": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/strip-json-comments/-/strip-json-comments-2.0.1.tgz", - "integrity": "sha1-PFMZQukIwml8DsNEhYwobHygpgo=", - "dev": true, - "optional": true - }, - "tar": { - "version": "2.2.1", - "resolved": "https://registry.npmjs.org/tar/-/tar-2.2.1.tgz", - "integrity": "sha1-jk0qJWwOIYXGsYrWlK7JaLg8sdE=", - "dev": true, - "requires": { - "block-stream": "0.0.9", - "fstream": "1.0.11", - "inherits": "2.0.3" - } - }, - "tar-pack": { - "version": "3.4.0", - "resolved": "https://registry.npmjs.org/tar-pack/-/tar-pack-3.4.0.tgz", - "integrity": "sha1-I74tf2cagzk3bL2wuP4/3r8xeYQ=", - "dev": true, - "optional": true, - "requires": { - "debug": "2.6.8", - "fstream": "1.0.11", - "fstream-ignore": "1.0.5", - "once": "1.4.0", - "readable-stream": "2.2.9", - "rimraf": "2.6.1", - "tar": "2.2.1", - "uid-number": "0.0.6" - } - }, - "tough-cookie": { - "version": "2.3.2", - "resolved": "https://registry.npmjs.org/tough-cookie/-/tough-cookie-2.3.2.tgz", - "integrity": "sha1-8IH3bkyFcg5sN6X6ztc3FQ2EByo=", - "dev": true, - "optional": true, - "requires": { - "punycode": "1.4.1" - } - }, - "tunnel-agent": { - "version": "0.6.0", - "resolved": "https://registry.npmjs.org/tunnel-agent/-/tunnel-agent-0.6.0.tgz", - "integrity": "sha1-J6XeoGs2sEoKmWZ3SykIaPD8QP0=", - "dev": true, - "optional": true, - "requires": { - "safe-buffer": "5.0.1" - } - }, - "tweetnacl": { - "version": "0.14.5", - "resolved": "https://registry.npmjs.org/tweetnacl/-/tweetnacl-0.14.5.tgz", - "integrity": "sha1-WuaBd/GS1EViadEIr6k/+HQ/T2Q=", - "dev": true, - "optional": true - }, - "uid-number": { - "version": "0.0.6", - "resolved": "https://registry.npmjs.org/uid-number/-/uid-number-0.0.6.tgz", - "integrity": "sha1-DqEOgDXo61uOREnwbaHHMGY7qoE=", - "dev": true, - "optional": true - }, - "util-deprecate": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/util-deprecate/-/util-deprecate-1.0.2.tgz", - "integrity": "sha1-RQ1Nyfpw3nMnYvvS1KKJgUGaDM8=", - "dev": true - }, - "uuid": { - "version": "3.0.1", - "resolved": "https://registry.npmjs.org/uuid/-/uuid-3.0.1.tgz", - "integrity": "sha1-ZUS7ot/ajBzxfmKaOjBeK7H+5sE=", - "dev": true, - "optional": true - }, - "verror": { - "version": "1.3.6", - "resolved": "https://registry.npmjs.org/verror/-/verror-1.3.6.tgz", - "integrity": "sha1-z/XfEpRtKX0rqu+qJoniW+AcAFw=", - "dev": true, - "optional": true, - "requires": { - "extsprintf": "1.0.2" - } - }, - "wide-align": { - "version": "1.1.2", - "resolved": "https://registry.npmjs.org/wide-align/-/wide-align-1.1.2.tgz", - "integrity": "sha512-ijDLlyQ7s6x1JgCLur53osjm/UXUYD9+0PbYKrBsYisYXzCxN+HC3mYDNy/dWdmf3AwqwU3CXwDCvsNgGK1S0w==", - "dev": true, - "optional": true, - "requires": { - "string-width": "1.0.2" - } - }, - "wrappy": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/wrappy/-/wrappy-1.0.2.tgz", - "integrity": "sha1-tSQ9jz7BqjXxNkYFvA0QNuMKtp8=", - "dev": true - } - } - }, - "fstream": { - "version": "1.0.11", - "resolved": "https://registry.npmjs.org/fstream/-/fstream-1.0.11.tgz", - "integrity": "sha1-XB+x8RdHcRTwYyoOtLcbPLD9MXE=", - "dev": true, - "requires": { - "graceful-fs": "4.1.11", - "inherits": "2.0.3", - "mkdirp": "0.5.1", - "rimraf": "2.6.2" - }, - "dependencies": { - "graceful-fs": { - "version": "4.1.11", - "resolved": "https://registry.npmjs.org/graceful-fs/-/graceful-fs-4.1.11.tgz", - "integrity": "sha1-Dovf5NHduIVNZOBOp8AOKgJuVlg=", - "dev": true - } - } - }, - "gaze": { - "version": "0.5.2", - "resolved": "https://registry.npmjs.org/gaze/-/gaze-0.5.2.tgz", - "integrity": "sha1-QLcJU30k0dRXZ9takIaJ3+aaxE8=", - "dev": true, - "requires": { - "globule": "0.1.0" - } - }, - "generate-function": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/generate-function/-/generate-function-2.0.0.tgz", - "integrity": "sha1-aFj+fAlpt9TpCTM3ZHrHn2DfvnQ=", - "dev": true - }, - "generate-object-property": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/generate-object-property/-/generate-object-property-1.2.0.tgz", - "integrity": "sha1-nA4cQDCM6AT0eDYYuTf6iPmdUNA=", - "dev": true, - "requires": { - "is-property": "1.0.2" - } - }, - "get-stream": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/get-stream/-/get-stream-3.0.0.tgz", - "integrity": "sha1-jpQ9E1jcN1VQVOy+LtsFqhdO3hQ=", - "dev": true - }, - "getpass": { - "version": "0.1.7", - "resolved": "https://registry.npmjs.org/getpass/-/getpass-0.1.7.tgz", - "integrity": "sha1-Xv+OPmhNVprkyysSgmBOi6YhSfo=", - "dev": true, - "requires": { - "assert-plus": "1.0.0" - }, - "dependencies": { - "assert-plus": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/assert-plus/-/assert-plus-1.0.0.tgz", - "integrity": "sha1-8S4PPF13sLHN2RRpQuTpbB5N1SU=", - "dev": true - } - } - }, - "glob": { - "version": "7.1.2", - "resolved": "https://registry.npmjs.org/glob/-/glob-7.1.2.tgz", - "integrity": "sha512-MJTUg1kjuLeQCJ+ccE4Vpa6kKVXkPYJ2mOCQyUuKLcLQsdrMCpBPUi8qVE6+YuaJkozeA9NusTAw3hLr8Xe5EQ==", - "requires": { - "fs.realpath": "1.0.0", - "inflight": "1.0.6", - "inherits": "2.0.3", - "minimatch": "3.0.4", - "once": "1.4.0", - "path-is-absolute": "1.0.1" - } - }, - "glob-base": { - "version": "0.3.0", - "resolved": "https://registry.npmjs.org/glob-base/-/glob-base-0.3.0.tgz", - "integrity": "sha1-27Fk9iIbHAscz4Kuoyi0l98Oo8Q=", - "dev": true, - "requires": { - "glob-parent": "2.0.0", - "is-glob": "2.0.1" - } - }, - "glob-parent": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/glob-parent/-/glob-parent-2.0.0.tgz", - "integrity": "sha1-gTg9ctsFT8zPUzbaqQLxgvbtuyg=", - "dev": true, - "requires": { - "is-glob": "2.0.1" - } - }, - "glob-stream": { - "version": "3.1.18", - "resolved": "https://registry.npmjs.org/glob-stream/-/glob-stream-3.1.18.tgz", - "integrity": "sha1-kXCl8St5Awb9/lmPMT+PeVT9FDs=", - "dev": true, - "requires": { - "glob": "4.5.3", - "glob2base": "0.0.12", - "minimatch": "2.0.10", - "ordered-read-streams": "0.1.0", - "through2": "0.6.5", - "unique-stream": "1.0.0" - }, - "dependencies": { - "glob": { - "version": "4.5.3", - "resolved": "https://registry.npmjs.org/glob/-/glob-4.5.3.tgz", - "integrity": "sha1-xstz0yJsHv7wTePFbQEvAzd+4V8=", - "dev": true, - "requires": { - "inflight": "1.0.6", - "inherits": "2.0.3", - "minimatch": "2.0.10", - "once": "1.4.0" - } - }, - "minimatch": { - "version": "2.0.10", - "resolved": "https://registry.npmjs.org/minimatch/-/minimatch-2.0.10.tgz", - "integrity": "sha1-jQh8OcazjAAbl/ynzm0OHoCvusc=", - "dev": true, - "requires": { - "brace-expansion": "1.1.8" - } - }, - "readable-stream": { - "version": "1.0.34", - "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-1.0.34.tgz", - "integrity": "sha1-Elgg40vIQtLyqq+v5MKRbuMsFXw=", - "dev": true, - "requires": { - "core-util-is": "1.0.2", - "inherits": "2.0.3", - "isarray": "0.0.1", - "string_decoder": "0.10.31" - } - }, - "through2": { - "version": "0.6.5", - "resolved": "https://registry.npmjs.org/through2/-/through2-0.6.5.tgz", - "integrity": "sha1-QaucZ7KdVyCQcUEOHXp6lozTrUg=", - "dev": true, - "requires": { - "readable-stream": "1.0.34", - "xtend": "4.0.1" - } - } - } - }, - "glob-watcher": { - "version": "0.0.6", - "resolved": "https://registry.npmjs.org/glob-watcher/-/glob-watcher-0.0.6.tgz", - "integrity": "sha1-uVtKjfdLOcgymLDAXJeLTZo7cQs=", - "dev": true, - "requires": { - "gaze": "0.5.2" - } - }, - "glob2base": { - "version": "0.0.12", - "resolved": "https://registry.npmjs.org/glob2base/-/glob2base-0.0.12.tgz", - "integrity": "sha1-nUGbPijxLoOjYhZKJ3BVkiycDVY=", - "dev": true, - "requires": { - "find-index": "0.1.1" - } - }, - "global-dirs": { - "version": "0.1.1", - "resolved": "https://registry.npmjs.org/global-dirs/-/global-dirs-0.1.1.tgz", - "integrity": "sha1-sxnA3UYH81PzvpzKTHL8FIxJ9EU=", - "dev": true, - "requires": { - "ini": "1.3.5" - } - }, - "global-modules": { - "version": "0.2.3", - "resolved": "https://registry.npmjs.org/global-modules/-/global-modules-0.2.3.tgz", - "integrity": "sha1-6lo77ULG1s6ZWk+KEmm12uIjgo0=", - "dev": true, - "requires": { - "global-prefix": "0.1.5", - "is-windows": "0.2.0" - } - }, - "global-prefix": { - "version": "0.1.5", - "resolved": "https://registry.npmjs.org/global-prefix/-/global-prefix-0.1.5.tgz", - "integrity": "sha1-jTvGuNo8qBEqFg2NSW/wRiv+948=", - "dev": true, - "requires": { - "homedir-polyfill": "1.0.1", - "ini": "1.3.5", - "is-windows": "0.2.0", - "which": "1.3.0" - } - }, - "globby": { - "version": "6.1.0", - "resolved": "https://registry.npmjs.org/globby/-/globby-6.1.0.tgz", - "integrity": "sha1-9abXDoOV4hyFj7BInWTfAkJNUGw=", - "dev": true, - "requires": { - "array-union": "1.0.2", - "glob": "7.1.2", - "object-assign": "4.1.1", - "pify": "2.3.0", - "pinkie-promise": "2.0.1" - }, - "dependencies": { - "pify": { - "version": "2.3.0", - "resolved": "https://registry.npmjs.org/pify/-/pify-2.3.0.tgz", - "integrity": "sha1-7RQaasBDqEnqWISY59yosVMw6Qw=", - "dev": true - } - } - }, - "globule": { - "version": "0.1.0", - "resolved": "https://registry.npmjs.org/globule/-/globule-0.1.0.tgz", - "integrity": "sha1-2cjt3h2nnRJaFRt5UzuXhnY0auU=", - "dev": true, - "requires": { - "glob": "3.1.21", - "lodash": "1.0.2", - "minimatch": "0.2.14" - }, - "dependencies": { - "glob": { - "version": "3.1.21", - "resolved": "https://registry.npmjs.org/glob/-/glob-3.1.21.tgz", - "integrity": "sha1-0p4KBV3qUTj00H7UDomC6DwgZs0=", - "dev": true, - "requires": { - "graceful-fs": "1.2.3", - "inherits": "1.0.2", - "minimatch": "0.2.14" - } - }, - "graceful-fs": { - "version": "1.2.3", - "resolved": "https://registry.npmjs.org/graceful-fs/-/graceful-fs-1.2.3.tgz", - "integrity": "sha1-FaSAaldUfLLS2/J/QuiajDRRs2Q=", - "dev": true - }, - "inherits": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/inherits/-/inherits-1.0.2.tgz", - "integrity": "sha1-ykMJ2t7mtUzAuNJH6NfHoJdb3Js=", - "dev": true - }, - "lru-cache": { - "version": "2.7.3", - "resolved": "https://registry.npmjs.org/lru-cache/-/lru-cache-2.7.3.tgz", - "integrity": "sha1-bUUk6LlV+V1PW1iFHOId1y+06VI=", - "dev": true - }, - "minimatch": { - "version": "0.2.14", - "resolved": "https://registry.npmjs.org/minimatch/-/minimatch-0.2.14.tgz", - "integrity": "sha1-x054BXT2PG+aCQ6Q775u9TpqdWo=", - "dev": true, - "requires": { - "lru-cache": "2.7.3", - "sigmund": "1.0.1" - } - } - } - }, - "glogg": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/glogg/-/glogg-1.0.0.tgz", - "integrity": "sha1-f+DxmfV6yQbPUS/urY+Q7kooT8U=", - "dev": true, - "requires": { - "sparkles": "1.0.0" - } - }, - "got": { - "version": "6.7.1", - "resolved": "https://registry.npmjs.org/got/-/got-6.7.1.tgz", - "integrity": "sha1-JAzQV4WpoY5WHcG0S0HHY+8ejbA=", - "dev": true, - "requires": { - "create-error-class": "3.0.2", - "duplexer3": "0.1.4", - "get-stream": "3.0.0", - "is-redirect": "1.0.0", - "is-retry-allowed": "1.1.0", - "is-stream": "1.1.0", - "lowercase-keys": "1.0.0", - "safe-buffer": "5.1.1", - "timed-out": "4.0.1", - "unzip-response": "2.0.1", - "url-parse-lax": "1.0.0" - } - }, - "graceful-fs": { - "version": "3.0.11", - "resolved": "https://registry.npmjs.org/graceful-fs/-/graceful-fs-3.0.11.tgz", - "integrity": "sha1-dhPHeKGv6mLyXGMKCG1/Osu92Bg=", - "dev": true, - "requires": { - "natives": "1.1.0" - } - }, - "growl": { - "version": "1.10.3", - "resolved": "https://registry.npmjs.org/growl/-/growl-1.10.3.tgz", - "integrity": "sha512-hKlsbA5Vu3xsh1Cg3J7jSmX/WaW6A5oBeqzM88oNbCRQFz+zUaXm6yxS4RVytp1scBoJzSYl4YAEOQIt6O8V1Q==", - "dev": true - }, - "gulp": { - "version": "3.9.1", - "resolved": "https://registry.npmjs.org/gulp/-/gulp-3.9.1.tgz", - "integrity": "sha1-VxzkWSjdQK9lFPxAEYZgFsE4RbQ=", - "dev": true, - "requires": { - "archy": "1.0.0", - "chalk": "1.1.3", - "deprecated": "0.0.1", - "gulp-util": "3.0.8", - "interpret": "1.0.4", - "liftoff": "2.3.0", - "minimist": "1.2.0", - "orchestrator": "0.3.8", - "pretty-hrtime": "1.0.3", - "semver": "4.3.6", - "tildify": "1.2.0", - "v8flags": "2.1.1", - "vinyl-fs": "0.3.14" - } - }, - "gulp-chmod": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/gulp-chmod/-/gulp-chmod-2.0.0.tgz", - "integrity": "sha1-AMOQuSigeZslGsz2MaoJ4BzGKZw=", - "dev": true, - "requires": { - "deep-assign": "1.0.0", - "stat-mode": "0.2.2", - "through2": "2.0.3" - } - }, - "gulp-filter": { - "version": "5.0.1", - "resolved": "https://registry.npmjs.org/gulp-filter/-/gulp-filter-5.0.1.tgz", - "integrity": "sha512-5olRzAhFdXB2klCu1lnazP65aO9YdA/5WfC9VdInIc8PrUeDIoZfaA3Edb0yUBGhVdHv4eHKL9Fg5tUoEJ9z5A==", - "dev": true, - "requires": { - "gulp-util": "3.0.8", - "multimatch": "2.1.0", - "streamfilter": "1.0.5" - } - }, - "gulp-gunzip": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/gulp-gunzip/-/gulp-gunzip-1.0.0.tgz", - "integrity": "sha1-FbdBFF6Dqcb1CIYkG1fMWHHxUak=", - "dev": true, - "requires": { - "through2": "0.6.5", - "vinyl": "0.4.6" - }, - "dependencies": { - "clone": { - "version": "0.2.0", - "resolved": "https://registry.npmjs.org/clone/-/clone-0.2.0.tgz", - "integrity": "sha1-xhJqkK1Pctv1rNskPMN3JP6T/B8=", - "dev": true - }, - "readable-stream": { - "version": "1.0.34", - "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-1.0.34.tgz", - "integrity": "sha1-Elgg40vIQtLyqq+v5MKRbuMsFXw=", - "dev": true, - "requires": { - "core-util-is": "1.0.2", - "inherits": "2.0.3", - "isarray": "0.0.1", - "string_decoder": "0.10.31" - } - }, - "through2": { - "version": "0.6.5", - "resolved": "https://registry.npmjs.org/through2/-/through2-0.6.5.tgz", - "integrity": "sha1-QaucZ7KdVyCQcUEOHXp6lozTrUg=", - "dev": true, - "requires": { - "readable-stream": "1.0.34", - "xtend": "4.0.1" - } - }, - "vinyl": { - "version": "0.4.6", - "resolved": "https://registry.npmjs.org/vinyl/-/vinyl-0.4.6.tgz", - "integrity": "sha1-LzVsh6VQolVGHza76ypbqL94SEc=", - "dev": true, - "requires": { - "clone": "0.2.0", - "clone-stats": "0.0.1" - } - } - } - }, - "gulp-remote-src": { - "version": "0.4.3", - "resolved": "https://registry.npmjs.org/gulp-remote-src/-/gulp-remote-src-0.4.3.tgz", - "integrity": "sha1-VyjP1kNDPdSEXd7wlp8PlxoqtKE=", - "dev": true, - "requires": { - "event-stream": "3.3.4", - "node.extend": "1.1.6", - "request": "2.79.0", - "through2": "2.0.3", - "vinyl": "2.0.2" - }, - "dependencies": { - "clone-stats": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/clone-stats/-/clone-stats-1.0.0.tgz", - "integrity": "sha1-s3gt/4u1R04Yuba/D9/ngvh3doA=", - "dev": true - }, - "replace-ext": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/replace-ext/-/replace-ext-1.0.0.tgz", - "integrity": "sha1-3mMSg3P8v3w8z6TeWkgMRaZ5WOs=", - "dev": true - }, - "request": { - "version": "2.79.0", - "resolved": "https://registry.npmjs.org/request/-/request-2.79.0.tgz", - "integrity": "sha1-Tf5b9r6LjNw3/Pk+BLZVd3InEN4=", - "dev": true, - "requires": { - "aws-sign2": "0.6.0", - "aws4": "1.6.0", - "caseless": "0.11.0", - "combined-stream": "1.0.5", - "extend": "3.0.1", - "forever-agent": "0.6.1", - "form-data": "2.1.4", - "har-validator": "2.0.6", - "hawk": "3.1.3", - "http-signature": "1.1.1", - "is-typedarray": "1.0.0", - "isstream": "0.1.2", - "json-stringify-safe": "5.0.1", - "mime-types": "2.1.17", - "oauth-sign": "0.8.2", - "qs": "6.3.2", - "stringstream": "0.0.5", - "tough-cookie": "2.3.3", - "tunnel-agent": "0.4.3", - "uuid": "3.1.0" - } - }, - "vinyl": { - "version": "2.0.2", - "resolved": "https://registry.npmjs.org/vinyl/-/vinyl-2.0.2.tgz", - "integrity": "sha1-CjcT2NTpIhxY8QyhbAEWyeJe2nw=", - "dev": true, - "requires": { - "clone": "1.0.3", - "clone-buffer": "1.0.0", - "clone-stats": "1.0.0", - "cloneable-readable": "1.0.0", - "is-stream": "1.1.0", - "remove-trailing-separator": "1.1.0", - "replace-ext": "1.0.0" - } - } - } - }, - "gulp-sourcemaps": { - "version": "2.6.1", - "resolved": "https://registry.npmjs.org/gulp-sourcemaps/-/gulp-sourcemaps-2.6.1.tgz", - "integrity": "sha512-1qHCI3hdmsMdq/SUotxwUh/L8YzlI6J9zQ5ifNOtx4Y6KV5y5sGuORv1KZzWhuKtz/mXNh5xLESUtwC4EndCjA==", - "dev": true, - "requires": { - "@gulp-sourcemaps/identity-map": "1.0.1", - "@gulp-sourcemaps/map-sources": "1.0.0", - "acorn": "4.0.13", - "convert-source-map": "1.5.0", - "css": "2.2.1", - "debug-fabulous": "0.2.1", - "detect-newline": "2.1.0", - "graceful-fs": "4.1.11", - "source-map": "0.6.1", - "strip-bom-string": "1.0.0", - "through2": "2.0.3", - "vinyl": "1.2.0" - }, - "dependencies": { - "graceful-fs": { - "version": "4.1.11", - "resolved": "https://registry.npmjs.org/graceful-fs/-/graceful-fs-4.1.11.tgz", - "integrity": "sha1-Dovf5NHduIVNZOBOp8AOKgJuVlg=", - "dev": true - }, - "vinyl": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/vinyl/-/vinyl-1.2.0.tgz", - "integrity": "sha1-XIgDbPVl5d8FVYv8kR+GVt8hiIQ=", - "dev": true, - "requires": { - "clone": "1.0.3", - "clone-stats": "0.0.1", - "replace-ext": "0.0.1" - } - } - } - }, - "gulp-symdest": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/gulp-symdest/-/gulp-symdest-1.1.0.tgz", - "integrity": "sha1-wWUyBzLRks5W/ZQnH/oSMjS/KuA=", - "dev": true, - "requires": { - "event-stream": "3.3.4", - "mkdirp": "0.5.1", - "queue": "3.1.0", - "vinyl-fs": "2.4.4" - }, - "dependencies": { - "glob": { - "version": "5.0.15", - "resolved": "https://registry.npmjs.org/glob/-/glob-5.0.15.tgz", - "integrity": "sha1-G8k2ueAvSmA/zCIuz3Yz0wuLk7E=", - "dev": true, - "requires": { - "inflight": "1.0.6", - "inherits": "2.0.3", - "minimatch": "3.0.4", - "once": "1.4.0", - "path-is-absolute": "1.0.1" - } - }, - "glob-parent": { - "version": "3.1.0", - "resolved": "https://registry.npmjs.org/glob-parent/-/glob-parent-3.1.0.tgz", - "integrity": "sha1-nmr2KZ2NO9K9QEMIMr0RPfkGxa4=", - "dev": true, - "requires": { - "is-glob": "3.1.0", - "path-dirname": "1.0.2" - } - }, - "glob-stream": { - "version": "5.3.5", - "resolved": "https://registry.npmjs.org/glob-stream/-/glob-stream-5.3.5.tgz", - "integrity": "sha1-pVZlqajM3EGRWofHAeMtTgFvrSI=", - "dev": true, - "requires": { - "extend": "3.0.1", - "glob": "5.0.15", - "glob-parent": "3.1.0", - "micromatch": "2.3.11", - "ordered-read-streams": "0.3.0", - "through2": "0.6.5", - "to-absolute-glob": "0.1.1", - "unique-stream": "2.2.1" - }, - "dependencies": { - "isarray": { - "version": "0.0.1", - "resolved": "https://registry.npmjs.org/isarray/-/isarray-0.0.1.tgz", - "integrity": "sha1-ihis/Kmo9Bd+Cav8YDiTmwXR7t8=", - "dev": true - }, - "readable-stream": { - "version": "1.0.34", - "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-1.0.34.tgz", - "integrity": "sha1-Elgg40vIQtLyqq+v5MKRbuMsFXw=", - "dev": true, - "requires": { - "core-util-is": "1.0.2", - "inherits": "2.0.3", - "isarray": "0.0.1", - "string_decoder": "0.10.31" - } - }, - "string_decoder": { - "version": "0.10.31", - "resolved": "https://registry.npmjs.org/string_decoder/-/string_decoder-0.10.31.tgz", - "integrity": "sha1-YuIDvEF2bGwoyfyEMB2rHFMQ+pQ=", - "dev": true - }, - "through2": { - "version": "0.6.5", - "resolved": "https://registry.npmjs.org/through2/-/through2-0.6.5.tgz", - "integrity": "sha1-QaucZ7KdVyCQcUEOHXp6lozTrUg=", - "dev": true, - "requires": { - "readable-stream": "1.0.34", - "xtend": "4.0.1" - } - } - } - }, - "graceful-fs": { - "version": "4.1.11", - "resolved": "https://registry.npmjs.org/graceful-fs/-/graceful-fs-4.1.11.tgz", - "integrity": "sha1-Dovf5NHduIVNZOBOp8AOKgJuVlg=", - "dev": true - }, - "gulp-sourcemaps": { - "version": "1.6.0", - "resolved": "https://registry.npmjs.org/gulp-sourcemaps/-/gulp-sourcemaps-1.6.0.tgz", - "integrity": "sha1-uG/zSdgBzrVuHZ59x7vLS33uYAw=", - "dev": true, - "requires": { - "convert-source-map": "1.5.0", - "graceful-fs": "4.1.11", - "strip-bom": "2.0.0", - "through2": "2.0.3", - "vinyl": "1.2.0" - } - }, - "is-extglob": { - "version": "2.1.1", - "resolved": "https://registry.npmjs.org/is-extglob/-/is-extglob-2.1.1.tgz", - "integrity": "sha1-qIwCU1eR8C7TfHahueqXc8gz+MI=", - "dev": true - }, - "is-glob": { - "version": "3.1.0", - "resolved": "https://registry.npmjs.org/is-glob/-/is-glob-3.1.0.tgz", - "integrity": "sha1-e6WuJCF4BKxwcHuWkiVnSGzD6Eo=", - "dev": true, - "requires": { - "is-extglob": "2.1.1" - } - }, - "isarray": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/isarray/-/isarray-1.0.0.tgz", - "integrity": "sha1-u5NdSFgsuhaMBoNJV6VKPgcSTxE=", - "dev": true - }, - "ordered-read-streams": { - "version": "0.3.0", - "resolved": "https://registry.npmjs.org/ordered-read-streams/-/ordered-read-streams-0.3.0.tgz", - "integrity": "sha1-cTfmmzKYuzQiR6G77jiByA4v14s=", - "dev": true, - "requires": { - "is-stream": "1.1.0", - "readable-stream": "2.3.3" - } - }, - "readable-stream": { - "version": "2.3.3", - "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-2.3.3.tgz", - "integrity": "sha512-m+qzzcn7KUxEmd1gMbchF+Y2eIUbieUaxkWtptyHywrX0rE8QEYqPC07Vuy4Wm32/xE16NcdBctb8S0Xe/5IeQ==", - "dev": true, - "requires": { - "core-util-is": "1.0.2", - "inherits": "2.0.3", - "isarray": "1.0.0", - "process-nextick-args": "1.0.7", - "safe-buffer": "5.1.1", - "string_decoder": "1.0.3", - "util-deprecate": "1.0.2" - } - }, - "string_decoder": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/string_decoder/-/string_decoder-1.0.3.tgz", - "integrity": "sha512-4AH6Z5fzNNBcH+6XDMfA/BTt87skxqJlO0lAh3Dker5zThcAxG6mKz+iGu308UKoPPQ8Dcqx/4JhujzltRa+hQ==", - "dev": true, - "requires": { - "safe-buffer": "5.1.1" - } - }, - "strip-bom": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/strip-bom/-/strip-bom-2.0.0.tgz", - "integrity": "sha1-YhmoVhZSBJHzV4i9vxRHqZx+aw4=", - "dev": true, - "requires": { - "is-utf8": "0.2.1" - } - }, - "unique-stream": { - "version": "2.2.1", - "resolved": "https://registry.npmjs.org/unique-stream/-/unique-stream-2.2.1.tgz", - "integrity": "sha1-WqADz76Uxf+GbE59ZouxxNuts2k=", - "dev": true, - "requires": { - "json-stable-stringify": "1.0.1", - "through2-filter": "2.0.0" - } - }, - "vinyl": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/vinyl/-/vinyl-1.2.0.tgz", - "integrity": "sha1-XIgDbPVl5d8FVYv8kR+GVt8hiIQ=", - "dev": true, - "requires": { - "clone": "1.0.3", - "clone-stats": "0.0.1", - "replace-ext": "0.0.1" - } - }, - "vinyl-fs": { - "version": "2.4.4", - "resolved": "https://registry.npmjs.org/vinyl-fs/-/vinyl-fs-2.4.4.tgz", - "integrity": "sha1-vm/zJwy1Xf19MGNkDegfJddTIjk=", - "dev": true, - "requires": { - "duplexify": "3.5.1", - "glob-stream": "5.3.5", - "graceful-fs": "4.1.11", - "gulp-sourcemaps": "1.6.0", - "is-valid-glob": "0.3.0", - "lazystream": "1.0.0", - "lodash.isequal": "4.5.0", - "merge-stream": "1.0.1", - "mkdirp": "0.5.1", - "object-assign": "4.1.1", - "readable-stream": "2.3.3", - "strip-bom": "2.0.0", - "strip-bom-stream": "1.0.0", - "through2": "2.0.3", - "through2-filter": "2.0.0", - "vali-date": "1.0.0", - "vinyl": "1.2.0" - } - } - } - }, - "gulp-tsb": { - "version": "2.0.4", - "resolved": "https://registry.npmjs.org/gulp-tsb/-/gulp-tsb-2.0.4.tgz", - "integrity": "sha1-CymAktTf1OXP2AZ57Uwdk7/bpko=", - "dev": true, - "requires": { - "gulp-util": "3.0.8", - "through": "2.3.8", - "vinyl": "0.4.6" - }, - "dependencies": { - "clone": { - "version": "0.2.0", - "resolved": "https://registry.npmjs.org/clone/-/clone-0.2.0.tgz", - "integrity": "sha1-xhJqkK1Pctv1rNskPMN3JP6T/B8=", - "dev": true - }, - "vinyl": { - "version": "0.4.6", - "resolved": "https://registry.npmjs.org/vinyl/-/vinyl-0.4.6.tgz", - "integrity": "sha1-LzVsh6VQolVGHza76ypbqL94SEc=", - "dev": true, - "requires": { - "clone": "0.2.0", - "clone-stats": "0.0.1" - } - } - } - }, - "gulp-tslint": { - "version": "8.1.2", - "resolved": "https://registry.npmjs.org/gulp-tslint/-/gulp-tslint-8.1.2.tgz", - "integrity": "sha512-0RNGqbp2TKPdbG+sWU3mNMXEMuF/noY1KS4+jd5lOStkvuFINkFL29dHX3IT1u+vVFD4Glwf+lkcdR2QMVNMzA==", - "dev": true, - "requires": { - "gulp-util": "3.0.8", - "map-stream": "0.0.7", - "through": "2.3.8" - }, - "dependencies": { - "map-stream": { - "version": "0.0.7", - "resolved": "https://registry.npmjs.org/map-stream/-/map-stream-0.0.7.tgz", - "integrity": "sha1-ih8HiW2CsQkmvTdEokIACfiJdKg=", - "dev": true - } - } - }, - "gulp-typescript": { - "version": "3.2.2", - "resolved": "https://registry.npmjs.org/gulp-typescript/-/gulp-typescript-3.2.2.tgz", - "integrity": "sha1-t+Xh08s193LlPmBAJmAYJuK+d/w=", - "dev": true, - "requires": { - "gulp-util": "3.0.8", - "source-map": "0.5.7", - "through2": "2.0.3", - "vinyl-fs": "2.4.4" - }, - "dependencies": { - "glob": { - "version": "5.0.15", - "resolved": "https://registry.npmjs.org/glob/-/glob-5.0.15.tgz", - "integrity": "sha1-G8k2ueAvSmA/zCIuz3Yz0wuLk7E=", - "dev": true, - "requires": { - "inflight": "1.0.6", - "inherits": "2.0.3", - "minimatch": "3.0.4", - "once": "1.4.0", - "path-is-absolute": "1.0.1" - } - }, - "glob-parent": { - "version": "3.1.0", - "resolved": "https://registry.npmjs.org/glob-parent/-/glob-parent-3.1.0.tgz", - "integrity": "sha1-nmr2KZ2NO9K9QEMIMr0RPfkGxa4=", - "dev": true, - "requires": { - "is-glob": "3.1.0", - "path-dirname": "1.0.2" - } - }, - "glob-stream": { - "version": "5.3.5", - "resolved": "https://registry.npmjs.org/glob-stream/-/glob-stream-5.3.5.tgz", - "integrity": "sha1-pVZlqajM3EGRWofHAeMtTgFvrSI=", - "dev": true, - "requires": { - "extend": "3.0.1", - "glob": "5.0.15", - "glob-parent": "3.1.0", - "micromatch": "2.3.11", - "ordered-read-streams": "0.3.0", - "through2": "0.6.5", - "to-absolute-glob": "0.1.1", - "unique-stream": "2.2.1" - }, - "dependencies": { - "isarray": { - "version": "0.0.1", - "resolved": "https://registry.npmjs.org/isarray/-/isarray-0.0.1.tgz", - "integrity": "sha1-ihis/Kmo9Bd+Cav8YDiTmwXR7t8=", - "dev": true - }, - "readable-stream": { - "version": "1.0.34", - "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-1.0.34.tgz", - "integrity": "sha1-Elgg40vIQtLyqq+v5MKRbuMsFXw=", - "dev": true, - "requires": { - "core-util-is": "1.0.2", - "inherits": "2.0.3", - "isarray": "0.0.1", - "string_decoder": "0.10.31" - } - }, - "string_decoder": { - "version": "0.10.31", - "resolved": "https://registry.npmjs.org/string_decoder/-/string_decoder-0.10.31.tgz", - "integrity": "sha1-YuIDvEF2bGwoyfyEMB2rHFMQ+pQ=", - "dev": true - }, - "through2": { - "version": "0.6.5", - "resolved": "https://registry.npmjs.org/through2/-/through2-0.6.5.tgz", - "integrity": "sha1-QaucZ7KdVyCQcUEOHXp6lozTrUg=", - "dev": true, - "requires": { - "readable-stream": "1.0.34", - "xtend": "4.0.1" - } - } - } - }, - "graceful-fs": { - "version": "4.1.11", - "resolved": "https://registry.npmjs.org/graceful-fs/-/graceful-fs-4.1.11.tgz", - "integrity": "sha1-Dovf5NHduIVNZOBOp8AOKgJuVlg=", - "dev": true - }, - "gulp-sourcemaps": { - "version": "1.6.0", - "resolved": "https://registry.npmjs.org/gulp-sourcemaps/-/gulp-sourcemaps-1.6.0.tgz", - "integrity": "sha1-uG/zSdgBzrVuHZ59x7vLS33uYAw=", - "dev": true, - "requires": { - "convert-source-map": "1.5.0", - "graceful-fs": "4.1.11", - "strip-bom": "2.0.0", - "through2": "2.0.3", - "vinyl": "1.2.0" - } - }, - "is-extglob": { - "version": "2.1.1", - "resolved": "https://registry.npmjs.org/is-extglob/-/is-extglob-2.1.1.tgz", - "integrity": "sha1-qIwCU1eR8C7TfHahueqXc8gz+MI=", - "dev": true - }, - "is-glob": { - "version": "3.1.0", - "resolved": "https://registry.npmjs.org/is-glob/-/is-glob-3.1.0.tgz", - "integrity": "sha1-e6WuJCF4BKxwcHuWkiVnSGzD6Eo=", - "dev": true, - "requires": { - "is-extglob": "2.1.1" - } - }, - "isarray": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/isarray/-/isarray-1.0.0.tgz", - "integrity": "sha1-u5NdSFgsuhaMBoNJV6VKPgcSTxE=", - "dev": true - }, - "ordered-read-streams": { - "version": "0.3.0", - "resolved": "https://registry.npmjs.org/ordered-read-streams/-/ordered-read-streams-0.3.0.tgz", - "integrity": "sha1-cTfmmzKYuzQiR6G77jiByA4v14s=", - "dev": true, - "requires": { - "is-stream": "1.1.0", - "readable-stream": "2.3.3" - } - }, - "readable-stream": { - "version": "2.3.3", - "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-2.3.3.tgz", - "integrity": "sha512-m+qzzcn7KUxEmd1gMbchF+Y2eIUbieUaxkWtptyHywrX0rE8QEYqPC07Vuy4Wm32/xE16NcdBctb8S0Xe/5IeQ==", - "dev": true, - "requires": { - "core-util-is": "1.0.2", - "inherits": "2.0.3", - "isarray": "1.0.0", - "process-nextick-args": "1.0.7", - "safe-buffer": "5.1.1", - "string_decoder": "1.0.3", - "util-deprecate": "1.0.2" - } - }, - "source-map": { - "version": "0.5.7", - "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.5.7.tgz", - "integrity": "sha1-igOdLRAh0i0eoUyA2OpGi6LvP8w=", - "dev": true - }, - "string_decoder": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/string_decoder/-/string_decoder-1.0.3.tgz", - "integrity": "sha512-4AH6Z5fzNNBcH+6XDMfA/BTt87skxqJlO0lAh3Dker5zThcAxG6mKz+iGu308UKoPPQ8Dcqx/4JhujzltRa+hQ==", - "dev": true, - "requires": { - "safe-buffer": "5.1.1" - } - }, - "strip-bom": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/strip-bom/-/strip-bom-2.0.0.tgz", - "integrity": "sha1-YhmoVhZSBJHzV4i9vxRHqZx+aw4=", - "dev": true, - "requires": { - "is-utf8": "0.2.1" - } - }, - "unique-stream": { - "version": "2.2.1", - "resolved": "https://registry.npmjs.org/unique-stream/-/unique-stream-2.2.1.tgz", - "integrity": "sha1-WqADz76Uxf+GbE59ZouxxNuts2k=", - "dev": true, - "requires": { - "json-stable-stringify": "1.0.1", - "through2-filter": "2.0.0" - } - }, - "vinyl": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/vinyl/-/vinyl-1.2.0.tgz", - "integrity": "sha1-XIgDbPVl5d8FVYv8kR+GVt8hiIQ=", - "dev": true, - "requires": { - "clone": "1.0.3", - "clone-stats": "0.0.1", - "replace-ext": "0.0.1" - } - }, - "vinyl-fs": { - "version": "2.4.4", - "resolved": "https://registry.npmjs.org/vinyl-fs/-/vinyl-fs-2.4.4.tgz", - "integrity": "sha1-vm/zJwy1Xf19MGNkDegfJddTIjk=", - "dev": true, - "requires": { - "duplexify": "3.5.1", - "glob-stream": "5.3.5", - "graceful-fs": "4.1.11", - "gulp-sourcemaps": "1.6.0", - "is-valid-glob": "0.3.0", - "lazystream": "1.0.0", - "lodash.isequal": "4.5.0", - "merge-stream": "1.0.1", - "mkdirp": "0.5.1", - "object-assign": "4.1.1", - "readable-stream": "2.3.3", - "strip-bom": "2.0.0", - "strip-bom-stream": "1.0.0", - "through2": "2.0.3", - "through2-filter": "2.0.0", - "vali-date": "1.0.0", - "vinyl": "1.2.0" - } - } - } - }, - "gulp-uglify": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/gulp-uglify/-/gulp-uglify-2.0.0.tgz", - "integrity": "sha1-y+Sq5P4La912AzW8RvIA//aZxK8=", - "dev": true, - "requires": { - "gulplog": "1.0.0", - "has-gulplog": "0.1.0", - "lodash": "4.17.4", - "make-error-cause": "1.2.2", - "through2": "2.0.3", - "uglify-js": "2.7.0", - "uglify-save-license": "0.4.1", - "vinyl-sourcemaps-apply": "0.2.1" - }, - "dependencies": { - "lodash": { - "version": "4.17.4", - "resolved": "https://registry.npmjs.org/lodash/-/lodash-4.17.4.tgz", - "integrity": "sha1-eCA6TRwyiuHYbcpkYONptX9AVa4=", - "dev": true - } - } - }, - "gulp-untar": { - "version": "0.0.6", - "resolved": "https://registry.npmjs.org/gulp-untar/-/gulp-untar-0.0.6.tgz", - "integrity": "sha1-1r3v3n6ajgVMnxYjhaB4LEvnQAA=", - "dev": true, - "requires": { - "event-stream": "3.3.4", - "gulp-util": "3.0.8", - "streamifier": "0.1.1", - "tar": "2.2.1", - "through2": "2.0.3" - } - }, - "gulp-util": { - "version": "3.0.8", - "resolved": "https://registry.npmjs.org/gulp-util/-/gulp-util-3.0.8.tgz", - "integrity": "sha1-AFTh50RQLifATBh8PsxQXdVLu08=", - "dev": true, - "requires": { - "array-differ": "1.0.0", - "array-uniq": "1.0.3", - "beeper": "1.1.1", - "chalk": "1.1.3", - "dateformat": "2.2.0", - "fancy-log": "1.3.0", - "gulplog": "1.0.0", - "has-gulplog": "0.1.0", - "lodash._reescape": "3.0.0", - "lodash._reevaluate": "3.0.0", - "lodash._reinterpolate": "3.0.0", - "lodash.template": "3.6.2", - "minimist": "1.2.0", - "multipipe": "0.1.2", - "object-assign": "3.0.0", - "replace-ext": "0.0.1", - "through2": "2.0.3", - "vinyl": "0.5.3" - }, - "dependencies": { - "object-assign": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/object-assign/-/object-assign-3.0.0.tgz", - "integrity": "sha1-m+3VygiXlJvKR+f/QIBi1Un1h/I=", - "dev": true - } - } - }, - "gulp-vinyl-zip": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/gulp-vinyl-zip/-/gulp-vinyl-zip-2.1.0.tgz", - "integrity": "sha1-JOQGhdwFtxSZlSRQmeBZAmO+ja0=", - "dev": true, - "requires": { - "event-stream": "3.3.4", - "queue": "4.4.2", - "through2": "2.0.3", - "vinyl": "2.1.0", - "vinyl-fs": "2.4.4", - "yauzl": "2.9.1", - "yazl": "2.4.3" - }, - "dependencies": { - "clone": { - "version": "2.1.1", - "resolved": "https://registry.npmjs.org/clone/-/clone-2.1.1.tgz", - "integrity": "sha1-0hfR6WERjjrJpLi7oyhVU79kfNs=", - "dev": true - }, - "clone-stats": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/clone-stats/-/clone-stats-1.0.0.tgz", - "integrity": "sha1-s3gt/4u1R04Yuba/D9/ngvh3doA=", - "dev": true - }, - "glob": { - "version": "5.0.15", - "resolved": "https://registry.npmjs.org/glob/-/glob-5.0.15.tgz", - "integrity": "sha1-G8k2ueAvSmA/zCIuz3Yz0wuLk7E=", - "dev": true, - "requires": { - "inflight": "1.0.6", - "inherits": "2.0.3", - "minimatch": "3.0.4", - "once": "1.4.0", - "path-is-absolute": "1.0.1" - } - }, - "glob-parent": { - "version": "3.1.0", - "resolved": "https://registry.npmjs.org/glob-parent/-/glob-parent-3.1.0.tgz", - "integrity": "sha1-nmr2KZ2NO9K9QEMIMr0RPfkGxa4=", - "dev": true, - "requires": { - "is-glob": "3.1.0", - "path-dirname": "1.0.2" - } - }, - "glob-stream": { - "version": "5.3.5", - "resolved": "https://registry.npmjs.org/glob-stream/-/glob-stream-5.3.5.tgz", - "integrity": "sha1-pVZlqajM3EGRWofHAeMtTgFvrSI=", - "dev": true, - "requires": { - "extend": "3.0.1", - "glob": "5.0.15", - "glob-parent": "3.1.0", - "micromatch": "2.3.11", - "ordered-read-streams": "0.3.0", - "through2": "0.6.5", - "to-absolute-glob": "0.1.1", - "unique-stream": "2.2.1" - }, - "dependencies": { - "isarray": { - "version": "0.0.1", - "resolved": "https://registry.npmjs.org/isarray/-/isarray-0.0.1.tgz", - "integrity": "sha1-ihis/Kmo9Bd+Cav8YDiTmwXR7t8=", - "dev": true - }, - "readable-stream": { - "version": "1.0.34", - "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-1.0.34.tgz", - "integrity": "sha1-Elgg40vIQtLyqq+v5MKRbuMsFXw=", - "dev": true, - "requires": { - "core-util-is": "1.0.2", - "inherits": "2.0.3", - "isarray": "0.0.1", - "string_decoder": "0.10.31" - } - }, - "string_decoder": { - "version": "0.10.31", - "resolved": "https://registry.npmjs.org/string_decoder/-/string_decoder-0.10.31.tgz", - "integrity": "sha1-YuIDvEF2bGwoyfyEMB2rHFMQ+pQ=", - "dev": true - }, - "through2": { - "version": "0.6.5", - "resolved": "https://registry.npmjs.org/through2/-/through2-0.6.5.tgz", - "integrity": "sha1-QaucZ7KdVyCQcUEOHXp6lozTrUg=", - "dev": true, - "requires": { - "readable-stream": "1.0.34", - "xtend": "4.0.1" - } - } - } - }, - "graceful-fs": { - "version": "4.1.11", - "resolved": "https://registry.npmjs.org/graceful-fs/-/graceful-fs-4.1.11.tgz", - "integrity": "sha1-Dovf5NHduIVNZOBOp8AOKgJuVlg=", - "dev": true - }, - "gulp-sourcemaps": { - "version": "1.6.0", - "resolved": "https://registry.npmjs.org/gulp-sourcemaps/-/gulp-sourcemaps-1.6.0.tgz", - "integrity": "sha1-uG/zSdgBzrVuHZ59x7vLS33uYAw=", - "dev": true, - "requires": { - "convert-source-map": "1.5.0", - "graceful-fs": "4.1.11", - "strip-bom": "2.0.0", - "through2": "2.0.3", - "vinyl": "1.2.0" - }, - "dependencies": { - "clone": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/clone/-/clone-1.0.3.tgz", - "integrity": "sha1-KY1+IjFmD0DAA8LtMUDezz9TCF8=", - "dev": true - }, - "clone-stats": { - "version": "0.0.1", - "resolved": "https://registry.npmjs.org/clone-stats/-/clone-stats-0.0.1.tgz", - "integrity": "sha1-uI+UqCzzi4eR1YBG6kAprYjKmdE=", - "dev": true - }, - "replace-ext": { - "version": "0.0.1", - "resolved": "https://registry.npmjs.org/replace-ext/-/replace-ext-0.0.1.tgz", - "integrity": "sha1-KbvZIHinOfC8zitO5B6DeVNSKSQ=", - "dev": true - }, - "vinyl": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/vinyl/-/vinyl-1.2.0.tgz", - "integrity": "sha1-XIgDbPVl5d8FVYv8kR+GVt8hiIQ=", - "dev": true, - "requires": { - "clone": "1.0.3", - "clone-stats": "0.0.1", - "replace-ext": "0.0.1" - } - } - } - }, - "is-extglob": { - "version": "2.1.1", - "resolved": "https://registry.npmjs.org/is-extglob/-/is-extglob-2.1.1.tgz", - "integrity": "sha1-qIwCU1eR8C7TfHahueqXc8gz+MI=", - "dev": true - }, - "is-glob": { - "version": "3.1.0", - "resolved": "https://registry.npmjs.org/is-glob/-/is-glob-3.1.0.tgz", - "integrity": "sha1-e6WuJCF4BKxwcHuWkiVnSGzD6Eo=", - "dev": true, - "requires": { - "is-extglob": "2.1.1" - } - }, - "isarray": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/isarray/-/isarray-1.0.0.tgz", - "integrity": "sha1-u5NdSFgsuhaMBoNJV6VKPgcSTxE=", - "dev": true - }, - "ordered-read-streams": { - "version": "0.3.0", - "resolved": "https://registry.npmjs.org/ordered-read-streams/-/ordered-read-streams-0.3.0.tgz", - "integrity": "sha1-cTfmmzKYuzQiR6G77jiByA4v14s=", - "dev": true, - "requires": { - "is-stream": "1.1.0", - "readable-stream": "2.3.3" - } - }, - "queue": { - "version": "4.4.2", - "resolved": "https://registry.npmjs.org/queue/-/queue-4.4.2.tgz", - "integrity": "sha512-fSMRXbwhMwipcDZ08enW2vl+YDmAmhcNcr43sCJL8DIg+CFOsoRLG23ctxA+fwNk1w55SePSiS7oqQQSgQoVJQ==", - "dev": true, - "requires": { - "inherits": "2.0.3" - } - }, - "readable-stream": { - "version": "2.3.3", - "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-2.3.3.tgz", - "integrity": "sha512-m+qzzcn7KUxEmd1gMbchF+Y2eIUbieUaxkWtptyHywrX0rE8QEYqPC07Vuy4Wm32/xE16NcdBctb8S0Xe/5IeQ==", - "dev": true, - "requires": { - "core-util-is": "1.0.2", - "inherits": "2.0.3", - "isarray": "1.0.0", - "process-nextick-args": "1.0.7", - "safe-buffer": "5.1.1", - "string_decoder": "1.0.3", - "util-deprecate": "1.0.2" - } - }, - "replace-ext": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/replace-ext/-/replace-ext-1.0.0.tgz", - "integrity": "sha1-3mMSg3P8v3w8z6TeWkgMRaZ5WOs=", - "dev": true - }, - "string_decoder": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/string_decoder/-/string_decoder-1.0.3.tgz", - "integrity": "sha512-4AH6Z5fzNNBcH+6XDMfA/BTt87skxqJlO0lAh3Dker5zThcAxG6mKz+iGu308UKoPPQ8Dcqx/4JhujzltRa+hQ==", - "dev": true, - "requires": { - "safe-buffer": "5.1.1" - } - }, - "strip-bom": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/strip-bom/-/strip-bom-2.0.0.tgz", - "integrity": "sha1-YhmoVhZSBJHzV4i9vxRHqZx+aw4=", - "dev": true, - "requires": { - "is-utf8": "0.2.1" - } - }, - "unique-stream": { - "version": "2.2.1", - "resolved": "https://registry.npmjs.org/unique-stream/-/unique-stream-2.2.1.tgz", - "integrity": "sha1-WqADz76Uxf+GbE59ZouxxNuts2k=", - "dev": true, - "requires": { - "json-stable-stringify": "1.0.1", - "through2-filter": "2.0.0" - } - }, - "vinyl": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/vinyl/-/vinyl-2.1.0.tgz", - "integrity": "sha1-Ah+cLPlR1rk5lDyJ617lrdT9kkw=", - "dev": true, - "requires": { - "clone": "2.1.1", - "clone-buffer": "1.0.0", - "clone-stats": "1.0.0", - "cloneable-readable": "1.0.0", - "remove-trailing-separator": "1.1.0", - "replace-ext": "1.0.0" - } - }, - "vinyl-fs": { - "version": "2.4.4", - "resolved": "https://registry.npmjs.org/vinyl-fs/-/vinyl-fs-2.4.4.tgz", - "integrity": "sha1-vm/zJwy1Xf19MGNkDegfJddTIjk=", - "dev": true, - "requires": { - "duplexify": "3.5.1", - "glob-stream": "5.3.5", - "graceful-fs": "4.1.11", - "gulp-sourcemaps": "1.6.0", - "is-valid-glob": "0.3.0", - "lazystream": "1.0.0", - "lodash.isequal": "4.5.0", - "merge-stream": "1.0.1", - "mkdirp": "0.5.1", - "object-assign": "4.1.1", - "readable-stream": "2.3.3", - "strip-bom": "2.0.0", - "strip-bom-stream": "1.0.0", - "through2": "2.0.3", - "through2-filter": "2.0.0", - "vali-date": "1.0.0", - "vinyl": "1.2.0" - }, - "dependencies": { - "clone": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/clone/-/clone-1.0.3.tgz", - "integrity": "sha1-KY1+IjFmD0DAA8LtMUDezz9TCF8=", - "dev": true - }, - "clone-stats": { - "version": "0.0.1", - "resolved": "https://registry.npmjs.org/clone-stats/-/clone-stats-0.0.1.tgz", - "integrity": "sha1-uI+UqCzzi4eR1YBG6kAprYjKmdE=", - "dev": true - }, - "replace-ext": { - "version": "0.0.1", - "resolved": "https://registry.npmjs.org/replace-ext/-/replace-ext-0.0.1.tgz", - "integrity": "sha1-KbvZIHinOfC8zitO5B6DeVNSKSQ=", - "dev": true - }, - "vinyl": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/vinyl/-/vinyl-1.2.0.tgz", - "integrity": "sha1-XIgDbPVl5d8FVYv8kR+GVt8hiIQ=", - "dev": true, - "requires": { - "clone": "1.0.3", - "clone-stats": "0.0.1", - "replace-ext": "0.0.1" - } - } - } - } - } - }, - "gulplog": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/gulplog/-/gulplog-1.0.0.tgz", - "integrity": "sha1-4oxNRdBey77YGDY86PnFkmIp/+U=", - "dev": true, - "requires": { - "glogg": "1.0.0" - } - }, - "har-schema": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/har-schema/-/har-schema-2.0.0.tgz", - "integrity": "sha1-qUwiJOvKwEeCoNkDVSHyRzW37JI=", - "dev": true - }, - "har-validator": { - "version": "2.0.6", - "resolved": "https://registry.npmjs.org/har-validator/-/har-validator-2.0.6.tgz", - "integrity": "sha1-zcvAgYgmWtEZtqWnyKtw7s+10n0=", - "dev": true, - "requires": { - "chalk": "1.1.3", - "commander": "2.11.0", - "is-my-json-valid": "2.16.1", - "pinkie-promise": "2.0.1" - } - }, - "has-ansi": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/has-ansi/-/has-ansi-2.0.0.tgz", - "integrity": "sha1-NPUEnOHs3ysGSa8+8k5F7TVBbZE=", - "dev": true, - "requires": { - "ansi-regex": "2.1.1" - } - }, - "has-flag": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-2.0.0.tgz", - "integrity": "sha1-6CB68cx7MNRGzHC3NLXovhj4jVE=", - "dev": true - }, - "has-gulplog": { - "version": "0.1.0", - "resolved": "https://registry.npmjs.org/has-gulplog/-/has-gulplog-0.1.0.tgz", - "integrity": "sha1-ZBTIKRNpfaUVkDl9r7EvIpZ4Ec4=", - "dev": true, - "requires": { - "sparkles": "1.0.0" - } - }, - "hawk": { - "version": "3.1.3", - "resolved": "https://registry.npmjs.org/hawk/-/hawk-3.1.3.tgz", - "integrity": "sha1-B4REvXwWQLD+VA0sm3PVlnjo4cQ=", - "dev": true, - "requires": { - "boom": "2.10.1", - "cryptiles": "2.0.5", - "hoek": "2.16.3", - "sntp": "1.0.9" - } - }, - "he": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/he/-/he-1.1.1.tgz", - "integrity": "sha1-k0EP0hsAlzUVH4howvJx80J+I/0=", - "dev": true - }, - "hoek": { - "version": "2.16.3", - "resolved": "https://registry.npmjs.org/hoek/-/hoek-2.16.3.tgz", - "integrity": "sha1-ILt0A9POo5jpHcRxCo/xuCdKJe0=", - "dev": true - }, - "homedir-polyfill": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/homedir-polyfill/-/homedir-polyfill-1.0.1.tgz", - "integrity": "sha1-TCu8inWJmP7r9e1oWA921GdotLw=", - "dev": true, - "requires": { - "parse-passwd": "1.0.0" - } - }, - "htmlparser2": { - "version": "3.9.2", - "resolved": "https://registry.npmjs.org/htmlparser2/-/htmlparser2-3.9.2.tgz", - "integrity": "sha1-G9+HrMoPP55T+k/M6w9LTLsAszg=", - "dev": true, - "requires": { - "domelementtype": "1.3.0", - "domhandler": "2.4.1", - "domutils": "1.5.1", - "entities": "1.1.1", - "inherits": "2.0.3", - "readable-stream": "2.3.3" - }, - "dependencies": { - "isarray": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/isarray/-/isarray-1.0.0.tgz", - "integrity": "sha1-u5NdSFgsuhaMBoNJV6VKPgcSTxE=", - "dev": true - }, - "readable-stream": { - "version": "2.3.3", - "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-2.3.3.tgz", - "integrity": "sha512-m+qzzcn7KUxEmd1gMbchF+Y2eIUbieUaxkWtptyHywrX0rE8QEYqPC07Vuy4Wm32/xE16NcdBctb8S0Xe/5IeQ==", - "dev": true, - "requires": { - "core-util-is": "1.0.2", - "inherits": "2.0.3", - "isarray": "1.0.0", - "process-nextick-args": "1.0.7", - "safe-buffer": "5.1.1", - "string_decoder": "1.0.3", - "util-deprecate": "1.0.2" - } - }, - "string_decoder": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/string_decoder/-/string_decoder-1.0.3.tgz", - "integrity": "sha512-4AH6Z5fzNNBcH+6XDMfA/BTt87skxqJlO0lAh3Dker5zThcAxG6mKz+iGu308UKoPPQ8Dcqx/4JhujzltRa+hQ==", - "dev": true, - "requires": { - "safe-buffer": "5.1.1" - } - } - } - }, - "http-proxy-agent": { - "version": "0.2.7", - "resolved": "https://registry.npmjs.org/http-proxy-agent/-/http-proxy-agent-0.2.7.tgz", - "integrity": "sha1-4X/aZfCQLZUs55IeYsf/iGJlWl4=", - "requires": { - "agent-base": "1.0.2", - "debug": "2.6.9", - "extend": "3.0.1" - } - }, - "http-signature": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/http-signature/-/http-signature-1.1.1.tgz", - "integrity": "sha1-33LiZwZs0Kxn+3at+OE0qPvPkb8=", - "dev": true, - "requires": { - "assert-plus": "0.2.0", - "jsprim": "1.4.1", - "sshpk": "1.13.1" - } - }, - "https-proxy-agent": { - "version": "0.3.6", - "resolved": "https://registry.npmjs.org/https-proxy-agent/-/https-proxy-agent-0.3.6.tgz", - "integrity": "sha1-cT+jjl01P1DrFKNC/r4pAz7RYZs=", - "requires": { - "agent-base": "1.0.2", - "debug": "2.6.9", - "extend": "3.0.1" - } - }, - "iconv-lite": { - "version": "0.4.19", - "resolved": "https://registry.npmjs.org/iconv-lite/-/iconv-lite-0.4.19.tgz", - "integrity": "sha512-oTZqweIP51xaGPI4uPa56/Pri/480R+mo7SeU+YETByQNhDG55ycFyNLIgta9vXhILrxXDmF7ZGhqZIcuN0gJQ==", - "dev": true - }, - "ignore-by-default": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/ignore-by-default/-/ignore-by-default-1.0.1.tgz", - "integrity": "sha1-SMptcvbGo68Aqa1K5odr44ieKwk=", - "dev": true - }, - "import-lazy": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/import-lazy/-/import-lazy-2.1.0.tgz", - "integrity": "sha1-BWmOPUXIjo1+nZLLBYTnfwlvPkM=", - "dev": true - }, - "imurmurhash": { - "version": "0.1.4", - "resolved": "https://registry.npmjs.org/imurmurhash/-/imurmurhash-0.1.4.tgz", - "integrity": "sha1-khi5srkoojixPcT7a21XbyMUU+o=", - "dev": true - }, - "inflight": { - "version": "1.0.6", - "resolved": "https://registry.npmjs.org/inflight/-/inflight-1.0.6.tgz", - "integrity": "sha1-Sb1jMdfQLQwJvJEKEHW6gWW1bfk=", - "requires": { - "once": "1.4.0", - "wrappy": "1.0.2" - } - }, - "inherits": { - "version": "2.0.3", - "resolved": "https://registry.npmjs.org/inherits/-/inherits-2.0.3.tgz", - "integrity": "sha1-Yzwsg+PaQqUC9SRmAiSA9CCCYd4=" - }, - "ini": { - "version": "1.3.5", - "resolved": "https://registry.npmjs.org/ini/-/ini-1.3.5.tgz", - "integrity": "sha512-RZY5huIKCMRWDUqZlEi72f/lmXKMvuszcMBduliQ3nnWbx9X/ZBQO7DijMEYS9EhHBb2qacRUMtC7svLwe0lcw==", - "dev": true - }, - "interpret": { - "version": "1.0.4", - "resolved": "https://registry.npmjs.org/interpret/-/interpret-1.0.4.tgz", - "integrity": "sha1-ggzdWIuGj/sZGoCVBtbJyPISsbA=", - "dev": true - }, - "invert-kv": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/invert-kv/-/invert-kv-1.0.0.tgz", - "integrity": "sha1-EEqOSqym09jNFXqO+L+rLXo//bY=", - "dev": true - }, - "is": { - "version": "3.2.1", - "resolved": "https://registry.npmjs.org/is/-/is-3.2.1.tgz", - "integrity": "sha1-0Kwq1V63sL7JJqUmb2xmKqqD3KU=", - "dev": true - }, - "is-absolute": { - "version": "0.2.6", - "resolved": "https://registry.npmjs.org/is-absolute/-/is-absolute-0.2.6.tgz", - "integrity": "sha1-IN5p89uULvLYe5wto28XIjWxtes=", - "dev": true, - "requires": { - "is-relative": "0.2.1", - "is-windows": "0.2.0" - } - }, - "is-binary-path": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/is-binary-path/-/is-binary-path-1.0.1.tgz", - "integrity": "sha1-dfFmQrSA8YenEcgUFh/TpKdlWJg=", - "dev": true, - "requires": { - "binary-extensions": "1.11.0" - } - }, - "is-buffer": { - "version": "1.1.6", - "resolved": "https://registry.npmjs.org/is-buffer/-/is-buffer-1.1.6.tgz", - "integrity": "sha512-NcdALwpXkTm5Zvvbk7owOUSvVvBKDgKP5/ewfXEznmQFfs4ZRmanOeKBTjRVjka3QFoN6XJ+9F3USqfHqTaU5w==", - "dev": true - }, - "is-dotfile": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/is-dotfile/-/is-dotfile-1.0.3.tgz", - "integrity": "sha1-pqLzL/0t+wT1yiXs0Pa4PPeYoeE=", - "dev": true - }, - "is-equal-shallow": { - "version": "0.1.3", - "resolved": "https://registry.npmjs.org/is-equal-shallow/-/is-equal-shallow-0.1.3.tgz", - "integrity": "sha1-IjgJj8Ih3gvPpdnqxMRdY4qhxTQ=", - "dev": true, - "requires": { - "is-primitive": "2.0.0" - } - }, - "is-extendable": { - "version": "0.1.1", - "resolved": "https://registry.npmjs.org/is-extendable/-/is-extendable-0.1.1.tgz", - "integrity": "sha1-YrEQ4omkcUGOPsNqYX1HLjAd/Ik=", - "dev": true - }, - "is-extglob": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/is-extglob/-/is-extglob-1.0.0.tgz", - "integrity": "sha1-rEaBd8SUNAWgkvyPKXYMb/xiBsA=", - "dev": true - }, - "is-fullwidth-code-point": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/is-fullwidth-code-point/-/is-fullwidth-code-point-2.0.0.tgz", - "integrity": "sha1-o7MKXE8ZkYMWeqq5O+764937ZU8=", - "dev": true - }, - "is-glob": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/is-glob/-/is-glob-2.0.1.tgz", - "integrity": "sha1-0Jb5JqPe1WAPP9/ZEZjLCIjC2GM=", - "dev": true, - "requires": { - "is-extglob": "1.0.0" - } - }, - "is-installed-globally": { - "version": "0.1.0", - "resolved": "https://registry.npmjs.org/is-installed-globally/-/is-installed-globally-0.1.0.tgz", - "integrity": "sha1-Df2Y9akRFxbdU13aZJL2e/PSWoA=", - "dev": true, - "requires": { - "global-dirs": "0.1.1", - "is-path-inside": "1.0.0" - } - }, - "is-my-json-valid": { - "version": "2.16.1", - "resolved": "https://registry.npmjs.org/is-my-json-valid/-/is-my-json-valid-2.16.1.tgz", - "integrity": "sha512-ochPsqWS1WXj8ZnMIV0vnNXooaMhp7cyL4FMSIPKTtnV0Ha/T19G2b9kkhcNsabV9bxYkze7/aLZJb/bYuFduQ==", - "dev": true, - "requires": { - "generate-function": "2.0.0", - "generate-object-property": "1.2.0", - "jsonpointer": "4.0.1", - "xtend": "4.0.1" - } - }, - "is-npm": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/is-npm/-/is-npm-1.0.0.tgz", - "integrity": "sha1-8vtjpl5JBbQGyGBydloaTceTufQ=", - "dev": true - }, - "is-number": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/is-number/-/is-number-2.1.0.tgz", - "integrity": "sha1-Afy7s5NGOlSPL0ZszhbezknbkI8=", - "dev": true, - "requires": { - "kind-of": "3.2.2" - } - }, - "is-obj": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/is-obj/-/is-obj-1.0.1.tgz", - "integrity": "sha1-PkcprB9f3gJc19g6iW2rn09n2w8=", - "dev": true - }, - "is-path-cwd": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/is-path-cwd/-/is-path-cwd-1.0.0.tgz", - "integrity": "sha1-0iXsIxMuie3Tj9p2dHLmLmXxEG0=", - "dev": true - }, - "is-path-in-cwd": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/is-path-in-cwd/-/is-path-in-cwd-1.0.0.tgz", - "integrity": "sha1-ZHdYK4IU1gI0YJRWcAO+ip6sBNw=", - "dev": true, - "requires": { - "is-path-inside": "1.0.0" - } - }, - "is-path-inside": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/is-path-inside/-/is-path-inside-1.0.0.tgz", - "integrity": "sha1-/AbloWg/vaE95mev9xe7wQpI838=", - "dev": true, - "requires": { - "path-is-inside": "1.0.2" - } - }, - "is-plain-object": { - "version": "2.0.4", - "resolved": "https://registry.npmjs.org/is-plain-object/-/is-plain-object-2.0.4.tgz", - "integrity": "sha512-h5PpgXkWitc38BBMYawTYMWJHFZJVnBquFE57xFpjB8pJFiF6gZ+bU+WyI/yqXiFR5mdLsgYNaPe8uao6Uv9Og==", - "dev": true, - "requires": { - "isobject": "3.0.1" - }, - "dependencies": { - "isobject": { - "version": "3.0.1", - "resolved": "https://registry.npmjs.org/isobject/-/isobject-3.0.1.tgz", - "integrity": "sha1-TkMekrEalzFjaqH5yNHMvP2reN8=", - "dev": true - } - } - }, - "is-posix-bracket": { - "version": "0.1.1", - "resolved": "https://registry.npmjs.org/is-posix-bracket/-/is-posix-bracket-0.1.1.tgz", - "integrity": "sha1-MzTceXdDaOkvAW5vvAqI9c1ua8Q=", - "dev": true - }, - "is-primitive": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/is-primitive/-/is-primitive-2.0.0.tgz", - "integrity": "sha1-IHurkWOEmcB7Kt8kCkGochADRXU=", - "dev": true - }, - "is-promise": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/is-promise/-/is-promise-2.1.0.tgz", - "integrity": "sha1-eaKp7OfwlugPNtKy87wWwf9L8/o=", - "dev": true - }, - "is-property": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/is-property/-/is-property-1.0.2.tgz", - "integrity": "sha1-V/4cTkhHTt1lsJkR8msc1Ald2oQ=", - "dev": true - }, - "is-redirect": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/is-redirect/-/is-redirect-1.0.0.tgz", - "integrity": "sha1-HQPd7VO9jbDzDCbk+V02/HyH3CQ=", - "dev": true - }, - "is-relative": { - "version": "0.2.1", - "resolved": "https://registry.npmjs.org/is-relative/-/is-relative-0.2.1.tgz", - "integrity": "sha1-0n9MfVFtF1+2ENuEu+7yPDvJeqU=", - "dev": true, - "requires": { - "is-unc-path": "0.1.2" - } - }, - "is-retry-allowed": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/is-retry-allowed/-/is-retry-allowed-1.1.0.tgz", - "integrity": "sha1-EaBgVotnM5REAz0BJaYaINVk+zQ=", - "dev": true - }, - "is-stream": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/is-stream/-/is-stream-1.1.0.tgz", - "integrity": "sha1-EtSj3U5o4Lec6428hBc66A2RykQ=", - "dev": true - }, - "is-typedarray": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/is-typedarray/-/is-typedarray-1.0.0.tgz", - "integrity": "sha1-5HnICFjfDBsR3dppQPlgEfzaSpo=", - "dev": true - }, - "is-unc-path": { - "version": "0.1.2", - "resolved": "https://registry.npmjs.org/is-unc-path/-/is-unc-path-0.1.2.tgz", - "integrity": "sha1-arBTpyVzwQJQ/0FqOBTDUXivObk=", - "dev": true, - "requires": { - "unc-path-regex": "0.1.2" - } - }, - "is-utf8": { - "version": "0.2.1", - "resolved": "https://registry.npmjs.org/is-utf8/-/is-utf8-0.2.1.tgz", - "integrity": "sha1-Sw2hRCEE0bM2NA6AeX6GXPOffXI=", - "dev": true - }, - "is-valid-glob": { - "version": "0.3.0", - "resolved": "https://registry.npmjs.org/is-valid-glob/-/is-valid-glob-0.3.0.tgz", - "integrity": "sha1-1LVcafUYhvm2XHDWwmItN+KfSP4=", - "dev": true - }, - "is-windows": { - "version": "0.2.0", - "resolved": "https://registry.npmjs.org/is-windows/-/is-windows-0.2.0.tgz", - "integrity": "sha1-3hqm1j6indJIc3tp8f+LgALSEIw=", - "dev": true - }, - "isarray": { - "version": "0.0.1", - "resolved": "https://registry.npmjs.org/isarray/-/isarray-0.0.1.tgz", - "integrity": "sha1-ihis/Kmo9Bd+Cav8YDiTmwXR7t8=", - "dev": true - }, - "isexe": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/isexe/-/isexe-2.0.0.tgz", - "integrity": "sha1-6PvzdNxVb/iUehDcsFctYz8s+hA=", - "dev": true - }, - "isobject": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/isobject/-/isobject-2.1.0.tgz", - "integrity": "sha1-8GVWEJaj8dou9GJy+BXIQNh+DIk=", - "dev": true, - "requires": { - "isarray": "1.0.0" - }, - "dependencies": { - "isarray": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/isarray/-/isarray-1.0.0.tgz", - "integrity": "sha1-u5NdSFgsuhaMBoNJV6VKPgcSTxE=", - "dev": true - } - } - }, - "isstream": { - "version": "0.1.2", - "resolved": "https://registry.npmjs.org/isstream/-/isstream-0.1.2.tgz", - "integrity": "sha1-R+Y/evVa+m+S4VAOaQ64uFKcCZo=", - "dev": true - }, - "js-tokens": { - "version": "3.0.2", - "resolved": "https://registry.npmjs.org/js-tokens/-/js-tokens-3.0.2.tgz", - "integrity": "sha1-mGbfOVECEw449/mWvOtlRDIJwls=", - "dev": true - }, - "jsbn": { - "version": "0.1.1", - "resolved": "https://registry.npmjs.org/jsbn/-/jsbn-0.1.1.tgz", - "integrity": "sha1-peZUwuWi3rXyAdls77yoDA7y9RM=", - "dev": true, - "optional": true - }, - "json-schema": { - "version": "0.2.3", - "resolved": "https://registry.npmjs.org/json-schema/-/json-schema-0.2.3.tgz", - "integrity": "sha1-tIDIkuWaLwWVTOcnvT8qTogvnhM=", - "dev": true - }, - "json-schema-traverse": { - "version": "0.3.1", - "resolved": "https://registry.npmjs.org/json-schema-traverse/-/json-schema-traverse-0.3.1.tgz", - "integrity": "sha1-NJptRMU6Ud6JtAgFxdXlm0F9M0A=", - "dev": true - }, - "json-stable-stringify": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/json-stable-stringify/-/json-stable-stringify-1.0.1.tgz", - "integrity": "sha1-mnWdOcXy/1A/1TAGRu1EX4jE+a8=", - "dev": true, - "requires": { - "jsonify": "0.0.0" - } - }, - "json-stringify-safe": { - "version": "5.0.1", - "resolved": "https://registry.npmjs.org/json-stringify-safe/-/json-stringify-safe-5.0.1.tgz", - "integrity": "sha1-Epai1Y/UXxmg9s4B1lcB4sc1tus=", - "dev": true - }, - "jsonify": { - "version": "0.0.0", - "resolved": "https://registry.npmjs.org/jsonify/-/jsonify-0.0.0.tgz", - "integrity": "sha1-LHS27kHZPKUbe1qu6PUDYx0lKnM=", - "dev": true - }, - "jsonpointer": { - "version": "4.0.1", - "resolved": "https://registry.npmjs.org/jsonpointer/-/jsonpointer-4.0.1.tgz", - "integrity": "sha1-T9kss04OnbPInIYi7PUfm5eMbLk=", - "dev": true - }, - "jsprim": { - "version": "1.4.1", - "resolved": "https://registry.npmjs.org/jsprim/-/jsprim-1.4.1.tgz", - "integrity": "sha1-MT5mvB5cwG5Di8G3SZwuXFastqI=", - "dev": true, - "requires": { - "assert-plus": "1.0.0", - "extsprintf": "1.3.0", - "json-schema": "0.2.3", - "verror": "1.10.0" - }, - "dependencies": { - "assert-plus": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/assert-plus/-/assert-plus-1.0.0.tgz", - "integrity": "sha1-8S4PPF13sLHN2RRpQuTpbB5N1SU=", - "dev": true - } - } - }, - "kind-of": { - "version": "3.2.2", - "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-3.2.2.tgz", - "integrity": "sha1-MeohpzS6ubuw8yRm2JOupR5KPGQ=", - "dev": true, - "requires": { - "is-buffer": "1.1.6" - } - }, - "latest-version": { - "version": "3.1.0", - "resolved": "https://registry.npmjs.org/latest-version/-/latest-version-3.1.0.tgz", - "integrity": "sha1-ogU4P+oyKzO1rjsYq+4NwvNW7hU=", - "dev": true, - "requires": { - "package-json": "4.0.1" - } - }, - "lazy-cache": { - "version": "1.0.4", - "resolved": "https://registry.npmjs.org/lazy-cache/-/lazy-cache-1.0.4.tgz", - "integrity": "sha1-odePw6UEdMuAhF07O24dpJpEbo4=", - "dev": true - }, - "lazystream": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/lazystream/-/lazystream-1.0.0.tgz", - "integrity": "sha1-9plf4PggOS9hOWvolGJAe7dxaOQ=", - "dev": true, - "requires": { - "readable-stream": "2.3.3" - }, - "dependencies": { - "isarray": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/isarray/-/isarray-1.0.0.tgz", - "integrity": "sha1-u5NdSFgsuhaMBoNJV6VKPgcSTxE=", - "dev": true - }, - "readable-stream": { - "version": "2.3.3", - "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-2.3.3.tgz", - "integrity": "sha512-m+qzzcn7KUxEmd1gMbchF+Y2eIUbieUaxkWtptyHywrX0rE8QEYqPC07Vuy4Wm32/xE16NcdBctb8S0Xe/5IeQ==", - "dev": true, - "requires": { - "core-util-is": "1.0.2", - "inherits": "2.0.3", - "isarray": "1.0.0", - "process-nextick-args": "1.0.7", - "safe-buffer": "5.1.1", - "string_decoder": "1.0.3", - "util-deprecate": "1.0.2" - } - }, - "string_decoder": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/string_decoder/-/string_decoder-1.0.3.tgz", - "integrity": "sha512-4AH6Z5fzNNBcH+6XDMfA/BTt87skxqJlO0lAh3Dker5zThcAxG6mKz+iGu308UKoPPQ8Dcqx/4JhujzltRa+hQ==", - "dev": true, - "requires": { - "safe-buffer": "5.1.1" - } - } - } - }, - "lcid": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/lcid/-/lcid-1.0.0.tgz", - "integrity": "sha1-MIrMr6C8SDo4Z7S28rlQYlHRuDU=", - "dev": true, - "requires": { - "invert-kv": "1.0.0" - } - }, - "liftoff": { - "version": "2.3.0", - "resolved": "https://registry.npmjs.org/liftoff/-/liftoff-2.3.0.tgz", - "integrity": "sha1-qY8v9nGD2Lp8+soQVIvX/wVQs4U=", - "dev": true, - "requires": { - "extend": "3.0.1", - "findup-sync": "0.4.3", - "fined": "1.1.0", - "flagged-respawn": "0.3.2", - "lodash.isplainobject": "4.0.6", - "lodash.isstring": "4.0.1", - "lodash.mapvalues": "4.6.0", - "rechoir": "0.6.2", - "resolve": "1.5.0" - } - }, - "linkify-it": { - "version": "2.0.3", - "resolved": "https://registry.npmjs.org/linkify-it/-/linkify-it-2.0.3.tgz", - "integrity": "sha1-2UpGSPmxwXnWT6lykSaL22zpQ08=", - "dev": true, - "requires": { - "uc.micro": "1.0.3" - } - }, - "lodash": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/lodash/-/lodash-1.0.2.tgz", - "integrity": "sha1-j1dWDIO1n8JwvT1WG2kAQ0MOJVE=", - "dev": true - }, - "lodash._baseassign": { - "version": "3.2.0", - "resolved": "https://registry.npmjs.org/lodash._baseassign/-/lodash._baseassign-3.2.0.tgz", - "integrity": "sha1-jDigmVAPIVrQnlnxci/QxSv+Ck4=", - "dev": true, - "requires": { - "lodash._basecopy": "3.0.1", - "lodash.keys": "3.1.2" - } - }, - "lodash._basecopy": { - "version": "3.0.1", - "resolved": "https://registry.npmjs.org/lodash._basecopy/-/lodash._basecopy-3.0.1.tgz", - "integrity": "sha1-jaDmqHbPNEwK2KVIghEd08XHyjY=", - "dev": true - }, - "lodash._basetostring": { - "version": "3.0.1", - "resolved": "https://registry.npmjs.org/lodash._basetostring/-/lodash._basetostring-3.0.1.tgz", - "integrity": "sha1-0YYdh3+CSlL2aYMtyvPuFVZqB9U=", - "dev": true - }, - "lodash._basevalues": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/lodash._basevalues/-/lodash._basevalues-3.0.0.tgz", - "integrity": "sha1-W3dXYoAr3j0yl1A+JjAIIP32Ybc=", - "dev": true - }, - "lodash._bindcallback": { - "version": "3.0.1", - "resolved": "https://registry.npmjs.org/lodash._bindcallback/-/lodash._bindcallback-3.0.1.tgz", - "integrity": "sha1-5THCdkTPi1epnhftlbNcdIeJOS4=", - "dev": true - }, - "lodash._createassigner": { - "version": "3.1.1", - "resolved": "https://registry.npmjs.org/lodash._createassigner/-/lodash._createassigner-3.1.1.tgz", - "integrity": "sha1-g4pbri/aymOsIt7o4Z+k5taXCxE=", - "dev": true, - "requires": { - "lodash._bindcallback": "3.0.1", - "lodash._isiterateecall": "3.0.9", - "lodash.restparam": "3.6.1" - } - }, - "lodash._getnative": { - "version": "3.9.1", - "resolved": "https://registry.npmjs.org/lodash._getnative/-/lodash._getnative-3.9.1.tgz", - "integrity": "sha1-VwvH3t5G1hzc3mh9ZdPuy6o6r/U=", - "dev": true - }, - "lodash._isiterateecall": { - "version": "3.0.9", - "resolved": "https://registry.npmjs.org/lodash._isiterateecall/-/lodash._isiterateecall-3.0.9.tgz", - "integrity": "sha1-UgOte6Ql+uhCRg5pbbnPPmqsBXw=", - "dev": true - }, - "lodash._reescape": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/lodash._reescape/-/lodash._reescape-3.0.0.tgz", - "integrity": "sha1-Kx1vXf4HyKNVdT5fJ/rH8c3hYWo=", - "dev": true - }, - "lodash._reevaluate": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/lodash._reevaluate/-/lodash._reevaluate-3.0.0.tgz", - "integrity": "sha1-WLx0xAZklTrgsSTYBpltrKQx4u0=", - "dev": true - }, - "lodash._reinterpolate": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/lodash._reinterpolate/-/lodash._reinterpolate-3.0.0.tgz", - "integrity": "sha1-DM8tiRZq8Ds2Y8eWU4t1rG4RTZ0=", - "dev": true - }, - "lodash._root": { - "version": "3.0.1", - "resolved": "https://registry.npmjs.org/lodash._root/-/lodash._root-3.0.1.tgz", - "integrity": "sha1-+6HEUkwZ7ppfgTa0YJ8BfPTe1pI=", - "dev": true - }, - "lodash.assign": { - "version": "3.2.0", - "resolved": "https://registry.npmjs.org/lodash.assign/-/lodash.assign-3.2.0.tgz", - "integrity": "sha1-POnwI0tLIiPilrj6CsH+6OvKZPo=", - "dev": true, - "requires": { - "lodash._baseassign": "3.2.0", - "lodash._createassigner": "3.1.1", - "lodash.keys": "3.1.2" - } - }, - "lodash.defaults": { - "version": "3.1.2", - "resolved": "https://registry.npmjs.org/lodash.defaults/-/lodash.defaults-3.1.2.tgz", - "integrity": "sha1-xzCLGNv4vJNy1wGnNJPGEZK9Liw=", - "dev": true, - "requires": { - "lodash.assign": "3.2.0", - "lodash.restparam": "3.6.1" - } - }, - "lodash.escape": { - "version": "3.2.0", - "resolved": "https://registry.npmjs.org/lodash.escape/-/lodash.escape-3.2.0.tgz", - "integrity": "sha1-mV7g3BjBtIzJLv+ucaEKq1tIdpg=", - "dev": true, - "requires": { - "lodash._root": "3.0.1" - } - }, - "lodash.isarguments": { - "version": "3.1.0", - "resolved": "https://registry.npmjs.org/lodash.isarguments/-/lodash.isarguments-3.1.0.tgz", - "integrity": "sha1-L1c9hcaiQon/AGY7SRwdM4/zRYo=", - "dev": true - }, - "lodash.isarray": { - "version": "3.0.4", - "resolved": "https://registry.npmjs.org/lodash.isarray/-/lodash.isarray-3.0.4.tgz", - "integrity": "sha1-eeTriMNqgSKvhvhEqpvNhRtfu1U=", - "dev": true - }, - "lodash.isequal": { - "version": "4.5.0", - "resolved": "https://registry.npmjs.org/lodash.isequal/-/lodash.isequal-4.5.0.tgz", - "integrity": "sha1-QVxEePK8wwEgwizhDtMib30+GOA=", - "dev": true - }, - "lodash.isplainobject": { - "version": "4.0.6", - "resolved": "https://registry.npmjs.org/lodash.isplainobject/-/lodash.isplainobject-4.0.6.tgz", - "integrity": "sha1-fFJqUtibRcRcxpC4gWO+BJf1UMs=", - "dev": true - }, - "lodash.isstring": { - "version": "4.0.1", - "resolved": "https://registry.npmjs.org/lodash.isstring/-/lodash.isstring-4.0.1.tgz", - "integrity": "sha1-1SfftUVuynzJu5XV2ur4i6VKVFE=", - "dev": true - }, - "lodash.keys": { - "version": "3.1.2", - "resolved": "https://registry.npmjs.org/lodash.keys/-/lodash.keys-3.1.2.tgz", - "integrity": "sha1-TbwEcrFWvlCgsoaFXRvQsMZWCYo=", - "dev": true, - "requires": { - "lodash._getnative": "3.9.1", - "lodash.isarguments": "3.1.0", - "lodash.isarray": "3.0.4" - } - }, - "lodash.mapvalues": { - "version": "4.6.0", - "resolved": "https://registry.npmjs.org/lodash.mapvalues/-/lodash.mapvalues-4.6.0.tgz", - "integrity": "sha1-G6+lAF3p3W9PJmaMMMo3IwzJaJw=", - "dev": true - }, - "lodash.restparam": { - "version": "3.6.1", - "resolved": "https://registry.npmjs.org/lodash.restparam/-/lodash.restparam-3.6.1.tgz", - "integrity": "sha1-k2pOMJ7zMKdkXtQUWYbIWuWyCAU=", - "dev": true - }, - "lodash.template": { - "version": "3.6.2", - "resolved": "https://registry.npmjs.org/lodash.template/-/lodash.template-3.6.2.tgz", - "integrity": "sha1-+M3sxhaaJVvpCYrosMU9N4kx0U8=", - "dev": true, - "requires": { - "lodash._basecopy": "3.0.1", - "lodash._basetostring": "3.0.1", - "lodash._basevalues": "3.0.0", - "lodash._isiterateecall": "3.0.9", - "lodash._reinterpolate": "3.0.0", - "lodash.escape": "3.2.0", - "lodash.keys": "3.1.2", - "lodash.restparam": "3.6.1", - "lodash.templatesettings": "3.1.1" - } - }, - "lodash.templatesettings": { - "version": "3.1.1", - "resolved": "https://registry.npmjs.org/lodash.templatesettings/-/lodash.templatesettings-3.1.1.tgz", - "integrity": "sha1-+zB4RHU7Zrnxr6VOJix0UwfbqOU=", - "dev": true, - "requires": { - "lodash._reinterpolate": "3.0.0", - "lodash.escape": "3.2.0" - } - }, - "longest": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/longest/-/longest-1.0.1.tgz", - "integrity": "sha1-MKCy2jj3N3DoKUoNIuZiXtd9AJc=", - "dev": true - }, - "lowercase-keys": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/lowercase-keys/-/lowercase-keys-1.0.0.tgz", - "integrity": "sha1-TjNms55/VFfjXxMkvfb4jQv8cwY=", - "dev": true - }, - "lru-cache": { - "version": "4.1.1", - "resolved": "https://registry.npmjs.org/lru-cache/-/lru-cache-4.1.1.tgz", - "integrity": "sha512-q4spe4KTfsAS1SUHLO0wz8Qiyf1+vMIAgpRYioFYDMNqKfHQbg+AVDH3i4fvpl71/P1L0dBl+fQi+P37UYf0ew==", - "dev": true, - "requires": { - "pseudomap": "1.0.2", - "yallist": "2.1.2" - } - }, - "lru-queue": { - "version": "0.1.0", - "resolved": "https://registry.npmjs.org/lru-queue/-/lru-queue-0.1.0.tgz", - "integrity": "sha1-Jzi9nw089PhEkMVzbEhpmsYyzaM=", - "dev": true, - "requires": { - "es5-ext": "0.10.35" - } - }, - "make-dir": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/make-dir/-/make-dir-1.1.0.tgz", - "integrity": "sha512-0Pkui4wLJ7rxvmfUvs87skoEaxmu0hCUApF8nonzpl7q//FWp9zu8W61Scz4sd/kUiqDxvUhtoam2efDyiBzcA==", - "dev": true, - "requires": { - "pify": "3.0.0" - } - }, - "make-error": { - "version": "1.3.0", - "resolved": "https://registry.npmjs.org/make-error/-/make-error-1.3.0.tgz", - "integrity": "sha1-Uq06M5zPEM5itAQLcI/nByRLi5Y=", - "dev": true - }, - "make-error-cause": { - "version": "1.2.2", - "resolved": "https://registry.npmjs.org/make-error-cause/-/make-error-cause-1.2.2.tgz", - "integrity": "sha1-3wOI/NCzeBbf8KX7gQiTl3fcvJ0=", - "dev": true, - "requires": { - "make-error": "1.3.0" - } - }, - "map-cache": { - "version": "0.2.2", - "resolved": "https://registry.npmjs.org/map-cache/-/map-cache-0.2.2.tgz", - "integrity": "sha1-wyq9C9ZSXZsFFkW7TyasXcmKDb8=", - "dev": true - }, - "map-stream": { - "version": "0.1.0", - "resolved": "https://registry.npmjs.org/map-stream/-/map-stream-0.1.0.tgz", - "integrity": "sha1-5WqpTEyAVaFkBKBnS3jyFffI4ZQ=", - "dev": true - }, - "markdown-it": { - "version": "8.4.0", - "resolved": "https://registry.npmjs.org/markdown-it/-/markdown-it-8.4.0.tgz", - "integrity": "sha512-tNuOCCfunY5v5uhcO2AUMArvKAyKMygX8tfup/JrgnsDqcCATQsAExBq7o5Ml9iMmO82bk6jYNLj6khcrl0JGA==", - "dev": true, - "requires": { - "argparse": "1.0.9", - "entities": "1.1.1", - "linkify-it": "2.0.3", - "mdurl": "1.0.1", - "uc.micro": "1.0.3" - } - }, - "mdurl": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/mdurl/-/mdurl-1.0.1.tgz", - "integrity": "sha1-/oWy7HWlkDfyrf7BAP1sYBdhFS4=", - "dev": true - }, - "memoizee": { - "version": "0.4.11", - "resolved": "https://registry.npmjs.org/memoizee/-/memoizee-0.4.11.tgz", - "integrity": "sha1-vemBdmPJ5A/bKk6hw2cpYIeujI8=", - "dev": true, - "requires": { - "d": "1.0.0", - "es5-ext": "0.10.35", - "es6-weak-map": "2.0.2", - "event-emitter": "0.3.5", - "is-promise": "2.1.0", - "lru-queue": "0.1.0", - "next-tick": "1.0.0", - "timers-ext": "0.1.2" - } - }, - "merge-stream": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/merge-stream/-/merge-stream-1.0.1.tgz", - "integrity": "sha1-QEEgLVCKNCugAXQAjfDCUbjBNeE=", - "dev": true, - "requires": { - "readable-stream": "2.3.3" - }, - "dependencies": { - "isarray": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/isarray/-/isarray-1.0.0.tgz", - "integrity": "sha1-u5NdSFgsuhaMBoNJV6VKPgcSTxE=", - "dev": true - }, - "readable-stream": { - "version": "2.3.3", - "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-2.3.3.tgz", - "integrity": "sha512-m+qzzcn7KUxEmd1gMbchF+Y2eIUbieUaxkWtptyHywrX0rE8QEYqPC07Vuy4Wm32/xE16NcdBctb8S0Xe/5IeQ==", - "dev": true, - "requires": { - "core-util-is": "1.0.2", - "inherits": "2.0.3", - "isarray": "1.0.0", - "process-nextick-args": "1.0.7", - "safe-buffer": "5.1.1", - "string_decoder": "1.0.3", - "util-deprecate": "1.0.2" - } - }, - "string_decoder": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/string_decoder/-/string_decoder-1.0.3.tgz", - "integrity": "sha512-4AH6Z5fzNNBcH+6XDMfA/BTt87skxqJlO0lAh3Dker5zThcAxG6mKz+iGu308UKoPPQ8Dcqx/4JhujzltRa+hQ==", - "dev": true, - "requires": { - "safe-buffer": "5.1.1" - } - } - } - }, - "micromatch": { - "version": "2.3.11", - "resolved": "https://registry.npmjs.org/micromatch/-/micromatch-2.3.11.tgz", - "integrity": "sha1-hmd8l9FyCzY0MdBNDRUpO9OMFWU=", - "dev": true, - "requires": { - "arr-diff": "2.0.0", - "array-unique": "0.2.1", - "braces": "1.8.5", - "expand-brackets": "0.1.5", - "extglob": "0.3.2", - "filename-regex": "2.0.1", - "is-extglob": "1.0.0", - "is-glob": "2.0.1", - "kind-of": "3.2.2", - "normalize-path": "2.1.1", - "object.omit": "2.0.1", - "parse-glob": "3.0.4", - "regex-cache": "0.4.4" - } - }, - "mime": { - "version": "1.5.0", - "resolved": "https://registry.npmjs.org/mime/-/mime-1.5.0.tgz", - "integrity": "sha512-v/jMDoK/qKptnTuC3YUNbIj8uUYvTCIHzVu9BHldKSWja48wusAtfjlcBlqnFrqClu3yf69ScDxBPrIyFnF51g==", - "dev": true - }, - "mime-db": { - "version": "1.30.0", - "resolved": "https://registry.npmjs.org/mime-db/-/mime-db-1.30.0.tgz", - "integrity": "sha1-dMZD2i3Z1qRTmZY0ZbJtXKfXHwE=", - "dev": true - }, - "mime-types": { - "version": "2.1.17", - "resolved": "https://registry.npmjs.org/mime-types/-/mime-types-2.1.17.tgz", - "integrity": "sha1-Cdejk/A+mVp5+K+Fe3Cp4KsWVXo=", - "dev": true, - "requires": { - "mime-db": "1.30.0" - } - }, - "minimatch": { - "version": "3.0.4", - "resolved": "https://registry.npmjs.org/minimatch/-/minimatch-3.0.4.tgz", - "integrity": "sha512-yJHVQEhyqPLUTgt9B83PXu6W3rx4MvvHvSUvToogpwoGDOUQ+yDrR0HRot+yOCdCO7u4hX3pWft6kWBBcqh0UA==", - "requires": { - "brace-expansion": "1.1.8" - } - }, - "minimist": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/minimist/-/minimist-1.2.0.tgz", - "integrity": "sha1-o1AIsg9BOD7sH7kU9M1d95omQoQ=", - "dev": true - }, - "mkdirp": { - "version": "0.5.1", - "resolved": "https://registry.npmjs.org/mkdirp/-/mkdirp-0.5.1.tgz", - "integrity": "sha1-MAV0OOrGz3+MR2fzhkjWaX11yQM=", - "dev": true, - "requires": { - "minimist": "0.0.8" - }, - "dependencies": { - "minimist": { - "version": "0.0.8", - "resolved": "https://registry.npmjs.org/minimist/-/minimist-0.0.8.tgz", - "integrity": "sha1-hX/Kv8M5fSYluCKCYuhqp6ARsF0=", - "dev": true - } - } - }, - "mocha": { - "version": "4.0.1", - "resolved": "https://registry.npmjs.org/mocha/-/mocha-4.0.1.tgz", - "integrity": "sha512-evDmhkoA+cBNiQQQdSKZa2b9+W2mpLoj50367lhy+Klnx9OV8XlCIhigUnn1gaTFLQCa0kdNhEGDr0hCXOQFDw==", - "dev": true, - "requires": { - "browser-stdout": "1.3.0", - "commander": "2.11.0", - "debug": "3.1.0", - "diff": "3.3.1", - "escape-string-regexp": "1.0.5", - "glob": "7.1.2", - "growl": "1.10.3", - "he": "1.1.1", - "mkdirp": "0.5.1", - "supports-color": "4.4.0" - }, - "dependencies": { - "debug": { - "version": "3.1.0", - "resolved": "https://registry.npmjs.org/debug/-/debug-3.1.0.tgz", - "integrity": "sha512-OX8XqP7/1a9cqkxYw2yXss15f26NKWBpDXQd0/uK/KPqdQhxbPa994hnzjcE2VqQpDslf55723cKPUOGSmMY3g==", - "dev": true, - "requires": { - "ms": "2.0.0" - } - }, - "supports-color": { - "version": "4.4.0", - "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-4.4.0.tgz", - "integrity": "sha512-rKC3+DyXWgK0ZLKwmRsrkyHVZAjNkfzeehuFWdGGcqGDTZFH73+RH6S/RDAAxl9GusSjZSUWYLmT9N5pzXFOXQ==", - "dev": true, - "requires": { - "has-flag": "2.0.0" - } - } - } - }, - "ms": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/ms/-/ms-2.0.0.tgz", - "integrity": "sha1-VgiurfwAvmwpAd9fmGF4jeDVl8g=" - }, - "multimatch": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/multimatch/-/multimatch-2.1.0.tgz", - "integrity": "sha1-nHkGoi+0wCkZ4vX3UWG0zb1LKis=", - "dev": true, - "requires": { - "array-differ": "1.0.0", - "array-union": "1.0.2", - "arrify": "1.0.1", - "minimatch": "3.0.4" - } - }, - "multipipe": { - "version": "0.1.2", - "resolved": "https://registry.npmjs.org/multipipe/-/multipipe-0.1.2.tgz", - "integrity": "sha1-Ko8t33Du1WTf8tV/HhoTfZ8FB4s=", - "dev": true, - "requires": { - "duplexer2": "0.0.2" - } - }, - "mute-stream": { - "version": "0.0.7", - "resolved": "https://registry.npmjs.org/mute-stream/-/mute-stream-0.0.7.tgz", - "integrity": "sha1-MHXOk7whuPq0PhvE2n6BFe0ee6s=", - "dev": true - }, - "nan": { - "version": "2.8.0", - "resolved": "https://registry.npmjs.org/nan/-/nan-2.8.0.tgz", - "integrity": "sha1-7XFfP+neArV6XmJS2QqWZ14fCFo=", - "dev": true, - "optional": true - }, - "natives": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/natives/-/natives-1.1.0.tgz", - "integrity": "sha1-6f+EFBimsux6SV6TmYT3jxY+bjE=", - "dev": true - }, - "next-tick": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/next-tick/-/next-tick-1.0.0.tgz", - "integrity": "sha1-yobR/ogoFpsBICCOPchCS524NCw=", - "dev": true - }, - "node.extend": { - "version": "1.1.6", - "resolved": "https://registry.npmjs.org/node.extend/-/node.extend-1.1.6.tgz", - "integrity": "sha1-p7iCyC1sk6SGOlUEvV3o7IYli5Y=", - "dev": true, - "requires": { - "is": "3.2.1" - } - }, - "nodemon": { - "version": "1.12.1", - "resolved": "https://registry.npmjs.org/nodemon/-/nodemon-1.12.1.tgz", - "integrity": "sha1-mWpW3EnZ8Wu/G3ik3gjxNjSzh40=", - "dev": true, - "requires": { - "chokidar": "1.7.0", - "debug": "2.6.9", - "es6-promise": "3.3.1", - "ignore-by-default": "1.0.1", - "lodash.defaults": "3.1.2", - "minimatch": "3.0.4", - "ps-tree": "1.1.0", - "touch": "3.1.0", - "undefsafe": "0.0.3", - "update-notifier": "2.3.0" - } - }, - "nopt": { - "version": "1.0.10", - "resolved": "https://registry.npmjs.org/nopt/-/nopt-1.0.10.tgz", - "integrity": "sha1-bd0hvSoxQXuScn3Vhfim83YI6+4=", - "dev": true, - "requires": { - "abbrev": "1.1.1" - } - }, - "normalize-path": { - "version": "2.1.1", - "resolved": "https://registry.npmjs.org/normalize-path/-/normalize-path-2.1.1.tgz", - "integrity": "sha1-GrKLVW4Zg2Oowab35vogE3/mrtk=", - "dev": true, - "requires": { - "remove-trailing-separator": "1.1.0" - } - }, - "npm-run-path": { - "version": "2.0.2", - "resolved": "https://registry.npmjs.org/npm-run-path/-/npm-run-path-2.0.2.tgz", - "integrity": "sha1-NakjLfo11wZ7TLLd8jV7GHFTbF8=", - "dev": true, - "requires": { - "path-key": "2.0.1" - } - }, - "nth-check": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/nth-check/-/nth-check-1.0.1.tgz", - "integrity": "sha1-mSms32KPwsQQmN6rgqxYDPFJquQ=", - "dev": true, - "requires": { - "boolbase": "1.0.0" - } - }, - "number-is-nan": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/number-is-nan/-/number-is-nan-1.0.1.tgz", - "integrity": "sha1-CXtgK1NCKlIsGvuHkDGDNpQaAR0=", - "dev": true - }, - "oauth-sign": { - "version": "0.8.2", - "resolved": "https://registry.npmjs.org/oauth-sign/-/oauth-sign-0.8.2.tgz", - "integrity": "sha1-Rqarfwrq2N6unsBWV4C31O/rnUM=", - "dev": true - }, - "object-assign": { - "version": "4.1.1", - "resolved": "https://registry.npmjs.org/object-assign/-/object-assign-4.1.1.tgz", - "integrity": "sha1-IQmtx5ZYh8/AXLvUQsrIv7s2CGM=", - "dev": true - }, - "object.defaults": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/object.defaults/-/object.defaults-1.1.0.tgz", - "integrity": "sha1-On+GgzS0B96gbaFtiNXNKeQ1/s8=", - "dev": true, - "requires": { - "array-each": "1.0.1", - "array-slice": "1.0.0", - "for-own": "1.0.0", - "isobject": "3.0.1" - }, - "dependencies": { - "for-own": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/for-own/-/for-own-1.0.0.tgz", - "integrity": "sha1-xjMy9BXO3EsE2/5wz4NklMU8tEs=", - "dev": true, - "requires": { - "for-in": "1.0.2" - } - }, - "isobject": { - "version": "3.0.1", - "resolved": "https://registry.npmjs.org/isobject/-/isobject-3.0.1.tgz", - "integrity": "sha1-TkMekrEalzFjaqH5yNHMvP2reN8=", - "dev": true - } - } - }, - "object.omit": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/object.omit/-/object.omit-2.0.1.tgz", - "integrity": "sha1-Gpx0SCnznbuFjHbKNXmuKlTr0fo=", - "dev": true, - "requires": { - "for-own": "0.1.5", - "is-extendable": "0.1.1" - } - }, - "object.pick": { - "version": "1.3.0", - "resolved": "https://registry.npmjs.org/object.pick/-/object.pick-1.3.0.tgz", - "integrity": "sha1-h6EKxMFpS9Lhy/U1kaZhQftd10c=", - "dev": true, - "requires": { - "isobject": "3.0.1" - }, - "dependencies": { - "isobject": { - "version": "3.0.1", - "resolved": "https://registry.npmjs.org/isobject/-/isobject-3.0.1.tgz", - "integrity": "sha1-TkMekrEalzFjaqH5yNHMvP2reN8=", - "dev": true - } - } - }, - "once": { - "version": "1.4.0", - "resolved": "https://registry.npmjs.org/once/-/once-1.4.0.tgz", - "integrity": "sha1-WDsap3WWHUsROsF9nFC6753Xa9E=", - "requires": { - "wrappy": "1.0.2" - } - }, - "orchestrator": { - "version": "0.3.8", - "resolved": "https://registry.npmjs.org/orchestrator/-/orchestrator-0.3.8.tgz", - "integrity": "sha1-FOfp4nZPcxX7rBhOUGx6pt+UrX4=", - "dev": true, - "requires": { - "end-of-stream": "0.1.5", - "sequencify": "0.0.7", - "stream-consume": "0.1.0" - } - }, - "ordered-read-streams": { - "version": "0.1.0", - "resolved": "https://registry.npmjs.org/ordered-read-streams/-/ordered-read-streams-0.1.0.tgz", - "integrity": "sha1-/VZamvjrRHO6abbtijQ1LLVS8SY=", - "dev": true - }, - "os-homedir": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/os-homedir/-/os-homedir-1.0.2.tgz", - "integrity": "sha1-/7xJiDNuDoM94MFox+8VISGqf7M=", - "dev": true - }, - "os-locale": { - "version": "1.4.0", - "resolved": "https://registry.npmjs.org/os-locale/-/os-locale-1.4.0.tgz", - "integrity": "sha1-IPnxeuKe00XoveWDsT0gCYA8FNk=", - "dev": true, - "requires": { - "lcid": "1.0.0" - } - }, - "os-tmpdir": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/os-tmpdir/-/os-tmpdir-1.0.2.tgz", - "integrity": "sha1-u+Z0BseaqFxc/sdm/lc0VV36EnQ=", - "dev": true - }, - "osenv": { - "version": "0.1.4", - "resolved": "https://registry.npmjs.org/osenv/-/osenv-0.1.4.tgz", - "integrity": "sha1-Qv5tWVPfBsgGS+bxdsPQWqqjRkQ=", - "dev": true, - "requires": { - "os-homedir": "1.0.2", - "os-tmpdir": "1.0.2" - } - }, - "p-finally": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/p-finally/-/p-finally-1.0.0.tgz", - "integrity": "sha1-P7z7FbiZpEEjs0ttzBi3JDNqLK4=", - "dev": true - }, - "p-map": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/p-map/-/p-map-1.2.0.tgz", - "integrity": "sha512-r6zKACMNhjPJMTl8KcFH4li//gkrXWfbD6feV8l6doRHlzljFWGJ2AP6iKaCJXyZmAUMOPtvbW7EXkbWO/pLEA==", - "dev": true - }, - "package-json": { - "version": "4.0.1", - "resolved": "https://registry.npmjs.org/package-json/-/package-json-4.0.1.tgz", - "integrity": "sha1-iGmgQBJTZhxMTKPabCEh7VVfXu0=", - "dev": true, - "requires": { - "got": "6.7.1", - "registry-auth-token": "3.3.1", - "registry-url": "3.1.0", - "semver": "5.4.1" - }, - "dependencies": { - "semver": { - "version": "5.4.1", - "resolved": "https://registry.npmjs.org/semver/-/semver-5.4.1.tgz", - "integrity": "sha512-WfG/X9+oATh81XtllIo/I8gOiY9EXRdv1cQdyykeXK17YcUW3EXUAi2To4pcH6nZtJPr7ZOpM5OMyWJZm+8Rsg==", - "dev": true - } - } - }, - "parse-filepath": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/parse-filepath/-/parse-filepath-1.0.1.tgz", - "integrity": "sha1-FZ1hVdQ5BNFsEO9piRHaHpGWm3M=", - "dev": true, - "requires": { - "is-absolute": "0.2.6", - "map-cache": "0.2.2", - "path-root": "0.1.1" - } - }, - "parse-glob": { - "version": "3.0.4", - "resolved": "https://registry.npmjs.org/parse-glob/-/parse-glob-3.0.4.tgz", - "integrity": "sha1-ssN2z7EfNVE7rdFz7wu246OIORw=", - "dev": true, - "requires": { - "glob-base": "0.3.0", - "is-dotfile": "1.0.3", - "is-extglob": "1.0.0", - "is-glob": "2.0.1" - } - }, - "parse-passwd": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/parse-passwd/-/parse-passwd-1.0.0.tgz", - "integrity": "sha1-bVuTSkVpk7I9N/QKOC1vFmao5cY=", - "dev": true - }, - "parse-semver": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/parse-semver/-/parse-semver-1.1.1.tgz", - "integrity": "sha1-mkr9bfBj3Egm+T+6SpnPIj9mbLg=", - "dev": true, - "requires": { - "semver": "5.4.1" - }, - "dependencies": { - "semver": { - "version": "5.4.1", - "resolved": "https://registry.npmjs.org/semver/-/semver-5.4.1.tgz", - "integrity": "sha512-WfG/X9+oATh81XtllIo/I8gOiY9EXRdv1cQdyykeXK17YcUW3EXUAi2To4pcH6nZtJPr7ZOpM5OMyWJZm+8Rsg==", - "dev": true - } - } - }, - "parse5": { - "version": "3.0.3", - "resolved": "https://registry.npmjs.org/parse5/-/parse5-3.0.3.tgz", - "integrity": "sha512-rgO9Zg5LLLkfJF9E6CCmXlSE4UVceloys8JrFqCcHloC3usd/kJCyPDwH2SOlzix2j3xaP9sUX3e8+kvkuleAA==", - "dev": true, - "requires": { - "@types/node": "7.0.43" - } - }, - "path-dirname": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/path-dirname/-/path-dirname-1.0.2.tgz", - "integrity": "sha1-zDPSTVJeCZpTiMAzbG4yuRYGCeA=", - "dev": true - }, - "path-is-absolute": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/path-is-absolute/-/path-is-absolute-1.0.1.tgz", - "integrity": "sha1-F0uSaHNVNP+8es5r9TpanhtcX18=" - }, - "path-is-inside": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/path-is-inside/-/path-is-inside-1.0.2.tgz", - "integrity": "sha1-NlQX3t5EQw0cEa9hAn+s8HS9/FM=", - "dev": true - }, - "path-key": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/path-key/-/path-key-2.0.1.tgz", - "integrity": "sha1-QRyttXTFoUDTpLGRDUDYDMn0C0A=", - "dev": true - }, - "path-parse": { - "version": "1.0.5", - "resolved": "https://registry.npmjs.org/path-parse/-/path-parse-1.0.5.tgz", - "integrity": "sha1-PBrfhx6pzWyUMbbqK9dKD/BVxME=", - "dev": true - }, - "path-root": { - "version": "0.1.1", - "resolved": "https://registry.npmjs.org/path-root/-/path-root-0.1.1.tgz", - "integrity": "sha1-mkpoFMrBwM1zNgqV8yCDyOpHRbc=", - "dev": true, - "requires": { - "path-root-regex": "0.1.2" - } - }, - "path-root-regex": { - "version": "0.1.2", - "resolved": "https://registry.npmjs.org/path-root-regex/-/path-root-regex-0.1.2.tgz", - "integrity": "sha1-v8zcjfWxLcUsi0PsONGNcsBLqW0=", - "dev": true - }, - "pause-stream": { - "version": "0.0.11", - "resolved": "https://registry.npmjs.org/pause-stream/-/pause-stream-0.0.11.tgz", - "integrity": "sha1-/lo0sMvOErWqaitAPuLnO2AvFEU=", - "dev": true, - "requires": { - "through": "2.3.8" - } - }, - "pend": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/pend/-/pend-1.2.0.tgz", - "integrity": "sha1-elfrVQpng/kRUzH89GY9XI4AelA=", - "dev": true - }, - "performance-now": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/performance-now/-/performance-now-2.1.0.tgz", - "integrity": "sha1-Ywn04OX6kT7BxpMHrjZLSzd8nns=", - "dev": true - }, - "pify": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/pify/-/pify-3.0.0.tgz", - "integrity": "sha1-5aSs0sEB/fPZpNB/DbxNtJ3SgXY=", - "dev": true - }, - "pinkie": { - "version": "2.0.4", - "resolved": "https://registry.npmjs.org/pinkie/-/pinkie-2.0.4.tgz", - "integrity": "sha1-clVrgM+g1IqXToDnckjoDtT3+HA=", - "dev": true - }, - "pinkie-promise": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/pinkie-promise/-/pinkie-promise-2.0.1.tgz", - "integrity": "sha1-ITXW36ejWMBprJsXh3YogihFD/o=", - "dev": true, - "requires": { - "pinkie": "2.0.4" - } - }, - "prepend-http": { - "version": "1.0.4", - "resolved": "https://registry.npmjs.org/prepend-http/-/prepend-http-1.0.4.tgz", - "integrity": "sha1-1PRWKwzjaW5BrFLQ4ALlemNdxtw=", - "dev": true - }, - "preserve": { - "version": "0.2.0", - "resolved": "https://registry.npmjs.org/preserve/-/preserve-0.2.0.tgz", - "integrity": "sha1-gV7R9uvGWSb4ZbMQwHE7yzMVzks=", - "dev": true - }, - "pretty-hrtime": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/pretty-hrtime/-/pretty-hrtime-1.0.3.tgz", - "integrity": "sha1-t+PqQkNaTJsnWdmeDyAesZWALuE=", - "dev": true - }, - "process-nextick-args": { - "version": "1.0.7", - "resolved": "https://registry.npmjs.org/process-nextick-args/-/process-nextick-args-1.0.7.tgz", - "integrity": "sha1-FQ4gt1ZZCtP5EJPyWk8q2L/zC6M=", - "dev": true - }, - "ps-tree": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/ps-tree/-/ps-tree-1.1.0.tgz", - "integrity": "sha1-tCGyQUDWID8e08dplrRCewjowBQ=", - "dev": true, - "requires": { - "event-stream": "3.3.4" - } - }, - "pseudomap": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/pseudomap/-/pseudomap-1.0.2.tgz", - "integrity": "sha1-8FKijacOYYkX7wqKw0wa5aaChrM=", - "dev": true - }, - "punycode": { - "version": "1.4.1", - "resolved": "https://registry.npmjs.org/punycode/-/punycode-1.4.1.tgz", - "integrity": "sha1-wNWmOycYgArY4esPpSachN1BhF4=", - "dev": true - }, - "q": { - "version": "1.5.1", - "resolved": "https://registry.npmjs.org/q/-/q-1.5.1.tgz", - "integrity": "sha1-fjL3W0E4EpHQRhHxvxQQmsAGUdc=", - "dev": true - }, - "qs": { - "version": "6.3.2", - "resolved": "https://registry.npmjs.org/qs/-/qs-6.3.2.tgz", - "integrity": "sha1-51vV9uJoEioqDgvaYwslUMFmUCw=", - "dev": true - }, - "querystringify": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/querystringify/-/querystringify-1.0.0.tgz", - "integrity": "sha1-YoYkIRLFtxL6ZU5SZlK/ahP/Bcs=", - "dev": true - }, - "queue": { - "version": "3.1.0", - "resolved": "https://registry.npmjs.org/queue/-/queue-3.1.0.tgz", - "integrity": "sha1-bEnQHwCeIlZ4h4nyv/rGuLmZBYU=", - "dev": true, - "requires": { - "inherits": "2.0.3" - } - }, - "randomatic": { - "version": "1.1.7", - "resolved": "https://registry.npmjs.org/randomatic/-/randomatic-1.1.7.tgz", - "integrity": "sha512-D5JUjPyJbaJDkuAazpVnSfVkLlpeO3wDlPROTMLGKG1zMFNFRgrciKo1ltz/AzNTkqE0HzDx655QOL51N06how==", - "dev": true, - "requires": { - "is-number": "3.0.0", - "kind-of": "4.0.0" - }, - "dependencies": { - "is-number": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/is-number/-/is-number-3.0.0.tgz", - "integrity": "sha1-JP1iAaR4LPUFYcgQJ2r8fRLXEZU=", - "dev": true, - "requires": { - "kind-of": "3.2.2" - }, - "dependencies": { - "kind-of": { - "version": "3.2.2", - "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-3.2.2.tgz", - "integrity": "sha1-MeohpzS6ubuw8yRm2JOupR5KPGQ=", - "dev": true, - "requires": { - "is-buffer": "1.1.6" - } - } - } - }, - "kind-of": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-4.0.0.tgz", - "integrity": "sha1-IIE989cSkosgc3hpGkUGb65y3Vc=", - "dev": true, - "requires": { - "is-buffer": "1.1.6" - } - } - } - }, - "rc": { - "version": "1.2.2", - "resolved": "https://registry.npmjs.org/rc/-/rc-1.2.2.tgz", - "integrity": "sha1-2M6ctX6NZNnHut2YdsfDTL48cHc=", - "dev": true, - "requires": { - "deep-extend": "0.4.2", - "ini": "1.3.5", - "minimist": "1.2.0", - "strip-json-comments": "2.0.1" - } - }, - "read": { - "version": "1.0.7", - "resolved": "https://registry.npmjs.org/read/-/read-1.0.7.tgz", - "integrity": "sha1-s9oZvQUkMal2cdRKQmNK33ELQMQ=", - "dev": true, - "requires": { - "mute-stream": "0.0.7" - } - }, - "readable-stream": { - "version": "1.1.14", - "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-1.1.14.tgz", - "integrity": "sha1-fPTFTvZI44EwhMY23SB54WbAgdk=", - "dev": true, - "requires": { - "core-util-is": "1.0.2", - "inherits": "2.0.3", - "isarray": "0.0.1", - "string_decoder": "0.10.31" - } - }, - "readdirp": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/readdirp/-/readdirp-2.1.0.tgz", - "integrity": "sha1-TtCtBg3zBzMAxIRANz9y0cxkLXg=", - "dev": true, - "requires": { - "graceful-fs": "4.1.11", - "minimatch": "3.0.4", - "readable-stream": "2.3.3", - "set-immediate-shim": "1.0.1" - }, - "dependencies": { - "graceful-fs": { - "version": "4.1.11", - "resolved": "https://registry.npmjs.org/graceful-fs/-/graceful-fs-4.1.11.tgz", - "integrity": "sha1-Dovf5NHduIVNZOBOp8AOKgJuVlg=", - "dev": true - }, - "isarray": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/isarray/-/isarray-1.0.0.tgz", - "integrity": "sha1-u5NdSFgsuhaMBoNJV6VKPgcSTxE=", - "dev": true - }, - "readable-stream": { - "version": "2.3.3", - "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-2.3.3.tgz", - "integrity": "sha512-m+qzzcn7KUxEmd1gMbchF+Y2eIUbieUaxkWtptyHywrX0rE8QEYqPC07Vuy4Wm32/xE16NcdBctb8S0Xe/5IeQ==", - "dev": true, - "requires": { - "core-util-is": "1.0.2", - "inherits": "2.0.3", - "isarray": "1.0.0", - "process-nextick-args": "1.0.7", - "safe-buffer": "5.1.1", - "string_decoder": "1.0.3", - "util-deprecate": "1.0.2" - } - }, - "string_decoder": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/string_decoder/-/string_decoder-1.0.3.tgz", - "integrity": "sha512-4AH6Z5fzNNBcH+6XDMfA/BTt87skxqJlO0lAh3Dker5zThcAxG6mKz+iGu308UKoPPQ8Dcqx/4JhujzltRa+hQ==", - "dev": true, - "requires": { - "safe-buffer": "5.1.1" - } - } - } - }, - "rechoir": { - "version": "0.6.2", - "resolved": "https://registry.npmjs.org/rechoir/-/rechoir-0.6.2.tgz", - "integrity": "sha1-hSBLVNuoLVdC4oyWdW70OvUOM4Q=", - "dev": true, - "requires": { - "resolve": "1.5.0" - } - }, - "regex-cache": { - "version": "0.4.4", - "resolved": "https://registry.npmjs.org/regex-cache/-/regex-cache-0.4.4.tgz", - "integrity": "sha512-nVIZwtCjkC9YgvWkpM55B5rBhBYRZhAaJbgcFYXXsHnbZ9UZI9nnVWYZpBlCqv9ho2eZryPnWrZGsOdPwVWXWQ==", - "dev": true, - "requires": { - "is-equal-shallow": "0.1.3" - } - }, - "registry-auth-token": { - "version": "3.3.1", - "resolved": "https://registry.npmjs.org/registry-auth-token/-/registry-auth-token-3.3.1.tgz", - "integrity": "sha1-+w0yie4Nmtosu1KvXf5mywcNMAY=", - "dev": true, - "requires": { - "rc": "1.2.2", - "safe-buffer": "5.1.1" - } - }, - "registry-url": { - "version": "3.1.0", - "resolved": "https://registry.npmjs.org/registry-url/-/registry-url-3.1.0.tgz", - "integrity": "sha1-PU74cPc93h138M+aOBQyRE4XSUI=", - "dev": true, - "requires": { - "rc": "1.2.2" - } - }, - "remove-trailing-separator": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/remove-trailing-separator/-/remove-trailing-separator-1.1.0.tgz", - "integrity": "sha1-wkvOKig62tW8P1jg1IJJuSN52O8=", - "dev": true - }, - "repeat-element": { - "version": "1.1.2", - "resolved": "https://registry.npmjs.org/repeat-element/-/repeat-element-1.1.2.tgz", - "integrity": "sha1-7wiaF40Ug7quTZPrmLT55OEdmQo=", - "dev": true - }, - "repeat-string": { - "version": "1.6.1", - "resolved": "https://registry.npmjs.org/repeat-string/-/repeat-string-1.6.1.tgz", - "integrity": "sha1-jcrkcOHIirwtYA//Sndihtp15jc=", - "dev": true - }, - "replace-ext": { - "version": "0.0.1", - "resolved": "https://registry.npmjs.org/replace-ext/-/replace-ext-0.0.1.tgz", - "integrity": "sha1-KbvZIHinOfC8zitO5B6DeVNSKSQ=", - "dev": true - }, - "request": { - "version": "2.83.0", - "resolved": "https://registry.npmjs.org/request/-/request-2.83.0.tgz", - "integrity": "sha512-lR3gD69osqm6EYLk9wB/G1W/laGWjzH90t1vEa2xuxHD5KUrSzp9pUSfTm+YC5Nxt2T8nMPEvKlhbQayU7bgFw==", - "dev": true, - "requires": { - "aws-sign2": "0.7.0", - "aws4": "1.6.0", - "caseless": "0.12.0", - "combined-stream": "1.0.5", - "extend": "3.0.1", - "forever-agent": "0.6.1", - "form-data": "2.3.1", - "har-validator": "5.0.3", - "hawk": "6.0.2", - "http-signature": "1.2.0", - "is-typedarray": "1.0.0", - "isstream": "0.1.2", - "json-stringify-safe": "5.0.1", - "mime-types": "2.1.17", - "oauth-sign": "0.8.2", - "performance-now": "2.1.0", - "qs": "6.5.1", - "safe-buffer": "5.1.1", - "stringstream": "0.0.5", - "tough-cookie": "2.3.3", - "tunnel-agent": "0.6.0", - "uuid": "3.1.0" - }, - "dependencies": { - "assert-plus": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/assert-plus/-/assert-plus-1.0.0.tgz", - "integrity": "sha1-8S4PPF13sLHN2RRpQuTpbB5N1SU=", - "dev": true - }, - "aws-sign2": { - "version": "0.7.0", - "resolved": "https://registry.npmjs.org/aws-sign2/-/aws-sign2-0.7.0.tgz", - "integrity": "sha1-tG6JCTSpWR8tL2+G1+ap8bP+dqg=", - "dev": true - }, - "boom": { - "version": "4.3.1", - "resolved": "https://registry.npmjs.org/boom/-/boom-4.3.1.tgz", - "integrity": "sha1-T4owBctKfjiJ90kDD9JbluAdLjE=", - "dev": true, - "requires": { - "hoek": "4.2.0" - } - }, - "caseless": { - "version": "0.12.0", - "resolved": "https://registry.npmjs.org/caseless/-/caseless-0.12.0.tgz", - "integrity": "sha1-G2gcIf+EAzyCZUMJBolCDRhxUdw=", - "dev": true - }, - "cryptiles": { - "version": "3.1.2", - "resolved": "https://registry.npmjs.org/cryptiles/-/cryptiles-3.1.2.tgz", - "integrity": "sha1-qJ+7Ig9c4l7FboxKqKT9e1sNKf4=", - "dev": true, - "requires": { - "boom": "5.2.0" - }, - "dependencies": { - "boom": { - "version": "5.2.0", - "resolved": "https://registry.npmjs.org/boom/-/boom-5.2.0.tgz", - "integrity": "sha512-Z5BTk6ZRe4tXXQlkqftmsAUANpXmuwlsF5Oov8ThoMbQRzdGTA1ngYRW160GexgOgjsFOKJz0LYhoNi+2AMBUw==", - "dev": true, - "requires": { - "hoek": "4.2.0" - } - } - } - }, - "form-data": { - "version": "2.3.1", - "resolved": "https://registry.npmjs.org/form-data/-/form-data-2.3.1.tgz", - "integrity": "sha1-b7lPvXGIUwbXPRXMSX/kzE7NRL8=", - "dev": true, - "requires": { - "asynckit": "0.4.0", - "combined-stream": "1.0.5", - "mime-types": "2.1.17" - } - }, - "har-validator": { - "version": "5.0.3", - "resolved": "https://registry.npmjs.org/har-validator/-/har-validator-5.0.3.tgz", - "integrity": "sha1-ukAsJmGU8VlW7xXg/PJCmT9qff0=", - "dev": true, - "requires": { - "ajv": "5.4.0", - "har-schema": "2.0.0" - } - }, - "hawk": { - "version": "6.0.2", - "resolved": "https://registry.npmjs.org/hawk/-/hawk-6.0.2.tgz", - "integrity": "sha512-miowhl2+U7Qle4vdLqDdPt9m09K6yZhkLDTWGoUiUzrQCn+mHHSmfJgAyGaLRZbPmTqfFFjRV1QWCW0VWUJBbQ==", - "dev": true, - "requires": { - "boom": "4.3.1", - "cryptiles": "3.1.2", - "hoek": "4.2.0", - "sntp": "2.1.0" - } - }, - "hoek": { - "version": "4.2.0", - "resolved": "https://registry.npmjs.org/hoek/-/hoek-4.2.0.tgz", - "integrity": "sha512-v0XCLxICi9nPfYrS9RL8HbYnXi9obYAeLbSP00BmnZwCK9+Ih9WOjoZ8YoHCoav2csqn4FOz4Orldsy2dmDwmQ==", - "dev": true - }, - "http-signature": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/http-signature/-/http-signature-1.2.0.tgz", - "integrity": "sha1-muzZJRFHcvPZW2WmCruPfBj7rOE=", - "dev": true, - "requires": { - "assert-plus": "1.0.0", - "jsprim": "1.4.1", - "sshpk": "1.13.1" - } - }, - "qs": { - "version": "6.5.1", - "resolved": "https://registry.npmjs.org/qs/-/qs-6.5.1.tgz", - "integrity": "sha512-eRzhrN1WSINYCDCbrz796z37LOe3m5tmW7RQf6oBntukAG1nmovJvhnwHHRMAfeoItc1m2Hk02WER2aQ/iqs+A==", - "dev": true - }, - "sntp": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/sntp/-/sntp-2.1.0.tgz", - "integrity": "sha512-FL1b58BDrqS3A11lJ0zEdnJ3UOKqVxawAkF3k7F0CVN7VQ34aZrV+G8BZ1WC9ZL7NyrwsW0oviwsWDgRuVYtJg==", - "dev": true, - "requires": { - "hoek": "4.2.0" - } - }, - "tunnel-agent": { - "version": "0.6.0", - "resolved": "https://registry.npmjs.org/tunnel-agent/-/tunnel-agent-0.6.0.tgz", - "integrity": "sha1-J6XeoGs2sEoKmWZ3SykIaPD8QP0=", - "dev": true, - "requires": { - "safe-buffer": "5.1.1" - } - } - } - }, - "request-light": { - "version": "0.2.1", - "resolved": "https://registry.npmjs.org/request-light/-/request-light-0.2.1.tgz", - "integrity": "sha1-mG9agok+nRymqJbr5vRsUca0VX8=", - "requires": { - "http-proxy-agent": "0.2.7", - "https-proxy-agent": "0.3.6", - "vscode-nls": "2.0.2" - } - }, - "requires-port": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/requires-port/-/requires-port-1.0.0.tgz", - "integrity": "sha1-kl0mAdOaxIXgkc8NpcbmlNw9yv8=", - "dev": true - }, - "resolve": { - "version": "1.5.0", - "resolved": "https://registry.npmjs.org/resolve/-/resolve-1.5.0.tgz", - "integrity": "sha512-hgoSGrc3pjzAPHNBg+KnFcK2HwlHTs/YrAGUr6qgTVUZmXv1UEXXl0bZNBKMA9fud6lRYFdPGz0xXxycPzmmiw==", - "dev": true, - "requires": { - "path-parse": "1.0.5" - } - }, - "resolve-dir": { - "version": "0.1.1", - "resolved": "https://registry.npmjs.org/resolve-dir/-/resolve-dir-0.1.1.tgz", - "integrity": "sha1-shklmlYC+sXFxJatiUpujMQwJh4=", - "dev": true, - "requires": { - "expand-tilde": "1.2.2", - "global-modules": "0.2.3" - } - }, - "resolve-url": { - "version": "0.2.1", - "resolved": "https://registry.npmjs.org/resolve-url/-/resolve-url-0.2.1.tgz", - "integrity": "sha1-LGN/53yJOv0qZj/iGqkIAGjiBSo=", - "dev": true - }, - "right-align": { - "version": "0.1.3", - "resolved": "https://registry.npmjs.org/right-align/-/right-align-0.1.3.tgz", - "integrity": "sha1-YTObci/mo1FWiSENJOFMlhSGE+8=", - "dev": true, - "requires": { - "align-text": "0.1.4" - } - }, - "rimraf": { - "version": "2.6.2", - "resolved": "https://registry.npmjs.org/rimraf/-/rimraf-2.6.2.tgz", - "integrity": "sha512-lreewLK/BlghmxtfH36YYVg1i8IAce4TI7oao75I1g245+6BctqTVQiBP3YUJ9C6DQOXJmkYR9X9fCLtCOJc5w==", - "dev": true, - "requires": { - "glob": "7.1.2" - } - }, - "run-sequence": { - "version": "2.2.0", - "resolved": "https://registry.npmjs.org/run-sequence/-/run-sequence-2.2.0.tgz", - "integrity": "sha512-xW5DmUwdvoyYQUMPKN8UW7TZSFs7AxtT59xo1m5y91jHbvwGlGgOmdV1Yw5P68fkjf3aHUZ4G1o1mZCtNe0qtw==", - "dev": true, - "requires": { - "chalk": "1.1.3", - "gulp-util": "3.0.8" - } - }, - "safe-buffer": { - "version": "5.1.1", - "resolved": "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.1.1.tgz", - "integrity": "sha512-kKvNJn6Mm93gAczWVJg7wH+wGYWNrDHdWvpUmHyEsgCtIwwo3bqPtV4tR5tuPaUhTOo/kvhVwd8XwwOllGYkbg==", - "dev": true - }, - "sax": { - "version": "1.2.4", - "resolved": "https://registry.npmjs.org/sax/-/sax-1.2.4.tgz", - "integrity": "sha512-NqVDv9TpANUjFm0N8uM5GxL36UgKi9/atZw+x7YFnQ8ckwFGKrl4xX4yWtrey3UJm5nP1kUbnYgLopqWNSRhWw==", - "dev": true - }, - "semver": { - "version": "4.3.6", - "resolved": "https://registry.npmjs.org/semver/-/semver-4.3.6.tgz", - "integrity": "sha1-MAvG4OhjdPe6YQaLWx7NV/xlMto=", - "dev": true - }, - "semver-diff": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/semver-diff/-/semver-diff-2.1.0.tgz", - "integrity": "sha1-S7uEN8jTfksM8aaP1ybsbWRdbTY=", - "dev": true, - "requires": { - "semver": "5.4.1" - }, - "dependencies": { - "semver": { - "version": "5.4.1", - "resolved": "https://registry.npmjs.org/semver/-/semver-5.4.1.tgz", - "integrity": "sha512-WfG/X9+oATh81XtllIo/I8gOiY9EXRdv1cQdyykeXK17YcUW3EXUAi2To4pcH6nZtJPr7ZOpM5OMyWJZm+8Rsg==", - "dev": true - } - } - }, - "sequencify": { - "version": "0.0.7", - "resolved": "https://registry.npmjs.org/sequencify/-/sequencify-0.0.7.tgz", - "integrity": "sha1-kM/xnQLgcCf9dn9erT57ldHnOAw=", - "dev": true - }, - "set-immediate-shim": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/set-immediate-shim/-/set-immediate-shim-1.0.1.tgz", - "integrity": "sha1-SysbJ+uAip+NzEgaWOXlb1mfP2E=", - "dev": true - }, - "shebang-command": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/shebang-command/-/shebang-command-1.2.0.tgz", - "integrity": "sha1-RKrGW2lbAzmJaMOfNj/uXer98eo=", - "dev": true, - "requires": { - "shebang-regex": "1.0.0" - } - }, - "shebang-regex": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/shebang-regex/-/shebang-regex-1.0.0.tgz", - "integrity": "sha1-2kL0l0DAtC2yypcoVxyxkMmO/qM=", - "dev": true - }, - "sigmund": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/sigmund/-/sigmund-1.0.1.tgz", - "integrity": "sha1-P/IfGYytIXX587eBhT/ZTQ0ZtZA=", - "dev": true - }, - "signal-exit": { - "version": "3.0.2", - "resolved": "https://registry.npmjs.org/signal-exit/-/signal-exit-3.0.2.tgz", - "integrity": "sha1-tf3AjxKH6hF4Yo5BXiUTK3NkbG0=", - "dev": true - }, - "sntp": { - "version": "1.0.9", - "resolved": "https://registry.npmjs.org/sntp/-/sntp-1.0.9.tgz", - "integrity": "sha1-ZUEYTMkK7qbG57NeJlkIJEPGYZg=", - "dev": true, - "requires": { - "hoek": "2.16.3" - } - }, - "source-map": { - "version": "0.6.1", - "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.6.1.tgz", - "integrity": "sha512-UjgapumWlbMhkBgzT7Ykc5YXUT46F0iKu8SGXq0bcwP5dz/h0Plj6enJqjz1Zbq2l5WaqYnrVbwWOWMyF3F47g==" - }, - "source-map-resolve": { - "version": "0.3.1", - "resolved": "https://registry.npmjs.org/source-map-resolve/-/source-map-resolve-0.3.1.tgz", - "integrity": "sha1-YQ9hIqRFuN1RU1oqcbeD38Ekh2E=", - "dev": true, - "requires": { - "atob": "1.1.3", - "resolve-url": "0.2.1", - "source-map-url": "0.3.0", - "urix": "0.1.0" - } - }, - "source-map-support": { - "version": "0.5.0", - "resolved": "https://registry.npmjs.org/source-map-support/-/source-map-support-0.5.0.tgz", - "integrity": "sha512-vUoN3I7fHQe0R/SJLKRdKYuEdRGogsviXFkHHo17AWaTGv17VLnxw+CFXvqy+y4ORZ3doWLQcxRYfwKrsd/H7Q==", - "dev": true, - "requires": { - "source-map": "0.6.1" - } - }, - "source-map-url": { - "version": "0.3.0", - "resolved": "https://registry.npmjs.org/source-map-url/-/source-map-url-0.3.0.tgz", - "integrity": "sha1-fsrxO1e80J2opAxdJp2zN5nUqvk=", - "dev": true - }, - "sparkles": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/sparkles/-/sparkles-1.0.0.tgz", - "integrity": "sha1-Gsu/tZJDbRC76PeFt8xvgoFQEsM=", - "dev": true - }, - "split": { - "version": "0.3.3", - "resolved": "https://registry.npmjs.org/split/-/split-0.3.3.tgz", - "integrity": "sha1-zQ7qXmOiEd//frDwkcQTPi0N0o8=", - "dev": true, - "requires": { - "through": "2.3.8" - } - }, - "sprintf-js": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/sprintf-js/-/sprintf-js-1.0.3.tgz", - "integrity": "sha1-BOaSb2YolTVPPdAVIDYzuFcpfiw=", - "dev": true - }, - "sshpk": { - "version": "1.13.1", - "resolved": "https://registry.npmjs.org/sshpk/-/sshpk-1.13.1.tgz", - "integrity": "sha1-US322mKHFEMW3EwY/hzx2UBzm+M=", - "dev": true, - "requires": { - "asn1": "0.2.3", - "assert-plus": "1.0.0", - "bcrypt-pbkdf": "1.0.1", - "dashdash": "1.14.1", - "ecc-jsbn": "0.1.1", - "getpass": "0.1.7", - "jsbn": "0.1.1", - "tweetnacl": "0.14.5" - }, - "dependencies": { - "assert-plus": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/assert-plus/-/assert-plus-1.0.0.tgz", - "integrity": "sha1-8S4PPF13sLHN2RRpQuTpbB5N1SU=", - "dev": true - } - } - }, - "stat-mode": { - "version": "0.2.2", - "resolved": "https://registry.npmjs.org/stat-mode/-/stat-mode-0.2.2.tgz", - "integrity": "sha1-5sgLYjEj19gM8TLOU480YokHJQI=", - "dev": true - }, - "stream-combiner": { - "version": "0.0.4", - "resolved": "https://registry.npmjs.org/stream-combiner/-/stream-combiner-0.0.4.tgz", - "integrity": "sha1-TV5DPBhSYd3mI8o/RMWGvPXErRQ=", - "dev": true, - "requires": { - "duplexer": "0.1.1" - } - }, - "stream-consume": { - "version": "0.1.0", - "resolved": "https://registry.npmjs.org/stream-consume/-/stream-consume-0.1.0.tgz", - "integrity": "sha1-pB6tGm1ggc63n2WwYZAbbY89HQ8=", - "dev": true - }, - "stream-shift": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/stream-shift/-/stream-shift-1.0.0.tgz", - "integrity": "sha1-1cdSgl5TZ+eG944Y5EXqIjoVWVI=", - "dev": true - }, - "streamfilter": { - "version": "1.0.5", - "resolved": "https://registry.npmjs.org/streamfilter/-/streamfilter-1.0.5.tgz", - "integrity": "sha1-h1BxEb644phFFxe1Ec/tjwAqv1M=", - "dev": true, - "requires": { - "readable-stream": "2.3.3" - }, - "dependencies": { - "isarray": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/isarray/-/isarray-1.0.0.tgz", - "integrity": "sha1-u5NdSFgsuhaMBoNJV6VKPgcSTxE=", - "dev": true - }, - "readable-stream": { - "version": "2.3.3", - "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-2.3.3.tgz", - "integrity": "sha512-m+qzzcn7KUxEmd1gMbchF+Y2eIUbieUaxkWtptyHywrX0rE8QEYqPC07Vuy4Wm32/xE16NcdBctb8S0Xe/5IeQ==", - "dev": true, - "requires": { - "core-util-is": "1.0.2", - "inherits": "2.0.3", - "isarray": "1.0.0", - "process-nextick-args": "1.0.7", - "safe-buffer": "5.1.1", - "string_decoder": "1.0.3", - "util-deprecate": "1.0.2" - } - }, - "string_decoder": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/string_decoder/-/string_decoder-1.0.3.tgz", - "integrity": "sha512-4AH6Z5fzNNBcH+6XDMfA/BTt87skxqJlO0lAh3Dker5zThcAxG6mKz+iGu308UKoPPQ8Dcqx/4JhujzltRa+hQ==", - "dev": true, - "requires": { - "safe-buffer": "5.1.1" - } - } - } - }, - "streamifier": { - "version": "0.1.1", - "resolved": "https://registry.npmjs.org/streamifier/-/streamifier-0.1.1.tgz", - "integrity": "sha1-l+mNj6TRBdYqJpHR3AfoINuN/E8=", - "dev": true - }, - "string-width": { - "version": "2.1.1", - "resolved": "https://registry.npmjs.org/string-width/-/string-width-2.1.1.tgz", - "integrity": "sha512-nOqH59deCq9SRHlxq1Aw85Jnt4w6KvLKqWVik6oA9ZklXLNIOlqg4F2yrT1MVaTjAqvVwdfeZ7w7aCvJD7ugkw==", - "dev": true, - "requires": { - "is-fullwidth-code-point": "2.0.0", - "strip-ansi": "4.0.0" - }, - "dependencies": { - "ansi-regex": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-3.0.0.tgz", - "integrity": "sha1-7QMXwyIGT3lGbAKWa922Bas32Zg=", - "dev": true - }, - "strip-ansi": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-4.0.0.tgz", - "integrity": "sha1-qEeQIusaw2iocTibY1JixQXuNo8=", - "dev": true, - "requires": { - "ansi-regex": "3.0.0" - } - } - } - }, - "string_decoder": { - "version": "0.10.31", - "resolved": "https://registry.npmjs.org/string_decoder/-/string_decoder-0.10.31.tgz", - "integrity": "sha1-YuIDvEF2bGwoyfyEMB2rHFMQ+pQ=", - "dev": true - }, - "stringstream": { - "version": "0.0.5", - "resolved": "https://registry.npmjs.org/stringstream/-/stringstream-0.0.5.tgz", - "integrity": "sha1-TkhM1N5aC7vuGORjB3EKioFiGHg=", - "dev": true - }, - "strip-ansi": { - "version": "3.0.1", - "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-3.0.1.tgz", - "integrity": "sha1-ajhfuIU9lS1f8F0Oiq+UJ43GPc8=", - "dev": true, - "requires": { - "ansi-regex": "2.1.1" - } - }, - "strip-bom": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/strip-bom/-/strip-bom-1.0.0.tgz", - "integrity": "sha1-hbiGLzhEtabV7IRnqTWYFzo295Q=", - "dev": true, - "requires": { - "first-chunk-stream": "1.0.0", - "is-utf8": "0.2.1" - } - }, - "strip-bom-stream": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/strip-bom-stream/-/strip-bom-stream-1.0.0.tgz", - "integrity": "sha1-5xRDmFd9Uaa+0PoZlPoF9D/ZiO4=", - "dev": true, - "requires": { - "first-chunk-stream": "1.0.0", - "strip-bom": "2.0.0" - }, - "dependencies": { - "strip-bom": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/strip-bom/-/strip-bom-2.0.0.tgz", - "integrity": "sha1-YhmoVhZSBJHzV4i9vxRHqZx+aw4=", - "dev": true, - "requires": { - "is-utf8": "0.2.1" - } - } - } - }, - "strip-bom-string": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/strip-bom-string/-/strip-bom-string-1.0.0.tgz", - "integrity": "sha1-5SEekiQ2n7uB1jOi8ABE3IztrZI=", - "dev": true - }, - "strip-eof": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/strip-eof/-/strip-eof-1.0.0.tgz", - "integrity": "sha1-u0P/VZim6wXYm1n80SnJgzE2Br8=", - "dev": true - }, - "strip-json-comments": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/strip-json-comments/-/strip-json-comments-2.0.1.tgz", - "integrity": "sha1-PFMZQukIwml8DsNEhYwobHygpgo=", - "dev": true - }, - "supports-color": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-2.0.0.tgz", - "integrity": "sha1-U10EXOa2Nj+kARcIRimZXp3zJMc=", - "dev": true - }, - "tar": { - "version": "2.2.1", - "resolved": "https://registry.npmjs.org/tar/-/tar-2.2.1.tgz", - "integrity": "sha1-jk0qJWwOIYXGsYrWlK7JaLg8sdE=", - "dev": true, - "requires": { - "block-stream": "0.0.9", - "fstream": "1.0.11", - "inherits": "2.0.3" - } - }, - "term-size": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/term-size/-/term-size-1.2.0.tgz", - "integrity": "sha1-RYuDiH8oj8Vtb/+/rSYuJmOO+mk=", - "dev": true, - "requires": { - "execa": "0.7.0" - } - }, - "through": { - "version": "2.3.8", - "resolved": "https://registry.npmjs.org/through/-/through-2.3.8.tgz", - "integrity": "sha1-DdTJ/6q8NXlgsbckEV1+Doai4fU=", - "dev": true - }, - "through2": { - "version": "2.0.3", - "resolved": "https://registry.npmjs.org/through2/-/through2-2.0.3.tgz", - "integrity": "sha1-AARWmzfHx0ujnEPzzteNGtlBQL4=", - "dev": true, - "requires": { - "readable-stream": "2.3.3", - "xtend": "4.0.1" - }, - "dependencies": { - "isarray": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/isarray/-/isarray-1.0.0.tgz", - "integrity": "sha1-u5NdSFgsuhaMBoNJV6VKPgcSTxE=", - "dev": true - }, - "readable-stream": { - "version": "2.3.3", - "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-2.3.3.tgz", - "integrity": "sha512-m+qzzcn7KUxEmd1gMbchF+Y2eIUbieUaxkWtptyHywrX0rE8QEYqPC07Vuy4Wm32/xE16NcdBctb8S0Xe/5IeQ==", - "dev": true, - "requires": { - "core-util-is": "1.0.2", - "inherits": "2.0.3", - "isarray": "1.0.0", - "process-nextick-args": "1.0.7", - "safe-buffer": "5.1.1", - "string_decoder": "1.0.3", - "util-deprecate": "1.0.2" - } - }, - "string_decoder": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/string_decoder/-/string_decoder-1.0.3.tgz", - "integrity": "sha512-4AH6Z5fzNNBcH+6XDMfA/BTt87skxqJlO0lAh3Dker5zThcAxG6mKz+iGu308UKoPPQ8Dcqx/4JhujzltRa+hQ==", - "dev": true, - "requires": { - "safe-buffer": "5.1.1" - } - } - } - }, - "through2-filter": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/through2-filter/-/through2-filter-2.0.0.tgz", - "integrity": "sha1-YLxVoNrLdghdsfna6Zq0P4PWIuw=", - "dev": true, - "requires": { - "through2": "2.0.3", - "xtend": "4.0.1" - } - }, - "tildify": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/tildify/-/tildify-1.2.0.tgz", - "integrity": "sha1-3OwD9V3Km3qj5bBPIYF+tW5jWIo=", - "dev": true, - "requires": { - "os-homedir": "1.0.2" - } - }, - "time-stamp": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/time-stamp/-/time-stamp-1.1.0.tgz", - "integrity": "sha1-dkpaEa9QVhkhsTPztE5hhofg9cM=", - "dev": true - }, - "timed-out": { - "version": "4.0.1", - "resolved": "https://registry.npmjs.org/timed-out/-/timed-out-4.0.1.tgz", - "integrity": "sha1-8y6srFoXW+ol1/q1Zas+2HQe9W8=", - "dev": true - }, - "timers-ext": { - "version": "0.1.2", - "resolved": "https://registry.npmjs.org/timers-ext/-/timers-ext-0.1.2.tgz", - "integrity": "sha1-YcxHp2wavTGV8UUn+XjViulMUgQ=", - "dev": true, - "requires": { - "es5-ext": "0.10.35", - "next-tick": "1.0.0" - } - }, - "tmp": { - "version": "0.0.29", - "resolved": "https://registry.npmjs.org/tmp/-/tmp-0.0.29.tgz", - "integrity": "sha1-8lEl/w3Z2jzLDC3Tce4SiLuRKMA=", - "dev": true, - "requires": { - "os-tmpdir": "1.0.2" - } - }, - "to-absolute-glob": { - "version": "0.1.1", - "resolved": "https://registry.npmjs.org/to-absolute-glob/-/to-absolute-glob-0.1.1.tgz", - "integrity": "sha1-HN+kcqnvUMI57maZm2YsoOs5k38=", - "dev": true, - "requires": { - "extend-shallow": "2.0.1" - } - }, - "touch": { - "version": "3.1.0", - "resolved": "https://registry.npmjs.org/touch/-/touch-3.1.0.tgz", - "integrity": "sha512-WBx8Uy5TLtOSRtIq+M03/sKDrXCLHxwDcquSP2c43Le03/9serjQBIztjRz6FkJez9D/hleyAXTBGLwwZUw9lA==", - "dev": true, - "requires": { - "nopt": "1.0.10" - } - }, - "tough-cookie": { - "version": "2.3.3", - "resolved": "https://registry.npmjs.org/tough-cookie/-/tough-cookie-2.3.3.tgz", - "integrity": "sha1-C2GKVWW23qkL80JdBNVe3EdadWE=", - "dev": true, - "requires": { - "punycode": "1.4.1" - } - }, - "tslib": { - "version": "1.8.0", - "resolved": "https://registry.npmjs.org/tslib/-/tslib-1.8.0.tgz", - "integrity": "sha512-ymKWWZJST0/CkgduC2qkzjMOWr4bouhuURNXCn/inEX0L57BnRG6FhX76o7FOnsjHazCjfU2LKeSrlS2sIKQJg==", - "dev": true - }, - "tslint": { - "version": "5.8.0", - "resolved": "https://registry.npmjs.org/tslint/-/tslint-5.8.0.tgz", - "integrity": "sha1-H0mtWy53x2w69N3K5VKuTjYS6xM=", - "dev": true, - "requires": { - "babel-code-frame": "6.26.0", - "builtin-modules": "1.1.1", - "chalk": "2.3.0", - "commander": "2.11.0", - "diff": "3.3.1", - "glob": "7.1.2", - "minimatch": "3.0.4", - "resolve": "1.5.0", - "semver": "5.4.1", - "tslib": "1.8.0", - "tsutils": "2.12.2" - }, - "dependencies": { - "ansi-styles": { - "version": "3.2.0", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-3.2.0.tgz", - "integrity": "sha512-NnSOmMEYtVR2JVMIGTzynRkkaxtiq1xnFBcdQD/DnNCYPoEPsVJhM98BDyaoNOQIi7p4okdi3E27eN7GQbsUug==", - "dev": true, - "requires": { - "color-convert": "1.9.1" - } - }, - "chalk": { - "version": "2.3.0", - "resolved": "https://registry.npmjs.org/chalk/-/chalk-2.3.0.tgz", - "integrity": "sha512-Az5zJR2CBujap2rqXGaJKaPHyJ0IrUimvYNX+ncCy8PJP4ltOGTrHUIo097ZaL2zMeKYpiCdqDvS6zdrTFok3Q==", - "dev": true, - "requires": { - "ansi-styles": "3.2.0", - "escape-string-regexp": "1.0.5", - "supports-color": "4.5.0" - } - }, - "semver": { - "version": "5.4.1", - "resolved": "https://registry.npmjs.org/semver/-/semver-5.4.1.tgz", - "integrity": "sha512-WfG/X9+oATh81XtllIo/I8gOiY9EXRdv1cQdyykeXK17YcUW3EXUAi2To4pcH6nZtJPr7ZOpM5OMyWJZm+8Rsg==", - "dev": true - }, - "supports-color": { - "version": "4.5.0", - "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-4.5.0.tgz", - "integrity": "sha1-vnoN5ITexcXN34s9WRJQRJEvY1s=", - "dev": true, - "requires": { - "has-flag": "2.0.0" - } - } - } - }, - "tslint-microsoft-contrib": { - "version": "5.0.1", - "resolved": "https://registry.npmjs.org/tslint-microsoft-contrib/-/tslint-microsoft-contrib-5.0.1.tgz", - "integrity": "sha1-Mo7pwo0HzfeTKTIEyW4v+rkiGZQ=", - "dev": true, - "requires": { - "tsutils": "1.9.1" - }, - "dependencies": { - "tsutils": { - "version": "1.9.1", - "resolved": "https://registry.npmjs.org/tsutils/-/tsutils-1.9.1.tgz", - "integrity": "sha1-ufmrROVa+WgYMdXyjQrur1x1DLA=", - "dev": true - } - } - }, - "tsutils": { - "version": "2.12.2", - "resolved": "https://registry.npmjs.org/tsutils/-/tsutils-2.12.2.tgz", - "integrity": "sha1-rVikhl0X7D3bZjG2ylO+FKVlb/M=", - "dev": true, - "requires": { - "tslib": "1.8.0" - } - }, - "tunnel": { - "version": "0.0.4", - "resolved": "https://registry.npmjs.org/tunnel/-/tunnel-0.0.4.tgz", - "integrity": "sha1-LTeFoVjBdMmhbcLARuxfxfF0IhM=", - "dev": true - }, - "tunnel-agent": { - "version": "0.4.3", - "resolved": "https://registry.npmjs.org/tunnel-agent/-/tunnel-agent-0.4.3.tgz", - "integrity": "sha1-Y3PbdpCf5XDgjXNYM2Xtgop07us=", - "dev": true - }, - "tweetnacl": { - "version": "0.14.5", - "resolved": "https://registry.npmjs.org/tweetnacl/-/tweetnacl-0.14.5.tgz", - "integrity": "sha1-WuaBd/GS1EViadEIr6k/+HQ/T2Q=", - "dev": true, - "optional": true - }, - "typed-rest-client": { - "version": "0.9.0", - "resolved": "https://registry.npmjs.org/typed-rest-client/-/typed-rest-client-0.9.0.tgz", - "integrity": "sha1-92jMDcP06VDwbgSCXDaz54NKofI=", - "dev": true, - "requires": { - "tunnel": "0.0.4", - "underscore": "1.8.3" - } - }, - "typescript": { - "version": "2.6.1", - "resolved": "https://registry.npmjs.org/typescript/-/typescript-2.6.1.tgz", - "integrity": "sha1-7znN6ierrAtQAkLWcmq5DgyEZjE=", - "dev": true - }, - "uc.micro": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/uc.micro/-/uc.micro-1.0.3.tgz", - "integrity": "sha1-ftUNXg+an7ClczeSWfKndFjVAZI=", - "dev": true - }, - "uglify-js": { - "version": "2.7.0", - "resolved": "https://registry.npmjs.org/uglify-js/-/uglify-js-2.7.0.tgz", - "integrity": "sha1-8CHji6LKdAhg9b1caVwqgXNF8Ow=", - "dev": true, - "requires": { - "async": "0.2.10", - "source-map": "0.5.7", - "uglify-to-browserify": "1.0.2", - "yargs": "3.10.0" - }, - "dependencies": { - "source-map": { - "version": "0.5.7", - "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.5.7.tgz", - "integrity": "sha1-igOdLRAh0i0eoUyA2OpGi6LvP8w=", - "dev": true - } - } - }, - "uglify-save-license": { - "version": "0.4.1", - "resolved": "https://registry.npmjs.org/uglify-save-license/-/uglify-save-license-0.4.1.tgz", - "integrity": "sha1-lXJsF8xv0XHDYX479NjYKqjEzOE=", - "dev": true - }, - "uglify-to-browserify": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/uglify-to-browserify/-/uglify-to-browserify-1.0.2.tgz", - "integrity": "sha1-bgkk1r2mta/jSeOabWMoUKD4grc=", - "dev": true - }, - "unc-path-regex": { - "version": "0.1.2", - "resolved": "https://registry.npmjs.org/unc-path-regex/-/unc-path-regex-0.1.2.tgz", - "integrity": "sha1-5z3T17DXxe2G+6xrCufYxqadUPo=", - "dev": true - }, - "undefsafe": { - "version": "0.0.3", - "resolved": "https://registry.npmjs.org/undefsafe/-/undefsafe-0.0.3.tgz", - "integrity": "sha1-7Mo6A+VrmvFzhbqsgSrIO5lKli8=", - "dev": true - }, - "underscore": { - "version": "1.8.3", - "resolved": "https://registry.npmjs.org/underscore/-/underscore-1.8.3.tgz", - "integrity": "sha1-Tz+1OxBuYJf8+ctBCfKl6b36UCI=", - "dev": true - }, - "unique-stream": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/unique-stream/-/unique-stream-1.0.0.tgz", - "integrity": "sha1-1ZpKdUJ0R9mqbJHnAmP40mpLEEs=", - "dev": true - }, - "unique-string": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/unique-string/-/unique-string-1.0.0.tgz", - "integrity": "sha1-nhBXzKhRq7kzmPizOuGHuZyuwRo=", - "dev": true, - "requires": { - "crypto-random-string": "1.0.0" - } - }, - "unzip-response": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/unzip-response/-/unzip-response-2.0.1.tgz", - "integrity": "sha1-0vD3N9FrBhXnKmk17QQhRXLVb5c=", - "dev": true - }, - "update-notifier": { - "version": "2.3.0", - "resolved": "https://registry.npmjs.org/update-notifier/-/update-notifier-2.3.0.tgz", - "integrity": "sha1-TognpruRUUCrCTVZ1wFOPruDdFE=", - "dev": true, - "requires": { - "boxen": "1.2.2", - "chalk": "2.3.0", - "configstore": "3.1.1", - "import-lazy": "2.1.0", - "is-installed-globally": "0.1.0", - "is-npm": "1.0.0", - "latest-version": "3.1.0", - "semver-diff": "2.1.0", - "xdg-basedir": "3.0.0" - }, - "dependencies": { - "ansi-styles": { - "version": "3.2.0", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-3.2.0.tgz", - "integrity": "sha512-NnSOmMEYtVR2JVMIGTzynRkkaxtiq1xnFBcdQD/DnNCYPoEPsVJhM98BDyaoNOQIi7p4okdi3E27eN7GQbsUug==", - "dev": true, - "requires": { - "color-convert": "1.9.1" - } - }, - "chalk": { - "version": "2.3.0", - "resolved": "https://registry.npmjs.org/chalk/-/chalk-2.3.0.tgz", - "integrity": "sha512-Az5zJR2CBujap2rqXGaJKaPHyJ0IrUimvYNX+ncCy8PJP4ltOGTrHUIo097ZaL2zMeKYpiCdqDvS6zdrTFok3Q==", - "dev": true, - "requires": { - "ansi-styles": "3.2.0", - "escape-string-regexp": "1.0.5", - "supports-color": "4.5.0" - } - }, - "supports-color": { - "version": "4.5.0", - "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-4.5.0.tgz", - "integrity": "sha1-vnoN5ITexcXN34s9WRJQRJEvY1s=", - "dev": true, - "requires": { - "has-flag": "2.0.0" - } - } - } - }, - "urix": { - "version": "0.1.0", - "resolved": "https://registry.npmjs.org/urix/-/urix-0.1.0.tgz", - "integrity": "sha1-2pN/emLiH+wf0Y1Js1wpNQZ6bHI=", - "dev": true - }, - "url-join": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/url-join/-/url-join-1.1.0.tgz", - "integrity": "sha1-dBxsL0WWxIMNZxhGCSDQySIC3Hg=", - "dev": true - }, - "url-parse": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/url-parse/-/url-parse-1.2.0.tgz", - "integrity": "sha512-DT1XbYAfmQP65M/mE6OALxmXzZ/z1+e5zk2TcSKe/KiYbNGZxgtttzC0mR/sjopbpOXcbniq7eIKmocJnUWlEw==", - "dev": true, - "requires": { - "querystringify": "1.0.0", - "requires-port": "1.0.0" - } - }, - "url-parse-lax": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/url-parse-lax/-/url-parse-lax-1.0.0.tgz", - "integrity": "sha1-evjzA2Rem9eaJy56FKxovAYJ2nM=", - "dev": true, - "requires": { - "prepend-http": "1.0.4" - } - }, - "user-home": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/user-home/-/user-home-1.1.1.tgz", - "integrity": "sha1-K1viOjK2Onyd640PKNSFcko98ZA=", - "dev": true - }, - "util-deprecate": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/util-deprecate/-/util-deprecate-1.0.2.tgz", - "integrity": "sha1-RQ1Nyfpw3nMnYvvS1KKJgUGaDM8=", - "dev": true - }, - "uuid": { - "version": "3.1.0", - "resolved": "https://registry.npmjs.org/uuid/-/uuid-3.1.0.tgz", - "integrity": "sha512-DIWtzUkw04M4k3bf1IcpS2tngXEL26YUD2M0tMDUpnUrz2hgzUBlD55a4FjdLGPvfHxS6uluGWvaVEqgBcVa+g==", - "dev": true - }, - "v8flags": { - "version": "2.1.1", - "resolved": "https://registry.npmjs.org/v8flags/-/v8flags-2.1.1.tgz", - "integrity": "sha1-qrGh+jDUX4jdMhFIh1rALAtV5bQ=", - "dev": true, - "requires": { - "user-home": "1.1.1" - } - }, - "vali-date": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/vali-date/-/vali-date-1.0.0.tgz", - "integrity": "sha1-G5BKWWCfsyjvB4E4Qgk09rhnCaY=", - "dev": true - }, - "verror": { - "version": "1.10.0", - "resolved": "https://registry.npmjs.org/verror/-/verror-1.10.0.tgz", - "integrity": "sha1-OhBcoXBTr1XW4nDB+CiGguGNpAA=", - "dev": true, - "requires": { - "assert-plus": "1.0.0", - "core-util-is": "1.0.2", - "extsprintf": "1.3.0" - }, - "dependencies": { - "assert-plus": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/assert-plus/-/assert-plus-1.0.0.tgz", - "integrity": "sha1-8S4PPF13sLHN2RRpQuTpbB5N1SU=", - "dev": true - } - } - }, - "vinyl": { - "version": "0.5.3", - "resolved": "https://registry.npmjs.org/vinyl/-/vinyl-0.5.3.tgz", - "integrity": "sha1-sEVbOPxeDPMNQyUTLkYZcMIJHN4=", - "dev": true, - "requires": { - "clone": "1.0.3", - "clone-stats": "0.0.1", - "replace-ext": "0.0.1" - } - }, - "vinyl-fs": { - "version": "0.3.14", - "resolved": "https://registry.npmjs.org/vinyl-fs/-/vinyl-fs-0.3.14.tgz", - "integrity": "sha1-mmhRzhysHBzqX+hsCTHWIMLPqeY=", - "dev": true, - "requires": { - "defaults": "1.0.3", - "glob-stream": "3.1.18", - "glob-watcher": "0.0.6", - "graceful-fs": "3.0.11", - "mkdirp": "0.5.1", - "strip-bom": "1.0.0", - "through2": "0.6.5", - "vinyl": "0.4.6" - }, - "dependencies": { - "clone": { - "version": "0.2.0", - "resolved": "https://registry.npmjs.org/clone/-/clone-0.2.0.tgz", - "integrity": "sha1-xhJqkK1Pctv1rNskPMN3JP6T/B8=", - "dev": true - }, - "readable-stream": { - "version": "1.0.34", - "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-1.0.34.tgz", - "integrity": "sha1-Elgg40vIQtLyqq+v5MKRbuMsFXw=", - "dev": true, - "requires": { - "core-util-is": "1.0.2", - "inherits": "2.0.3", - "isarray": "0.0.1", - "string_decoder": "0.10.31" - } - }, - "through2": { - "version": "0.6.5", - "resolved": "https://registry.npmjs.org/through2/-/through2-0.6.5.tgz", - "integrity": "sha1-QaucZ7KdVyCQcUEOHXp6lozTrUg=", - "dev": true, - "requires": { - "readable-stream": "1.0.34", - "xtend": "4.0.1" - } - }, - "vinyl": { - "version": "0.4.6", - "resolved": "https://registry.npmjs.org/vinyl/-/vinyl-0.4.6.tgz", - "integrity": "sha1-LzVsh6VQolVGHza76ypbqL94SEc=", - "dev": true, - "requires": { - "clone": "0.2.0", - "clone-stats": "0.0.1" - } - } - } - }, - "vinyl-source-stream": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/vinyl-source-stream/-/vinyl-source-stream-1.1.0.tgz", - "integrity": "sha1-RMvlEIIFJ53rDFZTwJSiiHk4sas=", - "dev": true, - "requires": { - "through2": "0.6.5", - "vinyl": "0.4.6" - }, - "dependencies": { - "clone": { - "version": "0.2.0", - "resolved": "https://registry.npmjs.org/clone/-/clone-0.2.0.tgz", - "integrity": "sha1-xhJqkK1Pctv1rNskPMN3JP6T/B8=", - "dev": true - }, - "readable-stream": { - "version": "1.0.34", - "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-1.0.34.tgz", - "integrity": "sha1-Elgg40vIQtLyqq+v5MKRbuMsFXw=", - "dev": true, - "requires": { - "core-util-is": "1.0.2", - "inherits": "2.0.3", - "isarray": "0.0.1", - "string_decoder": "0.10.31" - } - }, - "through2": { - "version": "0.6.5", - "resolved": "https://registry.npmjs.org/through2/-/through2-0.6.5.tgz", - "integrity": "sha1-QaucZ7KdVyCQcUEOHXp6lozTrUg=", - "dev": true, - "requires": { - "readable-stream": "1.0.34", - "xtend": "4.0.1" - } - }, - "vinyl": { - "version": "0.4.6", - "resolved": "https://registry.npmjs.org/vinyl/-/vinyl-0.4.6.tgz", - "integrity": "sha1-LzVsh6VQolVGHza76ypbqL94SEc=", - "dev": true, - "requires": { - "clone": "0.2.0", - "clone-stats": "0.0.1" - } - } - } - }, - "vinyl-sourcemaps-apply": { - "version": "0.2.1", - "resolved": "https://registry.npmjs.org/vinyl-sourcemaps-apply/-/vinyl-sourcemaps-apply-0.2.1.tgz", - "integrity": "sha1-q2VJ1h0XLCsbh75cUI0jnI74dwU=", - "dev": true, - "requires": { - "source-map": "0.5.7" - }, - "dependencies": { - "source-map": { - "version": "0.5.7", - "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.5.7.tgz", - "integrity": "sha1-igOdLRAh0i0eoUyA2OpGi6LvP8w=", - "dev": true - } - } - }, - "vsce": { - "version": "1.33.2", - "resolved": "https://registry.npmjs.org/vsce/-/vsce-1.33.2.tgz", - "integrity": "sha1-NkX2mq+YTiL3TqSdNfON0Y1m/18=", - "dev": true, - "requires": { - "cheerio": "1.0.0-rc.2", - "commander": "2.11.0", - "denodeify": "1.2.1", - "glob": "7.1.2", - "lodash": "4.17.4", - "markdown-it": "8.4.0", - "mime": "1.5.0", - "minimatch": "3.0.4", - "osenv": "0.1.4", - "parse-semver": "1.1.1", - "read": "1.0.7", - "semver": "5.4.1", - "tmp": "0.0.29", - "url-join": "1.1.0", - "vso-node-api": "6.1.2-preview", - "yauzl": "2.9.1", - "yazl": "2.4.3" - }, - "dependencies": { - "lodash": { - "version": "4.17.4", - "resolved": "https://registry.npmjs.org/lodash/-/lodash-4.17.4.tgz", - "integrity": "sha1-eCA6TRwyiuHYbcpkYONptX9AVa4=", - "dev": true - }, - "semver": { - "version": "5.4.1", - "resolved": "https://registry.npmjs.org/semver/-/semver-5.4.1.tgz", - "integrity": "sha512-WfG/X9+oATh81XtllIo/I8gOiY9EXRdv1cQdyykeXK17YcUW3EXUAi2To4pcH6nZtJPr7ZOpM5OMyWJZm+8Rsg==", - "dev": true - } - } - }, - "vscode": { - "version": "1.1.8", - "resolved": "https://registry.npmjs.org/vscode/-/vscode-1.1.8.tgz", - "integrity": "sha512-kT6sIA1AEKR5M+us2fXk5dxwV9SR/IEdLHNmVW4/dl1wNBHoEvgIo1qMQwHNxPVTQmw70KTGZ9UVeVb8FbpNFA==", - "dev": true, - "requires": { - "glob": "7.1.2", - "gulp-chmod": "2.0.0", - "gulp-filter": "5.0.1", - "gulp-gunzip": "1.0.0", - "gulp-remote-src": "0.4.3", - "gulp-symdest": "1.1.0", - "gulp-untar": "0.0.6", - "gulp-vinyl-zip": "2.1.0", - "mocha": "4.0.1", - "request": "2.83.0", - "semver": "5.4.1", - "source-map-support": "0.5.0", - "url-parse": "1.2.0", - "vinyl-source-stream": "1.1.0" - }, - "dependencies": { - "semver": { - "version": "5.4.1", - "resolved": "https://registry.npmjs.org/semver/-/semver-5.4.1.tgz", - "integrity": "sha512-WfG/X9+oATh81XtllIo/I8gOiY9EXRdv1cQdyykeXK17YcUW3EXUAi2To4pcH6nZtJPr7ZOpM5OMyWJZm+8Rsg==", - "dev": true - } - } - }, - "vscode-debugadapter": { - "version": "1.25.0", - "resolved": "https://registry.npmjs.org/vscode-debugadapter/-/vscode-debugadapter-1.25.0.tgz", - "integrity": "sha512-tsOtNNKKTbnQanARdkFfUxI8qKVKba+QHOKWC1reDDeeyvzoNKkLMGkL/xsiKn5vQDeaP3zFBcLY8Ysak9GrvQ==", - "requires": { - "vscode-debugprotocol": "1.25.0" - } - }, - "vscode-debugadapter-testsupport": { - "version": "1.25.0", - "resolved": "https://registry.npmjs.org/vscode-debugadapter-testsupport/-/vscode-debugadapter-testsupport-1.25.0.tgz", - "integrity": "sha512-6E2N7CoH7B0KEDvI9mFVFt4H+dRFDhtj3PmLVjNojfZ1VZZS2yfhE0XO0E5Axdhef3zTpUU6WZoeOOMVFGZGIg==", - "dev": true, - "requires": { - "vscode-debugprotocol": "1.25.0" - } - }, - "vscode-debugprotocol": { - "version": "1.25.0", - "resolved": "https://registry.npmjs.org/vscode-debugprotocol/-/vscode-debugprotocol-1.25.0.tgz", - "integrity": "sha512-e1EUy/5npqa0NlAwRCUu8A9LnVRf6tkwiPQcCLyUFCC9o2GxcAqH5Va4mqXDoxQ58ar3zODivKQeRb3z1KH7WA==" - }, - "vscode-nls": { - "version": "2.0.2", - "resolved": "https://registry.npmjs.org/vscode-nls/-/vscode-nls-2.0.2.tgz", - "integrity": "sha1-gIUiOAhEuK0VNJmvXDsDkhrqAto=" - }, - "vscode-nls-dev": { - "version": "2.1.6", - "resolved": "https://registry.npmjs.org/vscode-nls-dev/-/vscode-nls-dev-2.1.6.tgz", - "integrity": "sha512-1IylC/ekENYqz1vEItfrzrMXS8LW9aZQnNTU6BfdwT0Jddzed+l+nvU8amgVKFFmC1/GoiMFk5wtC20zWBbEbw==", - "dev": true, - "requires": { - "clone": "1.0.3", - "event-stream": "3.3.4", - "glob": "6.0.4", - "gulp-util": "3.0.8", - "iconv-lite": "0.4.19", - "is": "3.2.1", - "source-map": "0.5.7", - "typescript": "2.6.1", - "vinyl": "1.2.0", - "xml2js": "0.4.19", - "yargs": "3.32.0" - }, - "dependencies": { - "camelcase": { - "version": "2.1.1", - "resolved": "https://registry.npmjs.org/camelcase/-/camelcase-2.1.1.tgz", - "integrity": "sha1-fB0W1nmhu+WcoCys7PsBHiAfWh8=", - "dev": true - }, - "cliui": { - "version": "3.2.0", - "resolved": "https://registry.npmjs.org/cliui/-/cliui-3.2.0.tgz", - "integrity": "sha1-EgYBU3qRbSmUD5NNo7SNWFo5IT0=", - "dev": true, - "requires": { - "string-width": "1.0.2", - "strip-ansi": "3.0.1", - "wrap-ansi": "2.1.0" - } - }, - "glob": { - "version": "6.0.4", - "resolved": "https://registry.npmjs.org/glob/-/glob-6.0.4.tgz", - "integrity": "sha1-DwiGD2oVUSey+t1PnOJLGqtuTSI=", - "dev": true, - "requires": { - "inflight": "1.0.6", - "inherits": "2.0.3", - "minimatch": "3.0.4", - "once": "1.4.0", - "path-is-absolute": "1.0.1" - } - }, - "is-fullwidth-code-point": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/is-fullwidth-code-point/-/is-fullwidth-code-point-1.0.0.tgz", - "integrity": "sha1-754xOG8DGn8NZDr4L95QxFfvAMs=", - "dev": true, - "requires": { - "number-is-nan": "1.0.1" - } - }, - "source-map": { - "version": "0.5.7", - "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.5.7.tgz", - "integrity": "sha1-igOdLRAh0i0eoUyA2OpGi6LvP8w=", - "dev": true - }, - "string-width": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/string-width/-/string-width-1.0.2.tgz", - "integrity": "sha1-EYvfW4zcUaKn5w0hHgfisLmxB9M=", - "dev": true, - "requires": { - "code-point-at": "1.1.0", - "is-fullwidth-code-point": "1.0.0", - "strip-ansi": "3.0.1" - } - }, - "vinyl": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/vinyl/-/vinyl-1.2.0.tgz", - "integrity": "sha1-XIgDbPVl5d8FVYv8kR+GVt8hiIQ=", - "dev": true, - "requires": { - "clone": "1.0.3", - "clone-stats": "0.0.1", - "replace-ext": "0.0.1" - } - }, - "window-size": { - "version": "0.1.4", - "resolved": "https://registry.npmjs.org/window-size/-/window-size-0.1.4.tgz", - "integrity": "sha1-+OGqHuWlPsW/FR/6CXQqatdpeHY=", - "dev": true - }, - "yargs": { - "version": "3.32.0", - "resolved": "https://registry.npmjs.org/yargs/-/yargs-3.32.0.tgz", - "integrity": "sha1-AwiOnr+edWtpdRYR0qXvWRSCyZU=", - "dev": true, - "requires": { - "camelcase": "2.1.1", - "cliui": "3.2.0", - "decamelize": "1.2.0", - "os-locale": "1.4.0", - "string-width": "1.0.2", - "window-size": "0.1.4", - "y18n": "3.2.1" - } - } - } - }, - "vso-node-api": { - "version": "6.1.2-preview", - "resolved": "https://registry.npmjs.org/vso-node-api/-/vso-node-api-6.1.2-preview.tgz", - "integrity": "sha1-qrNUbfJFHs2JTgcbuZtd8Zxfp48=", - "dev": true, - "requires": { - "q": "1.5.1", - "tunnel": "0.0.4", - "typed-rest-client": "0.9.0", - "underscore": "1.8.3" - } - }, - "which": { - "version": "1.3.0", - "resolved": "https://registry.npmjs.org/which/-/which-1.3.0.tgz", - "integrity": "sha512-xcJpopdamTuY5duC/KnTTNBraPK54YwpenP4lzxU8H91GudWpFv38u0CKjclE1Wi2EH2EDz5LRcHcKbCIzqGyg==", - "dev": true, - "requires": { - "isexe": "2.0.0" - } - }, - "widest-line": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/widest-line/-/widest-line-1.0.0.tgz", - "integrity": "sha1-DAnIXCqUaD0Nfq+O4JfVZL8OEFw=", - "dev": true, - "requires": { - "string-width": "1.0.2" - }, - "dependencies": { - "is-fullwidth-code-point": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/is-fullwidth-code-point/-/is-fullwidth-code-point-1.0.0.tgz", - "integrity": "sha1-754xOG8DGn8NZDr4L95QxFfvAMs=", - "dev": true, - "requires": { - "number-is-nan": "1.0.1" - } - }, - "string-width": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/string-width/-/string-width-1.0.2.tgz", - "integrity": "sha1-EYvfW4zcUaKn5w0hHgfisLmxB9M=", - "dev": true, - "requires": { - "code-point-at": "1.1.0", - "is-fullwidth-code-point": "1.0.0", - "strip-ansi": "3.0.1" - } - } - } - }, - "window-size": { - "version": "0.1.0", - "resolved": "https://registry.npmjs.org/window-size/-/window-size-0.1.0.tgz", - "integrity": "sha1-VDjNLqk7IC76Ohn+iIeu58lPnJ0=", - "dev": true - }, - "wordwrap": { - "version": "0.0.2", - "resolved": "https://registry.npmjs.org/wordwrap/-/wordwrap-0.0.2.tgz", - "integrity": "sha1-t5Zpu0LstAn4PVg8rVLKF+qhZD8=", - "dev": true - }, - "wrap-ansi": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/wrap-ansi/-/wrap-ansi-2.1.0.tgz", - "integrity": "sha1-2Pw9KE3QV5T+hJc8rs3Rz4JP3YU=", - "dev": true, - "requires": { - "string-width": "1.0.2", - "strip-ansi": "3.0.1" - }, - "dependencies": { - "is-fullwidth-code-point": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/is-fullwidth-code-point/-/is-fullwidth-code-point-1.0.0.tgz", - "integrity": "sha1-754xOG8DGn8NZDr4L95QxFfvAMs=", - "dev": true, - "requires": { - "number-is-nan": "1.0.1" - } - }, - "string-width": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/string-width/-/string-width-1.0.2.tgz", - "integrity": "sha1-EYvfW4zcUaKn5w0hHgfisLmxB9M=", - "dev": true, - "requires": { - "code-point-at": "1.1.0", - "is-fullwidth-code-point": "1.0.0", - "strip-ansi": "3.0.1" - } - } - } - }, - "wrappy": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/wrappy/-/wrappy-1.0.2.tgz", - "integrity": "sha1-tSQ9jz7BqjXxNkYFvA0QNuMKtp8=" - }, - "write-file-atomic": { - "version": "2.3.0", - "resolved": "https://registry.npmjs.org/write-file-atomic/-/write-file-atomic-2.3.0.tgz", - "integrity": "sha512-xuPeK4OdjWqtfi59ylvVL0Yn35SF3zgcAcv7rBPFHVaEapaDr4GdGgm3j7ckTwH9wHL7fGmgfAnb0+THrHb8tA==", - "dev": true, - "requires": { - "graceful-fs": "4.1.11", - "imurmurhash": "0.1.4", - "signal-exit": "3.0.2" - }, - "dependencies": { - "graceful-fs": { - "version": "4.1.11", - "resolved": "https://registry.npmjs.org/graceful-fs/-/graceful-fs-4.1.11.tgz", - "integrity": "sha1-Dovf5NHduIVNZOBOp8AOKgJuVlg=", - "dev": true - } - } - }, - "xdg-basedir": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/xdg-basedir/-/xdg-basedir-3.0.0.tgz", - "integrity": "sha1-SWsswQnsqNus/i3HK2A8F8WHCtQ=", - "dev": true - }, - "xml2js": { - "version": "0.4.19", - "resolved": "https://registry.npmjs.org/xml2js/-/xml2js-0.4.19.tgz", - "integrity": "sha512-esZnJZJOiJR9wWKMyuvSE1y6Dq5LCuJanqhxslH2bxM6duahNZ+HMpCLhBQGZkbX6xRf8x1Y2eJlgt2q3qo49Q==", - "dev": true, - "requires": { - "sax": "1.2.4", - "xmlbuilder": "9.0.4" - } - }, - "xmlbuilder": { - "version": "9.0.4", - "resolved": "https://registry.npmjs.org/xmlbuilder/-/xmlbuilder-9.0.4.tgz", - "integrity": "sha1-UZy0ymhtAFqEINNJbz8MruzKWA8=", - "dev": true - }, - "xtend": { - "version": "4.0.1", - "resolved": "https://registry.npmjs.org/xtend/-/xtend-4.0.1.tgz", - "integrity": "sha1-pcbVMr5lbiPbgg77lDofBJmNY68=", - "dev": true - }, - "y18n": { - "version": "3.2.1", - "resolved": "https://registry.npmjs.org/y18n/-/y18n-3.2.1.tgz", - "integrity": "sha1-bRX7qITAhnnA136I53WegR4H+kE=", - "dev": true - }, - "yallist": { - "version": "2.1.2", - "resolved": "https://registry.npmjs.org/yallist/-/yallist-2.1.2.tgz", - "integrity": "sha1-HBH5IY8HYImkfdUS+TxmmaaoHVI=", - "dev": true - }, - "yargs": { - "version": "3.10.0", - "resolved": "https://registry.npmjs.org/yargs/-/yargs-3.10.0.tgz", - "integrity": "sha1-9+572FfdfB0tOMDnTvvWgdFDH9E=", - "dev": true, - "requires": { - "camelcase": "1.2.1", - "cliui": "2.1.0", - "decamelize": "1.2.0", - "window-size": "0.1.0" - } - }, - "yauzl": { - "version": "2.9.1", - "resolved": "https://registry.npmjs.org/yauzl/-/yauzl-2.9.1.tgz", - "integrity": "sha1-qBmB6nCleUYTOIPwKcWCGok1mn8=", - "dev": true, - "requires": { - "buffer-crc32": "0.2.13", - "fd-slicer": "1.0.1" - } - }, - "yazl": { - "version": "2.4.3", - "resolved": "https://registry.npmjs.org/yazl/-/yazl-2.4.3.tgz", - "integrity": "sha1-7CblzIfVYBud+EMtvdPNLlFzoHE=", - "dev": true, - "requires": { - "buffer-crc32": "0.2.13" - } - } - } -} diff --git a/extensions/ms-vscode.node-debug/package.json b/extensions/ms-vscode.node-debug/package.json deleted file mode 100644 index 9d065dd4a5c..00000000000 --- a/extensions/ms-vscode.node-debug/package.json +++ /dev/null @@ -1,8 +0,0 @@ -{ - "name": "node-debug", - "version": "1.6.0", - "publisher": "ms-vscode", - "engines": { - "vscode": "1.6.x" - } -} \ No newline at end of file diff --git a/extensions/ms-vscode.node-debug2/package-lock.json b/extensions/ms-vscode.node-debug2/package-lock.json deleted file mode 100644 index 7f8ba502cc4..00000000000 --- a/extensions/ms-vscode.node-debug2/package-lock.json +++ /dev/null @@ -1,5106 +0,0 @@ -{ - "name": "node-debug2", - "version": "1.19.0", - "lockfileVersion": 1, - "requires": true, - "dependencies": { - "@gulp-sourcemaps/identity-map": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/@gulp-sourcemaps/identity-map/-/identity-map-1.0.1.tgz", - "integrity": "sha1-z6I7xYQPkQTOMqZedNt+epdLvuE=", - "dev": true, - "requires": { - "acorn": "https://registry.npmjs.org/acorn/-/acorn-5.2.1.tgz", - "css": "2.2.1", - "normalize-path": "2.1.1", - "source-map": "https://registry.npmjs.org/source-map/-/source-map-0.5.6.tgz", - "through2": "2.0.3" - }, - "dependencies": { - "acorn": { - "version": "https://registry.npmjs.org/acorn/-/acorn-5.2.1.tgz", - "integrity": "sha1-MXrHghgmwixwLWYYmrg1lnXxNdc=", - "dev": true - } - } - }, - "@gulp-sourcemaps/map-sources": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/@gulp-sourcemaps/map-sources/-/map-sources-1.0.0.tgz", - "integrity": "sha1-iQrnxdjId/bThIYCFazp1+yUW9o=", - "dev": true, - "requires": { - "normalize-path": "2.1.1", - "through2": "2.0.3" - } - }, - "@types/mocha": { - "version": "2.2.44", - "resolved": "https://registry.npmjs.org/@types/mocha/-/mocha-2.2.44.tgz", - "integrity": "sha512-k2tWTQU8G4+iSMvqKi0Q9IIsWAp/n8xzdZS4Q4YVIltApoMA00wFBFdlJnmoaK1/z7B0Cy0yPe6GgXteSmdUNw==", - "dev": true - }, - "@types/node": { - "version": "6.0.92", - "resolved": "https://registry.npmjs.org/@types/node/-/node-6.0.92.tgz", - "integrity": "sha512-awEYSSTn7dauwVCYSx2CJaPTu0Z1Ht2oR1b2AD3CYao6ZRb+opb6EL43fzmD7eMFgMHzTBWSUzlWSD+S8xN0Nw==", - "dev": true - }, - "@types/source-map": { - "version": "https://registry.npmjs.org/@types/source-map/-/source-map-0.1.29.tgz", - "integrity": "sha1-1wSKYBgLCfiqbVO9oxHGtRy9cBg=" - }, - "acorn": { - "version": "4.0.13", - "resolved": "https://registry.npmjs.org/acorn/-/acorn-4.0.13.tgz", - "integrity": "sha1-EFSVrlNh1pe9GVyCUZLhrX8lN4c=", - "dev": true - }, - "agent-base": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/agent-base/-/agent-base-1.0.2.tgz", - "integrity": "sha1-aJDT+yFwBLYrcPiSjg+uX4lSpwY=" - }, - "ajv": { - "version": "5.5.0", - "resolved": "https://registry.npmjs.org/ajv/-/ajv-5.5.0.tgz", - "integrity": "sha1-6yhAdG6dxIvV4GOjbj/UAMXqtak=", - "dev": true, - "requires": { - "co": "4.6.0", - "fast-deep-equal": "1.0.0", - "fast-json-stable-stringify": "2.0.0", - "json-schema-traverse": "0.3.1" - } - }, - "amdefine": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/amdefine/-/amdefine-1.0.1.tgz", - "integrity": "sha1-SlKCrBZHKek2Gbz9OtFR+BfOkfU=", - "dev": true - }, - "ansi-regex": { - "version": "2.1.1", - "resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-2.1.1.tgz", - "integrity": "sha1-w7M6te42DYbg5ijwRorn7yfWVN8=", - "dev": true - }, - "ansi-styles": { - "version": "2.2.1", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-2.2.1.tgz", - "integrity": "sha1-tDLdM1i2NM914eRmQ2gkBTPB3b4=", - "dev": true - }, - "archy": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/archy/-/archy-1.0.0.tgz", - "integrity": "sha1-+cjBN1fMHde8N5rHeyxipcKGjEA=", - "dev": true - }, - "argparse": { - "version": "1.0.9", - "resolved": "https://registry.npmjs.org/argparse/-/argparse-1.0.9.tgz", - "integrity": "sha1-c9g7wmP4bpf4zE9rrhsOkKfSLIY=", - "dev": true, - "requires": { - "sprintf-js": "1.0.3" - } - }, - "arr-diff": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/arr-diff/-/arr-diff-2.0.0.tgz", - "integrity": "sha1-jzuCf5Vai9ZpaX5KQlasPOrjVs8=", - "dev": true, - "requires": { - "arr-flatten": "https://registry.npmjs.org/arr-flatten/-/arr-flatten-1.1.0.tgz" - } - }, - "arr-flatten": { - "version": "https://registry.npmjs.org/arr-flatten/-/arr-flatten-1.1.0.tgz", - "integrity": "sha1-NgSLv/TntH4TZkQxbJlmnqWukfE=", - "dev": true - }, - "array-differ": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/array-differ/-/array-differ-1.0.0.tgz", - "integrity": "sha1-7/UuN1gknTO+QCuLuOVkuytdQDE=", - "dev": true - }, - "array-each": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/array-each/-/array-each-1.0.1.tgz", - "integrity": "sha1-p5SvDAWrF1KEbudTofIRoFugxE8=", - "dev": true - }, - "array-slice": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/array-slice/-/array-slice-1.0.0.tgz", - "integrity": "sha1-5zA08A3MH0CHYAj9IP6ud71LfC8=", - "dev": true - }, - "array-union": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/array-union/-/array-union-1.0.2.tgz", - "integrity": "sha1-mjRBDk9OPaI96jdb5b5w8kd47Dk=", - "dev": true, - "requires": { - "array-uniq": "1.0.3" - } - }, - "array-uniq": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/array-uniq/-/array-uniq-1.0.3.tgz", - "integrity": "sha1-r2rId6Jcx/dOBYiUdThY39sk/bY=", - "dev": true - }, - "array-unique": { - "version": "0.2.1", - "resolved": "https://registry.npmjs.org/array-unique/-/array-unique-0.2.1.tgz", - "integrity": "sha1-odl8yvy8JiXMcPrc6zalDFiwGlM=", - "dev": true - }, - "arrify": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/arrify/-/arrify-1.0.1.tgz", - "integrity": "sha1-iYUI2iIm84DfkEcoRWhJwVAaSw0=", - "dev": true - }, - "asn1": { - "version": "0.2.3", - "resolved": "https://registry.npmjs.org/asn1/-/asn1-0.2.3.tgz", - "integrity": "sha1-2sh4dxPJlmhJ/IGAd36+nB3fO4Y=", - "dev": true - }, - "assert-plus": { - "version": "0.2.0", - "resolved": "https://registry.npmjs.org/assert-plus/-/assert-plus-0.2.0.tgz", - "integrity": "sha1-104bh+ev/A24qttwIfP+SBAasjQ=", - "dev": true - }, - "asynckit": { - "version": "0.4.0", - "resolved": "https://registry.npmjs.org/asynckit/-/asynckit-0.4.0.tgz", - "integrity": "sha1-x57Zf380y48robyXkLzDZkdLS3k=", - "dev": true - }, - "atob": { - "version": "1.1.3", - "resolved": "https://registry.npmjs.org/atob/-/atob-1.1.3.tgz", - "integrity": "sha1-lfE2KbEsOlGl0hWr3OKqnzL4B3M=", - "dev": true - }, - "aws-sign2": { - "version": "0.6.0", - "resolved": "https://registry.npmjs.org/aws-sign2/-/aws-sign2-0.6.0.tgz", - "integrity": "sha1-FDQt0428yU0OW4fXY81jYSwOeU8=", - "dev": true - }, - "aws4": { - "version": "1.6.0", - "resolved": "https://registry.npmjs.org/aws4/-/aws4-1.6.0.tgz", - "integrity": "sha1-g+9cqGCysy5KDe7e6MdxudtXRx4=", - "dev": true - }, - "babel-code-frame": { - "version": "6.26.0", - "resolved": "https://registry.npmjs.org/babel-code-frame/-/babel-code-frame-6.26.0.tgz", - "integrity": "sha1-Y/1D99weO7fONZR9uP42mj9Yx0s=", - "dev": true, - "requires": { - "chalk": "1.1.3", - "esutils": "2.0.2", - "js-tokens": "3.0.2" - } - }, - "balanced-match": { - "version": "https://registry.npmjs.org/balanced-match/-/balanced-match-1.0.0.tgz", - "integrity": "sha1-ibTRmasr7kneFk6gK4nORi1xt2c=" - }, - "bcrypt-pbkdf": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/bcrypt-pbkdf/-/bcrypt-pbkdf-1.0.1.tgz", - "integrity": "sha1-Y7xdy2EzG5K8Bf1SiVPDNGKgb40=", - "dev": true, - "optional": true, - "requires": { - "tweetnacl": "0.14.5" - } - }, - "beeper": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/beeper/-/beeper-1.1.1.tgz", - "integrity": "sha1-5tXqjF2tABMEpwsiY4RH9pyy+Ak=", - "dev": true - }, - "block-stream": { - "version": "0.0.9", - "resolved": "https://registry.npmjs.org/block-stream/-/block-stream-0.0.9.tgz", - "integrity": "sha1-E+v+d4oDIFz+A3UUgeu0szAMEmo=", - "dev": true, - "requires": { - "inherits": "https://registry.npmjs.org/inherits/-/inherits-2.0.3.tgz" - } - }, - "boolbase": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/boolbase/-/boolbase-1.0.0.tgz", - "integrity": "sha1-aN/1++YMUes3cl6p4+0xDcwed24=", - "dev": true - }, - "boom": { - "version": "2.10.1", - "resolved": "https://registry.npmjs.org/boom/-/boom-2.10.1.tgz", - "integrity": "sha1-OciRjO/1eZ+D+UkqhI9iWt0Mdm8=", - "dev": true, - "requires": { - "hoek": "2.16.3" - } - }, - "brace-expansion": { - "version": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-1.1.8.tgz", - "integrity": "sha1-wHshHHyVLsH479Uad+8NHTmQopI=", - "requires": { - "balanced-match": "https://registry.npmjs.org/balanced-match/-/balanced-match-1.0.0.tgz", - "concat-map": "https://registry.npmjs.org/concat-map/-/concat-map-0.0.1.tgz" - } - }, - "braces": { - "version": "1.8.5", - "resolved": "https://registry.npmjs.org/braces/-/braces-1.8.5.tgz", - "integrity": "sha1-uneWLhLf+WnWt2cR6RS3N4V79qc=", - "dev": true, - "requires": { - "expand-range": "1.8.2", - "preserve": "0.2.0", - "repeat-element": "1.1.2" - } - }, - "browser-stdout": { - "version": "1.3.0", - "resolved": "https://registry.npmjs.org/browser-stdout/-/browser-stdout-1.3.0.tgz", - "integrity": "sha1-81HTKWnTL6XXpVZxVCY9korjvR8=", - "dev": true - }, - "buffer-crc32": { - "version": "0.2.13", - "resolved": "https://registry.npmjs.org/buffer-crc32/-/buffer-crc32-0.2.13.tgz", - "integrity": "sha1-DTM+PwDqxQqhRUq9MO+MKl2ackI=", - "dev": true - }, - "builtin-modules": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/builtin-modules/-/builtin-modules-1.1.1.tgz", - "integrity": "sha1-Jw8HbFpywC9bZaR9+Uxf46J4iS8=", - "dev": true - }, - "camelcase": { - "version": "2.1.1", - "resolved": "https://registry.npmjs.org/camelcase/-/camelcase-2.1.1.tgz", - "integrity": "sha1-fB0W1nmhu+WcoCys7PsBHiAfWh8=", - "dev": true - }, - "caseless": { - "version": "0.11.0", - "resolved": "https://registry.npmjs.org/caseless/-/caseless-0.11.0.tgz", - "integrity": "sha1-cVuW6phBWTzDMGeSP17GDr2k99c=", - "dev": true - }, - "chalk": { - "version": "1.1.3", - "resolved": "https://registry.npmjs.org/chalk/-/chalk-1.1.3.tgz", - "integrity": "sha1-qBFcVeSnAv5NFQq9OHKCKn4J/Jg=", - "dev": true, - "requires": { - "ansi-styles": "2.2.1", - "escape-string-regexp": "1.0.5", - "has-ansi": "2.0.0", - "strip-ansi": "3.0.1", - "supports-color": "2.0.0" - } - }, - "cheerio": { - "version": "1.0.0-rc.2", - "resolved": "https://registry.npmjs.org/cheerio/-/cheerio-1.0.0-rc.2.tgz", - "integrity": "sha1-S59TqBsn5NXawxwP/Qz6A8xoMNs=", - "dev": true, - "requires": { - "css-select": "1.2.0", - "dom-serializer": "0.1.0", - "entities": "1.1.1", - "htmlparser2": "3.9.2", - "lodash": "4.17.4", - "parse5": "https://registry.npmjs.org/parse5/-/parse5-3.0.3.tgz" - }, - "dependencies": { - "lodash": { - "version": "4.17.4", - "resolved": "https://registry.npmjs.org/lodash/-/lodash-4.17.4.tgz", - "integrity": "sha1-eCA6TRwyiuHYbcpkYONptX9AVa4=", - "dev": true - } - } - }, - "cliui": { - "version": "3.2.0", - "resolved": "https://registry.npmjs.org/cliui/-/cliui-3.2.0.tgz", - "integrity": "sha1-EgYBU3qRbSmUD5NNo7SNWFo5IT0=", - "dev": true, - "requires": { - "string-width": "1.0.2", - "strip-ansi": "3.0.1", - "wrap-ansi": "2.1.0" - } - }, - "clone": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/clone/-/clone-1.0.3.tgz", - "integrity": "sha1-KY1+IjFmD0DAA8LtMUDezz9TCF8=", - "dev": true - }, - "clone-buffer": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/clone-buffer/-/clone-buffer-1.0.0.tgz", - "integrity": "sha1-4+JbIHrE5wGvch4staFnksrD3Fg=", - "dev": true - }, - "clone-stats": { - "version": "0.0.1", - "resolved": "https://registry.npmjs.org/clone-stats/-/clone-stats-0.0.1.tgz", - "integrity": "sha1-uI+UqCzzi4eR1YBG6kAprYjKmdE=", - "dev": true - }, - "cloneable-readable": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/cloneable-readable/-/cloneable-readable-1.0.0.tgz", - "integrity": "sha1-pikNQT8hemEjL5XkWP84QYz7ARc=", - "dev": true, - "requires": { - "inherits": "https://registry.npmjs.org/inherits/-/inherits-2.0.3.tgz", - "process-nextick-args": "1.0.7", - "through2": "2.0.3" - } - }, - "co": { - "version": "4.6.0", - "resolved": "https://registry.npmjs.org/co/-/co-4.6.0.tgz", - "integrity": "sha1-bqa989hTrlTMuOR7+gvz+QMfsYQ=", - "dev": true - }, - "code-point-at": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/code-point-at/-/code-point-at-1.1.0.tgz", - "integrity": "sha1-DQcLTQQ6W+ozovGkDi7bPZpMz3c=", - "dev": true - }, - "color-convert": { - "version": "1.9.1", - "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-1.9.1.tgz", - "integrity": "sha512-mjGanIiwQJskCC18rPR6OmrZ6fm2Lc7PeGFYwCmy5J34wC6F1PzdGL6xeMfmgicfYcNLGuVFA3WzXtIDCQSZxQ==", - "dev": true, - "requires": { - "color-name": "1.1.3" - } - }, - "color-name": { - "version": "1.1.3", - "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.3.tgz", - "integrity": "sha1-p9BVi9icQveV3UIyj3QIMcpTvCU=", - "dev": true - }, - "combined-stream": { - "version": "1.0.5", - "resolved": "https://registry.npmjs.org/combined-stream/-/combined-stream-1.0.5.tgz", - "integrity": "sha1-k4NwpXtKUd6ix3wV1cX9+JUWQAk=", - "dev": true, - "requires": { - "delayed-stream": "1.0.0" - } - }, - "commander": { - "version": "2.9.0", - "resolved": "https://registry.npmjs.org/commander/-/commander-2.9.0.tgz", - "integrity": "sha1-nJkJQXbhIkDLItbFFGCYQA/g99Q=", - "dev": true, - "requires": { - "graceful-readlink": "1.0.1" - } - }, - "concat-map": { - "version": "https://registry.npmjs.org/concat-map/-/concat-map-0.0.1.tgz", - "integrity": "sha1-2Klr13/Wjfd5OnMDajug1UBdR3s=" - }, - "convert-source-map": { - "version": "1.5.1", - "resolved": "https://registry.npmjs.org/convert-source-map/-/convert-source-map-1.5.1.tgz", - "integrity": "sha1-uCeAl7m8IpNl3lxiz1/K7YtVmeU=", - "dev": true - }, - "core-util-is": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/core-util-is/-/core-util-is-1.0.2.tgz", - "integrity": "sha1-tf1UIgqivFq1eqtxQMlAdUUDwac=", - "dev": true - }, - "cryptiles": { - "version": "2.0.5", - "resolved": "https://registry.npmjs.org/cryptiles/-/cryptiles-2.0.5.tgz", - "integrity": "sha1-O9/s3GCBR8HGcgL6KR59ylnqo7g=", - "dev": true, - "requires": { - "boom": "2.10.1" - } - }, - "css": { - "version": "2.2.1", - "resolved": "https://registry.npmjs.org/css/-/css-2.2.1.tgz", - "integrity": "sha1-c6TIHehdtmTU7mdPfUcIXjstVdw=", - "dev": true, - "requires": { - "inherits": "https://registry.npmjs.org/inherits/-/inherits-2.0.3.tgz", - "source-map": "0.1.43", - "source-map-resolve": "0.3.1", - "urix": "0.1.0" - }, - "dependencies": { - "source-map": { - "version": "0.1.43", - "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.1.43.tgz", - "integrity": "sha1-wkvBRspRfBRx9drL4lcbK3+eM0Y=", - "dev": true, - "requires": { - "amdefine": "1.0.1" - } - } - } - }, - "css-select": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/css-select/-/css-select-1.2.0.tgz", - "integrity": "sha1-KzoRBTnFNV8c2NMUYj6HCxIeyFg=", - "dev": true, - "requires": { - "boolbase": "1.0.0", - "css-what": "2.1.0", - "domutils": "1.5.1", - "nth-check": "1.0.1" - } - }, - "css-what": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/css-what/-/css-what-2.1.0.tgz", - "integrity": "sha1-lGfQMsOM+u+58teVASUwYvh/ob0=", - "dev": true - }, - "d": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/d/-/d-1.0.0.tgz", - "integrity": "sha1-dUu1v+VUUdpppYuU1F9MWwRi1Y8=", - "dev": true, - "requires": { - "es5-ext": "0.10.37" - } - }, - "dashdash": { - "version": "1.14.1", - "resolved": "https://registry.npmjs.org/dashdash/-/dashdash-1.14.1.tgz", - "integrity": "sha1-hTz6D3y+L+1d4gMmuN1YEDX24vA=", - "dev": true, - "requires": { - "assert-plus": "1.0.0" - }, - "dependencies": { - "assert-plus": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/assert-plus/-/assert-plus-1.0.0.tgz", - "integrity": "sha1-8S4PPF13sLHN2RRpQuTpbB5N1SU=", - "dev": true - } - } - }, - "dateformat": { - "version": "2.2.0", - "resolved": "https://registry.npmjs.org/dateformat/-/dateformat-2.2.0.tgz", - "integrity": "sha1-QGXiATz5+5Ft39gu+1Bq1MZ2kGI=", - "dev": true - }, - "debug": { - "version": "https://registry.npmjs.org/debug/-/debug-2.6.8.tgz", - "integrity": "sha1-5zFTHKLt4n0YgiJCfaF4IdaP9Pw=", - "requires": { - "ms": "https://registry.npmjs.org/ms/-/ms-2.0.0.tgz" - } - }, - "debug-fabulous": { - "version": "https://registry.npmjs.org/debug-fabulous/-/debug-fabulous-0.2.1.tgz", - "integrity": "sha1-V+EWS6DprW2aZfIAdf88K9a94Nw=", - "dev": true, - "requires": { - "debug": "3.1.0", - "memoizee": "0.4.11", - "object-assign": "4.1.1" - }, - "dependencies": { - "debug": { - "version": "3.1.0", - "resolved": "https://registry.npmjs.org/debug/-/debug-3.1.0.tgz", - "integrity": "sha512-OX8XqP7/1a9cqkxYw2yXss15f26NKWBpDXQd0/uK/KPqdQhxbPa994hnzjcE2VqQpDslf55723cKPUOGSmMY3g==", - "dev": true, - "requires": { - "ms": "https://registry.npmjs.org/ms/-/ms-2.0.0.tgz" - } - } - } - }, - "decamelize": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/decamelize/-/decamelize-1.2.0.tgz", - "integrity": "sha1-9lNNFRSCabIDUue+4m9QH5oZEpA=", - "dev": true - }, - "deep-assign": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/deep-assign/-/deep-assign-1.0.0.tgz", - "integrity": "sha1-sJJ0O+hCfcYh6gBnzex+cN0Z83s=", - "dev": true, - "requires": { - "is-obj": "1.0.1" - } - }, - "defaults": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/defaults/-/defaults-1.0.3.tgz", - "integrity": "sha1-xlYFHpgX2f8I7YgUd/P+QBnz730=", - "dev": true, - "requires": { - "clone": "1.0.3" - } - }, - "del": { - "version": "2.2.2", - "resolved": "https://registry.npmjs.org/del/-/del-2.2.2.tgz", - "integrity": "sha1-wSyYHQZ4RshLyvhiz/kw2Qf/0ag=", - "dev": true, - "requires": { - "globby": "5.0.0", - "is-path-cwd": "1.0.0", - "is-path-in-cwd": "1.0.0", - "object-assign": "4.1.1", - "pify": "2.3.0", - "pinkie-promise": "2.0.1", - "rimraf": "https://registry.npmjs.org/rimraf/-/rimraf-2.6.2.tgz" - } - }, - "delayed-stream": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/delayed-stream/-/delayed-stream-1.0.0.tgz", - "integrity": "sha1-3zrhmayt+31ECqrgsp4icrJOxhk=", - "dev": true - }, - "denodeify": { - "version": "1.2.1", - "resolved": "https://registry.npmjs.org/denodeify/-/denodeify-1.2.1.tgz", - "integrity": "sha1-OjYof1A05pnnV3kBBSwubJQlFjE=", - "dev": true - }, - "deprecated": { - "version": "0.0.1", - "resolved": "https://registry.npmjs.org/deprecated/-/deprecated-0.0.1.tgz", - "integrity": "sha1-+cmvVGSvoeepcUWKi97yqpTVuxk=", - "dev": true - }, - "detect-file": { - "version": "0.1.0", - "resolved": "https://registry.npmjs.org/detect-file/-/detect-file-0.1.0.tgz", - "integrity": "sha1-STXe39lIhkjgBrASlWbpOGcR6mM=", - "dev": true, - "requires": { - "fs-exists-sync": "0.1.0" - } - }, - "detect-newline": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/detect-newline/-/detect-newline-2.1.0.tgz", - "integrity": "sha1-9B8cEL5LAOh7XxPaaAdZ8sW/0+I=", - "dev": true - }, - "diff": { - "version": "3.2.0", - "resolved": "https://registry.npmjs.org/diff/-/diff-3.2.0.tgz", - "integrity": "sha1-yc45Okt8vQsFinJck98pkCeGj/k=", - "dev": true - }, - "dom-serializer": { - "version": "0.1.0", - "resolved": "https://registry.npmjs.org/dom-serializer/-/dom-serializer-0.1.0.tgz", - "integrity": "sha1-BzxpdUbOB4DOI75KKOKT5AvDDII=", - "dev": true, - "requires": { - "domelementtype": "1.1.3", - "entities": "1.1.1" - }, - "dependencies": { - "domelementtype": { - "version": "1.1.3", - "resolved": "https://registry.npmjs.org/domelementtype/-/domelementtype-1.1.3.tgz", - "integrity": "sha1-vSh3PiZCiBrsUVRJJCmcXNgiGFs=", - "dev": true - } - } - }, - "domelementtype": { - "version": "1.3.0", - "resolved": "https://registry.npmjs.org/domelementtype/-/domelementtype-1.3.0.tgz", - "integrity": "sha1-sXrtguirWeUt2cGbF1bg/BhyBMI=", - "dev": true - }, - "domhandler": { - "version": "2.4.1", - "resolved": "https://registry.npmjs.org/domhandler/-/domhandler-2.4.1.tgz", - "integrity": "sha1-iS5HAAqZvlW783dP/qBWHYh5wlk=", - "dev": true, - "requires": { - "domelementtype": "1.3.0" - } - }, - "domutils": { - "version": "1.5.1", - "resolved": "https://registry.npmjs.org/domutils/-/domutils-1.5.1.tgz", - "integrity": "sha1-3NhIiib1Y9YQeeSMn3t+Mjc2gs8=", - "dev": true, - "requires": { - "dom-serializer": "0.1.0", - "domelementtype": "1.3.0" - } - }, - "duplexer": { - "version": "0.1.1", - "resolved": "https://registry.npmjs.org/duplexer/-/duplexer-0.1.1.tgz", - "integrity": "sha1-rOb/gIwc5mtX0ev5eXessCM0z8E=", - "dev": true - }, - "duplexer2": { - "version": "0.0.2", - "resolved": "https://registry.npmjs.org/duplexer2/-/duplexer2-0.0.2.tgz", - "integrity": "sha1-xhTc9n4vsUmVqRcR5aYX6KYKMds=", - "dev": true, - "requires": { - "readable-stream": "1.1.14" - } - }, - "duplexify": { - "version": "https://registry.npmjs.org/duplexify/-/duplexify-3.5.1.tgz", - "integrity": "sha1-ThUWvmiDi8kKSZlPCzmm5ZYL780=", - "dev": true, - "requires": { - "end-of-stream": "1.4.0", - "inherits": "https://registry.npmjs.org/inherits/-/inherits-2.0.3.tgz", - "readable-stream": "https://registry.npmjs.org/readable-stream/-/readable-stream-2.3.3.tgz", - "stream-shift": "1.0.0" - }, - "dependencies": { - "end-of-stream": { - "version": "1.4.0", - "resolved": "https://registry.npmjs.org/end-of-stream/-/end-of-stream-1.4.0.tgz", - "integrity": "sha1-epDYM+/abPpurA9JSduw+tOmMgY=", - "dev": true, - "requires": { - "once": "https://registry.npmjs.org/once/-/once-1.4.0.tgz" - } - }, - "isarray": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/isarray/-/isarray-1.0.0.tgz", - "integrity": "sha1-u5NdSFgsuhaMBoNJV6VKPgcSTxE=", - "dev": true - }, - "readable-stream": { - "version": "https://registry.npmjs.org/readable-stream/-/readable-stream-2.3.3.tgz", - "integrity": "sha1-No8lEtefnUb9/HE0mueHi7weuVw=", - "dev": true, - "requires": { - "core-util-is": "1.0.2", - "inherits": "https://registry.npmjs.org/inherits/-/inherits-2.0.3.tgz", - "isarray": "1.0.0", - "process-nextick-args": "1.0.7", - "safe-buffer": "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.1.1.tgz", - "string_decoder": "https://registry.npmjs.org/string_decoder/-/string_decoder-1.0.3.tgz", - "util-deprecate": "1.0.2" - } - }, - "string_decoder": { - "version": "https://registry.npmjs.org/string_decoder/-/string_decoder-1.0.3.tgz", - "integrity": "sha1-D8Z9fBQYJd6UKC3VNr7GubzoYKs=", - "dev": true, - "requires": { - "safe-buffer": "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.1.1.tgz" - } - } - } - }, - "ecc-jsbn": { - "version": "0.1.1", - "resolved": "https://registry.npmjs.org/ecc-jsbn/-/ecc-jsbn-0.1.1.tgz", - "integrity": "sha1-D8c6ntXw1Tw4GTOYUj735UN3dQU=", - "dev": true, - "optional": true, - "requires": { - "jsbn": "0.1.1" - } - }, - "end-of-stream": { - "version": "0.1.5", - "resolved": "https://registry.npmjs.org/end-of-stream/-/end-of-stream-0.1.5.tgz", - "integrity": "sha1-jhdyBsPICDfYVjLouTWd/osvbq8=", - "dev": true, - "requires": { - "once": "1.3.3" - }, - "dependencies": { - "once": { - "version": "1.3.3", - "resolved": "https://registry.npmjs.org/once/-/once-1.3.3.tgz", - "integrity": "sha1-suJhVXzkwxTsgwTz+oJmPkKXyiA=", - "dev": true, - "requires": { - "wrappy": "https://registry.npmjs.org/wrappy/-/wrappy-1.0.2.tgz" - } - } - } - }, - "entities": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/entities/-/entities-1.1.1.tgz", - "integrity": "sha1-blwtClYhtdra7O+AuQ7ftc13cvA=", - "dev": true - }, - "es5-ext": { - "version": "0.10.37", - "resolved": "https://registry.npmjs.org/es5-ext/-/es5-ext-0.10.37.tgz", - "integrity": "sha1-DudB0Ui4AGm6J9AgOTdWryV978M=", - "dev": true, - "requires": { - "es6-iterator": "2.0.3", - "es6-symbol": "3.1.1" - } - }, - "es6-iterator": { - "version": "2.0.3", - "resolved": "https://registry.npmjs.org/es6-iterator/-/es6-iterator-2.0.3.tgz", - "integrity": "sha1-p96IkUGgWpSwhUQDstCg+/qY87c=", - "dev": true, - "requires": { - "d": "1.0.0", - "es5-ext": "0.10.37", - "es6-symbol": "3.1.1" - } - }, - "es6-symbol": { - "version": "3.1.1", - "resolved": "https://registry.npmjs.org/es6-symbol/-/es6-symbol-3.1.1.tgz", - "integrity": "sha1-vwDvT9q2uhtG7Le2KbTH7VcVzHc=", - "dev": true, - "requires": { - "d": "1.0.0", - "es5-ext": "0.10.37" - } - }, - "es6-weak-map": { - "version": "2.0.2", - "resolved": "https://registry.npmjs.org/es6-weak-map/-/es6-weak-map-2.0.2.tgz", - "integrity": "sha1-XjqzIlH/0VOKH45f+hNXdy+S2W8=", - "dev": true, - "requires": { - "d": "1.0.0", - "es5-ext": "0.10.37", - "es6-iterator": "2.0.3", - "es6-symbol": "3.1.1" - } - }, - "escape-string-regexp": { - "version": "1.0.5", - "resolved": "https://registry.npmjs.org/escape-string-regexp/-/escape-string-regexp-1.0.5.tgz", - "integrity": "sha1-G2HAViGQqN/2rjuyzwIAyhMLhtQ=", - "dev": true - }, - "esutils": { - "version": "2.0.2", - "resolved": "https://registry.npmjs.org/esutils/-/esutils-2.0.2.tgz", - "integrity": "sha1-Cr9PHKpbyx96nYrMbepPqqBLrJs=", - "dev": true - }, - "event-emitter": { - "version": "0.3.5", - "resolved": "https://registry.npmjs.org/event-emitter/-/event-emitter-0.3.5.tgz", - "integrity": "sha1-34xp7vFkeSPHFXuc6DhAYQsCzDk=", - "dev": true, - "requires": { - "d": "1.0.0", - "es5-ext": "0.10.37" - } - }, - "event-stream": { - "version": "3.3.4", - "resolved": "https://registry.npmjs.org/event-stream/-/event-stream-3.3.4.tgz", - "integrity": "sha1-SrTJoPWlTbkzi0w02Gv86PSzVXE=", - "dev": true, - "requires": { - "duplexer": "0.1.1", - "from": "0.1.7", - "map-stream": "0.1.0", - "pause-stream": "0.0.11", - "split": "0.3.3", - "stream-combiner": "0.0.4", - "through": "2.3.8" - } - }, - "expand-brackets": { - "version": "0.1.5", - "resolved": "https://registry.npmjs.org/expand-brackets/-/expand-brackets-0.1.5.tgz", - "integrity": "sha1-3wcoTjQqgHzXM6xa9yQR5YHRF3s=", - "dev": true, - "requires": { - "is-posix-bracket": "0.1.1" - } - }, - "expand-range": { - "version": "1.8.2", - "resolved": "https://registry.npmjs.org/expand-range/-/expand-range-1.8.2.tgz", - "integrity": "sha1-opnv/TNf4nIeuujiV+x5ZE/IUzc=", - "dev": true, - "requires": { - "fill-range": "2.2.3" - } - }, - "expand-tilde": { - "version": "1.2.2", - "resolved": "https://registry.npmjs.org/expand-tilde/-/expand-tilde-1.2.2.tgz", - "integrity": "sha1-C4HrqJflo9MdHD0QL48BRB5VlEk=", - "dev": true, - "requires": { - "os-homedir": "1.0.2" - } - }, - "extend": { - "version": "https://registry.npmjs.org/extend/-/extend-3.0.1.tgz", - "integrity": "sha1-p1Xqe8Gt/MWjHOfnYtuq3F5jZEQ=" - }, - "extend-shallow": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/extend-shallow/-/extend-shallow-2.0.1.tgz", - "integrity": "sha1-Ua99YUrZqfYQ6huvu5idaxxWiQ8=", - "dev": true, - "requires": { - "is-extendable": "0.1.1" - } - }, - "extglob": { - "version": "0.3.2", - "resolved": "https://registry.npmjs.org/extglob/-/extglob-0.3.2.tgz", - "integrity": "sha1-Lhj/PS9JqydlzskCPwEdqo2DSaE=", - "dev": true, - "requires": { - "is-extglob": "1.0.0" - } - }, - "extsprintf": { - "version": "1.3.0", - "resolved": "https://registry.npmjs.org/extsprintf/-/extsprintf-1.3.0.tgz", - "integrity": "sha1-lpGEQOMEGnpBT4xS48V06zw+HgU=", - "dev": true - }, - "fancy-log": { - "version": "1.3.0", - "resolved": "https://registry.npmjs.org/fancy-log/-/fancy-log-1.3.0.tgz", - "integrity": "sha1-Rb4X0Cu5kX1gzP/UmVyZnmyMmUg=", - "dev": true, - "requires": { - "chalk": "1.1.3", - "time-stamp": "1.1.0" - } - }, - "fast-deep-equal": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/fast-deep-equal/-/fast-deep-equal-1.0.0.tgz", - "integrity": "sha1-liVqO8l1WV6zbYLpkp0GDYk0Of8=", - "dev": true - }, - "fast-json-stable-stringify": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/fast-json-stable-stringify/-/fast-json-stable-stringify-2.0.0.tgz", - "integrity": "sha1-1RQsDK7msRifh9OnYREGT4bIu/I=", - "dev": true - }, - "fd-slicer": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/fd-slicer/-/fd-slicer-1.0.1.tgz", - "integrity": "sha1-i1vL2ewyfFBBv5qwI/1nUPEXfmU=", - "dev": true, - "requires": { - "pend": "1.2.0" - } - }, - "filename-regex": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/filename-regex/-/filename-regex-2.0.1.tgz", - "integrity": "sha1-wcS5vuPglyXdsQa3XB4wH+LxiyY=", - "dev": true - }, - "fill-range": { - "version": "2.2.3", - "resolved": "https://registry.npmjs.org/fill-range/-/fill-range-2.2.3.tgz", - "integrity": "sha1-ULd9/X5Gm8dJJHCWNpn+eoSFpyM=", - "dev": true, - "requires": { - "is-number": "2.1.0", - "isobject": "2.1.0", - "randomatic": "https://registry.npmjs.org/randomatic/-/randomatic-1.1.7.tgz", - "repeat-element": "1.1.2", - "repeat-string": "1.6.1" - } - }, - "find-index": { - "version": "0.1.1", - "resolved": "https://registry.npmjs.org/find-index/-/find-index-0.1.1.tgz", - "integrity": "sha1-Z101iyyjiS15Whq0cjL4tuLg3eQ=", - "dev": true - }, - "findup-sync": { - "version": "0.4.3", - "resolved": "https://registry.npmjs.org/findup-sync/-/findup-sync-0.4.3.tgz", - "integrity": "sha1-QAQ5Kee8YK3wt/SCfExudaDeyhI=", - "dev": true, - "requires": { - "detect-file": "0.1.0", - "is-glob": "2.0.1", - "micromatch": "2.3.11", - "resolve-dir": "0.1.1" - } - }, - "fined": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/fined/-/fined-1.1.0.tgz", - "integrity": "sha1-s33IRLdqL15wgeiE98CuNE8VNHY=", - "dev": true, - "requires": { - "expand-tilde": "2.0.2", - "is-plain-object": "https://registry.npmjs.org/is-plain-object/-/is-plain-object-2.0.4.tgz", - "object.defaults": "1.1.0", - "object.pick": "1.3.0", - "parse-filepath": "1.0.1" - }, - "dependencies": { - "expand-tilde": { - "version": "2.0.2", - "resolved": "https://registry.npmjs.org/expand-tilde/-/expand-tilde-2.0.2.tgz", - "integrity": "sha1-l+gBqgUt8CRU3kawK/YhZCzchQI=", - "dev": true, - "requires": { - "homedir-polyfill": "1.0.1" - } - } - } - }, - "first-chunk-stream": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/first-chunk-stream/-/first-chunk-stream-1.0.0.tgz", - "integrity": "sha1-Wb+1DNkF9g18OUzT2ayqtOatk04=", - "dev": true - }, - "flagged-respawn": { - "version": "0.3.2", - "resolved": "https://registry.npmjs.org/flagged-respawn/-/flagged-respawn-0.3.2.tgz", - "integrity": "sha1-/xke3c1wiKZ1smEP/8l2vpuAdLU=", - "dev": true - }, - "for-in": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/for-in/-/for-in-1.0.2.tgz", - "integrity": "sha1-gQaNKVqBQuwKxybG4iAMMPttXoA=", - "dev": true - }, - "for-own": { - "version": "0.1.5", - "resolved": "https://registry.npmjs.org/for-own/-/for-own-0.1.5.tgz", - "integrity": "sha1-UmXGgaTylNq78XyVCbZ2OqhFEM4=", - "dev": true, - "requires": { - "for-in": "1.0.2" - } - }, - "forever-agent": { - "version": "0.6.1", - "resolved": "https://registry.npmjs.org/forever-agent/-/forever-agent-0.6.1.tgz", - "integrity": "sha1-+8cfDEGt6zf5bFd60e1C2P2sypE=", - "dev": true - }, - "form-data": { - "version": "2.1.4", - "resolved": "https://registry.npmjs.org/form-data/-/form-data-2.1.4.tgz", - "integrity": "sha1-M8GDrPGTJ27KqYFDpp6Uv+4XUNE=", - "dev": true, - "requires": { - "asynckit": "0.4.0", - "combined-stream": "1.0.5", - "mime-types": "2.1.17" - } - }, - "from": { - "version": "0.1.7", - "resolved": "https://registry.npmjs.org/from/-/from-0.1.7.tgz", - "integrity": "sha1-g8YK/Fi5xWmXAH7Rp2izqzA6RP4=", - "dev": true - }, - "fs-exists-sync": { - "version": "0.1.0", - "resolved": "https://registry.npmjs.org/fs-exists-sync/-/fs-exists-sync-0.1.0.tgz", - "integrity": "sha1-mC1ok6+RjnLQjeyehnP/K1qNat0=", - "dev": true - }, - "fs.realpath": { - "version": "https://registry.npmjs.org/fs.realpath/-/fs.realpath-1.0.0.tgz", - "integrity": "sha1-FQStJSMVjKpA20onh8sBQRmU6k8=" - }, - "fstream": { - "version": "1.0.11", - "resolved": "https://registry.npmjs.org/fstream/-/fstream-1.0.11.tgz", - "integrity": "sha1-XB+x8RdHcRTwYyoOtLcbPLD9MXE=", - "dev": true, - "requires": { - "graceful-fs": "4.1.11", - "inherits": "https://registry.npmjs.org/inherits/-/inherits-2.0.3.tgz", - "mkdirp": "0.5.1", - "rimraf": "https://registry.npmjs.org/rimraf/-/rimraf-2.6.2.tgz" - }, - "dependencies": { - "graceful-fs": { - "version": "4.1.11", - "resolved": "https://registry.npmjs.org/graceful-fs/-/graceful-fs-4.1.11.tgz", - "integrity": "sha1-Dovf5NHduIVNZOBOp8AOKgJuVlg=", - "dev": true - } - } - }, - "gaze": { - "version": "0.5.2", - "resolved": "https://registry.npmjs.org/gaze/-/gaze-0.5.2.tgz", - "integrity": "sha1-QLcJU30k0dRXZ9takIaJ3+aaxE8=", - "dev": true, - "requires": { - "globule": "0.1.0" - } - }, - "generate-function": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/generate-function/-/generate-function-2.0.0.tgz", - "integrity": "sha1-aFj+fAlpt9TpCTM3ZHrHn2DfvnQ=", - "dev": true - }, - "generate-object-property": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/generate-object-property/-/generate-object-property-1.2.0.tgz", - "integrity": "sha1-nA4cQDCM6AT0eDYYuTf6iPmdUNA=", - "dev": true, - "requires": { - "is-property": "1.0.2" - } - }, - "getpass": { - "version": "0.1.7", - "resolved": "https://registry.npmjs.org/getpass/-/getpass-0.1.7.tgz", - "integrity": "sha1-Xv+OPmhNVprkyysSgmBOi6YhSfo=", - "dev": true, - "requires": { - "assert-plus": "1.0.0" - }, - "dependencies": { - "assert-plus": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/assert-plus/-/assert-plus-1.0.0.tgz", - "integrity": "sha1-8S4PPF13sLHN2RRpQuTpbB5N1SU=", - "dev": true - } - } - }, - "glob": { - "version": "https://registry.npmjs.org/glob/-/glob-7.1.2.tgz", - "integrity": "sha1-wZyd+aAocC1nhhI4SmVSQExjbRU=", - "requires": { - "fs.realpath": "https://registry.npmjs.org/fs.realpath/-/fs.realpath-1.0.0.tgz", - "inflight": "https://registry.npmjs.org/inflight/-/inflight-1.0.6.tgz", - "inherits": "https://registry.npmjs.org/inherits/-/inherits-2.0.3.tgz", - "minimatch": "https://registry.npmjs.org/minimatch/-/minimatch-3.0.4.tgz", - "once": "https://registry.npmjs.org/once/-/once-1.4.0.tgz", - "path-is-absolute": "https://registry.npmjs.org/path-is-absolute/-/path-is-absolute-1.0.1.tgz" - } - }, - "glob-base": { - "version": "0.3.0", - "resolved": "https://registry.npmjs.org/glob-base/-/glob-base-0.3.0.tgz", - "integrity": "sha1-27Fk9iIbHAscz4Kuoyi0l98Oo8Q=", - "dev": true, - "requires": { - "glob-parent": "2.0.0", - "is-glob": "2.0.1" - } - }, - "glob-parent": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/glob-parent/-/glob-parent-2.0.0.tgz", - "integrity": "sha1-gTg9ctsFT8zPUzbaqQLxgvbtuyg=", - "dev": true, - "requires": { - "is-glob": "2.0.1" - } - }, - "glob-stream": { - "version": "3.1.18", - "resolved": "https://registry.npmjs.org/glob-stream/-/glob-stream-3.1.18.tgz", - "integrity": "sha1-kXCl8St5Awb9/lmPMT+PeVT9FDs=", - "dev": true, - "requires": { - "glob": "4.5.3", - "glob2base": "0.0.12", - "minimatch": "2.0.10", - "ordered-read-streams": "0.1.0", - "through2": "0.6.5", - "unique-stream": "1.0.0" - }, - "dependencies": { - "glob": { - "version": "4.5.3", - "resolved": "https://registry.npmjs.org/glob/-/glob-4.5.3.tgz", - "integrity": "sha1-xstz0yJsHv7wTePFbQEvAzd+4V8=", - "dev": true, - "requires": { - "inflight": "https://registry.npmjs.org/inflight/-/inflight-1.0.6.tgz", - "inherits": "https://registry.npmjs.org/inherits/-/inherits-2.0.3.tgz", - "minimatch": "2.0.10", - "once": "https://registry.npmjs.org/once/-/once-1.4.0.tgz" - } - }, - "minimatch": { - "version": "2.0.10", - "resolved": "https://registry.npmjs.org/minimatch/-/minimatch-2.0.10.tgz", - "integrity": "sha1-jQh8OcazjAAbl/ynzm0OHoCvusc=", - "dev": true, - "requires": { - "brace-expansion": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-1.1.8.tgz" - } - }, - "readable-stream": { - "version": "1.0.34", - "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-1.0.34.tgz", - "integrity": "sha1-Elgg40vIQtLyqq+v5MKRbuMsFXw=", - "dev": true, - "requires": { - "core-util-is": "1.0.2", - "inherits": "https://registry.npmjs.org/inherits/-/inherits-2.0.3.tgz", - "isarray": "0.0.1", - "string_decoder": "0.10.31" - } - }, - "through2": { - "version": "0.6.5", - "resolved": "https://registry.npmjs.org/through2/-/through2-0.6.5.tgz", - "integrity": "sha1-QaucZ7KdVyCQcUEOHXp6lozTrUg=", - "dev": true, - "requires": { - "readable-stream": "1.0.34", - "xtend": "4.0.1" - } - } - } - }, - "glob-watcher": { - "version": "0.0.6", - "resolved": "https://registry.npmjs.org/glob-watcher/-/glob-watcher-0.0.6.tgz", - "integrity": "sha1-uVtKjfdLOcgymLDAXJeLTZo7cQs=", - "dev": true, - "requires": { - "gaze": "0.5.2" - } - }, - "glob2base": { - "version": "0.0.12", - "resolved": "https://registry.npmjs.org/glob2base/-/glob2base-0.0.12.tgz", - "integrity": "sha1-nUGbPijxLoOjYhZKJ3BVkiycDVY=", - "dev": true, - "requires": { - "find-index": "0.1.1" - } - }, - "global-modules": { - "version": "0.2.3", - "resolved": "https://registry.npmjs.org/global-modules/-/global-modules-0.2.3.tgz", - "integrity": "sha1-6lo77ULG1s6ZWk+KEmm12uIjgo0=", - "dev": true, - "requires": { - "global-prefix": "0.1.5", - "is-windows": "0.2.0" - } - }, - "global-prefix": { - "version": "0.1.5", - "resolved": "https://registry.npmjs.org/global-prefix/-/global-prefix-0.1.5.tgz", - "integrity": "sha1-jTvGuNo8qBEqFg2NSW/wRiv+948=", - "dev": true, - "requires": { - "homedir-polyfill": "1.0.1", - "ini": "1.3.5", - "is-windows": "0.2.0", - "which": "https://registry.npmjs.org/which/-/which-1.3.0.tgz" - } - }, - "globby": { - "version": "5.0.0", - "resolved": "https://registry.npmjs.org/globby/-/globby-5.0.0.tgz", - "integrity": "sha1-69hGZ8oNuzMLmbz8aOrCvFQ3Dg0=", - "dev": true, - "requires": { - "array-union": "1.0.2", - "arrify": "1.0.1", - "glob": "https://registry.npmjs.org/glob/-/glob-7.1.2.tgz", - "object-assign": "4.1.1", - "pify": "2.3.0", - "pinkie-promise": "2.0.1" - } - }, - "globule": { - "version": "0.1.0", - "resolved": "https://registry.npmjs.org/globule/-/globule-0.1.0.tgz", - "integrity": "sha1-2cjt3h2nnRJaFRt5UzuXhnY0auU=", - "dev": true, - "requires": { - "glob": "3.1.21", - "lodash": "1.0.2", - "minimatch": "0.2.14" - }, - "dependencies": { - "glob": { - "version": "3.1.21", - "resolved": "https://registry.npmjs.org/glob/-/glob-3.1.21.tgz", - "integrity": "sha1-0p4KBV3qUTj00H7UDomC6DwgZs0=", - "dev": true, - "requires": { - "graceful-fs": "1.2.3", - "inherits": "1.0.2", - "minimatch": "0.2.14" - } - }, - "graceful-fs": { - "version": "1.2.3", - "resolved": "https://registry.npmjs.org/graceful-fs/-/graceful-fs-1.2.3.tgz", - "integrity": "sha1-FaSAaldUfLLS2/J/QuiajDRRs2Q=", - "dev": true - }, - "inherits": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/inherits/-/inherits-1.0.2.tgz", - "integrity": "sha1-ykMJ2t7mtUzAuNJH6NfHoJdb3Js=", - "dev": true - }, - "minimatch": { - "version": "0.2.14", - "resolved": "https://registry.npmjs.org/minimatch/-/minimatch-0.2.14.tgz", - "integrity": "sha1-x054BXT2PG+aCQ6Q775u9TpqdWo=", - "dev": true, - "requires": { - "lru-cache": "2.7.3", - "sigmund": "1.0.1" - } - } - } - }, - "glogg": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/glogg/-/glogg-1.0.0.tgz", - "integrity": "sha1-f+DxmfV6yQbPUS/urY+Q7kooT8U=", - "dev": true, - "requires": { - "sparkles": "1.0.0" - } - }, - "graceful-fs": { - "version": "3.0.11", - "resolved": "https://registry.npmjs.org/graceful-fs/-/graceful-fs-3.0.11.tgz", - "integrity": "sha1-dhPHeKGv6mLyXGMKCG1/Osu92Bg=", - "dev": true, - "requires": { - "natives": "1.1.0" - } - }, - "graceful-readlink": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/graceful-readlink/-/graceful-readlink-1.0.1.tgz", - "integrity": "sha1-TK+tdrxi8C+gObL5Tpo906ORpyU=", - "dev": true - }, - "growl": { - "version": "1.9.2", - "resolved": "https://registry.npmjs.org/growl/-/growl-1.9.2.tgz", - "integrity": "sha1-Dqd0NxXbjY3ixe3hd14bRayFwC8=", - "dev": true - }, - "gulp": { - "version": "3.9.1", - "resolved": "https://registry.npmjs.org/gulp/-/gulp-3.9.1.tgz", - "integrity": "sha1-VxzkWSjdQK9lFPxAEYZgFsE4RbQ=", - "dev": true, - "requires": { - "archy": "1.0.0", - "chalk": "1.1.3", - "deprecated": "0.0.1", - "gulp-util": "3.0.8", - "interpret": "1.0.4", - "liftoff": "2.3.0", - "minimist": "1.2.0", - "orchestrator": "0.3.8", - "pretty-hrtime": "1.0.3", - "semver": "4.3.6", - "tildify": "1.2.0", - "v8flags": "2.1.1", - "vinyl-fs": "0.3.14" - } - }, - "gulp-chmod": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/gulp-chmod/-/gulp-chmod-2.0.0.tgz", - "integrity": "sha1-AMOQuSigeZslGsz2MaoJ4BzGKZw=", - "dev": true, - "requires": { - "deep-assign": "1.0.0", - "stat-mode": "0.2.2", - "through2": "2.0.3" - } - }, - "gulp-filter": { - "version": "https://registry.npmjs.org/gulp-filter/-/gulp-filter-5.0.1.tgz", - "integrity": "sha1-XYf2YuMX5YOe92UOYg5skAj/ktA=", - "dev": true, - "requires": { - "gulp-util": "3.0.8", - "multimatch": "2.1.0", - "streamfilter": "1.0.5" - } - }, - "gulp-gunzip": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/gulp-gunzip/-/gulp-gunzip-1.0.0.tgz", - "integrity": "sha1-FbdBFF6Dqcb1CIYkG1fMWHHxUak=", - "dev": true, - "requires": { - "through2": "0.6.5", - "vinyl": "0.4.6" - }, - "dependencies": { - "clone": { - "version": "0.2.0", - "resolved": "https://registry.npmjs.org/clone/-/clone-0.2.0.tgz", - "integrity": "sha1-xhJqkK1Pctv1rNskPMN3JP6T/B8=", - "dev": true - }, - "readable-stream": { - "version": "1.0.34", - "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-1.0.34.tgz", - "integrity": "sha1-Elgg40vIQtLyqq+v5MKRbuMsFXw=", - "dev": true, - "requires": { - "core-util-is": "1.0.2", - "inherits": "https://registry.npmjs.org/inherits/-/inherits-2.0.3.tgz", - "isarray": "0.0.1", - "string_decoder": "0.10.31" - } - }, - "through2": { - "version": "0.6.5", - "resolved": "https://registry.npmjs.org/through2/-/through2-0.6.5.tgz", - "integrity": "sha1-QaucZ7KdVyCQcUEOHXp6lozTrUg=", - "dev": true, - "requires": { - "readable-stream": "1.0.34", - "xtend": "4.0.1" - } - }, - "vinyl": { - "version": "0.4.6", - "resolved": "https://registry.npmjs.org/vinyl/-/vinyl-0.4.6.tgz", - "integrity": "sha1-LzVsh6VQolVGHza76ypbqL94SEc=", - "dev": true, - "requires": { - "clone": "0.2.0", - "clone-stats": "0.0.1" - } - } - } - }, - "gulp-remote-src": { - "version": "0.4.3", - "resolved": "https://registry.npmjs.org/gulp-remote-src/-/gulp-remote-src-0.4.3.tgz", - "integrity": "sha1-VyjP1kNDPdSEXd7wlp8PlxoqtKE=", - "dev": true, - "requires": { - "event-stream": "3.3.4", - "node.extend": "1.1.6", - "request": "2.79.0", - "through2": "2.0.3", - "vinyl": "2.0.2" - }, - "dependencies": { - "clone-stats": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/clone-stats/-/clone-stats-1.0.0.tgz", - "integrity": "sha1-s3gt/4u1R04Yuba/D9/ngvh3doA=", - "dev": true - }, - "replace-ext": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/replace-ext/-/replace-ext-1.0.0.tgz", - "integrity": "sha1-3mMSg3P8v3w8z6TeWkgMRaZ5WOs=", - "dev": true - }, - "request": { - "version": "2.79.0", - "resolved": "https://registry.npmjs.org/request/-/request-2.79.0.tgz", - "integrity": "sha1-Tf5b9r6LjNw3/Pk+BLZVd3InEN4=", - "dev": true, - "requires": { - "aws-sign2": "0.6.0", - "aws4": "1.6.0", - "caseless": "0.11.0", - "combined-stream": "1.0.5", - "extend": "https://registry.npmjs.org/extend/-/extend-3.0.1.tgz", - "forever-agent": "0.6.1", - "form-data": "2.1.4", - "har-validator": "2.0.6", - "hawk": "3.1.3", - "http-signature": "1.1.1", - "is-typedarray": "1.0.0", - "isstream": "0.1.2", - "json-stringify-safe": "5.0.1", - "mime-types": "2.1.17", - "oauth-sign": "0.8.2", - "qs": "6.3.2", - "stringstream": "0.0.5", - "tough-cookie": "2.3.3", - "tunnel-agent": "0.4.3", - "uuid": "https://registry.npmjs.org/uuid/-/uuid-3.1.0.tgz" - } - }, - "vinyl": { - "version": "2.0.2", - "resolved": "https://registry.npmjs.org/vinyl/-/vinyl-2.0.2.tgz", - "integrity": "sha1-CjcT2NTpIhxY8QyhbAEWyeJe2nw=", - "dev": true, - "requires": { - "clone": "1.0.3", - "clone-buffer": "1.0.0", - "clone-stats": "1.0.0", - "cloneable-readable": "1.0.0", - "is-stream": "1.1.0", - "remove-trailing-separator": "1.1.0", - "replace-ext": "1.0.0" - } - } - } - }, - "gulp-sourcemaps": { - "version": "https://registry.npmjs.org/gulp-sourcemaps/-/gulp-sourcemaps-2.6.1.tgz", - "integrity": "sha1-gzpOKPC49GYQdQMs14JBf3zY+ws=", - "dev": true, - "requires": { - "@gulp-sourcemaps/identity-map": "1.0.1", - "@gulp-sourcemaps/map-sources": "1.0.0", - "acorn": "4.0.13", - "convert-source-map": "1.5.1", - "css": "2.2.1", - "debug-fabulous": "https://registry.npmjs.org/debug-fabulous/-/debug-fabulous-0.2.1.tgz", - "detect-newline": "2.1.0", - "graceful-fs": "4.1.11", - "source-map": "https://registry.npmjs.org/source-map/-/source-map-0.5.6.tgz", - "strip-bom-string": "1.0.0", - "through2": "2.0.3", - "vinyl": "1.2.0" - }, - "dependencies": { - "graceful-fs": { - "version": "4.1.11", - "resolved": "https://registry.npmjs.org/graceful-fs/-/graceful-fs-4.1.11.tgz", - "integrity": "sha1-Dovf5NHduIVNZOBOp8AOKgJuVlg=", - "dev": true - }, - "vinyl": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/vinyl/-/vinyl-1.2.0.tgz", - "integrity": "sha1-XIgDbPVl5d8FVYv8kR+GVt8hiIQ=", - "dev": true, - "requires": { - "clone": "1.0.3", - "clone-stats": "0.0.1", - "replace-ext": "0.0.1" - } - } - } - }, - "gulp-symdest": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/gulp-symdest/-/gulp-symdest-1.1.0.tgz", - "integrity": "sha1-wWUyBzLRks5W/ZQnH/oSMjS/KuA=", - "dev": true, - "requires": { - "event-stream": "3.3.4", - "mkdirp": "0.5.1", - "queue": "3.1.0", - "vinyl-fs": "2.4.4" - }, - "dependencies": { - "glob": { - "version": "5.0.15", - "resolved": "https://registry.npmjs.org/glob/-/glob-5.0.15.tgz", - "integrity": "sha1-G8k2ueAvSmA/zCIuz3Yz0wuLk7E=", - "dev": true, - "requires": { - "inflight": "https://registry.npmjs.org/inflight/-/inflight-1.0.6.tgz", - "inherits": "https://registry.npmjs.org/inherits/-/inherits-2.0.3.tgz", - "minimatch": "https://registry.npmjs.org/minimatch/-/minimatch-3.0.4.tgz", - "once": "https://registry.npmjs.org/once/-/once-1.4.0.tgz", - "path-is-absolute": "https://registry.npmjs.org/path-is-absolute/-/path-is-absolute-1.0.1.tgz" - } - }, - "glob-parent": { - "version": "3.1.0", - "resolved": "https://registry.npmjs.org/glob-parent/-/glob-parent-3.1.0.tgz", - "integrity": "sha1-nmr2KZ2NO9K9QEMIMr0RPfkGxa4=", - "dev": true, - "requires": { - "is-glob": "3.1.0", - "path-dirname": "1.0.2" - } - }, - "glob-stream": { - "version": "5.3.5", - "resolved": "https://registry.npmjs.org/glob-stream/-/glob-stream-5.3.5.tgz", - "integrity": "sha1-pVZlqajM3EGRWofHAeMtTgFvrSI=", - "dev": true, - "requires": { - "extend": "https://registry.npmjs.org/extend/-/extend-3.0.1.tgz", - "glob": "5.0.15", - "glob-parent": "3.1.0", - "micromatch": "2.3.11", - "ordered-read-streams": "0.3.0", - "through2": "0.6.5", - "to-absolute-glob": "0.1.1", - "unique-stream": "2.2.1" - }, - "dependencies": { - "isarray": { - "version": "0.0.1", - "resolved": "https://registry.npmjs.org/isarray/-/isarray-0.0.1.tgz", - "integrity": "sha1-ihis/Kmo9Bd+Cav8YDiTmwXR7t8=", - "dev": true - }, - "readable-stream": { - "version": "1.0.34", - "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-1.0.34.tgz", - "integrity": "sha1-Elgg40vIQtLyqq+v5MKRbuMsFXw=", - "dev": true, - "requires": { - "core-util-is": "1.0.2", - "inherits": "https://registry.npmjs.org/inherits/-/inherits-2.0.3.tgz", - "isarray": "0.0.1", - "string_decoder": "0.10.31" - } - }, - "string_decoder": { - "version": "0.10.31", - "resolved": "https://registry.npmjs.org/string_decoder/-/string_decoder-0.10.31.tgz", - "integrity": "sha1-YuIDvEF2bGwoyfyEMB2rHFMQ+pQ=", - "dev": true - }, - "through2": { - "version": "0.6.5", - "resolved": "https://registry.npmjs.org/through2/-/through2-0.6.5.tgz", - "integrity": "sha1-QaucZ7KdVyCQcUEOHXp6lozTrUg=", - "dev": true, - "requires": { - "readable-stream": "1.0.34", - "xtend": "4.0.1" - } - } - } - }, - "graceful-fs": { - "version": "4.1.11", - "resolved": "https://registry.npmjs.org/graceful-fs/-/graceful-fs-4.1.11.tgz", - "integrity": "sha1-Dovf5NHduIVNZOBOp8AOKgJuVlg=", - "dev": true - }, - "gulp-sourcemaps": { - "version": "1.6.0", - "resolved": "https://registry.npmjs.org/gulp-sourcemaps/-/gulp-sourcemaps-1.6.0.tgz", - "integrity": "sha1-uG/zSdgBzrVuHZ59x7vLS33uYAw=", - "dev": true, - "requires": { - "convert-source-map": "1.5.1", - "graceful-fs": "4.1.11", - "strip-bom": "2.0.0", - "through2": "2.0.3", - "vinyl": "1.2.0" - } - }, - "is-extglob": { - "version": "2.1.1", - "resolved": "https://registry.npmjs.org/is-extglob/-/is-extglob-2.1.1.tgz", - "integrity": "sha1-qIwCU1eR8C7TfHahueqXc8gz+MI=", - "dev": true - }, - "is-glob": { - "version": "3.1.0", - "resolved": "https://registry.npmjs.org/is-glob/-/is-glob-3.1.0.tgz", - "integrity": "sha1-e6WuJCF4BKxwcHuWkiVnSGzD6Eo=", - "dev": true, - "requires": { - "is-extglob": "2.1.1" - } - }, - "isarray": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/isarray/-/isarray-1.0.0.tgz", - "integrity": "sha1-u5NdSFgsuhaMBoNJV6VKPgcSTxE=", - "dev": true - }, - "ordered-read-streams": { - "version": "0.3.0", - "resolved": "https://registry.npmjs.org/ordered-read-streams/-/ordered-read-streams-0.3.0.tgz", - "integrity": "sha1-cTfmmzKYuzQiR6G77jiByA4v14s=", - "dev": true, - "requires": { - "is-stream": "1.1.0", - "readable-stream": "https://registry.npmjs.org/readable-stream/-/readable-stream-2.3.3.tgz" - } - }, - "readable-stream": { - "version": "https://registry.npmjs.org/readable-stream/-/readable-stream-2.3.3.tgz", - "integrity": "sha1-No8lEtefnUb9/HE0mueHi7weuVw=", - "dev": true, - "requires": { - "core-util-is": "1.0.2", - "inherits": "https://registry.npmjs.org/inherits/-/inherits-2.0.3.tgz", - "isarray": "1.0.0", - "process-nextick-args": "1.0.7", - "safe-buffer": "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.1.1.tgz", - "string_decoder": "https://registry.npmjs.org/string_decoder/-/string_decoder-1.0.3.tgz", - "util-deprecate": "1.0.2" - } - }, - "string_decoder": { - "version": "https://registry.npmjs.org/string_decoder/-/string_decoder-1.0.3.tgz", - "integrity": "sha1-D8Z9fBQYJd6UKC3VNr7GubzoYKs=", - "dev": true, - "requires": { - "safe-buffer": "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.1.1.tgz" - } - }, - "strip-bom": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/strip-bom/-/strip-bom-2.0.0.tgz", - "integrity": "sha1-YhmoVhZSBJHzV4i9vxRHqZx+aw4=", - "dev": true, - "requires": { - "is-utf8": "0.2.1" - } - }, - "unique-stream": { - "version": "2.2.1", - "resolved": "https://registry.npmjs.org/unique-stream/-/unique-stream-2.2.1.tgz", - "integrity": "sha1-WqADz76Uxf+GbE59ZouxxNuts2k=", - "dev": true, - "requires": { - "json-stable-stringify": "1.0.1", - "through2-filter": "2.0.0" - } - }, - "vinyl": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/vinyl/-/vinyl-1.2.0.tgz", - "integrity": "sha1-XIgDbPVl5d8FVYv8kR+GVt8hiIQ=", - "dev": true, - "requires": { - "clone": "1.0.3", - "clone-stats": "0.0.1", - "replace-ext": "0.0.1" - } - }, - "vinyl-fs": { - "version": "2.4.4", - "resolved": "https://registry.npmjs.org/vinyl-fs/-/vinyl-fs-2.4.4.tgz", - "integrity": "sha1-vm/zJwy1Xf19MGNkDegfJddTIjk=", - "dev": true, - "requires": { - "duplexify": "https://registry.npmjs.org/duplexify/-/duplexify-3.5.1.tgz", - "glob-stream": "5.3.5", - "graceful-fs": "4.1.11", - "gulp-sourcemaps": "1.6.0", - "is-valid-glob": "0.3.0", - "lazystream": "1.0.0", - "lodash.isequal": "4.5.0", - "merge-stream": "1.0.1", - "mkdirp": "0.5.1", - "object-assign": "4.1.1", - "readable-stream": "https://registry.npmjs.org/readable-stream/-/readable-stream-2.3.3.tgz", - "strip-bom": "2.0.0", - "strip-bom-stream": "1.0.0", - "through2": "2.0.3", - "through2-filter": "2.0.0", - "vali-date": "1.0.0", - "vinyl": "1.2.0" - } - } - } - }, - "gulp-tslint": { - "version": "https://registry.npmjs.org/gulp-tslint/-/gulp-tslint-8.1.2.tgz", - "integrity": "sha1-4PQxlLRz1+drtFpY/oxg59/jvrI=", - "dev": true, - "requires": { - "gulp-util": "3.0.8", - "map-stream": "0.0.7", - "through": "2.3.8" - }, - "dependencies": { - "map-stream": { - "version": "0.0.7", - "resolved": "https://registry.npmjs.org/map-stream/-/map-stream-0.0.7.tgz", - "integrity": "sha1-ih8HiW2CsQkmvTdEokIACfiJdKg=", - "dev": true - } - } - }, - "gulp-typescript": { - "version": "3.2.3", - "resolved": "https://registry.npmjs.org/gulp-typescript/-/gulp-typescript-3.2.3.tgz", - "integrity": "sha512-Np2sJXgtDUwIAoMtlJ9uXsVmpu1FWXlKZw164hLuo56uJa7qo5W2KZ0yAYiYH/HUsaz5L0O2toMOcLIokpFCPg==", - "dev": true, - "requires": { - "gulp-util": "3.0.8", - "source-map": "https://registry.npmjs.org/source-map/-/source-map-0.5.6.tgz", - "through2": "2.0.3", - "vinyl-fs": "2.4.4" - }, - "dependencies": { - "glob": { - "version": "5.0.15", - "resolved": "https://registry.npmjs.org/glob/-/glob-5.0.15.tgz", - "integrity": "sha1-G8k2ueAvSmA/zCIuz3Yz0wuLk7E=", - "dev": true, - "requires": { - "inflight": "https://registry.npmjs.org/inflight/-/inflight-1.0.6.tgz", - "inherits": "https://registry.npmjs.org/inherits/-/inherits-2.0.3.tgz", - "minimatch": "https://registry.npmjs.org/minimatch/-/minimatch-3.0.4.tgz", - "once": "https://registry.npmjs.org/once/-/once-1.4.0.tgz", - "path-is-absolute": "https://registry.npmjs.org/path-is-absolute/-/path-is-absolute-1.0.1.tgz" - } - }, - "glob-parent": { - "version": "3.1.0", - "resolved": "https://registry.npmjs.org/glob-parent/-/glob-parent-3.1.0.tgz", - "integrity": "sha1-nmr2KZ2NO9K9QEMIMr0RPfkGxa4=", - "dev": true, - "requires": { - "is-glob": "3.1.0", - "path-dirname": "1.0.2" - } - }, - "glob-stream": { - "version": "5.3.5", - "resolved": "https://registry.npmjs.org/glob-stream/-/glob-stream-5.3.5.tgz", - "integrity": "sha1-pVZlqajM3EGRWofHAeMtTgFvrSI=", - "dev": true, - "requires": { - "extend": "https://registry.npmjs.org/extend/-/extend-3.0.1.tgz", - "glob": "5.0.15", - "glob-parent": "3.1.0", - "micromatch": "2.3.11", - "ordered-read-streams": "0.3.0", - "through2": "0.6.5", - "to-absolute-glob": "0.1.1", - "unique-stream": "2.2.1" - }, - "dependencies": { - "isarray": { - "version": "0.0.1", - "resolved": "https://registry.npmjs.org/isarray/-/isarray-0.0.1.tgz", - "integrity": "sha1-ihis/Kmo9Bd+Cav8YDiTmwXR7t8=", - "dev": true - }, - "readable-stream": { - "version": "1.0.34", - "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-1.0.34.tgz", - "integrity": "sha1-Elgg40vIQtLyqq+v5MKRbuMsFXw=", - "dev": true, - "requires": { - "core-util-is": "1.0.2", - "inherits": "https://registry.npmjs.org/inherits/-/inherits-2.0.3.tgz", - "isarray": "0.0.1", - "string_decoder": "0.10.31" - } - }, - "string_decoder": { - "version": "0.10.31", - "resolved": "https://registry.npmjs.org/string_decoder/-/string_decoder-0.10.31.tgz", - "integrity": "sha1-YuIDvEF2bGwoyfyEMB2rHFMQ+pQ=", - "dev": true - }, - "through2": { - "version": "0.6.5", - "resolved": "https://registry.npmjs.org/through2/-/through2-0.6.5.tgz", - "integrity": "sha1-QaucZ7KdVyCQcUEOHXp6lozTrUg=", - "dev": true, - "requires": { - "readable-stream": "1.0.34", - "xtend": "4.0.1" - } - } - } - }, - "graceful-fs": { - "version": "4.1.11", - "resolved": "https://registry.npmjs.org/graceful-fs/-/graceful-fs-4.1.11.tgz", - "integrity": "sha1-Dovf5NHduIVNZOBOp8AOKgJuVlg=", - "dev": true - }, - "gulp-sourcemaps": { - "version": "1.6.0", - "resolved": "https://registry.npmjs.org/gulp-sourcemaps/-/gulp-sourcemaps-1.6.0.tgz", - "integrity": "sha1-uG/zSdgBzrVuHZ59x7vLS33uYAw=", - "dev": true, - "requires": { - "convert-source-map": "1.5.1", - "graceful-fs": "4.1.11", - "strip-bom": "2.0.0", - "through2": "2.0.3", - "vinyl": "1.2.0" - } - }, - "is-extglob": { - "version": "2.1.1", - "resolved": "https://registry.npmjs.org/is-extglob/-/is-extglob-2.1.1.tgz", - "integrity": "sha1-qIwCU1eR8C7TfHahueqXc8gz+MI=", - "dev": true - }, - "is-glob": { - "version": "3.1.0", - "resolved": "https://registry.npmjs.org/is-glob/-/is-glob-3.1.0.tgz", - "integrity": "sha1-e6WuJCF4BKxwcHuWkiVnSGzD6Eo=", - "dev": true, - "requires": { - "is-extglob": "2.1.1" - } - }, - "isarray": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/isarray/-/isarray-1.0.0.tgz", - "integrity": "sha1-u5NdSFgsuhaMBoNJV6VKPgcSTxE=", - "dev": true - }, - "ordered-read-streams": { - "version": "0.3.0", - "resolved": "https://registry.npmjs.org/ordered-read-streams/-/ordered-read-streams-0.3.0.tgz", - "integrity": "sha1-cTfmmzKYuzQiR6G77jiByA4v14s=", - "dev": true, - "requires": { - "is-stream": "1.1.0", - "readable-stream": "https://registry.npmjs.org/readable-stream/-/readable-stream-2.3.3.tgz" - } - }, - "readable-stream": { - "version": "https://registry.npmjs.org/readable-stream/-/readable-stream-2.3.3.tgz", - "integrity": "sha1-No8lEtefnUb9/HE0mueHi7weuVw=", - "dev": true, - "requires": { - "core-util-is": "1.0.2", - "inherits": "https://registry.npmjs.org/inherits/-/inherits-2.0.3.tgz", - "isarray": "1.0.0", - "process-nextick-args": "1.0.7", - "safe-buffer": "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.1.1.tgz", - "string_decoder": "https://registry.npmjs.org/string_decoder/-/string_decoder-1.0.3.tgz", - "util-deprecate": "1.0.2" - } - }, - "string_decoder": { - "version": "https://registry.npmjs.org/string_decoder/-/string_decoder-1.0.3.tgz", - "integrity": "sha1-D8Z9fBQYJd6UKC3VNr7GubzoYKs=", - "dev": true, - "requires": { - "safe-buffer": "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.1.1.tgz" - } - }, - "strip-bom": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/strip-bom/-/strip-bom-2.0.0.tgz", - "integrity": "sha1-YhmoVhZSBJHzV4i9vxRHqZx+aw4=", - "dev": true, - "requires": { - "is-utf8": "0.2.1" - } - }, - "unique-stream": { - "version": "2.2.1", - "resolved": "https://registry.npmjs.org/unique-stream/-/unique-stream-2.2.1.tgz", - "integrity": "sha1-WqADz76Uxf+GbE59ZouxxNuts2k=", - "dev": true, - "requires": { - "json-stable-stringify": "1.0.1", - "through2-filter": "2.0.0" - } - }, - "vinyl": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/vinyl/-/vinyl-1.2.0.tgz", - "integrity": "sha1-XIgDbPVl5d8FVYv8kR+GVt8hiIQ=", - "dev": true, - "requires": { - "clone": "1.0.3", - "clone-stats": "0.0.1", - "replace-ext": "0.0.1" - } - }, - "vinyl-fs": { - "version": "2.4.4", - "resolved": "https://registry.npmjs.org/vinyl-fs/-/vinyl-fs-2.4.4.tgz", - "integrity": "sha1-vm/zJwy1Xf19MGNkDegfJddTIjk=", - "dev": true, - "requires": { - "duplexify": "https://registry.npmjs.org/duplexify/-/duplexify-3.5.1.tgz", - "glob-stream": "5.3.5", - "graceful-fs": "4.1.11", - "gulp-sourcemaps": "1.6.0", - "is-valid-glob": "0.3.0", - "lazystream": "1.0.0", - "lodash.isequal": "4.5.0", - "merge-stream": "1.0.1", - "mkdirp": "0.5.1", - "object-assign": "4.1.1", - "readable-stream": "https://registry.npmjs.org/readable-stream/-/readable-stream-2.3.3.tgz", - "strip-bom": "2.0.0", - "strip-bom-stream": "1.0.0", - "through2": "2.0.3", - "through2-filter": "2.0.0", - "vali-date": "1.0.0", - "vinyl": "1.2.0" - } - } - } - }, - "gulp-untar": { - "version": "0.0.6", - "resolved": "https://registry.npmjs.org/gulp-untar/-/gulp-untar-0.0.6.tgz", - "integrity": "sha1-1r3v3n6ajgVMnxYjhaB4LEvnQAA=", - "dev": true, - "requires": { - "event-stream": "3.3.4", - "gulp-util": "3.0.8", - "streamifier": "0.1.1", - "tar": "2.2.1", - "through2": "2.0.3" - } - }, - "gulp-util": { - "version": "3.0.8", - "resolved": "https://registry.npmjs.org/gulp-util/-/gulp-util-3.0.8.tgz", - "integrity": "sha1-AFTh50RQLifATBh8PsxQXdVLu08=", - "dev": true, - "requires": { - "array-differ": "1.0.0", - "array-uniq": "1.0.3", - "beeper": "1.1.1", - "chalk": "1.1.3", - "dateformat": "2.2.0", - "fancy-log": "1.3.0", - "gulplog": "1.0.0", - "has-gulplog": "0.1.0", - "lodash._reescape": "3.0.0", - "lodash._reevaluate": "3.0.0", - "lodash._reinterpolate": "3.0.0", - "lodash.template": "3.6.2", - "minimist": "1.2.0", - "multipipe": "0.1.2", - "object-assign": "3.0.0", - "replace-ext": "0.0.1", - "through2": "2.0.3", - "vinyl": "0.5.3" - }, - "dependencies": { - "object-assign": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/object-assign/-/object-assign-3.0.0.tgz", - "integrity": "sha1-m+3VygiXlJvKR+f/QIBi1Un1h/I=", - "dev": true - } - } - }, - "gulp-vinyl-zip": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/gulp-vinyl-zip/-/gulp-vinyl-zip-2.1.0.tgz", - "integrity": "sha1-JOQGhdwFtxSZlSRQmeBZAmO+ja0=", - "dev": true, - "requires": { - "event-stream": "3.3.4", - "queue": "4.4.2", - "through2": "2.0.3", - "vinyl": "2.1.0", - "vinyl-fs": "2.4.4", - "yauzl": "2.9.1", - "yazl": "2.4.3" - }, - "dependencies": { - "clone": { - "version": "2.1.1", - "resolved": "https://registry.npmjs.org/clone/-/clone-2.1.1.tgz", - "integrity": "sha1-0hfR6WERjjrJpLi7oyhVU79kfNs=", - "dev": true - }, - "clone-stats": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/clone-stats/-/clone-stats-1.0.0.tgz", - "integrity": "sha1-s3gt/4u1R04Yuba/D9/ngvh3doA=", - "dev": true - }, - "glob": { - "version": "5.0.15", - "resolved": "https://registry.npmjs.org/glob/-/glob-5.0.15.tgz", - "integrity": "sha1-G8k2ueAvSmA/zCIuz3Yz0wuLk7E=", - "dev": true, - "requires": { - "inflight": "https://registry.npmjs.org/inflight/-/inflight-1.0.6.tgz", - "inherits": "https://registry.npmjs.org/inherits/-/inherits-2.0.3.tgz", - "minimatch": "https://registry.npmjs.org/minimatch/-/minimatch-3.0.4.tgz", - "once": "https://registry.npmjs.org/once/-/once-1.4.0.tgz", - "path-is-absolute": "https://registry.npmjs.org/path-is-absolute/-/path-is-absolute-1.0.1.tgz" - } - }, - "glob-parent": { - "version": "3.1.0", - "resolved": "https://registry.npmjs.org/glob-parent/-/glob-parent-3.1.0.tgz", - "integrity": "sha1-nmr2KZ2NO9K9QEMIMr0RPfkGxa4=", - "dev": true, - "requires": { - "is-glob": "3.1.0", - "path-dirname": "1.0.2" - } - }, - "glob-stream": { - "version": "5.3.5", - "resolved": "https://registry.npmjs.org/glob-stream/-/glob-stream-5.3.5.tgz", - "integrity": "sha1-pVZlqajM3EGRWofHAeMtTgFvrSI=", - "dev": true, - "requires": { - "extend": "https://registry.npmjs.org/extend/-/extend-3.0.1.tgz", - "glob": "5.0.15", - "glob-parent": "3.1.0", - "micromatch": "2.3.11", - "ordered-read-streams": "0.3.0", - "through2": "0.6.5", - "to-absolute-glob": "0.1.1", - "unique-stream": "2.2.1" - }, - "dependencies": { - "isarray": { - "version": "0.0.1", - "resolved": "https://registry.npmjs.org/isarray/-/isarray-0.0.1.tgz", - "integrity": "sha1-ihis/Kmo9Bd+Cav8YDiTmwXR7t8=", - "dev": true - }, - "readable-stream": { - "version": "1.0.34", - "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-1.0.34.tgz", - "integrity": "sha1-Elgg40vIQtLyqq+v5MKRbuMsFXw=", - "dev": true, - "requires": { - "core-util-is": "1.0.2", - "inherits": "https://registry.npmjs.org/inherits/-/inherits-2.0.3.tgz", - "isarray": "0.0.1", - "string_decoder": "0.10.31" - } - }, - "string_decoder": { - "version": "0.10.31", - "resolved": "https://registry.npmjs.org/string_decoder/-/string_decoder-0.10.31.tgz", - "integrity": "sha1-YuIDvEF2bGwoyfyEMB2rHFMQ+pQ=", - "dev": true - }, - "through2": { - "version": "0.6.5", - "resolved": "https://registry.npmjs.org/through2/-/through2-0.6.5.tgz", - "integrity": "sha1-QaucZ7KdVyCQcUEOHXp6lozTrUg=", - "dev": true, - "requires": { - "readable-stream": "1.0.34", - "xtend": "4.0.1" - } - } - } - }, - "graceful-fs": { - "version": "4.1.11", - "resolved": "https://registry.npmjs.org/graceful-fs/-/graceful-fs-4.1.11.tgz", - "integrity": "sha1-Dovf5NHduIVNZOBOp8AOKgJuVlg=", - "dev": true - }, - "gulp-sourcemaps": { - "version": "1.6.0", - "resolved": "https://registry.npmjs.org/gulp-sourcemaps/-/gulp-sourcemaps-1.6.0.tgz", - "integrity": "sha1-uG/zSdgBzrVuHZ59x7vLS33uYAw=", - "dev": true, - "requires": { - "convert-source-map": "1.5.1", - "graceful-fs": "4.1.11", - "strip-bom": "2.0.0", - "through2": "2.0.3", - "vinyl": "1.2.0" - }, - "dependencies": { - "clone": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/clone/-/clone-1.0.3.tgz", - "integrity": "sha1-KY1+IjFmD0DAA8LtMUDezz9TCF8=", - "dev": true - }, - "clone-stats": { - "version": "0.0.1", - "resolved": "https://registry.npmjs.org/clone-stats/-/clone-stats-0.0.1.tgz", - "integrity": "sha1-uI+UqCzzi4eR1YBG6kAprYjKmdE=", - "dev": true - }, - "replace-ext": { - "version": "0.0.1", - "resolved": "https://registry.npmjs.org/replace-ext/-/replace-ext-0.0.1.tgz", - "integrity": "sha1-KbvZIHinOfC8zitO5B6DeVNSKSQ=", - "dev": true - }, - "vinyl": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/vinyl/-/vinyl-1.2.0.tgz", - "integrity": "sha1-XIgDbPVl5d8FVYv8kR+GVt8hiIQ=", - "dev": true, - "requires": { - "clone": "1.0.3", - "clone-stats": "0.0.1", - "replace-ext": "0.0.1" - } - } - } - }, - "is-extglob": { - "version": "2.1.1", - "resolved": "https://registry.npmjs.org/is-extglob/-/is-extglob-2.1.1.tgz", - "integrity": "sha1-qIwCU1eR8C7TfHahueqXc8gz+MI=", - "dev": true - }, - "is-glob": { - "version": "3.1.0", - "resolved": "https://registry.npmjs.org/is-glob/-/is-glob-3.1.0.tgz", - "integrity": "sha1-e6WuJCF4BKxwcHuWkiVnSGzD6Eo=", - "dev": true, - "requires": { - "is-extglob": "2.1.1" - } - }, - "isarray": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/isarray/-/isarray-1.0.0.tgz", - "integrity": "sha1-u5NdSFgsuhaMBoNJV6VKPgcSTxE=", - "dev": true - }, - "ordered-read-streams": { - "version": "0.3.0", - "resolved": "https://registry.npmjs.org/ordered-read-streams/-/ordered-read-streams-0.3.0.tgz", - "integrity": "sha1-cTfmmzKYuzQiR6G77jiByA4v14s=", - "dev": true, - "requires": { - "is-stream": "1.1.0", - "readable-stream": "2.3.3" - } - }, - "queue": { - "version": "4.4.2", - "resolved": "https://registry.npmjs.org/queue/-/queue-4.4.2.tgz", - "integrity": "sha512-fSMRXbwhMwipcDZ08enW2vl+YDmAmhcNcr43sCJL8DIg+CFOsoRLG23ctxA+fwNk1w55SePSiS7oqQQSgQoVJQ==", - "dev": true, - "requires": { - "inherits": "https://registry.npmjs.org/inherits/-/inherits-2.0.3.tgz" - } - }, - "readable-stream": { - "version": "2.3.3", - "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-2.3.3.tgz", - "integrity": "sha512-m+qzzcn7KUxEmd1gMbchF+Y2eIUbieUaxkWtptyHywrX0rE8QEYqPC07Vuy4Wm32/xE16NcdBctb8S0Xe/5IeQ==", - "dev": true, - "requires": { - "core-util-is": "1.0.2", - "inherits": "https://registry.npmjs.org/inherits/-/inherits-2.0.3.tgz", - "isarray": "1.0.0", - "process-nextick-args": "1.0.7", - "safe-buffer": "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.1.1.tgz", - "string_decoder": "1.0.3", - "util-deprecate": "1.0.2" - } - }, - "replace-ext": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/replace-ext/-/replace-ext-1.0.0.tgz", - "integrity": "sha1-3mMSg3P8v3w8z6TeWkgMRaZ5WOs=", - "dev": true - }, - "string_decoder": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/string_decoder/-/string_decoder-1.0.3.tgz", - "integrity": "sha512-4AH6Z5fzNNBcH+6XDMfA/BTt87skxqJlO0lAh3Dker5zThcAxG6mKz+iGu308UKoPPQ8Dcqx/4JhujzltRa+hQ==", - "dev": true, - "requires": { - "safe-buffer": "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.1.1.tgz" - } - }, - "strip-bom": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/strip-bom/-/strip-bom-2.0.0.tgz", - "integrity": "sha1-YhmoVhZSBJHzV4i9vxRHqZx+aw4=", - "dev": true, - "requires": { - "is-utf8": "0.2.1" - } - }, - "unique-stream": { - "version": "2.2.1", - "resolved": "https://registry.npmjs.org/unique-stream/-/unique-stream-2.2.1.tgz", - "integrity": "sha1-WqADz76Uxf+GbE59ZouxxNuts2k=", - "dev": true, - "requires": { - "json-stable-stringify": "1.0.1", - "through2-filter": "2.0.0" - } - }, - "vinyl": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/vinyl/-/vinyl-2.1.0.tgz", - "integrity": "sha1-Ah+cLPlR1rk5lDyJ617lrdT9kkw=", - "dev": true, - "requires": { - "clone": "2.1.1", - "clone-buffer": "1.0.0", - "clone-stats": "1.0.0", - "cloneable-readable": "1.0.0", - "remove-trailing-separator": "1.1.0", - "replace-ext": "1.0.0" - } - }, - "vinyl-fs": { - "version": "2.4.4", - "resolved": "https://registry.npmjs.org/vinyl-fs/-/vinyl-fs-2.4.4.tgz", - "integrity": "sha1-vm/zJwy1Xf19MGNkDegfJddTIjk=", - "dev": true, - "requires": { - "duplexify": "https://registry.npmjs.org/duplexify/-/duplexify-3.5.1.tgz", - "glob-stream": "5.3.5", - "graceful-fs": "4.1.11", - "gulp-sourcemaps": "1.6.0", - "is-valid-glob": "0.3.0", - "lazystream": "1.0.0", - "lodash.isequal": "4.5.0", - "merge-stream": "1.0.1", - "mkdirp": "0.5.1", - "object-assign": "4.1.1", - "readable-stream": "2.3.3", - "strip-bom": "2.0.0", - "strip-bom-stream": "1.0.0", - "through2": "2.0.3", - "through2-filter": "2.0.0", - "vali-date": "1.0.0", - "vinyl": "1.2.0" - }, - "dependencies": { - "clone": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/clone/-/clone-1.0.3.tgz", - "integrity": "sha1-KY1+IjFmD0DAA8LtMUDezz9TCF8=", - "dev": true - }, - "clone-stats": { - "version": "0.0.1", - "resolved": "https://registry.npmjs.org/clone-stats/-/clone-stats-0.0.1.tgz", - "integrity": "sha1-uI+UqCzzi4eR1YBG6kAprYjKmdE=", - "dev": true - }, - "replace-ext": { - "version": "0.0.1", - "resolved": "https://registry.npmjs.org/replace-ext/-/replace-ext-0.0.1.tgz", - "integrity": "sha1-KbvZIHinOfC8zitO5B6DeVNSKSQ=", - "dev": true - }, - "vinyl": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/vinyl/-/vinyl-1.2.0.tgz", - "integrity": "sha1-XIgDbPVl5d8FVYv8kR+GVt8hiIQ=", - "dev": true, - "requires": { - "clone": "1.0.3", - "clone-stats": "0.0.1", - "replace-ext": "0.0.1" - } - } - } - } - } - }, - "gulplog": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/gulplog/-/gulplog-1.0.0.tgz", - "integrity": "sha1-4oxNRdBey77YGDY86PnFkmIp/+U=", - "dev": true, - "requires": { - "glogg": "1.0.0" - } - }, - "har-schema": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/har-schema/-/har-schema-2.0.0.tgz", - "integrity": "sha1-qUwiJOvKwEeCoNkDVSHyRzW37JI=", - "dev": true - }, - "har-validator": { - "version": "2.0.6", - "resolved": "https://registry.npmjs.org/har-validator/-/har-validator-2.0.6.tgz", - "integrity": "sha1-zcvAgYgmWtEZtqWnyKtw7s+10n0=", - "dev": true, - "requires": { - "chalk": "1.1.3", - "commander": "2.9.0", - "is-my-json-valid": "https://registry.npmjs.org/is-my-json-valid/-/is-my-json-valid-2.16.1.tgz", - "pinkie-promise": "2.0.1" - } - }, - "has-ansi": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/has-ansi/-/has-ansi-2.0.0.tgz", - "integrity": "sha1-NPUEnOHs3ysGSa8+8k5F7TVBbZE=", - "dev": true, - "requires": { - "ansi-regex": "2.1.1" - } - }, - "has-flag": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-1.0.0.tgz", - "integrity": "sha1-nZ55MWXOAXoA8AQYxD+UKnsdEfo=", - "dev": true - }, - "has-gulplog": { - "version": "0.1.0", - "resolved": "https://registry.npmjs.org/has-gulplog/-/has-gulplog-0.1.0.tgz", - "integrity": "sha1-ZBTIKRNpfaUVkDl9r7EvIpZ4Ec4=", - "dev": true, - "requires": { - "sparkles": "1.0.0" - } - }, - "hawk": { - "version": "3.1.3", - "resolved": "https://registry.npmjs.org/hawk/-/hawk-3.1.3.tgz", - "integrity": "sha1-B4REvXwWQLD+VA0sm3PVlnjo4cQ=", - "dev": true, - "requires": { - "boom": "2.10.1", - "cryptiles": "2.0.5", - "hoek": "2.16.3", - "sntp": "1.0.9" - } - }, - "he": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/he/-/he-1.1.1.tgz", - "integrity": "sha1-k0EP0hsAlzUVH4howvJx80J+I/0=", - "dev": true - }, - "hoek": { - "version": "2.16.3", - "resolved": "https://registry.npmjs.org/hoek/-/hoek-2.16.3.tgz", - "integrity": "sha1-ILt0A9POo5jpHcRxCo/xuCdKJe0=", - "dev": true - }, - "homedir-polyfill": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/homedir-polyfill/-/homedir-polyfill-1.0.1.tgz", - "integrity": "sha1-TCu8inWJmP7r9e1oWA921GdotLw=", - "dev": true, - "requires": { - "parse-passwd": "1.0.0" - } - }, - "htmlparser2": { - "version": "3.9.2", - "resolved": "https://registry.npmjs.org/htmlparser2/-/htmlparser2-3.9.2.tgz", - "integrity": "sha1-G9+HrMoPP55T+k/M6w9LTLsAszg=", - "dev": true, - "requires": { - "domelementtype": "1.3.0", - "domhandler": "2.4.1", - "domutils": "1.5.1", - "entities": "1.1.1", - "inherits": "https://registry.npmjs.org/inherits/-/inherits-2.0.3.tgz", - "readable-stream": "https://registry.npmjs.org/readable-stream/-/readable-stream-2.3.3.tgz" - }, - "dependencies": { - "isarray": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/isarray/-/isarray-1.0.0.tgz", - "integrity": "sha1-u5NdSFgsuhaMBoNJV6VKPgcSTxE=", - "dev": true - }, - "readable-stream": { - "version": "https://registry.npmjs.org/readable-stream/-/readable-stream-2.3.3.tgz", - "integrity": "sha1-No8lEtefnUb9/HE0mueHi7weuVw=", - "dev": true, - "requires": { - "core-util-is": "1.0.2", - "inherits": "https://registry.npmjs.org/inherits/-/inherits-2.0.3.tgz", - "isarray": "1.0.0", - "process-nextick-args": "1.0.7", - "safe-buffer": "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.1.1.tgz", - "string_decoder": "https://registry.npmjs.org/string_decoder/-/string_decoder-1.0.3.tgz", - "util-deprecate": "1.0.2" - } - }, - "string_decoder": { - "version": "https://registry.npmjs.org/string_decoder/-/string_decoder-1.0.3.tgz", - "integrity": "sha1-D8Z9fBQYJd6UKC3VNr7GubzoYKs=", - "dev": true, - "requires": { - "safe-buffer": "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.1.1.tgz" - } - } - } - }, - "http-proxy-agent": { - "version": "0.2.7", - "resolved": "https://registry.npmjs.org/http-proxy-agent/-/http-proxy-agent-0.2.7.tgz", - "integrity": "sha1-4X/aZfCQLZUs55IeYsf/iGJlWl4=", - "requires": { - "agent-base": "1.0.2", - "debug": "https://registry.npmjs.org/debug/-/debug-2.6.8.tgz", - "extend": "https://registry.npmjs.org/extend/-/extend-3.0.1.tgz" - } - }, - "http-signature": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/http-signature/-/http-signature-1.1.1.tgz", - "integrity": "sha1-33LiZwZs0Kxn+3at+OE0qPvPkb8=", - "dev": true, - "requires": { - "assert-plus": "0.2.0", - "jsprim": "1.4.1", - "sshpk": "1.13.1" - } - }, - "https-proxy-agent": { - "version": "0.3.6", - "resolved": "https://registry.npmjs.org/https-proxy-agent/-/https-proxy-agent-0.3.6.tgz", - "integrity": "sha1-cT+jjl01P1DrFKNC/r4pAz7RYZs=", - "requires": { - "agent-base": "1.0.2", - "debug": "https://registry.npmjs.org/debug/-/debug-2.6.8.tgz", - "extend": "https://registry.npmjs.org/extend/-/extend-3.0.1.tgz" - } - }, - "iconv-lite": { - "version": "https://registry.npmjs.org/iconv-lite/-/iconv-lite-0.4.19.tgz", - "integrity": "sha1-90aPYBNfXl2tM5nAqBvpoWA6CCs=", - "dev": true - }, - "inflight": { - "version": "https://registry.npmjs.org/inflight/-/inflight-1.0.6.tgz", - "integrity": "sha1-Sb1jMdfQLQwJvJEKEHW6gWW1bfk=", - "requires": { - "once": "https://registry.npmjs.org/once/-/once-1.4.0.tgz", - "wrappy": "https://registry.npmjs.org/wrappy/-/wrappy-1.0.2.tgz" - } - }, - "inherits": { - "version": "https://registry.npmjs.org/inherits/-/inherits-2.0.3.tgz", - "integrity": "sha1-Yzwsg+PaQqUC9SRmAiSA9CCCYd4=" - }, - "ini": { - "version": "1.3.5", - "resolved": "https://registry.npmjs.org/ini/-/ini-1.3.5.tgz", - "integrity": "sha512-RZY5huIKCMRWDUqZlEi72f/lmXKMvuszcMBduliQ3nnWbx9X/ZBQO7DijMEYS9EhHBb2qacRUMtC7svLwe0lcw==", - "dev": true - }, - "interpret": { - "version": "1.0.4", - "resolved": "https://registry.npmjs.org/interpret/-/interpret-1.0.4.tgz", - "integrity": "sha1-ggzdWIuGj/sZGoCVBtbJyPISsbA=", - "dev": true - }, - "invert-kv": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/invert-kv/-/invert-kv-1.0.0.tgz", - "integrity": "sha1-EEqOSqym09jNFXqO+L+rLXo//bY=", - "dev": true - }, - "is": { - "version": "3.2.1", - "resolved": "https://registry.npmjs.org/is/-/is-3.2.1.tgz", - "integrity": "sha1-0Kwq1V63sL7JJqUmb2xmKqqD3KU=", - "dev": true - }, - "is-absolute": { - "version": "0.2.6", - "resolved": "https://registry.npmjs.org/is-absolute/-/is-absolute-0.2.6.tgz", - "integrity": "sha1-IN5p89uULvLYe5wto28XIjWxtes=", - "dev": true, - "requires": { - "is-relative": "0.2.1", - "is-windows": "0.2.0" - } - }, - "is-buffer": { - "version": "https://registry.npmjs.org/is-buffer/-/is-buffer-1.1.6.tgz", - "integrity": "sha1-76ouqdqg16suoTqXsritUf776L4=", - "dev": true - }, - "is-dotfile": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/is-dotfile/-/is-dotfile-1.0.3.tgz", - "integrity": "sha1-pqLzL/0t+wT1yiXs0Pa4PPeYoeE=", - "dev": true - }, - "is-equal-shallow": { - "version": "0.1.3", - "resolved": "https://registry.npmjs.org/is-equal-shallow/-/is-equal-shallow-0.1.3.tgz", - "integrity": "sha1-IjgJj8Ih3gvPpdnqxMRdY4qhxTQ=", - "dev": true, - "requires": { - "is-primitive": "2.0.0" - } - }, - "is-extendable": { - "version": "0.1.1", - "resolved": "https://registry.npmjs.org/is-extendable/-/is-extendable-0.1.1.tgz", - "integrity": "sha1-YrEQ4omkcUGOPsNqYX1HLjAd/Ik=", - "dev": true - }, - "is-extglob": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/is-extglob/-/is-extglob-1.0.0.tgz", - "integrity": "sha1-rEaBd8SUNAWgkvyPKXYMb/xiBsA=", - "dev": true - }, - "is-fullwidth-code-point": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/is-fullwidth-code-point/-/is-fullwidth-code-point-1.0.0.tgz", - "integrity": "sha1-754xOG8DGn8NZDr4L95QxFfvAMs=", - "dev": true, - "requires": { - "number-is-nan": "1.0.1" - } - }, - "is-glob": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/is-glob/-/is-glob-2.0.1.tgz", - "integrity": "sha1-0Jb5JqPe1WAPP9/ZEZjLCIjC2GM=", - "dev": true, - "requires": { - "is-extglob": "1.0.0" - } - }, - "is-my-json-valid": { - "version": "https://registry.npmjs.org/is-my-json-valid/-/is-my-json-valid-2.16.1.tgz", - "integrity": "sha1-WoRnd+LCYg0eaRBOXToDsfYIjxE=", - "dev": true, - "requires": { - "generate-function": "2.0.0", - "generate-object-property": "1.2.0", - "jsonpointer": "4.0.1", - "xtend": "4.0.1" - } - }, - "is-number": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/is-number/-/is-number-2.1.0.tgz", - "integrity": "sha1-Afy7s5NGOlSPL0ZszhbezknbkI8=", - "dev": true, - "requires": { - "kind-of": "3.2.2" - } - }, - "is-obj": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/is-obj/-/is-obj-1.0.1.tgz", - "integrity": "sha1-PkcprB9f3gJc19g6iW2rn09n2w8=", - "dev": true - }, - "is-path-cwd": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/is-path-cwd/-/is-path-cwd-1.0.0.tgz", - "integrity": "sha1-0iXsIxMuie3Tj9p2dHLmLmXxEG0=", - "dev": true - }, - "is-path-in-cwd": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/is-path-in-cwd/-/is-path-in-cwd-1.0.0.tgz", - "integrity": "sha1-ZHdYK4IU1gI0YJRWcAO+ip6sBNw=", - "dev": true, - "requires": { - "is-path-inside": "1.0.0" - } - }, - "is-path-inside": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/is-path-inside/-/is-path-inside-1.0.0.tgz", - "integrity": "sha1-/AbloWg/vaE95mev9xe7wQpI838=", - "dev": true, - "requires": { - "path-is-inside": "1.0.2" - } - }, - "is-plain-object": { - "version": "https://registry.npmjs.org/is-plain-object/-/is-plain-object-2.0.4.tgz", - "integrity": "sha1-LBY7P6+xtgbZ0Xko8FwqHDjgdnc=", - "dev": true, - "requires": { - "isobject": "3.0.1" - }, - "dependencies": { - "isobject": { - "version": "3.0.1", - "resolved": "https://registry.npmjs.org/isobject/-/isobject-3.0.1.tgz", - "integrity": "sha1-TkMekrEalzFjaqH5yNHMvP2reN8=", - "dev": true - } - } - }, - "is-posix-bracket": { - "version": "0.1.1", - "resolved": "https://registry.npmjs.org/is-posix-bracket/-/is-posix-bracket-0.1.1.tgz", - "integrity": "sha1-MzTceXdDaOkvAW5vvAqI9c1ua8Q=", - "dev": true - }, - "is-primitive": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/is-primitive/-/is-primitive-2.0.0.tgz", - "integrity": "sha1-IHurkWOEmcB7Kt8kCkGochADRXU=", - "dev": true - }, - "is-promise": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/is-promise/-/is-promise-2.1.0.tgz", - "integrity": "sha1-eaKp7OfwlugPNtKy87wWwf9L8/o=", - "dev": true - }, - "is-property": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/is-property/-/is-property-1.0.2.tgz", - "integrity": "sha1-V/4cTkhHTt1lsJkR8msc1Ald2oQ=", - "dev": true - }, - "is-relative": { - "version": "0.2.1", - "resolved": "https://registry.npmjs.org/is-relative/-/is-relative-0.2.1.tgz", - "integrity": "sha1-0n9MfVFtF1+2ENuEu+7yPDvJeqU=", - "dev": true, - "requires": { - "is-unc-path": "0.1.2" - } - }, - "is-stream": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/is-stream/-/is-stream-1.1.0.tgz", - "integrity": "sha1-EtSj3U5o4Lec6428hBc66A2RykQ=", - "dev": true - }, - "is-typedarray": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/is-typedarray/-/is-typedarray-1.0.0.tgz", - "integrity": "sha1-5HnICFjfDBsR3dppQPlgEfzaSpo=", - "dev": true - }, - "is-unc-path": { - "version": "0.1.2", - "resolved": "https://registry.npmjs.org/is-unc-path/-/is-unc-path-0.1.2.tgz", - "integrity": "sha1-arBTpyVzwQJQ/0FqOBTDUXivObk=", - "dev": true, - "requires": { - "unc-path-regex": "0.1.2" - } - }, - "is-utf8": { - "version": "0.2.1", - "resolved": "https://registry.npmjs.org/is-utf8/-/is-utf8-0.2.1.tgz", - "integrity": "sha1-Sw2hRCEE0bM2NA6AeX6GXPOffXI=", - "dev": true - }, - "is-valid-glob": { - "version": "0.3.0", - "resolved": "https://registry.npmjs.org/is-valid-glob/-/is-valid-glob-0.3.0.tgz", - "integrity": "sha1-1LVcafUYhvm2XHDWwmItN+KfSP4=", - "dev": true - }, - "is-windows": { - "version": "0.2.0", - "resolved": "https://registry.npmjs.org/is-windows/-/is-windows-0.2.0.tgz", - "integrity": "sha1-3hqm1j6indJIc3tp8f+LgALSEIw=", - "dev": true - }, - "isarray": { - "version": "0.0.1", - "resolved": "https://registry.npmjs.org/isarray/-/isarray-0.0.1.tgz", - "integrity": "sha1-ihis/Kmo9Bd+Cav8YDiTmwXR7t8=", - "dev": true - }, - "isexe": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/isexe/-/isexe-2.0.0.tgz", - "integrity": "sha1-6PvzdNxVb/iUehDcsFctYz8s+hA=", - "dev": true - }, - "isobject": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/isobject/-/isobject-2.1.0.tgz", - "integrity": "sha1-8GVWEJaj8dou9GJy+BXIQNh+DIk=", - "dev": true, - "requires": { - "isarray": "1.0.0" - }, - "dependencies": { - "isarray": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/isarray/-/isarray-1.0.0.tgz", - "integrity": "sha1-u5NdSFgsuhaMBoNJV6VKPgcSTxE=", - "dev": true - } - } - }, - "isstream": { - "version": "0.1.2", - "resolved": "https://registry.npmjs.org/isstream/-/isstream-0.1.2.tgz", - "integrity": "sha1-R+Y/evVa+m+S4VAOaQ64uFKcCZo=", - "dev": true - }, - "js-tokens": { - "version": "3.0.2", - "resolved": "https://registry.npmjs.org/js-tokens/-/js-tokens-3.0.2.tgz", - "integrity": "sha1-mGbfOVECEw449/mWvOtlRDIJwls=", - "dev": true - }, - "jsbn": { - "version": "0.1.1", - "resolved": "https://registry.npmjs.org/jsbn/-/jsbn-0.1.1.tgz", - "integrity": "sha1-peZUwuWi3rXyAdls77yoDA7y9RM=", - "dev": true, - "optional": true - }, - "json-schema": { - "version": "0.2.3", - "resolved": "https://registry.npmjs.org/json-schema/-/json-schema-0.2.3.tgz", - "integrity": "sha1-tIDIkuWaLwWVTOcnvT8qTogvnhM=", - "dev": true - }, - "json-schema-traverse": { - "version": "0.3.1", - "resolved": "https://registry.npmjs.org/json-schema-traverse/-/json-schema-traverse-0.3.1.tgz", - "integrity": "sha1-NJptRMU6Ud6JtAgFxdXlm0F9M0A=", - "dev": true - }, - "json-stable-stringify": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/json-stable-stringify/-/json-stable-stringify-1.0.1.tgz", - "integrity": "sha1-mnWdOcXy/1A/1TAGRu1EX4jE+a8=", - "dev": true, - "requires": { - "jsonify": "0.0.0" - } - }, - "json-stringify-safe": { - "version": "5.0.1", - "resolved": "https://registry.npmjs.org/json-stringify-safe/-/json-stringify-safe-5.0.1.tgz", - "integrity": "sha1-Epai1Y/UXxmg9s4B1lcB4sc1tus=", - "dev": true - }, - "json3": { - "version": "3.3.2", - "resolved": "https://registry.npmjs.org/json3/-/json3-3.3.2.tgz", - "integrity": "sha1-PAQ0dD35Pi9cQq7nsZvLSDV19OE=", - "dev": true - }, - "jsonify": { - "version": "0.0.0", - "resolved": "https://registry.npmjs.org/jsonify/-/jsonify-0.0.0.tgz", - "integrity": "sha1-LHS27kHZPKUbe1qu6PUDYx0lKnM=", - "dev": true - }, - "jsonpointer": { - "version": "4.0.1", - "resolved": "https://registry.npmjs.org/jsonpointer/-/jsonpointer-4.0.1.tgz", - "integrity": "sha1-T9kss04OnbPInIYi7PUfm5eMbLk=", - "dev": true - }, - "jsprim": { - "version": "1.4.1", - "resolved": "https://registry.npmjs.org/jsprim/-/jsprim-1.4.1.tgz", - "integrity": "sha1-MT5mvB5cwG5Di8G3SZwuXFastqI=", - "dev": true, - "requires": { - "assert-plus": "1.0.0", - "extsprintf": "1.3.0", - "json-schema": "0.2.3", - "verror": "1.10.0" - }, - "dependencies": { - "assert-plus": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/assert-plus/-/assert-plus-1.0.0.tgz", - "integrity": "sha1-8S4PPF13sLHN2RRpQuTpbB5N1SU=", - "dev": true - } - } - }, - "kind-of": { - "version": "3.2.2", - "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-3.2.2.tgz", - "integrity": "sha1-MeohpzS6ubuw8yRm2JOupR5KPGQ=", - "dev": true, - "requires": { - "is-buffer": "https://registry.npmjs.org/is-buffer/-/is-buffer-1.1.6.tgz" - } - }, - "lazystream": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/lazystream/-/lazystream-1.0.0.tgz", - "integrity": "sha1-9plf4PggOS9hOWvolGJAe7dxaOQ=", - "dev": true, - "requires": { - "readable-stream": "https://registry.npmjs.org/readable-stream/-/readable-stream-2.3.3.tgz" - }, - "dependencies": { - "isarray": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/isarray/-/isarray-1.0.0.tgz", - "integrity": "sha1-u5NdSFgsuhaMBoNJV6VKPgcSTxE=", - "dev": true - }, - "readable-stream": { - "version": "https://registry.npmjs.org/readable-stream/-/readable-stream-2.3.3.tgz", - "integrity": "sha1-No8lEtefnUb9/HE0mueHi7weuVw=", - "dev": true, - "requires": { - "core-util-is": "1.0.2", - "inherits": "https://registry.npmjs.org/inherits/-/inherits-2.0.3.tgz", - "isarray": "1.0.0", - "process-nextick-args": "1.0.7", - "safe-buffer": "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.1.1.tgz", - "string_decoder": "https://registry.npmjs.org/string_decoder/-/string_decoder-1.0.3.tgz", - "util-deprecate": "1.0.2" - } - }, - "string_decoder": { - "version": "https://registry.npmjs.org/string_decoder/-/string_decoder-1.0.3.tgz", - "integrity": "sha1-D8Z9fBQYJd6UKC3VNr7GubzoYKs=", - "dev": true, - "requires": { - "safe-buffer": "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.1.1.tgz" - } - } - } - }, - "lcid": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/lcid/-/lcid-1.0.0.tgz", - "integrity": "sha1-MIrMr6C8SDo4Z7S28rlQYlHRuDU=", - "dev": true, - "requires": { - "invert-kv": "1.0.0" - } - }, - "liftoff": { - "version": "2.3.0", - "resolved": "https://registry.npmjs.org/liftoff/-/liftoff-2.3.0.tgz", - "integrity": "sha1-qY8v9nGD2Lp8+soQVIvX/wVQs4U=", - "dev": true, - "requires": { - "extend": "https://registry.npmjs.org/extend/-/extend-3.0.1.tgz", - "findup-sync": "0.4.3", - "fined": "1.1.0", - "flagged-respawn": "0.3.2", - "lodash.isplainobject": "4.0.6", - "lodash.isstring": "4.0.1", - "lodash.mapvalues": "4.6.0", - "rechoir": "0.6.2", - "resolve": "https://registry.npmjs.org/resolve/-/resolve-1.5.0.tgz" - } - }, - "linkify-it": { - "version": "2.0.3", - "resolved": "https://registry.npmjs.org/linkify-it/-/linkify-it-2.0.3.tgz", - "integrity": "sha1-2UpGSPmxwXnWT6lykSaL22zpQ08=", - "dev": true, - "requires": { - "uc.micro": "1.0.3" - } - }, - "lodash": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/lodash/-/lodash-1.0.2.tgz", - "integrity": "sha1-j1dWDIO1n8JwvT1WG2kAQ0MOJVE=", - "dev": true - }, - "lodash._baseassign": { - "version": "3.2.0", - "resolved": "https://registry.npmjs.org/lodash._baseassign/-/lodash._baseassign-3.2.0.tgz", - "integrity": "sha1-jDigmVAPIVrQnlnxci/QxSv+Ck4=", - "dev": true, - "requires": { - "lodash._basecopy": "3.0.1", - "lodash.keys": "3.1.2" - } - }, - "lodash._basecopy": { - "version": "3.0.1", - "resolved": "https://registry.npmjs.org/lodash._basecopy/-/lodash._basecopy-3.0.1.tgz", - "integrity": "sha1-jaDmqHbPNEwK2KVIghEd08XHyjY=", - "dev": true - }, - "lodash._basecreate": { - "version": "3.0.3", - "resolved": "https://registry.npmjs.org/lodash._basecreate/-/lodash._basecreate-3.0.3.tgz", - "integrity": "sha1-G8ZhYU2qf8MRt9A78WgGoCE8+CE=", - "dev": true - }, - "lodash._basetostring": { - "version": "3.0.1", - "resolved": "https://registry.npmjs.org/lodash._basetostring/-/lodash._basetostring-3.0.1.tgz", - "integrity": "sha1-0YYdh3+CSlL2aYMtyvPuFVZqB9U=", - "dev": true - }, - "lodash._basevalues": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/lodash._basevalues/-/lodash._basevalues-3.0.0.tgz", - "integrity": "sha1-W3dXYoAr3j0yl1A+JjAIIP32Ybc=", - "dev": true - }, - "lodash._getnative": { - "version": "3.9.1", - "resolved": "https://registry.npmjs.org/lodash._getnative/-/lodash._getnative-3.9.1.tgz", - "integrity": "sha1-VwvH3t5G1hzc3mh9ZdPuy6o6r/U=", - "dev": true - }, - "lodash._isiterateecall": { - "version": "3.0.9", - "resolved": "https://registry.npmjs.org/lodash._isiterateecall/-/lodash._isiterateecall-3.0.9.tgz", - "integrity": "sha1-UgOte6Ql+uhCRg5pbbnPPmqsBXw=", - "dev": true - }, - "lodash._reescape": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/lodash._reescape/-/lodash._reescape-3.0.0.tgz", - "integrity": "sha1-Kx1vXf4HyKNVdT5fJ/rH8c3hYWo=", - "dev": true - }, - "lodash._reevaluate": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/lodash._reevaluate/-/lodash._reevaluate-3.0.0.tgz", - "integrity": "sha1-WLx0xAZklTrgsSTYBpltrKQx4u0=", - "dev": true - }, - "lodash._reinterpolate": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/lodash._reinterpolate/-/lodash._reinterpolate-3.0.0.tgz", - "integrity": "sha1-DM8tiRZq8Ds2Y8eWU4t1rG4RTZ0=", - "dev": true - }, - "lodash._root": { - "version": "3.0.1", - "resolved": "https://registry.npmjs.org/lodash._root/-/lodash._root-3.0.1.tgz", - "integrity": "sha1-+6HEUkwZ7ppfgTa0YJ8BfPTe1pI=", - "dev": true - }, - "lodash.create": { - "version": "3.1.1", - "resolved": "https://registry.npmjs.org/lodash.create/-/lodash.create-3.1.1.tgz", - "integrity": "sha1-1/KEnw29p+BGgruM1yqwIkYd6+c=", - "dev": true, - "requires": { - "lodash._baseassign": "3.2.0", - "lodash._basecreate": "3.0.3", - "lodash._isiterateecall": "3.0.9" - } - }, - "lodash.escape": { - "version": "3.2.0", - "resolved": "https://registry.npmjs.org/lodash.escape/-/lodash.escape-3.2.0.tgz", - "integrity": "sha1-mV7g3BjBtIzJLv+ucaEKq1tIdpg=", - "dev": true, - "requires": { - "lodash._root": "3.0.1" - } - }, - "lodash.isarguments": { - "version": "3.1.0", - "resolved": "https://registry.npmjs.org/lodash.isarguments/-/lodash.isarguments-3.1.0.tgz", - "integrity": "sha1-L1c9hcaiQon/AGY7SRwdM4/zRYo=", - "dev": true - }, - "lodash.isarray": { - "version": "3.0.4", - "resolved": "https://registry.npmjs.org/lodash.isarray/-/lodash.isarray-3.0.4.tgz", - "integrity": "sha1-eeTriMNqgSKvhvhEqpvNhRtfu1U=", - "dev": true - }, - "lodash.isequal": { - "version": "4.5.0", - "resolved": "https://registry.npmjs.org/lodash.isequal/-/lodash.isequal-4.5.0.tgz", - "integrity": "sha1-QVxEePK8wwEgwizhDtMib30+GOA=", - "dev": true - }, - "lodash.isplainobject": { - "version": "4.0.6", - "resolved": "https://registry.npmjs.org/lodash.isplainobject/-/lodash.isplainobject-4.0.6.tgz", - "integrity": "sha1-fFJqUtibRcRcxpC4gWO+BJf1UMs=", - "dev": true - }, - "lodash.isstring": { - "version": "4.0.1", - "resolved": "https://registry.npmjs.org/lodash.isstring/-/lodash.isstring-4.0.1.tgz", - "integrity": "sha1-1SfftUVuynzJu5XV2ur4i6VKVFE=", - "dev": true - }, - "lodash.keys": { - "version": "3.1.2", - "resolved": "https://registry.npmjs.org/lodash.keys/-/lodash.keys-3.1.2.tgz", - "integrity": "sha1-TbwEcrFWvlCgsoaFXRvQsMZWCYo=", - "dev": true, - "requires": { - "lodash._getnative": "3.9.1", - "lodash.isarguments": "3.1.0", - "lodash.isarray": "3.0.4" - } - }, - "lodash.mapvalues": { - "version": "4.6.0", - "resolved": "https://registry.npmjs.org/lodash.mapvalues/-/lodash.mapvalues-4.6.0.tgz", - "integrity": "sha1-G6+lAF3p3W9PJmaMMMo3IwzJaJw=", - "dev": true - }, - "lodash.restparam": { - "version": "3.6.1", - "resolved": "https://registry.npmjs.org/lodash.restparam/-/lodash.restparam-3.6.1.tgz", - "integrity": "sha1-k2pOMJ7zMKdkXtQUWYbIWuWyCAU=", - "dev": true - }, - "lodash.template": { - "version": "3.6.2", - "resolved": "https://registry.npmjs.org/lodash.template/-/lodash.template-3.6.2.tgz", - "integrity": "sha1-+M3sxhaaJVvpCYrosMU9N4kx0U8=", - "dev": true, - "requires": { - "lodash._basecopy": "3.0.1", - "lodash._basetostring": "3.0.1", - "lodash._basevalues": "3.0.0", - "lodash._isiterateecall": "3.0.9", - "lodash._reinterpolate": "3.0.0", - "lodash.escape": "3.2.0", - "lodash.keys": "3.1.2", - "lodash.restparam": "3.6.1", - "lodash.templatesettings": "3.1.1" - } - }, - "lodash.templatesettings": { - "version": "3.1.1", - "resolved": "https://registry.npmjs.org/lodash.templatesettings/-/lodash.templatesettings-3.1.1.tgz", - "integrity": "sha1-+zB4RHU7Zrnxr6VOJix0UwfbqOU=", - "dev": true, - "requires": { - "lodash._reinterpolate": "3.0.0", - "lodash.escape": "3.2.0" - } - }, - "lru-cache": { - "version": "2.7.3", - "resolved": "https://registry.npmjs.org/lru-cache/-/lru-cache-2.7.3.tgz", - "integrity": "sha1-bUUk6LlV+V1PW1iFHOId1y+06VI=", - "dev": true - }, - "lru-queue": { - "version": "0.1.0", - "resolved": "https://registry.npmjs.org/lru-queue/-/lru-queue-0.1.0.tgz", - "integrity": "sha1-Jzi9nw089PhEkMVzbEhpmsYyzaM=", - "dev": true, - "requires": { - "es5-ext": "0.10.37" - } - }, - "map-cache": { - "version": "0.2.2", - "resolved": "https://registry.npmjs.org/map-cache/-/map-cache-0.2.2.tgz", - "integrity": "sha1-wyq9C9ZSXZsFFkW7TyasXcmKDb8=", - "dev": true - }, - "map-stream": { - "version": "0.1.0", - "resolved": "https://registry.npmjs.org/map-stream/-/map-stream-0.1.0.tgz", - "integrity": "sha1-5WqpTEyAVaFkBKBnS3jyFffI4ZQ=", - "dev": true - }, - "markdown-it": { - "version": "https://registry.npmjs.org/markdown-it/-/markdown-it-8.4.0.tgz", - "integrity": "sha1-4kAIgb8XH3AY7RvZ2kQdrIr2MG0=", - "dev": true, - "requires": { - "argparse": "1.0.9", - "entities": "1.1.1", - "linkify-it": "2.0.3", - "mdurl": "1.0.1", - "uc.micro": "1.0.3" - } - }, - "mdurl": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/mdurl/-/mdurl-1.0.1.tgz", - "integrity": "sha1-/oWy7HWlkDfyrf7BAP1sYBdhFS4=", - "dev": true - }, - "memoizee": { - "version": "0.4.11", - "resolved": "https://registry.npmjs.org/memoizee/-/memoizee-0.4.11.tgz", - "integrity": "sha1-vemBdmPJ5A/bKk6hw2cpYIeujI8=", - "dev": true, - "requires": { - "d": "1.0.0", - "es5-ext": "0.10.37", - "es6-weak-map": "2.0.2", - "event-emitter": "0.3.5", - "is-promise": "2.1.0", - "lru-queue": "0.1.0", - "next-tick": "1.0.0", - "timers-ext": "0.1.2" - } - }, - "merge-stream": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/merge-stream/-/merge-stream-1.0.1.tgz", - "integrity": "sha1-QEEgLVCKNCugAXQAjfDCUbjBNeE=", - "dev": true, - "requires": { - "readable-stream": "https://registry.npmjs.org/readable-stream/-/readable-stream-2.3.3.tgz" - }, - "dependencies": { - "isarray": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/isarray/-/isarray-1.0.0.tgz", - "integrity": "sha1-u5NdSFgsuhaMBoNJV6VKPgcSTxE=", - "dev": true - }, - "readable-stream": { - "version": "https://registry.npmjs.org/readable-stream/-/readable-stream-2.3.3.tgz", - "integrity": "sha1-No8lEtefnUb9/HE0mueHi7weuVw=", - "dev": true, - "requires": { - "core-util-is": "1.0.2", - "inherits": "https://registry.npmjs.org/inherits/-/inherits-2.0.3.tgz", - "isarray": "1.0.0", - "process-nextick-args": "1.0.7", - "safe-buffer": "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.1.1.tgz", - "string_decoder": "https://registry.npmjs.org/string_decoder/-/string_decoder-1.0.3.tgz", - "util-deprecate": "1.0.2" - } - }, - "string_decoder": { - "version": "https://registry.npmjs.org/string_decoder/-/string_decoder-1.0.3.tgz", - "integrity": "sha1-D8Z9fBQYJd6UKC3VNr7GubzoYKs=", - "dev": true, - "requires": { - "safe-buffer": "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.1.1.tgz" - } - } - } - }, - "micromatch": { - "version": "2.3.11", - "resolved": "https://registry.npmjs.org/micromatch/-/micromatch-2.3.11.tgz", - "integrity": "sha1-hmd8l9FyCzY0MdBNDRUpO9OMFWU=", - "dev": true, - "requires": { - "arr-diff": "2.0.0", - "array-unique": "0.2.1", - "braces": "1.8.5", - "expand-brackets": "0.1.5", - "extglob": "0.3.2", - "filename-regex": "2.0.1", - "is-extglob": "1.0.0", - "is-glob": "2.0.1", - "kind-of": "3.2.2", - "normalize-path": "2.1.1", - "object.omit": "2.0.1", - "parse-glob": "3.0.4", - "regex-cache": "https://registry.npmjs.org/regex-cache/-/regex-cache-0.4.4.tgz" - } - }, - "mime": { - "version": "1.6.0", - "resolved": "https://registry.npmjs.org/mime/-/mime-1.6.0.tgz", - "integrity": "sha512-x0Vn8spI+wuJ1O6S7gnbaQg8Pxh4NNHb7KSINmEWKiPE4RKOplvijn+NkmYmmRgP68mc70j2EbeTFRsrswaQeg==", - "dev": true - }, - "mime-db": { - "version": "1.30.0", - "resolved": "https://registry.npmjs.org/mime-db/-/mime-db-1.30.0.tgz", - "integrity": "sha1-dMZD2i3Z1qRTmZY0ZbJtXKfXHwE=", - "dev": true - }, - "mime-types": { - "version": "2.1.17", - "resolved": "https://registry.npmjs.org/mime-types/-/mime-types-2.1.17.tgz", - "integrity": "sha1-Cdejk/A+mVp5+K+Fe3Cp4KsWVXo=", - "dev": true, - "requires": { - "mime-db": "1.30.0" - } - }, - "minimatch": { - "version": "https://registry.npmjs.org/minimatch/-/minimatch-3.0.4.tgz", - "integrity": "sha1-UWbihkV/AzBgZL5Ul+jbsMPTIIM=", - "requires": { - "brace-expansion": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-1.1.8.tgz" - } - }, - "minimist": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/minimist/-/minimist-1.2.0.tgz", - "integrity": "sha1-o1AIsg9BOD7sH7kU9M1d95omQoQ=", - "dev": true - }, - "mkdirp": { - "version": "0.5.1", - "resolved": "https://registry.npmjs.org/mkdirp/-/mkdirp-0.5.1.tgz", - "integrity": "sha1-MAV0OOrGz3+MR2fzhkjWaX11yQM=", - "dev": true, - "requires": { - "minimist": "0.0.8" - }, - "dependencies": { - "minimist": { - "version": "0.0.8", - "resolved": "https://registry.npmjs.org/minimist/-/minimist-0.0.8.tgz", - "integrity": "sha1-hX/Kv8M5fSYluCKCYuhqp6ARsF0=", - "dev": true - } - } - }, - "mocha": { - "version": "3.5.3", - "resolved": "https://registry.npmjs.org/mocha/-/mocha-3.5.3.tgz", - "integrity": "sha512-/6na001MJWEtYxHOV1WLfsmR4YIynkUEhBwzsb+fk2qmQ3iqsi258l/Q2MWHJMImAcNpZ8DEdYAK72NHoIQ9Eg==", - "dev": true, - "requires": { - "browser-stdout": "1.3.0", - "commander": "2.9.0", - "debug": "https://registry.npmjs.org/debug/-/debug-2.6.8.tgz", - "diff": "3.2.0", - "escape-string-regexp": "1.0.5", - "glob": "7.1.1", - "growl": "1.9.2", - "he": "1.1.1", - "json3": "3.3.2", - "lodash.create": "3.1.1", - "mkdirp": "0.5.1", - "supports-color": "3.1.2" - }, - "dependencies": { - "glob": { - "version": "7.1.1", - "resolved": "https://registry.npmjs.org/glob/-/glob-7.1.1.tgz", - "integrity": "sha1-gFIR3wT6rxxjo2ADBs31reULLsg=", - "dev": true, - "requires": { - "fs.realpath": "https://registry.npmjs.org/fs.realpath/-/fs.realpath-1.0.0.tgz", - "inflight": "https://registry.npmjs.org/inflight/-/inflight-1.0.6.tgz", - "inherits": "https://registry.npmjs.org/inherits/-/inherits-2.0.3.tgz", - "minimatch": "https://registry.npmjs.org/minimatch/-/minimatch-3.0.4.tgz", - "once": "https://registry.npmjs.org/once/-/once-1.4.0.tgz", - "path-is-absolute": "https://registry.npmjs.org/path-is-absolute/-/path-is-absolute-1.0.1.tgz" - } - }, - "supports-color": { - "version": "3.1.2", - "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-3.1.2.tgz", - "integrity": "sha1-cqJiiU2dQIuVbKBf83su2KbiotU=", - "dev": true, - "requires": { - "has-flag": "1.0.0" - } - } - } - }, - "ms": { - "version": "https://registry.npmjs.org/ms/-/ms-2.0.0.tgz", - "integrity": "sha1-VgiurfwAvmwpAd9fmGF4jeDVl8g=" - }, - "multimatch": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/multimatch/-/multimatch-2.1.0.tgz", - "integrity": "sha1-nHkGoi+0wCkZ4vX3UWG0zb1LKis=", - "dev": true, - "requires": { - "array-differ": "1.0.0", - "array-union": "1.0.2", - "arrify": "1.0.1", - "minimatch": "https://registry.npmjs.org/minimatch/-/minimatch-3.0.4.tgz" - } - }, - "multipipe": { - "version": "0.1.2", - "resolved": "https://registry.npmjs.org/multipipe/-/multipipe-0.1.2.tgz", - "integrity": "sha1-Ko8t33Du1WTf8tV/HhoTfZ8FB4s=", - "dev": true, - "requires": { - "duplexer2": "0.0.2" - } - }, - "mute-stream": { - "version": "0.0.7", - "resolved": "https://registry.npmjs.org/mute-stream/-/mute-stream-0.0.7.tgz", - "integrity": "sha1-MHXOk7whuPq0PhvE2n6BFe0ee6s=", - "dev": true - }, - "natives": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/natives/-/natives-1.1.0.tgz", - "integrity": "sha1-6f+EFBimsux6SV6TmYT3jxY+bjE=", - "dev": true - }, - "next-tick": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/next-tick/-/next-tick-1.0.0.tgz", - "integrity": "sha1-yobR/ogoFpsBICCOPchCS524NCw=", - "dev": true - }, - "node.extend": { - "version": "1.1.6", - "resolved": "https://registry.npmjs.org/node.extend/-/node.extend-1.1.6.tgz", - "integrity": "sha1-p7iCyC1sk6SGOlUEvV3o7IYli5Y=", - "dev": true, - "requires": { - "is": "3.2.1" - } - }, - "noice-json-rpc": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/noice-json-rpc/-/noice-json-rpc-1.0.1.tgz", - "integrity": "sha1-XnKJpgocIIgEicsVEBVSusOSJm4=" - }, - "normalize-path": { - "version": "2.1.1", - "resolved": "https://registry.npmjs.org/normalize-path/-/normalize-path-2.1.1.tgz", - "integrity": "sha1-GrKLVW4Zg2Oowab35vogE3/mrtk=", - "dev": true, - "requires": { - "remove-trailing-separator": "1.1.0" - } - }, - "nth-check": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/nth-check/-/nth-check-1.0.1.tgz", - "integrity": "sha1-mSms32KPwsQQmN6rgqxYDPFJquQ=", - "dev": true, - "requires": { - "boolbase": "1.0.0" - } - }, - "number-is-nan": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/number-is-nan/-/number-is-nan-1.0.1.tgz", - "integrity": "sha1-CXtgK1NCKlIsGvuHkDGDNpQaAR0=", - "dev": true - }, - "oauth-sign": { - "version": "0.8.2", - "resolved": "https://registry.npmjs.org/oauth-sign/-/oauth-sign-0.8.2.tgz", - "integrity": "sha1-Rqarfwrq2N6unsBWV4C31O/rnUM=", - "dev": true - }, - "object-assign": { - "version": "4.1.1", - "resolved": "https://registry.npmjs.org/object-assign/-/object-assign-4.1.1.tgz", - "integrity": "sha1-IQmtx5ZYh8/AXLvUQsrIv7s2CGM=", - "dev": true - }, - "object.defaults": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/object.defaults/-/object.defaults-1.1.0.tgz", - "integrity": "sha1-On+GgzS0B96gbaFtiNXNKeQ1/s8=", - "dev": true, - "requires": { - "array-each": "1.0.1", - "array-slice": "1.0.0", - "for-own": "1.0.0", - "isobject": "3.0.1" - }, - "dependencies": { - "for-own": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/for-own/-/for-own-1.0.0.tgz", - "integrity": "sha1-xjMy9BXO3EsE2/5wz4NklMU8tEs=", - "dev": true, - "requires": { - "for-in": "1.0.2" - } - }, - "isobject": { - "version": "3.0.1", - "resolved": "https://registry.npmjs.org/isobject/-/isobject-3.0.1.tgz", - "integrity": "sha1-TkMekrEalzFjaqH5yNHMvP2reN8=", - "dev": true - } - } - }, - "object.omit": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/object.omit/-/object.omit-2.0.1.tgz", - "integrity": "sha1-Gpx0SCnznbuFjHbKNXmuKlTr0fo=", - "dev": true, - "requires": { - "for-own": "0.1.5", - "is-extendable": "0.1.1" - } - }, - "object.pick": { - "version": "1.3.0", - "resolved": "https://registry.npmjs.org/object.pick/-/object.pick-1.3.0.tgz", - "integrity": "sha1-h6EKxMFpS9Lhy/U1kaZhQftd10c=", - "dev": true, - "requires": { - "isobject": "3.0.1" - }, - "dependencies": { - "isobject": { - "version": "3.0.1", - "resolved": "https://registry.npmjs.org/isobject/-/isobject-3.0.1.tgz", - "integrity": "sha1-TkMekrEalzFjaqH5yNHMvP2reN8=", - "dev": true - } - } - }, - "once": { - "version": "https://registry.npmjs.org/once/-/once-1.4.0.tgz", - "integrity": "sha1-WDsap3WWHUsROsF9nFC6753Xa9E=", - "requires": { - "wrappy": "https://registry.npmjs.org/wrappy/-/wrappy-1.0.2.tgz" - } - }, - "options": { - "version": "0.0.6", - "resolved": "https://registry.npmjs.org/options/-/options-0.0.6.tgz", - "integrity": "sha1-7CLTEoBrtT5zF3Pnza788cZDEo8=" - }, - "orchestrator": { - "version": "0.3.8", - "resolved": "https://registry.npmjs.org/orchestrator/-/orchestrator-0.3.8.tgz", - "integrity": "sha1-FOfp4nZPcxX7rBhOUGx6pt+UrX4=", - "dev": true, - "requires": { - "end-of-stream": "0.1.5", - "sequencify": "0.0.7", - "stream-consume": "0.1.0" - } - }, - "ordered-read-streams": { - "version": "0.1.0", - "resolved": "https://registry.npmjs.org/ordered-read-streams/-/ordered-read-streams-0.1.0.tgz", - "integrity": "sha1-/VZamvjrRHO6abbtijQ1LLVS8SY=", - "dev": true - }, - "os-homedir": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/os-homedir/-/os-homedir-1.0.2.tgz", - "integrity": "sha1-/7xJiDNuDoM94MFox+8VISGqf7M=", - "dev": true - }, - "os-locale": { - "version": "1.4.0", - "resolved": "https://registry.npmjs.org/os-locale/-/os-locale-1.4.0.tgz", - "integrity": "sha1-IPnxeuKe00XoveWDsT0gCYA8FNk=", - "dev": true, - "requires": { - "lcid": "1.0.0" - } - }, - "os-tmpdir": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/os-tmpdir/-/os-tmpdir-1.0.2.tgz", - "integrity": "sha1-u+Z0BseaqFxc/sdm/lc0VV36EnQ=", - "dev": true - }, - "osenv": { - "version": "0.1.4", - "resolved": "https://registry.npmjs.org/osenv/-/osenv-0.1.4.tgz", - "integrity": "sha1-Qv5tWVPfBsgGS+bxdsPQWqqjRkQ=", - "dev": true, - "requires": { - "os-homedir": "1.0.2", - "os-tmpdir": "1.0.2" - } - }, - "parse-filepath": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/parse-filepath/-/parse-filepath-1.0.1.tgz", - "integrity": "sha1-FZ1hVdQ5BNFsEO9piRHaHpGWm3M=", - "dev": true, - "requires": { - "is-absolute": "0.2.6", - "map-cache": "0.2.2", - "path-root": "0.1.1" - } - }, - "parse-glob": { - "version": "3.0.4", - "resolved": "https://registry.npmjs.org/parse-glob/-/parse-glob-3.0.4.tgz", - "integrity": "sha1-ssN2z7EfNVE7rdFz7wu246OIORw=", - "dev": true, - "requires": { - "glob-base": "0.3.0", - "is-dotfile": "1.0.3", - "is-extglob": "1.0.0", - "is-glob": "2.0.1" - } - }, - "parse-passwd": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/parse-passwd/-/parse-passwd-1.0.0.tgz", - "integrity": "sha1-bVuTSkVpk7I9N/QKOC1vFmao5cY=", - "dev": true - }, - "parse-semver": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/parse-semver/-/parse-semver-1.1.1.tgz", - "integrity": "sha1-mkr9bfBj3Egm+T+6SpnPIj9mbLg=", - "dev": true, - "requires": { - "semver": "5.4.1" - }, - "dependencies": { - "semver": { - "version": "5.4.1", - "resolved": "https://registry.npmjs.org/semver/-/semver-5.4.1.tgz", - "integrity": "sha512-WfG/X9+oATh81XtllIo/I8gOiY9EXRdv1cQdyykeXK17YcUW3EXUAi2To4pcH6nZtJPr7ZOpM5OMyWJZm+8Rsg==", - "dev": true - } - } - }, - "parse5": { - "version": "https://registry.npmjs.org/parse5/-/parse5-3.0.3.tgz", - "integrity": "sha1-BC95L/3TaFFVHPTp4Gazh0q0W1w=", - "dev": true, - "requires": { - "@types/node": "6.0.92" - } - }, - "path-dirname": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/path-dirname/-/path-dirname-1.0.2.tgz", - "integrity": "sha1-zDPSTVJeCZpTiMAzbG4yuRYGCeA=", - "dev": true - }, - "path-is-absolute": { - "version": "https://registry.npmjs.org/path-is-absolute/-/path-is-absolute-1.0.1.tgz", - "integrity": "sha1-F0uSaHNVNP+8es5r9TpanhtcX18=" - }, - "path-is-inside": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/path-is-inside/-/path-is-inside-1.0.2.tgz", - "integrity": "sha1-NlQX3t5EQw0cEa9hAn+s8HS9/FM=", - "dev": true - }, - "path-parse": { - "version": "1.0.5", - "resolved": "https://registry.npmjs.org/path-parse/-/path-parse-1.0.5.tgz", - "integrity": "sha1-PBrfhx6pzWyUMbbqK9dKD/BVxME=", - "dev": true - }, - "path-root": { - "version": "0.1.1", - "resolved": "https://registry.npmjs.org/path-root/-/path-root-0.1.1.tgz", - "integrity": "sha1-mkpoFMrBwM1zNgqV8yCDyOpHRbc=", - "dev": true, - "requires": { - "path-root-regex": "0.1.2" - } - }, - "path-root-regex": { - "version": "0.1.2", - "resolved": "https://registry.npmjs.org/path-root-regex/-/path-root-regex-0.1.2.tgz", - "integrity": "sha1-v8zcjfWxLcUsi0PsONGNcsBLqW0=", - "dev": true - }, - "pause-stream": { - "version": "0.0.11", - "resolved": "https://registry.npmjs.org/pause-stream/-/pause-stream-0.0.11.tgz", - "integrity": "sha1-/lo0sMvOErWqaitAPuLnO2AvFEU=", - "dev": true, - "requires": { - "through": "2.3.8" - } - }, - "pend": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/pend/-/pend-1.2.0.tgz", - "integrity": "sha1-elfrVQpng/kRUzH89GY9XI4AelA=", - "dev": true - }, - "performance-now": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/performance-now/-/performance-now-2.1.0.tgz", - "integrity": "sha1-Ywn04OX6kT7BxpMHrjZLSzd8nns=", - "dev": true - }, - "pify": { - "version": "2.3.0", - "resolved": "https://registry.npmjs.org/pify/-/pify-2.3.0.tgz", - "integrity": "sha1-7RQaasBDqEnqWISY59yosVMw6Qw=", - "dev": true - }, - "pinkie": { - "version": "2.0.4", - "resolved": "https://registry.npmjs.org/pinkie/-/pinkie-2.0.4.tgz", - "integrity": "sha1-clVrgM+g1IqXToDnckjoDtT3+HA=", - "dev": true - }, - "pinkie-promise": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/pinkie-promise/-/pinkie-promise-2.0.1.tgz", - "integrity": "sha1-ITXW36ejWMBprJsXh3YogihFD/o=", - "dev": true, - "requires": { - "pinkie": "2.0.4" - } - }, - "preserve": { - "version": "0.2.0", - "resolved": "https://registry.npmjs.org/preserve/-/preserve-0.2.0.tgz", - "integrity": "sha1-gV7R9uvGWSb4ZbMQwHE7yzMVzks=", - "dev": true - }, - "pretty-hrtime": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/pretty-hrtime/-/pretty-hrtime-1.0.3.tgz", - "integrity": "sha1-t+PqQkNaTJsnWdmeDyAesZWALuE=", - "dev": true - }, - "process-nextick-args": { - "version": "1.0.7", - "resolved": "https://registry.npmjs.org/process-nextick-args/-/process-nextick-args-1.0.7.tgz", - "integrity": "sha1-FQ4gt1ZZCtP5EJPyWk8q2L/zC6M=", - "dev": true - }, - "punycode": { - "version": "1.4.1", - "resolved": "https://registry.npmjs.org/punycode/-/punycode-1.4.1.tgz", - "integrity": "sha1-wNWmOycYgArY4esPpSachN1BhF4=", - "dev": true - }, - "q": { - "version": "1.5.1", - "resolved": "https://registry.npmjs.org/q/-/q-1.5.1.tgz", - "integrity": "sha1-fjL3W0E4EpHQRhHxvxQQmsAGUdc=", - "dev": true - }, - "qs": { - "version": "6.3.2", - "resolved": "https://registry.npmjs.org/qs/-/qs-6.3.2.tgz", - "integrity": "sha1-51vV9uJoEioqDgvaYwslUMFmUCw=", - "dev": true - }, - "querystringify": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/querystringify/-/querystringify-1.0.0.tgz", - "integrity": "sha1-YoYkIRLFtxL6ZU5SZlK/ahP/Bcs=", - "dev": true - }, - "queue": { - "version": "3.1.0", - "resolved": "https://registry.npmjs.org/queue/-/queue-3.1.0.tgz", - "integrity": "sha1-bEnQHwCeIlZ4h4nyv/rGuLmZBYU=", - "dev": true, - "requires": { - "inherits": "https://registry.npmjs.org/inherits/-/inherits-2.0.3.tgz" - } - }, - "randomatic": { - "version": "https://registry.npmjs.org/randomatic/-/randomatic-1.1.7.tgz", - "integrity": "sha1-x6vpzIuHwLqodrGf3oP9RkeX44w=", - "dev": true, - "requires": { - "is-number": "3.0.0", - "kind-of": "4.0.0" - }, - "dependencies": { - "is-number": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/is-number/-/is-number-3.0.0.tgz", - "integrity": "sha1-JP1iAaR4LPUFYcgQJ2r8fRLXEZU=", - "dev": true, - "requires": { - "kind-of": "3.2.2" - }, - "dependencies": { - "kind-of": { - "version": "3.2.2", - "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-3.2.2.tgz", - "integrity": "sha1-MeohpzS6ubuw8yRm2JOupR5KPGQ=", - "dev": true, - "requires": { - "is-buffer": "https://registry.npmjs.org/is-buffer/-/is-buffer-1.1.6.tgz" - } - } - } - }, - "kind-of": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-4.0.0.tgz", - "integrity": "sha1-IIE989cSkosgc3hpGkUGb65y3Vc=", - "dev": true, - "requires": { - "is-buffer": "https://registry.npmjs.org/is-buffer/-/is-buffer-1.1.6.tgz" - } - } - } - }, - "read": { - "version": "1.0.7", - "resolved": "https://registry.npmjs.org/read/-/read-1.0.7.tgz", - "integrity": "sha1-s9oZvQUkMal2cdRKQmNK33ELQMQ=", - "dev": true, - "requires": { - "mute-stream": "0.0.7" - } - }, - "readable-stream": { - "version": "1.1.14", - "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-1.1.14.tgz", - "integrity": "sha1-fPTFTvZI44EwhMY23SB54WbAgdk=", - "dev": true, - "requires": { - "core-util-is": "1.0.2", - "inherits": "https://registry.npmjs.org/inherits/-/inherits-2.0.3.tgz", - "isarray": "0.0.1", - "string_decoder": "0.10.31" - } - }, - "rechoir": { - "version": "0.6.2", - "resolved": "https://registry.npmjs.org/rechoir/-/rechoir-0.6.2.tgz", - "integrity": "sha1-hSBLVNuoLVdC4oyWdW70OvUOM4Q=", - "dev": true, - "requires": { - "resolve": "https://registry.npmjs.org/resolve/-/resolve-1.5.0.tgz" - } - }, - "regex-cache": { - "version": "https://registry.npmjs.org/regex-cache/-/regex-cache-0.4.4.tgz", - "integrity": "sha1-db3FiioUls7EihKDW8VMjVYjNt0=", - "dev": true, - "requires": { - "is-equal-shallow": "0.1.3" - } - }, - "remove-trailing-separator": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/remove-trailing-separator/-/remove-trailing-separator-1.1.0.tgz", - "integrity": "sha1-wkvOKig62tW8P1jg1IJJuSN52O8=", - "dev": true - }, - "repeat-element": { - "version": "1.1.2", - "resolved": "https://registry.npmjs.org/repeat-element/-/repeat-element-1.1.2.tgz", - "integrity": "sha1-7wiaF40Ug7quTZPrmLT55OEdmQo=", - "dev": true - }, - "repeat-string": { - "version": "1.6.1", - "resolved": "https://registry.npmjs.org/repeat-string/-/repeat-string-1.6.1.tgz", - "integrity": "sha1-jcrkcOHIirwtYA//Sndihtp15jc=", - "dev": true - }, - "replace-ext": { - "version": "0.0.1", - "resolved": "https://registry.npmjs.org/replace-ext/-/replace-ext-0.0.1.tgz", - "integrity": "sha1-KbvZIHinOfC8zitO5B6DeVNSKSQ=", - "dev": true - }, - "request": { - "version": "https://registry.npmjs.org/request/-/request-2.83.0.tgz", - "integrity": "sha1-ygtl2gLtYpNYh4COb1EDgQNOM1Y=", - "dev": true, - "requires": { - "aws-sign2": "0.7.0", - "aws4": "1.6.0", - "caseless": "0.12.0", - "combined-stream": "1.0.5", - "extend": "https://registry.npmjs.org/extend/-/extend-3.0.1.tgz", - "forever-agent": "0.6.1", - "form-data": "2.3.1", - "har-validator": "5.0.3", - "hawk": "https://registry.npmjs.org/hawk/-/hawk-6.0.2.tgz", - "http-signature": "1.2.0", - "is-typedarray": "1.0.0", - "isstream": "0.1.2", - "json-stringify-safe": "5.0.1", - "mime-types": "2.1.17", - "oauth-sign": "0.8.2", - "performance-now": "2.1.0", - "qs": "https://registry.npmjs.org/qs/-/qs-6.5.1.tgz", - "safe-buffer": "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.1.1.tgz", - "stringstream": "0.0.5", - "tough-cookie": "2.3.3", - "tunnel-agent": "0.6.0", - "uuid": "https://registry.npmjs.org/uuid/-/uuid-3.1.0.tgz" - }, - "dependencies": { - "assert-plus": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/assert-plus/-/assert-plus-1.0.0.tgz", - "integrity": "sha1-8S4PPF13sLHN2RRpQuTpbB5N1SU=", - "dev": true - }, - "aws-sign2": { - "version": "0.7.0", - "resolved": "https://registry.npmjs.org/aws-sign2/-/aws-sign2-0.7.0.tgz", - "integrity": "sha1-tG6JCTSpWR8tL2+G1+ap8bP+dqg=", - "dev": true - }, - "boom": { - "version": "4.3.1", - "resolved": "https://registry.npmjs.org/boom/-/boom-4.3.1.tgz", - "integrity": "sha1-T4owBctKfjiJ90kDD9JbluAdLjE=", - "dev": true, - "requires": { - "hoek": "https://registry.npmjs.org/hoek/-/hoek-4.2.0.tgz" - } - }, - "caseless": { - "version": "0.12.0", - "resolved": "https://registry.npmjs.org/caseless/-/caseless-0.12.0.tgz", - "integrity": "sha1-G2gcIf+EAzyCZUMJBolCDRhxUdw=", - "dev": true - }, - "cryptiles": { - "version": "3.1.2", - "resolved": "https://registry.npmjs.org/cryptiles/-/cryptiles-3.1.2.tgz", - "integrity": "sha1-qJ+7Ig9c4l7FboxKqKT9e1sNKf4=", - "dev": true, - "requires": { - "boom": "https://registry.npmjs.org/boom/-/boom-5.2.0.tgz" - }, - "dependencies": { - "boom": { - "version": "https://registry.npmjs.org/boom/-/boom-5.2.0.tgz", - "integrity": "sha1-XdnabuOl8wIHdDYpDLcX0/SlTgI=", - "dev": true, - "requires": { - "hoek": "https://registry.npmjs.org/hoek/-/hoek-4.2.0.tgz" - } - } - } - }, - "form-data": { - "version": "2.3.1", - "resolved": "https://registry.npmjs.org/form-data/-/form-data-2.3.1.tgz", - "integrity": "sha1-b7lPvXGIUwbXPRXMSX/kzE7NRL8=", - "dev": true, - "requires": { - "asynckit": "0.4.0", - "combined-stream": "1.0.5", - "mime-types": "2.1.17" - } - }, - "har-validator": { - "version": "5.0.3", - "resolved": "https://registry.npmjs.org/har-validator/-/har-validator-5.0.3.tgz", - "integrity": "sha1-ukAsJmGU8VlW7xXg/PJCmT9qff0=", - "dev": true, - "requires": { - "ajv": "5.5.0", - "har-schema": "2.0.0" - } - }, - "hawk": { - "version": "https://registry.npmjs.org/hawk/-/hawk-6.0.2.tgz", - "integrity": "sha1-r02RTrBl+bXOTZ0RwcshJu7MMDg=", - "dev": true, - "requires": { - "boom": "4.3.1", - "cryptiles": "3.1.2", - "hoek": "https://registry.npmjs.org/hoek/-/hoek-4.2.0.tgz", - "sntp": "https://registry.npmjs.org/sntp/-/sntp-2.1.0.tgz" - } - }, - "hoek": { - "version": "https://registry.npmjs.org/hoek/-/hoek-4.2.0.tgz", - "integrity": "sha1-ctnQdU9/4lyi0BrY+PmpRJqJUm0=", - "dev": true - }, - "http-signature": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/http-signature/-/http-signature-1.2.0.tgz", - "integrity": "sha1-muzZJRFHcvPZW2WmCruPfBj7rOE=", - "dev": true, - "requires": { - "assert-plus": "1.0.0", - "jsprim": "1.4.1", - "sshpk": "1.13.1" - } - }, - "qs": { - "version": "https://registry.npmjs.org/qs/-/qs-6.5.1.tgz", - "integrity": "sha1-NJzfbu+J7EXBLX1es/wMhwNDptg=", - "dev": true - }, - "sntp": { - "version": "https://registry.npmjs.org/sntp/-/sntp-2.1.0.tgz", - "integrity": "sha1-LGzsFP7cIiJznK+bXD2F0cxaLMg=", - "dev": true, - "requires": { - "hoek": "https://registry.npmjs.org/hoek/-/hoek-4.2.0.tgz" - } - }, - "tunnel-agent": { - "version": "0.6.0", - "resolved": "https://registry.npmjs.org/tunnel-agent/-/tunnel-agent-0.6.0.tgz", - "integrity": "sha1-J6XeoGs2sEoKmWZ3SykIaPD8QP0=", - "dev": true, - "requires": { - "safe-buffer": "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.1.1.tgz" - } - } - } - }, - "request-light": { - "version": "0.1.0", - "resolved": "https://registry.npmjs.org/request-light/-/request-light-0.1.0.tgz", - "integrity": "sha1-/mXd/7suh5RPDMr9hcuDnpE4U0U=", - "requires": { - "http-proxy-agent": "0.2.7", - "https-proxy-agent": "0.3.6", - "vscode-nls": "1.0.7" - }, - "dependencies": { - "vscode-nls": { - "version": "1.0.7", - "resolved": "https://registry.npmjs.org/vscode-nls/-/vscode-nls-1.0.7.tgz", - "integrity": "sha1-KYwB/Oh4AsZEwKFe9SajPGLA1Y4=" - } - } - }, - "requires-port": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/requires-port/-/requires-port-1.0.0.tgz", - "integrity": "sha1-kl0mAdOaxIXgkc8NpcbmlNw9yv8=", - "dev": true - }, - "resolve": { - "version": "https://registry.npmjs.org/resolve/-/resolve-1.5.0.tgz", - "integrity": "sha1-HwmsznlsmnYlefMbLBzEw83fnzY=", - "dev": true, - "requires": { - "path-parse": "1.0.5" - } - }, - "resolve-dir": { - "version": "0.1.1", - "resolved": "https://registry.npmjs.org/resolve-dir/-/resolve-dir-0.1.1.tgz", - "integrity": "sha1-shklmlYC+sXFxJatiUpujMQwJh4=", - "dev": true, - "requires": { - "expand-tilde": "1.2.2", - "global-modules": "0.2.3" - } - }, - "resolve-url": { - "version": "0.2.1", - "resolved": "https://registry.npmjs.org/resolve-url/-/resolve-url-0.2.1.tgz", - "integrity": "sha1-LGN/53yJOv0qZj/iGqkIAGjiBSo=", - "dev": true - }, - "rimraf": { - "version": "https://registry.npmjs.org/rimraf/-/rimraf-2.6.2.tgz", - "integrity": "sha1-LtgVDSShbqhlHm1u8PR8QVjOejY=", - "dev": true, - "requires": { - "glob": "https://registry.npmjs.org/glob/-/glob-7.1.2.tgz" - } - }, - "run-sequence": { - "version": "1.2.2", - "resolved": "https://registry.npmjs.org/run-sequence/-/run-sequence-1.2.2.tgz", - "integrity": "sha1-UJWgvr6YczsBQL0I3YDsAw3azes=", - "dev": true, - "requires": { - "chalk": "1.1.3", - "gulp-util": "3.0.8" - } - }, - "safe-buffer": { - "version": "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.1.1.tgz", - "integrity": "sha1-iTMSr2myEj3vcfV4iQAWce6yyFM=", - "dev": true - }, - "sax": { - "version": "https://registry.npmjs.org/sax/-/sax-1.2.4.tgz", - "integrity": "sha1-KBYjTiN4vdxOU1T6tcqold9xANk=", - "dev": true - }, - "semver": { - "version": "4.3.6", - "resolved": "https://registry.npmjs.org/semver/-/semver-4.3.6.tgz", - "integrity": "sha1-MAvG4OhjdPe6YQaLWx7NV/xlMto=", - "dev": true - }, - "sequencify": { - "version": "0.0.7", - "resolved": "https://registry.npmjs.org/sequencify/-/sequencify-0.0.7.tgz", - "integrity": "sha1-kM/xnQLgcCf9dn9erT57ldHnOAw=", - "dev": true - }, - "sigmund": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/sigmund/-/sigmund-1.0.1.tgz", - "integrity": "sha1-P/IfGYytIXX587eBhT/ZTQ0ZtZA=", - "dev": true - }, - "sntp": { - "version": "1.0.9", - "resolved": "https://registry.npmjs.org/sntp/-/sntp-1.0.9.tgz", - "integrity": "sha1-ZUEYTMkK7qbG57NeJlkIJEPGYZg=", - "dev": true, - "requires": { - "hoek": "2.16.3" - } - }, - "source-map": { - "version": "https://registry.npmjs.org/source-map/-/source-map-0.5.6.tgz", - "integrity": "sha1-dc449SvwczxafwwRjYEzSiu19BI=" - }, - "source-map-resolve": { - "version": "0.3.1", - "resolved": "https://registry.npmjs.org/source-map-resolve/-/source-map-resolve-0.3.1.tgz", - "integrity": "sha1-YQ9hIqRFuN1RU1oqcbeD38Ekh2E=", - "dev": true, - "requires": { - "atob": "1.1.3", - "resolve-url": "0.2.1", - "source-map-url": "0.3.0", - "urix": "0.1.0" - } - }, - "source-map-support": { - "version": "0.5.0", - "resolved": "https://registry.npmjs.org/source-map-support/-/source-map-support-0.5.0.tgz", - "integrity": "sha512-vUoN3I7fHQe0R/SJLKRdKYuEdRGogsviXFkHHo17AWaTGv17VLnxw+CFXvqy+y4ORZ3doWLQcxRYfwKrsd/H7Q==", - "dev": true, - "requires": { - "source-map": "0.6.1" - }, - "dependencies": { - "source-map": { - "version": "0.6.1", - "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.6.1.tgz", - "integrity": "sha512-UjgapumWlbMhkBgzT7Ykc5YXUT46F0iKu8SGXq0bcwP5dz/h0Plj6enJqjz1Zbq2l5WaqYnrVbwWOWMyF3F47g==", - "dev": true - } - } - }, - "source-map-url": { - "version": "0.3.0", - "resolved": "https://registry.npmjs.org/source-map-url/-/source-map-url-0.3.0.tgz", - "integrity": "sha1-fsrxO1e80J2opAxdJp2zN5nUqvk=", - "dev": true - }, - "sparkles": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/sparkles/-/sparkles-1.0.0.tgz", - "integrity": "sha1-Gsu/tZJDbRC76PeFt8xvgoFQEsM=", - "dev": true - }, - "split": { - "version": "0.3.3", - "resolved": "https://registry.npmjs.org/split/-/split-0.3.3.tgz", - "integrity": "sha1-zQ7qXmOiEd//frDwkcQTPi0N0o8=", - "dev": true, - "requires": { - "through": "2.3.8" - } - }, - "sprintf-js": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/sprintf-js/-/sprintf-js-1.0.3.tgz", - "integrity": "sha1-BOaSb2YolTVPPdAVIDYzuFcpfiw=", - "dev": true - }, - "sshpk": { - "version": "1.13.1", - "resolved": "https://registry.npmjs.org/sshpk/-/sshpk-1.13.1.tgz", - "integrity": "sha1-US322mKHFEMW3EwY/hzx2UBzm+M=", - "dev": true, - "requires": { - "asn1": "0.2.3", - "assert-plus": "1.0.0", - "bcrypt-pbkdf": "1.0.1", - "dashdash": "1.14.1", - "ecc-jsbn": "0.1.1", - "getpass": "0.1.7", - "jsbn": "0.1.1", - "tweetnacl": "0.14.5" - }, - "dependencies": { - "assert-plus": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/assert-plus/-/assert-plus-1.0.0.tgz", - "integrity": "sha1-8S4PPF13sLHN2RRpQuTpbB5N1SU=", - "dev": true - } - } - }, - "stat-mode": { - "version": "0.2.2", - "resolved": "https://registry.npmjs.org/stat-mode/-/stat-mode-0.2.2.tgz", - "integrity": "sha1-5sgLYjEj19gM8TLOU480YokHJQI=", - "dev": true - }, - "stream-combiner": { - "version": "0.0.4", - "resolved": "https://registry.npmjs.org/stream-combiner/-/stream-combiner-0.0.4.tgz", - "integrity": "sha1-TV5DPBhSYd3mI8o/RMWGvPXErRQ=", - "dev": true, - "requires": { - "duplexer": "0.1.1" - } - }, - "stream-consume": { - "version": "0.1.0", - "resolved": "https://registry.npmjs.org/stream-consume/-/stream-consume-0.1.0.tgz", - "integrity": "sha1-pB6tGm1ggc63n2WwYZAbbY89HQ8=", - "dev": true - }, - "stream-shift": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/stream-shift/-/stream-shift-1.0.0.tgz", - "integrity": "sha1-1cdSgl5TZ+eG944Y5EXqIjoVWVI=", - "dev": true - }, - "streamfilter": { - "version": "1.0.5", - "resolved": "https://registry.npmjs.org/streamfilter/-/streamfilter-1.0.5.tgz", - "integrity": "sha1-h1BxEb644phFFxe1Ec/tjwAqv1M=", - "dev": true, - "requires": { - "readable-stream": "https://registry.npmjs.org/readable-stream/-/readable-stream-2.3.3.tgz" - }, - "dependencies": { - "isarray": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/isarray/-/isarray-1.0.0.tgz", - "integrity": "sha1-u5NdSFgsuhaMBoNJV6VKPgcSTxE=", - "dev": true - }, - "readable-stream": { - "version": "https://registry.npmjs.org/readable-stream/-/readable-stream-2.3.3.tgz", - "integrity": "sha1-No8lEtefnUb9/HE0mueHi7weuVw=", - "dev": true, - "requires": { - "core-util-is": "1.0.2", - "inherits": "https://registry.npmjs.org/inherits/-/inherits-2.0.3.tgz", - "isarray": "1.0.0", - "process-nextick-args": "1.0.7", - "safe-buffer": "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.1.1.tgz", - "string_decoder": "https://registry.npmjs.org/string_decoder/-/string_decoder-1.0.3.tgz", - "util-deprecate": "1.0.2" - } - }, - "string_decoder": { - "version": "https://registry.npmjs.org/string_decoder/-/string_decoder-1.0.3.tgz", - "integrity": "sha1-D8Z9fBQYJd6UKC3VNr7GubzoYKs=", - "dev": true, - "requires": { - "safe-buffer": "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.1.1.tgz" - } - } - } - }, - "streamifier": { - "version": "0.1.1", - "resolved": "https://registry.npmjs.org/streamifier/-/streamifier-0.1.1.tgz", - "integrity": "sha1-l+mNj6TRBdYqJpHR3AfoINuN/E8=", - "dev": true - }, - "string-width": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/string-width/-/string-width-1.0.2.tgz", - "integrity": "sha1-EYvfW4zcUaKn5w0hHgfisLmxB9M=", - "dev": true, - "requires": { - "code-point-at": "1.1.0", - "is-fullwidth-code-point": "1.0.0", - "strip-ansi": "3.0.1" - } - }, - "string_decoder": { - "version": "0.10.31", - "resolved": "https://registry.npmjs.org/string_decoder/-/string_decoder-0.10.31.tgz", - "integrity": "sha1-YuIDvEF2bGwoyfyEMB2rHFMQ+pQ=", - "dev": true - }, - "stringstream": { - "version": "0.0.5", - "resolved": "https://registry.npmjs.org/stringstream/-/stringstream-0.0.5.tgz", - "integrity": "sha1-TkhM1N5aC7vuGORjB3EKioFiGHg=", - "dev": true - }, - "strip-ansi": { - "version": "3.0.1", - "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-3.0.1.tgz", - "integrity": "sha1-ajhfuIU9lS1f8F0Oiq+UJ43GPc8=", - "dev": true, - "requires": { - "ansi-regex": "2.1.1" - } - }, - "strip-bom": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/strip-bom/-/strip-bom-1.0.0.tgz", - "integrity": "sha1-hbiGLzhEtabV7IRnqTWYFzo295Q=", - "dev": true, - "requires": { - "first-chunk-stream": "1.0.0", - "is-utf8": "0.2.1" - } - }, - "strip-bom-stream": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/strip-bom-stream/-/strip-bom-stream-1.0.0.tgz", - "integrity": "sha1-5xRDmFd9Uaa+0PoZlPoF9D/ZiO4=", - "dev": true, - "requires": { - "first-chunk-stream": "1.0.0", - "strip-bom": "2.0.0" - }, - "dependencies": { - "strip-bom": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/strip-bom/-/strip-bom-2.0.0.tgz", - "integrity": "sha1-YhmoVhZSBJHzV4i9vxRHqZx+aw4=", - "dev": true, - "requires": { - "is-utf8": "0.2.1" - } - } - } - }, - "strip-bom-string": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/strip-bom-string/-/strip-bom-string-1.0.0.tgz", - "integrity": "sha1-5SEekiQ2n7uB1jOi8ABE3IztrZI=", - "dev": true - }, - "supports-color": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-2.0.0.tgz", - "integrity": "sha1-U10EXOa2Nj+kARcIRimZXp3zJMc=", - "dev": true - }, - "tar": { - "version": "2.2.1", - "resolved": "https://registry.npmjs.org/tar/-/tar-2.2.1.tgz", - "integrity": "sha1-jk0qJWwOIYXGsYrWlK7JaLg8sdE=", - "dev": true, - "requires": { - "block-stream": "0.0.9", - "fstream": "1.0.11", - "inherits": "https://registry.npmjs.org/inherits/-/inherits-2.0.3.tgz" - } - }, - "through": { - "version": "2.3.8", - "resolved": "https://registry.npmjs.org/through/-/through-2.3.8.tgz", - "integrity": "sha1-DdTJ/6q8NXlgsbckEV1+Doai4fU=", - "dev": true - }, - "through2": { - "version": "2.0.3", - "resolved": "https://registry.npmjs.org/through2/-/through2-2.0.3.tgz", - "integrity": "sha1-AARWmzfHx0ujnEPzzteNGtlBQL4=", - "dev": true, - "requires": { - "readable-stream": "https://registry.npmjs.org/readable-stream/-/readable-stream-2.3.3.tgz", - "xtend": "4.0.1" - }, - "dependencies": { - "isarray": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/isarray/-/isarray-1.0.0.tgz", - "integrity": "sha1-u5NdSFgsuhaMBoNJV6VKPgcSTxE=", - "dev": true - }, - "readable-stream": { - "version": "https://registry.npmjs.org/readable-stream/-/readable-stream-2.3.3.tgz", - "integrity": "sha1-No8lEtefnUb9/HE0mueHi7weuVw=", - "dev": true, - "requires": { - "core-util-is": "1.0.2", - "inherits": "https://registry.npmjs.org/inherits/-/inherits-2.0.3.tgz", - "isarray": "1.0.0", - "process-nextick-args": "1.0.7", - "safe-buffer": "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.1.1.tgz", - "string_decoder": "https://registry.npmjs.org/string_decoder/-/string_decoder-1.0.3.tgz", - "util-deprecate": "1.0.2" - } - }, - "string_decoder": { - "version": "https://registry.npmjs.org/string_decoder/-/string_decoder-1.0.3.tgz", - "integrity": "sha1-D8Z9fBQYJd6UKC3VNr7GubzoYKs=", - "dev": true, - "requires": { - "safe-buffer": "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.1.1.tgz" - } - } - } - }, - "through2-filter": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/through2-filter/-/through2-filter-2.0.0.tgz", - "integrity": "sha1-YLxVoNrLdghdsfna6Zq0P4PWIuw=", - "dev": true, - "requires": { - "through2": "2.0.3", - "xtend": "4.0.1" - } - }, - "tildify": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/tildify/-/tildify-1.2.0.tgz", - "integrity": "sha1-3OwD9V3Km3qj5bBPIYF+tW5jWIo=", - "dev": true, - "requires": { - "os-homedir": "1.0.2" - } - }, - "time-stamp": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/time-stamp/-/time-stamp-1.1.0.tgz", - "integrity": "sha1-dkpaEa9QVhkhsTPztE5hhofg9cM=", - "dev": true - }, - "timers-ext": { - "version": "0.1.2", - "resolved": "https://registry.npmjs.org/timers-ext/-/timers-ext-0.1.2.tgz", - "integrity": "sha1-YcxHp2wavTGV8UUn+XjViulMUgQ=", - "dev": true, - "requires": { - "es5-ext": "0.10.37", - "next-tick": "1.0.0" - } - }, - "tmp": { - "version": "0.0.29", - "resolved": "https://registry.npmjs.org/tmp/-/tmp-0.0.29.tgz", - "integrity": "sha1-8lEl/w3Z2jzLDC3Tce4SiLuRKMA=", - "dev": true, - "requires": { - "os-tmpdir": "1.0.2" - } - }, - "to-absolute-glob": { - "version": "0.1.1", - "resolved": "https://registry.npmjs.org/to-absolute-glob/-/to-absolute-glob-0.1.1.tgz", - "integrity": "sha1-HN+kcqnvUMI57maZm2YsoOs5k38=", - "dev": true, - "requires": { - "extend-shallow": "2.0.1" - } - }, - "tough-cookie": { - "version": "2.3.3", - "resolved": "https://registry.npmjs.org/tough-cookie/-/tough-cookie-2.3.3.tgz", - "integrity": "sha1-C2GKVWW23qkL80JdBNVe3EdadWE=", - "dev": true, - "requires": { - "punycode": "1.4.1" - } - }, - "tslib": { - "version": "https://registry.npmjs.org/tslib/-/tslib-1.8.0.tgz", - "integrity": "sha1-3GBOutZLy/aW1hPabJVKoOfqHrY=", - "dev": true - }, - "tslint": { - "version": "5.8.0", - "resolved": "https://registry.npmjs.org/tslint/-/tslint-5.8.0.tgz", - "integrity": "sha1-H0mtWy53x2w69N3K5VKuTjYS6xM=", - "dev": true, - "requires": { - "babel-code-frame": "6.26.0", - "builtin-modules": "1.1.1", - "chalk": "2.3.0", - "commander": "2.9.0", - "diff": "3.2.0", - "glob": "https://registry.npmjs.org/glob/-/glob-7.1.2.tgz", - "minimatch": "https://registry.npmjs.org/minimatch/-/minimatch-3.0.4.tgz", - "resolve": "https://registry.npmjs.org/resolve/-/resolve-1.5.0.tgz", - "semver": "https://registry.npmjs.org/semver/-/semver-5.4.1.tgz", - "tslib": "https://registry.npmjs.org/tslib/-/tslib-1.8.0.tgz", - "tsutils": "2.12.2" - }, - "dependencies": { - "ansi-styles": { - "version": "3.2.0", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-3.2.0.tgz", - "integrity": "sha512-NnSOmMEYtVR2JVMIGTzynRkkaxtiq1xnFBcdQD/DnNCYPoEPsVJhM98BDyaoNOQIi7p4okdi3E27eN7GQbsUug==", - "dev": true, - "requires": { - "color-convert": "1.9.1" - } - }, - "chalk": { - "version": "2.3.0", - "resolved": "https://registry.npmjs.org/chalk/-/chalk-2.3.0.tgz", - "integrity": "sha512-Az5zJR2CBujap2rqXGaJKaPHyJ0IrUimvYNX+ncCy8PJP4ltOGTrHUIo097ZaL2zMeKYpiCdqDvS6zdrTFok3Q==", - "dev": true, - "requires": { - "ansi-styles": "3.2.0", - "escape-string-regexp": "1.0.5", - "supports-color": "4.5.0" - } - }, - "has-flag": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-2.0.0.tgz", - "integrity": "sha1-6CB68cx7MNRGzHC3NLXovhj4jVE=", - "dev": true - }, - "semver": { - "version": "https://registry.npmjs.org/semver/-/semver-5.4.1.tgz", - "integrity": "sha1-4FnAnYVx8FQII3M0M1BdOi8AsY4=", - "dev": true - }, - "supports-color": { - "version": "4.5.0", - "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-4.5.0.tgz", - "integrity": "sha1-vnoN5ITexcXN34s9WRJQRJEvY1s=", - "dev": true, - "requires": { - "has-flag": "2.0.0" - } - } - } - }, - "tsutils": { - "version": "2.12.2", - "resolved": "https://registry.npmjs.org/tsutils/-/tsutils-2.12.2.tgz", - "integrity": "sha1-rVikhl0X7D3bZjG2ylO+FKVlb/M=", - "dev": true, - "requires": { - "tslib": "https://registry.npmjs.org/tslib/-/tslib-1.8.0.tgz" - } - }, - "tunnel": { - "version": "0.0.4", - "resolved": "https://registry.npmjs.org/tunnel/-/tunnel-0.0.4.tgz", - "integrity": "sha1-LTeFoVjBdMmhbcLARuxfxfF0IhM=", - "dev": true - }, - "tunnel-agent": { - "version": "0.4.3", - "resolved": "https://registry.npmjs.org/tunnel-agent/-/tunnel-agent-0.4.3.tgz", - "integrity": "sha1-Y3PbdpCf5XDgjXNYM2Xtgop07us=", - "dev": true - }, - "tweetnacl": { - "version": "0.14.5", - "resolved": "https://registry.npmjs.org/tweetnacl/-/tweetnacl-0.14.5.tgz", - "integrity": "sha1-WuaBd/GS1EViadEIr6k/+HQ/T2Q=", - "dev": true, - "optional": true - }, - "typed-rest-client": { - "version": "0.9.0", - "resolved": "https://registry.npmjs.org/typed-rest-client/-/typed-rest-client-0.9.0.tgz", - "integrity": "sha1-92jMDcP06VDwbgSCXDaz54NKofI=", - "dev": true, - "requires": { - "tunnel": "0.0.4", - "underscore": "1.8.3" - } - }, - "typescript": { - "version": "2.6.1", - "resolved": "https://registry.npmjs.org/typescript/-/typescript-2.6.1.tgz", - "integrity": "sha1-7znN6ierrAtQAkLWcmq5DgyEZjE=", - "dev": true - }, - "uc.micro": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/uc.micro/-/uc.micro-1.0.3.tgz", - "integrity": "sha1-ftUNXg+an7ClczeSWfKndFjVAZI=", - "dev": true - }, - "ultron": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/ultron/-/ultron-1.0.2.tgz", - "integrity": "sha1-rOEWq1V80Zc4ak6I9GhTeMiy5Po=" - }, - "unc-path-regex": { - "version": "0.1.2", - "resolved": "https://registry.npmjs.org/unc-path-regex/-/unc-path-regex-0.1.2.tgz", - "integrity": "sha1-5z3T17DXxe2G+6xrCufYxqadUPo=", - "dev": true - }, - "underscore": { - "version": "1.8.3", - "resolved": "https://registry.npmjs.org/underscore/-/underscore-1.8.3.tgz", - "integrity": "sha1-Tz+1OxBuYJf8+ctBCfKl6b36UCI=", - "dev": true - }, - "unique-stream": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/unique-stream/-/unique-stream-1.0.0.tgz", - "integrity": "sha1-1ZpKdUJ0R9mqbJHnAmP40mpLEEs=", - "dev": true - }, - "urix": { - "version": "0.1.0", - "resolved": "https://registry.npmjs.org/urix/-/urix-0.1.0.tgz", - "integrity": "sha1-2pN/emLiH+wf0Y1Js1wpNQZ6bHI=", - "dev": true - }, - "url-join": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/url-join/-/url-join-1.1.0.tgz", - "integrity": "sha1-dBxsL0WWxIMNZxhGCSDQySIC3Hg=", - "dev": true - }, - "url-parse": { - "version": "https://registry.npmjs.org/url-parse/-/url-parse-1.2.0.tgz", - "integrity": "sha1-OhnoqqbQI93SfcxEy0/I9/7COYY=", - "dev": true, - "requires": { - "querystringify": "1.0.0", - "requires-port": "1.0.0" - } - }, - "user-home": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/user-home/-/user-home-1.1.1.tgz", - "integrity": "sha1-K1viOjK2Onyd640PKNSFcko98ZA=", - "dev": true - }, - "util-deprecate": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/util-deprecate/-/util-deprecate-1.0.2.tgz", - "integrity": "sha1-RQ1Nyfpw3nMnYvvS1KKJgUGaDM8=", - "dev": true - }, - "uuid": { - "version": "https://registry.npmjs.org/uuid/-/uuid-3.1.0.tgz", - "integrity": "sha1-PdPT55Crwk17DToDT/q6vijrvAQ=", - "dev": true - }, - "v8flags": { - "version": "2.1.1", - "resolved": "https://registry.npmjs.org/v8flags/-/v8flags-2.1.1.tgz", - "integrity": "sha1-qrGh+jDUX4jdMhFIh1rALAtV5bQ=", - "dev": true, - "requires": { - "user-home": "1.1.1" - } - }, - "vali-date": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/vali-date/-/vali-date-1.0.0.tgz", - "integrity": "sha1-G5BKWWCfsyjvB4E4Qgk09rhnCaY=", - "dev": true - }, - "verror": { - "version": "1.10.0", - "resolved": "https://registry.npmjs.org/verror/-/verror-1.10.0.tgz", - "integrity": "sha1-OhBcoXBTr1XW4nDB+CiGguGNpAA=", - "dev": true, - "requires": { - "assert-plus": "1.0.0", - "core-util-is": "1.0.2", - "extsprintf": "1.3.0" - }, - "dependencies": { - "assert-plus": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/assert-plus/-/assert-plus-1.0.0.tgz", - "integrity": "sha1-8S4PPF13sLHN2RRpQuTpbB5N1SU=", - "dev": true - } - } - }, - "vinyl": { - "version": "0.5.3", - "resolved": "https://registry.npmjs.org/vinyl/-/vinyl-0.5.3.tgz", - "integrity": "sha1-sEVbOPxeDPMNQyUTLkYZcMIJHN4=", - "dev": true, - "requires": { - "clone": "1.0.3", - "clone-stats": "0.0.1", - "replace-ext": "0.0.1" - } - }, - "vinyl-fs": { - "version": "0.3.14", - "resolved": "https://registry.npmjs.org/vinyl-fs/-/vinyl-fs-0.3.14.tgz", - "integrity": "sha1-mmhRzhysHBzqX+hsCTHWIMLPqeY=", - "dev": true, - "requires": { - "defaults": "1.0.3", - "glob-stream": "3.1.18", - "glob-watcher": "0.0.6", - "graceful-fs": "3.0.11", - "mkdirp": "0.5.1", - "strip-bom": "1.0.0", - "through2": "0.6.5", - "vinyl": "0.4.6" - }, - "dependencies": { - "clone": { - "version": "0.2.0", - "resolved": "https://registry.npmjs.org/clone/-/clone-0.2.0.tgz", - "integrity": "sha1-xhJqkK1Pctv1rNskPMN3JP6T/B8=", - "dev": true - }, - "readable-stream": { - "version": "1.0.34", - "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-1.0.34.tgz", - "integrity": "sha1-Elgg40vIQtLyqq+v5MKRbuMsFXw=", - "dev": true, - "requires": { - "core-util-is": "1.0.2", - "inherits": "https://registry.npmjs.org/inherits/-/inherits-2.0.3.tgz", - "isarray": "0.0.1", - "string_decoder": "0.10.31" - } - }, - "through2": { - "version": "0.6.5", - "resolved": "https://registry.npmjs.org/through2/-/through2-0.6.5.tgz", - "integrity": "sha1-QaucZ7KdVyCQcUEOHXp6lozTrUg=", - "dev": true, - "requires": { - "readable-stream": "1.0.34", - "xtend": "4.0.1" - } - }, - "vinyl": { - "version": "0.4.6", - "resolved": "https://registry.npmjs.org/vinyl/-/vinyl-0.4.6.tgz", - "integrity": "sha1-LzVsh6VQolVGHza76ypbqL94SEc=", - "dev": true, - "requires": { - "clone": "0.2.0", - "clone-stats": "0.0.1" - } - } - } - }, - "vinyl-source-stream": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/vinyl-source-stream/-/vinyl-source-stream-1.1.0.tgz", - "integrity": "sha1-RMvlEIIFJ53rDFZTwJSiiHk4sas=", - "dev": true, - "requires": { - "through2": "0.6.5", - "vinyl": "0.4.6" - }, - "dependencies": { - "clone": { - "version": "0.2.0", - "resolved": "https://registry.npmjs.org/clone/-/clone-0.2.0.tgz", - "integrity": "sha1-xhJqkK1Pctv1rNskPMN3JP6T/B8=", - "dev": true - }, - "readable-stream": { - "version": "1.0.34", - "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-1.0.34.tgz", - "integrity": "sha1-Elgg40vIQtLyqq+v5MKRbuMsFXw=", - "dev": true, - "requires": { - "core-util-is": "1.0.2", - "inherits": "https://registry.npmjs.org/inherits/-/inherits-2.0.3.tgz", - "isarray": "0.0.1", - "string_decoder": "0.10.31" - } - }, - "through2": { - "version": "0.6.5", - "resolved": "https://registry.npmjs.org/through2/-/through2-0.6.5.tgz", - "integrity": "sha1-QaucZ7KdVyCQcUEOHXp6lozTrUg=", - "dev": true, - "requires": { - "readable-stream": "1.0.34", - "xtend": "4.0.1" - } - }, - "vinyl": { - "version": "0.4.6", - "resolved": "https://registry.npmjs.org/vinyl/-/vinyl-0.4.6.tgz", - "integrity": "sha1-LzVsh6VQolVGHza76ypbqL94SEc=", - "dev": true, - "requires": { - "clone": "0.2.0", - "clone-stats": "0.0.1" - } - } - } - }, - "vsce": { - "version": "1.33.2", - "resolved": "https://registry.npmjs.org/vsce/-/vsce-1.33.2.tgz", - "integrity": "sha1-NkX2mq+YTiL3TqSdNfON0Y1m/18=", - "dev": true, - "requires": { - "cheerio": "1.0.0-rc.2", - "commander": "2.9.0", - "denodeify": "1.2.1", - "glob": "https://registry.npmjs.org/glob/-/glob-7.1.2.tgz", - "lodash": "4.17.4", - "markdown-it": "https://registry.npmjs.org/markdown-it/-/markdown-it-8.4.0.tgz", - "mime": "1.6.0", - "minimatch": "https://registry.npmjs.org/minimatch/-/minimatch-3.0.4.tgz", - "osenv": "0.1.4", - "parse-semver": "1.1.1", - "read": "1.0.7", - "semver": "https://registry.npmjs.org/semver/-/semver-5.4.1.tgz", - "tmp": "0.0.29", - "url-join": "1.1.0", - "vso-node-api": "6.1.2-preview", - "yauzl": "2.9.1", - "yazl": "2.4.3" - }, - "dependencies": { - "lodash": { - "version": "4.17.4", - "resolved": "https://registry.npmjs.org/lodash/-/lodash-4.17.4.tgz", - "integrity": "sha1-eCA6TRwyiuHYbcpkYONptX9AVa4=", - "dev": true - }, - "semver": { - "version": "https://registry.npmjs.org/semver/-/semver-5.4.1.tgz", - "integrity": "sha1-4FnAnYVx8FQII3M0M1BdOi8AsY4=", - "dev": true - } - } - }, - "vscode": { - "version": "1.1.8", - "resolved": "https://registry.npmjs.org/vscode/-/vscode-1.1.8.tgz", - "integrity": "sha512-kT6sIA1AEKR5M+us2fXk5dxwV9SR/IEdLHNmVW4/dl1wNBHoEvgIo1qMQwHNxPVTQmw70KTGZ9UVeVb8FbpNFA==", - "dev": true, - "requires": { - "glob": "https://registry.npmjs.org/glob/-/glob-7.1.2.tgz", - "gulp-chmod": "2.0.0", - "gulp-filter": "https://registry.npmjs.org/gulp-filter/-/gulp-filter-5.0.1.tgz", - "gulp-gunzip": "1.0.0", - "gulp-remote-src": "0.4.3", - "gulp-symdest": "1.1.0", - "gulp-untar": "0.0.6", - "gulp-vinyl-zip": "2.1.0", - "mocha": "4.0.1", - "request": "https://registry.npmjs.org/request/-/request-2.83.0.tgz", - "semver": "https://registry.npmjs.org/semver/-/semver-5.4.1.tgz", - "source-map-support": "0.5.0", - "url-parse": "https://registry.npmjs.org/url-parse/-/url-parse-1.2.0.tgz", - "vinyl-source-stream": "1.1.0" - }, - "dependencies": { - "commander": { - "version": "2.11.0", - "resolved": "https://registry.npmjs.org/commander/-/commander-2.11.0.tgz", - "integrity": "sha512-b0553uYA5YAEGgyYIGYROzKQ7X5RAqedkfjiZxwi0kL1g3bOaBNNZfYkzt/CL0umgD5wc9Jec2FbB98CjkMRvQ==", - "dev": true - }, - "debug": { - "version": "3.1.0", - "resolved": "https://registry.npmjs.org/debug/-/debug-3.1.0.tgz", - "integrity": "sha512-OX8XqP7/1a9cqkxYw2yXss15f26NKWBpDXQd0/uK/KPqdQhxbPa994hnzjcE2VqQpDslf55723cKPUOGSmMY3g==", - "dev": true, - "requires": { - "ms": "https://registry.npmjs.org/ms/-/ms-2.0.0.tgz" - } - }, - "diff": { - "version": "3.3.1", - "resolved": "https://registry.npmjs.org/diff/-/diff-3.3.1.tgz", - "integrity": "sha512-MKPHZDMB0o6yHyDryUOScqZibp914ksXwAMYMTHj6KO8UeKsRYNJD3oNCKjTqZon+V488P7N/HzXF8t7ZR95ww==", - "dev": true - }, - "growl": { - "version": "1.10.3", - "resolved": "https://registry.npmjs.org/growl/-/growl-1.10.3.tgz", - "integrity": "sha512-hKlsbA5Vu3xsh1Cg3J7jSmX/WaW6A5oBeqzM88oNbCRQFz+zUaXm6yxS4RVytp1scBoJzSYl4YAEOQIt6O8V1Q==", - "dev": true - }, - "has-flag": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-2.0.0.tgz", - "integrity": "sha1-6CB68cx7MNRGzHC3NLXovhj4jVE=", - "dev": true - }, - "mocha": { - "version": "4.0.1", - "resolved": "https://registry.npmjs.org/mocha/-/mocha-4.0.1.tgz", - "integrity": "sha512-evDmhkoA+cBNiQQQdSKZa2b9+W2mpLoj50367lhy+Klnx9OV8XlCIhigUnn1gaTFLQCa0kdNhEGDr0hCXOQFDw==", - "dev": true, - "requires": { - "browser-stdout": "1.3.0", - "commander": "2.11.0", - "debug": "3.1.0", - "diff": "3.3.1", - "escape-string-regexp": "1.0.5", - "glob": "https://registry.npmjs.org/glob/-/glob-7.1.2.tgz", - "growl": "1.10.3", - "he": "1.1.1", - "mkdirp": "0.5.1", - "supports-color": "4.4.0" - } - }, - "semver": { - "version": "https://registry.npmjs.org/semver/-/semver-5.4.1.tgz", - "integrity": "sha1-4FnAnYVx8FQII3M0M1BdOi8AsY4=", - "dev": true - }, - "supports-color": { - "version": "4.4.0", - "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-4.4.0.tgz", - "integrity": "sha512-rKC3+DyXWgK0ZLKwmRsrkyHVZAjNkfzeehuFWdGGcqGDTZFH73+RH6S/RDAAxl9GusSjZSUWYLmT9N5pzXFOXQ==", - "dev": true, - "requires": { - "has-flag": "2.0.0" - } - } - } - }, - "vscode-chrome-debug-core": { - "version": "3.19.0", - "resolved": "https://registry.npmjs.org/vscode-chrome-debug-core/-/vscode-chrome-debug-core-3.19.0.tgz", - "integrity": "sha1-70aLFweJqQhC+2wsQVS7OsZXvvc=", - "requires": { - "@types/source-map": "https://registry.npmjs.org/@types/source-map/-/source-map-0.1.29.tgz", - "glob": "https://registry.npmjs.org/glob/-/glob-7.1.2.tgz", - "noice-json-rpc": "1.0.1", - "request-light": "0.1.0", - "source-map": "https://registry.npmjs.org/source-map/-/source-map-0.5.6.tgz", - "vscode-debugadapter": "https://registry.npmjs.org/vscode-debugadapter/-/vscode-debugadapter-1.24.0.tgz", - "vscode-debugprotocol": "https://registry.npmjs.org/vscode-debugprotocol/-/vscode-debugprotocol-1.24.0.tgz", - "vscode-nls": "https://registry.npmjs.org/vscode-nls/-/vscode-nls-2.0.2.tgz", - "ws": "1.1.5" - } - }, - "vscode-chrome-debug-core-testsupport": { - "version": "3.17.1", - "resolved": "https://registry.npmjs.org/vscode-chrome-debug-core-testsupport/-/vscode-chrome-debug-core-testsupport-3.17.1.tgz", - "integrity": "sha1-DUazMXWZooWLSkz+QgzDUuQZiBw=", - "dev": true, - "requires": { - "vscode-debugadapter-testsupport": "1.24.0" - }, - "dependencies": { - "vscode-debugadapter-testsupport": { - "version": "1.24.0", - "resolved": "https://registry.npmjs.org/vscode-debugadapter-testsupport/-/vscode-debugadapter-testsupport-1.24.0.tgz", - "integrity": "sha1-rDZ1scU/wW+1JMvSt+znEhtiXng=", - "dev": true, - "requires": { - "vscode-debugprotocol": "https://registry.npmjs.org/vscode-debugprotocol/-/vscode-debugprotocol-1.24.0.tgz" - } - } - } - }, - "vscode-debugadapter": { - "version": "https://registry.npmjs.org/vscode-debugadapter/-/vscode-debugadapter-1.24.0.tgz", - "integrity": "sha1-KAY7AcyorB5fehPRGOMgem6If/0=", - "requires": { - "vscode-debugprotocol": "https://registry.npmjs.org/vscode-debugprotocol/-/vscode-debugprotocol-1.24.0.tgz" - } - }, - "vscode-debugadapter-testsupport": { - "version": "1.23.0", - "resolved": "https://registry.npmjs.org/vscode-debugadapter-testsupport/-/vscode-debugadapter-testsupport-1.23.0.tgz", - "integrity": "sha1-pItd5CrYChckDZxRHDeGA41pbRs=", - "dev": true, - "requires": { - "vscode-debugprotocol": "https://registry.npmjs.org/vscode-debugprotocol/-/vscode-debugprotocol-1.24.0.tgz" - } - }, - "vscode-debugprotocol": { - "version": "https://registry.npmjs.org/vscode-debugprotocol/-/vscode-debugprotocol-1.24.0.tgz", - "integrity": "sha1-28EOjX2VsQJyehmvPw/O9+JSsI4=" - }, - "vscode-nls": { - "version": "https://registry.npmjs.org/vscode-nls/-/vscode-nls-2.0.2.tgz", - "integrity": "sha1-gIUiOAhEuK0VNJmvXDsDkhrqAto=" - }, - "vscode-nls-dev": { - "version": "2.1.6", - "resolved": "https://registry.npmjs.org/vscode-nls-dev/-/vscode-nls-dev-2.1.6.tgz", - "integrity": "sha512-1IylC/ekENYqz1vEItfrzrMXS8LW9aZQnNTU6BfdwT0Jddzed+l+nvU8amgVKFFmC1/GoiMFk5wtC20zWBbEbw==", - "dev": true, - "requires": { - "clone": "1.0.3", - "event-stream": "3.3.4", - "glob": "6.0.4", - "gulp-util": "3.0.8", - "iconv-lite": "https://registry.npmjs.org/iconv-lite/-/iconv-lite-0.4.19.tgz", - "is": "3.2.1", - "source-map": "https://registry.npmjs.org/source-map/-/source-map-0.5.6.tgz", - "typescript": "2.6.1", - "vinyl": "1.2.0", - "xml2js": "https://registry.npmjs.org/xml2js/-/xml2js-0.4.19.tgz", - "yargs": "3.32.0" - }, - "dependencies": { - "glob": { - "version": "6.0.4", - "resolved": "https://registry.npmjs.org/glob/-/glob-6.0.4.tgz", - "integrity": "sha1-DwiGD2oVUSey+t1PnOJLGqtuTSI=", - "dev": true, - "requires": { - "inflight": "https://registry.npmjs.org/inflight/-/inflight-1.0.6.tgz", - "inherits": "https://registry.npmjs.org/inherits/-/inherits-2.0.3.tgz", - "minimatch": "https://registry.npmjs.org/minimatch/-/minimatch-3.0.4.tgz", - "once": "https://registry.npmjs.org/once/-/once-1.4.0.tgz", - "path-is-absolute": "https://registry.npmjs.org/path-is-absolute/-/path-is-absolute-1.0.1.tgz" - } - }, - "vinyl": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/vinyl/-/vinyl-1.2.0.tgz", - "integrity": "sha1-XIgDbPVl5d8FVYv8kR+GVt8hiIQ=", - "dev": true, - "requires": { - "clone": "1.0.3", - "clone-stats": "0.0.1", - "replace-ext": "0.0.1" - } - } - } - }, - "vso-node-api": { - "version": "6.1.2-preview", - "resolved": "https://registry.npmjs.org/vso-node-api/-/vso-node-api-6.1.2-preview.tgz", - "integrity": "sha1-qrNUbfJFHs2JTgcbuZtd8Zxfp48=", - "dev": true, - "requires": { - "q": "1.5.1", - "tunnel": "0.0.4", - "typed-rest-client": "0.9.0", - "underscore": "1.8.3" - } - }, - "which": { - "version": "https://registry.npmjs.org/which/-/which-1.3.0.tgz", - "integrity": "sha1-/wS9/AEO5UfXgL7DjhrBwnd9JTo=", - "dev": true, - "requires": { - "isexe": "2.0.0" - } - }, - "window-size": { - "version": "0.1.4", - "resolved": "https://registry.npmjs.org/window-size/-/window-size-0.1.4.tgz", - "integrity": "sha1-+OGqHuWlPsW/FR/6CXQqatdpeHY=", - "dev": true - }, - "wrap-ansi": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/wrap-ansi/-/wrap-ansi-2.1.0.tgz", - "integrity": "sha1-2Pw9KE3QV5T+hJc8rs3Rz4JP3YU=", - "dev": true, - "requires": { - "string-width": "1.0.2", - "strip-ansi": "3.0.1" - } - }, - "wrappy": { - "version": "https://registry.npmjs.org/wrappy/-/wrappy-1.0.2.tgz", - "integrity": "sha1-tSQ9jz7BqjXxNkYFvA0QNuMKtp8=" - }, - "ws": { - "version": "1.1.5", - "resolved": "https://registry.npmjs.org/ws/-/ws-1.1.5.tgz", - "integrity": "sha512-o3KqipXNUdS7wpQzBHSe180lBGO60SoK0yVo3CYJgb2MkobuWuBX6dhkYP5ORCLd55y+SaflMOV5fqAB53ux4w==", - "requires": { - "options": "0.0.6", - "ultron": "1.0.2" - } - }, - "xml2js": { - "version": "https://registry.npmjs.org/xml2js/-/xml2js-0.4.19.tgz", - "integrity": "sha1-aGwg8hMgnpSr8NG88e+qKRx4J6c=", - "dev": true, - "requires": { - "sax": "https://registry.npmjs.org/sax/-/sax-1.2.4.tgz", - "xmlbuilder": "9.0.4" - } - }, - "xmlbuilder": { - "version": "9.0.4", - "resolved": "https://registry.npmjs.org/xmlbuilder/-/xmlbuilder-9.0.4.tgz", - "integrity": "sha1-UZy0ymhtAFqEINNJbz8MruzKWA8=", - "dev": true - }, - "xtend": { - "version": "4.0.1", - "resolved": "https://registry.npmjs.org/xtend/-/xtend-4.0.1.tgz", - "integrity": "sha1-pcbVMr5lbiPbgg77lDofBJmNY68=", - "dev": true - }, - "y18n": { - "version": "3.2.1", - "resolved": "https://registry.npmjs.org/y18n/-/y18n-3.2.1.tgz", - "integrity": "sha1-bRX7qITAhnnA136I53WegR4H+kE=", - "dev": true - }, - "yargs": { - "version": "3.32.0", - "resolved": "https://registry.npmjs.org/yargs/-/yargs-3.32.0.tgz", - "integrity": "sha1-AwiOnr+edWtpdRYR0qXvWRSCyZU=", - "dev": true, - "requires": { - "camelcase": "2.1.1", - "cliui": "3.2.0", - "decamelize": "1.2.0", - "os-locale": "1.4.0", - "string-width": "1.0.2", - "window-size": "0.1.4", - "y18n": "3.2.1" - } - }, - "yauzl": { - "version": "2.9.1", - "resolved": "https://registry.npmjs.org/yauzl/-/yauzl-2.9.1.tgz", - "integrity": "sha1-qBmB6nCleUYTOIPwKcWCGok1mn8=", - "dev": true, - "requires": { - "buffer-crc32": "0.2.13", - "fd-slicer": "1.0.1" - } - }, - "yazl": { - "version": "2.4.3", - "resolved": "https://registry.npmjs.org/yazl/-/yazl-2.4.3.tgz", - "integrity": "sha1-7CblzIfVYBud+EMtvdPNLlFzoHE=", - "dev": true, - "requires": { - "buffer-crc32": "0.2.13" - } - } - } -} \ No newline at end of file diff --git a/extensions/ms-vscode.node-debug2/package.json b/extensions/ms-vscode.node-debug2/package.json deleted file mode 100644 index 96c454263b3..00000000000 --- a/extensions/ms-vscode.node-debug2/package.json +++ /dev/null @@ -1,8 +0,0 @@ -{ - "name": "node-debug2", - "version": "0.0.3", - "publisher": "ms-vscode", - "engines": { - "vscode": "1.6.x" - } -} \ No newline at end of file From 6fe6061960dee368c052c388842666c5b53090ca Mon Sep 17 00:00:00 2001 From: Sandeep Somavarapu Date: Tue, 23 Jan 2018 17:59:09 +0100 Subject: [PATCH 17/63] #39574 Revert extension changs --- src/vs/workbench/api/electron-browser/mainThreadLogService.ts | 4 ++-- src/vs/workbench/api/node/extHost.protocol.ts | 2 +- 2 files changed, 3 insertions(+), 3 deletions(-) diff --git a/src/vs/workbench/api/electron-browser/mainThreadLogService.ts b/src/vs/workbench/api/electron-browser/mainThreadLogService.ts index c24b24c619a..17bd91b65f9 100644 --- a/src/vs/workbench/api/electron-browser/mainThreadLogService.ts +++ b/src/vs/workbench/api/electron-browser/mainThreadLogService.ts @@ -5,7 +5,7 @@ 'use strict'; -import { ExtHostContext, IExtHostContext } from '../node/extHost.protocol'; +import { IExtHostContext } from '../node/extHost.protocol'; import { extHostCustomer } from 'vs/workbench/api/electron-browser/extHostCustomers'; import { ILogService } from 'vs/platform/log/common/log'; import { Disposable } from 'vs/base/common/lifecycle'; @@ -18,7 +18,7 @@ export class MainThreadLogLevelManagementChannel extends Disposable { @ILogService logService: ILogService, ) { super(); - this._register(logService.onDidChangeLogLevel(level => extHostContext.getProxy(ExtHostContext.ExtHostLogService).$setLogLevel(level))); + // this._register(logService.onDidChangeLogLevel(level => extHostContext.getProxy(ExtHostContext.ExtHostLogService).$setLogLevel(level))); } } \ No newline at end of file diff --git a/src/vs/workbench/api/node/extHost.protocol.ts b/src/vs/workbench/api/node/extHost.protocol.ts index 955e29ee3fc..a72f7b6d570 100644 --- a/src/vs/workbench/api/node/extHost.protocol.ts +++ b/src/vs/workbench/api/node/extHost.protocol.ts @@ -799,7 +799,7 @@ export const ExtHostContext = { ExtHostLanguageFeatures: createExtId('ExtHostLanguageFeatures'), ExtHostQuickOpen: createExtId('ExtHostQuickOpen'), ExtHostExtensionService: createExtId('ExtHostExtensionService'), - ExtHostLogService: createExtId('ExtHostLogService'), + // ExtHostLogService: createExtId('ExtHostLogService'), ExtHostTerminalService: createExtId('ExtHostTerminalService'), ExtHostSCM: createExtId('ExtHostSCM'), ExtHostTask: createExtId('ExtHostTask', ProxyType.CustomMarshaller), From 2fe2829517f3d877514a0ec63708e25908c0dcd6 Mon Sep 17 00:00:00 2001 From: Daniel Imms Date: Tue, 23 Jan 2018 08:46:57 -0800 Subject: [PATCH 18/63] vscode-xterm@3.1.0-beta8 --- package.json | 4 ++-- yarn.lock | 6 +++--- 2 files changed, 5 insertions(+), 5 deletions(-) diff --git a/package.json b/package.json index 744c612172f..1d8d44d2a1b 100644 --- a/package.json +++ b/package.json @@ -45,7 +45,7 @@ "vscode-debugprotocol": "1.25.0", "vscode-ripgrep": "^0.7.1-patch.0", "vscode-textmate": "^3.2.0", - "vscode-xterm": "3.1.0-beta7", + "vscode-xterm": "3.1.0-beta8", "yauzl": "2.8.0" }, "devDependencies": { @@ -129,4 +129,4 @@ "windows-mutex": "^0.2.0", "windows-process-tree": "0.1.6" } -} \ No newline at end of file +} diff --git a/yarn.lock b/yarn.lock index 91fc8617773..bcc807feb45 100644 --- a/yarn.lock +++ b/yarn.lock @@ -5808,9 +5808,9 @@ vscode-textmate@^3.2.0: fast-plist "^0.1.2" oniguruma "^6.0.1" -vscode-xterm@3.1.0-beta7: - version "3.1.0-beta7" - resolved "https://registry.yarnpkg.com/vscode-xterm/-/vscode-xterm-3.1.0-beta7.tgz#10b0162baf8ddbf8454ba3ccb723c8808f8803af" +vscode-xterm@3.1.0-beta8: + version "3.1.0-beta8" + resolved "https://registry.yarnpkg.com/vscode-xterm/-/vscode-xterm-3.1.0-beta8.tgz#cc0d7016dfe486566fd835bcf3e8503884dde09b" vso-node-api@^6.1.2-preview: version "6.1.2-preview" From 8b3b72d1d9dee042f7aff06aefddd7a8e5796d02 Mon Sep 17 00:00:00 2001 From: Daniel Imms Date: Tue, 23 Jan 2018 09:01:07 -0800 Subject: [PATCH 19/63] Add fontWeight/fontWeightBold terminal settings, remove enableBold Fixes #29887 --- src/typings/vscode-xterm.d.ts | 15 +++++++++++++++ .../workbench/parts/terminal/common/terminal.ts | 5 ++++- .../electron-browser/terminal.contribution.ts | 15 +++++++++++---- .../terminal/electron-browser/terminalInstance.ts | 10 +++++++--- 4 files changed, 37 insertions(+), 8 deletions(-) diff --git a/src/typings/vscode-xterm.d.ts b/src/typings/vscode-xterm.d.ts index 5e76f2033ee..df8bf449cea 100644 --- a/src/typings/vscode-xterm.d.ts +++ b/src/typings/vscode-xterm.d.ts @@ -8,6 +8,11 @@ */ declare module 'vscode-xterm' { + /** + * A string representing text font weight. + */ + export type FontWeight = 'normal' | 'bold' | '100' | '200' | '300' | '400' | '500' | '600' | '700' | '800' | '900'; + /** * An object containing start up options for the terminal. */ @@ -57,6 +62,16 @@ declare module 'vscode-xterm' { */ fontFamily?: string; + /** + * The font weight used to render non-bold text. + */ + fontWeight?: FontWeight; + + /** + * The font weight used to render bold text. + */ + fontWeightBold?: FontWeight; + /** * The spacing in whole pixels between characters.. */ diff --git a/src/vs/workbench/parts/terminal/common/terminal.ts b/src/vs/workbench/parts/terminal/common/terminal.ts index 59e4747ed75..3ad222245eb 100644 --- a/src/vs/workbench/parts/terminal/common/terminal.ts +++ b/src/vs/workbench/parts/terminal/common/terminal.ts @@ -49,6 +49,8 @@ export const TerminalCursorStyle = { export const TERMINAL_CONFIG_SECTION = 'terminal.integrated'; +export type FontWeight = 'normal' | 'bold' | '100' | '200' | '300' | '400' | '500' | '600' | '700' | '800' | '900'; + export interface ITerminalConfiguration { shell: { linux: string; @@ -60,12 +62,13 @@ export interface ITerminalConfiguration { osx: string[]; windows: string[]; }; - enableBold: boolean; macOptionIsMeta: boolean; rightClickCopyPaste: boolean; cursorBlinking: boolean; cursorStyle: string; fontFamily: string; + fontWeight: FontWeight; + fontWeightBold: FontWeight; // fontLigatures: boolean; fontSize: number; lineHeight: number; diff --git a/src/vs/workbench/parts/terminal/electron-browser/terminal.contribution.ts b/src/vs/workbench/parts/terminal/electron-browser/terminal.contribution.ts index 98e2a2357b8..99e9d1d4b49 100644 --- a/src/vs/workbench/parts/terminal/electron-browser/terminal.contribution.ts +++ b/src/vs/workbench/parts/terminal/electron-browser/terminal.contribution.ts @@ -150,10 +150,17 @@ configurationRegistry.registerConfiguration({ 'type': 'number', 'default': 1 }, - 'terminal.integrated.enableBold': { - 'type': 'boolean', - 'description': nls.localize('terminal.integrated.enableBold', "Whether to enable bold text within the terminal, note that this requires support from the terminal shell."), - 'default': true + 'terminal.integrated.fontWeight': { + 'type': 'string', + 'enum': ['normal', 'bold', '100', '200', '300', '400', '500', '600', '700', '800', '900'], + 'description': nls.localize('terminal.integrated.fontWeight', "The font weight to use within the termianl for non-bold text."), + 'default': 'normal' + }, + 'terminal.integrated.fontWeightBold': { + 'type': 'string', + 'enum': ['normal', 'bold', '100', '200', '300', '400', '500', '600', '700', '800', '900'], + 'description': nls.localize('terminal.integrated.fontWeightBold', "The font weight to use within the termianl for bold text."), + 'default': 'bold' }, 'terminal.integrated.cursorBlinking': { 'description': nls.localize('terminal.integrated.cursorBlinking', "Controls whether the terminal cursor blinks."), diff --git a/src/vs/workbench/parts/terminal/electron-browser/terminalInstance.ts b/src/vs/workbench/parts/terminal/electron-browser/terminalInstance.ts index 46bdcaefbca..035f619324c 100644 --- a/src/vs/workbench/parts/terminal/electron-browser/terminalInstance.ts +++ b/src/vs/workbench/parts/terminal/electron-browser/terminalInstance.ts @@ -278,9 +278,10 @@ export class TerminalInstance implements ITerminalInstance { scrollback: this._configHelper.config.scrollback, theme: this._getXtermTheme(), fontFamily: font.fontFamily, + fontWeight: this._configHelper.config.fontWeight, + fontWeightBold: this._configHelper.config.fontWeightBold, fontSize: font.fontSize, lineHeight: font.lineHeight, - enableBold: this._configHelper.config.enableBold, bellStyle: this._configHelper.config.enableBell ? 'sound' : 'none', screenReaderMode: accessibilitySupport === 'on', macOptionIsMeta: this._configHelper.config.macOptionIsMeta @@ -1056,8 +1057,11 @@ export class TerminalInstance implements ITerminalInstance { if (this._xterm.getOption('fontFamily') !== font.fontFamily) { this._xterm.setOption('fontFamily', font.fontFamily); } - if (this._xterm.getOption('enableBold') !== this._configHelper.config.enableBold) { - this._xterm.setOption('enableBold', this._configHelper.config.enableBold); + if (this._xterm.getOption('fontWeight') !== this._configHelper.config.fontWeight) { + this._xterm.setOption('fontWeight', this._configHelper.config.fontWeight); + } + if (this._xterm.getOption('fontWeightBold') !== this._configHelper.config.fontWeightBold) { + this._xterm.setOption('fontWeightBold', this._configHelper.config.fontWeightBold); } } From dd56a283a8a9137f96f6c0feed4c3568a771d4e4 Mon Sep 17 00:00:00 2001 From: isidor Date: Tue, 23 Jan 2018 18:14:09 +0100 Subject: [PATCH 20/63] debug: schema for compound configurations names --- src/vs/workbench/parts/debug/common/debug.ts | 2 +- .../debugConfigurationManager.ts | 21 ++++++++++++++++--- .../debug/electron-browser/debugService.ts | 9 +++----- 3 files changed, 22 insertions(+), 10 deletions(-) diff --git a/src/vs/workbench/parts/debug/common/debug.ts b/src/vs/workbench/parts/debug/common/debug.ts index 8356f23b448..598c69684af 100644 --- a/src/vs/workbench/parts/debug/common/debug.ts +++ b/src/vs/workbench/parts/debug/common/debug.ts @@ -460,7 +460,7 @@ export interface ILaunch { * Returns the names of all configurations and compounds. * Ignores configurations which are invalid. */ - getConfigurationNames(): string[]; + getConfigurationNames(includeCompounds?: boolean): string[]; /** * Returns the resolved configuration. diff --git a/src/vs/workbench/parts/debug/electron-browser/debugConfigurationManager.ts b/src/vs/workbench/parts/debug/electron-browser/debugConfigurationManager.ts index c7351052731..a9a6226e949 100644 --- a/src/vs/workbench/parts/debug/electron-browser/debugConfigurationManager.ts +++ b/src/vs/workbench/parts/debug/electron-browser/debugConfigurationManager.ts @@ -187,7 +187,12 @@ const schema: IJSONSchema = { type: 'array', default: [], items: { - type: 'string' + oneOf: [{ + enum: [], + description: nls.localize('useUniqueNames', "Please use unique configuration names.") + }, { + type: 'object' + }] }, description: nls.localize('app.launch.json.compounds.configurations', "Names of configurations that will be started as part of this compound.") } @@ -311,6 +316,8 @@ export class ConfigurationManager implements IConfigurationManager { items.defaultSnippets.push(...configurationSnippets); } }); + + this.setCompoundSchemaValues(); }); breakpointsExtPoint.setHandler(extensions => { @@ -328,6 +335,7 @@ export class ConfigurationManager implements IConfigurationManager { this.toDispose.push(this.configurationService.onDidChangeConfiguration(e => { if (e.affectsConfiguration('launch')) { this.selectConfiguration(); + this.setCompoundSchemaValues(); } })); @@ -345,6 +353,13 @@ export class ConfigurationManager implements IConfigurationManager { } } + private setCompoundSchemaValues(): void { + const compoundConfigurationsSchema = (schema.properties['compounds'].items).properties['configurations']; + (compoundConfigurationsSchema.items).oneOf[0].enum = this.launches.map(l => + l.getConfigurationNames(false)).reduce((first, second) => first.concat(second), []); + jsonRegistry.registerSchema(launchSchemaId, schema); + } + public getLaunches(): ILaunch[] { return this.launches; } @@ -495,13 +510,13 @@ class Launch implements ILaunch { return config.compounds.filter(compound => compound.name === name).pop(); } - public getConfigurationNames(): string[] { + public getConfigurationNames(includeCompounds = true): string[] { const config = this.getConfig(); if (!config || !config.configurations || !Array.isArray(config.configurations)) { return []; } else { const names = config.configurations.filter(cfg => cfg && typeof cfg.name === 'string').map(cfg => cfg.name); - if (names.length > 0 && config.compounds) { + if (includeCompounds && names.length > 0 && config.compounds) { if (config.compounds) { names.push(...config.compounds.filter(compound => typeof compound.name === 'string' && compound.configurations && compound.configurations.length) .map(compound => compound.name)); diff --git a/src/vs/workbench/parts/debug/electron-browser/debugService.ts b/src/vs/workbench/parts/debug/electron-browser/debugService.ts index b42ea9956db..462d8d630a2 100644 --- a/src/vs/workbench/parts/debug/electron-browser/debugService.ts +++ b/src/vs/workbench/parts/debug/electron-browser/debugService.ts @@ -699,12 +699,9 @@ export class DebugService implements debug.IDebugService { } let rootForName = root; - if (launch === this.configurationManager.getWorkspaceLaunch()) { - // For workspace launches allow comound referencing configurations across folder - const launchContainingName = this.configurationManager.getLaunches().filter(l => !!l.getConfiguration(name)).pop(); - if (launchContainingName) { - rootForName = launchContainingName.workspace; - } + const launchesContainingName = this.configurationManager.getLaunches().filter(l => !!l.getConfiguration(name)); + if (launchesContainingName && launchesContainingName.length === 1) { + rootForName = launchesContainingName[0].workspace; } return this.startDebugging(rootForName, name, noDebug, topCompoundName || compound.name); From 7155f39d031980c1f00b645a82a1ec3a4cadde93 Mon Sep 17 00:00:00 2001 From: Nicolas Ramz Date: Tue, 23 Jan 2018 18:37:15 +0100 Subject: [PATCH 21/63] FIXED: issue window opened as child, fixes #42024 --- build/gulpfile.hygiene.js | 2 +- src/vs/platform/issue/electron-main/issueService.ts | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/build/gulpfile.hygiene.js b/build/gulpfile.hygiene.js index f766cfaca0f..eecc080ad1d 100644 --- a/build/gulpfile.hygiene.js +++ b/build/gulpfile.hygiene.js @@ -198,7 +198,7 @@ const hygiene = exports.hygiene = (some, options) => { tsfmt.processString(file.path, file.contents.toString('utf8'), { verify: true, tsfmt: true, - // verbose: true + verbose: true }).then(result => { if (result.error) { console.error(result.message); diff --git a/src/vs/platform/issue/electron-main/issueService.ts b/src/vs/platform/issue/electron-main/issueService.ts index 26ba9c5f6bd..ba398e53b21 100644 --- a/src/vs/platform/issue/electron-main/issueService.ts +++ b/src/vs/platform/issue/electron-main/issueService.ts @@ -40,7 +40,7 @@ export class IssueService implements IIssueService { width: 800, height: 900, title: 'Issue Reporter', - alwaysOnTop: true + parent: BrowserWindow.getFocusedWindow() }); this._issueWindow.setMenuBarVisibility(false); // workaround for now, until a menu is implemented From f2b303f3ccbe3451d462417d660da33b430ce5fd Mon Sep 17 00:00:00 2001 From: Sandeep Somavarapu Date: Tue, 23 Jan 2018 18:50:45 +0100 Subject: [PATCH 22/63] #39574 Define interface ILogLevelSetter --- .../sharedProcess/sharedProcessMain.ts | 4 +-- src/vs/code/electron-main/app.ts | 4 +-- src/vs/platform/log/common/log.ts | 26 +++++++++++++------ src/vs/platform/log/common/logIpc.ts | 18 ++++++------- src/vs/workbench/electron-browser/main.ts | 4 +-- 5 files changed, 33 insertions(+), 23 deletions(-) diff --git a/src/vs/code/electron-browser/sharedProcess/sharedProcessMain.ts b/src/vs/code/electron-browser/sharedProcess/sharedProcessMain.ts index 17fdc47c3e7..08d4961b251 100644 --- a/src/vs/code/electron-browser/sharedProcess/sharedProcessMain.ts +++ b/src/vs/code/electron-browser/sharedProcess/sharedProcessMain.ts @@ -39,7 +39,7 @@ import { IDisposable, dispose } from 'vs/base/common/lifecycle'; import { createSharedProcessContributions } from 'vs/code/electron-browser/sharedProcess/contrib/contributions'; import { createSpdLogService } from 'vs/platform/log/node/spdlogService'; import { ILogService, FollowerLogService } from 'vs/platform/log/common/log'; -import { LogLevelChannelClient } from 'vs/platform/log/common/logIpc'; +import { LogLevelSetterChannelClient } from 'vs/platform/log/common/logIpc'; export interface ISharedProcessConfiguration { readonly machineId: string; @@ -82,7 +82,7 @@ function main(server: Server, initData: ISharedProcessInitData, configuration: I const services = new ServiceCollection(); const environmentService = new EnvironmentService(initData.args, process.execPath); - const logLevelClient = new LogLevelChannelClient(server.getChannel('loglevel', { route: () => 'main' })); + const logLevelClient = new LogLevelSetterChannelClient(server.getChannel('loglevel', { route: () => 'main' })); const logService = new FollowerLogService(logLevelClient, createSpdLogService('sharedprocess', environmentService)); process.once('exit', () => logService.dispose()); diff --git a/src/vs/code/electron-main/app.ts b/src/vs/code/electron-main/app.ts index eec6c2bae9b..c23a0587ca0 100644 --- a/src/vs/code/electron-main/app.ts +++ b/src/vs/code/electron-main/app.ts @@ -57,7 +57,7 @@ import { DarwinUpdateService } from 'vs/platform/update/electron-main/updateServ import { IIssueService } from 'vs/platform/issue/common/issue'; import { IssueChannel } from 'vs/platform/issue/common/issueIpc'; import { IssueService } from 'vs/platform/issue/electron-main/issueService'; -import { LogLevelChannel } from 'vs/platform/log/common/logIpc'; +import { LogLevelSetterChannel } from 'vs/platform/log/common/logIpc'; export class CodeApplication { @@ -380,7 +380,7 @@ export class CodeApplication { this.sharedProcessClient.done(client => client.registerChannel('windows', windowsChannel)); // Log level management - const logLevelChannel = new LogLevelChannel(accessor.get(ILogService)); + const logLevelChannel = new LogLevelSetterChannel(accessor.get(ILogService)); this.electronIpcServer.registerChannel('loglevel', logLevelChannel); this.sharedProcessClient.done(client => client.registerChannel('loglevel', logLevelChannel)); diff --git a/src/vs/platform/log/common/log.ts b/src/vs/platform/log/common/log.ts index f7019d95418..615070982ec 100644 --- a/src/vs/platform/log/common/log.ts +++ b/src/vs/platform/log/common/log.ts @@ -10,7 +10,6 @@ import { createDecorator as createServiceDecorator } from 'vs/platform/instantia import { IDisposable, Disposable } from 'vs/base/common/lifecycle'; import { isWindows } from 'vs/base/common/platform'; import Event, { Emitter } from 'vs/base/common/event'; -import { LogLevelChannelClient } from 'vs/platform/log/common/logIpc'; export const ILogService = createServiceDecorator('logService'); @@ -24,11 +23,14 @@ export enum LogLevel { Off } -export interface ILogService extends IDisposable { - _serviceBrand: any; - +export interface ILogLevelSetter { onDidChangeLogLevel: Event; setLevel(level: LogLevel): void; +} + +export interface ILogService extends ILogLevelSetter, IDisposable { + _serviceBrand: any; + getLevel(): LogLevel; trace(message: string, ...args: any[]): void; debug(message: string, ...args: any[]): void; @@ -237,16 +239,24 @@ export class MultiplexLogService extends AbstractLogService implements ILogServi } } -export class FollowerLogService extends AbstractLogService implements ILogService { +export class FollowerLogService extends Disposable implements ILogService { _serviceBrand: any; - constructor(private client: LogLevelChannelClient, private logService: ILogService) { + constructor(private master: ILogLevelSetter, private logService: ILogService) { super(); - this._register(client.onDidChangeLogLevel(level => logService.setLevel(level))); + this._register(master.onDidChangeLogLevel(level => logService.setLevel(level))); + } + + get onDidChangeLogLevel(): Event { + return this.logService.onDidChangeLogLevel; } setLevel(level: LogLevel): void { - this.client.setLogLevel(level); + this.master.setLevel(level); + } + + getLevel(): LogLevel { + return this.logService.getLevel(); } trace(message: string, ...args: any[]): void { diff --git a/src/vs/platform/log/common/logIpc.ts b/src/vs/platform/log/common/logIpc.ts index 9eb0764c54e..e8c10a8416d 100644 --- a/src/vs/platform/log/common/logIpc.ts +++ b/src/vs/platform/log/common/logIpc.ts @@ -5,15 +5,15 @@ import { IChannel, eventToCall, eventFromCall } from 'vs/base/parts/ipc/common/ipc'; import { TPromise } from 'vs/base/common/winjs.base'; -import { LogLevel, ILogService } from 'vs/platform/log/common/log'; +import { LogLevel, ILogService, ILogLevelSetter } from 'vs/platform/log/common/log'; import Event, { buffer } from 'vs/base/common/event'; -export interface ILogLevelManagementChannel extends IChannel { +export interface ILogLevelSetterChannel extends IChannel { call(command: 'event:onDidChangeLogLevel'): TPromise; - call(command: 'setLogLevel', logLevel: LogLevel): TPromise; + call(command: 'setLevel', logLevel: LogLevel): TPromise; } -export class LogLevelChannel implements ILogLevelManagementChannel { +export class LogLevelSetterChannel implements ILogLevelSetterChannel { onDidChangeLogLevel: Event; @@ -24,20 +24,20 @@ export class LogLevelChannel implements ILogLevelManagementChannel { call(command: string, arg?: any): TPromise { switch (command) { case 'event:onDidChangeLogLevel': return eventToCall(this.onDidChangeLogLevel); - case 'setLogLevel': this.service.setLevel(arg); return TPromise.as(null); + case 'setLevel': this.service.setLevel(arg); return TPromise.as(null); } return undefined; } } -export class LogLevelChannelClient { +export class LogLevelSetterChannelClient implements ILogLevelSetter { - constructor(private channel: ILogLevelManagementChannel) { } + constructor(private channel: ILogLevelSetterChannel) { } private _onDidChangeLogLevel = eventFromCall(this.channel, 'event:onDidChangeLogLevel'); get onDidChangeLogLevel(): Event { return this._onDidChangeLogLevel; } - setLogLevel(level: LogLevel): TPromise { - return this.channel.call('setLogLevel', level); + setLevel(level: LogLevel): TPromise { + return this.channel.call('setLevel', level); } } \ No newline at end of file diff --git a/src/vs/workbench/electron-browser/main.ts b/src/vs/workbench/electron-browser/main.ts index f40edbae3fc..315865aef12 100644 --- a/src/vs/workbench/electron-browser/main.ts +++ b/src/vs/workbench/electron-browser/main.ts @@ -46,7 +46,7 @@ import fs = require('fs'); import { ConsoleLogService, MultiplexLogService, ILogService, FollowerLogService } from 'vs/platform/log/common/log'; import { IssueChannelClient } from 'vs/platform/issue/common/issueIpc'; import { IIssueService } from 'vs/platform/issue/common/issue'; -import { LogLevelChannelClient } from 'vs/platform/log/common/logIpc'; +import { LogLevelSetterChannelClient } from 'vs/platform/log/common/logIpc'; gracefulFs.gracefulify(fs); // enable gracefulFs export function startup(configuration: IWindowConfiguration): TPromise { @@ -202,7 +202,7 @@ function createLogService(mainProcessClient: ElectronIPCClient, configuration: I const spdlogService = createSpdLogService(`renderer${configuration.windowId}`, environmentService); const consoleLogService = new ConsoleLogService(environmentService); const logService = new MultiplexLogService([consoleLogService, spdlogService]); - const logLevelClient = new LogLevelChannelClient(mainProcessClient.getChannel('loglevel')); + const logLevelClient = new LogLevelSetterChannelClient(mainProcessClient.getChannel('loglevel')); return new FollowerLogService(logLevelClient, logService); } From c9b291978cae610aebfc4d434802b34d1901bff0 Mon Sep 17 00:00:00 2001 From: Sandeep Somavarapu Date: Tue, 23 Jan 2018 19:30:44 +0100 Subject: [PATCH 23/63] #39574 Implement log level transmission to extension host --- src/vs/platform/log/common/log.ts | 20 +++++++++++++++---- .../extensionHost.contribution.ts | 1 + .../electron-browser/mainThreadLogService.ts | 6 +++--- src/vs/workbench/api/node/extHost.api.impl.ts | 11 +++++----- src/vs/workbench/api/node/extHost.protocol.ts | 4 ++-- .../api/node/extHostExtensionService.ts | 16 +++++++-------- .../workbench/api/node/extHostLogService.ts | 19 +++++++++--------- src/vs/workbench/node/extensionHostMain.ts | 17 ++++++++-------- 8 files changed, 53 insertions(+), 41 deletions(-) diff --git a/src/vs/platform/log/common/log.ts b/src/vs/platform/log/common/log.ts index 615070982ec..176320014a7 100644 --- a/src/vs/platform/log/common/log.ts +++ b/src/vs/platform/log/common/log.ts @@ -239,12 +239,11 @@ export class MultiplexLogService extends AbstractLogService implements ILogServi } } -export class FollowerLogService extends Disposable implements ILogService { +export class DelegatedLogService extends Disposable implements ILogService { _serviceBrand: any; - constructor(private master: ILogLevelSetter, private logService: ILogService) { + constructor(private logService: ILogService) { super(); - this._register(master.onDidChangeLogLevel(level => logService.setLevel(level))); } get onDidChangeLogLevel(): Event { @@ -252,7 +251,7 @@ export class FollowerLogService extends Disposable implements ILogService { } setLevel(level: LogLevel): void { - this.master.setLevel(level); + this.logService.setLevel(level); } getLevel(): LogLevel { @@ -288,6 +287,19 @@ export class FollowerLogService extends Disposable implements ILogService { } } +export class FollowerLogService extends DelegatedLogService implements ILogService { + _serviceBrand: any; + + constructor(private master: ILogLevelSetter, logService: ILogService) { + super(logService); + this._register(master.onDidChangeLogLevel(level => logService.setLevel(level))); + } + + setLevel(level: LogLevel): void { + this.master.setLevel(level); + } +} + export class NullLogService implements ILogService { _serviceBrand: any; readonly onDidChangeLogLevel: Event = new Emitter().event; diff --git a/src/vs/workbench/api/electron-browser/extensionHost.contribution.ts b/src/vs/workbench/api/electron-browser/extensionHost.contribution.ts index 6217b1dadcd..d610ada2b88 100644 --- a/src/vs/workbench/api/electron-browser/extensionHost.contribution.ts +++ b/src/vs/workbench/api/electron-browser/extensionHost.contribution.ts @@ -46,6 +46,7 @@ import './mainThreadTask'; import './mainThreadTelemetry'; import './mainThreadTerminalService'; import './mainThreadTreeViews'; +import './mainThreadLogService'; import './mainThreadWindow'; import './mainThreadWorkspace'; diff --git a/src/vs/workbench/api/electron-browser/mainThreadLogService.ts b/src/vs/workbench/api/electron-browser/mainThreadLogService.ts index 17bd91b65f9..213ad68da8b 100644 --- a/src/vs/workbench/api/electron-browser/mainThreadLogService.ts +++ b/src/vs/workbench/api/electron-browser/mainThreadLogService.ts @@ -5,20 +5,20 @@ 'use strict'; -import { IExtHostContext } from '../node/extHost.protocol'; import { extHostCustomer } from 'vs/workbench/api/electron-browser/extHostCustomers'; import { ILogService } from 'vs/platform/log/common/log'; import { Disposable } from 'vs/base/common/lifecycle'; +import { IExtHostContext, ExtHostContext } from 'vs/workbench/api/node/extHost.protocol'; @extHostCustomer -export class MainThreadLogLevelManagementChannel extends Disposable { +export class MainThreadLogService extends Disposable { constructor( extHostContext: IExtHostContext, @ILogService logService: ILogService, ) { super(); - // this._register(logService.onDidChangeLogLevel(level => extHostContext.getProxy(ExtHostContext.ExtHostLogService).$setLogLevel(level))); + this._register(logService.onDidChangeLogLevel(level => extHostContext.getProxy(ExtHostContext.ExtHostLogService).$setLevel(level))); } } \ No newline at end of file diff --git a/src/vs/workbench/api/node/extHost.api.impl.ts b/src/vs/workbench/api/node/extHost.api.impl.ts index cc7aafe634b..39b0905b90e 100644 --- a/src/vs/workbench/api/node/extHost.api.impl.ts +++ b/src/vs/workbench/api/node/extHost.api.impl.ts @@ -55,8 +55,8 @@ import { ExtHostDecorations } from 'vs/workbench/api/node/extHostDecorations'; import { toGlobPattern, toLanguageSelector } from 'vs/workbench/api/node/extHostTypeConverters'; import { ExtensionActivatedByAPI } from 'vs/workbench/api/node/extHostExtensionActivator'; import { isFalsyOrEmpty } from 'vs/base/common/arrays'; -import { ILogService } from 'vs/platform/log/common/log'; import { OverviewRulerLane } from 'vs/editor/common/model'; +import { ExtHostLogService } from 'vs/workbench/api/node/extHostLogService'; export interface IExtensionApiFactory { (extension: IExtensionDescription): typeof vscode; @@ -89,18 +89,19 @@ export function createApiFactory( extHostWorkspace: ExtHostWorkspace, extHostConfiguration: ExtHostConfiguration, extensionService: ExtHostExtensionService, - logService: ILogService + extHostLogService: ExtHostLogService ): IExtensionApiFactory { // Addressable instances + rpcProtocol.set(ExtHostContext.ExtHostLogService, extHostLogService); const extHostHeapService = rpcProtocol.set(ExtHostContext.ExtHostHeapService, new ExtHostHeapService()); const extHostDecorations = rpcProtocol.set(ExtHostContext.ExtHostDecorations, new ExtHostDecorations(rpcProtocol)); const extHostDocumentsAndEditors = rpcProtocol.set(ExtHostContext.ExtHostDocumentsAndEditors, new ExtHostDocumentsAndEditors(rpcProtocol)); const extHostDocuments = rpcProtocol.set(ExtHostContext.ExtHostDocuments, new ExtHostDocuments(rpcProtocol, extHostDocumentsAndEditors)); const extHostDocumentContentProviders = rpcProtocol.set(ExtHostContext.ExtHostDocumentContentProviders, new ExtHostDocumentContentProvider(rpcProtocol, extHostDocumentsAndEditors)); - const extHostDocumentSaveParticipant = rpcProtocol.set(ExtHostContext.ExtHostDocumentSaveParticipant, new ExtHostDocumentSaveParticipant(logService, extHostDocuments, rpcProtocol.getProxy(MainContext.MainThreadEditors))); + const extHostDocumentSaveParticipant = rpcProtocol.set(ExtHostContext.ExtHostDocumentSaveParticipant, new ExtHostDocumentSaveParticipant(extHostLogService, extHostDocuments, rpcProtocol.getProxy(MainContext.MainThreadEditors))); const extHostEditors = rpcProtocol.set(ExtHostContext.ExtHostEditors, new ExtHostEditors(rpcProtocol, extHostDocumentsAndEditors)); - const extHostCommands = rpcProtocol.set(ExtHostContext.ExtHostCommands, new ExtHostCommands(rpcProtocol, extHostHeapService, logService)); + const extHostCommands = rpcProtocol.set(ExtHostContext.ExtHostCommands, new ExtHostCommands(rpcProtocol, extHostHeapService, extHostLogService)); const extHostTreeViews = rpcProtocol.set(ExtHostContext.ExtHostTreeViews, new ExtHostTreeViews(rpcProtocol.getProxy(MainContext.MainThreadTreeViews), extHostCommands)); rpcProtocol.set(ExtHostContext.ExtHostWorkspace, extHostWorkspace); const extHostDebugService = rpcProtocol.set(ExtHostContext.ExtHostDebugService, new ExtHostDebugService(rpcProtocol, extHostWorkspace)); @@ -111,7 +112,7 @@ export function createApiFactory( const extHostFileSystemEvent = rpcProtocol.set(ExtHostContext.ExtHostFileSystemEventService, new ExtHostFileSystemEventService()); const extHostQuickOpen = rpcProtocol.set(ExtHostContext.ExtHostQuickOpen, new ExtHostQuickOpen(rpcProtocol, extHostWorkspace, extHostCommands)); const extHostTerminalService = rpcProtocol.set(ExtHostContext.ExtHostTerminalService, new ExtHostTerminalService(rpcProtocol)); - const extHostSCM = rpcProtocol.set(ExtHostContext.ExtHostSCM, new ExtHostSCM(rpcProtocol, extHostCommands, logService)); + const extHostSCM = rpcProtocol.set(ExtHostContext.ExtHostSCM, new ExtHostSCM(rpcProtocol, extHostCommands, extHostLogService)); const extHostTask = rpcProtocol.set(ExtHostContext.ExtHostTask, new ExtHostTask(rpcProtocol, extHostWorkspace)); const extHostWindow = rpcProtocol.set(ExtHostContext.ExtHostWindow, new ExtHostWindow(rpcProtocol)); rpcProtocol.set(ExtHostContext.ExtHostExtensionService, extensionService); diff --git a/src/vs/workbench/api/node/extHost.protocol.ts b/src/vs/workbench/api/node/extHost.protocol.ts index a72f7b6d570..e8d27c90b2c 100644 --- a/src/vs/workbench/api/node/extHost.protocol.ts +++ b/src/vs/workbench/api/node/extHost.protocol.ts @@ -746,7 +746,7 @@ export interface ExtHostWindowShape { } export interface ExtHostLogServiceShape { - $setLogLevel(level: LogLevel); + $setLevel(level: LogLevel); } // --- proxy identifiers @@ -799,7 +799,7 @@ export const ExtHostContext = { ExtHostLanguageFeatures: createExtId('ExtHostLanguageFeatures'), ExtHostQuickOpen: createExtId('ExtHostQuickOpen'), ExtHostExtensionService: createExtId('ExtHostExtensionService'), - // ExtHostLogService: createExtId('ExtHostLogService'), + ExtHostLogService: createExtId('ExtHostLogService'), ExtHostTerminalService: createExtId('ExtHostTerminalService'), ExtHostSCM: createExtId('ExtHostSCM'), ExtHostTask: createExtId('ExtHostTask', ProxyType.CustomMarshaller), diff --git a/src/vs/workbench/api/node/extHostExtensionService.ts b/src/vs/workbench/api/node/extHostExtensionService.ts index fb50ec716d8..2ea4f37ba86 100644 --- a/src/vs/workbench/api/node/extHostExtensionService.ts +++ b/src/vs/workbench/api/node/extHostExtensionService.ts @@ -128,7 +128,6 @@ export class ExtHostExtensionService implements ExtHostExtensionServiceShape { private readonly _storage: ExtHostStorage; private readonly _storagePath: ExtensionStoragePath; private readonly _proxy: MainThreadExtensionServiceShape; - private readonly _logService: ILogService; private readonly _extHostLogService: ExtHostLogService; private _activator: ExtensionsActivator; private _extensionPathIndex: TPromise>; @@ -139,21 +138,20 @@ export class ExtHostExtensionService implements ExtHostExtensionServiceShape { extHostContext: IExtHostContext, extHostWorkspace: ExtHostWorkspace, extHostConfiguration: ExtHostConfiguration, - logService: ILogService, + extHostLogService: ExtHostLogService, environmentService: IEnvironmentService ) { this._barrier = new Barrier(); this._registry = new ExtensionDescriptionRegistry(initData.extensions); - this._logService = logService; + this._extHostLogService = extHostLogService; this._mainThreadTelemetry = extHostContext.getProxy(MainContext.MainThreadTelemetry); this._storage = new ExtHostStorage(extHostContext); this._storagePath = new ExtensionStoragePath(initData.workspace, initData.environment); this._proxy = extHostContext.getProxy(MainContext.MainThreadExtensionService); this._activator = null; - this._extHostLogService = new ExtHostLogService(environmentService, this._logService); // initialize API first (i.e. do not release barrier until the API is initialized) - const apiFactory = createApiFactory(initData, extHostContext, extHostWorkspace, extHostConfiguration, this, logService); + const apiFactory = createApiFactory(initData, extHostContext, extHostWorkspace, extHostConfiguration, this, this._extHostLogService); initializeExtensionApi(this, apiFactory).then(() => { @@ -314,14 +312,14 @@ export class ExtHostExtensionService implements ExtHostExtensionServiceShape { return TPromise.as(new EmptyExtension(ExtensionActivationTimes.NONE)); } - this._logService.info(`ExtensionService#_doActivateExtension ${extensionDescription.id} ${JSON.stringify(reason)}`); + this._extHostLogService.info(`ExtensionService#_doActivateExtension ${extensionDescription.id} ${JSON.stringify(reason)}`); const activationTimesBuilder = new ExtensionActivationTimesBuilder(reason.startup); return TPromise.join([ - loadCommonJSModule(this._logService, extensionDescription.main, activationTimesBuilder), + loadCommonJSModule(this._extHostLogService, extensionDescription.main, activationTimesBuilder), this._loadExtensionContext(extensionDescription) ]).then(values => { - return ExtHostExtensionService._callActivate(this._logService, extensionDescription.id, values[0], values[1], activationTimesBuilder); + return ExtHostExtensionService._callActivate(this._extHostLogService, extensionDescription.id, values[0], values[1], activationTimesBuilder); }, (errors: any[]) => { // Avoid failing with an array of errors, fail with a single error if (errors[0]) { @@ -339,7 +337,7 @@ export class ExtHostExtensionService implements ExtHostExtensionServiceShape { let globalState = new ExtensionMemento(extensionDescription.id, true, this._storage); let workspaceState = new ExtensionMemento(extensionDescription.id, false, this._storage); - this._logService.trace(`ExtensionService#loadExtensionContext ${extensionDescription.id}`); + this._extHostLogService.trace(`ExtensionService#loadExtensionContext ${extensionDescription.id}`); return TPromise.join([ globalState.whenReady, workspaceState.whenReady, diff --git a/src/vs/workbench/api/node/extHostLogService.ts b/src/vs/workbench/api/node/extHostLogService.ts index 4689e038ae8..60b000101e1 100644 --- a/src/vs/workbench/api/node/extHostLogService.ts +++ b/src/vs/workbench/api/node/extHostLogService.ts @@ -10,25 +10,26 @@ import { TPromise } from 'vs/base/common/winjs.base'; import { mkdirp, dirExists } from 'vs/base/node/pfs'; import Event from 'vs/base/common/event'; import { LogLevel } from 'vs/workbench/api/node/extHostTypes'; -import { ILogService } from 'vs/platform/log/common/log'; +import { ILogService, DelegatedLogService } from 'vs/platform/log/common/log'; import { createSpdLogService } from 'vs/platform/log/node/spdlogService'; import { IEnvironmentService } from 'vs/platform/environment/common/environment'; import { memoize } from 'vs/base/common/decorators'; import { ExtHostLogServiceShape } from 'vs/workbench/api/node/extHost.protocol'; -import { Disposable } from 'vs/base/common/lifecycle'; -export class ExtHostLogService extends Disposable implements ExtHostLogServiceShape { + +export class ExtHostLogService extends DelegatedLogService implements ILogService, ExtHostLogServiceShape { + private _loggers: Map = new Map(); constructor( - private _environmentService: IEnvironmentService, - private _logService: ILogService + windowId: number, + private _environmentService: IEnvironmentService ) { - super(); + super(createSpdLogService(`exthost${windowId}`, _environmentService)); } - $setLogLevel(level: LogLevel) { - this._logService.setLevel(level); + $setLevel(level: LogLevel): void { + this.setLevel(level); } getExtLogger(extensionID: string): ExtHostLogger { @@ -43,7 +44,7 @@ export class ExtHostLogService extends Disposable implements ExtHostLogServiceSh private createLogger(extensionID: string): ExtHostLogger { const logService = createSpdLogService(extensionID, this._environmentService, extensionID); const logsDirPath = path.join(this._environmentService.logsPath, extensionID); - this._register(this._logService.onDidChangeLogLevel(level => logService.setLevel(level))); + this._register(this.onDidChangeLogLevel(level => logService.setLevel(level))); return new ExtHostLogger(logService, logsDirPath); } } diff --git a/src/vs/workbench/node/extensionHostMain.ts b/src/vs/workbench/node/extensionHostMain.ts index 7af498132c5..60314f50234 100644 --- a/src/vs/workbench/node/extensionHostMain.ts +++ b/src/vs/workbench/node/extensionHostMain.ts @@ -21,12 +21,11 @@ import * as watchdog from 'native-watchdog'; import * as glob from 'vs/base/common/glob'; import { ExtensionActivatedByEvent } from 'vs/workbench/api/node/extHostExtensionActivator'; import { EnvironmentService } from 'vs/platform/environment/node/environmentService'; -import { createSpdLogService } from 'vs/platform/log/node/spdlogService'; import { IDisposable, dispose } from 'vs/base/common/lifecycle'; -import { ILogService } from 'vs/platform/log/common/log'; import { IMessagePassingProtocol } from 'vs/base/parts/ipc/common/ipc'; import { RPCProtocol } from 'vs/workbench/services/extensions/node/rpcProtocol'; import URI from 'vs/base/common/uri'; +import { ExtHostLogService } from 'vs/workbench/api/node/extHostLogService'; // const nativeExit = process.exit.bind(process); function patchProcess(allowExit: boolean) { @@ -78,7 +77,7 @@ export class ExtensionHostMain { private _environment: IEnvironment; private _extensionService: ExtHostExtensionService; private _extHostConfiguration: ExtHostConfiguration; - private _logService: ILogService; + private _extHostLogService: ExtHostLogService; private disposables: IDisposable[] = []; constructor(protocol: IMessagePassingProtocol, initData: IInitData) { @@ -92,14 +91,14 @@ export class ExtensionHostMain { const rpcProtocol = new RPCProtocol(protocol); const extHostWorkspace = new ExtHostWorkspace(rpcProtocol, initData.workspace); const environmentService = new EnvironmentService(initData.args, initData.execPath); - this._logService = createSpdLogService(`exthost${initData.windowId}`, environmentService); - this.disposables.push(this._logService); + this._extHostLogService = new ExtHostLogService(initData.windowId, environmentService); + this.disposables.push(this._extHostLogService); - this._logService.info('extension host started'); - this._logService.trace('initData', initData); + this._extHostLogService.info('extension host started'); + this._extHostLogService.trace('initData', initData); this._extHostConfiguration = new ExtHostConfiguration(rpcProtocol.getProxy(MainContext.MainThreadConfiguration), extHostWorkspace, initData.configuration); - this._extensionService = new ExtHostExtensionService(initData, rpcProtocol, extHostWorkspace, this._extHostConfiguration, this._logService, environmentService); + this._extensionService = new ExtHostExtensionService(initData, rpcProtocol, extHostWorkspace, this._extHostConfiguration, this._extHostLogService, environmentService); // error forwarding and stack trace scanning const extensionErrors = new WeakMap(); @@ -143,7 +142,7 @@ export class ExtensionHostMain { .then(() => this.handleEagerExtensions()) .then(() => this.handleExtensionTests()) .then(() => { - this._logService.info(`eager extensions activated`); + this._extHostLogService.info(`eager extensions activated`); }); } From d260ccffecefd809ca81d856e857a0441522417e Mon Sep 17 00:00:00 2001 From: Benjamin Pasero Date: Tue, 23 Jan 2018 19:33:07 +0100 Subject: [PATCH 24/63] workaround #41987 --- .../browser/parts/quickopen/quickOpenController.ts | 13 ++++++++++++- 1 file changed, 12 insertions(+), 1 deletion(-) diff --git a/src/vs/workbench/browser/parts/quickopen/quickOpenController.ts b/src/vs/workbench/browser/parts/quickopen/quickOpenController.ts index 935b7d8bed5..1da92a9404f 100644 --- a/src/vs/workbench/browser/parts/quickopen/quickOpenController.ts +++ b/src/vs/workbench/browser/parts/quickopen/quickOpenController.ts @@ -55,6 +55,7 @@ import { FileKind, IFileService } from 'vs/platform/files/common/files'; import { scoreItem, ScorerCache, compareItemsByScore, prepareQuery } from 'vs/base/parts/quickopen/common/quickOpenScorer'; import { getBaseLabel } from 'vs/base/common/labels'; import { WorkbenchTree } from 'vs/platform/list/browser/listService'; +import { dirname } from 'vs/base/common/paths'; const HELP_PREFIX = '?'; @@ -1259,7 +1260,7 @@ export class EditorHistoryEntry extends EditorQuickOpenEntry { const resourceInput = input as IResourceInput; this.resource = resourceInput.resource; this.label = getBaseLabel(resourceInput.resource); - this.description = labels.getPathLabel(resources.dirname(this.resource), contextService, environmentService); + this.description = labels.getPathLabel(this.safeDirname(this.resource), contextService, environmentService); this.dirty = this.resource && this.textFileService.isDirty(this.resource); if (this.dirty && this.textFileService.getAutoSaveMode() === AutoSaveMode.AFTER_SHORT_DELAY) { @@ -1268,6 +1269,16 @@ export class EditorHistoryEntry extends EditorQuickOpenEntry { } } + private safeDirname(resource: URI): string | URI { + try { + return resources.dirname(resource); // workaround for https://github.com/Microsoft/vscode/issues/41987 + } catch (error) { + console.warn(`Unable to resolve to parent resource: ${resource.toString()}`, resource, error); + + return dirname(resource.fsPath); + } + } + public getIcon(): string { return this.dirty ? 'dirty' : ''; } From 013fff3f9e1702948c3d209e29f48f703a1ed524 Mon Sep 17 00:00:00 2001 From: Steven Van Impe Date: Tue, 23 Jan 2018 19:57:01 +0100 Subject: [PATCH 25/63] Update Swift snippets (#42048) --- extensions/swift/snippets/swift.json | 174 +++++++++++++++++---------- 1 file changed, 108 insertions(+), 66 deletions(-) diff --git a/extensions/swift/snippets/swift.json b/extensions/swift/snippets/swift.json index 43591d13a7b..08161d1c825 100644 --- a/extensions/swift/snippets/swift.json +++ b/extensions/swift/snippets/swift.json @@ -1,133 +1,175 @@ { - "print(\"...\")": { - "prefix": "pr", - "body": "print(\"$1\")$0" + "print": { + "prefix": "print", + "body": "print(\"$1\")\n$0", + "description": "print(\"...\")" }, - "print(\"\\(...)\")": { - "prefix": "po", - "body": "print(\"\\($1)\")$0" + "print value": { + "prefix": "printv", + "body": "print(\"\\($1)\")\n$0", + "description": "print(\"\\(...)\")" }, - "repeat...while loop": { + "while": { + "prefix": "while", + "body": [ + "while ${1:condition} {", + "\t$0", + "}" + ], + "description": "while statement" + }, + "repeat-while": { "prefix": "repeat", "body": [ "repeat {", "\t$0", - "} while ${1:true}" + "} while ${1:condition}" ], - "description": "repeat...while loop" + "description": "repeat-while statement" }, - "While loop": { - "prefix": "while", - "body": [ - "while ${1:true} {", - "\t$0", - "}" - ], - "description": "While loop" - }, - "For-In statement": { - "prefix": "forin", + "for": { + "prefix": "for", "body": [ "for ${1:item} in ${2:collection} {", "\t$0", "}" ], - "description": "For-In statement" + "description": "for-in statement" }, - "Reverse for loop": { - "prefix": "forr", - "body": [ - "for var ${1:i} = ${2:length} - 1; ${1:i} >= 0; ${1:i}-- {", - "\t$0", - "}" - ], - "description": "Reverse for loop" - }, - "for loop": { - "prefix": "for", - "body": [ - "for var ${1:i} = 0; ${1:i} < ${2:length}; ${1:i}++ {", - "\t$0", - "}" - ], - "description": "for loop" - }, - "if statement": { + "if": { "prefix": "if", "body": [ - "if ${1:true} {", + "if ${1:condition} {", "\t$0", "}" ], "description": "if statement" }, - "else-if statement": { + "else if": { "prefix": "elif", "body": [ - "else if ${1:true} {", + "else if ${1:condition} {", "\t$0", "}" ], - "description": "if statement" + "description": "else clause with a nested if statement" }, - "Else statement": { + "else": { "prefix": "else", "body": [ "else {", "\t$0", "}" ], - "description": "Else statement" + "description": "else clause" }, - "Guard statement": { + "if let": { + "prefix": "iflet", + "body": [ + "if let ${1:value} = ${2:optional} {", + "\t$0", + "}" + ], + "description": "if statement with optional binding" + }, + "guard": { "prefix": "guard", "body": [ - "guard let ${1:a} = ${2:optional} else {", + "guard ${1:condition} else {", "\t$0", "}" ], - "description": "Guard statement" + "description": "guard statement" }, - "Optional Binding statement": { - "prefix": "ifnil", + "guard let": { + "prefix": "guardlet", "body": [ - "if let ${1:a} = ${2:optional} {", + "guard let ${1:value} = ${2:optional} else {", "\t$0", "}" ], - "description": "Optional Binding statement" + "description": "guard statement with optional binding" }, - "Switch statement": { + "switch": { "prefix": "switch", "body": [ - "switch ${1:switch_on} {", - "case ${2:a}:", + "switch ${1:value} {", + "case ${2:pattern}:", "\t$0", "default:", - "\t$1", + "\t", "}" ], - "description": "Switch statement" + "description": "switch statement" }, - "Do catch": { - "prefix": "docatch", + "do": { + "prefix": "do", "body": [ "do {", - "\ttry ${1:function that throws}", - "} catch ${2:pattern} {", + "\t$0", + "} catch ${1:error} {", + "\t$2", + "}" + ], + "description": "do statement" + }, + "func": { + "prefix": "func", + "body": [ + "func ${1:name}(${2:parameters}) -> ${3:Type} {", "\t$0", "}" ], - "description": "Try catch" + "description": "function declaration" }, - "Enum": { + "struct": { + "prefix": "struct", + "body": [ + "struct ${1:Name} {", + "", + "\t$0", + "}" + ], + "description": "struct declaration" + }, + "enum": { "prefix": "enum", "body": [ "enum ${1:Name} {", + "", "\tcase $0", "}" ], - "description": "Enum" + "description": "enum declaration" + }, + "class": { + "prefix": "class", + "body": [ + "class ${1:Name} {", + "", + "\t$0", + "}" + ], + "description": "class declaration" + }, + "protocol": { + "prefix": "protocol", + "body": [ + "protocol ${1:Name} {", + "", + "\t$0", + "}" + ], + "description": "protocol declaration" + }, + "extension": { + "prefix": "extension", + "body": [ + "extension ${1:Type} {", + "", + "\t$0", + "}" + ], + "description": "extension declaration" } } - From 087899f428f50df61f4ebacdce1d433f59cfb94e Mon Sep 17 00:00:00 2001 From: Daniel Imms Date: Tue, 23 Jan 2018 10:42:49 -0800 Subject: [PATCH 26/63] Place terminal textarea below rows, fix nav mode reading wrong item --- package.json | 2 +- yarn.lock | 6 +++--- 2 files changed, 4 insertions(+), 4 deletions(-) diff --git a/package.json b/package.json index 1d8d44d2a1b..38c1c1a8342 100644 --- a/package.json +++ b/package.json @@ -45,7 +45,7 @@ "vscode-debugprotocol": "1.25.0", "vscode-ripgrep": "^0.7.1-patch.0", "vscode-textmate": "^3.2.0", - "vscode-xterm": "3.1.0-beta8", + "vscode-xterm": "3.1.0-beta10", "yauzl": "2.8.0" }, "devDependencies": { diff --git a/yarn.lock b/yarn.lock index bcc807feb45..71dafbf80d3 100644 --- a/yarn.lock +++ b/yarn.lock @@ -5808,9 +5808,9 @@ vscode-textmate@^3.2.0: fast-plist "^0.1.2" oniguruma "^6.0.1" -vscode-xterm@3.1.0-beta8: - version "3.1.0-beta8" - resolved "https://registry.yarnpkg.com/vscode-xterm/-/vscode-xterm-3.1.0-beta8.tgz#cc0d7016dfe486566fd835bcf3e8503884dde09b" +vscode-xterm@3.1.0-beta10: + version "3.1.0-beta10" + resolved "https://registry.yarnpkg.com/vscode-xterm/-/vscode-xterm-3.1.0-beta10.tgz#274ab2f41c0417f477c4fe4488788a8be740784e" vso-node-api@^6.1.2-preview: version "6.1.2-preview" From 07d50ff62e6a4a4049d4ad0fe0f8a268f8f6f817 Mon Sep 17 00:00:00 2001 From: Sandeep Somavarapu Date: Tue, 23 Jan 2018 20:30:48 +0100 Subject: [PATCH 27/63] Fix #39574 --- .../sharedProcess/sharedProcessMain.ts | 5 ++- src/vs/code/electron-main/app.ts | 2 +- src/vs/code/electron-main/main.ts | 6 +-- src/vs/code/electron-main/sharedProcess.ts | 7 +++- src/vs/code/electron-main/window.ts | 3 +- src/vs/code/node/cliProcessMain.ts | 4 +- .../electron-main/backupMainService.test.ts | 2 +- .../environment/common/environment.ts | 2 - .../environment/node/environmentService.ts | 28 ------------- src/vs/platform/log/common/log.ts | 40 ++++++++++++++++--- src/vs/platform/log/node/spdlogService.ts | 9 ++--- src/vs/platform/windows/common/windows.ts | 2 + .../workspacesMainService.test.ts | 2 +- src/vs/workbench/api/node/extHost.protocol.ts | 1 + .../workbench/api/node/extHostLogService.ts | 5 ++- src/vs/workbench/electron-browser/main.ts | 4 +- src/vs/workbench/node/extensionHostMain.ts | 2 +- .../electron-browser/extensionHost.ts | 7 +++- 18 files changed, 71 insertions(+), 60 deletions(-) diff --git a/src/vs/code/electron-browser/sharedProcess/sharedProcessMain.ts b/src/vs/code/electron-browser/sharedProcess/sharedProcessMain.ts index 08d4961b251..335f01d17fe 100644 --- a/src/vs/code/electron-browser/sharedProcess/sharedProcessMain.ts +++ b/src/vs/code/electron-browser/sharedProcess/sharedProcessMain.ts @@ -38,7 +38,7 @@ import { ipcRenderer } from 'electron'; import { IDisposable, dispose } from 'vs/base/common/lifecycle'; import { createSharedProcessContributions } from 'vs/code/electron-browser/sharedProcess/contrib/contributions'; import { createSpdLogService } from 'vs/platform/log/node/spdlogService'; -import { ILogService, FollowerLogService } from 'vs/platform/log/common/log'; +import { ILogService, FollowerLogService, LogLevel } from 'vs/platform/log/common/log'; import { LogLevelSetterChannelClient } from 'vs/platform/log/common/logIpc'; export interface ISharedProcessConfiguration { @@ -52,6 +52,7 @@ export function startup(configuration: ISharedProcessConfiguration) { interface ISharedProcessInitData { sharedIPCHandle: string; args: ParsedArgs; + logLevel: LogLevel; } class ActiveWindowManager implements IDisposable { @@ -83,7 +84,7 @@ function main(server: Server, initData: ISharedProcessInitData, configuration: I const environmentService = new EnvironmentService(initData.args, process.execPath); const logLevelClient = new LogLevelSetterChannelClient(server.getChannel('loglevel', { route: () => 'main' })); - const logService = new FollowerLogService(logLevelClient, createSpdLogService('sharedprocess', environmentService)); + const logService = new FollowerLogService(logLevelClient, createSpdLogService('sharedprocess', initData.logLevel, environmentService.logsPath)); process.once('exit', () => logService.dispose()); logService.info('main', JSON.stringify(configuration)); diff --git a/src/vs/code/electron-main/app.ts b/src/vs/code/electron-main/app.ts index c23a0587ca0..64c73d5b91c 100644 --- a/src/vs/code/electron-main/app.ts +++ b/src/vs/code/electron-main/app.ts @@ -273,7 +273,7 @@ export class CodeApplication { this.logService.trace(`Resolved machine identifier: ${machineId}`); // Spawn shared process - this.sharedProcess = new SharedProcess(this.environmentService, machineId, this.userEnv); + this.sharedProcess = new SharedProcess(this.environmentService, machineId, this.userEnv, this.logService); this.toDispose.push(this.sharedProcess); this.sharedProcessClient = this.sharedProcess.whenReady().then(() => connect(this.environmentService.sharedIPCHandle, 'main')); diff --git a/src/vs/code/electron-main/main.ts b/src/vs/code/electron-main/main.ts index 8ba25df359b..276db5a62ae 100644 --- a/src/vs/code/electron-main/main.ts +++ b/src/vs/code/electron-main/main.ts @@ -21,7 +21,7 @@ import { ServicesAccessor, IInstantiationService } from 'vs/platform/instantiati import { InstantiationService } from 'vs/platform/instantiation/common/instantiationService'; import { ServiceCollection } from 'vs/platform/instantiation/common/serviceCollection'; import { SyncDescriptor } from 'vs/platform/instantiation/common/descriptors'; -import { ILogService, ConsoleLogMainService, MultiplexLogService } from 'vs/platform/log/common/log'; +import { ILogService, ConsoleLogMainService, MultiplexLogService, getLogLevel } from 'vs/platform/log/common/log'; import { StateService } from 'vs/platform/state/node/stateService'; import { IStateService } from 'vs/platform/state/common/state'; import { IBackupMainService } from 'vs/platform/backup/common/backup'; @@ -51,7 +51,7 @@ function createServices(args: ParsedArgs, bufferLogService: BufferLogService): I const services = new ServiceCollection(); const environmentService = new EnvironmentService(args, process.execPath); - const consoleLogService = new ConsoleLogMainService(environmentService); + const consoleLogService = new ConsoleLogMainService(getLogLevel(environmentService)); const logService = new MultiplexLogService([consoleLogService, bufferLogService]); process.once('exit', () => logService.dispose()); @@ -320,7 +320,7 @@ function main() { return instantiationService.invokeFunction(a => createPaths(a.get(IEnvironmentService))) .then(() => instantiationService.invokeFunction(setupIPC)) .then(mainIpcServer => { - bufferLogService.logger = createSpdLogService('main', environmentService); + bufferLogService.logger = createSpdLogService('main', bufferLogService.getLevel(), environmentService.logsPath); return instantiationService.createInstance(CodeApplication, mainIpcServer, instanceEnv).startup(); }); }).done(null, err => instantiationService.invokeFunction(quit, err)); diff --git a/src/vs/code/electron-main/sharedProcess.ts b/src/vs/code/electron-main/sharedProcess.ts index ff9f904cb68..e402ec33a5d 100644 --- a/src/vs/code/electron-main/sharedProcess.ts +++ b/src/vs/code/electron-main/sharedProcess.ts @@ -12,6 +12,7 @@ import { IProcessEnvironment } from 'vs/base/common/platform'; import { BrowserWindow, ipcMain } from 'electron'; import { ISharedProcess } from 'vs/platform/windows/electron-main/windows'; import { Barrier } from 'vs/base/common/async'; +import { ILogService } from 'vs/platform/log/common/log'; export class SharedProcess implements ISharedProcess { @@ -23,7 +24,8 @@ export class SharedProcess implements ISharedProcess { constructor( private environmentService: IEnvironmentService, private readonly machineId: string, - private readonly userEnv: IProcessEnvironment + private readonly userEnv: IProcessEnvironment, + private readonly logService: ILogService ) { } @memoize @@ -75,7 +77,8 @@ export class SharedProcess implements ISharedProcess { ipcMain.once('handshake:hello', ({ sender }: { sender: any }) => { sender.send('handshake:hey there', { sharedIPCHandle: this.environmentService.sharedIPCHandle, - args: this.environmentService.args + args: this.environmentService.args, + logLevel: this.logService.getLevel() }); ipcMain.once('handshake:im ready', () => c(null)); diff --git a/src/vs/code/electron-main/window.ts b/src/vs/code/electron-main/window.ts index e79a7400e20..dbe69eb291e 100644 --- a/src/vs/code/electron-main/window.ts +++ b/src/vs/code/electron-main/window.ts @@ -565,6 +565,7 @@ export class CodeWindow implements ICodeWindow { // Set window ID windowConfiguration.windowId = this._win.id; + windowConfiguration.logLevel = this.logService.getLevel(); // Set zoomlevel const windowConfig = this.configurationService.getValue('window'); @@ -593,7 +594,7 @@ export class CodeWindow implements ICodeWindow { const environment = parseArgs(process.argv); const config = objects.assign(environment, windowConfiguration); for (let key in config) { - if (!config[key]) { + if (config[key] === void 0 || config[key] === null || config[key] === '') { delete config[key]; // only send over properties that have a true value } } diff --git a/src/vs/code/node/cliProcessMain.ts b/src/vs/code/node/cliProcessMain.ts index 0d99eadec4f..a01bebe6cf7 100644 --- a/src/vs/code/node/cliProcessMain.ts +++ b/src/vs/code/node/cliProcessMain.ts @@ -36,7 +36,7 @@ import { getBaseLabel } from 'vs/base/common/labels'; import { IStateService } from 'vs/platform/state/common/state'; import { StateService } from 'vs/platform/state/node/stateService'; import { createSpdLogService } from 'vs/platform/log/node/spdlogService'; -import { ILogService } from 'vs/platform/log/common/log'; +import { ILogService, getLogLevel } from 'vs/platform/log/common/log'; import { isPromiseCanceledError } from 'vs/base/common/errors'; const notFound = (id: string) => localize('notFound', "Extension '{0}' not found.", id); @@ -196,7 +196,7 @@ export function main(argv: ParsedArgs): TPromise { const services = new ServiceCollection(); const environmentService = new EnvironmentService(argv, process.execPath); - const logService = createSpdLogService('cli', environmentService); + const logService = createSpdLogService('cli', getLogLevel(environmentService), environmentService.logsPath); process.once('exit', () => logService.dispose()); logService.info('main', argv); diff --git a/src/vs/platform/backup/test/electron-main/backupMainService.test.ts b/src/vs/platform/backup/test/electron-main/backupMainService.test.ts index 0fae04bac59..60c83ef1746 100644 --- a/src/vs/platform/backup/test/electron-main/backupMainService.test.ts +++ b/src/vs/platform/backup/test/electron-main/backupMainService.test.ts @@ -34,7 +34,7 @@ suite('BackupMainService', () => { class TestBackupMainService extends BackupMainService { constructor(backupHome: string, backupWorkspacesPath: string, configService: TestConfigurationService) { - super(environmentService, configService, new ConsoleLogMainService(environmentService)); + super(environmentService, configService, new ConsoleLogMainService()); this.backupHome = backupHome; this.workspacesJsonPath = backupWorkspacesPath; diff --git a/src/vs/platform/environment/common/environment.ts b/src/vs/platform/environment/common/environment.ts index 3296b628490..7bd8700a868 100644 --- a/src/vs/platform/environment/common/environment.ts +++ b/src/vs/platform/environment/common/environment.ts @@ -4,7 +4,6 @@ *--------------------------------------------------------------------------------------------*/ import { createDecorator } from 'vs/platform/instantiation/common/instantiation'; -import { LogLevel } from 'vs/platform/log/common/log'; export interface ParsedArgs { [arg: string]: any; @@ -117,7 +116,6 @@ export interface IEnvironmentService { // logging logsPath: string; verbose: boolean; - logLevel: LogLevel; skipGettingStarted: boolean | undefined; skipReleaseNotes: boolean | undefined; diff --git a/src/vs/platform/environment/node/environmentService.ts b/src/vs/platform/environment/node/environmentService.ts index f50aa30396f..fcc62b80c75 100644 --- a/src/vs/platform/environment/node/environmentService.ts +++ b/src/vs/platform/environment/node/environmentService.ts @@ -12,7 +12,6 @@ import URI from 'vs/base/common/uri'; import { memoize } from 'vs/base/common/decorators'; import pkg from 'vs/platform/node/package'; import product from 'vs/platform/node/product'; -import { LogLevel } from 'vs/platform/log/common/log'; import { toLocalISOString } from 'vs/base/common/date'; import { isWindows, isLinux } from 'vs/base/common/platform'; @@ -152,33 +151,6 @@ export class EnvironmentService implements IEnvironmentService { get isBuilt(): boolean { return !process.env['VSCODE_DEV']; } get verbose(): boolean { return this._args.verbose; } - @memoize - get logLevel(): LogLevel { - if (this.verbose) { - return LogLevel.Trace; - } - if (typeof this._args.log === 'string') { - const logLevel = this._args.log.toLowerCase(); - switch (logLevel) { - case 'trace': - return LogLevel.Trace; - case 'debug': - return LogLevel.Debug; - case 'info': - return LogLevel.Info; - case 'warn': - return LogLevel.Warning; - case 'error': - return LogLevel.Error; - case 'critical': - return LogLevel.Critical; - case 'off': - return LogLevel.Off; - } - } - return LogLevel.Info; - } - get wait(): boolean { return this._args.wait; } get logExtensionHostCommunication(): boolean { return this._args.logExtensionHostCommunication; } diff --git a/src/vs/platform/log/common/log.ts b/src/vs/platform/log/common/log.ts index 176320014a7..5617bff5eb3 100644 --- a/src/vs/platform/log/common/log.ts +++ b/src/vs/platform/log/common/log.ts @@ -5,11 +5,11 @@ 'use strict'; -import { IEnvironmentService } from 'vs/platform/environment/common/environment'; import { createDecorator as createServiceDecorator } from 'vs/platform/instantiation/common/instantiation'; import { IDisposable, Disposable } from 'vs/base/common/lifecycle'; import { isWindows } from 'vs/base/common/platform'; import Event, { Emitter } from 'vs/base/common/event'; +import { IEnvironmentService } from 'vs/platform/environment/common/environment'; export const ILogService = createServiceDecorator('logService'); @@ -63,9 +63,9 @@ export class ConsoleLogMainService extends AbstractLogService implements ILogSer _serviceBrand: any; private useColors: boolean; - constructor( @IEnvironmentService environmentService: IEnvironmentService) { + constructor(logLevel: LogLevel = LogLevel.Error) { super(); - this.setLevel(environmentService.logLevel); + this.setLevel(logLevel); this.useColors = !isWindows; } @@ -138,9 +138,9 @@ export class ConsoleLogService extends AbstractLogService implements ILogService _serviceBrand: any; - constructor( @IEnvironmentService environmentService: IEnvironmentService) { + constructor(logLevel: LogLevel = LogLevel.Error) { super(); - this.setLevel(environmentService.logLevel); + this.setLevel(logLevel); } trace(message: string, ...args: any[]): void { @@ -187,6 +187,9 @@ export class MultiplexLogService extends AbstractLogService implements ILogServi constructor(private logServices: ILogService[]) { super(); + if (logServices.length) { + this.setLevel(logServices[0].getLevel()); + } } setLevel(level: LogLevel): void { @@ -313,3 +316,30 @@ export class NullLogService implements ILogService { critical(message: string | Error, ...args: any[]): void { } dispose(): void { } } + + +export function getLogLevel(environmentService: IEnvironmentService): LogLevel { + if (environmentService.verbose) { + return LogLevel.Trace; + } + if (typeof environmentService.args.log === 'string') { + const logLevel = environmentService.args.log.toLowerCase(); + switch (logLevel) { + case 'trace': + return LogLevel.Trace; + case 'debug': + return LogLevel.Debug; + case 'info': + return LogLevel.Info; + case 'warn': + return LogLevel.Warning; + case 'error': + return LogLevel.Error; + case 'critical': + return LogLevel.Critical; + case 'off': + return LogLevel.Off; + } + } + return LogLevel.Info; +} \ No newline at end of file diff --git a/src/vs/platform/log/node/spdlogService.ts b/src/vs/platform/log/node/spdlogService.ts index 9df00ce99f6..8627fc959ee 100644 --- a/src/vs/platform/log/node/spdlogService.ts +++ b/src/vs/platform/log/node/spdlogService.ts @@ -7,18 +7,17 @@ import * as path from 'path'; import { ILogService, LogLevel, NullLogService, AbstractLogService } from 'vs/platform/log/common/log'; -import { IEnvironmentService } from 'vs/platform/environment/common/environment'; import { RotatingLogger, setAsyncMode } from 'spdlog'; -export function createSpdLogService(processName: string, environmentService: IEnvironmentService, logsSubfolder?: string): ILogService { +export function createSpdLogService(processName: string, logLevel: LogLevel, logsFolder: string, logsSubfolder?: string): ILogService { try { setAsyncMode(8192, 2000); - const logsDirPath = logsSubfolder ? path.join(environmentService.logsPath, logsSubfolder) : environmentService.logsPath; + const logsDirPath = logsSubfolder ? path.join(logsFolder, logsSubfolder) : logsFolder; const logfilePath = path.join(logsDirPath, `${processName}.log`); const logger = new RotatingLogger(processName, logfilePath, 1024 * 1024 * 5, 6); logger.setLevel(0); - return new SpdLogService(logger, environmentService.logLevel); + return new SpdLogService(logger, logLevel); } catch (e) { console.error(e); } @@ -31,7 +30,7 @@ class SpdLogService extends AbstractLogService implements ILogService { constructor( private readonly logger: RotatingLogger, - level: LogLevel + level: LogLevel = LogLevel.Error ) { super(); this.setLevel(level); diff --git a/src/vs/platform/windows/common/windows.ts b/src/vs/platform/windows/common/windows.ts index c20b1900988..3a2cabf156a 100644 --- a/src/vs/platform/windows/common/windows.ts +++ b/src/vs/platform/windows/common/windows.ts @@ -15,6 +15,7 @@ import { IWorkspaceIdentifier, IWorkspaceFolderCreationData } from 'vs/platform/ import { IRecentlyOpened } from 'vs/platform/history/common/history'; import { ICommandAction } from 'vs/platform/actions/common/actions'; import { PerformanceEntry } from 'vs/base/common/performance'; +import { LogLevel } from 'vs/platform/log/common/log'; export const IWindowsService = createDecorator('windowsService'); @@ -297,6 +298,7 @@ export interface IAddFoldersRequest { export interface IWindowConfiguration extends ParsedArgs, IOpenFileRequest { machineId: string; windowId: number; + logLevel: LogLevel; appRoot: string; execPath: string; diff --git a/src/vs/platform/workspaces/test/electron-main/workspacesMainService.test.ts b/src/vs/platform/workspaces/test/electron-main/workspacesMainService.test.ts index 7031cb06470..ff060086c77 100644 --- a/src/vs/platform/workspaces/test/electron-main/workspacesMainService.test.ts +++ b/src/vs/platform/workspaces/test/electron-main/workspacesMainService.test.ts @@ -48,7 +48,7 @@ suite('WorkspacesMainService', () => { } const environmentService = new TestEnvironmentService(parseArgs(process.argv), process.execPath); - const logService = new ConsoleLogMainService(environmentService); + const logService = new ConsoleLogMainService(); let service: TestWorkspacesMainService; diff --git a/src/vs/workbench/api/node/extHost.protocol.ts b/src/vs/workbench/api/node/extHost.protocol.ts index e8d27c90b2c..9df097ce6ef 100644 --- a/src/vs/workbench/api/node/extHost.protocol.ts +++ b/src/vs/workbench/api/node/extHost.protocol.ts @@ -84,6 +84,7 @@ export interface IInitData { windowId: number; args: ParsedArgs; execPath: string; + logLevel: LogLevel; } export interface IConfigurationInitData extends IConfigurationData { diff --git a/src/vs/workbench/api/node/extHostLogService.ts b/src/vs/workbench/api/node/extHostLogService.ts index 60b000101e1..9e5dd3f93c0 100644 --- a/src/vs/workbench/api/node/extHostLogService.ts +++ b/src/vs/workbench/api/node/extHostLogService.ts @@ -23,9 +23,10 @@ export class ExtHostLogService extends DelegatedLogService implements ILogServic constructor( windowId: number, + logLevel: LogLevel, private _environmentService: IEnvironmentService ) { - super(createSpdLogService(`exthost${windowId}`, _environmentService)); + super(createSpdLogService(`exthost${windowId}`, logLevel, _environmentService.logsPath)); } $setLevel(level: LogLevel): void { @@ -42,7 +43,7 @@ export class ExtHostLogService extends DelegatedLogService implements ILogServic } private createLogger(extensionID: string): ExtHostLogger { - const logService = createSpdLogService(extensionID, this._environmentService, extensionID); + const logService = createSpdLogService(extensionID, this.getLevel(), this._environmentService.logsPath, extensionID); const logsDirPath = path.join(this._environmentService.logsPath, extensionID); this._register(this.onDidChangeLogLevel(level => logService.setLevel(level))); return new ExtHostLogger(logService, logsDirPath); diff --git a/src/vs/workbench/electron-browser/main.ts b/src/vs/workbench/electron-browser/main.ts index 315865aef12..50deed29769 100644 --- a/src/vs/workbench/electron-browser/main.ts +++ b/src/vs/workbench/electron-browser/main.ts @@ -199,8 +199,8 @@ function createStorageService(workspaceService: IWorkspaceContextService, enviro } function createLogService(mainProcessClient: ElectronIPCClient, configuration: IWindowConfiguration, environmentService: IEnvironmentService): ILogService { - const spdlogService = createSpdLogService(`renderer${configuration.windowId}`, environmentService); - const consoleLogService = new ConsoleLogService(environmentService); + const spdlogService = createSpdLogService(`renderer${configuration.windowId}`, configuration.logLevel, environmentService.logsPath); + const consoleLogService = new ConsoleLogService(configuration.logLevel); const logService = new MultiplexLogService([consoleLogService, spdlogService]); const logLevelClient = new LogLevelSetterChannelClient(mainProcessClient.getChannel('loglevel')); return new FollowerLogService(logLevelClient, logService); diff --git a/src/vs/workbench/node/extensionHostMain.ts b/src/vs/workbench/node/extensionHostMain.ts index 60314f50234..1a37fc04768 100644 --- a/src/vs/workbench/node/extensionHostMain.ts +++ b/src/vs/workbench/node/extensionHostMain.ts @@ -91,7 +91,7 @@ export class ExtensionHostMain { const rpcProtocol = new RPCProtocol(protocol); const extHostWorkspace = new ExtHostWorkspace(rpcProtocol, initData.workspace); const environmentService = new EnvironmentService(initData.args, initData.execPath); - this._extHostLogService = new ExtHostLogService(initData.windowId, environmentService); + this._extHostLogService = new ExtHostLogService(initData.windowId, initData.logLevel, environmentService); this.disposables.push(this._extHostLogService); this._extHostLogService.info('extension host started'); diff --git a/src/vs/workbench/services/extensions/electron-browser/extensionHost.ts b/src/vs/workbench/services/extensions/electron-browser/extensionHost.ts index 62474f4acbc..ee35a4980f5 100644 --- a/src/vs/workbench/services/extensions/electron-browser/extensionHost.ts +++ b/src/vs/workbench/services/extensions/electron-browser/extensionHost.ts @@ -35,6 +35,7 @@ import { EXTENSION_CLOSE_EXTHOST_BROADCAST_CHANNEL, EXTENSION_RELOAD_BROADCAST_C import { IDisposable, dispose } from 'vs/base/common/lifecycle'; import { IRemoteConsoleLog, log, parse } from 'vs/base/node/console'; import { getScopes } from 'vs/platform/configuration/common/configurationRegistry'; +import { ILogService } from 'vs/platform/log/common/log'; export class ExtensionHostProcessWorker { @@ -70,7 +71,8 @@ export class ExtensionHostProcessWorker { @IEnvironmentService private readonly _environmentService: IEnvironmentService, @IWorkspaceConfigurationService private readonly _configurationService: IWorkspaceConfigurationService, @ITelemetryService private readonly _telemetryService: ITelemetryService, - @ICrashReporterService private readonly _crashReporterService: ICrashReporterService + @ICrashReporterService private readonly _crashReporterService: ICrashReporterService, + @ILogService private readonly _logService: ILogService ) { // handle extension host lifecycle a bit special when we know we are developing an extension that runs inside this._isExtensionDevHost = this._environmentService.isExtensionDevelopment; @@ -377,7 +379,8 @@ export class ExtensionHostProcessWorker { telemetryInfo, args: this._environmentService.args, execPath: this._environmentService.execPath, - windowId: this._windowService.getCurrentWindowId() + windowId: this._windowService.getCurrentWindowId(), + logLevel: this._logService.getLevel() }; return r; }); From 1e9acc4bb0aacd169e97e1f2a80b15d2a4713b93 Mon Sep 17 00:00:00 2001 From: Ramya Achutha Rao Date: Tue, 23 Jan 2018 12:13:00 -0800 Subject: [PATCH 28/63] New property for OSVersion with possible PII from self compiled linux kernels stripped --- src/vs/platform/telemetry/node/commonProperties.ts | 2 ++ src/vs/platform/telemetry/node/workbenchCommonProperties.ts | 3 --- .../telemetry/test/electron-browser/commonProperties.test.ts | 1 + 3 files changed, 3 insertions(+), 3 deletions(-) diff --git a/src/vs/platform/telemetry/node/commonProperties.ts b/src/vs/platform/telemetry/node/commonProperties.ts index 0d232325091..a9e9ecf1705 100644 --- a/src/vs/platform/telemetry/node/commonProperties.ts +++ b/src/vs/platform/telemetry/node/commonProperties.ts @@ -21,6 +21,8 @@ export function resolveCommonProperties(commit: string, version: string, machine result['version'] = version; // __GDPR__COMMON__ "common.osVersion" : { "classification": "SystemMetaData", "purpose": "FeatureInsight" } result['common.osVersion'] = os.release(); + // __GDPR__COMMON__ "common.platformVersion" : { "classification": "SystemMetaData", "purpose": "FeatureInsight" } + result['common.platformVersion'] = (os.release() || '').replace(/^(\d+)(\.\d+)?(\.\d+)?(.*)/, '$1$2$3'); // __GDPR__COMMON__ "common.platform" : { "classification": "SystemMetaData", "purpose": "FeatureInsight" } result['common.platform'] = Platform.Platform[Platform.platform]; // __GDPR__COMMON__ "common.nodePlatform" : { "classification": "SystemMetaData", "purpose": "FeatureInsight" } diff --git a/src/vs/platform/telemetry/node/workbenchCommonProperties.ts b/src/vs/platform/telemetry/node/workbenchCommonProperties.ts index 41a7901dffb..a7688ef16ba 100644 --- a/src/vs/platform/telemetry/node/workbenchCommonProperties.ts +++ b/src/vs/platform/telemetry/node/workbenchCommonProperties.ts @@ -3,7 +3,6 @@ * Licensed under the MIT License. See License.txt in the project root for license information. *--------------------------------------------------------------------------------------------*/ -import * as os from 'os'; import { TPromise } from 'vs/base/common/winjs.base'; import * as uuid from 'vs/base/common/uuid'; import { IStorageService } from 'vs/platform/storage/common/storage'; @@ -15,8 +14,6 @@ export function resolveWorkbenchCommonProperties(storageService: IStorageService result['common.version.shell'] = process.versions && (process).versions['electron']; // __GDPR__COMMON__ "common.version.renderer" : { "classification": "SystemMetaData", "purpose": "FeatureInsight" } result['common.version.renderer'] = process.versions && (process).versions['chrome']; - // __GDPR__COMMON__ "common.osVersion" : { "classification": "SystemMetaData", "purpose": "FeatureInsight" } - result['common.osVersion'] = os.release(); const lastSessionDate = storageService.get('telemetry.lastSessionDate'); const firstSessionDate = storageService.get('telemetry.firstSessionDate') || new Date().toUTCString(); diff --git a/src/vs/platform/telemetry/test/electron-browser/commonProperties.test.ts b/src/vs/platform/telemetry/test/electron-browser/commonProperties.test.ts index 725718f20bc..fb89055b500 100644 --- a/src/vs/platform/telemetry/test/electron-browser/commonProperties.test.ts +++ b/src/vs/platform/telemetry/test/electron-browser/commonProperties.test.ts @@ -49,6 +49,7 @@ suite('Telemetry - common properties', function () { // assert.ok('common.version.shell' in first.data); // only when running on electron // assert.ok('common.version.renderer' in first.data); assert.ok('common.osVersion' in props, 'osVersion'); + assert.ok('common.platformVersion' in props, 'platformVersion'); assert.ok('version' in props); assert.equal(props['common.source'], 'my.install.source'); From 6957fb22dc168e3863ad384743e155e37d24a378 Mon Sep 17 00:00:00 2001 From: Ramya Achutha Rao Date: Tue, 23 Jan 2018 12:21:11 -0800 Subject: [PATCH 29/63] Sanitize OSVersion --- src/vs/platform/telemetry/node/commonProperties.ts | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/vs/platform/telemetry/node/commonProperties.ts b/src/vs/platform/telemetry/node/commonProperties.ts index a9e9ecf1705..c0e152aa53c 100644 --- a/src/vs/platform/telemetry/node/commonProperties.ts +++ b/src/vs/platform/telemetry/node/commonProperties.ts @@ -19,10 +19,10 @@ export function resolveCommonProperties(commit: string, version: string, machine result['commitHash'] = commit; // __GDPR__COMMON__ "version" : { "classification": "SystemMetaData", "purpose": "FeatureInsight" } result['version'] = version; - // __GDPR__COMMON__ "common.osVersion" : { "classification": "SystemMetaData", "purpose": "FeatureInsight" } - result['common.osVersion'] = os.release(); // __GDPR__COMMON__ "common.platformVersion" : { "classification": "SystemMetaData", "purpose": "FeatureInsight" } result['common.platformVersion'] = (os.release() || '').replace(/^(\d+)(\.\d+)?(\.\d+)?(.*)/, '$1$2$3'); + // __GDPR__COMMON__ "common.osVersion" : { "classification": "SystemMetaData", "purpose": "FeatureInsight" } + result['common.osVersion'] = result['common.platformVersion']; // TODO: Drop this after the move to Nova // __GDPR__COMMON__ "common.platform" : { "classification": "SystemMetaData", "purpose": "FeatureInsight" } result['common.platform'] = Platform.Platform[Platform.platform]; // __GDPR__COMMON__ "common.nodePlatform" : { "classification": "SystemMetaData", "purpose": "FeatureInsight" } From c398a079e7e7d7156810e86b2903ff6ce19058f3 Mon Sep 17 00:00:00 2001 From: Rachel Macfarlane Date: Tue, 23 Jan 2018 12:32:39 -0800 Subject: [PATCH 30/63] Localize issue reporter and fix flickering on load, fixes #41995 * Fix flickering on load * Localize issue reporter * Remove duplicated text --- .../electron-browser/issue/issueReporter.html | 106 ++---------------- .../electron-browser/issue/issueReporter.js | 26 ++++- .../issue/issueReporterMain.ts | 30 +++-- .../issue/issueReporterPage.ts | 98 ++++++++++++++++ .../issue/media/issueReporter.css | 1 - .../issue/electron-main/issueService.ts | 8 +- 6 files changed, 160 insertions(+), 109 deletions(-) create mode 100644 src/vs/code/electron-browser/issue/issueReporterPage.ts diff --git a/src/vs/code/electron-browser/issue/issueReporter.html b/src/vs/code/electron-browser/issue/issueReporter.html index ad3010252ec..629aab5ea44 100644 --- a/src/vs/code/electron-browser/issue/issueReporter.html +++ b/src/vs/code/electron-browser/issue/issueReporter.html @@ -1,102 +1,18 @@ - - - - - -
-
- - -
+ + + + + -
- - - - - - -
+ + Issue Reporter + -
-
- - -
-
- - -
-
+ + -
-
-
- My System Info - - - - -
- -
-
-
-
-
- Currently Running Processes - - - - -
- -
-
-
-
-
- My Workspace Stats - - - - -
-							
-								
-							
-						
-
-
-
- - - - -
- - We support GitHub-flavored Markdown. - You will still be able to edit your issue when we preview it on GitHub. - - - -
-
-
- - -
- - - - \ No newline at end of file + diff --git a/src/vs/code/electron-browser/issue/issueReporter.js b/src/vs/code/electron-browser/issue/issueReporter.js index 31dc101872f..ac9730d0d58 100644 --- a/src/vs/code/electron-browser/issue/issueReporter.js +++ b/src/vs/code/electron-browser/issue/issueReporter.js @@ -65,6 +65,25 @@ function main() { // Load the loader and start loading the workbench const rootUrl = uriFromPath(configuration.appRoot) + '/out'; + // Get the nls configuration into the process.env as early as possible. + var nlsConfig = { availableLanguages: {} }; + const config = process.env['VSCODE_NLS_CONFIG']; + if (config) { + process.env['VSCODE_NLS_CONFIG'] = config; + try { + nlsConfig = JSON.parse(config); + } catch (e) { /*noop*/ } + } + + var locale = nlsConfig.availableLanguages['*'] || 'en'; + if (locale === 'zh-tw') { + locale = 'zh-Hant'; + } else if (locale === 'zh-cn') { + locale = 'zh-Hans'; + } + + window.document.documentElement.setAttribute('lang', locale); + // In the bundled version the nls plugin is packaged with the loader so the NLS Plugins // loads as soon as the loader loads. To be able to have pseudo translation createScript(rootUrl + '/vs/loader.js', function () { @@ -72,7 +91,6 @@ function main() { window.MonacoEnvironment = {}; - var nlsConfig = { availableLanguages: {} }; require.config({ baseUrl: rootUrl, 'vs/nls': nlsConfig, @@ -80,6 +98,12 @@ function main() { nodeModules: [/*BUILD->INSERT_NODE_MODULES*/] }); + if (nlsConfig.pseudo) { + require(['vs/nls'], function (nlsPlugin) { + nlsPlugin.setPseudoTranslation(nlsConfig.pseudo); + }); + } + require(['vs/code/electron-browser/issue/issueReporterMain'], (issueReporter) => { issueReporter.startup(configuration); }); diff --git a/src/vs/code/electron-browser/issue/issueReporterMain.ts b/src/vs/code/electron-browser/issue/issueReporterMain.ts index 0b8148580cc..8ba1dd95e00 100644 --- a/src/vs/code/electron-browser/issue/issueReporterMain.ts +++ b/src/vs/code/electron-browser/issue/issueReporterMain.ts @@ -7,6 +7,7 @@ import 'vs/css!./media/issueReporter'; import { shell, ipcRenderer, webFrame, remote } from 'electron'; +import { localize } from 'vs/nls'; import { $ } from 'vs/base/browser/dom'; import * as browser from 'vs/base/browser/browser'; import product from 'vs/platform/node/product'; @@ -28,10 +29,17 @@ import { WindowsChannelClient } from 'vs/platform/windows/common/windowsIpc'; import { EnvironmentService } from 'vs/platform/environment/node/environmentService'; import { IssueReporterModel, IssueReporterData } from 'vs/code/electron-browser/issue/issueReporterModel'; import { IssueReporterStyles } from 'vs/platform/issue/common/issue'; +import BaseHtml from 'vs/code/electron-browser/issue/issueReporterPage'; export function startup(configuration: IWindowConfiguration) { + document.body.innerHTML = BaseHtml(); const issueReporter = new IssueReporter(configuration); - issueReporter.render(); + + // workaround for flickering on page load as css is applied + setTimeout(() => { + issueReporter.render(); + document.body.style.display = 'block'; + }, 10); } export class IssueReporter extends Disposable { @@ -61,7 +69,7 @@ export class IssueReporter extends Disposable { const submitButton = document.getElementById('github-submit-btn'); submitButton.disabled = false; - submitButton.textContent = 'Preview on GitHub'; + submitButton.textContent = localize('previewOnGitHub', "Preview on GitHub"); }); ipcRenderer.send('issueInfoRequest'); @@ -69,6 +77,10 @@ export class IssueReporter extends Disposable { this.initServices(configuration); this.setEventHandlers(); + + if (window.document.documentElement.lang !== 'en') { + show(document.getElementById('english')); + } } render(): void { @@ -132,8 +144,6 @@ export class IssueReporter extends Disposable { styleTag.innerHTML = content.join('\n'); document.head.appendChild(styleTag); - - document.body.style.backgroundColor = styles.backgroundColor; document.body.style.color = styles.color; } @@ -215,7 +225,7 @@ export class IssueReporter extends Disposable { if (result.items.length) { const issues = $('ul'); const issuesText = $('div.list-title'); - issuesText.textContent = 'Similar issues:'; + issuesText.textContent = localize('similarIssues', "Similar issues"); addIssuesToList(issues, result.items); similarIssues.appendChild(issuesText); similarIssues.appendChild(issues); @@ -255,9 +265,9 @@ export class IssueReporter extends Disposable { hide(processBlock); hide(workspaceBlock); - descriptionTitle.innerHTML = 'Steps to Reproduce *'; + descriptionTitle.innerHTML = `${localize('stepsToReproduce', "Steps to Reproduce")} *`; show(descriptionSubtitle); - descriptionSubtitle.innerHTML = 'How did you encounter this problem? Please provide clear steps to reproduce the problem during our investigation. What did you expect to happen and what actually did happen?'; + descriptionSubtitle.innerHTML = localize('bugDescription', "How did you encounter this problem? Please provide clear steps to reproduce the problem during our investigation. What did you expect to happen and what actually did happen?"); } // 2 - Perf Issue else if (issueType === 1) { @@ -265,9 +275,9 @@ export class IssueReporter extends Disposable { show(processBlock); show(workspaceBlock); - descriptionTitle.innerHTML = 'Steps to Reproduce *'; + descriptionTitle.innerHTML = `${localize('stepsToReproduce', "Steps to Reproduce")} *`; show(descriptionSubtitle); - descriptionSubtitle.innerHTML = 'When did this performance issue happen? For example, does it occur on startup or after a specific series of actions? Any details you can provide help our investigation.'; + descriptionSubtitle.innerHTML = localize('performanceIssueDesciption', "When did this performance issue happen? For example, does it occur on startup or after a specific series of actions? Any details you can provide help our investigation."); } // 3 - Feature Request else { @@ -275,7 +285,7 @@ export class IssueReporter extends Disposable { hide(processBlock); hide(workspaceBlock); - descriptionTitle.innerHTML = 'Description *'; + descriptionTitle.innerHTML = `${localize('description', "Description")} *`; hide(descriptionSubtitle); } } diff --git a/src/vs/code/electron-browser/issue/issueReporterPage.ts b/src/vs/code/electron-browser/issue/issueReporterPage.ts new file mode 100644 index 00000000000..2551db67e31 --- /dev/null +++ b/src/vs/code/electron-browser/issue/issueReporterPage.ts @@ -0,0 +1,98 @@ +/*--------------------------------------------------------------------------------------------- + * Copyright (c) Microsoft Corporation. All rights reserved. + * Licensed under the MIT License. See License.txt in the project root for license information. + *--------------------------------------------------------------------------------------------*/ +'use strict'; + +import { escape } from 'vs/base/common/strings'; +import { localize } from 'vs/nls'; + +export default (): string => ` +
+ + +
+ + +
+ +
+ + + + + + +
+ +
+
+ + +
+
+ + +
+
+ +
+
+
+ ${escape(localize('systemInfo', "My System Info"))} + + + + +
+ +
+
+
+
+
+ ${escape(localize('processes', "Currently Running Processes"))} + + + + +
+ +
+
+
+
+
+ ${escape(localize('workspaceStats', "My Workspace Stats"))} + + + + +
+					
+						
+					
+				
+
+
+
+ + + + +
+ ${escape(localize('githubMarkdown', "We support GitHub-flavored Markdown. You will still be able to edit your issue when we preview it on GitHub."))} + + +
+
+
+ + +
`; \ No newline at end of file diff --git a/src/vs/code/electron-browser/issue/media/issueReporter.css b/src/vs/code/electron-browser/issue/media/issueReporter.css index e4ca54e35b5..d7e3c8ec2d8 100644 --- a/src/vs/code/electron-browser/issue/media/issueReporter.css +++ b/src/vs/code/electron-browser/issue/media/issueReporter.css @@ -97,7 +97,6 @@ html { body { margin: 0; - background-color: #1E1E1E; } .hidden { diff --git a/src/vs/platform/issue/electron-main/issueService.ts b/src/vs/platform/issue/electron-main/issueService.ts index ba398e53b21..096aec418c8 100644 --- a/src/vs/platform/issue/electron-main/issueService.ts +++ b/src/vs/platform/issue/electron-main/issueService.ts @@ -6,12 +6,15 @@ 'use strict'; import { TPromise, Promise } from 'vs/base/common/winjs.base'; +import { localize } from 'vs/nls'; import { IIssueService, IssueReporterStyles } from 'vs/platform/issue/common/issue'; import { BrowserWindow, ipcMain } from 'electron'; import { ILaunchService } from 'vs/code/electron-main/launch'; import { buildDiagnostics, DiagnosticInfo } from 'vs/code/electron-main/diagnostics'; import { IEnvironmentService } from 'vs/platform/environment/common/environment'; +const DEFAULT_BACKGROUND_COLOR = '#1E1E1E'; + export class IssueService implements IIssueService { _serviceBrand: any; _issueWindow: BrowserWindow; @@ -39,8 +42,9 @@ export class IssueService implements IIssueService { this._issueWindow = new BrowserWindow({ width: 800, height: 900, - title: 'Issue Reporter', - parent: BrowserWindow.getFocusedWindow() + title: localize('issueReporter', "Issue Reporter"), + parent: BrowserWindow.getFocusedWindow(), + backgroundColor: theme && theme.backgroundColor || DEFAULT_BACKGROUND_COLOR }); this._issueWindow.setMenuBarVisibility(false); // workaround for now, until a menu is implemented From 1e117f4168408132500b134a5ce3c70f162cd4c0 Mon Sep 17 00:00:00 2001 From: Matt Bierner Date: Mon, 22 Jan 2018 21:47:56 -0800 Subject: [PATCH 31/63] Revert "Revert "Use special prefix to tell TS that a resource is in-memory only (#42001)"" This reverts commit 200e4013571881949f3c7196088c61f3752b1716. --- .../src/features/bufferSyncSupport.ts | 5 +-- .../typescript/src/typescriptServiceClient.ts | 37 +++++++++++++------ 2 files changed, 27 insertions(+), 15 deletions(-) diff --git a/extensions/typescript/src/features/bufferSyncSupport.ts b/extensions/typescript/src/features/bufferSyncSupport.ts index 63f0bdfbc86..186cd02ba6b 100644 --- a/extensions/typescript/src/features/bufferSyncSupport.ts +++ b/extensions/typescript/src/features/bufferSyncSupport.ts @@ -48,10 +48,7 @@ class SyncedBuffer { } if (this.client.apiVersion.has230Features()) { - const root = this.client.getWorkspaceRootForResource(this.document.uri); - if (root) { - args.projectRootPath = root; - } + args.projectRootPath = this.client.getWorkspaceRootForResource(this.document.uri); } if (this.client.apiVersion.has240Features()) { diff --git a/extensions/typescript/src/typescriptServiceClient.ts b/extensions/typescript/src/typescriptServiceClient.ts index 2901d184ba1..a36818b3905 100644 --- a/extensions/typescript/src/typescriptServiceClient.ts +++ b/extensions/typescript/src/typescriptServiceClient.ts @@ -578,12 +578,12 @@ export default class TypeScriptServiceClient implements ITypeScriptServiceClient } public normalizePath(resource: Uri): string | null { - if (resource.scheme === fileSchemes.walkThroughSnippet) { - return resource.toString(); - } - - if (resource.scheme === fileSchemes.untitled && this._apiVersion.has213Features()) { - return resource.toString(); + if (this._apiVersion.has213Features()) { + if (resource.scheme === fileSchemes.walkThroughSnippet || resource.scheme === fileSchemes.untitled) { + const dirName = path.dirname(resource.path); + const fileName = this.inMemoryResourcePrefix + path.basename(resource.path); + return resource.with({ path: path.join(dirName, fileName) }).toString(true); + } } if (resource.scheme !== fileSchemes.file) { @@ -599,11 +599,24 @@ export default class TypeScriptServiceClient implements ITypeScriptServiceClient return result.replace(new RegExp('\\' + this.pathSeparator, 'g'), '/'); } + private get inMemoryResourcePrefix(): string { + return this._apiVersion.has270Features() ? '^' : ''; + } + public asUrl(filepath: string): Uri { - if (filepath.startsWith(TypeScriptServiceClient.WALK_THROUGH_SNIPPET_SCHEME_COLON) - || (filepath.startsWith(fileSchemes.untitled + ':') && this._apiVersion.has213Features()) - ) { - return Uri.parse(filepath); + if (this._apiVersion.has213Features()) { + if (filepath.startsWith(TypeScriptServiceClient.WALK_THROUGH_SNIPPET_SCHEME_COLON) || (filepath.startsWith(fileSchemes.untitled + ':')) + ) { + let resource = Uri.parse(filepath); + if (this.inMemoryResourcePrefix) { + const dirName = path.dirname(resource.path); + const fileName = path.basename(resource.path); + if (fileName.startsWith(this.inMemoryResourcePrefix)) { + resource = resource.with({ path: path.join(dirName, fileName.slice(this.inMemoryResourcePrefix.length)) }); + } + } + return resource; + } } return Uri.file(filepath); } @@ -620,8 +633,10 @@ export default class TypeScriptServiceClient implements ITypeScriptServiceClient return root.uri.fsPath; } } + return roots[0].uri.fsPath; } - return roots[0].uri.fsPath; + + return undefined; } public execute(command: string, args: any, expectsResultOrToken?: boolean | CancellationToken): Promise { From 34d370a0af10894716911e7f69f2271bb00be35a Mon Sep 17 00:00:00 2001 From: Matt Bierner Date: Tue, 23 Jan 2018 13:10:06 -0800 Subject: [PATCH 32/63] check log uploader result type --- src/vs/code/electron-main/logUploader.ts | 10 ++++++++-- 1 file changed, 8 insertions(+), 2 deletions(-) diff --git a/src/vs/code/electron-main/logUploader.ts b/src/vs/code/electron-main/logUploader.ts index bbcc8a6a76a..e6d6b81f20c 100644 --- a/src/vs/code/electron-main/logUploader.ts +++ b/src/vs/code/electron-main/logUploader.ts @@ -101,8 +101,14 @@ async function postLogs( result.stream.on('end', () => { try { - const result = Buffer.concat(parts).toString('utf-8'); - res(JSON.parse(result)); + const response = Buffer.concat(parts).toString('utf-8'); + if (result.res.statusCode === 200) { + res(JSON.parse(response)); + } else { + const errorMessage = localize('responseError', 'Error posting logs. Got {0}', result.res.statusCode); + console.log(errorMessage); + reject(new Error(errorMessage)); + } } catch (e) { console.log(localize('parseError', 'Error parsing response')); reject(e); From 1ced6adf3d7a0b5227986f64847d9b51ea1280a4 Mon Sep 17 00:00:00 2001 From: Matt Bierner Date: Tue, 23 Jan 2018 14:10:11 -0800 Subject: [PATCH 33/63] make BASE64_MARKER static constant --- src/vs/base/browser/ui/resourceviewer/resourceViewer.ts | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/src/vs/base/browser/ui/resourceviewer/resourceViewer.ts b/src/vs/base/browser/ui/resourceviewer/resourceViewer.ts index 86ac9fbeee4..65c67397ddc 100644 --- a/src/vs/base/browser/ui/resourceviewer/resourceViewer.ts +++ b/src/vs/base/browser/ui/resourceviewer/resourceViewer.ts @@ -156,6 +156,7 @@ export class ResourceViewer { class ImageView { private static readonly MAX_IMAGE_SIZE = BinarySize.MB; // showing images inline is memory intense, so we have a limit + private static readonly BASE64_MARKER = 'base64,'; public static create( container: Builder, @@ -177,9 +178,8 @@ class ImageView { // Data URI if (descriptor.resource.scheme === Schemas.data) { - const BASE64_MARKER = 'base64,'; - const base64MarkerIndex = descriptor.resource.path.indexOf(BASE64_MARKER); - const hasData = base64MarkerIndex >= 0 && descriptor.resource.path.substring(base64MarkerIndex + BASE64_MARKER.length).length > 0; + const base64MarkerIndex = descriptor.resource.path.indexOf(ImageView.BASE64_MARKER); + const hasData = base64MarkerIndex >= 0 && descriptor.resource.path.substring(base64MarkerIndex + ImageView.BASE64_MARKER.length).length > 0; skipInlineImage = !hasData || descriptor.size > ImageView.MAX_IMAGE_SIZE || descriptor.resource.path.length > ImageView.MAX_IMAGE_SIZE; } From 92eb582302a035f8a1c5f7a549aa0c809813265d Mon Sep 17 00:00:00 2001 From: Rob Lourens Date: Tue, 23 Jan 2018 14:11:13 -0800 Subject: [PATCH 34/63] Settings search result message -> match>found --- .../workbench/parts/preferences/browser/preferencesEditor.ts | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/vs/workbench/parts/preferences/browser/preferencesEditor.ts b/src/vs/workbench/parts/preferences/browser/preferencesEditor.ts index 054e0266e42..6bb0a8d1a70 100644 --- a/src/vs/workbench/parts/preferences/browser/preferencesEditor.ts +++ b/src/vs/workbench/parts/preferences/browser/preferencesEditor.ts @@ -285,9 +285,9 @@ export class PreferencesEditor extends BaseEditor { if (count === 0) { this.searchWidget.showMessage(nls.localize('noSettingsFound', "No Results"), count); } else if (count === 1) { - this.searchWidget.showMessage(nls.localize('oneSettingFound', "1 Setting matched"), count); + this.searchWidget.showMessage(nls.localize('oneSettingFound', "1 Setting Found"), count); } else { - this.searchWidget.showMessage(nls.localize('settingsFound', "{0} Settings matched", count), count); + this.searchWidget.showMessage(nls.localize('settingsFound', "{0} Settings Found", count), count); } } else { this.searchWidget.showMessage(nls.localize('totalSettingsMessage', "Total {0} Settings", count), count); From 621aca2fe51439da71d914a950717eb587021247 Mon Sep 17 00:00:00 2001 From: Matt Bierner Date: Tue, 23 Jan 2018 14:28:47 -0800 Subject: [PATCH 35/63] Used pixelated scaling when image is zoomed more than 300% --- .../browser/ui/resourceviewer/resourceViewer.ts | 15 ++++++++++----- .../browser/ui/resourceviewer/resourceviewer.css | 1 - 2 files changed, 10 insertions(+), 6 deletions(-) diff --git a/src/vs/base/browser/ui/resourceviewer/resourceViewer.ts b/src/vs/base/browser/ui/resourceviewer/resourceViewer.ts index 65c67397ddc..1cc85d0ae29 100644 --- a/src/vs/base/browser/ui/resourceviewer/resourceViewer.ts +++ b/src/vs/base/browser/ui/resourceviewer/resourceViewer.ts @@ -241,7 +241,11 @@ class InlineImageView { private static readonly SCALE_FACTOR = 1.5; private static readonly MAX_SCALE = 20; private static readonly MIN_SCALE = 0.1; - private static readonly PIXELATION_THRESHOLD = 64; // enable image-rendering: pixelated for images less than this + + /** + * Enable image-rendering: pixelated for images scaled by more than this. + */ + private static readonly PIXELATION_THRESHOLD = 3; /** * Chrome is caching images very aggressively and so we use the ETag information to find out if @@ -279,16 +283,17 @@ class InlineImageView { img.removeClass('untouched'); updateScale(scale); } - if (imgElement.naturalWidth < InlineImageView.PIXELATION_THRESHOLD - || imgElement.naturalHeight < InlineImageView.PIXELATION_THRESHOLD) { - img.addClass('pixelated'); - } function setImageWidth(width) { img.style('width', `${width}px`); img.style('height', 'auto'); } function updateScale(newScale) { scale = clamp(newScale, InlineImageView.MIN_SCALE, InlineImageView.MAX_SCALE); + if (scale >= InlineImageView.PIXELATION_THRESHOLD) { + img.addClass('pixelated'); + } else { + img.removeClass('pixelated'); + } setImageWidth(Math.floor(imgElement.naturalWidth * scale)); InlineImageView.IMAGE_SCALE_CACHE.set(cacheKey, scale); scrollbar.scanDomNode(); diff --git a/src/vs/base/browser/ui/resourceviewer/resourceviewer.css b/src/vs/base/browser/ui/resourceviewer/resourceviewer.css index 054159a1281..1f7b897d6b8 100644 --- a/src/vs/base/browser/ui/resourceviewer/resourceviewer.css +++ b/src/vs/base/browser/ui/resourceviewer/resourceviewer.css @@ -42,7 +42,6 @@ .monaco-resource-viewer img.untouched { max-width: 100%; object-fit: contain; - image-rendering: auto; } .monaco-resource-viewer img { From d16baaaa1a63d9b0dbad5c869dcf8b79c660d8bd Mon Sep 17 00:00:00 2001 From: Matt Bierner Date: Tue, 23 Jan 2018 15:07:06 -0800 Subject: [PATCH 36/63] Use choice server for log uploader --- src/vs/code/electron-main/logUploader.ts | 35 ++++++++++++------------ src/vs/code/electron-main/main.ts | 6 +++- 2 files changed, 22 insertions(+), 19 deletions(-) diff --git a/src/vs/code/electron-main/logUploader.ts b/src/vs/code/electron-main/logUploader.ts index e6d6b81f20c..94280c83dcb 100644 --- a/src/vs/code/electron-main/logUploader.ts +++ b/src/vs/code/electron-main/logUploader.ts @@ -9,7 +9,6 @@ import * as os from 'os'; import * as cp from 'child_process'; import * as fs from 'fs'; import * as path from 'path'; -import * as readline from 'readline'; import { localize } from 'vs/nls'; import { ILaunchChannel } from 'vs/code/electron-main/launch'; @@ -17,6 +16,8 @@ import { TPromise } from 'vs/base/common/winjs.base'; import product from 'vs/platform/node/product'; import { IRequestService } from 'vs/platform/request/node/request'; import { IRequestContext } from 'vs/base/node/request'; +import { IChoiceService } from 'vs/platform/message/common/message'; +import Severity from 'vs/base/common/severity'; interface PostResult { readonly blob_id: string; @@ -35,7 +36,8 @@ class Endpoint { export async function uploadLogs( channel: ILaunchChannel, - requestService: IRequestService + requestService: IRequestService, + choiceService: IChoiceService ): TPromise { const endpoint = Endpoint.getFromProduct(); if (!endpoint) { @@ -45,7 +47,8 @@ export async function uploadLogs( const logsPath = await channel.call('get-logs-path', null); - if (await promptUserToConfirmLogUpload(logsPath)) { + if (await promptUserToConfirmLogUpload(logsPath, choiceService)) { + console.log(localize('beginUploading', 'Uploading...')); const outZip = await zipLogs(logsPath); const result = await postLogs(endpoint, outZip, requestService); console.log(localize('didUploadLogs', 'Uploaded logs ID: {0}', result.blob_id)); @@ -55,22 +58,18 @@ export async function uploadLogs( } async function promptUserToConfirmLogUpload( - logsPath: string + logsPath: string, + choiceService: IChoiceService ): Promise { - const rl = readline.createInterface({ - input: process.stdin, - output: process.stdout - }); - - return new TPromise(resolve => - rl.question( - localize('logUploadPromptHeader', 'Upload session logs to secure endpoint?') - + '\n\n' + localize('logUploadPromptBody', 'Please review your log files: \'{0}\'', logsPath) - + '\n\n' + localize('logUploadPromptKey', 'Enter \'y\' to confirm upload...'), - (answer: string) => { - rl.close(); - resolve(answer && answer.trim()[0].toLowerCase() === 'y'); - })); + const message = localize('logUploadPromptHeader', 'Upload session logs to secure endpoint?') + + '\n\n' + localize('logUploadPromptBody', 'Please review your log files here: \'{0}\'', logsPath) + + '\n\n' + localize('logUploadPromptBodyDetails', 'Logs may contain personal information such as full paths and file contents.') + + '\n\n'; + const choice = await choiceService.choose(Severity.Info, message, [ + localize('logUploadPromptKey', 'I have reviewed my logs. Proceed with upload...'), + localize('logUploadPromptCancel', 'Cancel'), + ], 1); + return choice === 0; } async function postLogs( diff --git a/src/vs/code/electron-main/main.ts b/src/vs/code/electron-main/main.ts index 276db5a62ae..4cde51e4de3 100644 --- a/src/vs/code/electron-main/main.ts +++ b/src/vs/code/electron-main/main.ts @@ -46,6 +46,8 @@ import { createSpdLogService } from 'vs/platform/log/node/spdlogService'; import { printDiagnostics } from 'vs/code/electron-main/diagnostics'; import { BufferLogService } from 'vs/platform/log/common/bufferLog'; import { uploadLogs } from 'vs/code/electron-main/logUploader'; +import { IChoiceService } from 'vs/platform/message/common/message'; +import { ChoiceCliService } from 'vs/platform/message/node/messageCli'; function createServices(args: ParsedArgs, bufferLogService: BufferLogService): IInstantiationService { const services = new ServiceCollection(); @@ -69,6 +71,7 @@ function createServices(args: ParsedArgs, bufferLogService: BufferLogService): I services.set(IRequestService, new SyncDescriptor(RequestService)); services.set(IURLService, new SyncDescriptor(URLService, args['open-url'] ? args._urls : [])); services.set(IBackupMainService, new SyncDescriptor(BackupMainService)); + services.set(IChoiceService, new SyncDescriptor(ChoiceCliService)); return new InstantiationService(services, true); } @@ -106,6 +109,7 @@ function setupIPC(accessor: ServicesAccessor): TPromise { const logService = accessor.get(ILogService); const environmentService = accessor.get(IEnvironmentService); const requestService = accessor.get(IRequestService); + const choiceService = accessor.get(IChoiceService); function allowSetForegroundWindow(service: LaunchChannelClient): TPromise { let promise = TPromise.wrap(void 0); @@ -199,7 +203,7 @@ function setupIPC(accessor: ServicesAccessor): TPromise { // Log uploader if (environmentService.args['upload-logs']) { - return uploadLogs(channel, requestService) + return uploadLogs(channel, requestService, choiceService) .then(() => TPromise.wrapError(new ExpectedError())); } From 560f5de0fafabfde8c0db2dc4d82989d184bd1a8 Mon Sep 17 00:00:00 2001 From: Ramya Achutha Rao Date: Tue, 23 Jan 2018 15:28:39 -0800 Subject: [PATCH 37/63] Name InstallCountWidget correctly --- src/vs/workbench/parts/extensions/browser/extensionEditor.ts | 4 ++-- src/vs/workbench/parts/extensions/browser/extensionsList.ts | 4 ++-- .../workbench/parts/extensions/browser/extensionsWidgets.ts | 2 +- 3 files changed, 5 insertions(+), 5 deletions(-) diff --git a/src/vs/workbench/parts/extensions/browser/extensionEditor.ts b/src/vs/workbench/parts/extensions/browser/extensionEditor.ts index 84e9f9c800e..dd66df55fde 100644 --- a/src/vs/workbench/parts/extensions/browser/extensionEditor.ts +++ b/src/vs/workbench/parts/extensions/browser/extensionEditor.ts @@ -30,7 +30,7 @@ import { ResolvedKeybinding, KeyMod, KeyCode } from 'vs/base/common/keyCodes'; import { ExtensionsInput } from 'vs/workbench/parts/extensions/common/extensionsInput'; import { IExtensionsWorkbenchService, IExtensionsViewlet, VIEWLET_ID, IExtension, IExtensionDependencies } from 'vs/workbench/parts/extensions/common/extensions'; import { Renderer, DataSource, Controller } from 'vs/workbench/parts/extensions/browser/dependenciesViewer'; -import { RatingsWidget, InstallWidget } from 'vs/workbench/parts/extensions/browser/extensionsWidgets'; +import { RatingsWidget, InstallCountWidget } from 'vs/workbench/parts/extensions/browser/extensionsWidgets'; import { EditorOptions } from 'vs/workbench/common/editor'; import { ActionBar } from 'vs/base/browser/ui/actionbar/actionbar'; import { CombinedInstallAction, UpdateAction, EnableAction, DisableAction, BuiltinStatusLabelAction, ReloadAction } from 'vs/workbench/parts/extensions/browser/extensionsActions'; @@ -337,7 +337,7 @@ export class ExtensionEditor extends BaseEditor { this.repository.style.display = 'none'; } - const install = this.instantiationService.createInstance(InstallWidget, this.installCount, { extension }); + const install = this.instantiationService.createInstance(InstallCountWidget, this.installCount, { extension }); this.transientDisposables.push(install); const ratings = this.instantiationService.createInstance(RatingsWidget, this.rating, { extension }); diff --git a/src/vs/workbench/parts/extensions/browser/extensionsList.ts b/src/vs/workbench/parts/extensions/browser/extensionsList.ts index 2179edff031..0b588e8353c 100644 --- a/src/vs/workbench/parts/extensions/browser/extensionsList.ts +++ b/src/vs/workbench/parts/extensions/browser/extensionsList.ts @@ -18,7 +18,7 @@ import { domEvent } from 'vs/base/browser/event'; import { IExtension, IExtensionsWorkbenchService } from 'vs/workbench/parts/extensions/common/extensions'; import { InstallAction, UpdateAction, BuiltinStatusLabelAction, ManageExtensionAction, ReloadAction, extensionButtonProminentBackground, extensionButtonProminentForeground } from 'vs/workbench/parts/extensions/browser/extensionsActions'; import { areSameExtensions } from 'vs/platform/extensionManagement/common/extensionManagementUtil'; -import { Label, RatingsWidget, InstallWidget } from 'vs/workbench/parts/extensions/browser/extensionsWidgets'; +import { Label, RatingsWidget, InstallCountWidget } from 'vs/workbench/parts/extensions/browser/extensionsWidgets'; import { IExtensionService } from 'vs/platform/extensions/common/extensions'; import { IExtensionTipsService } from 'vs/platform/extensionManagement/common/extensionManagement'; import { IThemeService } from 'vs/platform/theme/common/themeService'; @@ -93,7 +93,7 @@ export class Renderer implements IPagedRenderer { actionbar.onDidRun(({ error }) => error && this.messageService.show(Severity.Error, error)); const versionWidget = this.instantiationService.createInstance(Label, version, (e: IExtension) => e.version); - const installCountWidget = this.instantiationService.createInstance(InstallWidget, installCount, { small: true }); + const installCountWidget = this.instantiationService.createInstance(InstallCountWidget, installCount, { small: true }); const ratingsWidget = this.instantiationService.createInstance(RatingsWidget, ratings, { small: true }); const builtinStatusAction = this.instantiationService.createInstance(BuiltinStatusLabelAction); diff --git a/src/vs/workbench/parts/extensions/browser/extensionsWidgets.ts b/src/vs/workbench/parts/extensions/browser/extensionsWidgets.ts index 3167b710f49..f8e86e08d88 100644 --- a/src/vs/workbench/parts/extensions/browser/extensionsWidgets.ts +++ b/src/vs/workbench/parts/extensions/browser/extensionsWidgets.ts @@ -42,7 +42,7 @@ export class Label implements IDisposable { } } -export class InstallWidget implements IDisposable { +export class InstallCountWidget implements IDisposable { private disposables: IDisposable[] = []; private _extension: IExtension; From 7ce2824069c035fa63f31e7d7b3c2fc73eefdce7 Mon Sep 17 00:00:00 2001 From: Rob Lourens Date: Tue, 23 Jan 2018 15:39:50 -0800 Subject: [PATCH 38/63] Settings search - fix JSON-encoded default values from remote search --- .../parts/preferences/electron-browser/preferencesSearch.ts | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/src/vs/workbench/parts/preferences/electron-browser/preferencesSearch.ts b/src/vs/workbench/parts/preferences/electron-browser/preferencesSearch.ts index 7614813e29f..3366eafe38d 100644 --- a/src/vs/workbench/parts/preferences/electron-browser/preferencesSearch.ts +++ b/src/vs/workbench/parts/preferences/electron-browser/preferencesSearch.ts @@ -215,6 +215,9 @@ class RemoteSearchProvider implements ISearchProvider { const packageId = r['packageid']; const id = getSettingKey(key, packageId); + const value = r['value']; + const defaultValue = value ? JSON.parse(value) : value; + const packageName = r['packagename']; let extensionName: string; let extensionPublisher: string; @@ -225,7 +228,7 @@ class RemoteSearchProvider implements ISearchProvider { return { key, id, - defaultValue: r['value'], + defaultValue, score: r['@search.score'], description: JSON.parse(r['details']), packageId, From ea09c48688307607452c89ae0cd0c56bd05b9d13 Mon Sep 17 00:00:00 2001 From: Rob Lourens Date: Tue, 23 Jan 2018 15:40:31 -0800 Subject: [PATCH 39/63] Settings search - tweak labels --- src/vs/workbench/parts/preferences/browser/preferencesEditor.ts | 2 +- .../workbench/parts/preferences/browser/preferencesRenderers.ts | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/src/vs/workbench/parts/preferences/browser/preferencesEditor.ts b/src/vs/workbench/parts/preferences/browser/preferencesEditor.ts index 6bb0a8d1a70..88c601b8200 100644 --- a/src/vs/workbench/parts/preferences/browser/preferencesEditor.ts +++ b/src/vs/workbench/parts/preferences/browser/preferencesEditor.ts @@ -434,7 +434,7 @@ class PreferencesRenderersController extends Disposable { this._currentNewExtensionsSearchProvider = (updateCurrentResults && this._currentNewExtensionsSearchProvider) || this.preferencesSearchService.getRemoteSearchProvider(query, true); this._remoteFilterInProgress = this.filterOrSearchPreferences(query, this._currentRemoteSearchProvider, 'nlpResult', nls.localize('nlpResult', "Natural Language Results"), 1) - .then(result => this.filterOrSearchPreferences(query, this._currentNewExtensionsSearchProvider, 'newExtensionsResult', nls.localize('newExtensionsResult', "Other Extension Results"), 2)); + .then(result => this.filterOrSearchPreferences(query, this._currentNewExtensionsSearchProvider, 'newExtensionsResult', nls.localize('newExtensionsResult', "Marketplace Extension Results"), 2)); return this._remoteFilterInProgress.then(() => { this._remoteFilterInProgress = null; diff --git a/src/vs/workbench/parts/preferences/browser/preferencesRenderers.ts b/src/vs/workbench/parts/preferences/browser/preferencesRenderers.ts index b467aa4b539..24c071bd5ff 100644 --- a/src/vs/workbench/parts/preferences/browser/preferencesRenderers.ts +++ b/src/vs/workbench/parts/preferences/browser/preferencesRenderers.ts @@ -877,7 +877,7 @@ export class ExtensionCodelensRenderer extends Disposable implements CodeLensPro const extId = s.extensionPublisher + '.' + s.extensionName; return { command: { - title: nls.localize('newExtensionLabel', "View \"{0}\"", extId), + title: nls.localize('newExtensionLabel', "Show Extension \"{0}\"", extId), id: 'workbench.extensions.action.showExtensionsWithId', arguments: [extId.toLowerCase()] }, From 9265607eee84e9481ded55c2d6f5f458da44f217 Mon Sep 17 00:00:00 2001 From: Peng Lyu Date: Tue, 23 Jan 2018 13:19:58 -0800 Subject: [PATCH 40/63] update find results limit comment. --- src/vs/editor/contrib/find/findModel.ts | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/vs/editor/contrib/find/findModel.ts b/src/vs/editor/contrib/find/findModel.ts index deacb765f44..7f0a8ac7ab4 100644 --- a/src/vs/editor/contrib/find/findModel.ts +++ b/src/vs/editor/contrib/find/findModel.ts @@ -396,7 +396,7 @@ export class FindModelBoundToEditorModel { const findScope = this._decorations.getFindScope(); if (findScope === null && this._state.matchesCount >= MATCHES_LIMIT) { - // Doing a replace on the entire file that is over 1k matches + // Doing a replace on the entire file that is over ${MATCHES_LIMIT} matches this._largeReplaceAll(); } else { this._regularReplaceAll(findScope); From 08046c3aa4f827b66567207be8556b267c52fd49 Mon Sep 17 00:00:00 2001 From: Peng Lyu Date: Tue, 23 Jan 2018 14:17:00 -0800 Subject: [PATCH 41/63] piece tree perf is propotional to edit cnt so 10/100 edits are not necessary. --- .../model/benchmark/operations.benchmark.ts | 156 +++++++++--------- 1 file changed, 77 insertions(+), 79 deletions(-) diff --git a/src/vs/editor/test/common/model/benchmark/operations.benchmark.ts b/src/vs/editor/test/common/model/benchmark/operations.benchmark.ts index 5a83e5f29e9..286fd3531e7 100644 --- a/src/vs/editor/test/common/model/benchmark/operations.benchmark.ts +++ b/src/vs/editor/test/common/model/benchmark/operations.benchmark.ts @@ -42,38 +42,66 @@ for (let fileSize of fileSizes) { iterations: 10 }); - for (let i of [10, 100, 1000]) { - editsSuite.add({ - name: `apply ${i} edits`, - buildBuffer: (textBufferBuilder: ITextBufferBuilder) => { - chunks.forEach(ck => textBufferBuilder.acceptChunk(ck)); - return textBufferBuilder.finish(); - }, - preCycle: (textBuffer) => { - return textBuffer; - }, - fn: (textBuffer) => { - // for line model, this loop doesn't reflect the real situation. - for (let k = 0; k < edits.length && k < i; k++) { - textBuffer.applyEdits([edits[k]], false); - } + editsSuite.add({ + name: `apply 1000 edits`, + buildBuffer: (textBufferBuilder: ITextBufferBuilder) => { + chunks.forEach(ck => textBufferBuilder.acceptChunk(ck)); + return textBufferBuilder.finish(); + }, + preCycle: (textBuffer) => { + return textBuffer; + }, + fn: (textBuffer) => { + // for line model, this loop doesn't reflect the real situation. + for (let k = 0; k < edits.length; k++) { + textBuffer.applyEdits([edits[k]], false); } - }); + } + }); - editsSuite.add({ - name: `Read all lines after ${i} edits`, - buildBuffer: (textBufferBuilder: ITextBufferBuilder) => { - chunks.forEach(ck => textBufferBuilder.acceptChunk(ck)); - return textBufferBuilder.finish(); - }, - preCycle: (textBuffer) => { - for (let k = 0; k < edits.length && k < i; k++) { - textBuffer.applyEdits([edits[k]], false); - } - return textBuffer; - }, - fn: (textBuffer) => { - for (let j = 0, len = textBuffer.getLineCount(); j < len; j++) { + editsSuite.add({ + name: `Read all lines after 1000 edits`, + buildBuffer: (textBufferBuilder: ITextBufferBuilder) => { + chunks.forEach(ck => textBufferBuilder.acceptChunk(ck)); + return textBufferBuilder.finish(); + }, + preCycle: (textBuffer) => { + for (let k = 0; k < edits.length; k++) { + textBuffer.applyEdits([edits[k]], false); + } + return textBuffer; + }, + fn: (textBuffer) => { + for (let j = 0, len = textBuffer.getLineCount(); j < len; j++) { + var str = textBuffer.getLineContent(j + 1); + let firstChar = str.charCodeAt(0); + let lastChar = str.charCodeAt(str.length - 1); + firstChar = firstChar - lastChar; + lastChar = firstChar + lastChar; + firstChar = lastChar - firstChar; + } + } + }); + + editsSuite.add({ + name: `Read 10 random windows after 1000 edits`, + buildBuffer: (textBufferBuilder: ITextBufferBuilder) => { + chunks.forEach(ck => textBufferBuilder.acceptChunk(ck)); + return textBufferBuilder.finish(); + }, + preCycle: (textBuffer) => { + for (let k = 0; k < edits.length; k++) { + textBuffer.applyEdits([edits[k]], false); + } + return textBuffer; + }, + fn: (textBuffer) => { + for (let i = 0; i < 10; i++) { + let minLine = 1; + let maxLine = textBuffer.getLineCount(); + let startLine = getRandomInt(minLine, Math.max(minLine, maxLine - 100)); + let endLine = Math.min(maxLine, startLine + 100); + for (let j = startLine; j < endLine; j++) { var str = textBuffer.getLineContent(j + 1); let firstChar = str.charCodeAt(0); let lastChar = str.charCodeAt(str.length - 1); @@ -82,57 +110,27 @@ for (let fileSize of fileSizes) { firstChar = lastChar - firstChar; } } - }); + } + }); - editsSuite.add({ - name: `Read 10 random windows after ${i} edits`, - buildBuffer: (textBufferBuilder: ITextBufferBuilder) => { - chunks.forEach(ck => textBufferBuilder.acceptChunk(ck)); - return textBufferBuilder.finish(); - }, - preCycle: (textBuffer) => { - for (let k = 0; k < edits.length && k < i; k++) { - textBuffer.applyEdits([edits[k]], false); - } - return textBuffer; - }, - fn: (textBuffer) => { - for (let i = 0; i < 10; i++) { - let minLine = 1; - let maxLine = textBuffer.getLineCount(); - let startLine = getRandomInt(minLine, Math.max(minLine, maxLine - 100)); - let endLine = Math.min(maxLine, startLine + 100); - for (let j = startLine; j < endLine; j++) { - var str = textBuffer.getLineContent(j + 1); - let firstChar = str.charCodeAt(0); - let lastChar = str.charCodeAt(str.length - 1); - firstChar = firstChar - lastChar; - lastChar = firstChar + lastChar; - firstChar = lastChar - firstChar; - } - } + editsSuite.add({ + name: `save file after 1000 edits`, + buildBuffer: (textBufferBuilder: ITextBufferBuilder) => { + chunks.forEach(ck => textBufferBuilder.acceptChunk(ck)); + return textBufferBuilder.finish(); + }, + preCycle: (textBuffer) => { + for (let k = 0; k < edits.length; k++) { + textBuffer.applyEdits([edits[k]], false); } - }); - - editsSuite.add({ - name: `save file after ${i} edits`, - buildBuffer: (textBufferBuilder: ITextBufferBuilder) => { - chunks.forEach(ck => textBufferBuilder.acceptChunk(ck)); - return textBufferBuilder.finish(); - }, - preCycle: (textBuffer) => { - for (let k = 0; k < edits.length && k < i; k++) { - textBuffer.applyEdits([edits[k]], false); - } - return textBuffer; - }, - fn: (textBuffer) => { - const lineCount = textBuffer.getLineCount(); - const fullModelRange = new Range(1, 1, lineCount, textBuffer.getLineLength(lineCount) + 1); - textBuffer.getValueInRange(fullModelRange, EndOfLinePreference.LF); - } - }); - } + return textBuffer; + }, + fn: (textBuffer) => { + const lineCount = textBuffer.getLineCount(); + const fullModelRange = new Range(1, 1, lineCount, textBuffer.getLineLength(lineCount) + 1); + textBuffer.getValueInRange(fullModelRange, EndOfLinePreference.LF); + } + }); editsSuite.run(); } From c74962497616d0dacd89fd11cc25db4fbbe60637 Mon Sep 17 00:00:00 2001 From: Rob Lourens Date: Tue, 23 Jan 2018 16:51:31 -0800 Subject: [PATCH 42/63] Install builtInExtensions on windows too --- scripts/code.bat | 3 +++ 1 file changed, 3 insertions(+) diff --git a/scripts/code.bat b/scripts/code.bat index 3b403b1c64c..5a98f590c01 100644 --- a/scripts/code.bat +++ b/scripts/code.bat @@ -17,6 +17,9 @@ set CODE=".build\electron\%NAMESHORT%" node build\lib\electron.js if %errorlevel% neq 0 node .\node_modules\gulp\bin\gulp.js electron +:: Get built-in extensions +node build\lib\builtInExtensions.js || .\node_modules\.bin\gulp builtInExtensions + :: Build if not exist out node .\node_modules\gulp\bin\gulp.js compile From 6ae8a18cf42b746319b570c392970c5a544487bc Mon Sep 17 00:00:00 2001 From: Rachel Macfarlane Date: Tue, 23 Jan 2018 16:54:56 -0800 Subject: [PATCH 43/63] CSS tweaks to issue reporter, fixes #42064, #41993, and #42054 --- .../electron-browser/issue/issueReporter.html | 3 +-- .../issue/issueReporterMain.ts | 7 ++--- .../issue/issueReporterPage.ts | 27 ++++++++++--------- .../issue/media/issueReporter.css | 19 +++++++------ 4 files changed, 28 insertions(+), 28 deletions(-) diff --git a/src/vs/code/electron-browser/issue/issueReporter.html b/src/vs/code/electron-browser/issue/issueReporter.html index 629aab5ea44..695de78a4cb 100644 --- a/src/vs/code/electron-browser/issue/issueReporter.html +++ b/src/vs/code/electron-browser/issue/issueReporter.html @@ -8,8 +8,7 @@ - - Issue Reporter + diff --git a/src/vs/code/electron-browser/issue/issueReporterMain.ts b/src/vs/code/electron-browser/issue/issueReporterMain.ts index 8ba1dd95e00..93be7de5db0 100644 --- a/src/vs/code/electron-browser/issue/issueReporterMain.ts +++ b/src/vs/code/electron-browser/issue/issueReporterMain.ts @@ -115,7 +115,8 @@ export class IssueReporter extends Disposable { } if (styles.inputErrorBorder) { - content.push(`.invalid-input, .invalid-input:focus { border: 1px solid ${styles.inputErrorBorder}; }`); + content.push(`.invalid-input, .invalid-input:focus { border: 1px solid ${styles.inputErrorBorder} !important; }`); + content.push(`.validation-error { color: ${styles.inputErrorBorder}; }`); } if (styles.inputActiveBorder) { @@ -256,8 +257,8 @@ export class IssueReporter extends Disposable { const processBlock = document.querySelector('.block-process'); const workspaceBlock = document.querySelector('.block-workspace'); - const descriptionTitle = document.querySelector('.block-description .block-title'); - const descriptionSubtitle = document.querySelector('.block-description .block-subtitle'); + const descriptionTitle = document.getElementById('issue-description-label'); + const descriptionSubtitle = document.getElementById('issue-description-subtitle'); // 1 - Bug if (issueType === 0) { diff --git a/src/vs/code/electron-browser/issue/issueReporterPage.ts b/src/vs/code/electron-browser/issue/issueReporterPage.ts index 2551db67e31..5836f45bd10 100644 --- a/src/vs/code/electron-browser/issue/issueReporterPage.ts +++ b/src/vs/code/electron-browser/issue/issueReporterPage.ts @@ -40,7 +40,7 @@ export default (): string => ` -
+
${escape(localize('systemInfo', "My System Info"))} @@ -79,18 +79,19 @@ export default (): string => `
-
- - - - -
- ${escape(localize('githubMarkdown', "We support GitHub-flavored Markdown. You will still be able to edit your issue when we preview it on GitHub."))} - - -
+
+ +
+ + + + +
+ ${escape(localize('githubMarkdown', "We support GitHub-flavored Markdown. You will still be able to edit your issue when we preview it on GitHub."))} + +
diff --git a/src/vs/code/electron-browser/issue/media/issueReporter.css b/src/vs/code/electron-browser/issue/media/issueReporter.css index d7e3c8ec2d8..1444e6cd944 100644 --- a/src/vs/code/electron-browser/issue/media/issueReporter.css +++ b/src/vs/code/electron-browser/issue/media/issueReporter.css @@ -104,14 +104,7 @@ body { } #block-container { - margin-top: 20px; -} - -.block { - margin-bottom: 20px; -} -.block summary { - margin-bottom: 16px; + margin-top: 1em; } .block .block-info { @@ -170,23 +163,29 @@ select, input, textarea { summary { border: 1px solid transparent; + padding: 10px; + margin-bottom: 5px; } .validation-error { font-size: 12px; - font-weight: bold; margin-top: 1em; } .caption { display: inline-block; font-size: 12px; + vertical-align: middle; + height: 18px; } input[type="checkbox"] { margin-left: 1em; + height: 18px; width: auto; display: inline-block; + margin-top: 0; + vertical-align: middle; } input:disabled { @@ -213,7 +212,7 @@ a { border: 1px solid #be1100; } -.required-input { +.required-input, .validation-error { color: #be1100; } From d57363041c9f70e05932229724044aa039766b6f Mon Sep 17 00:00:00 2001 From: Rob Lourens Date: Tue, 23 Jan 2018 17:42:41 -0800 Subject: [PATCH 44/63] Settings search - fix feedback and telemetry to handle extension setting results --- .../preferences/browser/preferencesEditor.ts | 16 ++++--- .../browser/preferencesRenderers.ts | 43 +++++++++++-------- .../parts/preferences/common/preferences.ts | 6 ++- .../preferences/common/preferencesModels.ts | 26 ++++++++--- .../electron-browser/preferencesSearch.ts | 5 ++- 5 files changed, 63 insertions(+), 33 deletions(-) diff --git a/src/vs/workbench/parts/preferences/browser/preferencesEditor.ts b/src/vs/workbench/parts/preferences/browser/preferencesEditor.ts index 88c601b8200..d24e70fcd8e 100644 --- a/src/vs/workbench/parts/preferences/browser/preferencesEditor.ts +++ b/src/vs/workbench/parts/preferences/browser/preferencesEditor.ts @@ -294,20 +294,24 @@ export class PreferencesEditor extends BaseEditor { } } - private reportFilteringUsed(filter: string, counts: IStringDictionary, metadata?: IFilterMetadata): void { + private reportFilteringUsed(filter: string, counts: IStringDictionary, metadata?: IStringDictionary): void { if (filter && filter !== this._lastReportedFilter) { + let durations: any; + if (metadata) { + durations = Object.create(null); + Object.keys(metadata).forEach(key => durations[key] = metadata[key].duration); + } + let data = { filter, - duration: metadata ? metadata.duration : undefined, - context: metadata ? metadata.context : undefined, + durations, counts }; /* __GDPR__ "defaultSettings.filter" : { "filter": { "classification": "SystemMetaData", "purpose": "FeatureInsight" }, - "duration" : { "classification": "SystemMetaData", "purpose": "FeatureInsight" }, - "context" : { "classification": "SystemMetaData", "purpose": "FeatureInsight" }, + "durations" : { "classification": "SystemMetaData", "purpose": "FeatureInsight" }, "counts" : { "classification": "SystemMetaData", "purpose": "FeatureInsight" } } */ @@ -352,7 +356,7 @@ class SettingsNavigator implements INavigator { interface IFilterOrSearchResult { defaultSettingsGroupCounts: IStringDictionary; - metadata: IFilterMetadata; + metadata: IStringDictionary; } class PreferencesRenderersController extends Disposable { diff --git a/src/vs/workbench/parts/preferences/browser/preferencesRenderers.ts b/src/vs/workbench/parts/preferences/browser/preferencesRenderers.ts index 24c071bd5ff..4a9efa1869d 100644 --- a/src/vs/workbench/parts/preferences/browser/preferencesRenderers.ts +++ b/src/vs/workbench/parts/preferences/browser/preferencesRenderers.ts @@ -113,7 +113,6 @@ export class UserSettingsRenderer extends Disposable implements IPreferencesRend if (this.filterResult) { data['query'] = this.filterResult.query; - data['duration'] = this.filterResult.metadata && this.filterResult.metadata.duration; data['index'] = source.index; data['groupId'] = source.groupId; data['editableSide'] = !!fromEditableSettings; @@ -123,9 +122,8 @@ export class UserSettingsRenderer extends Disposable implements IPreferencesRend "defaultSettingsActions.copySetting" : { "userConfigurationKeys" : { "classification": "SystemMetaData", "purpose": "FeatureInsight" }, "query" : { "classification": "SystemMetaData", "purpose": "FeatureInsight" }, - "duration" : { "classification": "SystemMetaData", "purpose": "FeatureInsight" }, - "groupId" : { "classification": "SystemMetaData", "purpose": "FeatureInsight" }, "index" : { "classification": "SystemMetaData", "purpose": "FeatureInsight" }, + "groupId" : { "classification": "SystemMetaData", "purpose": "FeatureInsight" }, "editableSide" : { "classification": "SystemMetaData", "purpose": "FeatureInsight" } } */ @@ -622,31 +620,35 @@ export class FeedbackWidgetRenderer extends Disposable { } const result = this._currentResult; - const actualResults = result.metadata.scoredResults; + const metadata = result.metadata['nlpResult']; // Feedback only on nlpResult set for now + const marketplaceExtensionsResults = result.metadata['newExtensionsResult'] && result.metadata['newExtensionsResult'].scoredResults; + const actualResults = metadata ? metadata.scoredResults : {}; const actualResultIds = Object.keys(actualResults); const feedbackQuery: any = {}; feedbackQuery['comment'] = FeedbackWidgetRenderer.DEFAULT_COMMENT_TEXT; feedbackQuery['queryString'] = result.query; - feedbackQuery['resultScores'] = {}; + feedbackQuery['resultScores'] = []; actualResultIds.forEach(settingId => { - const outputKey = actualResults[settingId].key; - feedbackQuery['resultScores'][outputKey] = 10; + feedbackQuery['resultScores'].push({ + packageID: actualResults[settingId].packageId, + key: actualResults[settingId].key, + score: 10 + }); }); feedbackQuery['alts'] = []; const contents = FeedbackWidgetRenderer.INSTRUCTION_TEXT + '\n' + JSON.stringify(feedbackQuery, undefined, ' ') + '\n\n' + - actualResultIds.map(name => { - return `// ${actualResults[name].key}: ${actualResults[name].score}`; - }).join('\n'); + this.getScoreText(actualResults) + '\n\n' + + this.getScoreText(marketplaceExtensionsResults) + '\n'; this.editorService.openEditor({ contents, language: 'jsonc' }, /*sideBySide=*/true).then(feedbackEditor => { const sendFeedbackWidget = this._register(this.instantiationService.createInstance(FloatingClickWidget, feedbackEditor.getControl(), 'Send feedback', null)); sendFeedbackWidget.render(); this._register(sendFeedbackWidget.onClick(() => { - this.sendFeedback(feedbackEditor.getControl() as ICodeEditor, result, result.metadata.scoredResults).then(() => { + this.sendFeedback(feedbackEditor.getControl() as ICodeEditor, result, metadata.scoredResults).then(() => { sendFeedbackWidget.dispose(); this.messageService.show(Severity.Info, 'Feedback sent successfully'); }, err => { @@ -656,6 +658,17 @@ export class FeedbackWidgetRenderer extends Disposable { }); } + private getScoreText(results?: IScoredResults): string { + if (!results) { + return ''; + } + + return Object.keys(results) + .map(name => { + return `// ${results[name].key}: ${results[name].score}`; + }).join('\n'); + } + private sendFeedback(feedbackEditor: ICodeEditor, result: IFilterResult, actualResults: IScoredResults): TPromise { const model = feedbackEditor.getModel(); const expectedQueryLines = model.getLinesContent() @@ -685,11 +698,9 @@ export class FeedbackWidgetRenderer extends Disposable { "settingsSearchResultFeedback" : { "query" : { "classification": "CustomContent", "purpose": "FeatureInsight" }, "userComment" : { "classification": "CustomerContent", "purpose": "FeatureInsight" }, - "actualResults" : { "classification": "SystemMetaData", "purpose": "FeatureInsight" }, "expectedResults" : { "classification": "SystemMetaData", "purpose": "FeatureInsight" }, - "url" : { "classification": "CustomerContent", "purpose": "FeatureInsight" }, + "actualResults" : { "classification": "SystemMetaData", "purpose": "FeatureInsight" }, "duration" : { "classification": "SystemMetaData", "purpose": "FeatureInsight" }, - "timestamp" : { "classification": "SystemMetaData", "purpose": "FeatureInsight" } } */ return this.telemetryService.publicLog('settingsSearchResultFeedback', { @@ -697,9 +708,7 @@ export class FeedbackWidgetRenderer extends Disposable { userComment, actualResults, expectedResults: expectedQuery.resultScores, - url: result.metadata.remoteUrl, - duration: result.metadata.duration, - timestamp: result.metadata.timestamp, + duration: result.metadata['nlpResult'].duration, buildNumber: this.environmentService.settingsSearchBuildId, alts, autoIngest diff --git a/src/vs/workbench/parts/preferences/common/preferences.ts b/src/vs/workbench/parts/preferences/common/preferences.ts index 5157b9cefb8..519887d8e01 100644 --- a/src/vs/workbench/parts/preferences/common/preferences.ts +++ b/src/vs/workbench/parts/preferences/common/preferences.ts @@ -16,6 +16,7 @@ import { IWorkspaceContextService } from 'vs/platform/workspace/common/workspace import { join } from 'vs/base/common/paths'; import { ConfigurationTarget } from 'vs/platform/configuration/common/configuration'; import Event from 'vs/base/common/event'; +import { IStringDictionary } from 'vs/base/common/collections'; export interface IWorkbenchSettingsConfiguration { workbench: { @@ -79,7 +80,7 @@ export interface IFilterResult { filteredGroups: ISettingsGroup[]; allGroups: ISettingsGroup[]; matches: IRange[]; - metadata?: IFilterMetadata; + metadata?: IStringDictionary; } export interface ISettingMatch { @@ -104,7 +105,8 @@ export interface IRemoteSetting { } export interface IFilterMetadata { - remoteUrl: string; + requestUrl: string; + requestBody: string; timestamp: number; duration: number; scoredResults: IScoredResults; diff --git a/src/vs/workbench/parts/preferences/common/preferencesModels.ts b/src/vs/workbench/parts/preferences/common/preferencesModels.ts index 95c7d255962..af64f644416 100644 --- a/src/vs/workbench/parts/preferences/common/preferencesModels.ts +++ b/src/vs/workbench/parts/preferences/common/preferencesModels.ts @@ -6,7 +6,7 @@ import * as nls from 'vs/nls'; import { assign } from 'vs/base/common/objects'; import * as map from 'vs/base/common/map'; -import { tail, flatten, first } from 'vs/base/common/arrays'; +import { tail, flatten } from 'vs/base/common/arrays'; import URI from 'vs/base/common/uri'; import { IReference, Disposable } from 'vs/base/common/lifecycle'; import Event, { Emitter } from 'vs/base/common/event'; @@ -15,12 +15,13 @@ import { visit, JSONVisitor } from 'vs/base/common/json'; import { ITextModel, IIdentifiedSingleEditOperation } from 'vs/editor/common/model'; import { EditorModel } from 'vs/workbench/common/editor'; import { IConfigurationNode, IConfigurationRegistry, Extensions, OVERRIDE_PROPERTY_PATTERN, IConfigurationPropertySchema, ConfigurationScope } from 'vs/platform/configuration/common/configurationRegistry'; -import { ISettingsEditorModel, IKeybindingsEditorModel, ISettingsGroup, ISetting, IFilterResult, IGroupFilter, ISettingMatcher, ISettingMatch, ISearchResultGroup } from 'vs/workbench/parts/preferences/common/preferences'; +import { ISettingsEditorModel, IKeybindingsEditorModel, ISettingsGroup, ISetting, IFilterResult, IGroupFilter, ISettingMatcher, ISettingMatch, ISearchResultGroup, IFilterMetadata } from 'vs/workbench/parts/preferences/common/preferences'; import { IKeybindingService } from 'vs/platform/keybinding/common/keybinding'; import { ITextEditorModel } from 'vs/editor/common/services/resolverService'; import { IRange, Range } from 'vs/editor/common/core/range'; import { ConfigurationTarget } from 'vs/platform/configuration/common/configuration'; import { Selection } from 'vs/editor/common/core/selection'; +import { IStringDictionary } from 'vs/base/common/collections'; export abstract class AbstractSettingsModel extends EditorModel { @@ -114,6 +115,19 @@ export abstract class AbstractSettingsModel extends EditorModel { }; } + protected collectMetadata(groups: ISearchResultGroup[]): IStringDictionary { + const metadata = Object.create(null); + let hasMetadata = false; + groups.forEach(g => { + if (g.result.metadata) { + metadata[g.id] = g.result.metadata; + hasMetadata = true; + } + }); + + return hasMetadata ? metadata : null; + } + protected get filterGroups(): ISettingsGroup[] { return this.settingsGroups; @@ -205,12 +219,12 @@ export class SettingsEditorModel extends AbstractSettingsModel implements ISetti }; } - const groupWithMetadata = first(resultGroups, group => !!group.result.metadata); + const metadata = this.collectMetadata(resultGroups); return { allGroups: this.settingsGroups, filteredGroups: filteredGroup ? [filteredGroup] : [], matches, - metadata: groupWithMetadata && groupWithMetadata.result.metadata + metadata }; } } @@ -648,13 +662,13 @@ export class DefaultSettingsEditorModel extends AbstractSettingsModel implements const startLine = tail(this.settingsGroups).range.endLineNumber + 2; const { settingsGroups: filteredGroups, matches } = this.writeResultGroups(nonEmptyResultGroups, startLine); - const groupWithMetadata = first(resultGroups, group => !!group.result.metadata); + const metadata = this.collectMetadata(resultGroups); return resultGroups.length ? { allGroups: this.settingsGroups, filteredGroups, matches, - metadata: groupWithMetadata && groupWithMetadata.result.metadata + metadata } : null; } diff --git a/src/vs/workbench/parts/preferences/electron-browser/preferencesSearch.ts b/src/vs/workbench/parts/preferences/electron-browser/preferencesSearch.ts index 3366eafe38d..ac34222b586 100644 --- a/src/vs/workbench/parts/preferences/electron-browser/preferencesSearch.ts +++ b/src/vs/workbench/parts/preferences/electron-browser/preferencesSearch.ts @@ -243,7 +243,8 @@ class RemoteSearchProvider implements ISearchProvider { }); return { - remoteUrl: details.url, // telemetry for filter text? + requestUrl: details.url, + requestBody: details.body, duration, timestamp, scoredResults, @@ -337,7 +338,7 @@ class RemoteSearchProvider implements ISearchProvider { function getSettingKey(name: string, packageId?: string): string { return packageId ? - packageId + '_' + name : + packageId + '##' + name : name; } From 8eae654dd46d0a184353f8062d013279a73053a8 Mon Sep 17 00:00:00 2001 From: Rob Lourens Date: Tue, 23 Jan 2018 20:41:05 -0800 Subject: [PATCH 45/63] Fix code.bat builtInExtensions fallback --- scripts/code.bat | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/scripts/code.bat b/scripts/code.bat index 5a98f590c01..4917d3b9a8b 100644 --- a/scripts/code.bat +++ b/scripts/code.bat @@ -18,7 +18,8 @@ node build\lib\electron.js if %errorlevel% neq 0 node .\node_modules\gulp\bin\gulp.js electron :: Get built-in extensions -node build\lib\builtInExtensions.js || .\node_modules\.bin\gulp builtInExtensions +node build\lib\builtInExtensions.js +if %errorlevel% neq 0 node .\node_modules\gulp\bin\gulp.js builtInExtensions :: Build if not exist out node .\node_modules\gulp\bin\gulp.js compile From 6bfe9bbe8a910b8c57bb0c0a6e0557d46ebd64ba Mon Sep 17 00:00:00 2001 From: Rob Lourens Date: Tue, 23 Jan 2018 21:57:06 -0800 Subject: [PATCH 46/63] Bump distro --- package.json | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/package.json b/package.json index 38c1c1a8342..5079c68d462 100644 --- a/package.json +++ b/package.json @@ -1,7 +1,7 @@ { "name": "code-oss-dev", "version": "1.20.0", - "distro": "e14a5a3afaae557ff651b344462ed39e776435a2", + "distro": "d41bd1b8193403ffe9849b49fc37153e3d5b5a49", "author": { "name": "Microsoft Corporation" }, From 1b54bafade7ea995ed1340fbaf88f3cd26f9782f Mon Sep 17 00:00:00 2001 From: Sandeep Somavarapu Date: Wed, 24 Jan 2018 08:25:23 +0100 Subject: [PATCH 47/63] :lipstick: --- .../sharedProcess/sharedProcessMain.ts | 4 ++-- src/vs/platform/log/common/log.ts | 22 +++---------------- src/vs/platform/log/common/logIpc.ts | 17 ++++++++++++-- src/vs/workbench/electron-browser/main.ts | 4 ++-- 4 files changed, 22 insertions(+), 25 deletions(-) diff --git a/src/vs/code/electron-browser/sharedProcess/sharedProcessMain.ts b/src/vs/code/electron-browser/sharedProcess/sharedProcessMain.ts index 335f01d17fe..f13a6d2c95f 100644 --- a/src/vs/code/electron-browser/sharedProcess/sharedProcessMain.ts +++ b/src/vs/code/electron-browser/sharedProcess/sharedProcessMain.ts @@ -38,8 +38,8 @@ import { ipcRenderer } from 'electron'; import { IDisposable, dispose } from 'vs/base/common/lifecycle'; import { createSharedProcessContributions } from 'vs/code/electron-browser/sharedProcess/contrib/contributions'; import { createSpdLogService } from 'vs/platform/log/node/spdlogService'; -import { ILogService, FollowerLogService, LogLevel } from 'vs/platform/log/common/log'; -import { LogLevelSetterChannelClient } from 'vs/platform/log/common/logIpc'; +import { ILogService, LogLevel } from 'vs/platform/log/common/log'; +import { LogLevelSetterChannelClient, FollowerLogService } from 'vs/platform/log/common/logIpc'; export interface ISharedProcessConfiguration { readonly machineId: string; diff --git a/src/vs/platform/log/common/log.ts b/src/vs/platform/log/common/log.ts index 5617bff5eb3..09d85742184 100644 --- a/src/vs/platform/log/common/log.ts +++ b/src/vs/platform/log/common/log.ts @@ -23,15 +23,12 @@ export enum LogLevel { Off } -export interface ILogLevelSetter { - onDidChangeLogLevel: Event; - setLevel(level: LogLevel): void; -} - -export interface ILogService extends ILogLevelSetter, IDisposable { +export interface ILogService extends IDisposable { _serviceBrand: any; + onDidChangeLogLevel: Event; getLevel(): LogLevel; + setLevel(level: LogLevel): void; trace(message: string, ...args: any[]): void; debug(message: string, ...args: any[]): void; info(message: string, ...args: any[]): void; @@ -290,19 +287,6 @@ export class DelegatedLogService extends Disposable implements ILogService { } } -export class FollowerLogService extends DelegatedLogService implements ILogService { - _serviceBrand: any; - - constructor(private master: ILogLevelSetter, logService: ILogService) { - super(logService); - this._register(master.onDidChangeLogLevel(level => logService.setLevel(level))); - } - - setLevel(level: LogLevel): void { - this.master.setLevel(level); - } -} - export class NullLogService implements ILogService { _serviceBrand: any; readonly onDidChangeLogLevel: Event = new Emitter().event; diff --git a/src/vs/platform/log/common/logIpc.ts b/src/vs/platform/log/common/logIpc.ts index e8c10a8416d..b792dc83329 100644 --- a/src/vs/platform/log/common/logIpc.ts +++ b/src/vs/platform/log/common/logIpc.ts @@ -5,7 +5,7 @@ import { IChannel, eventToCall, eventFromCall } from 'vs/base/parts/ipc/common/ipc'; import { TPromise } from 'vs/base/common/winjs.base'; -import { LogLevel, ILogService, ILogLevelSetter } from 'vs/platform/log/common/log'; +import { LogLevel, ILogService, DelegatedLogService } from 'vs/platform/log/common/log'; import Event, { buffer } from 'vs/base/common/event'; export interface ILogLevelSetterChannel extends IChannel { @@ -30,7 +30,7 @@ export class LogLevelSetterChannel implements ILogLevelSetterChannel { } } -export class LogLevelSetterChannelClient implements ILogLevelSetter { +export class LogLevelSetterChannelClient { constructor(private channel: ILogLevelSetterChannel) { } @@ -40,4 +40,17 @@ export class LogLevelSetterChannelClient implements ILogLevelSetter { setLevel(level: LogLevel): TPromise { return this.channel.call('setLevel', level); } +} + +export class FollowerLogService extends DelegatedLogService implements ILogService { + _serviceBrand: any; + + constructor(private master: LogLevelSetterChannelClient, logService: ILogService) { + super(logService); + this._register(master.onDidChangeLogLevel(level => logService.setLevel(level))); + } + + setLevel(level: LogLevel): void { + this.master.setLevel(level); + } } \ No newline at end of file diff --git a/src/vs/workbench/electron-browser/main.ts b/src/vs/workbench/electron-browser/main.ts index 50deed29769..6c93107c6cc 100644 --- a/src/vs/workbench/electron-browser/main.ts +++ b/src/vs/workbench/electron-browser/main.ts @@ -43,10 +43,10 @@ import { IWorkspacesService } from 'vs/platform/workspaces/common/workspaces'; import { createSpdLogService } from 'vs/platform/log/node/spdlogService'; import fs = require('fs'); -import { ConsoleLogService, MultiplexLogService, ILogService, FollowerLogService } from 'vs/platform/log/common/log'; +import { ConsoleLogService, MultiplexLogService, ILogService } from 'vs/platform/log/common/log'; import { IssueChannelClient } from 'vs/platform/issue/common/issueIpc'; import { IIssueService } from 'vs/platform/issue/common/issue'; -import { LogLevelSetterChannelClient } from 'vs/platform/log/common/logIpc'; +import { LogLevelSetterChannelClient, FollowerLogService } from 'vs/platform/log/common/logIpc'; gracefulFs.gracefulify(fs); // enable gracefulFs export function startup(configuration: IWindowConfiguration): TPromise { From 8c81274edbe0bfcbbd259c077a4d3b44fd00b6c5 Mon Sep 17 00:00:00 2001 From: Alex Dima Date: Wed, 24 Jan 2018 09:15:30 +0100 Subject: [PATCH 48/63] Fix color registration --- .../contrib/bracketMatching/bracketMatching.ts | 12 ++++-------- 1 file changed, 4 insertions(+), 8 deletions(-) diff --git a/src/vs/editor/contrib/bracketMatching/bracketMatching.ts b/src/vs/editor/contrib/bracketMatching/bracketMatching.ts index 0ce6d4667cf..5b602985086 100644 --- a/src/vs/editor/contrib/bracketMatching/bracketMatching.ts +++ b/src/vs/editor/contrib/bracketMatching/bracketMatching.ts @@ -20,14 +20,10 @@ import { registerThemingParticipant, themeColorFromId } from 'vs/platform/theme/ import { editorBracketMatchBackground, editorBracketMatchBorder } from 'vs/editor/common/view/editorColorRegistry'; import { ModelDecorationOptions } from 'vs/editor/common/model/textModel'; import { ICodeEditor } from 'vs/editor/browser/editorBrowser'; -import { registerColor, overviewRulerSelectionHighlightForeground } from 'vs/platform/theme/common/colorRegistry'; +import { registerColor } from 'vs/platform/theme/common/colorRegistry'; import { TrackedRangeStickiness, IModelDeltaDecoration, OverviewRulerLane } from 'vs/editor/common/model'; -export const editorWordHighlight = registerColor('editor.wordHighlightBackground', { dark: '#575757B8', light: '#57575740', hc: null }, nls.localize('wordHighlight', 'Background color of a symbol during read-access, like reading a variable.')); -export const editorWordHighlightStrong = registerColor('editor.wordHighlightStrongBackground', { dark: '#004972B8', light: '#0e639c40', hc: null }, nls.localize('wordHighlightStrong', 'Background color of a symbol during write-access, like writing to a variable.')); - -export const overviewRulerWordHighlightForeground = registerColor('editorOverviewRuler.wordHighlightForeground', { dark: '#A0A0A0', light: '#A0A0A0', hc: '#A0A0A0' }, nls.localize('overviewRulerWordHighlightForeground', 'Overview ruler marker color for symbol highlights.')); -export const overviewRulerWordHighlightStrongForeground = registerColor('editorOverviewRuler.wordHighlightStrongForeground', { dark: '#C0A0C0', light: '#C0A0C0', hc: '#C0A0C0' }, nls.localize('overviewRulerWordHighlightStrongForeground', 'Overview ruler marker color for write-access symbol highlights.')); +const overviewRulerBracketMatchForeground = registerColor('editorOverviewRuler.bracketMatchForeground', { dark: '#A0A0A0', light: '#A0A0A0', hc: '#A0A0A0' }, nls.localize('overviewRulerBracketMatchForeground', 'Overview ruler marker color for matching brackets.')); class JumpToBracketAction extends EditorAction { constructor() { @@ -223,8 +219,8 @@ export class BracketMatchingController extends Disposable implements editorCommo stickiness: TrackedRangeStickiness.NeverGrowsWhenTypingAtEdges, className: 'bracket-match', overviewRuler: { - color: themeColorFromId(overviewRulerSelectionHighlightForeground), - darkColor: themeColorFromId(overviewRulerSelectionHighlightForeground), + color: themeColorFromId(overviewRulerBracketMatchForeground), + darkColor: themeColorFromId(overviewRulerBracketMatchForeground), position: OverviewRulerLane.Center } }); From bddc5d69c4cf4f1df90231973bee2798a14427fc Mon Sep 17 00:00:00 2001 From: Martin Aeschlimann Date: Wed, 24 Jan 2018 09:19:14 +0100 Subject: [PATCH 49/63] add IJSONContributionRegistry.notifySchemaChanged --- .../configuration/common/configurationRegistry.ts | 2 +- .../jsonschemas/common/jsonContributionRegistry.ts | 11 +++++++++++ 2 files changed, 12 insertions(+), 1 deletion(-) diff --git a/src/vs/platform/configuration/common/configurationRegistry.ts b/src/vs/platform/configuration/common/configurationRegistry.ts index 033f4501766..518898d9d85 100644 --- a/src/vs/platform/configuration/common/configurationRegistry.ts +++ b/src/vs/platform/configuration/common/configurationRegistry.ts @@ -143,7 +143,7 @@ class ConfigurationRegistry implements IConfigurationRegistry { } public notifyConfigurationSchemaUpdated(configuration: IConfigurationNode) { - contributionRegistry.registerSchema(editorConfigurationSchemaId, this.editorConfigurationSchema); + contributionRegistry.notifySchemaChanged(editorConfigurationSchemaId); } public registerOverrideIdentifiers(overrideIdentifiers: string[]): void { diff --git a/src/vs/platform/jsonschemas/common/jsonContributionRegistry.ts b/src/vs/platform/jsonschemas/common/jsonContributionRegistry.ts index b9c921d4505..94fcaf68949 100644 --- a/src/vs/platform/jsonschemas/common/jsonContributionRegistry.ts +++ b/src/vs/platform/jsonschemas/common/jsonContributionRegistry.ts @@ -25,6 +25,13 @@ export interface IJSONContributionRegistry { */ registerSchema(uri: string, unresolvedSchemaContent: IJSONSchema): void; + + /** + * Notifies all listeneres that the content of the given schema has changed. + * @param uri The id of the schema + */ + notifySchemaChanged(uri: string): void; + /** * Get all schemas */ @@ -60,6 +67,10 @@ class JSONContributionRegistry implements IJSONContributionRegistry { this._onDidChangeSchema.fire(uri); } + public notifySchemaChanged(uri: string): void { + this._onDidChangeSchema.fire(uri); + } + public getSchemaContributions(): ISchemaContributions { return { schemas: this.schemasById, From b5e2d0a6bcbae4f71099715dc813239d21975eb5 Mon Sep 17 00:00:00 2001 From: Johannes Rieken Date: Wed, 24 Jan 2018 09:34:33 +0100 Subject: [PATCH 50/63] some more jsdoc, #10659 --- src/vs/vscode.d.ts | 11 ++++++++--- 1 file changed, 8 insertions(+), 3 deletions(-) diff --git a/src/vs/vscode.d.ts b/src/vs/vscode.d.ts index 7b80ea7ab95..60976131c02 100644 --- a/src/vs/vscode.d.ts +++ b/src/vs/vscode.d.ts @@ -2495,7 +2495,8 @@ declare module 'vscode' { } /** - * A workspace edit represents textual changes for many documents. + * A workspace edit represents textual and files changes for + * multiple resources and documents. */ export class WorkspaceEdit { @@ -2556,7 +2557,7 @@ declare module 'vscode' { /** * Get all text edits grouped by resource. * - * @return An array of `[Uri, TextEdit[]]`-tuples. + * @return A shallow copy of `[Uri, TextEdit[]]`-tuples. */ entries(): [Uri, TextEdit[]][]; @@ -2585,14 +2586,18 @@ declare module 'vscode' { /** * Get the resource edits for this workspace edit. * - * @returns A array of uri-tuples in which a rename-edit + * @returns A shallow copy of uri-tuples in which a rename-edit * is represented as `[from, to]`, a delete-operation as `[from, null]`, * and a create-operation as `[null, to]`; */ resourceEdits(): [Uri, Uri][]; /** + * Get all edits, textual changes and file changes. The order is the order + * in which edits have been added to this workspace edits. Textuals edits + * are grouped and the first textual edit for a resource matters. * + * @returns A shallow copy of all changes. */ allEntries(): ([Uri, TextEdit[]] | [Uri, Uri])[]; } From 1d106e5afe0cb08ed7fb8998aba673d0cd4282c4 Mon Sep 17 00:00:00 2001 From: Joao Moreno Date: Wed, 24 Jan 2018 09:38:09 +0100 Subject: [PATCH 51/63] rename gulp tasks --- build/gulpfile.vscode.js | 11 ++++------- scripts/code.bat | 2 +- scripts/code.sh | 2 +- 3 files changed, 6 insertions(+), 9 deletions(-) diff --git a/build/gulpfile.vscode.js b/build/gulpfile.vscode.js index b0ff0a2a732..9ac087e38d4 100644 --- a/build/gulpfile.vscode.js +++ b/build/gulpfile.vscode.js @@ -585,18 +585,15 @@ gulp.task('generate-vscode-configuration', () => { }); //#region Built-In Extensions -gulp.task('clean-builtInExtensions', util.rimraf('.build/builtInExtensions')); - -gulp.task('builtInExtensions', ['clean-builtInExtensions'], function() { +gulp.task('clean-builtin-extensions', util.rimraf('.build/builtInExtensions')); +gulp.task('download-builtin-extensions', ['clean-builtin-extensions'], function () { const marketplaceExtensions = es.merge(...builtInExtensions.map(extension => { return ext.fromMarketplace(extension.name, extension.version) .pipe(rename(p => p.dirname = `${extension.name}/${p.dirname}`)); })); - return ( - marketplaceExtensions + return marketplaceExtensions .pipe(util.setExecutableBit(['**/*.sh'])) - .pipe(vfs.dest('.build/builtInExtensions')) - ); + .pipe(vfs.dest('.build/builtInExtensions')); }); //#endregion diff --git a/scripts/code.bat b/scripts/code.bat index 4917d3b9a8b..b23ee223546 100644 --- a/scripts/code.bat +++ b/scripts/code.bat @@ -19,7 +19,7 @@ if %errorlevel% neq 0 node .\node_modules\gulp\bin\gulp.js electron :: Get built-in extensions node build\lib\builtInExtensions.js -if %errorlevel% neq 0 node .\node_modules\gulp\bin\gulp.js builtInExtensions +if %errorlevel% neq 0 node .\node_modules\gulp\bin\gulp.js download-builtin-extensions :: Build if not exist out node .\node_modules\gulp\bin\gulp.js compile diff --git a/scripts/code.sh b/scripts/code.sh index 089d380c1b5..7f52ded6fe5 100755 --- a/scripts/code.sh +++ b/scripts/code.sh @@ -25,7 +25,7 @@ function code() { node build/lib/electron.js || ./node_modules/.bin/gulp electron # Get built-in extensions - node build/lib/builtInExtensions.js || ./node_modules/.bin/gulp builtInExtensions + node build/lib/builtInExtensions.js || ./node_modules/.bin/gulp download-builtin-extensions # Build test -d out || ./node_modules/.bin/gulp compile From 4fde7a37737b5ff2735568116f8ffa59084da509 Mon Sep 17 00:00:00 2001 From: Johannes Rieken Date: Wed, 24 Jan 2018 09:50:57 +0100 Subject: [PATCH 52/63] add main-side logging for save participants, #42013 --- .../api/electron-browser/mainThreadSaveParticipant.ts | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-) diff --git a/src/vs/workbench/api/electron-browser/mainThreadSaveParticipant.ts b/src/vs/workbench/api/electron-browser/mainThreadSaveParticipant.ts index ad20179ae9b..8bd469c9f82 100644 --- a/src/vs/workbench/api/electron-browser/mainThreadSaveParticipant.ts +++ b/src/vs/workbench/api/electron-browser/mainThreadSaveParticipant.ts @@ -27,6 +27,7 @@ import { ICodeEditor } from 'vs/editor/browser/editorBrowser'; import { IProgressService2, ProgressLocation } from 'vs/platform/progress/common/progress'; import { localize } from 'vs/nls'; import { isFalsyOrEmpty } from 'vs/base/common/arrays'; +import { ILogService } from 'vs/platform/log/common/log'; export interface ISaveParticipantParticipant extends ISaveParticipant { // progressMessage: string; @@ -279,8 +280,9 @@ export class SaveParticipant implements ISaveParticipant { constructor( extHostContext: IExtHostContext, + @IInstantiationService instantiationService: IInstantiationService, @IProgressService2 private _progressService: IProgressService2, - @IInstantiationService instantiationService: IInstantiationService + @ILogService private _logService: ILogService ) { this._saveParticipants = [ instantiationService.createInstance(TrimWhitespaceParticipant), @@ -303,7 +305,7 @@ export class SaveParticipant implements ISaveParticipant { const promiseFactory = this._saveParticipants.map(p => () => { return Promise.resolve(p.participate(model, env)); }); - return sequence(promiseFactory).then(() => { }); + return sequence(promiseFactory).then(() => { }, err => this._logService.error(err)); }); } } From acf50ea95a837828b4f0569bdc9fa5cff6f04fc0 Mon Sep 17 00:00:00 2001 From: Johannes Rieken Date: Wed, 24 Jan 2018 09:54:15 +0100 Subject: [PATCH 53/63] Revert "Revert "add 'configuration' (read uri/path) of workspace config file, #41408"" This reverts commit 1cacde34962c0c03cfa2de5eb72b3dbbc772e992. --- src/vs/platform/workspace/common/workspace.ts | 2 +- src/vs/workbench/api/node/extHost.protocol.ts | 1 + src/vs/workbench/api/node/extHostExtensionService.ts | 2 ++ 3 files changed, 4 insertions(+), 1 deletion(-) diff --git a/src/vs/platform/workspace/common/workspace.ts b/src/vs/platform/workspace/common/workspace.ts index af594644bae..1493935a013 100644 --- a/src/vs/platform/workspace/common/workspace.ts +++ b/src/vs/platform/workspace/common/workspace.ts @@ -198,7 +198,7 @@ export class Workspace implements IWorkspace { } public toJSON(): IWorkspace { - return { id: this.id, folders: this.folders, name: this.name }; + return { id: this.id, folders: this.folders, name: this.name, configuration: this.configuration }; } } diff --git a/src/vs/workbench/api/node/extHost.protocol.ts b/src/vs/workbench/api/node/extHost.protocol.ts index 332a2ee8940..1380aed2b40 100644 --- a/src/vs/workbench/api/node/extHost.protocol.ts +++ b/src/vs/workbench/api/node/extHost.protocol.ts @@ -72,6 +72,7 @@ export interface IWorkspaceData { id: string; name: string; folders: { uri: UriComponents, name: string, index: number }[]; + configuration: UriComponents; } export interface IInitData { diff --git a/src/vs/workbench/api/node/extHostExtensionService.ts b/src/vs/workbench/api/node/extHostExtensionService.ts index 2ea4f37ba86..b80f02c986f 100644 --- a/src/vs/workbench/api/node/extHostExtensionService.ts +++ b/src/vs/workbench/api/node/extHostExtensionService.ts @@ -22,6 +22,7 @@ import { Barrier } from 'vs/base/common/async'; import { ILogService } from 'vs/platform/log/common/log'; import { IEnvironmentService } from 'vs/platform/environment/common/environment'; import { ExtHostLogService } from 'vs/workbench/api/node/extHostLogService'; +import URI from 'vs/base/common/uri'; class ExtensionMemento implements IExtensionMemento { @@ -108,6 +109,7 @@ class ExtensionStoragePath { join(storagePath, 'meta.json'), JSON.stringify({ id: this._workspace.id, + configuration: URI.revive(this._workspace.configuration).toString(), name: this._workspace.name }, undefined, 2) ); From 3dd2035b13b3395f55afd5070ba875bcc230e464 Mon Sep 17 00:00:00 2001 From: Johannes Rieken Date: Wed, 24 Jan 2018 09:55:50 +0100 Subject: [PATCH 54/63] another try, #41408 --- src/vs/workbench/api/node/extHost.protocol.ts | 2 +- src/vs/workbench/api/node/extHostExtensionService.ts | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/src/vs/workbench/api/node/extHost.protocol.ts b/src/vs/workbench/api/node/extHost.protocol.ts index 1380aed2b40..84db14dbf9d 100644 --- a/src/vs/workbench/api/node/extHost.protocol.ts +++ b/src/vs/workbench/api/node/extHost.protocol.ts @@ -72,7 +72,7 @@ export interface IWorkspaceData { id: string; name: string; folders: { uri: UriComponents, name: string, index: number }[]; - configuration: UriComponents; + configuration?: UriComponents; } export interface IInitData { diff --git a/src/vs/workbench/api/node/extHostExtensionService.ts b/src/vs/workbench/api/node/extHostExtensionService.ts index b80f02c986f..c3972702415 100644 --- a/src/vs/workbench/api/node/extHostExtensionService.ts +++ b/src/vs/workbench/api/node/extHostExtensionService.ts @@ -109,7 +109,7 @@ class ExtensionStoragePath { join(storagePath, 'meta.json'), JSON.stringify({ id: this._workspace.id, - configuration: URI.revive(this._workspace.configuration).toString(), + configuration: this._workspace.configuration && URI.revive(this._workspace.configuration).toString(), name: this._workspace.name }, undefined, 2) ); From 2d01d1c4b1bce99babd2a7638d00696ed65aa385 Mon Sep 17 00:00:00 2001 From: Benjamin Pasero Date: Wed, 24 Jan 2018 09:59:25 +0100 Subject: [PATCH 55/63] fix #41987 --- src/vs/base/common/resources.ts | 7 ++++++- src/vs/base/test/common/resources.test.ts | 12 +++++++++++- .../browser/parts/quickopen/quickOpenController.ts | 13 +------------ 3 files changed, 18 insertions(+), 14 deletions(-) diff --git a/src/vs/base/common/resources.ts b/src/vs/base/common/resources.ts index 3012d4a5b15..bbc5c6ca223 100644 --- a/src/vs/base/common/resources.ts +++ b/src/vs/base/common/resources.ts @@ -38,8 +38,13 @@ export function isEqual(first: uri, second: uri, ignoreCase?: boolean): boolean } export function dirname(resource: uri): uri { + const dirname = paths.dirname(resource.path); + if (resource.authority && dirname && !paths.isAbsolute(dirname)) { + return null; // If a URI contains an authority component, then the path component must either be empty or begin with a slash ("/") character + } + return resource.with({ - path: paths.dirname(resource.path) + path: dirname }); } diff --git a/src/vs/base/test/common/resources.test.ts b/src/vs/base/test/common/resources.test.ts index f9275777a53..c0940975c3c 100644 --- a/src/vs/base/test/common/resources.test.ts +++ b/src/vs/base/test/common/resources.test.ts @@ -6,7 +6,7 @@ import * as assert from 'assert'; import URI from 'vs/base/common/uri'; -import { distinctParents } from 'vs/base/common/resources'; +import { distinctParents, dirname } from 'vs/base/common/resources'; suite('Resources', () => { @@ -40,4 +40,14 @@ suite('Resources', () => { assert.equal(distinct[1].toString(), resources[3].toString()); assert.equal(distinct[2].toString(), resources[4].toString()); }); + + test('dirname', (done) => { + const f = URI.file('/some/file/test.txt'); + const d = dirname(f); + assert.equal(d.fsPath, '/some/file'); + + // does not explode (https://github.com/Microsoft/vscode/issues/41987) + URI.from({ scheme: 'file', authority: '/users/someone/portal.h' }); + done(); + }); }); \ No newline at end of file diff --git a/src/vs/workbench/browser/parts/quickopen/quickOpenController.ts b/src/vs/workbench/browser/parts/quickopen/quickOpenController.ts index 1da92a9404f..935b7d8bed5 100644 --- a/src/vs/workbench/browser/parts/quickopen/quickOpenController.ts +++ b/src/vs/workbench/browser/parts/quickopen/quickOpenController.ts @@ -55,7 +55,6 @@ import { FileKind, IFileService } from 'vs/platform/files/common/files'; import { scoreItem, ScorerCache, compareItemsByScore, prepareQuery } from 'vs/base/parts/quickopen/common/quickOpenScorer'; import { getBaseLabel } from 'vs/base/common/labels'; import { WorkbenchTree } from 'vs/platform/list/browser/listService'; -import { dirname } from 'vs/base/common/paths'; const HELP_PREFIX = '?'; @@ -1260,7 +1259,7 @@ export class EditorHistoryEntry extends EditorQuickOpenEntry { const resourceInput = input as IResourceInput; this.resource = resourceInput.resource; this.label = getBaseLabel(resourceInput.resource); - this.description = labels.getPathLabel(this.safeDirname(this.resource), contextService, environmentService); + this.description = labels.getPathLabel(resources.dirname(this.resource), contextService, environmentService); this.dirty = this.resource && this.textFileService.isDirty(this.resource); if (this.dirty && this.textFileService.getAutoSaveMode() === AutoSaveMode.AFTER_SHORT_DELAY) { @@ -1269,16 +1268,6 @@ export class EditorHistoryEntry extends EditorQuickOpenEntry { } } - private safeDirname(resource: URI): string | URI { - try { - return resources.dirname(resource); // workaround for https://github.com/Microsoft/vscode/issues/41987 - } catch (error) { - console.warn(`Unable to resolve to parent resource: ${resource.toString()}`, resource, error); - - return dirname(resource.fsPath); - } - } - public getIcon(): string { return this.dirty ? 'dirty' : ''; } From d43d978b6334294b3ab893d5b1a0c7cea0036cb2 Mon Sep 17 00:00:00 2001 From: Sandeep Somavarapu Date: Wed, 24 Jan 2018 09:53:24 +0100 Subject: [PATCH 56/63] :lipstick: --- src/vs/platform/log/common/log.ts | 5 +---- 1 file changed, 1 insertion(+), 4 deletions(-) diff --git a/src/vs/platform/log/common/log.ts b/src/vs/platform/log/common/log.ts index 09d85742184..97418ed6f9a 100644 --- a/src/vs/platform/log/common/log.ts +++ b/src/vs/platform/log/common/log.ts @@ -244,6 +244,7 @@ export class DelegatedLogService extends Disposable implements ILogService { constructor(private logService: ILogService) { super(); + this._register(logService); } get onDidChangeLogLevel(): Event { @@ -281,10 +282,6 @@ export class DelegatedLogService extends Disposable implements ILogService { critical(message: string | Error, ...args: any[]): void { this.logService.critical(message, ...args); } - - dispose(): void { - this.logService.dispose(); - } } export class NullLogService implements ILogService { From d14d66d1e2dde65efe972c3092e322dc2e9c546b Mon Sep 17 00:00:00 2001 From: Sandeep Somavarapu Date: Wed, 24 Jan 2018 10:13:50 +0100 Subject: [PATCH 57/63] Show progress while searching for settings --- .../parts/preferences/browser/preferencesEditor.ts | 8 +++++--- 1 file changed, 5 insertions(+), 3 deletions(-) diff --git a/src/vs/workbench/parts/preferences/browser/preferencesEditor.ts b/src/vs/workbench/parts/preferences/browser/preferencesEditor.ts index d24e70fcd8e..5f6d1157f43 100644 --- a/src/vs/workbench/parts/preferences/browser/preferencesEditor.ts +++ b/src/vs/workbench/parts/preferences/browser/preferencesEditor.ts @@ -58,6 +58,7 @@ import { ConfigurationTarget } from 'vs/platform/configuration/common/configurat import { IHashService } from 'vs/workbench/services/hash/common/hashService'; import { ConfigurationScope } from 'vs/platform/configuration/common/configurationRegistry'; import { IStringDictionary } from 'vs/base/common/collections'; +import { IProgressService } from 'vs/platform/progress/common/progress'; export class PreferencesEditorInput extends SideBySideEditorInput { public static ID: string = 'workbench.editorinputs.preferencesEditorInput'; @@ -123,7 +124,8 @@ export class PreferencesEditor extends BaseEditor { @IWorkbenchEditorService private editorService: IWorkbenchEditorService, @IContextKeyService private contextKeyService: IContextKeyService, @IInstantiationService private instantiationService: IInstantiationService, - @IThemeService themeService: IThemeService + @IThemeService themeService: IThemeService, + @IProgressService private progressService: IProgressService ) { super(PreferencesEditor.ID, telemetryService, themeService); this.defaultSettingsEditorContextKey = CONTEXT_SETTINGS_EDITOR.bindTo(this.contextKeyService); @@ -240,10 +242,10 @@ export class PreferencesEditor extends BaseEditor { private onInputChanged(): void { const query = this.searchWidget.getValue().trim(); this.delayedFilterLogging.cancel(); - TPromise.join([ + this.progressService.showWhile(TPromise.join([ this.preferencesRenderers.localFilterPreferences(query), this.triggerThrottledSearch(query) - ]).then(() => { + ]), 250).then(() => { const result = this.preferencesRenderers.lastFilterResult; if (result) { this.delayedFilterLogging.trigger(() => this.reportFilteringUsed( From 93f3fc711b0a3afb80bfcb639e85ed2f1f858f9e Mon Sep 17 00:00:00 2001 From: Benjamin Pasero Date: Wed, 24 Jan 2018 11:18:44 +0100 Subject: [PATCH 58/63] avoid loading entire backup content for hot exit fixes #41986 --- src/vs/editor/common/model/textModel.ts | 6 +++- .../parts/editor/editorAreaDropHandler.ts | 18 ++++++++-- .../common/editor/untitledEditorModel.ts | 26 +++++++++------ .../services/backup/common/backup.ts | 9 +++-- .../services/backup/node/backupFileService.ts | 33 ++++++++++++++----- .../test/node/backupFileService.test.ts | 31 ++++++++++++++--- .../textfile/common/textFileEditorModel.ts | 10 +++--- .../workbench/test/workbenchTestServices.ts | 4 +++ 8 files changed, 98 insertions(+), 39 deletions(-) diff --git a/src/vs/editor/common/model/textModel.ts b/src/vs/editor/common/model/textModel.ts index 5a05edb5ccc..d64c382f47e 100644 --- a/src/vs/editor/common/model/textModel.ts +++ b/src/vs/editor/common/model/textModel.ts @@ -57,12 +57,16 @@ export function createTextBufferFactory(text: string): model.ITextBufferFactory return builder.finish(); } -export function createTextBufferFactoryFromStream(stream: IStringStream): TPromise { +export function createTextBufferFactoryFromStream(stream: IStringStream, filter?: (chunk: string) => string): TPromise { return new TPromise((c, e, p) => { let done = false; let builder = createTextBufferBuilder(); stream.on('data', (chunk) => { + if (filter) { + chunk = filter(chunk); + } + builder.acceptChunk(chunk); }); diff --git a/src/vs/workbench/browser/parts/editor/editorAreaDropHandler.ts b/src/vs/workbench/browser/parts/editor/editorAreaDropHandler.ts index 587ceeb9128..17920141664 100644 --- a/src/vs/workbench/browser/parts/editor/editorAreaDropHandler.ts +++ b/src/vs/workbench/browser/parts/editor/editorAreaDropHandler.ts @@ -12,7 +12,7 @@ import { IFileService } from 'vs/platform/files/common/files'; import { IWindowsService, IWindowService } from 'vs/platform/windows/common/windows'; import URI from 'vs/base/common/uri'; import { ITextFileService } from 'vs/workbench/services/textfile/common/textfiles'; -import { BACKUP_FILE_RESOLVE_OPTIONS, IBackupFileService } from 'vs/workbench/services/backup/common/backup'; +import { IBackupFileService } from 'vs/workbench/services/backup/common/backup'; import { IEditorGroupService } from 'vs/workbench/services/group/common/groupService'; import { TPromise } from 'vs/base/common/winjs.base'; import { Schemas } from 'vs/base/common/network'; @@ -20,6 +20,8 @@ import { IUntitledEditorService } from 'vs/workbench/services/untitled/common/un import { IWorkbenchEditorService } from 'vs/workbench/services/editor/common/editorService'; import { Position } from 'vs/platform/editor/common/editor'; import { onUnexpectedError } from 'vs/base/common/errors'; +import { DefaultEndOfLine } from 'vs/editor/common/model'; +import { IConfigurationService } from 'vs/platform/configuration/common/configuration'; /** * Shared function across some editor components to handle drag & drop of external resources. E.g. of folders and workspace files @@ -37,6 +39,7 @@ export class EditorAreaDropHandler { @IEditorGroupService private groupService: IEditorGroupService, @IUntitledEditorService private untitledEditorService: IUntitledEditorService, @IWorkbenchEditorService private editorService: IWorkbenchEditorService, + @IConfigurationService private configurationService: IConfigurationService ) { } @@ -107,13 +110,22 @@ export class EditorAreaDropHandler { } // Resolve the contents of the dropped dirty resource from source - return this.textFileService.resolveTextContent(droppedDirtyEditor.backupResource, BACKUP_FILE_RESOLVE_OPTIONS).then(content => { + return this.backupFileService.resolveBackupContent(droppedDirtyEditor.backupResource).then(content => { // Set the contents of to the resource to the target - return this.backupFileService.backupResource(droppedDirtyEditor.resource, this.backupFileService.parseBackupContent(content.value)); + return this.backupFileService.backupResource(droppedDirtyEditor.resource, content.create(this.getDefaultEOL()).createSnapshot(true)); }).then(() => false, () => false /* ignore any error */); } + private getDefaultEOL(): DefaultEndOfLine { + const eol = this.configurationService.getValue('files.eol'); + if (eol === '\r\n') { + return DefaultEndOfLine.CRLF; + } + + return DefaultEndOfLine.LF; + } + private handleWorkspaceFileDrop(resources: (IDraggedResource | IDraggedEditor)[]): TPromise { const externalResources = resources.filter(d => d.isExternal).map(d => d.resource); diff --git a/src/vs/workbench/common/editor/untitledEditorModel.ts b/src/vs/workbench/common/editor/untitledEditorModel.ts index c7dcee066bd..ee33d7720af 100644 --- a/src/vs/workbench/common/editor/untitledEditorModel.ts +++ b/src/vs/workbench/common/editor/untitledEditorModel.ts @@ -16,9 +16,10 @@ import { IModelService } from 'vs/editor/common/services/modelService'; import { IMode } from 'vs/editor/common/modes'; import Event, { Emitter } from 'vs/base/common/event'; import { RunOnceScheduler } from 'vs/base/common/async'; -import { IBackupFileService, BACKUP_FILE_RESOLVE_OPTIONS } from 'vs/workbench/services/backup/common/backup'; -import { ITextFileService } from 'vs/workbench/services/textfile/common/textfiles'; +import { IBackupFileService } from 'vs/workbench/services/backup/common/backup'; import { ITextResourceConfigurationService } from 'vs/editor/common/services/resourceConfiguration'; +import { ITextBufferFactory } from 'vs/editor/common/model'; +import { createTextBufferFactory } from 'vs/editor/common/model/textModel'; export class UntitledEditorModel extends BaseTextEditorModel implements IEncodingSupport { @@ -46,7 +47,6 @@ export class UntitledEditorModel extends BaseTextEditorModel implements IEncodin @IModeService modeService: IModeService, @IModelService modelService: IModelService, @IBackupFileService private backupFileService: IBackupFileService, - @ITextFileService private textFileService: ITextFileService, @ITextResourceConfigurationService private configurationService: ITextResourceConfigurationService ) { super(modelService, modeService); @@ -163,18 +163,24 @@ export class UntitledEditorModel extends BaseTextEditorModel implements IEncodin // Check for backups first return this.backupFileService.loadBackupResource(this.resource).then(backupResource => { if (backupResource) { - return this.textFileService.resolveTextContent(backupResource, BACKUP_FILE_RESOLVE_OPTIONS).then(rawTextContent => { - return this.backupFileService.parseBackupContent(rawTextContent.value); - }); + return this.backupFileService.resolveBackupContent(backupResource); } return null; - }).then(backupContent => { + }).then(backupTextBufferFactory => { + const hasBackup = !!backupTextBufferFactory; // untitled associated to file path are dirty right away as well as untitled with content - this.setDirty(this.hasAssociatedFilePath || !!backupContent); + this.setDirty(this.hasAssociatedFilePath || hasBackup); - return this.doLoad(backupContent || this.initialValue || '').then(model => { + let untitledContents: ITextBufferFactory; + if (backupTextBufferFactory) { + untitledContents = backupTextBufferFactory; + } else { + untitledContents = createTextBufferFactory(this.initialValue || ''); + } + + return this.doLoad(untitledContents).then(model => { // Encoding this.configuredEncoding = this.configurationService.getValue(this.resource, 'files.encoding'); @@ -189,7 +195,7 @@ export class UntitledEditorModel extends BaseTextEditorModel implements IEncodin }); } - private doLoad(content: string): TPromise { + private doLoad(content: ITextBufferFactory): TPromise { // Create text editor model if not yet done if (!this.textEditorModel) { diff --git a/src/vs/workbench/services/backup/common/backup.ts b/src/vs/workbench/services/backup/common/backup.ts index 0b4d35f5d0c..d398e7bdde8 100644 --- a/src/vs/workbench/services/backup/common/backup.ts +++ b/src/vs/workbench/services/backup/common/backup.ts @@ -65,13 +65,12 @@ export interface IBackupFileService { getWorkspaceFileBackups(): TPromise; /** - * Parses backup raw text content into the content, removing the metadata that is also stored - * in the file. + * Resolves the backup for the given resource. * - * @param textBufferFactory The ITextBufferFactory from a backup resource. - * @return The backup file's backed up content. + * @param value The contents from a backup resource as stream. + * @return The backup file's backed up content as text buffer factory. */ - parseBackupContent(textBufferFactory: ITextBufferFactory): string; + resolveBackupContent(backup: Uri): TPromise; /** * Discards the backup associated with a resource if it exists.. diff --git a/src/vs/workbench/services/backup/node/backupFileService.ts b/src/vs/workbench/services/backup/node/backupFileService.ts index 18c4e2a7b50..c0873744d49 100644 --- a/src/vs/workbench/services/backup/node/backupFileService.ts +++ b/src/vs/workbench/services/backup/node/backupFileService.ts @@ -10,12 +10,12 @@ import * as crypto from 'crypto'; import * as pfs from 'vs/base/node/pfs'; import Uri from 'vs/base/common/uri'; import { ResourceQueue } from 'vs/base/common/async'; -import { IBackupFileService, BACKUP_FILE_UPDATE_OPTIONS } from 'vs/workbench/services/backup/common/backup'; +import { IBackupFileService, BACKUP_FILE_UPDATE_OPTIONS, BACKUP_FILE_RESOLVE_OPTIONS } from 'vs/workbench/services/backup/common/backup'; import { IFileService, ITextSnapshot, IFileStat } from 'vs/platform/files/common/files'; import { TPromise } from 'vs/base/common/winjs.base'; import { readToMatchingString } from 'vs/base/node/stream'; -import { Range } from 'vs/editor/common/core/range'; -import { DefaultEndOfLine, ITextBufferFactory, EndOfLinePreference } from 'vs/editor/common/model'; +import { ITextBufferFactory } from 'vs/editor/common/model'; +import { createTextBufferFactoryFromStream } from 'vs/editor/common/model/textModel'; export interface IBackupFilesModel { resolve(backupRoot: string): TPromise; @@ -245,12 +245,27 @@ export class BackupFileService implements IBackupFileService { }); } - public parseBackupContent(textBufferFactory: ITextBufferFactory): string { - // The first line of a backup text file is the file name - const textBuffer = textBufferFactory.create(DefaultEndOfLine.LF); - const lineCount = textBuffer.getLineCount(); - const range = new Range(2, 1, lineCount, textBuffer.getLineLength(lineCount) + 1); - return textBuffer.getValueInRange(range, EndOfLinePreference.TextDefined); + public resolveBackupContent(backup: Uri): TPromise { + return this.fileService.resolveStreamContent(backup, BACKUP_FILE_RESOLVE_OPTIONS).then(content => { + + // Add a filter method to filter out everything until the meta marker + let metaFound = false; + const metaPreambleFilter = (chunk: string) => { + if (!metaFound && chunk) { + const metaIndex = chunk.indexOf(BackupFileService.META_MARKER); + if (metaIndex === -1) { + return ''; // meta not yet found, return empty string + } + + metaFound = true; + return chunk.substr(metaIndex + 1); // meta found, return everything after + } + + return chunk; + }; + + return createTextBufferFactoryFromStream(content.value, metaPreambleFilter); + }); } public toBackupResource(resource: Uri): Uri { diff --git a/src/vs/workbench/services/backup/test/node/backupFileService.test.ts b/src/vs/workbench/services/backup/test/node/backupFileService.test.ts index ff58403e381..e59a370b922 100644 --- a/src/vs/workbench/services/backup/test/node/backupFileService.test.ts +++ b/src/vs/workbench/services/backup/test/node/backupFileService.test.ts @@ -16,10 +16,12 @@ import pfs = require('vs/base/node/pfs'); import Uri from 'vs/base/common/uri'; import { BackupFileService, BackupFilesModel } from 'vs/workbench/services/backup/node/backupFileService'; import { FileService } from 'vs/workbench/services/files/node/fileService'; -import { createTextBufferFactory, TextModel } from 'vs/editor/common/model/textModel'; +import { TextModel } from 'vs/editor/common/model/textModel'; import { TestContextService, TestTextResourceConfigurationService, getRandomTestPath, TestLifecycleService } from 'vs/workbench/test/workbenchTestServices'; import { Workspace, toWorkspaceFolders } from 'vs/platform/workspace/common/workspace'; import { TestConfigurationService } from 'vs/platform/configuration/test/common/testConfigurationService'; +import { DefaultEndOfLine } from 'vs/editor/common/model'; +import { snapshotToString } from 'vs/platform/files/common/files'; const parentDir = getRandomTestPath(os.tmpdir(), 'vsctests', 'backupfileservice'); const backupHome = path.join(parentDir, 'Backups'); @@ -268,10 +270,29 @@ suite('BackupFileService', () => { }); }); - test('parseBackupContent', () => { - test('should separate metadata from content', () => { - const textBufferFactory = createTextBufferFactory('metadata\ncontent'); - assert.equal(service.parseBackupContent(textBufferFactory), 'content'); + test('resolveBackupContent', () => { + test('should restore the original contents (untitled file)', () => { + const contents = 'test\nand more stuff'; + service.backupResource(untitledFile, contents).then(() => { + service.resolveBackupContent(service.toBackupResource(untitledFile)).then(factory => { + assert.equal(contents, snapshotToString(factory.create(platform.isWindows ? DefaultEndOfLine.CRLF : DefaultEndOfLine.LF).createSnapshot(true))); + }); + }); + }); + + test('should restore the original contents (text file)', () => { + const contents = [ + 'Lorem ipsum ', + 'dolor öäü sit amet ', + 'consectetur ', + 'adipiscing ßß elit', + ].join(''); + + service.backupResource(fooFile, contents).then(() => { + service.resolveBackupContent(service.toBackupResource(untitledFile)).then(factory => { + assert.equal(contents, snapshotToString(factory.create(platform.isWindows ? DefaultEndOfLine.CRLF : DefaultEndOfLine.LF).createSnapshot(true))); + }); + }); }); }); }); diff --git a/src/vs/workbench/services/textfile/common/textFileEditorModel.ts b/src/vs/workbench/services/textfile/common/textFileEditorModel.ts index 88197be4a82..887cb059464 100644 --- a/src/vs/workbench/services/textfile/common/textFileEditorModel.ts +++ b/src/vs/workbench/services/textfile/common/textFileEditorModel.ts @@ -22,7 +22,7 @@ import { IEnvironmentService } from 'vs/platform/environment/common/environment' import { ITextFileService, IAutoSaveConfiguration, ModelState, ITextFileEditorModel, ISaveOptions, ISaveErrorHandler, ISaveParticipant, StateChange, SaveReason, IRawTextContent } from 'vs/workbench/services/textfile/common/textfiles'; import { EncodingMode } from 'vs/workbench/common/editor'; import { BaseTextEditorModel } from 'vs/workbench/common/editor/textEditorModel'; -import { IBackupFileService, BACKUP_FILE_RESOLVE_OPTIONS } from 'vs/workbench/services/backup/common/backup'; +import { IBackupFileService } from 'vs/workbench/services/backup/common/backup'; import { IFileService, IFileStat, FileOperationError, FileOperationResult, IContent, CONTENT_CHANGE_EVENT_BUFFER_DELAY, FileChangesEvent, FileChangeType } from 'vs/platform/files/common/files'; import { IInstantiationService } from 'vs/platform/instantiation/common/instantiation'; import { IMessageService, Severity } from 'vs/platform/message/common/message'; @@ -444,7 +444,7 @@ export class TextFileEditorModel extends BaseTextEditorModel implements ITextFil diag('load() - created text editor model', this.resource, new Date()); this.createTextEditorModelPromise = this.doLoadBackup(backup).then(backupContent => { - const hasBackupContent = (typeof backupContent === 'string'); + const hasBackupContent = !!backupContent; return this.createTextEditorModel(hasBackupContent ? backupContent : value, resource).then(() => { this.createTextEditorModelPromise = null; @@ -488,14 +488,12 @@ export class TextFileEditorModel extends BaseTextEditorModel implements ITextFil this.toDispose.push(this.textEditorModel.onDidChangeContent(() => this.onModelContentChanged())); } - private doLoadBackup(backup: URI): TPromise { + private doLoadBackup(backup: URI): TPromise { if (!backup) { return TPromise.as(null); } - return this.textFileService.resolveTextContent(backup, BACKUP_FILE_RESOLVE_OPTIONS).then(backup => { - return this.backupFileService.parseBackupContent(backup.value); - }, error => null /* ignore errors */); + return this.backupFileService.resolveBackupContent(backup).then(backupContent => backupContent, error => null /* ignore errors */); } protected getOrCreateMode(modeService: IModeService, preferredModeIds: string, firstLineText?: string): TPromise { diff --git a/src/vs/workbench/test/workbenchTestServices.ts b/src/vs/workbench/test/workbenchTestServices.ts index e5db572cc91..d4d3fbd6c25 100644 --- a/src/vs/workbench/test/workbenchTestServices.ts +++ b/src/vs/workbench/test/workbenchTestServices.ts @@ -872,6 +872,10 @@ export class TestBackupFileService implements IBackupFileService { return textBuffer.getValueInRange(range, EndOfLinePreference.TextDefined); } + public resolveBackupContent(backup: URI): TPromise { + return TPromise.as(null); + } + public discardResourceBackup(resource: URI): TPromise { return TPromise.as(void 0); } From 45967cd09dae4431adc6202c88dea2538f5155c8 Mon Sep 17 00:00:00 2001 From: Benjamin Pasero Date: Wed, 24 Jan 2018 11:46:04 +0100 Subject: [PATCH 59/63] fix tests on windows --- src/vs/base/test/common/resources.test.ts | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/src/vs/base/test/common/resources.test.ts b/src/vs/base/test/common/resources.test.ts index c0940975c3c..4c0925bcf14 100644 --- a/src/vs/base/test/common/resources.test.ts +++ b/src/vs/base/test/common/resources.test.ts @@ -7,6 +7,7 @@ import * as assert from 'assert'; import URI from 'vs/base/common/uri'; import { distinctParents, dirname } from 'vs/base/common/resources'; +import { normalize } from 'vs/base/common/paths'; suite('Resources', () => { @@ -44,7 +45,7 @@ suite('Resources', () => { test('dirname', (done) => { const f = URI.file('/some/file/test.txt'); const d = dirname(f); - assert.equal(d.fsPath, '/some/file'); + assert.equal(d.fsPath, normalize('/some/file', true)); // does not explode (https://github.com/Microsoft/vscode/issues/41987) URI.from({ scheme: 'file', authority: '/users/someone/portal.h' }); From fb1d21936ba117f7147b923971cb0063467ec235 Mon Sep 17 00:00:00 2001 From: Sandeep Somavarapu Date: Wed, 24 Jan 2018 11:46:54 +0100 Subject: [PATCH 60/63] #41071 Update the view quickpick list and add open view in views menu --- src/vs/code/electron-main/menus.ts | 2 ++ .../quickopen/browser/viewPickerHandler.ts | 35 ++++++------------- 2 files changed, 13 insertions(+), 24 deletions(-) diff --git a/src/vs/code/electron-main/menus.ts b/src/vs/code/electron-main/menus.ts index 7e389c63729..76be406fa4e 100644 --- a/src/vs/code/electron-main/menus.ts +++ b/src/vs/code/electron-main/menus.ts @@ -683,6 +683,7 @@ export class CodeMenu { } const commands = this.createMenuItem(nls.localize({ key: 'miCommandPalette', comment: ['&& denotes a mnemonic'] }, "&&Command Palette..."), 'workbench.action.showCommands'); + const openView = this.createMenuItem(nls.localize({ key: 'miOpenView', comment: ['&& denotes a mnemonic'] }, "&&Open View..."), 'workbench.action.openView'); const fullscreen = new MenuItem(this.withKeybinding('workbench.action.toggleFullScreen', { label: this.mnemonicLabel(nls.localize({ key: 'miToggleFullScreen', comment: ['&& denotes a mnemonic'] }, "Toggle &&Full Screen")), click: () => this.windowsMainService.getLastActiveWindow().toggleFullScreen(), enabled: this.windowsMainService.getWindowCount() > 0 })); const toggleZenMode = this.createMenuItem(nls.localize('miToggleZenMode', "Toggle Zen Mode"), 'workbench.action.toggleZenMode'); @@ -729,6 +730,7 @@ export class CodeMenu { arrays.coalesce([ commands, + openView, __separator__(), explorer, search, diff --git a/src/vs/workbench/parts/quickopen/browser/viewPickerHandler.ts b/src/vs/workbench/parts/quickopen/browser/viewPickerHandler.ts index 2c1c4186639..6157b6eb26f 100644 --- a/src/vs/workbench/parts/quickopen/browser/viewPickerHandler.ts +++ b/src/vs/workbench/parts/quickopen/browser/viewPickerHandler.ts @@ -138,40 +138,27 @@ export class ViewPickerHandler extends QuickOpenHandler { // Viewlets const viewlets = this.viewletService.getViewlets(); + viewlets.forEach((viewlet, index) => viewEntries.push(new ViewEntry(viewlet.name, nls.localize('views', "Views"), () => this.viewletService.openViewlet(viewlet.id, true).done(null, errors.onUnexpectedError)))); + + // Panels + const panels = this.panelService.getPanels(); + panels.forEach((panel, index) => viewEntries.push(new ViewEntry(panel.name, nls.localize('panels', "Panels"), () => this.panelService.openPanel(panel.id, true).done(null, errors.onUnexpectedError)))); + + // Views viewlets.forEach((viewlet, index) => { const viewLocation: ViewLocation = viewlet.id === EXPLORER_VIEWLET_ID ? ViewLocation.Explorer : viewlet.id === DEBUG_VIEWLET_ID ? ViewLocation.Debug : viewlet.id === EXTENSIONS_VIEWLET_ID ? ViewLocation.Extensions : null; - const viewEntriesForViewlet: ViewEntry[] = viewLocation ? getViewEntriesForViewlet(viewlet, viewLocation) - : [new ViewEntry(viewlet.name, nls.localize('views', "Views"), () => this.viewletService.openViewlet(viewlet.id, true).done(null, errors.onUnexpectedError))]; - - viewEntries.push(...viewEntriesForViewlet); - }); - - const terminals = this.terminalService.terminalInstances; - - // Panels - const panels = this.panelService.getPanels().filter(p => { - if (p.id === OUTPUT_PANEL_ID) { - return false; // since we already show output channels below + if (viewLocation) { + const viewEntriesForViewlet: ViewEntry[] = getViewEntriesForViewlet(viewlet, viewLocation); + viewEntries.push(...viewEntriesForViewlet); } - - if (p.id === TERMINAL_PANEL_ID && terminals.length > 0) { - return false; // since we already show terminal instances below - } - - return true; - }); - panels.forEach((panel, index) => { - const panelsCategory = nls.localize('panels', "Panels"); - const entry = new ViewEntry(panel.name, panelsCategory, () => this.panelService.openPanel(panel.id, true).done(null, errors.onUnexpectedError)); - - viewEntries.push(entry); }); // Terminals + const terminals = this.terminalService.terminalInstances; terminals.forEach((terminal, index) => { const terminalsCategory = nls.localize('terminals', "Terminal"); const entry = new ViewEntry(nls.localize('terminalTitle', "{0}: {1}", index + 1, terminal.title), terminalsCategory, () => { From 4644b60d31b03dc52827e81187cb937f6734bb6f Mon Sep 17 00:00:00 2001 From: Benjamin Pasero Date: Wed, 24 Jan 2018 12:02:09 +0100 Subject: [PATCH 61/63] remove internal API for accessing the value of a model directly --- .../common/editor/textEditorModel.ts | 39 ++++++++----------- .../services/backup/common/backup.ts | 4 +- .../services/backup/node/backupFileService.ts | 16 ++------ .../test/node/backupFileService.test.ts | 30 +++++++------- .../textfile/common/textFileEditorModel.ts | 15 +++---- .../test/common/editor/editorModel.test.ts | 13 +++++-- .../workbench/test/workbenchTestServices.ts | 2 +- 7 files changed, 56 insertions(+), 63 deletions(-) diff --git a/src/vs/workbench/common/editor/textEditorModel.ts b/src/vs/workbench/common/editor/textEditorModel.ts index 8c10065dfcc..63f9d2e6ba9 100644 --- a/src/vs/workbench/common/editor/textEditorModel.ts +++ b/src/vs/workbench/common/editor/textEditorModel.ts @@ -67,13 +67,13 @@ export abstract class BaseTextEditorModel extends EditorModel implements ITextEd /** * Creates the text editor model with the provided value, modeId (can be comma separated for multiple values) and optional resource URL. */ - protected createTextEditorModel(value: string | ITextBufferFactory, resource?: URI, modeId?: string): TPromise { + protected createTextEditorModel(value: ITextBufferFactory, resource?: URI, modeId?: string): TPromise { const firstLineText = this.getFirstLineText(value); const mode = this.getOrCreateMode(this.modeService, modeId, firstLineText); return TPromise.as(this.doCreateTextEditorModel(value, mode, resource)); } - private doCreateTextEditorModel(value: string | ITextBufferFactory, mode: TPromise, resource: URI): EditorModel { + private doCreateTextEditorModel(value: ITextBufferFactory, mode: TPromise, resource: URI): EditorModel { let model = resource && this.modelService.getModel(resource); if (!model) { model = this.modelService.createModel(value, mode, resource); @@ -91,24 +91,7 @@ export abstract class BaseTextEditorModel extends EditorModel implements ITextEd return this; } - protected getFirstLineText(value: string | ITextBufferFactory | ITextSnapshot): string { - - // string - if (typeof value === 'string') { - const firstLineText = value.substr(0, 100); - - let crIndex = firstLineText.indexOf('\r'); - if (crIndex < 0) { - crIndex = firstLineText.length; - } - - let lfIndex = firstLineText.indexOf('\n'); - if (lfIndex < 0) { - lfIndex = firstLineText.length; - } - - return firstLineText.substr(0, Math.min(crIndex, lfIndex)); - } + protected getFirstLineText(value: ITextBufferFactory | ITextSnapshot): string { // text buffer factory const textBufferFactory = value as ITextBufferFactory; @@ -118,7 +101,19 @@ export abstract class BaseTextEditorModel extends EditorModel implements ITextEd // text snapshot const textSnapshot = value as ITextSnapshot; - return this.getFirstLineText(textSnapshot.read() || ''); + const firstLineText = textSnapshot.read().substr(0, 100); + + let crIndex = firstLineText.indexOf('\r'); + if (crIndex < 0) { + crIndex = firstLineText.length; + } + + let lfIndex = firstLineText.indexOf('\n'); + if (lfIndex < 0) { + lfIndex = firstLineText.length; + } + + return firstLineText.substr(0, Math.min(crIndex, lfIndex)); } /** @@ -133,7 +128,7 @@ export abstract class BaseTextEditorModel extends EditorModel implements ITextEd /** * Updates the text editor model with the provided value. If the value is the same as the model has, this is a no-op. */ - protected updateTextEditorModel(newValue: string | ITextBufferFactory): void { + protected updateTextEditorModel(newValue: ITextBufferFactory): void { if (!this.textEditorModel) { return; } diff --git a/src/vs/workbench/services/backup/common/backup.ts b/src/vs/workbench/services/backup/common/backup.ts index d398e7bdde8..86d5326107e 100644 --- a/src/vs/workbench/services/backup/common/backup.ts +++ b/src/vs/workbench/services/backup/common/backup.ts @@ -52,10 +52,10 @@ export interface IBackupFileService { * Backs up a resource. * * @param resource The resource to back up. - * @param content The content of the resource as value or snapshot. + * @param content The content of the resource as snapshot. * @param versionId The version id of the resource to backup. */ - backupResource(resource: Uri, content: string | ITextSnapshot, versionId?: number): TPromise; + backupResource(resource: Uri, content: ITextSnapshot, versionId?: number): TPromise; /** * Gets a list of file backups for the current workspace. diff --git a/src/vs/workbench/services/backup/node/backupFileService.ts b/src/vs/workbench/services/backup/node/backupFileService.ts index c0873744d49..fdeea689752 100644 --- a/src/vs/workbench/services/backup/node/backupFileService.ts +++ b/src/vs/workbench/services/backup/node/backupFileService.ts @@ -11,7 +11,7 @@ import * as pfs from 'vs/base/node/pfs'; import Uri from 'vs/base/common/uri'; import { ResourceQueue } from 'vs/base/common/async'; import { IBackupFileService, BACKUP_FILE_UPDATE_OPTIONS, BACKUP_FILE_RESOLVE_OPTIONS } from 'vs/workbench/services/backup/common/backup'; -import { IFileService, ITextSnapshot, IFileStat } from 'vs/platform/files/common/files'; +import { IFileService, ITextSnapshot } from 'vs/platform/files/common/files'; import { TPromise } from 'vs/base/common/winjs.base'; import { readToMatchingString } from 'vs/base/node/stream'; import { ITextBufferFactory } from 'vs/editor/common/model'; @@ -171,7 +171,7 @@ export class BackupFileService implements IBackupFileService { }); } - public backupResource(resource: Uri, content: string | ITextSnapshot, versionId?: number): TPromise { + public backupResource(resource: Uri, content: ITextSnapshot, versionId?: number): TPromise { if (this.isShuttingDown) { return TPromise.as(void 0); } @@ -190,17 +190,7 @@ export class BackupFileService implements IBackupFileService { const preamble = `${resource.toString()}${BackupFileService.META_MARKER}`; // Update content with value - let updateContentPromise: TPromise; - if (typeof content === 'string') { - updateContentPromise = this.fileService.updateContent(backupResource, `${preamble}${content}`, BACKUP_FILE_UPDATE_OPTIONS); - } - - // Update content with snapshot - else { - updateContentPromise = this.fileService.updateContent(backupResource, new BackupSnapshot(content, preamble), BACKUP_FILE_UPDATE_OPTIONS); - } - - return updateContentPromise.then(() => model.add(backupResource, versionId)); + return this.fileService.updateContent(backupResource, new BackupSnapshot(content, preamble), BACKUP_FILE_UPDATE_OPTIONS).then(() => model.add(backupResource, versionId)); }); }); } diff --git a/src/vs/workbench/services/backup/test/node/backupFileService.test.ts b/src/vs/workbench/services/backup/test/node/backupFileService.test.ts index e59a370b922..2b9552200f4 100644 --- a/src/vs/workbench/services/backup/test/node/backupFileService.test.ts +++ b/src/vs/workbench/services/backup/test/node/backupFileService.test.ts @@ -16,7 +16,7 @@ import pfs = require('vs/base/node/pfs'); import Uri from 'vs/base/common/uri'; import { BackupFileService, BackupFilesModel } from 'vs/workbench/services/backup/node/backupFileService'; import { FileService } from 'vs/workbench/services/files/node/fileService'; -import { TextModel } from 'vs/editor/common/model/textModel'; +import { TextModel, createTextBufferFactory } from 'vs/editor/common/model/textModel'; import { TestContextService, TestTextResourceConfigurationService, getRandomTestPath, TestLifecycleService } from 'vs/workbench/test/workbenchTestServices'; import { Workspace, toWorkspaceFolders } from 'vs/platform/workspace/common/workspace'; import { TestConfigurationService } from 'vs/platform/configuration/test/common/testConfigurationService'; @@ -107,7 +107,7 @@ suite('BackupFileService', () => { suite('backupResource', () => { test('text file', function (done: () => void) { - service.backupResource(fooFile, 'test').then(() => { + service.backupResource(fooFile, createTextBufferFactory('test').create(DefaultEndOfLine.LF).createSnapshot(false)).then(() => { assert.equal(fs.readdirSync(path.join(workspaceBackupPath, 'file')).length, 1); assert.equal(fs.existsSync(fooBackupPath), true); assert.equal(fs.readFileSync(fooBackupPath), `${fooFile.toString()}\ntest`); @@ -116,7 +116,7 @@ suite('BackupFileService', () => { }); test('untitled file', function (done: () => void) { - service.backupResource(untitledFile, 'test').then(() => { + service.backupResource(untitledFile, createTextBufferFactory('test').create(DefaultEndOfLine.LF).createSnapshot(false)).then(() => { assert.equal(fs.readdirSync(path.join(workspaceBackupPath, 'untitled')).length, 1); assert.equal(fs.existsSync(untitledBackupPath), true); assert.equal(fs.readFileSync(untitledBackupPath), `${untitledFile.toString()}\ntest`); @@ -177,7 +177,7 @@ suite('BackupFileService', () => { suite('discardResourceBackup', () => { test('text file', function (done: () => void) { - service.backupResource(fooFile, 'test').then(() => { + service.backupResource(fooFile, createTextBufferFactory('test').create(DefaultEndOfLine.LF).createSnapshot(false)).then(() => { assert.equal(fs.readdirSync(path.join(workspaceBackupPath, 'file')).length, 1); service.discardResourceBackup(fooFile).then(() => { assert.equal(fs.existsSync(fooBackupPath), false); @@ -188,7 +188,7 @@ suite('BackupFileService', () => { }); test('untitled file', function (done: () => void) { - service.backupResource(untitledFile, 'test').then(() => { + service.backupResource(untitledFile, createTextBufferFactory('test').create(DefaultEndOfLine.LF).createSnapshot(false)).then(() => { assert.equal(fs.readdirSync(path.join(workspaceBackupPath, 'untitled')).length, 1); service.discardResourceBackup(untitledFile).then(() => { assert.equal(fs.existsSync(untitledBackupPath), false); @@ -201,9 +201,9 @@ suite('BackupFileService', () => { suite('discardAllWorkspaceBackups', () => { test('text file', function (done: () => void) { - service.backupResource(fooFile, 'test').then(() => { + service.backupResource(fooFile, createTextBufferFactory('test').create(DefaultEndOfLine.LF).createSnapshot(false)).then(() => { assert.equal(fs.readdirSync(path.join(workspaceBackupPath, 'file')).length, 1); - service.backupResource(barFile, 'test').then(() => { + service.backupResource(barFile, createTextBufferFactory('test').create(DefaultEndOfLine.LF).createSnapshot(false)).then(() => { assert.equal(fs.readdirSync(path.join(workspaceBackupPath, 'file')).length, 2); service.discardAllWorkspaceBackups().then(() => { assert.equal(fs.existsSync(fooBackupPath), false); @@ -216,7 +216,7 @@ suite('BackupFileService', () => { }); test('untitled file', function (done: () => void) { - service.backupResource(untitledFile, 'test').then(() => { + service.backupResource(untitledFile, createTextBufferFactory('test').create(DefaultEndOfLine.LF).createSnapshot(false)).then(() => { assert.equal(fs.readdirSync(path.join(workspaceBackupPath, 'untitled')).length, 1); service.discardAllWorkspaceBackups().then(() => { assert.equal(fs.existsSync(untitledBackupPath), false); @@ -228,7 +228,7 @@ suite('BackupFileService', () => { test('should disable further backups', function (done: () => void) { service.discardAllWorkspaceBackups().then(() => { - service.backupResource(untitledFile, 'test').then(() => { + service.backupResource(untitledFile, createTextBufferFactory('test').create(DefaultEndOfLine.LF).createSnapshot(false)).then(() => { assert.equal(fs.existsSync(workspaceBackupPath), false); done(); }); @@ -238,10 +238,10 @@ suite('BackupFileService', () => { suite('getWorkspaceFileBackups', () => { test('("file") - text file', done => { - service.backupResource(fooFile, `test`).then(() => { + service.backupResource(fooFile, createTextBufferFactory('test').create(DefaultEndOfLine.LF).createSnapshot(false)).then(() => { service.getWorkspaceFileBackups().then(textFiles => { assert.deepEqual(textFiles.map(f => f.fsPath), [fooFile.fsPath]); - service.backupResource(barFile, `test`).then(() => { + service.backupResource(barFile, createTextBufferFactory('test').create(DefaultEndOfLine.LF).createSnapshot(false)).then(() => { service.getWorkspaceFileBackups().then(textFiles => { assert.deepEqual(textFiles.map(f => f.fsPath), [fooFile.fsPath, barFile.fsPath]); done(); @@ -252,7 +252,7 @@ suite('BackupFileService', () => { }); test('("file") - untitled file', done => { - service.backupResource(untitledFile, `test`).then(() => { + service.backupResource(untitledFile, createTextBufferFactory('test').create(DefaultEndOfLine.LF).createSnapshot(false)).then(() => { service.getWorkspaceFileBackups().then(textFiles => { assert.deepEqual(textFiles.map(f => f.fsPath), [untitledFile.fsPath]); done(); @@ -261,7 +261,7 @@ suite('BackupFileService', () => { }); test('("untitled") - untitled file', done => { - service.backupResource(untitledFile, `test`).then(() => { + service.backupResource(untitledFile, createTextBufferFactory('test').create(DefaultEndOfLine.LF).createSnapshot(false)).then(() => { service.getWorkspaceFileBackups().then(textFiles => { assert.deepEqual(textFiles.map(f => f.fsPath), ['Untitled-1']); done(); @@ -273,7 +273,7 @@ suite('BackupFileService', () => { test('resolveBackupContent', () => { test('should restore the original contents (untitled file)', () => { const contents = 'test\nand more stuff'; - service.backupResource(untitledFile, contents).then(() => { + service.backupResource(untitledFile, createTextBufferFactory(contents).create(DefaultEndOfLine.LF).createSnapshot(false)).then(() => { service.resolveBackupContent(service.toBackupResource(untitledFile)).then(factory => { assert.equal(contents, snapshotToString(factory.create(platform.isWindows ? DefaultEndOfLine.CRLF : DefaultEndOfLine.LF).createSnapshot(true))); }); @@ -288,7 +288,7 @@ suite('BackupFileService', () => { 'adipiscing ßß elit', ].join(''); - service.backupResource(fooFile, contents).then(() => { + service.backupResource(fooFile, createTextBufferFactory(contents).create(DefaultEndOfLine.LF).createSnapshot(false)).then(() => { service.resolveBackupContent(service.toBackupResource(untitledFile)).then(factory => { assert.equal(contents, snapshotToString(factory.create(platform.isWindows ? DefaultEndOfLine.CRLF : DefaultEndOfLine.LF).createSnapshot(true))); }); diff --git a/src/vs/workbench/services/textfile/common/textFileEditorModel.ts b/src/vs/workbench/services/textfile/common/textFileEditorModel.ts index 887cb059464..981d07eaca2 100644 --- a/src/vs/workbench/services/textfile/common/textFileEditorModel.ts +++ b/src/vs/workbench/services/textfile/common/textFileEditorModel.ts @@ -23,7 +23,7 @@ import { ITextFileService, IAutoSaveConfiguration, ModelState, ITextFileEditorMo import { EncodingMode } from 'vs/workbench/common/editor'; import { BaseTextEditorModel } from 'vs/workbench/common/editor/textEditorModel'; import { IBackupFileService } from 'vs/workbench/services/backup/common/backup'; -import { IFileService, IFileStat, FileOperationError, FileOperationResult, IContent, CONTENT_CHANGE_EVENT_BUFFER_DELAY, FileChangesEvent, FileChangeType } from 'vs/platform/files/common/files'; +import { IFileService, IFileStat, FileOperationError, FileOperationResult, CONTENT_CHANGE_EVENT_BUFFER_DELAY, FileChangesEvent, FileChangeType } from 'vs/platform/files/common/files'; import { IInstantiationService } from 'vs/platform/instantiation/common/instantiation'; import { IMessageService, Severity } from 'vs/platform/message/common/message'; import { IModeService } from 'vs/editor/common/services/modeService'; @@ -32,6 +32,7 @@ import { ITelemetryService } from 'vs/platform/telemetry/common/telemetry'; import { RunOnceScheduler } from 'vs/base/common/async'; import { ITextBufferFactory } from 'vs/editor/common/model'; import { IHashService } from 'vs/workbench/services/hash/common/hashService'; +import { createTextBufferFactory } from 'vs/editor/common/model/textModel'; /** * The text file editor model listens to changes to its underlying code editor model and saves these changes through the file service back to the disk. @@ -290,12 +291,12 @@ export class TextFileEditorModel extends BaseTextEditorModel implements ITextFil // If we have a backup, continue loading with it if (!!backup) { - const content: IContent = { + const content: IRawTextContent = { resource: this.resource, name: paths.basename(this.resource.fsPath), mtime: Date.now(), etag: void 0, - value: '', /* will be filled later from backup */ + value: createTextBufferFactory(''), /* will be filled later from backup */ encoding: this.fileService.getEncoding(this.resource, this.preferredEncoding) }; @@ -355,7 +356,7 @@ export class TextFileEditorModel extends BaseTextEditorModel implements ITextFil return TPromise.wrapError(error); } - private loadWithContent(content: IRawTextContent | IContent, backup?: URI): TPromise { + private loadWithContent(content: IRawTextContent, backup?: URI): TPromise { return this.doLoadWithContent(content, backup).then(model => { // Telemetry: We log the fileGet telemetry event after the model has been loaded to ensure a good mimetype @@ -379,7 +380,7 @@ export class TextFileEditorModel extends BaseTextEditorModel implements ITextFil }); } - private doLoadWithContent(content: IRawTextContent | IContent, backup?: URI): TPromise { + private doLoadWithContent(content: IRawTextContent, backup?: URI): TPromise { diag('load() - resolved content', this.resource, new Date()); // Update our resolved disk stat model @@ -420,7 +421,7 @@ export class TextFileEditorModel extends BaseTextEditorModel implements ITextFil return this.doCreateTextModel(content.resource, content.value, backup); } - private doUpdateTextModel(value: string | ITextBufferFactory): TPromise { + private doUpdateTextModel(value: ITextBufferFactory): TPromise { diag('load() - updated text editor model', this.resource, new Date()); // Ensure we are not tracking a stale state @@ -440,7 +441,7 @@ export class TextFileEditorModel extends BaseTextEditorModel implements ITextFil return TPromise.as(this); } - private doCreateTextModel(resource: URI, value: string | ITextBufferFactory, backup: URI): TPromise { + private doCreateTextModel(resource: URI, value: ITextBufferFactory, backup: URI): TPromise { diag('load() - created text editor model', this.resource, new Date()); this.createTextEditorModelPromise = this.doLoadBackup(backup).then(backupContent => { diff --git a/src/vs/workbench/test/common/editor/editorModel.test.ts b/src/vs/workbench/test/common/editor/editorModel.test.ts index b0c237b73bb..843e19701a6 100644 --- a/src/vs/workbench/test/common/editor/editorModel.test.ts +++ b/src/vs/workbench/test/common/editor/editorModel.test.ts @@ -15,9 +15,16 @@ import { ModeServiceImpl } from 'vs/editor/common/services/modeServiceImpl'; import { IConfigurationService } from 'vs/platform/configuration/common/configuration'; import { TestConfigurationService } from 'vs/platform/configuration/test/common/testConfigurationService'; import { ModelServiceImpl } from 'vs/editor/common/services/modelServiceImpl'; +import { ITextBufferFactory } from 'vs/editor/common/model'; +import URI from 'vs/base/common/uri'; +import { createTextBufferFactory } from 'vs/editor/common/model/textModel'; class MyEditorModel extends EditorModel { } -class MyTextEditorModel extends BaseTextEditorModel { } +class MyTextEditorModel extends BaseTextEditorModel { + public createTextEditorModel(value: ITextBufferFactory, resource?: URI, modeId?: string) { + return super.createTextEditorModel(value, resource, modeId); + } +} suite('Workbench - EditorModel', () => { @@ -51,9 +58,9 @@ suite('Workbench - EditorModel', () => { let modelService = stubModelService(instantiationService); let m = new MyTextEditorModel(modelService, modeService); - m.load().then((model: any) => { + m.load().then((model: MyTextEditorModel) => { assert(model === m); - return model.createTextEditorModel('foo', null, 'text/plain').then(() => { + return model.createTextEditorModel(createTextBufferFactory('foo'), null, 'text/plain').then(() => { assert.strictEqual(m.isResolved(), true); }); }).done(() => { diff --git a/src/vs/workbench/test/workbenchTestServices.ts b/src/vs/workbench/test/workbenchTestServices.ts index d4d3fbd6c25..0b7031c62fa 100644 --- a/src/vs/workbench/test/workbenchTestServices.ts +++ b/src/vs/workbench/test/workbenchTestServices.ts @@ -857,7 +857,7 @@ export class TestBackupFileService implements IBackupFileService { return null; } - public backupResource(resource: URI, content: string | ITextSnapshot): TPromise { + public backupResource(resource: URI, content: ITextSnapshot): TPromise { return TPromise.as(void 0); } From e77cd91a23b6aef028a80bd8abb4651879b347d4 Mon Sep 17 00:00:00 2001 From: Benjamin Pasero Date: Wed, 24 Jan 2018 12:24:10 +0100 Subject: [PATCH 62/63] some message telemetry (for #22388) --- .../services/message/browser/messageList.ts | 16 +++++++- .../electron-browser/messageService.ts | 40 +++++++++---------- 2 files changed, 34 insertions(+), 22 deletions(-) diff --git a/src/vs/workbench/services/message/browser/messageList.ts b/src/vs/workbench/services/message/browser/messageList.ts index a882703c7ae..76db707f70b 100644 --- a/src/vs/workbench/services/message/browser/messageList.ts +++ b/src/vs/workbench/services/message/browser/messageList.ts @@ -190,6 +190,18 @@ export class MessageList { private doShowMessage(id: Error, message: string, severity: Severity, onHide: () => void): () => void; private doShowMessage(id: IMessageWithAction, message: string, severity: Severity, onHide: () => void): () => void; private doShowMessage(id: any, message: string, severity: Severity, onHide: () => void): () => void { + const actions = (id).actions; + const source = (id).source; + + // Telemetry (TODO@Ben remove me later) + /* __GDPR__ + "showMessage" : { + "message" : { "classification": "SystemMetaData", "purpose": "FeatureInsight" } + "source" : { "classification": "SystemMetaData", "purpose": "FeatureInsight" } + "buttons" : { "classification": "SystemMetaData", "purpose": "FeatureInsight" } + } + */ + this.telemetryService.publicLog('showMessage', { message, source, buttons: actions ? actions.map(a => a.label) : void 0 }); // Trigger Auto-Purge of messages to keep list small this.purgeMessages(); @@ -200,8 +212,8 @@ export class MessageList { text: message, severity: severity, time: Date.now(), - actions: (id).actions, - source: (id).source, + actions, + source, onHide }); diff --git a/src/vs/workbench/services/message/electron-browser/messageService.ts b/src/vs/workbench/services/message/electron-browser/messageService.ts index 0c04c556de5..6e7a376cd96 100644 --- a/src/vs/workbench/services/message/electron-browser/messageService.ts +++ b/src/vs/workbench/services/message/electron-browser/messageService.ts @@ -13,7 +13,7 @@ import { IConfirmation, Severity, IChoiceService, IConfirmationResult } from 'vs import { isLinux } from 'vs/base/common/platform'; import { ITelemetryService } from 'vs/platform/telemetry/common/telemetry'; import { Action } from 'vs/base/common/actions'; -import { IWindowService, IMessageBoxResult } from 'vs/platform/windows/common/windows'; +import { IWindowService } from 'vs/platform/windows/common/windows'; import { mnemonicButtonLabel } from 'vs/base/common/labels'; export class MessageService extends WorkbenchMessageService implements IChoiceService { @@ -27,31 +27,22 @@ export class MessageService extends WorkbenchMessageService implements IChoiceSe } public confirmWithCheckbox(confirmation: IConfirmation): TPromise { - const opts = this.getConfirmOptions(confirmation); - - return this.showMessageBoxWithCheckbox(opts).then(result => { - return { - confirmed: result.button === 0 ? true : false, - checkboxChecked: result.checkboxChecked - } as IConfirmationResult; - }); - } - - private showMessageBoxWithCheckbox(opts: Electron.MessageBoxOptions): TPromise { - opts = this.massageMessageBoxOptions(opts); + const opts = this.massageMessageBoxOptions(this.getConfirmOptions(confirmation)); return this.windowService.showMessageBox(opts).then(result => { + const button = isLinux ? opts.buttons.length - result.button - 1 : result.button; + return { - button: isLinux ? opts.buttons.length - result.button - 1 : result.button, + confirmed: button === 0 ? true : false, checkboxChecked: result.checkboxChecked - } as IMessageBoxResult; + } as IConfirmationResult; }); } public confirm(confirmation: IConfirmation): TPromise { const opts = this.getConfirmOptions(confirmation); - return this.showMessageBox(opts).then(result => result === 0 ? true : false); + return this.doShowMessageBox(opts).then(result => result === 0 ? true : false); } private getConfirmOptions(confirmation: IConfirmation): Electron.MessageBoxOptions { @@ -94,16 +85,25 @@ export class MessageService extends WorkbenchMessageService implements IChoiceSe public choose(severity: Severity, message: string, options: string[], cancelId: number, modal: boolean = false): TPromise { if (modal) { - const type: 'none' | 'info' | 'error' | 'question' | 'warning' = severity === Severity.Info ? 'question' : severity === Severity.Error ? 'error' : severity === Severity.Warning ? 'warning' : 'none'; - - return this.showMessageBox({ message, buttons: options, type, cancelId }); + return this.doChooseModal(severity, message, options, cancelId); } + return this.doChooseWithMessage(severity, message, options); + } + + private doChooseModal(severity: Severity, message: string, options: string[], cancelId: number): TPromise { + const type: 'none' | 'info' | 'error' | 'question' | 'warning' = severity === Severity.Info ? 'question' : severity === Severity.Error ? 'error' : severity === Severity.Warning ? 'warning' : 'none'; + + return this.doShowMessageBox({ message, buttons: options, type, cancelId }); + } + + private doChooseWithMessage(severity: Severity, message: string, options: string[]): TPromise { let onCancel: () => void = null; const promise = new TPromise((c, e) => { const callback = (index: number) => () => { c(index); + return TPromise.as(true); }; @@ -115,7 +115,7 @@ export class MessageService extends WorkbenchMessageService implements IChoiceSe return promise; } - private showMessageBox(opts: Electron.MessageBoxOptions): TPromise { + private doShowMessageBox(opts: Electron.MessageBoxOptions): TPromise { opts = this.massageMessageBoxOptions(opts); return this.windowService.showMessageBox(opts).then(result => isLinux ? opts.buttons.length - result.button - 1 : result.button); From 10d26e14d3e5dd39c68528462a3bf41db7eabee3 Mon Sep 17 00:00:00 2001 From: Benjamin Pasero Date: Wed, 24 Jan 2018 13:22:42 +0100 Subject: [PATCH 63/63] fix warnings --- src/vs/workbench/parts/quickopen/browser/viewPickerHandler.ts | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/vs/workbench/parts/quickopen/browser/viewPickerHandler.ts b/src/vs/workbench/parts/quickopen/browser/viewPickerHandler.ts index 6157b6eb26f..7b41004a587 100644 --- a/src/vs/workbench/parts/quickopen/browser/viewPickerHandler.ts +++ b/src/vs/workbench/parts/quickopen/browser/viewPickerHandler.ts @@ -11,8 +11,8 @@ import { Mode, IEntryRunContext, IAutoFocus, IQuickNavigateConfiguration, IModel import { QuickOpenModel, QuickOpenEntryGroup, QuickOpenEntry } from 'vs/base/parts/quickopen/browser/quickOpenModel'; import { QuickOpenHandler, QuickOpenAction } from 'vs/workbench/browser/quickopen'; import { IViewletService } from 'vs/workbench/services/viewlet/browser/viewlet'; -import { IOutputService, OUTPUT_PANEL_ID } from 'vs/workbench/parts/output/common/output'; -import { ITerminalService, TERMINAL_PANEL_ID } from 'vs/workbench/parts/terminal/common/terminal'; +import { IOutputService } from 'vs/workbench/parts/output/common/output'; +import { ITerminalService } from 'vs/workbench/parts/terminal/common/terminal'; import { IPanelService } from 'vs/workbench/services/panel/common/panelService'; import { IQuickOpenService } from 'vs/platform/quickOpen/common/quickOpen'; import { Action } from 'vs/base/common/actions';