How to track file creation and modification - linux

We have put together a perl script that essentially looks at the argument that is being passed to it checks if is creating or modifying a file then it saves that in a mysql database so that it is easily accessible later. Here is the interesting part, how do I make this perl script run before all of the commands typed in the terminal. I need to make this dummy proof so people don't forget to run it.
Sorry I didn't formulate this question properly. What I want to do is prepend to each command such that each command will run like so "./run.pl ls" for example. That way I can track file changes if the command is mv or it creates an out file for example. The script pretty much takes care of that but I just don't know how to run it seamlessly to the user.
I am running ubuntu server with the bash terminal.
Thanks

If I understood correctly you need to execute a function before running every command, something similar to preexec and precmd in zsh.
Unfortunately bash doesn't have a native support for this but you can do it using DEBUG trap.
Here is a sample code applying this method.
This page also provide some useful information.

You can modify the ~/.bashrc file and launch your script there. Do note that each user would (and should) still have the privelege to modify this file, potentially removing the script invocation.
The /etc/bash.bashrc file is system-wide and only changeable by root.
These .bashrcs are executed when a new instance of bash is created (e.g. new terminal).
It is not the same as sh, the system shell, that is dash on Ubuntu systems.

Related

log every linux command line ever used?

so, I'm solid on linux basics, and have never written a shell script. But there is something I would like to get, or do.
Would it be possible to have linux log ALL COMMANDS I EVER TYPE in a single file? I.e., every ls -l and cd /this/folder etc., but also the install records I have done and more.
If this file exists great. If there is a persistent file created for EACH session and user, then maybe I can write a script to conjoin the lines. Or, what other options are available?
I'd like the file to have 3 columns, user executing, datetime executed, and copy of the command string. Some kind of results or error if returned would be great. MANY THANKS from a guy who is amazed what Linux is capable of doing!
Assuming you're running bash, look at your ~/.bash_history file.

Bash script ignores arguments when in /bin

I have this bash script that I can pass up to three arguments to. It works like a charm when I call it from the directory ./script -h but when I copy the same file to /bin and call it from anywhere with script -h, it seems to ignore the arguments passed.
Why? or maybe more importantly:
What can I do do change that?
script is a very useful standard utility program which take a copy of your current session (look for a file called typescript). It creates another shell interface, so you probably didn't notice it was running.
When you write a new program, use a naming convention, like script.sh.
Edit:
If you don't like using a file suffix (because it looks too much like Windows) then fine, but use some other naming convention which will ensure your script names do not clash with existing commands. test is another favorite, for example. You can use type to check a command, but that only checks your current environment, you might still have a name collision when running from a different username, for example.

How do I get GNU screen to read .bash_profile/.bash_rc changes?

After I make changes in .bash_rc or .bash_profile, when I start GNU screen, it doesn't recognize those changes.
I can
source ~/.bash_profile
and it works for the current screen window I have open, but I have to do that for every screen window I have open.
How do I get screen to read my latest changes in my bash configuration?
If you want screen to always treat your shell as a login shell, and source the same files that would be read if just started a new shell normally, add the following to ~/.screenrc (or maybe ~/.byobu/.screenrc, as pointed out in the comment):
shell -$SHELL
This way, you don't need to manually tell it to source your files each time you start a new screen. Though you would have to if you just made changes and wanted those changes to be reflected in your current screen.
The documentation for this (and lots of other screen details) can be found here. Basically, shell is a command to screen telling it to run the following when it needs to create a new shell. $SHELL is the usual variable holding the path to your preferred shell. And the dash - in front of $SHELL indicates that it should be run as a login shell (which will typically mean it sources your ~/.bash_profile, etc.).
It's worth pointing out, however, that screen defaults to just inheriting most environment variables from the shell where you start screen; and a login sub-shell may alter some environment variables in unexpected ways. I ran into a situation where elements of my $PATH were basically permuted. I solved the problem thanks to this particularly excellent answer on superuser.
You may notice the source command available. It's important to note that this sources a file of screen commands, rather than shell commands. Other relevant (screen) commands include eval and exec.
You have to do it in each screen that you have open since they are all different shells. If you need the change every time a new shell is opened, I suggest you put the changes in ~/.bashrc instead.
Apparently, you can send a command to all windows at once using this syntax:
C-a :
at "#" stuff "source ~/.bash_profile^M"

Launch multiple scripted screen sessions from another script

I've written a script (that doesn't work) that looks something like this:
#!/bin/sh
screen -dmS "somename" $HOME/somescript.sh
j=13
for i in {0..5}; do
screen -dmS "name$i" $HOME/anotherscript.sh $i $j
j=10
done
If I copy and paste this into a terminal, it creates 7 detached screen sessions, as I expect. If I run it from within a script, however, I get only the first session, "somename," when I run screen -ls.
I realize screen can be used to create multiple windows within one session. It doesn't really matter to me how these scripts get run. I just want to get to the bottom of why this doesn't work as a script.
Note: I've asked this question on SuperUser without any suitable responses. I figured maybe that's the wrong place to ask what could be considered a programming question.
One thing you might be getting bitten on is which specific version of which specific shell you're running. /bin/sh could actually be bash, or it could be bourne, and that can make a difference on how your loop syntax is interpreted. The {0..5} construct isn't understood in older versions of bash (v2.x), for instance, nor in bourne (at least it wasn't when I finally managed to track down a /bin/sh that was a real, live bourne shell :-).
My suggestion is to change your shebang line to /bin/bash if you need its syntax, and check that your bash is version 3.x or later. Since you say it works from the commandline, my bet is on the shebang line, though.

When executing a shell script in Ubuntu (or any unix-type enviro) how can I persist exports outside of the script?

I'm new to Linux and especially to Ubuntu 11 which I'm just trying today for the first time. I need Linux for some development which requires a Linux-based emulator, so I'm trying to write a shell script that sets up my dev environment.
Now I've created a .scripts folder in my home dir and added it to my path by exporting it in .bashrc so every time I start a new terminal instance, I can execute any custom scripts I drop in there.
Now one (three actually) of those scripts sets up all my dev-related paths, exports, as well as a cd command which switches to the appropriate folder for this dev. However (again forgive me if you already know this...) the script runs in its own 'session' (for lack of a better word) so although the enviro-vars and such are all set up and do execute (as was proven by embedding echo calls throughout) when the script finishes and I'm returned back to the terminal where I executed the script, that other session no longer exists and with the exception of clearing the screen and echoing output, there's nothing else showing the script ever ran.
Now I'm not sure its even possible to extend exported variables outside of that script back to the calling 'instance' or of there's some kind of flag I can set to execute the script in the existing session, so I'm stumped.
Now if that is not possible, is it at least possible to write a script or set up an icon that can launch a new terminal window, then execute the script but leaving the window open and initialized?
Thanks!
Mark
Put the script in a function definition in ~/.bashrc. For example
enter_dev_env() {
cd /home/foo/src
export foo="bar"
}
Run the command with source.
source foo.sh

Resources