Search code examples
bashstdoutstderrtee

Inside a bash script STDOUT to LOG, STDERR to LOG and console


I have a bash script and want to write

  • STDOUT to a log file only (not to the console)
  • STDERR to the same log file and to the console

I tried

#!/bin/bash

main() {
        echo "HELLO"
        >&2 echo "ERROR"
}

LOGFILE=/tmp/mylog.log
main 1>>$LOGFILE 2>(tee -a $LOGFILE)

HELLO goes to the log file and ERROR just goes to the console.

What am I doing wrong?


Solution

  • You may use this script:

    #!/usr/bin/env bash
    
    logfile='/tmp/mylog.log'
    
    # open fd=3 redirecting to 1 (stdout)
    exec 3>&1
    
    # redirect stdout/stderr to a file but show stderr on terminal
    exec >"$logfile" 2> >(tee >(cat >&3))
    
    #exec 1>"$logfile" 2> >(tee -a "$logfile") 
    
    main() {
       echo "HELLO"
       echo "ERROR" >&2
    }
    
    main
    
    # close fd=3
    exec 3>&-
    

    It will write ERROR on your terminal but both HELLO and ERROR to $logfile.