bashshellcsvawktop-command

Add timestamp to the end of each line of a CSV file


I am trying to get the first 5 lines of top command using shell script. Here is the output of my shell script.

PID,USER,PR,NI,VIRT,RES,SHR,S,%CPU,%MEM,TIME+,COMMAND
3983,arun,20,0,1874616,500356,24132,R,47.6,10.3,53:19.92,gnome-shell
11,root,20,0,0,0,0,R,4.8,0.0,0:22.51,rcuos/0
2016,root,20,0,219396,44408,9120,S,4.8,0.9,9:53.96,Xorg
12081,arun,20,0,2689552,304132,7076,S,4.8,6.3,13:36.17,java
1,root,20,0,141660,5336,2940,S,0.0,0.1,0:08.40,systemd
3983,arun,20,0,1874616,500356,24132,R,56.2,10.3,53:20.99,gnome-shell
2016,root,20,0,219396,44408,9120,R,18.8,0.9,9:54.17,Xorg
4969,arun,20,0,1287084,162948,48472,S,12.5,3.4,5:39.99,chrome
16108,arun,20,0,130020,1692,1172,R,6.2,0.0,0:00.01,top
1,root,20,0,141660,5336,2940,S,0.0,0.1,0:08.40,systemd
3983,arun,20,0,1874616,500356,24132,R,43.8,10.3,53:24.56,gnome-shell
4969,arun,20,0,1275992,147104,32424,S,37.5,3.0,5:41.10,chrome
1,root,20,0,141660,5336,2940,S,0.0,0.1,0:08.40,systemd
2,root,20,0,0,0,0,S,0.0,0.0,0:00.06,kthreadd
3,root,20,0,0,0,0,S,0.0,0.0,0:04.93,ksoftirqd/0

Here is my shell script top.sh

 #!/bin/bash
echo "started.."
top -b -n 3 | sed -n '7,1{s/^ *//;s/ *$//;s/  */,/gp;};12q' >> out.txt

while [ true ]; do
  sleep 5
  echo "inside loop.."
  top -b -n 3 | sed -n '8,12{s/^ *//;s/ *$//;s/  */,/gp;};12q' >> out.txt
done

Now , I need to add timestamp at the end of each lines . I have tried to do the same using awk command , But it didn't work for me ! I have edited my code like this -

#!/bin/bash
    echo "started.."
    t= =$(date +"%T")

    top -b -n 3 | sed -n '7,1{s/^ *//;s/ *$//;s/  */,/gp;};12q' >> out.txt
    awk -F, '{$(NF+1)="TIME";}1' OFS=, out.txt    

    while [ true ]; do
      sleep 5
      t=$(date +"%T")
      echo "inside loop.."
      top -b -n 3 | sed -n '8,12{s/^ *//;s/ *$//;s/  */,/gp;};12q' >> out.txt
      awk -F, '{$(NF+1)=$t;}1' OFS=, file
    done

Solution

  • Your Awk commands would run over the entire file (or an entire unrelated or unexistent file in the second instance) and print to standard output. Fixing the command to overwrite the input file would add time stamps to lines which already have them. You want to inline the datestamp addition to the command which appends new data to the file, instead of adding more datestamps to the entire file, anyway.

    The sed script already performs a number of substitutions. It's simple to factor in the timestamp as well. You'll need to use double quotes instead of single in order for the shell to expand the value of the variable.

    #!/bin/bash
    
    t=$(date +"%T")   #### Syntax error fixed
    top -b -n 3 |
    sed -n -e '7!b;s/^ *//' -e "s/ *$/,$t/" -e 's/  */,/gp;q' >> out.txt
    #### ^sed script refactored; only work on line 7, not until 12
    
    while true; do   #### Wacky syntax fixed
      sleep 5
      t=$(date +"%T")
      top -b -n 3 |
      sed -n -e '8,12{s/^ *//' -e "s/ *$/,$t/" -e 's/  */,/gp;};12q' >> out.txt
    done