mirror of
https://github.com/microsoft/TypeScript.git
synced 2026-02-15 11:35:42 -06:00
shutdown typing installer if parent process is exited
This commit is contained in:
parent
758d8de8f9
commit
ce35f96892
@ -12,6 +12,7 @@ namespace ts.server {
|
||||
interface NodeChildProcess {
|
||||
send(message: any, sendHandle?: any): void;
|
||||
on(message: "message", f: (m: any) => void): void;
|
||||
kill(): void;
|
||||
}
|
||||
|
||||
const childProcess: {
|
||||
@ -175,6 +176,10 @@ namespace ts.server {
|
||||
|
||||
this.installer = childProcess.fork(combinePaths(__dirname, "typingsInstaller.js"));
|
||||
this.installer.on("message", m => this.handleMessage(m));
|
||||
process.on("exit", () => {
|
||||
this.installer.kill();
|
||||
})
|
||||
|
||||
}
|
||||
|
||||
onProjectClosed(p: Project): void {
|
||||
|
||||
@ -52,6 +52,9 @@ namespace ts.server.typingsInstaller {
|
||||
|
||||
constructor(log?: Log) {
|
||||
super(getGlobalCacheLocation(), toPath("typingSafeList.json", __dirname, createGetCanonicalFileName(sys.useCaseSensitiveFileNames)), log);
|
||||
if (this.log.isEnabled()) {
|
||||
this.log.writeLine(`Process id: ${process.pid}`);
|
||||
}
|
||||
const { exec, execSync } = require("child_process");
|
||||
this.execSync = execSync;
|
||||
this.exec = exec;
|
||||
@ -84,20 +87,34 @@ namespace ts.server.typingsInstaller {
|
||||
|
||||
protected isPackageInstalled(packageName: string) {
|
||||
try {
|
||||
this.execSync(`npm list --global --depth=1 ${packageName}`, { stdio: "ignore" });
|
||||
const output = this.execSync(`npm list --global --depth=1 ${packageName}`, { stdio: "pipe" }).toString();
|
||||
if (this.log.isEnabled()) {
|
||||
this.log.writeLine(`IsPackageInstalled::stdout '${output}'`);
|
||||
}
|
||||
return true;
|
||||
}
|
||||
catch (e) {
|
||||
if (this.log.isEnabled()) {
|
||||
this.log.writeLine(`IsPackageInstalled::err::stdout '${e.stdout && e.stdout.toString()}'`);
|
||||
this.log.writeLine(`IsPackageInstalled::err::stderr '${e.stdout && e.stderr.toString()}'`);
|
||||
}
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
protected installPackage(packageName: string) {
|
||||
try {
|
||||
this.execSync(`npm install --global ${packageName}`, { stdio: "ignore" });
|
||||
const output = this.execSync(`npm install --global ${packageName}`, { stdio: "pipe" }).toString();
|
||||
if (this.log.isEnabled()) {
|
||||
this.log.writeLine(`installPackage::stdout '${output}'`);
|
||||
}
|
||||
return true;
|
||||
}
|
||||
catch (e) {
|
||||
if (this.log.isEnabled()) {
|
||||
this.log.writeLine(`installPackage::err::stdout '${e.stdout && e.stdout.toString()}'`);
|
||||
this.log.writeLine(`installPackage::err::stderr '${e.stdout && e.stderr.toString()}'`);
|
||||
}
|
||||
return false;
|
||||
}
|
||||
}
|
||||
@ -107,6 +124,9 @@ namespace ts.server.typingsInstaller {
|
||||
this.log.writeLine(`Sending response: ${JSON.stringify(response)}`)
|
||||
}
|
||||
process.send(response);
|
||||
if (this.log.isEnabled()) {
|
||||
this.log.writeLine(`Response has been sent.`)
|
||||
}
|
||||
}
|
||||
|
||||
protected runTsd(cachePath: string, typingsToInstall: string[], postInstallAction: (installedTypings: string[]) => void): void {
|
||||
@ -139,11 +159,15 @@ namespace ts.server.typingsInstaller {
|
||||
}
|
||||
|
||||
const log = new FileLog(process.env.TI_LOG_FILE);
|
||||
process.on("uncaughtException", (e: Error) => {
|
||||
if (log.isEnabled()) {
|
||||
if (log.isEnabled()) {
|
||||
process.on("uncaughtException", (e: Error) => {
|
||||
log.writeLine(`Unhandled exception: ${e} at ${e.stack}`);
|
||||
}
|
||||
})
|
||||
});
|
||||
process.on("disconnect", () => {
|
||||
log.writeLine(`Parent process has exited, shutting down...`);
|
||||
process.exit(0);
|
||||
});
|
||||
}
|
||||
const installer = new NodeTypingsInstaller(log);
|
||||
installer.init();
|
||||
}
|
||||
@ -72,7 +72,7 @@ namespace ts.server.typingsInstaller {
|
||||
this.closeWatchers(req.projectName);
|
||||
}
|
||||
|
||||
private closeWatchers(projectName: string): boolean {
|
||||
private closeWatchers(projectName: string): void {
|
||||
if (this.log.isEnabled()) {
|
||||
this.log.writeLine(`Closing file watchers for project '${projectName}'`);
|
||||
}
|
||||
@ -82,7 +82,7 @@ namespace ts.server.typingsInstaller {
|
||||
this.log.writeLine(`No watchers are registered for project '${projectName}'`);
|
||||
}
|
||||
|
||||
return false;
|
||||
return;
|
||||
}
|
||||
for (const w of watchers) {
|
||||
w.close();
|
||||
@ -93,8 +93,6 @@ namespace ts.server.typingsInstaller {
|
||||
if (this.log.isEnabled()) {
|
||||
this.log.writeLine(`Closing file watchers for project '${projectName}' - done.`);
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
install(req: DiscoverTypings) {
|
||||
@ -137,7 +135,14 @@ namespace ts.server.typingsInstaller {
|
||||
this.watchFiles(req.projectName, discoverTypingsResult.filesToWatch);
|
||||
|
||||
// install typings
|
||||
this.installTypings(req, req.cachePath || this.globalCachePath, discoverTypingsResult.cachedTypingPaths, discoverTypingsResult.newTypingNames);
|
||||
if (discoverTypingsResult.newTypingNames.length) {
|
||||
this.installTypings(req, req.cachePath || this.globalCachePath, discoverTypingsResult.cachedTypingPaths, discoverTypingsResult.newTypingNames);
|
||||
}
|
||||
else {
|
||||
if (this.log.isEnabled()) {
|
||||
this.log.writeLine(`No new typings were requested as a result of typings discovery`);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private processCacheLocation(cacheLocation: string) {
|
||||
@ -259,17 +264,23 @@ namespace ts.server.typingsInstaller {
|
||||
if (!files.length) {
|
||||
return;
|
||||
}
|
||||
// shut down existing watchers
|
||||
this.closeWatchers(projectName);
|
||||
|
||||
// handler should be invoked once for the entire set of files since it will trigger full rediscovery of typings
|
||||
let isInvoked = false;
|
||||
const watchers: FileWatcher[] = [];
|
||||
for (const file of files) {
|
||||
const w = this.installTypingHost.watchFile(file, f => {
|
||||
if (this.log.isEnabled()) {
|
||||
this.log.writeLine(`FS notification for '${f}', sending 'clean' message for project '${projectName}'`);
|
||||
this.log.writeLine(`Got FS notification for ${f}, handler is already invoked '${isInvoked}'`);
|
||||
}
|
||||
this.closeWatchers(projectName);
|
||||
this.sendResponse(<InvalidateCachedTypings>{ projectName: projectName, kind: "invalidate" })
|
||||
this.sendResponse({ projectName: projectName, kind: "invalidate" });
|
||||
isInvoked = true;
|
||||
});
|
||||
watchers.push(w);
|
||||
}
|
||||
this.projectWatchers[projectName] = watchers;
|
||||
}
|
||||
|
||||
private createSetTypings(request: DiscoverTypings, typings: string[]): SetTypings {
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user