代码之家  ›  专栏  ›  技术社区  ›  sr28

app.config-配置系统无法使用自定义节初始化

  •  0
  • sr28  · 技术社区  · 8 年前

    我有一个web api,我在其中根据以下链接将自定义部分添加到web.config中: https://msdn.microsoft.com/en-us/library/2tw134k3.aspx

    <?xml version="1.0" encoding="utf-8"?>
    <!--
      For more information on how to configure your ASP.NET application, please 
      visit https://go.microsoft.com/fwlink/?LinkId=301879
    -->
    <configuration>
      <configSections>
        <sectionGroup name="productGroup">
          <section
           name="product"
           type="myProject.Stuff.Api.ProductSection"
           allowLocation="true"
           allowDefinition="Everywhere"
          />
        </sectionGroup>
      </configSections>
      <appSettings>
        <!-- various app settings -->
      </appSettings>
      <productGroup>
        <product name="my name" id="1" />
        <product name="my name 2" id="2" />
      </productGroup>
    
    <!-- other standard elements -->
    
    </configuration>
    

    我在configSections和productGroup中添加了。然后,我将c类定义为ProductSection,如下所示:

    使用系统配置;

    namespace myProject.Stuff.Api
    {
        public class ProductSection : ConfigurationSection
        {
            [ConfigurationProperty("name", IsRequired = true)]
            public string Name
            {
                get
                {
                    return (string)this["name"];
                }
                set
                {
                    this["name"] = value;
                }
            }
    
            [ConfigurationProperty("id", IsRequired = true)]
            public int Id
            {
                get
                {
                    return (int)this["id"];
                }
                set
                {
                    this["id"] = value;
                }
            }
        }
    }
    

    我已经将这两个部分复制到了我的测试项目中的app.config中,但是当我现在尝试调试一个测试时,我得到了初始化失败错误。当我注释掉productGroup部分时,它就会停止抱怨。我做错了什么?

    作为补充说明,我最后把它结构得更简单了一点。因为我的“产品”部分只需要一个名称和id,所以它们根据appSettings将自己借给键值对。所以我创建了这样一个部分:

    <configSections>
      <section name="productGroup"
               type="System..Configuration.NameValueSectionHandler"
               allowLocation="true"
               allowDefinition="Everywhere"/>
    </configSections>
    

    注意我改变了类型。我的产品组是这样的:

    <productGroup>
      <add key="product1" value="1" />
      <add key="product2" value="2" />
    </productGroup>
    

    然后我可以完全删除ProductSection类,只需引用我的产品组,如下所示:

    var products = ConfigurationManager.GetSection("productGroup") as NameValueCollection;
    
    if (products.AllKeys.Contains(myProduct))
    {
        var myValue = products[myProduct];
    }    
    
    1 回复  |  直到 8 年前
        1
  •  0
  •   pfx    8 年前

    我注意到两件事

    配置节在配置文件中只能出现1次。
    完全初始化异常显示:

    System.Configuration.ConfigurationErrorsException:配置系统初始化失败---> 每个配置文件中的节只能出现一次 .

    这意味着你只能有一个 product

    <productGroup>
        <product name="my name" id="1" />       
    </productGroup>
    

    如果需要多个,则需要使用 唯一节名称

    <configuration>
        <sectionGroup name="productGroup">
            <section name="product" type="myProject.Stuff.Api.ProductSection" />
            <section name="product2" type="myProject.Stuff.Api.ProductSection" />
        </sectionGroup>
    
        <!-- Other configuration elements -->
    
        <productGroup>
            <product name="my name" id="1" />
            <product2 name="my name 2" id="2" />
        </productGroup>
    </configuration>
    

    最佳做法是在 app/web.config 用它 ,
    其中包括程序集的名称(不带文件扩展名)。
    如果类/节是在外部程序集中定义的,则必须执行此操作;此处 ProductionSection 在除主unittest之一之外的程序集中定义。

    App.config unittest项目的文件。
    程序集的名称包含ProductSectionClass和程序集的名称。

    <section
        name="product"
        type="myProject.Stuff.Api.ProductSection, NameOfTheAssemblyContainingTheProductSectionClass"             
        />