Git is excellent tool and it offers some amazing options / commands which can make daily work easier. Below I am going to describe some of commands I find useful, some of them and straightforward, some not, but all of them can make git experience better.

Among all git tools, I find git filter-branch strongest and most awesome git command. It can do so much good things. As its names suggest, this git command will “filter” branch. Where is this useful? In all cases where is necessary to filter out some data we do not want to be visible in history, or it ever existed in repository.

Let’s assume there is local repository where are all internal information like hostnames, passwords are present, and at some time point it is decided to make internal repository public.
Logical question would be how to remove internal information from git history / files. Luckily, git filter-branch can be used exactly for that.

Eg. to remove all traces in history of particular hostname and rename files with name of particular hostname, it is possible to do that with below command

$ git filter-branch -f --tree-filter 'find . -type f -name "*" | while read  FNAME; do mv "$FNAME" "${FNAME//}"; done' --tag-name-filter cat -- --all

this will filter out all strings from git history where is present.

Important note, above command will do this on all branches, so if run in some branch different than master, master will be filtered too.

If we wanted first to experiment with git filter-branch on single branch, then that is possible too, instead of –all pass branch name where to do change, eg

$ git filter-branch -f --tree-filter 'find . -type f -name "*" | while read  FNAME; do mv "$FNAME" "${FNAME//}"; done' --tag-name-filter cat -- mybranch

to remove password from history and from files

$ git filter-branch --tree-filter "find . -type f -exec sed -i -e 's/origpass/newpassword/g' {} \;"

To remove remote branch

$ git push origin --delete branchname

push local branch to remote

$ git push -u origin local_branch 

clone remote branch

$ git clone -b branch_name remote_repo

clone remote branch an track it

$ git fetch origin
$ git checkout -b 
$ git branch --set-upstream-to=origin/ 
$ git pull

After this, last updates from remote branch will be reflected to newly created local branch

Check out file from another branch to current branch

$ git checkout branch_name
$ git checkout file_to_check.txt
$ git add file_checked 
$ git commit -s 

rebase last X commits into one commit

$ git rebase -i HEAD~X 

and follow steps in editor. Read carefully!

Sometimes I edit some file, and then I got distracted before committing / pushing stuff to repository, and days / hours later I do not remember exactly what changed, git can help here too, if run git status is output like

$ git status 
On branch master
Your branch is up-to-date with 'origin/master'.
Changes not staged for commit:
  (use "git add ..." to update what will be committed)
  (use "git checkout -- ..." to discard changes in working directory)

    modified:   file.txt

then running,

$ git diff HEAD file.txt 

will show changes between committed version vs staged version.

To see to what branch last commits were sent,

$ git for-each-ref --sort=-committerdate refs/heads/

will list what git branch was updated as last one.

Track remote branch

$ git remote add upstream
$ git remote -v 

In output of git remote -v will be showed what upstream git repository is and ten it can be used to fetch changes which can be merged to local master

$ git fetch upstream 
$ git checkout master 
$ git merge upstream master

#git, #git-branch, #git-filter-branch, #linux

git server setup

In previous post I wrote that memory card in my Raspberry PI died ( more here RaspberryPI machine rebuild ), that meant dns/dncp/iptables/git/squid servers were down. Git server was not critical for my workflow, as I proceed working on stuff but without pushing to git, good thing was I had local repository synced before card died, so was easy to go back.

# aptitude install -y git 
# useradd -m egit 
# su - egit
$ mkdir egit .ssh; cd egit; git init --bare

Added my key ( I do not know more elegant approach for keys than this ), by opening /home/elvir/.ssh/ on client machine ( then one I use for regular work ) and adding and adding it to .ssh/authorised_keys on git server side.
One more thing would be to edit /etc/password and for git user change default shell from /bin/shell to /usr/bin/git-shell. After this, it was easy to push stuff to git server and proceed with usual workflow ( git pull/push/commit… )

#git, #git-server