Thursday, 9 September 2010

Quick Tip: PUT - scp files from remote machine to local machine

It is often desirable to have a quick look at a file on a remote machine, such as an HPC cluster, on your desktop machine. I use MacFUSE and SSHFS for this but sometimes I like to move a file without finding my current location in a finder windows. I have written a quick wrapper around scp with a line to determine the IP address of my local machine, stored as an environment variable.

Add the following lines to your .bashrc on the remote machine.


export DESKTOP=$(last -100 |grep $(whoami) |head -n 1 |perl -ane 'print $F[2]')
put(){
if [ -z "$1" ]; then
    echo "put - Sends specified files to Desktop of local machine";
    echo "usage: put filesToSend";
else
find "$*" |xargs -I % scp % $DESKTOP:~/Desktop
fi
}

Then reload the file with source .bashrc. You should now be able to type put fileName, and the file will appear on your desktop. As long as you have your rsa keys set up, otherwise it will ask for a password too. It works for multiple files too, such as *.png. 

I find it useful for quickly viewing pdfs and images. 

Wednesday, 8 September 2010

My very quick guide to Screen.

Intro:
Due to lots of power outages today I thought I should resurrect by usage of screen, which I have neglected recently.

It is difficult to explain what screen is, much easier to say what it does, or at least what I use it for. Screen allows you to resume an interactive terminal session, from any other machine. For example I ssh from ym desktop machine into our cluster then run R interactively, but if my local machine dies or I accidentally close the terminal window that session ends and I loose everything. However, if I use screen I can resume it. Better still I can go home VPN into work and resume the same session on my laptop. It is ideally for running long interactive jobs, without having to leave my desktop machine on overnight. I could also run screen on my desktop machine, log into the cluster, then ssh into my desktop from another machine and I can resume the session, getting straight into the cluster.
There are lots of features which are explained elsewhere, but I will detail how I use it and give my config files in case they are useful to anyone else.

Basic usage:
It really couldn't be simpler to get started, just type screen. Nothing much will change, you are still at the terminal, and can do everything as normal, but now you can detach this session and resume at on another machine if you want to, or shut down your desktop and resume when you come back. To resume you just need to do screen -r. 


Another great feature is having multiple screens, which is a bit like having a tabbed terminal window. So you can edit a file in one window, then quickly switch to the other one to run it. The Ctrl-z Ctrl-z command does this very quickly, see below. You can also split the screen, so you can edit at the top, run at the bottom, or maybe monitor something on the top while working on the bottom. Very nice. 


Config:
I use emacs a lot, so the default screen key of Ctrl-a is a bit of a pain as that means move to the start of the line in emacs, something I do a lot. So I have re-mapped my screen key to Ctrl-z, though you can do anything. I have also made a few other changes to my .screenrc


I also added the following lines to my .bashrc to stop screen Woofing at me. Yes, Woofing. 



### http://benmabey.com/2007/12/13/wuff-wuff.html
alias screen='TERM=screen screen'



Basic Keys:
Ctrl-z Ctrl-c : Create a new window
Ctrl-z " : Show a list of windows
Ctrl-z 0
.. : Switch to window x
Ctrl-z 9
Ctrl-z Ctrl-z : Toggle to previous window
Ctrl-z A : Name the current Window

Ctrl-z S : Split the window horizontally
Ctrl-z TAB : Move focus to other section of split screen
Ctrl-z Q : Remove all but current section

You can view all the default command by doing a Ctrl-z ? within screen, or using Google.

There is a lot more to screen than that, and maybe one day I will go into some of the most advanced features.

Monday, 5 July 2010

BASH: Per directory BASH history

A while ago I found this post, describing how to have a per directory bash history. I have been meaning to implement this for a while and today managed to.

It enables each directory to have a separate searchable bash history file. So simply by changing into a directory you can view what you did in there. I think this will be useful backup for remembering what commands I used and for editing to make scripts etc.

