HOWTO use GIT with SVN server

Introduction

During COVID-lockdown, one of the challenges is to understand how to smart work as best as possible.

One of my problems is that I haven’t remote access to the SVN server.

I began to wonder if and how GIT can alleviate my smart work problems.
The found answer is: yes, it can.

Both repository types have their strong and weak points.
My personal impression is that GIT can become quite chaotic if there aren’t strong iron rules to follow.

In my scenario, the main problem is the SVN sandboxes only work if they can reach their SVN server.
There is no way to work offline from it.

On the other side, GIT is working mainly offline, and, I discovered that it can also work with SVN servers. This means that I can work offline with my local GITed sandboxes accumulating, and then flushing the changes only when they are needed to the SVN server.

There are several interesting points in using this approach:

  • It is possible to clone the whole repository or only a part of it (a folder/subproject)
  • The GITed sandbox starts its history from its creation time resulting very compact in terms of disk space.
  • From this point, it can accumulate any update you commit.
  • It can flush all offline commits to the SVN server, keeping the same detail level for each commit.
  • It can also be updated, with any new change present in the SVN server (by issuing a “rebase”).

The only drawback I read about is:

  • branches: it seems that it may have some problems with (but it is not my case).

Step 1 – Needed software

Since I am using Windows 10, these are the needed free packages to install:

If you need an SVN server to test/check/verify/tweak this process, you can use:

Step 2 – Preliminary Tweaks

One of the hardest points to care about is the credentials processing.

It seems that there is a standard location for SVN cached credentials (at least for TortoiseSVN & Git for Windows).

Optionally if you wish to melt both caches, you need to:

  • locate the ‘main’ one,
  • create a junction for the others to point them to the main one.

In my case, I choose TortoiseSVN as the main one and Git for Windows as a secondary.

So I needed to:

  • delete or rename Git for Windows folder: c:\users\<user_folder>\.subversion
  • create a junction to point to the Tortoise SVN one by running the following script:
c:
cd "\users\<user_folder>"
mklink /j svn "AppData\Roaming\Subversion"
ren "svn" ".subversion"

Step 3 – cloning SVN sandboxes

Before cloning our SVN sandboxes, we need to briefly focus on how to organize their GIT counterparts.

Generally speaking for each SVN sandbox, we can clone a GIT one.

There is the only exception for the statement above:
if we have some modules that have shared resources (including files, libs, …), it will be better to group them in a single GITed sandbox.

This is needed to preserve the timeline of our changes to the shared resources when we will upload them to the SVN server.

Every time we change a shared resource across several GIT sandboxes, we need to flush them to the SVN server before changing anything else.

Since we try to work offline as much as possible, these will be annoying events to care about.
The more we can regroup modules with shared resources, the less we will need to consolidate offline commits to the SVN server.

Back to SVN sandboxes, I need to keep them working (when possible) together with their GIT counterpart.
In my case, I will have something like this:

c:\projectx <== SVN sandbox of projectX
c:\projectx_git <== GITed sandbox

The further step is to use the same output folder to compile/debug the program. This may be needed if this folder contains resources, you usually need (configuration, database, …) without changing anything in your makefile/project file.

Supposing that projectX has its output folder into:

c:\projectX\out

we need to create a junction with the following line:

mklink /j "c:\projectX_git\out" "c:\projectX\out"

Step 3.1 – Time to clone SVN sandboxes

Finally, the time has come to clone our SVN sandboxes.

For each one, we need to run the following command:

git svn clone -rHEAD --username="<svn_username>" "<full_svn_url>"

where:
<svn_username> is the SVN server’s local account username.  According to my personal experience, this command worked fine only on servers using HTTP/HTTPS protocol.
<full_svn_url> is the full URL used by our sandbox. Using TortoiseSVN, you can get it from File Explorer properties page.

In case, we are trying to aggregate several modules (in the same SVN folder), we can also add the following parameter in our command line:

--ignore-paths="<regex_string>"

To get a proper <regex_string>, my advice is to use this awesome site: https://regex101.com/

Another available parameter to play with maybe:

--include-paths="<regex_string>"

The command will prompt for the user password the first time only.

There is one last side effect to care about.
If you clone, the following SVN folder:

\projects\c_libs

The command will create ‘c_lib’ in the current folder.

My current approach is to clone it in a temporary folder and rename/move it to the final ‘destination’ with the desired folder name.

Actually, you can write down a script similar to this one:

git svn clone -rHEAD --username=”<svn_username>” "<svn_full_url>"
ren "c_lib" "\ProjectX_git"
mklink /j "c:\ProjectX_git\out" "c:\ProjectX\out"

From this point, we can use our GITed sandboxes to commit any changes offline.

Step 4 – Upload local commits to the SVN server

From time to time, we will need to consolidate/upload our offline commits.

We can do this with the commands below:

git svn dcommit –username="<svn_username>"
git svn rebase

The first one will upload the commits to the server.
The second one will download any missing changes present to the SVN server.

Offline only scenario

Can we use GITed sandboxes in offline scenarios?

Yes, we can with the help of someone that can reach the SVN server.
The key is to write down scripts to ease the ‘remote’ tasks and to avoid human mistakes.

You can organize the cloning process in quite simple scripts. The only critical point is inserting your account password the first time.

The resulting GITed sandbox should be quite compact because its commit history has just started.
Naturally, the size is also depending on what has been ‘sandboxed’.

The upload process is similar:

  • zip the GITed sandbox without any not-versioned file and the full ‘.git’ folder,
  • send it to the online_guy,
  • he shall unzip it,
  • execute the script to upload and update the sandbox,
  • zip it again, and send it back to us,

To quickly update our GITed sandbox, we have to:

  • delete ‘<GITed_sandbox>\.git’ folder
  • unzip the updated one in a temporary folder
  • copy it into ‘<GITed_sandbox>‘ everything overwriting any existing file.

In this way, we will preserve any junctions, unversioned files…

If needed, we can arrange sandbox cloning in a similar way.

Conclusions

At first glance, it may appear a bit complex process, but the key is the design of our solution.  Using scripts to bury annoying command lines is a great way to ease it.

The invaluable reward of all these efforts is the ability to work offline from your SVN server.