Bash – How to log every command typed into bash and every file operation

bashlogs

I would like to log every command typed into bash (by either root or user) as well as every file operation.

The idea is that I could write tools that could interrogate this log file and provide very useful information.

For example it would be great to list all commands ever typed, one per line, with "- – -" for 8-24h time gap and "= = = e.g. 24 June 2014 = = =" for >24h gap. If it also eliminated duplicates within a "= = =…" session even better!

That would mean that whenever I accomplish some task such as "upgrade flask/mod_wsgi/apache to Python 3.x" a record is left behind, a trail I can pick up if I have to do the same thing six months later.

To the same end it would be very nice to see what file system changes occurred after installing a particular package. That would let me know where the config files got put.

PS I'm on Ubuntu 14.04

Best Answer

This is not as comprehensive as real accounting, and it can be undone easily by a user, but assuming it doesn't have to be a real accounting system and that both BASH and rsyslog are in use, edit the system-wide BASH RC file:

sudo -e /etc/bash.bashrc

Append to the end of that file:

export PROMPT_COMMAND='RET_VAL=$?;logger -p local6.debug "$(whoami) [$$]: $(history 1 | sed "s/^[ ]*[0-9]\+[ ]*//" ) [$RET_VAL]"'

Above, logger records the time, user, command, and command return value. Set up logging for "local6" with a new file:

sudo -e /etc/rsyslog.d/bash.conf

And the contents...

local6.*    /var/log/bash_commands.log

Restart rsyslog:

sudo service rsyslog restart

Log out. Log in. Log rotation:

sudo -e /etc/logrotate.d/rsyslog

There is a list of log files to rotate the same way...

/var/log/mail.warn
/var/log/mail.err
[...]
/var/log/message

Add the new bash-commands log file in that list:

/var/log/bash_commands.log

Save and restart/reload rsyslog. (The rotation will eventually overwrite log files, so more thought or configuration may be needed.)

To see all the files that a package has installed:

dpkg-query -L [package_name]

So you could execute something like that when you install software.

dpkg-query -L abc-package > /var/log/files_abc-package.log
Related Question