Reputation: 20818
I have a command to which I send data through Stdin and expect 28 output streams (including Stdout
).
So I wanted to use the cmd.ExtraFiles
field with an os.Pipe
for each of the os.ExtraFiles
.
I wrote the following:
backgroundContext, cancelCommand := context.WithCancel(context.Background())
cmd := exec.CommandContext(backgroundContext, "command", args...)
cmd.ExtraFiles = make([]*io.File, 27, 0)
var outputPipe io.ReadCloser
var inputPipe io.WriteCloser
outputPipe, inputPipe, err = os.Pipe()
cmd.ExtraFiles[0] = &inputPipe
cmd.ExtraFiles[1] = &outputPipe
The last two lines generate an error since the types do not match:
./main.go:876:26: cannot use &inputPipe (type *io.WriteCloser) as type *os.File in assignment
./main.go:877:26: cannot use &outputPipe (type *io.ReadCloser) as type *os.File in assignment
I'm sure we can assign pipes since I can for example use the StdoutPipe()
function and it works as expected.
How am I supposed to do that with the os.ExtraFiles
?
Upvotes: 1
Views: 164
Reputation: 121139
The code in the question does not compile because the *os.File
values returned from os.Pipe are stored in variables with interfaces types io.ReadCloser
and io.WriteCloser
. Pointers to values with these types are not assignable to an *os.File
.
Fix by assigning the return values to variables with type *os.File
.
cmd.ExtraFiles = make([]*os.File, 27)
outputPipe, inputPipe, err := os.Pipe()
if err != nil {
// handle error
}
cmd.ExtraFiles[0] = inputPipe
cmd.ExtraFiles[1] = outputPipe
Bonus fixes:
os.File
, not io.File
.Upvotes: 1