Advanced Git Tricks

Tue 28 August 2012
By balrok

A compilation of git commandos which are only needed once in a while.

Rewrite Author in history

Taken from here:

git filter-branch -f --commit-filter  '
        if [ "$GIT_COMMITTER_NAME" = "XX" ];
        then
                GIT_COMMITTER_NAME="XX";
                GIT_AUTHOR_NAME="XX";
                GIT_COMMITTER_EMAIL="XX";
                GIT_AUTHOR_EMAIL="XX";
                git commit-tree "$@";
        else
                git commit-tree "$@";
        fi' HEAD

Note: this changes the history and you might need to force-push and bring lots of troubles to other ;)

gitconfig

Some things for gitconfig:

[alias]
    st = status
    ci = commit
    br = branch
    co = checkout
    cp = cherry-pick
    df = diff
    lg = log -p
    los = log --graph --decorate --pretty=oneline --abbrev-commit --format='format:%Cred%h%Creset(%Cblue%an%Creset)%Cgreen%ad%Creset %s' --date=short --stat=200,200

Those are abbreviations for common used methods + "los" which is a nicer log.. It will print everything in pretty colors + adds full filenames like in the image.

Don't track changes in a file

For example if the project tracks the config file and you need to change the password without committing it or some crude rules in .htaccess force you to do local modifications without committing the following can be used:

git filter-branch -f --commit-filter  '
        if [ "$GIT_COMMITTER_NAME" = "XX" ];
        then
                GIT_COMMITTER_NAME="XX";
                GIT_AUTHOR_NAME="XX";
                GIT_COMMITTER_EMAIL="XX";
                GIT_AUTHOR_EMAIL="XX";
                git commit-tree "$@";
        else
                git commit-tree "$@";
        fi' HEAD

The first line will ignore all current changes inside the file.. Warning the checkout -f will still remove the hidden changes. While for example git reset HEAD\~1 doesn't touch the file.

Auto publish with every push

This is extremely useful for web development.. Instead of changing code, committing and uploading via ftp you just can push and everything will be visible right after that.

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
#!/bin/bash

PROJECTNAME="reponame"
PUBLISHPLACE="/var/www/example.com"

mkdir $PROJECTNAME.git
cd $PROJECTNAME.git
git init --bare
git config core.worktree $PUBLISHPLACE
git config core.bare false
git config receive.denycurrentbranch ignore
echo "#!/bin/sh
git checkout -f" > hooks/post-receive

chmod +x hooks/post-receive

What the script does: it creates a new repo and adds a post-receive hook which publishes to the publish-space.. Now your local git repo just needs:

git remote add web ssh://yourname@example.com/home/example/reponame.git

and you can git push web master

Convert Git Repo to SVN

There aren't much articles about it (just this one here) So I post the script I used to convert a \~1000 commits single-branch git repo into a SVN repo:

#0. setup the svn
svn checkout --username=".." --password=".." https://...
cd svnRepo
svn mkdir trunk
svn mkdir branches
svn mkdir tags
svn commit
#1. clone the svn repo over your existing .git repo (I made a backup before but shouldn't make problems)
git svn clone --username=".." --password=".." https://... --trunk=trunk --branches=branches --tags=tags MY_EXISTING_LOKAL_REPO
#2. rebase your current branch over that from svn
git checkout master
git rebase remotes/trunk
#3. commit your code into svn
git svn dcommit

Of course be careful with this script since SVN and balrok are both evil and may harm your existing code base.. So do a backup beforehand ;)

Commentaires: