Simple tee example

1.7k views Asked by At

Can someone please explain why tee works here:

echo "testtext" | tee file1 > file2

My understanding was that tee duplicates the input and prints 1 to screen.

The above example allows the output from echo to be sent to 2 files, the first redirecting to the second.

I would expect 'testtext' to be printed to screen and passed through file1 and landing in file2. Similar as to how the text in the following example would only end up in file2.

echo "testtext" > file1 > file2

Can anyone explain what i am missing in my understanding?

Edit

Is it because its writing to file and then to stdout which gets redirected?

3

There are 3 answers

0
marbu On

Your description is right: tee receives data from stdin and writes it both into file and stdout. But when you redirect tee's stdout into another file, there is obviously nothing written into terminal because the data ended up inside the second file.

Is it because its writing to file and then to stdout which gets redirected?

Exactly.

What you are trying to do could be done like this (demonstrating how tee works):

$ echo "testtext" | tee file1 | tee file2
testtext

But since tee from gnu coreutils accepts several output files to be specified, one can do just:

$ echo "testtext" | tee file1 file2
testtext

But your idea of passed through file1 and landing in file2 is not correct. Your shell example:

echo "testtext" > file1 > file2

makes the shell open both files file1 and file2 for writing which effectively truncates them and since stdout can be only redirected into another file directly, only the last redirection is effective (as it overrides the previous ones).

0
Jrican On

"is it because its writing to file and then to stdout which gets redirected?" That is correct

tee sends output to the specified file, and to stdout. the last ">" redirects standout to the second file specified.

0
chepner On

tee writes its input to each of the files named in its arguments (it can take more than one) as well as to standard output. The example could also be written

echo "testtext" | tee file1 file2 > /dev/null

where you explicitly write to the two files, then ignore what goes to standard output, rather than redirecting standard output to one of the files.

The > file2 in the command you showed does not somehow "extract" what was written to file1, leaving standard output to be written to the screen. Rather, > file2 instructs the shell to pass a file handle opened on file2 (rather than the terminal) to tee for it to use as standard output.