Git for Victims of Subversion
Initializing new projects
| Git | SVN |
|---|---|
git init git add . git commit |
svnadmin create repo svn import file://repo svn checkout file://repo . or svnadmin create repo svn checkout repo . svn add . svn commit |
Browsing repository
| Git | SVN |
|---|---|
git show rev:file git show rev:directory git show rev |
svn cat file svn list directory svn log -rrev url svn diff -crev url |
Exporting
| Git | SVN |
|---|---|
git archive git archive --format=zip HEAD > project.zip |
svn export |
Basic Commands
| Git | SVN |
|---|---|
git add file git rm file git mv file |
svn add file svn rm file svn mv file |
Committing
| Git | SVN |
|---|---|
git commit -a git commit (without -a) will NOT add all added files!!! Have a look at git commit -a -v |
svn commit |
Exercise
- sudo mkdir /rcs
- sudo chmod 777 /rcs
- mkdir /rcs/repo
- cd /rcs/repo
- echo first line > afile.txt
- mkdir afolder
- Initialize repository
- Add all files to the repository
- Check whether files have been added
- Commit the changes
- Check whether the files have been committed
- What is the SHA1 of the commit?
Tracking Changes
| Git | SVN |
|---|---|
git diff git diff rev path git apply git status git show |
svn diff | less svn diff -rrev path patch -p0 svn status |
Reverting
| Git | SVN |
|---|---|
git checkout path Removes all local changes!!! |
svn revert path |
Working with SVN (git svn)
Create SVN repo
mkdir svn; cd svn svnadmin create ./ svn mkdir file:///rcs/svn/afolder svn import /etc/passwd file:///rcs/svn/passwod
Check it out with git
mkdir gitsvnwc git svn clone file:///rcs/svn gitsvnwc/
Updating (git svn)
| Pull changes from SVN | Push changes to SVN |
|---|---|
Make some changes to the SVN repo
svn import /etc/resolv.conf file:///rcs/svn/resolv.conf Update git working copy git svn rebase |
echo aline > afile.txt git add afile.txt git commit git svn dcommit svn ls file:///rcs/svn |
git svn limitations
- Some of the Git features do not work in SVN
- Do not dcommit Git merge commits to the Subversion repository (i.e., no merging from other branches, just rebasing)
- Do not amend, reorder, or otherwise change commits that have been dcommited to Subversion (same as to the central git repo). Subversion cannot handle modifying or reordering commits.
Exercises
SVN to GIT
1. Server and repos preparations:
## svn part
sudo mkdir /rcs
sudo chmod 777 /rcs
cd /rcs
mkdir svn; cd svn
svnadmin create ./
svn mkdir file:///rcs/svn/trunk
svn mkdir file:///rcs/svn/branches
svn mkdir file:///rcs/svn/tags
svn import ~/slideshow_ file:///rcs/svn/trunk
svn copy file:///rcs/svn/trunk file:///rcs/svn/branches/slbr1 -m "New branch"
svn copy file:///rcs/svn/trunk file:///rcs/svn/tags/v1.0 -m "Tagging first stable version"
# new user-devel
sudo adduser geek
sudo usermod -G osboxes -a geek
su geek
cd
svn checkout file:///rcs/svn/trunk ~/wc1svn
cd ~/wc1svn
echo geek > logo.html
svn ci -m "geek change"
svn st -uv
exit
2. Simple migration without: history, branches and tags
cd
mkdir gitsvnwc
git svn clone file:///rcs/svn gitsvnwc/
cd gitsvnwc
git svn log
git log
rm -Rf .git branches tags
cd trunk
git init
git add .
git commit -m "moved from svn without history, etc"
git clone --bare . ~/repos/newslideshow.git
3. Migration with nicer history and users' credentials
cd
mkdir gitsvnwc1
git svn clone file:///rcs/svn gitsvnwc1/
cd gitsvnwc1
touch users.txt
nano users.txt
####
osboxes = Ms Devel <msdevel@gmail.com>
geek = Geek Geekovsky <gg@gmail.com>
####
cd
svn checkout file:///rcs/svn/trunk ~/wc2svn
cd ~/wc2svn
svn log --xml --quiet | grep author | sort -u | perl -pe 's/.*>(.*?)<.*/$1 = /' > users1.txt
nano users1.txt
...
cd ~/gitsvnwc1
git svn clone file:///rcs/svn/ --authors-file=/home/osboxes/gitsvnwc1/users.txt --no-metadata --prefix "" -s ~/slideshow_nice
cd ~/slideshow_nice
git log
git tag
git branch -a
# migrating tags:
# for t in $(git for-each-ref --format='%(refname:short)' refs/remotes/tags); do git tag ${t/tags\//} $t && git branch -D -r $t; done
# migrating branches:
# for b in $(git for-each-ref --format='%(refname:short)' refs/remotes); do git branch $b refs/remotes/$b && git branch -D -r $b; done
# cleaning:
# git branch -d trunk
# Connecting to new remote git server:
# git clone --bare ~/slideshow ~/repos/slideshowclean.git
# git remote add origin ~/repos/slideshowclean.git
# Pushing to repo
# git push origin --all
# git push origin --tags
4. Working with 'git svn' bridge tool
(https://training-course-material.com/training/Git_for_Victims_of_Subversion)
5. Refusing force-pushes, etc
git config --system receive.denyNonFastForwards true
Workaround for user: delete the branch and then push it back up with the new reference
Solution for admins:
git config --system receive.denyDeletes true
6. Blocking edition of files for specific users, etc
(https://git-scm.com/book/en/v2/Customizing-Git-An-Example-Git-Enforced-Policy)