Merge from vscode 8a997f7321ae6612fc0e6eb3eac4f358a6233bfb

This commit is contained in:
ADS Merger
2020-02-11 07:08:19 +00:00
parent 0f934081e1
commit 085752f111
217 changed files with 2561 additions and 2063 deletions

View File

@@ -440,7 +440,7 @@ export class IssueReporter extends Disposable {
sendWorkbenchCommand('workbench.action.reloadWindowWithExtensionsDisabled');
});
this.addEventListener('extensionBugsLink', 'click', (e: MouseEvent) => {
this.addEventListener('extensionBugsLink', 'click', (e: Event) => {
const url = (<HTMLElement>e.target).innerText;
shell.openExternal(url);
});

View File

@@ -12,7 +12,7 @@ import { SyncDescriptor } from 'vs/platform/instantiation/common/descriptors';
import { InstantiationService } from 'vs/platform/instantiation/common/instantiationService';
import { IEnvironmentService, ParsedArgs } from 'vs/platform/environment/common/environment';
import { EnvironmentService } from 'vs/platform/environment/node/environmentService';
import { ExtensionManagementChannel, GlobalExtensionEnablementServiceClient } from 'vs/platform/extensionManagement/common/extensionManagementIpc';
import { ExtensionManagementChannel } from 'vs/platform/extensionManagement/common/extensionManagementIpc';
import { IExtensionManagementService, IExtensionGalleryService, IGlobalExtensionEnablementService } from 'vs/platform/extensionManagement/common/extensionManagement';
import { ExtensionManagementService } from 'vs/platform/extensionManagement/node/extensionManagementService';
import { ExtensionGalleryService } from 'vs/platform/extensionManagement/common/extensionGalleryService';
@@ -49,7 +49,7 @@ import { IFileService } from 'vs/platform/files/common/files';
import { DiskFileSystemProvider } from 'vs/platform/files/electron-browser/diskFileSystemProvider';
import { Schemas } from 'vs/base/common/network';
import { IProductService } from 'vs/platform/product/common/productService';
import { IUserDataSyncService, IUserDataSyncStoreService, registerConfiguration, IUserDataSyncLogService, IUserDataSyncUtilService, ISettingsSyncService, IUserDataAuthTokenService } from 'vs/platform/userDataSync/common/userDataSync';
import { IUserDataSyncService, IUserDataSyncStoreService, registerConfiguration, IUserDataSyncLogService, IUserDataSyncUtilService, ISettingsSyncService, IUserDataAuthTokenService, IUserDataSyncEnablementService } from 'vs/platform/userDataSync/common/userDataSync';
import { UserDataSyncService } from 'vs/platform/userDataSync/common/userDataSyncService';
import { UserDataSyncStoreService } from 'vs/platform/userDataSync/common/userDataSyncStoreService';
import { UserDataSyncChannel, UserDataSyncUtilServiceClient, SettingsSyncChannel, UserDataAuthTokenServiceChannel, UserDataAutoSyncChannel } from 'vs/platform/userDataSync/common/userDataSyncIpc';
@@ -61,6 +61,11 @@ import { KeytarCredentialsService } from 'vs/platform/credentials/node/credentia
import { UserDataAutoSyncService } from 'vs/platform/userDataSync/electron-browser/userDataAutoSyncService';
import { SettingsSynchroniser } from 'vs/platform/userDataSync/common/settingsSync';
import { UserDataAuthTokenService } from 'vs/platform/userDataSync/common/userDataAuthTokenService';
import { NativeStorageService } from 'vs/platform/storage/node/storageService';
import { GlobalStorageDatabaseChannelClient } from 'vs/platform/storage/node/storageIpc';
import { IStorageService } from 'vs/platform/storage/common/storage';
import { GlobalExtensionEnablementService } from 'vs/platform/extensionManagement/common/extensionEnablementService';
import { UserDataSyncEnablementService } from 'vs/platform/userDataSync/common/userDataSyncEnablementService';
export interface ISharedProcessConfiguration {
readonly machineId: string;
@@ -100,7 +105,7 @@ async function main(server: Server, initData: ISharedProcessInitData, configurat
const onExit = () => disposables.dispose();
process.once('exit', onExit);
ipcRenderer.once('handshake:goodbye', onExit);
ipcRenderer.once('electron-main->shared-process: exit', onExit);
disposables.add(server);
@@ -119,6 +124,11 @@ async function main(server: Server, initData: ISharedProcessInitData, configurat
disposables.add(configurationService);
await configurationService.initialize();
const storageService = new NativeStorageService(new GlobalStorageDatabaseChannelClient(mainProcessService.getChannel('storage')), logService, environmentService);
await storageService.initialize();
services.set(IStorageService, storageService);
disposables.add(toDisposable(() => storageService.flush()));
services.set(IEnvironmentService, environmentService);
services.set(IProductService, { _serviceBrand: undefined, ...product });
services.set(ILogService, logService);
@@ -147,7 +157,7 @@ async function main(server: Server, initData: ISharedProcessInitData, configurat
instantiationService.invokeFunction(accessor => {
const services = new ServiceCollection();
const environmentService = accessor.get(IEnvironmentService);
const { appRoot, extensionsPath, extensionDevelopmentLocationURI: extensionDevelopmentLocationURI, isBuilt, installSourcePath } = environmentService;
const { appRoot, extensionsPath, extensionDevelopmentLocationURI, isBuilt, installSourcePath } = environmentService;
const telemetryLogService = new FollowerLogService(loggerClient, new SpdLogService('telemetry', environmentService.logsPath, initData.logLevel));
telemetryLogService.info('The below are logs for every telemetry event sent from VS Code once the log level is set to trace.');
telemetryLogService.info('===========================================================');
@@ -181,8 +191,9 @@ async function main(server: Server, initData: ISharedProcessInitData, configurat
services.set(IUserDataAuthTokenService, new SyncDescriptor(UserDataAuthTokenService));
services.set(IUserDataSyncLogService, new SyncDescriptor(UserDataSyncLogService));
services.set(IUserDataSyncUtilService, new UserDataSyncUtilServiceClient(server.getChannel('userDataSyncUtil', client => client.ctx !== 'main')));
services.set(IGlobalExtensionEnablementService, new GlobalExtensionEnablementServiceClient(server.getChannel('globalExtensionEnablement', client => client.ctx !== 'main')));
services.set(IGlobalExtensionEnablementService, new SyncDescriptor(GlobalExtensionEnablementService));
services.set(IUserDataSyncStoreService, new SyncDescriptor(UserDataSyncStoreService));
services.set(IUserDataSyncEnablementService, new SyncDescriptor(UserDataSyncEnablementService));
services.set(ISettingsSyncService, new SyncDescriptor(SettingsSynchroniser));
services.set(IUserDataSyncService, new SyncDescriptor(UserDataSyncService));
registerConfiguration();
@@ -271,13 +282,20 @@ function setupIPC(hook: string): Promise<Server> {
}
async function handshake(configuration: ISharedProcessConfiguration): Promise<void> {
// receive payload from electron-main to start things
const data = await new Promise<ISharedProcessInitData>(c => {
ipcRenderer.once('handshake:hey there', (_: any, r: ISharedProcessInitData) => c(r));
ipcRenderer.send('handshake:hello');
ipcRenderer.once('electron-main->shared-process: payload', (_: any, r: ISharedProcessInitData) => c(r));
// tell electron-main we are ready to receive payload
ipcRenderer.send('shared-process->electron-main: ready-for-payload');
});
// await IPC connection and signal this back to electron-main
const server = await setupIPC(data.sharedIPCHandle);
ipcRenderer.send('shared-process->electron-main: ipc-ready');
// await initialization and signal this back to electron-main
await main(server, data, configuration);
ipcRenderer.send('handshake:im ready');
ipcRenderer.send('shared-process->electron-main: init-done');
}

View File

@@ -364,7 +364,14 @@ export class CodeApplication extends Disposable {
// Spawn shared process after the first window has opened and 3s have passed
const sharedProcess = this.instantiationService.createInstance(SharedProcess, machineId, this.userEnv);
const sharedProcessClient = sharedProcess.whenReady().then(() => connect(this.environmentService.sharedIPCHandle, 'main'));
const sharedProcessClient = sharedProcess.whenIpcReady().then(() => {
this.logService.trace('Shared process: IPC ready');
return connect(this.environmentService.sharedIPCHandle, 'main');
});
const sharedProcessReady = sharedProcess.whenReady().then(() => {
this.logService.trace('Shared process: init ready');
return sharedProcessClient;
});
this.lifecycleMainService.when(LifecycleMainPhase.AfterWindowOpen).then(() => {
this._register(new RunOnceScheduler(async () => {
const userEnv = await getShellEnvironment(this.logService, this.environmentService);
@@ -374,7 +381,7 @@ export class CodeApplication extends Disposable {
});
// Services
const appInstantiationService = await this.createServices(machineId, trueMachineId, sharedProcess, sharedProcessClient);
const appInstantiationService = await this.createServices(machineId, trueMachineId, sharedProcess, sharedProcessReady);
// Create driver
if (this.environmentService.driverHandle) {
@@ -391,7 +398,7 @@ export class CodeApplication extends Disposable {
const windows = appInstantiationService.invokeFunction(accessor => this.openFirstWindow(accessor, electronIpcServer, sharedProcessClient));
// Post Open Windows Tasks
this.afterWindowOpen();
appInstantiationService.invokeFunction(this.afterWindowOpen.bind(this));
// Tracing: Stop tracing after windows are ready if enabled
if (this.environmentService.args.trace) {
@@ -424,7 +431,7 @@ export class CodeApplication extends Disposable {
return { machineId, trueMachineId };
}
private async createServices(machineId: string, trueMachineId: string | undefined, sharedProcess: SharedProcess, sharedProcessClient: Promise<Client<string>>): Promise<IInstantiationService> {
private async createServices(machineId: string, trueMachineId: string | undefined, sharedProcess: SharedProcess, sharedProcessReady: Promise<Client<string>>): Promise<IInstantiationService> {
const services = new ServiceCollection();
const fileService = this._register(new FileService(this.logService));
@@ -456,7 +463,7 @@ export class CodeApplication extends Disposable {
services.set(ISharedProcessMainService, new SyncDescriptor(SharedProcessMainService, [sharedProcess]));
services.set(ILaunchMainService, new SyncDescriptor(LaunchMainService));
const diagnosticsChannel = getDelayedChannel(sharedProcessClient.then(client => client.getChannel('diagnostics')));
const diagnosticsChannel = getDelayedChannel(sharedProcessReady.then(client => client.getChannel('diagnostics')));
services.set(IDiagnosticsService, new SyncDescriptor(DiagnosticsService, [diagnosticsChannel]));
services.set(IIssueService, new SyncDescriptor(IssueMainService, [machineId, this.userEnv]));
@@ -477,7 +484,7 @@ export class CodeApplication extends Disposable {
// Telemetry
if (!this.environmentService.isExtensionDevelopment && !this.environmentService.args['disable-telemetry'] && !!product.enableTelemetry) {
const channel = getDelayedChannel(sharedProcessClient.then(client => client.getChannel('telemetryAppender')));
const channel = getDelayedChannel(sharedProcessReady.then(client => client.getChannel('telemetryAppender')));
const appender = combinedAppender(new TelemetryAppenderClient(channel), new LogAppender(this.logService));
const commonProperties = resolveCommonProperties(product.commit, product.version, machineId, product.msftInternalDomains, this.environmentService.installSourcePath);
const piiPaths = this.environmentService.extensionsPath ? [this.environmentService.appRoot, this.environmentService.extensionsPath] : [this.environmentService.appRoot];
@@ -571,6 +578,7 @@ export class CodeApplication extends Disposable {
const storageMainService = accessor.get(IStorageMainService);
const storageChannel = this._register(new GlobalStorageDatabaseChannel(this.logService, storageMainService));
electronIpcServer.registerChannel('storage', storageChannel);
sharedProcessClient.then(client => client.registerChannel('storage', storageChannel));
const loggerChannel = new LoggerChannel(accessor.get(ILogService));
electronIpcServer.registerChannel('logger', loggerChannel);
@@ -706,13 +714,18 @@ export class CodeApplication extends Disposable {
return { fileUri: URI.file(path) };
}
private afterWindowOpen(): void {
private afterWindowOpen(accessor: ServicesAccessor): void {
// Signal phase: after window open
this.lifecycleMainService.phase = LifecycleMainPhase.AfterWindowOpen;
// Remote Authorities
this.handleRemoteAuthorities();
// Initialize update service
const updateService = accessor.get(IUpdateService);
if (updateService instanceof Win32UpdateService || updateService instanceof LinuxUpdateService || updateService instanceof DarwinUpdateService) {
updateService.initialize();
}
}
private handleRemoteAuthorities(): void {

View File

@@ -21,6 +21,8 @@ export class SharedProcess implements ISharedProcess {
private window: BrowserWindow | null = null;
private readonly _whenReady: Promise<void>;
constructor(
private readonly machineId: string,
private userEnv: NodeJS.ProcessEnv,
@@ -28,10 +30,13 @@ export class SharedProcess implements ISharedProcess {
@ILifecycleMainService private readonly lifecycleMainService: ILifecycleMainService,
@ILogService private readonly logService: ILogService,
@IThemeMainService private readonly themeMainService: IThemeMainService
) { }
) {
// overall ready promise when shared process signals initialization is done
this._whenReady = new Promise<void>(c => ipcMain.once('shared-process->electron-main: init-done', () => c(undefined)));
}
@memoize
private get _whenReady(): Promise<void> {
private get _whenIpcReady(): Promise<void> {
this.window = new BrowserWindow({
show: false,
backgroundColor: this.themeMainService.getBackgroundColor(),
@@ -98,16 +103,19 @@ export class SharedProcess implements ISharedProcess {
});
return new Promise<void>(c => {
const onHello = Event.once(Event.fromNodeEventEmitter(ipcMain, 'handshake:hello', ({ sender }: { sender: WebContents }) => sender));
disposables.add(onHello(sender => {
sender.send('handshake:hey there', {
// send payload once shared process is ready to receive it
disposables.add(Event.once(Event.fromNodeEventEmitter(ipcMain, 'shared-process->electron-main: ready-for-payload', ({ sender }: { sender: WebContents }) => sender))(sender => {
sender.send('electron-main->shared-process: payload', {
sharedIPCHandle: this.environmentService.sharedIPCHandle,
args: this.environmentService.args,
logLevel: this.logService.getLevel()
});
disposables.add(toDisposable(() => sender.send('handshake:goodbye')));
ipcMain.once('handshake:im ready', () => c(undefined));
// signal exit to shared process when we get disposed
disposables.add(toDisposable(() => sender.send('electron-main->shared-process: exit')));
// complete IPC-ready promise when shared process signals this to us
ipcMain.once('shared-process->electron-main: ipc-ready', () => c(undefined));
}));
});
}
@@ -122,6 +130,11 @@ export class SharedProcess implements ISharedProcess {
await this._whenReady;
}
async whenIpcReady(): Promise<void> {
await this.barrier.wait();
await this._whenIpcReady;
}
toggle(): void {
if (!this.window || this.window.isVisible()) {
this.hide();

View File

@@ -331,7 +331,7 @@ export async function main(argv: ParsedArgs): Promise<void> {
const envService = accessor.get(IEnvironmentService);
const stateService = accessor.get(IStateService);
const { appRoot, extensionsPath, extensionDevelopmentLocationURI: extensionDevelopmentLocationURI, isBuilt, installSourcePath } = envService;
const { appRoot, extensionsPath, extensionDevelopmentLocationURI, isBuilt, installSourcePath } = envService;
const services = new ServiceCollection();