views:

296

answers:

4

I develop a variety of applications and have 3-4 miscellaneous libraries that I reuse across these apps (one for math, one for database functions etc.).

Currently I have one master source directory with each project as a top level directory (including my helper projects). And each project that needs a helper adds the entire project as a reference in the solution (not against the library). This allows for quick debug/updates of the helper library, but gets cumbersome quickly as I always have to rebuild the helpers and can make breaking changes to interfaces used by much older programs.

All of these are stored in a trunk directory of a subversion repository, and when I branch particular directories I create a massive branch, etc. This is quite difficult to maintain backwards compatibility as well as just shear code size and local size of the repository.

What is the best way to handle these situations? How do you layout your various projects.

Do you put each project in its own subversion repository? Or do you use one repository with multiple top level projects and trunk/branch/tags beneath that?

How do you reference alternate projects? Do you just compile these and reference the data?

A: 

I've never used subversion but I can provide some info outside of the repository question. My answer is it really depends on the scenairo and the company. For one of the largest projects I was involved we used the following structure. This project consisted of roughly 20 core assemblies which would be shared amongst various applications. We were also using TFS.

We defined a Common TFS project, which contained a single master build solution to build all the projects in the common project. When we build we would publish the binaries.

We then had a TFS project for each of the business units, and their various applications (Each BU could have anywhere from 1 to n projects / applications). We then setup the applications to pull the binaries into their own projects using a file reference. In this case the business units treated the common libraries as third party products.

In less formal situations we would have the Business Units reference the build outputs directly (they'd be checked back into the source control system). This allowed the business unit to get the new version once they were compiled but as you indicated introduces compatability issues. This is where having them completly isolated helps.

JoshBerke
Don't put anything that is generated into a source control system: it is not source. Versioning the output binaries is great, so don't compromise it with direct unversioned dependencies (which introduce compatibility issues like you said). Half-steps only increase cost, but don't grant benefit.
Rob Williams
Well putting them into source allowed us to control the source control tree and enabled us to easily do file references without having to dictate where binaries should be placed. I agree in most cases you shouldn't put generated output but in cases like this there can be a benefit
JoshBerke
+1  A: 

My reusable libraries are developed in separate projects with separate source code directories in the repository (I use TFS, but it should be applicable to SVN). I publish versions of these libraries in a common location -- in my case a network share referenced via DFS. I add references to the published libraries to my other projects as needed. Sometimes I use versioning (named versions) if I find that I need to maintain multiple versions of a library for some reason. In a sense I treat them all as 3rd-party components and don't reference their projects directly.

tvanfosson
A: 

i think you need a seperete solution for the common projects and have their own build process for them. I would link them in as binary references in your main projects. You can still debug into this code by using visual studio if you have the pdb files. I think this the only way to scale or you keep having these issues

One think to think about is put all shared libraries in one location and have the local projects create an ext directory to put all shared linked binaries. You can then write scripts to check for updated versions, etc to avoid having to mess around with manual upgrades

ooo
+1  A: 

Please see my answers at http://stackoverflow.com/questions/296643/projects-folder-structure-recommendation#296793 and http://stackoverflow.com/questions/222827/how-do-you-organize-your-version-control-repository#304036.

For your specific question, the issue is managing inter-project dependencies. The answer is to version them--each project that depends on another should depend ONLY on the binary deliverable from that project (or the closest equivalent if not a compiled program/library), and that deliverable should be versioned in each such reference. Of course, you first need to make sure that each project produces ONE and ONLY ONE binary deliverable (or equivalent).

By depending only on the binary deliverable from another project, you make each project stand-alone and greatly ease its maintenance, since its "build interface" is a single file. Reaching into another project's source/build is like reaching into the middle of a library's implementation = lots of problems.

By versioning each project, you can modify a particular project's source on behalf of another (new) project, but not affect any of the other old projects that used it. In effect, each project becomes a PRODUCT. Like any product, you should manage its releases and its compatibility with other products.

Rob Williams