0

Here's my command:

(time ( \
   time sleep 1; \
   time sleep 2 \
) 2>&1 | tee inner.txt ) 2>&1 | tee outer.txt

cat inner.txt shows:

real    0m1.003s
user    0m0.001s
sys 0m0.002s

real    0m2.003s
user    0m0.001s
sys 0m0.002s

and cat outer.txt shows:

real    0m1.003s
user    0m0.001s
sys 0m0.002s

real    0m2.003s
user    0m0.001s
sys 0m0.002s

real    0m3.068s
user    0m0.005s
sys 0m0.008s

How can I get just this into outer.txt?:

real    0m3.068s
user    0m0.005s
sys 0m0.008s

Even better, how can I get inner.txt, outer.txt, and both.txt, where both.txt would contain:

real    0m1.003s
user    0m0.001s
sys 0m0.002s

real    0m2.003s
user    0m0.001s
sys 0m0.002s

real    0m3.068s
user    0m0.005s
sys 0m0.008s

Note that the time cmd I'm using above is the bash built-in function time, not the /usr/bin/time command, which I learned about through my question here: How to pass optional arguments to time command

I'm on Linux Ubuntu 18.04.

This question is a follow-up to my answer here, in order to try to improve that answer: How to time a multiline, multi-subcommand command in bash, and optionally store all output into a file

1
  • 1
    tee prints to a file and stdout - use output redirection instead in the inner part if you don't want the inner output in outer.txt.
    – Panki
    Apr 21, 2022 at 7:24

1 Answer 1

0

For one, I think your inner tee is feeding the outer, i.e. when that tee prints to its stdout, it's redirected to the outer pipe along with anything else that's output on the outer level. In addition, on my Bash, I had to change the inner parentheses to braces to make it work (I've no idea why).

This seemed to work to get the output to the files (only):

(time { 
         time sleep 1;
         time sleep 2;
      } > inner.txt 2>&1
) > outer.txt 2>&1

To get the output to both the files and the terminal / the script's stdout, you'll need to arrange the inner tee to output "around" the outer one. E.g. save the script's stdout to another free file descriptor and print to that:

exec 3>&1;

(time {
         time sleep 1;
         time sleep 2;
      } 2>&1 | tee inner.txt >&3
) 2>&1 | tee outer.txt >&3

(The >&3 isn't necessary on the outer one, I just did it for symmetry. You could also print directly to the terminal with tee ... >/dev/tty (no need for the exec), but then redirecting or piping the output of the whole script won't work.)

With the above, you could do myscript |tee both.txt to get the three output files.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge that you have read and understand our privacy policy and code of conduct.

Not the answer you're looking for? Browse other questions tagged or ask your own question.