I have also added an hgrep command, to search all of the history files as I can imagine I will forget which directory I was in when I did something I want to do again. I have not decided wether this grep function should return the directory where the command was run or not. I will see after using it for a while.

If you would like to implement this, add the following code to your .bashrc file


hgrep (){ find ~/.dir_bash_history/ -type f|xargs grep -h $*;}


# Usage: mycd
# Replacement for builtin 'cd', wh ich keeps a separate bash-history
# for every directory.
shopt -s histappend
alias cd="mycd"
export HISTFILE="$HOME/.dir_bash_history$PWD/bash_history.txt"

function mycd()
{
history -w # write current history file
builtin cd "$@" # do actual c d
local HISTDIR="$HOME/.dir_bash_history$PWD" # use& nbsp;nested folders for history
if [ ! -d "$HISTDIR" ]; then # create folder if neede d
mkdir -p "$HISTDIR"
fi
export HISTFILE="$HISTDIR/bash_history.txt" # set& nbsp;new history file
history -c # clear memory
history -r #read from current histfile
}


The top line is my hgrep function, remove the -h if you want to see which directory each of the returned history items was run in. The rest should be transparent, just cd as normal and a new history file will be created.

Monday, 21 June 2010

googleCL - Command Line Access to the cloud

I have just installed googleCL and am blogging this from the command line. There are some really nice features that will be really useful to integrate into other scripts. For example adding calendar appointments or getting contacts e-mail addresses all at the command line. I have not explored all the features yet, but it looks like it will be really useful. I can't wait for access to Tasks which is the feature I really want.

Friday, 18 June 2010

R: Command Line Calculator using Rscript

I currently use an awesome little bash trick to get a command line calculator that was posted on lifehacker, and that I blogged about previously.

calc(){ awk "BEGIN{ print $* }" ;}
You just add this to your .bashrc file and then you can use it just like calc 2+2. 


This is really useful, however I recently stumbled upon Rscript. This comes with the standard R install and allows you to make a scripts similar to perl or bash with the shebang #!/usr/bin/Rscript, or wherever your Rscript is (you can check with a whereis Rscript command). The nice thing is that it also has a -e option for evaluating an expression at the command line, just like the perl -e for perl one liners. For example:


Rscript -e "round(runif(10,1,100),0)"


[1] 17 23 21 36 10 47 90 81 83  5


This gives you 10 random numbers uniformly distributed between 1 and 100. You can use any R functions this way, even plot for making figures.

Anyway, it seemed that Rscript would be really useful as a command line calculator too. So after a bit of playing and Googling I adapted a nice alias found in a comment on this blog post. Here it is :

alias Calc='Rscript -e "cat( file=stdout(), eval( parse( text=paste( commandArgs(TRUE), collapse=\"\"))),\"\n\")"'

So now you can type things like Calc "-log10(0.05)", whereas my above mentioned calc would just stare at me blinking, looking a bit embarrassed. You can really go to town if you like:


Calc "round(log2(sqrt(100)/exp(0.05)*(1/factorial(10))),2)"
Calc "plot(hist(rnorm(1E6),br=100))" 
I think I will probably keep the calc version too as it is a bit quicker, with it's lower overhead, but Calc should be useful for more complex things too.

Friday, 14 May 2010

Bash: Remove spaces from filename

Some people use spaces in file names, silly I know. Remove them!
find .|while read file;do mv "${file}" $(echo "${file}" | perl -ne 's/ /_/g;print;');done

Tuesday, 11 May 2010

Bash: mkcd - mkdir and cd

I found the useful hint here to create a new bash command which both recursively creates a directory and changes into that directory. Just add this line to your .bashrc file.

mkcd (){ mkdir -p "$*";cd "$*";}

It supports spaces in directory names, however I do not! It is evil.

I am sure if I ever remember to use it, this will save literally tens of key strokes each day. Now that is efficiency.