[SQL-Migration] Fix JSON-RPC Migration crash on ADS reload due to zombie process (#22036)

This PR fixes an issue where the JSON-RPC Migration Service crashes when ADS is reloaded.

This situation applies when user tried to reload ADS where SQL-migration extension was running:

when connecting to DB, SQL-migration extension loads and migration service launches
if a previous MigrationService zombie process is stil running (if extension was used before), then that zombie process will have a lock on the log file
new launches of MigrationService on reloaded ADS fails b/c it can't obtain log file handle due to lock in step 2
The fix stops the MigrationService on extension deactivate and will ensure that a zombie MigrationService process isn't hanging around on reloads.

No hotfix needed as 1.4.0 was baking in insiders and has not been released to stable yet. Additionally, this mainly affects developers as they are most likely to reload ADS this way. Caveat: users do need to reload after installing latest version, however they will not hit this code path (since the migration service process is only in new versions of the extension)
This commit is contained in:
AkshayMata
2023-02-25 19:28:36 -08:00
committed by GitHub
parent 8752ba434d
commit d39e503788

View File

@@ -9,8 +9,10 @@ import * as constants from './constants/strings';
import { ServiceClient } from './service/serviceClient';
import { migrationServiceProvider } from './service/provider';
import { TelemetryReporter } from './telemetry';
import { SqlOpsDataClient } from 'dataprotocol-client';
let widget: DashboardWidget;
let migrationServiceClient: SqlOpsDataClient | undefined;
export async function activate(context: vscode.ExtensionContext): Promise<DashboardWidget> {
if (!migrationServiceProvider) {
await vscode.window.showErrorMessage(constants.serviceProviderInitializationError);
@@ -18,8 +20,9 @@ export async function activate(context: vscode.ExtensionContext): Promise<Dashbo
// asynchronously starting the service
const outputChannel = vscode.window.createOutputChannel(constants.serviceName);
const serviceClient = new ServiceClient(outputChannel);
serviceClient.startService(context).catch((e) => {
migrationServiceClient = await serviceClient.startService(context).catch((e) => {
console.error(e);
return undefined;
});
widget = new DashboardWidget(context);
@@ -28,5 +31,8 @@ export async function activate(context: vscode.ExtensionContext): Promise<Dashbo
return widget;
}
export function deactivate(): void {
export async function deactivate(): Promise<void> {
if (migrationServiceClient) {
await migrationServiceClient.stop();
}
}