Commit 6eb540f

Anton Golub <antongolub@antongolub.com>
2024-10-31 14:22:44
refactor: pass stream err to pipe promise rejection (#928) tag: 8.2.0
continues #921
1 parent d0b5c2c
src/core.ts
@@ -319,12 +319,12 @@ export class ProcessPromise extends Promise<ProcessOutput> {
 
   // Essentials
   pipe(dest: TemplateStringsArray, ...args: any[]): ProcessPromise
-  pipe<D extends Writable>(dest: D): D & PromiseLike<void>
+  pipe<D extends Writable>(dest: D): D & PromiseLike<D>
   pipe<D extends ProcessPromise>(dest: D): D
   pipe(
     dest: Writable | ProcessPromise | TemplateStringsArray,
     ...args: any[]
-  ): (Writable & PromiseLike<void>) | ProcessPromise {
+  ): (Writable & PromiseLike<Writable>) | ProcessPromise {
     if (isStringLiteral(dest, ...args))
       return this.pipe($(dest as TemplateStringsArray, ...args))
     if (isString(dest))
src/util.ts
@@ -453,21 +453,21 @@ export const once = <T extends (...args: any[]) => any>(fn: T) => {
 
 export const promisifyStream = <S extends Writable>(
   stream: S
-): S & PromiseLike<void> =>
-  new Proxy(stream as S & PromiseLike<void>, {
+): S & PromiseLike<S> =>
+  new Proxy(stream as S & PromiseLike<S>, {
     get(target, key) {
       if (key === 'then') {
         return (res: any = noop, rej: any = noop) =>
           new Promise((_res, _rej) =>
             target
-              .once('error', () => _rej(rej()))
-              .once('finish', () => _res(res()))
+              .once('error', (e) => _rej(rej(e)))
+              .once('finish', () => _res(res(target)))
           )
       }
       const value = Reflect.get(target, key)
       if (key === 'pipe' && typeof value === 'function') {
         return function (...args: any) {
-          return promisifyStream(value.apply(target, args) as S)
+          return promisifyStream(value.apply(target, args))
         }
       }
       return value
test/core.test.js
@@ -411,6 +411,7 @@ describe('core', () => {
 
         test('$ > stream', async () => {
           const file = tempfile()
+          const fileStream = fs.createWriteStream(file)
           const p = $`echo "hello"`
             .pipe(
               new Transform({
@@ -419,10 +420,10 @@ describe('core', () => {
                 },
               })
             )
-            .pipe(fs.createWriteStream(file))
+            .pipe(fileStream)
 
           assert.ok(p instanceof WriteStream)
-          assert.equal(await p, undefined)
+          assert.equal(await p, fileStream)
           assert.equal((await fs.readFile(file)).toString(), 'HELLO\n')
           await fs.rm(file)
         })
test-d/core.test-d.ts
@@ -27,7 +27,9 @@ expectType<ProcessPromise>(p.nothrow())
 expectType<ProcessPromise>(p.quiet())
 expectType<ProcessPromise>(p.pipe($`cmd`))
 expectType<ProcessPromise>(p.pipe`cmd`)
-expectType<typeof process.stdout & PromiseLike<void>>(p.pipe(process.stdout))
+expectType<typeof process.stdout & PromiseLike<typeof process.stdout>>(
+  p.pipe(process.stdout)
+)
 expectType<ProcessPromise>(p.stdio('pipe'))
 expectType<ProcessPromise>(p.timeout('1s'))
 expectType<Promise<void>>(p.kill())