Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

bash: how to intercept every command

Tags:

bash

Is there a way to intercept every command given to bash? I can intercept a particular command, e.g., cd by defining a function cd() and I can do that for one-command-at-a-time for other commands as well. But can I write a function which gets called before every command is executed? I want to do some bookkeeping of commands, and then executed the command.

Michał Šrajer's idea PS4='$(echo $(date) $(history 1) >> /tmp/trace.txt) TRACE: ' looks very promising but here is the output I get:

$ ping www.google.com
 TRACE: ping www.google.com
PING www.l.google.com (74.125.224.52) 56(84) bytes of data.
64 bytes from 74.125.224.52: icmp_seq=1 ttl=56 time=3.77 ms
64 bytes from 74.125.224.52: icmp_seq=2 ttl=56 time=2.33 ms
^C
--- www.l.google.com ping statistics ---
2 packets transmitted, 2 received, 0% packet loss, time 1001ms
rtt min/avg/max/mdev = 2.334/3.054/3.774/0.720 ms
  TRACE: echo -ne '\033]0;myhost.com /home/yogeshwer/github/myproject\007'
  TRACE: grep -e '\* '
  TRACE: git branch
  TRACE: sed 's/^..\(.*\)/ {\1}/'

And Wed Aug 3 12:47:27 PDT 2011 6672 ping www.google.com get written in /tmp/trace.txt exactly 5 times. The four other ones comes from my definition of PS1 where I run the following command: $(git branch 2> /dev/null | grep -e "\* " | sed "s/^..\(.*\)/ {\1}/"). Two questions:

  • Is it possible to write the command to /tmp/trace.txt exactly?
  • And more importantly, is it possible to not clutter the output of the command, but only write the command to /tmp/trace.txt?

I am so excited about the possibility of being able to record commands from all my bash sessions in one place!

like image 316
Yogeshwer Sharma Avatar asked Aug 03 '11 17:08

Yogeshwer Sharma


People also ask

What is $() in bash?

$() means: "first evaluate this, and then evaluate the rest of the line". Ex : echo $(pwd)/myFile.txt. will be interpreted as echo /my/path/myFile.txt. On the other hand ${} expands a variable.

What does $_ mean in bash?

$_ (dollar underscore) is another special bash parameter and used to reference the absolute file name of the shell or bash script which is being executed as specified in the argument list. This bash parameter is also used to hold the name of mail file while checking emails. $@

What is a bash trap?

A built-in bash command that is used to execute a command when the shell receives any signal is called `trap`. When any event occurs then bash sends the notification by any signal. Many signals are available in bash. The most common signal of bash is SIGINT (Signal Interrupt).

How break multiple lines in Linux?

To split long commands into readable commands that span multiple lines, we need to use the backslash character (\). The backslash character instructs bash to read the commands that follow line by line until it encounters an EOL.


1 Answers

You can set the PS4 variable, which is evaluated for every command being executed just before the execution if trace is on:

PS4='$(echo $(date) $(history 1) >> /tmp/trace.txt) TRACE: '

Then, enable trace:

set -x

To stop tracing, just:

set +x
like image 141
Michał Šrajer Avatar answered Oct 11 '22 14:10

Michał Šrajer