views:

3713

answers:

5

I have been working on standardizing the source control structure for our Team Foundation Server rollout for the new year. I have started by using the Microsoft Team Foundation Server Branching Guidance documentation available on CodePlex.

I was hoping to get some feedback and answers to a few of the specific questions I have about the proposed structure. When it comes to structuring source control in TFS, I have learned that there are so many "standards" to choose from that there is not really a standard.

First, I will outline and describe the decisions and usage.

$/                                                
    {Team Project}/                               
        {Subproject}/                             
            Development/                          
                Trunk/                            
                    Source/
                    Tests/
                    Sandcastle/
                    TeamBuildTypes/
                        {Build Name}/
                Branches/
                    {Branch Name}/
                        Source/
                        Tests/
                        Sandcastle/
                        TeamBuildTypes/
                            {Build Name}/

            Integration/
                Source/
                Tests/
                Sandcastle/
                TeamBuildTypes/
                    {Build Name}/
            Production/
                Releases/
                    {Release Version}/
                        Source/
                        Tests/
                        Sandcastle/
                        TeamBuildTypes/
                            {Build Name}/
                Branches/
                    {Branch Name}/
                        Source/
                        Tests/
                        Sandcastle/
                        TeamBuildTypes/
                           {Build Name}/

The general logic is that a Team Project can contain either a single logical project (where there would be no {Subproject} entry) or multiple related projects in the form of a product or tool suite. The three major containers are called Development, Integration, and Production.

Within the Development container's Trunk, there are provisions for both the projects which make up the product in the Source folder, with corresponding unit tests available in the Tests folder. A majority of minor development would occur in the trunk, with branching available through the Trunk folder's sibling Branches folder, which acts as a branching container. One or more solution files would live within the Trunk, allowing for branches at that level to capture the solution, source, and unit tests.

The Integration container, often called "main" in non-TFS implementation, is solely used to integrate Changesets from Development to create a stable and testable build. It is initially created as a branch from the Development container once a testable product has been attained. The builds from this container will be used for our testing environment and load testing environment. We choose to include load testing with testable builds so that we can monitor for changes in performance, being able to rapidly isolate Changesets that may have contributed to any irregularities.

Production is used to produce pre-production and production quality builds. It is initially created as a branch from the Integration container once a stable build has been recommended for release. Within the Releases folder, a "branch by release" structure is followed, providing snapshotting and isolation in a single place. (For example, when Release 1.1 is ready for a pre-production build, the stable Integration container is branched into a new Release 1.1 folder in the Production/Releases structure. Subsequent RCs and RTWs/RTMs are promoted into this folder, as well.) A branching structure is also present, as seen in the Branches container. This allows for "hotfixes", usually a revision marker (Major.Minor.Revision). The branch is created from the current release and merged back into the new revision marker - like Release 1.1.1. The Changeset would be reverse integrated to the Development container's Trunk upon acceptance.

We feel that this structure is a fair balance between robustness and complexity. But there are a few nagging questions that I can not logically fit into the model. They are:

Team Build - The Development and Integration containers will initially start out as being nightly builds, eventually moving to Continuous Integration (CI). The Production container will be manually built.

  • Where should the build definitions live? Edit - Based upon a couple of responses, the TeamBuildTypes folder has been moved to the trunk and branched to the appropriate containers. This does, however, lead to a new question (follows).

  • By having the TeamBuildTypes folder in their appropriate containers, does that mean that all build definitions will be reproduced between the appropriate folders? For example, having a build definition for development quality builds, as well as testable builds, etc. all living in all TeamBuildType folders throughout the structure.

Documentation Generation - We use Sandcastle to generate documentation. Specifically, we also use Sandcastle Help File Builder to manage the output. This produces a project file in a format specific to SFHB.

  • Should generated documentation be stored in the source control structure?

  • Should documentation be generated for each container, or does it only posses value for pre-production and production quality builds?

  • To preserve fast local build times, should documentation creation be owned by a build definition?

  • Where should the SHFB-specific files live? My initial inkling is to put it as a peer to the Source and Tests folders. I agree with the recommondations that it be a peer to Source and Tests. Diagram changed to reflect this change.

Third Party Binaries

  • Should binaries (controls, libraries, etc.) be stored in source control?

  • If so, should it be it's own Team Project?

General Documentation - Non-generated documentation, such as requirements, design documents, test plans, etc. are not going to be reflected by a folder in the source control structure. After some research and discussion with my developers and peers, using the built-in Documents folder in Team Explorer provides more benefit, since it mirrors the structure within the Team Project Portal and some (business) users do not need the additional complexity of learning the source control aspect of TFS.


I will update the structure as I get answers to the questions to provide a clearer picture. I also welcome any other comments related to potential changes. If I have any other questions, I will make sure to modify this post.

Edits:

  • Clarification. Source and Tests folders do live under the Integration container, as well.

  • Both Micah and Josh brought up great points regarding third party binaries. Question added regarding the issue.

  • Documentation generation can be slow. Question added regarding whether documentation creation should be owned by a specific Team Build Type.

  • Added resolution related to non-generated documentation, such as requirements, design documents, test plans, etc.

  • Added resolution related to TeamBuildTypes folder for build defintions.

  • Based upon various feedback, moved the TeamBuildTypes folder to the trunk / branch levels.

