'Async child_process.exec with TypeScript
I'm trying to use a child_process.exec call with TypeScript, and error handling seems excessively hard to get right.
Here's the gist of what I'm trying to do:
import { promisify } from "util";
import { exec, ExecException } from "child_process";
const execPromise = promisify(exec);
export const myCommand = async (param: string) => {
const { stdout, stderr } = await execPromise(`my_command ${param}`);
return {
stdout,
stderr,
// some other fields
};
};
This works fine as long as my_command returns 0.
Now, my_command can sometimes return 1, but it should be an error, not an exception. It's kinda normal and I want to handle it. With promisify though, it becomes an Exception, so I tried to handle it this way:
let stdout, stderr: string;
try {
const { stdout: execStdout, stderr: execStderr } = await execPromise(`my_command ${param}`);
stdout = execStdout;
stderr = execStderr;
} catch (e: unknown) {
// ???
}
Here's what I tried for exception handling:
if (e instanceof ExecException) {}
but it fails with 'ExecException' only refers to a type, but is being used as a value here.
I also tried:
if ("stdout" in e) {}
because I want to retrieve stdout from the error but it fails with Object is of type 'unknown'..
I then tried to force a type assertion with:
e as ExecException
It kinda works but:
- it's risky
- I noticed ExecException doesn't have the
stdout/stderrfields that it should have, so I still can't get them in case of error, which makes no sense...
So I'm a bit stuck on what I should do. Could someone help me?
Solution 1:[1]
You can define a Type Guard:
function isStdError(err: any): err is { stderr: string } {
return !!err.stderr
}
Then in your code:
try {
await exec(`my_command`)
} catch (e) {
if (isStdError(e)) {
console.log(e.stderr)
} else {
throw e
}
}
Sources
This article follows the attribution requirements of Stack Overflow and is licensed under CC BY-SA 3.0.
Source: Stack Overflow
| Solution | Source |
|---|---|
| Solution 1 | xonya |
