Re: [ANNOUNCE] git-as-svn: subversion frontend server for git repository
From: Marat Radchenko <hidden>
Date: 2016-06-15 23:02:28
On Tue, Sep 09, 2014 at 09:49:03AM -0700, Junio C Hamano wrote:
Marat Radchenko [off-list ref] writes:quoted
Some time ago I complained [1] about troubles using Git on a project with high ratio of non-programmers. ... Then, a lost'n'forgotten git_svn_server [4] was found. ...Interesting.
Actually, no. As I said, git_svn_server made several ineffective architectural choices. It can be viewed as a proof-of-concept work though.
quoted
Current limitations: ... * You must not do 'inverted merges'. Old HEAD must be reachable from new HEAD by first-parent traversal.I am not sure what you mean by this to properly assess how significant this limitation is. Care to draw a simple picture?
SVN doesn't support nonlinear history (except merge-info crutch). Thus, we only expose "main" history line to SVN where "main" means "reachable through first-parent traversal from branch tip". To keep SVN history consistent, commits that once became visible to SVN have to remain visible. This limitation will be removed when git-as-svn gets persistent storage and will be able to remember what *was* main line. Imagine you had following history:
--- time --->
A -- B -- C
Now you merge (via Git) a feature branch:
A -- B -- C -- G
\ /
D -- E --- F
For SVN, history will look this way:
A -- B -- C -- F
We might introduce merge-info support for this one day.
And now the *bad* case. You have the same initial history but do *inverted merge*:
A -- D -- E -- F -- G'
\ /
B -- C ---------/
^
|
Previous branch tip
That's where things brake because for SVN, history transforms from
A -- B -- C
to
A -- D -- E -- F -- G'
And all users who checked out revisions B & C get their working copies screwed.
This also means that push --force also must not be performed.
Quoting my initial post [1] about inverted merges (you might call them
"merges with swapped parents").
I call it "swapped/reverse merge problem". In short: 1. Hack, hack, hack 2. Commit 3. Push, woops, reject (non-ff) 4. Pull 5. Push The root of evil is step #4 that creates a merge commit with "swapped" parents - local commits become first parent, remote commits become second. If one would want to make proper parent order, he would have to: 1. git fetch 2. git checkout origin/master -b tmp 3. git merge master 4. git push 5. git checkout master 6. git merge origin/master 7. git branch -d tmp And all this branch dance produces exactly the same commit (content-wise) as simple "pull, push" sequence with the only difference in parent order. And things become even worse if comeone pushes more commits to remote repo while you perform this dance. We can't expect all developers (especially, designers and artist) to do it. They don't want to use branches and just work on mainline. This is especially important on early development stages when new features (that designers' work depends upon) are added every day. Additionally, many git-related tools depend on first-parent convention and show wrong graphs/diffs.
[1] http://marc.info/?l=git&m=139866660018802