在运行时动态选择要使用的.dll版本

我正在研究SharePoint的实用程序。 这是一个适用于SharePoint 2007和2010的应用程序。当我引用SharePoint.dll的12.0.0.0版本时,该应用程序适用于SharePoint 2007,但不适用于2010.如果我引用版本14.0.0.0 dll,然后该应用程序适用于2010年,但不适用于2007年。

通过使用以下代码查看文件系统,在路径(SharePoint 2007)或14(SharePoint 2010)中检查12,我可以轻松地告诉我需要使用哪个.dll。

System.IO.File.Exists( Environment.GetFolderPath(Environment.SpecialFolder.CommonProgramFiles) + @"\Microsoft Shared\web server extensions\14\ISAPI\Microsoft.SharePoint.dll")); 

在开发时,我在Visual Studio中进行引用,因此它可以在2007或2010中构建。我希望能够在两个版本的SharePoint上发布适用的应用程序。 因此,我需要一些方法来加载/使用任何.dll对运行应用程序的用户有意义。

如何在运行时动态选择和加载.dll?

reflection? dependency injection? 你为自己的生活变得艰难!

编译Microsoft.SharePoint.dll v12,它将在2007年工作。

部署到2010并且它将“正常工作”(几乎在所有情况下),因为SharePoint 2010已经具有绑定重定向设置,因此对v12的任何引用都将重定向到v14。

您不需要做任何配置。

你需要比这更复杂的唯一情况是

  • 某些东西可以在2007年运行而不是在2010年运行的实例(我无法想到任何事情)。

  • 您可能希望利用2010年的特定function。

如果是这种情况那么我个人会做的是双重编译。 修改.csproj文件以生成2个稍微不同的版本,在必要时使用参数和条件编译(就像使用#if DEBUG一样)用于特定于产品的代码版本(这些版本中的代码很少)。 您也可以在.csproj中的引用中使用这些条件,例如

   PathToV12\Microsoft.SharePoint.dll PathToV14\Microsoft.SharePoint.dll  

缺点

  • 您最终得到了2个版本的程序

好处

  • 您最终得到了2个版本的程序! 您可能希望在2010版本中进行的许多更改都在manifet.xml,feature.xml和其他配置文件中 – reflection,dependency injection等在这里不会为您做任何事情。
  • 仍然有一个版本的源代码(带有次要的条件编译)
  • 编译器会发现更多的错误(例如,它不能在编译时弄清楚你在使用Reflection来调用v14中的新方法的那个时髦的东西实际上会起作用)

你需要使用reflection。 看看Assembly.LoadFile和Assembly.Load 。

如果你需要在其中使用类方法,你可以像这样使用它:

  Assembly u = Assembly.LoadFile(path); Type t = u.GetType(class title); if (t != null) { MethodInfo m = t.GetMethod(method); if (m != null) { if (parameters.Length >= 1) { object[] myparam = new object[1]; myparam[0] = ......; return (string)m.Invoke(null, myparam); } else { return (string)m.Invoke(null, null); } } } else { // throw exception. type not found } 

通过AppDomain.AssemblyResolve ,您可以检查DLL的存在并返回存在的任何一个:

 AppDomain.AssemblyResolve += delegate(object sender, ResolveEventArgs e) { if (e.Name == "Microsoft.SharePoint") { // do your check here and return the appropriate Assembly // or maybe just skip an explicit check and instead return either // Assembly.Load("Microsoft.SharePoint, Version=14.0.0.0") or // Assembly.Load("Microsoft.SharePoint, Version=12.0.0.0"), whichever works first // but beware of recursion! } }; 

在这种情况下,程序集绑定重定向对您不起作用,因为它在配置文件中是静态的,并且您希望它在具有SP2007或SP2010的任何计算机上动态工作。

我认为你需要在框架中查看程序集绑定重定向。

http://msdn.microsoft.com/en-us/library/2fc472t2.aspx

您可以使用“.net框架配置工具”来配置重定向。

对于使用Unity或Castle Windsor等DI框架之一的dependency injection来说,这听起来很棒。 还有其他人,但我只是提到这两个就已经冒着宗教战争的风险了。 🙂