X-Git-Url: https://gerrit.automotivelinux.org/gerrit/gitweb?a=blobdiff_plain;ds=inline;f=lib%2Fcommon%2FexecPipeWs.go;h=9bb45174f6ec2f62d5c61f9c4686682b6c7bc6d5;hb=ef33f263156fedd0907c45b033dee569f56f9ec8;hp=3b63cdc4db614157185bf3753099ce73d92af190;hpb=ec7051e1da665206f594c7616ad381bfeaea333a;p=src%2Fxds%2Fxds-server.git diff --git a/lib/common/execPipeWs.go b/lib/common/execPipeWs.go index 3b63cdc..9bb4517 100644 --- a/lib/common/execPipeWs.go +++ b/lib/common/execPipeWs.go @@ -5,6 +5,7 @@ import ( "fmt" "io" "os" + "strings" "time" "syscall" @@ -14,17 +15,17 @@ import ( ) // EmitOutputCB is the function callback used to emit data -type EmitOutputCB func(sid string, cmdID int, stdout, stderr string) +type EmitOutputCB func(sid string, cmdID int, stdout, stderr string, data *map[string]interface{}) // EmitExitCB is the function callback used to emit exit proc code -type EmitExitCB func(sid string, cmdID int, code int, err error) +type EmitExitCB func(sid string, cmdID int, code int, err error, data *map[string]interface{}) // Inspired by : // https://github.com/gorilla/websocket/blob/master/examples/command/main.go // ExecPipeWs executes a command and redirect stdout/stderr into a WebSocket -func ExecPipeWs(cmd string, so *socketio.Socket, sid string, cmdID int, - cmdExecTimeout int, log *logrus.Logger, eoCB EmitOutputCB, eeCB EmitExitCB) error { +func ExecPipeWs(cmd []string, env []string, so *socketio.Socket, sid string, cmdID int, + cmdExecTimeout int, log *logrus.Logger, eoCB EmitOutputCB, eeCB EmitExitCB, data *map[string]interface{}) error { outr, outw, err := os.Pipe() if err != nil { @@ -39,9 +40,10 @@ func ExecPipeWs(cmd string, so *socketio.Socket, sid string, cmdID int, return fmt.Errorf("Pipe stdin error: " + err.Error()) } - bashArgs := []string{"/bin/bash", "-c", cmd} + bashArgs := []string{"/bin/bash", "-c", strings.Join(cmd, " ")} proc, err := os.StartProcess("/bin/bash", bashArgs, &os.ProcAttr{ Files: []*os.File{inr, outw, outw}, + Env: append(os.Environ(), env...), }) if err != nil { outr.Close() @@ -58,10 +60,10 @@ func ExecPipeWs(cmd string, so *socketio.Socket, sid string, cmdID int, defer inw.Close() stdoutDone := make(chan struct{}) - go cmdPumpStdout(so, outr, stdoutDone, sid, cmdID, log, eoCB) + go cmdPumpStdout(so, outr, stdoutDone, sid, cmdID, log, eoCB, data) // Blocking function that poll input or wait for end of process - cmdPumpStdin(so, inw, proc, sid, cmdID, cmdExecTimeout, log, eeCB) + cmdPumpStdin(so, inw, proc, sid, cmdID, cmdExecTimeout, log, eeCB, data) // Some commands will exit when stdin is closed. inw.Close() @@ -92,7 +94,8 @@ func ExecPipeWs(cmd string, so *socketio.Socket, sid string, cmdID int, } func cmdPumpStdin(so *socketio.Socket, w io.Writer, proc *os.Process, - sid string, cmdID int, tmo int, log *logrus.Logger, exitFuncCB EmitExitCB) { + sid string, cmdID int, tmo int, log *logrus.Logger, exitFuncCB EmitExitCB, + data *map[string]interface{}) { /* XXX - code to add to support stdin through WS for { _, message, err := so. ?? ReadMessage() @@ -125,21 +128,21 @@ func cmdPumpStdin(so *socketio.Socket, w io.Writer, proc *os.Process, // Wait cmd complete select { case dC := <-done: - exitFuncCB(sid, cmdID, dC.status, dC.err) + exitFuncCB(sid, cmdID, dC.status, dC.err, data) case <-time.After(time.Duration(tmo) * time.Second): exitFuncCB(sid, cmdID, -99, - fmt.Errorf("Exit Timeout for command ID %v", cmdID)) + fmt.Errorf("Exit Timeout for command ID %v", cmdID), data) } } func cmdPumpStdout(so *socketio.Socket, r io.Reader, done chan struct{}, - sid string, cmdID int, log *logrus.Logger, emitFuncCB EmitOutputCB) { + sid string, cmdID int, log *logrus.Logger, emitFuncCB EmitOutputCB, data *map[string]interface{}) { defer func() { }() sc := bufio.NewScanner(r) for sc.Scan() { - emitFuncCB(sid, cmdID, string(sc.Bytes()), "") + emitFuncCB(sid, cmdID, string(sc.Bytes()), "", data) } if sc.Err() != nil { log.Errorln("scan:", sc.Err())