import { combineRaceCancellation , RaceCancellation , throwIfCancelled , } from "race-cancellation" ; import type { ProcessWithWebSocketUrl , SpawnOptions , Stdio } from "../types" ; import execa from "./execa" ; import newProcess from "./newProcess" ; import newWebSocketUrlParser from "./newWebSocketUrlParser" ; export default function newProcessWithWebSocketUrl ( command , args , options , debugCallback ) { const { stdio = "ignore" , cwd , env , extendEnv } = options ; const child = execa ( command , args , { buffer : false , stdio : [ stdio , stdio , "pipe" ] , cwd , extendEnv , env , } , debugCallback ) ; const process = newProcess ( child , command , debugCallback ) ; if ( child . stderr === null ) { throw new Error ( "missing stderr" ) ; } return Object . assign ( process , { url : createUrl ( child . stderr , stdio , process . raceExit ) , } ) ; } function createUrl ( stderr , stdio , raceExit ) { let promise ; return url ; async function url ( raceCancellation ? ) { return throwIfCancelled ( await combineRaceCancellation ( raceExit , raceCancellation ) ( ( ) => { if ( promise === undefined ) { promise = new Promise ( ( resolve ) => parseUrl ( stderr , stdio , resolve ) ) ; } return promise ; } ) ) ; } } function parseUrl ( stderr , stdio , callback ) { const parser = newWebSocketUrlParser ( callback ) ; stderr . pipe ( parser ) ; if ( stdio === "inherit" ) { parser . pipe ( process . stderr ) ; } else if ( stdio === "ignore" ) { parser . on ( "data" , ( ) => void 0 ) ; } else { throw new Error ( `invalid stdio arg ${ String ( stdio ) } expected ignore or inherit` ) ; } }