程序集 // 多个客户端引用的第三方/公共程序集,// 例如 NUnit、MVC:
[供应商名称] [库名称] [版本号]
您已经打开了被称为“如何处理我的 BINARY 依赖项”的蠕虫罐头。
并试图找到一个处理该问题的 SVN 解决方案。
所以你想找出快速修复?或者你准备好投入一些时间了吗?
…………
自 2005 年以来,来自 Apache 的“Ivy”一直在处理二进制依赖问题。“Nuget”几年前就加入了。
让我们举一个简单的案例。
您有一个名为“MyPDFHelper.dll”的第三方库(最初版本为 1.0.0.1)。您有 2 个解决方案,每个解决方案包含 3 个项目。(VS .sln 和 .csproj)。
Sln1, CSProjA, CSProjB, CSProjC
Sln2, CSProjW, CSProjX, CSProjY
Sln1/CSProjA depends on MyPDFHelper.dll, 1.0.0.1.
Sln2/CSProjX depends on MyPDFHelper.dll, 1.0.0.1.
PDFHelper 发布了新版本的 MyPDFHelper.dll,1.0.0.2。没有重大变化,一切都很酷。
PDFHelper 发布了新版本的 MyPDFHelper.dll,2.0.0.1。具有重大变化。
Sln2/CSProjX 上的开发人员想要使用 MyPDFHelper.dll, 2.0.0.1。但这将如何影响没有计划从 1.0.0.1 更新的 Sln1/CSProjA。
显然,您已经看到了这个问题,因为您有 [VersionNumber]。
但这是一个哲学问题。SVN 是为源代码(基本上是文本文件)还是作为源代码和二进制存储库的组合创建?
Ivy 和 Nuget 是 BINARY 存储库。
现在,我使用 Ivy(即使在 Microsoft 世界中),因为我在说出“Nuget”这个短语之前就解决了依赖问题。
……
这是一个略有不同的问题,但类似。
您有相同的“应用程序”项目。
Sln1, CSProjA, CSProjB, CSProjC
Sln2, CSProjW, CSProjX, CSProjY
但是您也有一个带有“框架”部分的 .sln。假设它是封装良好的电子邮件发送代码。
MyCompany.EmailLibrary.sln MyCompany.EmailLibrary.csproj 内置于 MyCompany.EmailLibrary.dll
Sln1 / CSProjB uses MyCompany.EmailLibrary.dll.
Sln2 / CSProjX uses MyCompany.EmailLibrary.dll.
当您对自己的框架部分进行重大更改时会发生什么?
…………
所以简而言之。
您无需将代码放入源代码存储库,而是
“发布”到二进制存储库
在我们的示例中:
MyPDFHelper.dll, 1.0.0.1. would be published
MyPDFHelper.dll, 1.0.0.2. would be published
MyPDFHelper.dll, 2.0.0.1. would be published
然后每个“依赖于”MyPDFHelper.dll 的项目,都会有某种配置值,上面写着“我想使用这个版本的 MyPDFHelper.dll”。
常春藤符号将类似于
“1.0.0+”或“1+”。
而当2.0.0.1为“发布”时,Sln2的配置可以改为“2.0.0+”。Sln1 配置保持不变,“1.0.0+”
这样,每个 Sln(1 和 2)都将“检索”适合他们需要的 MyPDFHelper.dll 版本。最终(并且当开发人员选择这样做时)Sln1 可以更改为“2.0.0+”,但开发人员可以在他/她想要时处理重大更改,而不是在其他开发人员将新的第三方 dll 放入时源头控制。
…………
现在,谈到 MyCompany.EmailLibrary.dll。基本上,每次 MyCompany.EmailLibrary.sln 构建时,您都会将新构建放入二进制存储库中。如果您所做的只是修复错误,那么您始终可以发布(并覆盖)版本“1.0.0.1”,但我更喜欢使用递增的数字发布。
MyCompany.EmailLibrary.dll v 1.0.0.333
MyCompany.EmailLibrary.dll v 1.0.0.334
MyCompany.EmailLibrary.dll v 1.0.0.444
(数字并不重要,只是它们增加的事实。
…………
我会查看 Nuget(带有私有存储库)或 Ivy(使用命令行选项)。
我没有为您提供确切的解决方案,而是向您介绍二进制存储库的概念。
===================编辑
至于“源代码结构”,我这样做:
\DotNet\src\v20Base\v20\
\DotNet\src\v20Base\v20\Applications\
\DotNet\src\v20Base\v20\Framework\
\DotNet\src\v20Base\v20\ThirdParty\
\DotNet\src\v20Base\v35\
\DotNet\src\v20Base\v35\Applications\
\DotNet\src\v20Base\v35\Framework\
\DotNet\src\v20Base\v35\ThirdParty\
\DotNet\src\v40Base\v40\
\DotNet\src\v40Base\v40\Applications\
\DotNet\src\v40Base\v40\Framework\
\DotNet\src\v40Base\v40\ThirdParty\
\DotNet\src\v40Base\v45\
\DotNet\src\v40Base\v45\Applications\
\DotNet\src\v40Base\v45\Framework\
\DotNet\src\v40Base\v45\ThirdParty\
Example Application
\DotNet\src\v40Base\v40\Applications\
\DotNet\src\v40Base\v40\Applications\SodaManagerSolution\
\DotNet\src\v40Base\v40\Applications\SodaManagerSolution\SodaManagerSolution.sln
\DotNet\src\v40Base\v40\Applications\SodaManagerSolution\Pres.AspNet\
\DotNet\src\v40Base\v40\Applications\SodaManagerSolution\Pres.WPF\
\DotNet\src\v40Base\v40\Applications\SodaManagerSolution\BusinessLogic\
\DotNet\src\v40Base\v40\Applications\SodaManagerSolution\DataLayer\
\DotNet\src\v40Base\v40\Applications\SodaManagerSolution\SqlScripts\
Example Framework
\DotNet\src\v40Base\v40\Framework\
\DotNet\src\v40Base\v40\Framework\MyCompany.EmailLibrary\
\DotNet\src\v40Base\v40\Framework\MyCompany.EmailLibrary\MyCompany.EmailLibrary.sln
\DotNet\src\v40Base\v40\Framework\MyCompany.EmailLibrary\MyCompany.EmailLibrary.csproj
DotNet 3.5(和 3.0)是 2.0 的“叠加层”。因此,3.5 解决方案可以毫无问题地使用 2.0 dll。4.0 是一个新的 CLR,因此是新的“v40Base”。
这可能感觉有点矫枉过正,但是当框架发生变化时......在一个大型源代码存储库中,它开始对哪个项目可以引用哪个其他项目感到困惑。