For a diagram illustrating how all of these pieces map together, please see BigGit at a glance

A note on the code samples in this wiki

The Install-BigGit function provides a convenience function consolidating many of the functions illustrated below. However, this wiki intends to demonstrate the inner workings of BigGit. Also, depending on the size of your repository, these functions may take a long time to complete. I work with a 13GB repo and some can take 30 minutes. This should be a one time cost that you will no longerhave to pay after everything is setup.

The Nonvolatile Workspace

The size of Large TFS repositories is often the greatest barrier to a viable git repository. Often this is because TFS repositories are structurally maintained in a different manner. Of course this varies greatly from organization to organization, but many companies may have a single repository and then create a folder or branching structure to separate code ownership. Over time, as the lines of ownership change or blur and "common" code is scattered about without much curation, the repository becomes quite large. Due to the workspace paradigm in TFS, this is made manageable. However, when one wants to use a tool like Git-Tf or Git-Tfs to bridge between the TFS workspace and the Git Repository, one is forced to map git to the top level TFS folder and they can end up with a Git repo of many Gigabytes resulting in unacceptably slow source control operations.

The NonVolatile workspace is intended for all workspace mappings that the repository user does not generally touch directly and changes infrequently. This may often be large binary dependencies, entire run times or other resources that the user needs in their source tree in order to build their application but that they will never change. This might take up 80% of the entire repository. While the user may want to sync active content daily, they may only care to suync this content monthly.

The first step in geting started with BigGit is identifying this content and then asking BigGit to set it aside and remain untracked by Git. It will still be seen in the source tree as symbolic links and the build system can still reference it, but it will not weigh down source control operations.

Here is how to create the NonVolatile workspace in BigGit:
$myWorkspace = "MyWorkspace;Matt Wrock"
$serverRoot="/root/branch"
$tfsUrl = "http://tfsServer:8080/tfs"

Invoke-TF workfold /collection:$tfsUrl /workspace:$myWorkspace | ?{ 
    $_.ToLower() -match "(
        $serverRoot/external(/|:)
    ) | (
        $serverRoot/build(/|:)
    ) | (
        $serverRoot/lib(/|:)
    ) | (
        $serverRoot/runtimes(/|:)
    )"
} | Add-NonVolatileEnlistment -branch "`$$serverRoot" -tfsUrl $tfsUrl -localSourcePath "c:\dev\NonVolatile"
Here we used BigGit's Invoke-TF which is simply a sort of fancy alias to the TF command line. We get the workspace mappings we want and pipe them to Add-NonVolatileEnlistment.
Note that a NonVolatile workspace is not requiered to use BigGit. If you simply need BigGit's ability to manage multi mapping repositories, you do not need to create a NonVolatile workspace.

The Volatile Workspace

The Volatile workspace should contain the mappings that you and your team actively work on or is actively worked on by a neighboring team that your team is dependent upon. This is the code that you want to sync regularly. Here is an example of how to create the volatile workspace:

Invoke-TF workfold /collection:$tfsUrl /workspace:$myWorkspace | ?{ 
    $_.ToLower() -notmatch "(
        $serverRoot/external(/|:)
    ) | (
        $serverRoot/build(/|:)
    ) | (
        $serverRoot/lib(/|:)
    ) | (
        $serverRoot/runtimes(/|:)
    )"
}  | Add-VolatileEnlistment -branch "`$$serverRoot" -tfsUrl $tfsUrl -localSourcePath "c:\dev\Volatile"
Once this completes you should see all your volatile folders and symbolic link ("shortcut") folders for the nonvolatile directories.

The Partial Branch

One of the limitations of git-tf is requiring the root of a bridged GIT repo be synced to a single TFS server path. While this is not be an issue for most TFS repos, if you need to create lots of mappings to pull together all the source you need to avoid a prohibitively large workspace, then the single folder root will likely not work.

Creating a partial branch allows you to bring just the content you need under a single TFS server path and map that to git with git-tf. You would do that with BigGit like so:

Invoke-TF workfold /workspace:$(Get-WorkspaceName "c:\dev\Volatile\src") | Add-PartialBranch -serverPathToBranch $root/branch -partialBranchPath $/root/feature/mybranch -tfsUrl $tfsUrl -localSourcePath "c:\dev\branch\src" -localPathToken "c:\dev\Volatile\src"
This pipes the mappings from your volatile branch into the BigGit Add-PartialBranch function which will branch the volatile enlistment to the PartialBranchPath specified and commits it.

The Local Git Repository

Now that we have all of our active source under a single TFS server folder, we can clone just that to git using Git-Tf. BigGit povides a Install-Git function which uses Chocolatey to download and install git-tf, git and the java runtime required by git-tf. With these installed, issue this command to clone the TFS Partial Branch to Git:

Add-PartialBranchGitClone -tfsUrl http://myserver:8080/tfs -PartialBranchPath $/root/feature/mybranch -LocalSourcePath "c:\dev\git\src" -remoteOrigin \\someserver\share
In addition to creating a git repository, this function does a few key things to make working with git better and optimized for git-tf:
  • Adds our NonVolitile symbolic links just like it does for our other TFS workspaces
  • Creates a Excludes file in .git/info so that the symbolic links will not be tracked by git
  • Configures Git to turn off autocrlf and turn on ignorecase. Otherwise merging will be filled with conflicts.
  • Creates a Bare Git repo as a Remote origin that we can push/pull to.

The Remote origin

A git Remote is simply another git repository that is remote to your local repository. Most have at least one remote to push and pull changes to and from. github, bitbucket and codeplex are good examples of remotes, but I could assign any repository to be a remote. I want to have a remote because I want to share changes with others and I want a place remote from my computer to serve as my backup or to sync between my desktop and laptop. Since our Git repository is a clone of TFS and we can use git-tf pull/checkin to sync between the two, why would we want another remote? Would not TFS suffice as our remote?

Git-tf will only sync the master branch. Most will tend to have all work in progress in separate branches. I might have a feature I'm working on in one branch, a bug fix in another and an experimental spike in yet another. However I still want to be able to push/pull these branches to a central remote. NOTE: you can use either a UNC file share path or a http/https/git path. If a http(s):// or git:// path is used, BigGit will not clone to a bare repo, but it will assign that path as the remote origin so that all git push/pull operations will go to that location by default.

Setting up everything with one command

If you prefer not to call each of these commands individually but would rather call a single command to do all of this work, use the Install-BigGit function as shown on the home page.

See Routine BigGit Usage to understand how to use BigGit daily.

Last edited Jan 14, 2013 at 2:30 AM by mwrock, version 14

Comments

No comments yet.