将 dll 的配置文件移动到调用 dll 的应用程序

Posted

技术标签:

【中文标题】将 dll 的配置文件移动到调用 dll 的应用程序【英文标题】:moving the config files for a dll to the app that calls the dll 【发布时间】:2012-04-03 12:16:32 【问题描述】:

我有一个具有搜索功能的网络应用程序。搜索算法被编译成一个单独的 dll。在搜索算法的 C# 代码中,我使用设置文件中保存的字符串来指向搜索索引所在的目录。编译搜索代码后,设置信息将包含在Search.dll.config 中,该Search.dll.config 与Search.dll 一起放在bin 目录中。现在在我的 Web 应用程序中,我将 Search.dll 添加到引用中。配置文件未添加到 Web 应用程序中。但是,Web 应用程序运行良好并且知道文件在哪里。因为在Settings.Designer 内部,如果配置文件不存在,它使用DefaultSettingValueAttribute 分配默认值。

如何将Search.dll.config 也添加到我的网络应用程序中,以便操作员可以根据需要更改服务器上索引文件的位置?

谢谢

编辑:

我尝试将配置文件添加到我的部署文件夹。但是 ASP.NET 将 dll 放在 C:\Windows\Microsoft.NET\Framework64\v4.0.30319\Temporary ASP.NET Files\root...... 的目录中,并且配置文件不会被复制到那里。所以此时我不知道如何在我的代码中包含配置文件。

感谢您的帮助。

注意:

我一直在使用以下代码将配置文件的值导入应用程序。但是,它取决于dll和配置文件在同一个文件夹中,我不知道如何完成。

    var executingAssembly = System.Reflection.Assembly.GetExecutingAssembly();
    var location = executingAssembly.Location; //C:\MyApp\bin\Debug\Search.dll
    var config = ConfigurationManager.OpenExeConfiguration(location);
    var sections = config.Sections; //count of this is 21
    ConfigurationSectionGroup csg = config.GetSectionGroup("applicationSettings");
    ConfigurationSectionCollection csc = csg.Sections;
    ConfigurationSection cs = csc.Get("Search.Properties.Settings");

【问题讨论】:

【参考方案1】:

以下是你如何做你想做的事,而不是一些人认为你应该做的事:

(对不起,我现在在 vb 工作)

假设 dll 被命名为 mycompany.mynamespace.dll

    将 dll 项目中的 app.config 文件重命名为 mycompany.mynamespace.dll.config 在其属性中,说 Copy If Newer

    使用此代码(在 dll 中)访问您的设置:

        Dim appConfig = ConfigurationManager.OpenExeConfiguration(Me.GetType.Assembly.Location)
        _WorkingDirectory = appConfig.AppSettings.Settings("WorkingDirectory").Value
    

【讨论】:

【参考方案2】:

理想的方法是从 DLL 中删除配置依赖项。 dll 是为应用程序设计的,配置属于应用程序而不是 dll。

在大多数情况下,您可以通过 DI 容器或通过手动 compose 使用依赖注入来摆脱对 dll 代码中配置的依赖/读取。

如果您的搜索 dll 依赖于设置,请将设置作为您的 dll 入口点类的依赖项,并假设您的入口点类以某种方式获取它的设置,然后继续执行 dll 代码。

然后,您可以从应用程序中提供设置值,无论是 web/windows/console 还是从配置文件/db/web 服务/文件系统中读取。

示例代码:

在 dll 中:

 public interface ISearcherDirectorySettings

    string[] SearchIndexPointers  get; 


public class Searcher

    private readonly ISearcherDirectorySettings _searchDirctorySettings;

    public Searcher(ISearcherDirectorySettings searchDirtorySettings)
    
        _searchDirctorySettings = searchDirtorySettings;
    

    public void SearchAlgorithm()
    
        var indexes = _searchDirctorySettings.SearchIndexPointers;
        // search code
    

在您的应用程序中:

public class SearcherDirectorySettings : ISearcherDirectorySettings

    private readonly string[] _pointers;
    public SearcherDirectorySettings(string[] pointers)
    
        _pointers = pointers;
    

    public string[] SearchIndexPointers
    
        get  return _pointers; 
    


public class ApplicationRootClass //Owns configuration file

    const string FirstPointerKey = "File1";
    const string SecondPointerKey = "File2";

    private Func<string, string> _getFromConfig = key => ConfigurationManager.AppSettings[key];

    public ApplicationRootClass()
    
        var searcherDirectorySettings = new SearcherDirectorySettings(new[]  _getFromConfig(FirstPointerKey),_getFromConfig(SecondPointerKey) );

        var searcher = new Searcher(searcherDirectorySettings);
        searcher.SearchAlgorithm();
    

有了这个,你可以实现“快速失败”。您可以在任何应用程序中使用搜索 dll,应用程序负责提供设置值。

如果您最终在多个应用程序/项目中使用 dll 并复制设置类代码,请使用实用程序组件来完成这项工作或将设置类移动到 dll 中,但将设置类的实例化留给应用程序。

【讨论】:

【参考方案3】:

最好的办法是直接将配置添加到 Web 项目中。 .NET 并不真正支持您尝试的方式与库关联的配置;这是设计使然。您库的其他用户可能需要不同的配置。将文件标记为应复制到输出文件夹的内容。

编辑:

为此,在文件属性中将“构建操作”设置为“内容”并将“复制到输出目录”设置为“如果较新则复制”。您可以使用HttpRuntime.BinDirectory 发现 bin 文件夹中的文件。您可能希望将此位置传递给您的库,而不是让库假定它在 Web 项目中运行。

或者,只需在 web.config 中嵌入您需要的配置(配置文件也可以将设置分解为单独的文件)。

最后,您可以考虑将文件嵌入为资源。

编辑:

查看您正在使用的代码,只需将其移至 web.config。容易得多,而且惯用语。一旦它在 web.config 中,只需使用 ConfigurationManager.GetSection() 阅读您的部分。

顺便说一句,有一个免费的配置部分设计器,可以非常轻松地创建支持自定义配置部分的类。在此处查看 VS 扩展在线图库:

http://visualstudiogallery.msdn.microsoft.com/2a69f74e-83df-4eb0-8cac-cd83b451cd1d?SRC=VSIDE

【讨论】:

谢谢!如何“将文件标记为应复制到输出文件夹的内容。”? 谢谢!我可以将配置行移至 web.config,但我的 dll 将如何读取 web.config?似乎 asp.net 将它们放在不同的随机命名的文件夹中。 编辑了我的答案来处理这个问题。

以上是关于将 dll 的配置文件移动到调用 dll 的应用程序的主要内容,如果未能解决你的问题,请参考以下文章

需要如何帮助将 system.serviceModel 配置部分移动到我的代码中

如何将 dll 配置文件添加到添加 dll 作为参考的项目中?

怎样可以将DLL编译到EXE文件里

将 DLL 动态加载到单独的应用程序域中,然后卸载

winform 部署 dll路径

eclipse如何开发并调用dll文件