This was the most popular question asked at our booth (and perhaps all of the VSTS area) at Tech Ed Developers 2008. It was asked in various forms, but they all boil down to basically the same question: How should I manage branching and merging?
Some folks are new to the concepts (e.g. many folks familiar with labels, sharing, and pinning in SourceSafe, but want to step up to TFS). Others have a system in place that they're unhappy with. Others have a system that is working, but they wonder (or even hope) that there is a better way they could be going about it.
First, the bad news: There is no silver bullet. There isn't a "right way" to go about this that applies to everyone. Even the solution we use internally has merits and drawbacks.
Now the good news: There ARE some general trends and associated best practices; odds are good one of these will be similar to your unique situation. We also have a lot of resources, examples, and experience that we can share. Finally, we're always open to feedback on what needs we aren't meeting, so if it sounds like you have needs that we can't yet meet, please let us know.
Before I go farther, one disclaimer: I am not an expert of this particular problem space. But, hopefully I know enough to get you started and point towards the experts.
The first resource I suggest everyone check out is the TFS Branching Guidance on Codeplex. This content covers branching and Team Project structures, physical layout, some "anti-patterns", and includes a comparison to SourceSafe.
I'll point to some previous blog posts that relate to this, but first, let me put my own spin on the topic.
In my opinion, there are two fairly common models that a lot of users will fall into (one or the other, sometimes some of both):
For people in the first category, a three-branch model (typically called "dev-test-production" or something similar) works well. Some of the details vary; for example, if you publish to a website, you might re-use your test and production branches constantly, whereas, for shrink-wrap releases, you'd probably create separate versions of these branches for each major release, and potentially additional ones for minor releases. In either case, your ongoing feature work happens in the main branch (or development branches off of it); you branch (or merge into) the test branch when you're ready to stablize for a release, and you branch (or merge into) the production branch when it goes live. On the merge side, you'd take fixes as needed in each branch, and merge them back up (from prod to test, and from test to dev) as needed.
For the second category, a branch per project makes perfect sense. If a given project has a formal release process, you might create the same dev-test-production structure underneath these branches as well. The key here is that the project-specific code and other artifacts are each in their own branch, while in the first model everything lives together.
A frequent variation to this scenario is where there's a set of shared tools or code that spans many or all of the projects. In the SourceSafe world, these are frequently shared, but you can't do that in TFS. Instead, I'd probably recommend a separate branch (and/or project) for the shared components. They probably have their own release cycle - so you make that tools branch the "master" and branch it into each project that needs them. You can then roll out versions to each consuming project in a predictable way. You might also consider limiting (or even preventing) changes to these components from ever merging BACK into the parent from the project branches, but either approach can work depending on your situation.
If neither of these scenarios sounds like your team, please leave comments/feedback - we can probably find a model that works for you.
Finally, here's a few posts that talk about branching and merging:
There are several other posts out there, but I think this are good places to start - if nothing else, to turn a few general questions into lots of specific ones! :)
I have a smile...stretched from ear to ear...