+2  A: 

Great layout and explanation. I've struggled with the exact same issues. I've wound up with a very similar structure. Mine varies slightly.

Development/
   Trunk/
      Binaries/  -- Shared libraries
      Source/
      Test/
      Docs/      -- Documentation
TeamBuildTypes/  -- Build definitions
  • Adding the binaries folder allows you to have one location in the branch where all your projects can reference shared libraries
  • We put the documentation here so it can travel along with it's specific branch.
  • Our build definitions are at the development level since we can figure them in one location for all of the branches, but it could definitely be at the branch level which may make more sense.

Should binaries (controls, libraries, etc.) be stored in source control? If so, should it be it's own Team Project?

I think they should definitely be source controlled, but I don't see any reason to put them in their own team project. One issue to be careful with is TFS for some reason treats binary files slightly different. I've had issues where I've updated the binaries in source control, but "Getting Latest" on other machines doesn't cause update of the files. Sometimes you need to do "Get Specific Version" and check the "Overwrite Unchanged Files" option for that particular file.

Micah
I thought that I had read the the TeamBuildTypes folder needed to be at the Team Project level. Perhaps this was for TFS 2005 that I had read it for? In having your own documentation folder, do you use the one that is in Team Explorer at all?
joseph.ferris
Yes. I use the Docs/ folder for product documentation and the Documents folder for things like design specs. You may be right about the build defs. It's in the location that TFS created for me.
Micah
Cool. Thanks for the clarification. Are you on 2005 or 2008? In 2008, you can put the build definitions wherever you want. See: http://blogs.microsoft.co.il/blogs/kolbis/archive/2008/01/27/teambuildtypes-folder-have-to-be-off-the-project-route.aspx
joseph.ferris
+3  A: 

I like your idea of putting the Sandcastle files as a peer to Source and Tests, I would add a documentation folder, that would then contain the sandcastle files, and optionally the actual documentation.

There are definetly differences of opinions and I'm sure I will be downvoted for this (since I have been before). I would put the generated documentation in TFS for a couple of reasons:

  1. Your going to want your documentation with each release, and using TFS is an easy aproach to ensure your documentation stays in the correct place.
  2. Using TFS to store it means everyone will know where to go get the documentation.

One thing I don't see which I always struggle with is where to third party dependancies, it might be that they belong down under the source so they are with each project although if you wanted to share them accross projects you could add a new top level node.

Edit

For my binaries I usually end up with

$/ThirdParty/Company/Product/Version/Src(optional)

So for example I have

$/ThirdParty/ Microsoft/ EntLib/ 3.1 4.0 ComponentArt/ WebUI/ 2008.1/ Src

I like to add the source, I've had to patch CA's source which I hate to do but when a third party doesn't fix the bug you have to resort to this.

JoshBerke
I am struggling with that, as well. Micah has them in the container, which I can see as making sense, as well. I think that I am leaning towards agreeing with you on the Sandcastle generated documentation.
joseph.ferris
Josh, just want to be clear... You list 3rd Part as being in $/ThirdParty. So you have a Team Project called ThirdParty that you put the products in, right? Interesting approach. I hadn't thought of that.
joseph.ferris
Not a seperate team project, sorry I'm currently stuck on VSS so I forget the team project concept. I'd never thought of a seperate team project but its interesting idea...
JoshBerke
Not a problem. I am trying to flesh out as many ideas as possible. :-) I made an edit to the original question to solicit more feedback.
joseph.ferris
+2  A: 

One thing I'd recommend is to not use the default location for team builds and include it in the 'branchable' level because as you branch for various reasons (say code promotions) you'll want your build scripts to be branched and synced with it.

Also a new and more scenario specific guide was just published as well at http://www.codeplex.com/TFSBranchingGuideII

Thanks for that link! Briefly looking over the documentation, I think that the concurrent hot fix, service pack, next release model is overkill for most projects, including my own. When I am back in the office, I will play with the TeamBuildTypes folder on your recommendation.
joseph.ferris
+2  A: 

You should put your TeamBuilds folder under your trunk. This was impossible in TFS2005 but Microsoft fixed it for 2008...

The reason for this is that your build may change with newer version (for example: new packaging schemes, different testing etc.) which may make it incompatible with older maintenance releases. Thats why you should couple the team build with the code's version.

This way, lets say you release a 1.0 version and put it under the Releases folder. You'll be able to build it and issue patches while working on v2.0 in your Development trunk (which may require modifying the build)

Eran Kampf
+2  A: 

For your binaries - obviously the only binaries that should be under version control are "third-party" assemblies that you aren't "building" as part of any automated build. If you have your own libraries that you have their source under version control etc - you should look at various strategies for building and synchronizing etc.

I then organize them like Josh - and then use branching to "copy" the binaries to an _ExternalReferences folder which is a peer to the .NET Project folders within the solution tree. This is a very efficient way server side as TFS Version control only stores "Deltas" - so essentially every "duplication" of those binaries across many projects is essentially like a "pointer".

fuzzbone
I disagree – what's the harm of storing binaries even for your own projects? If one project references a specific version of (the output of) another project, then storing the binary seems both clearer and more efficient (though that's probably not much of a concern on its own).
Kenny Evitt
If a project needs a specific version of a component - it should have that binary in IT'S source code folder.
fuzzbone