How do I make App.config values visible for referenced ClassLibraires (Assebmlies)

断了今生、忘了曾经 提交于 2019-12-25 05:17:11

问题


I have a C# Project called Application which is basically considered to represent the top most application layer. All other Layers are treated as ClassLibraries like BUSINESS, DAO and UTIL. Now I want that the application be configurable by using the App.config file. For that purpose I need to make this configuration file visible for the referenced ClassLibraries (Assemblies).

For me, the most suitable solution would be that the UTIL assembly has access to the App.config and is able to share those accessible items to the upper application layers.

So far I tried to create a Settings.settings file in the UTIL assembly which defines one item: Name: ElemName; Type: String; Scope: Application. The App.config file which is located within the Application assembly contains the following source:

<applicationSettings>
  <UTIL.Settings>
    <setting name="ElemName" serializesAs="String">
      <value>SomeValue</value>
    </setting>
  </UTIL.Settings>
</applicationSettings>

If I now try to access this property via: Settings.Default.ElemName, the build fails with error: 'UTIL.Settings' is inaccessible due to its protection level

A further approach, to make this property visible via a helper class inside assembly UTIL

public String GetElemName()
{
  return Settings.Default.ElemName;
}

fails with an: 'System.Configuration.ConfigurationErrorsException' occurred in System.Configuration.dll ... Additional information: Configuration system failed to initialize

How can I get it running? (I only need to read the configuration)


回答1:


The easiest is the following:

Add the required settings in the project properties of the DLL assemblies like you would do for any normal application.

Now, a DLL doesn't actually read its own app.config. The trick is to copy the entire <applicationSettings> block from the DLLs app.config to the application's app.config and also add the respective line in the <sectionGroup> section at the top of the file.


Example: Let's assume the app.config for your DLL looks like this:

<?xml version="1.0" encoding="utf-8" ?>
<configuration>
    <configSections>
        <sectionGroup name="applicationSettings" type="System.Configuration.ApplicationSettingsGroup, System, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089" >
            <section name="DLLSample.Properties.Settings" type="System.Configuration.ClientSettingsSection, System, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089" requirePermission="false" />
        </sectionGroup>
    </configSections>

    <connectionStrings>
        <add name="DLLSample.Properties.Settings.MyConnectionString" connectionString="Data Source=..." providerName="System.Data.SqlClient" />
    </connectionStrings>

    <applicationSettings>
        <DLLSample.Properties.Settings>
            <setting name="AllowStart" serializeAs="String">
                <value>True</value>
            </setting>
        </DLLSample.Properties.Settings>
    </applicationSettings>
</configuration>

And the app.config of your application looks like this:

<?xml version="1.0"?>
<configuration>
  <configSections>
    <sectionGroup name="applicationSettings" type="System.Configuration.ApplicationSettingsGroup, System, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089">
      <section name="App.Properties.Settings" type="System.Configuration.ClientSettingsSection, System, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089" requirePermission="false" />
    </sectionGroup>
  </configSections>

  <applicationSettings>        
    <App.Properties.Settings>
      <setting name="LogPath" serializeAs="String">
        <value>C:\Temp</value>
      </setting>
    </App.Properties.Settings>
  </applicationSettings>
</configuration>

After the above described changes, the application's config file should look like:

<?xml version="1.0"?>
<configuration>
  <configSections>
    <sectionGroup name="applicationSettings" type="System.Configuration.ApplicationSettingsGroup, System, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089">
      <section name="App.Properties.Settings" type="System.Configuration.ClientSettingsSection, System, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089" requirePermission="false" />
      <section name="DLLSample.Properties.Settings" type="System.Configuration.ClientSettingsSection, System, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089" requirePermission="false" />
    </sectionGroup>
  </configSections>

  <connectionStrings>
      <add name="DLLSample.Properties.Settings.MyConnectionString" connectionString="Data Source=..." providerName="System.Data.SqlClient" />
  </connectionStrings>

  <applicationSettings>        
    <App.Properties.Settings>
      <setting name="LogPath" serializeAs="String">
        <value>C:\Temp</value>
      </setting>
    </App.Properties.Settings>
    <DLLSample.Properties.Settings>
        <setting name="AllowStart" serializeAs="String">
            <value>True</value>
        </setting>
    </DLLSample.Properties.Settings>
  </applicationSettings>
</configuration>

From both your application and DLL code you'll be able to use the normal configuration settings mechanism, like access a value through Properties.Settings.Default.AllowStart from the DLL's code or Properties.Settings.Default.LogPath from the application's code.

Two things you can not do:

  1. Access the DLL config values from your application and vice versa
  2. Manage the DLLs config values from the application's property page. You need to edit the app.config manually to add/remove/modify settings.

Connection strings, by the way, can also be managed that way. I've added to the examples above.




回答2:


I solved this issue in a different way.

The Project called Application still contains the App.config file. All referenced assemblies (Business, DAO, UTIL, and TestAssemblies) just share the applications configuration.


How to share configuration:

  1. Project (Business, DAO, UTIL, etc.) -> Add -> Existing Item -> 'Select' App.config -> Add As Link
  2. Project -> Add Reference -> .NET -> System.Configuration -> OK
  3. string configValue = ConfigurationManager.AppSettings["token"];

How the App.config file looks like:

<?xml version="1.0" encoding="utf-8" ?>
<configuration>
...
  <appSettings>
    <add key="token" value="ConfigValue" />
  </appSettings>
...
</configuration>

Without this reference to the existing App.conifg file AppSettings["token"] won't resolve the value while running with NUnit. If the application is started in debug mode, everything works fine, even without the link to App.config as mentioned by user Maarten



来源:https://stackoverflow.com/questions/19838922/how-do-i-make-app-config-values-visible-for-referenced-classlibraires-assebmlie

标签
易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!