1

Right, so I have a Windows service that goes off and does some work on a server every few minutes. The service reads a whole lot of info (host, username, port etc) regarding the server it's connecting to from the App.config and it works just great.

I now have a requirement that the service caters for n different servers. So now my service needs to read from the App.config and do what it needs to do for server1..serverN sequentially. Wait a predetermined time and then start at server1 again.

I don't know how or what would be the best way to store n sets of server settings in the App.config and then programatically determine how many sets of settings there are and then read each set.

I've thought of having a setting that tells me that there are 5 servers and then having settings for server1..server5 but that's really not elegant.

Is there a better way to do this?

My full source file is below:

using System;
using System.Collections;
using System.Text;
using System.Configuration;
using System.Xml;

namespace FTPConfig
{
    public class MyAppConfig : ConfigurationSection
    {
        public static MyAppConfig GetConfiguration()
        {
            MyAppConfig configuration = ConfigurationManager.GetSection("MainSettings") as MyAppConfig;

            if (configuration != null) return configuration;

            return new MyAppConfig();
        }
    }

    [ConfigurationProperty("host", IsRequired = true)]
    public String Host 
    { 
        get 
        { 
            return this["host"] as string; 
        } 
    }
}
Chris A
  • 23
  • 3
  • 1
    I'd say the app.config is ill suited to this task. Why not persist your settings in a serializable xml doc, or in a DB? – Grant H. Nov 21 '12 at 18:11
  • @GrantH. A DB would be seriously overkill for this tiny little service application and since I don't have a UI, I'm hoping for a technical-user editable file that they can edit. Thanks though, I might not have a choice then. – Chris A Nov 21 '12 at 18:18

2 Answers2

2

You can use a custom section in the app.config file, and use any xml you like there.

Community
  • 1
  • 1
wimh
  • 15,072
  • 6
  • 47
  • 98
  • Yeah, I wish I could figure out why I get "The type or namespace name 'ConfigurationSection' could not be found (are you missing a using directive or an assembly reference?)" all the time. I don't know why, but I just can't get this to work no matter what I do... – Chris A Nov 21 '12 at 19:21
  • @ChrisA did you add a reference to `System.Configuration`? – wimh Nov 21 '12 at 20:03
  • yes. I will edit the original question with the full .cs now. – Chris A Nov 21 '12 at 20:42
  • 1
    You sir are a legend!! Thank you very much! Shows what happens when you try to self learn a new language & environment, I would never have though of that! – Chris A Nov 21 '12 at 21:11
0

I wanted to make some settings available for a model class of a library assembly and when searching for solutions I found a class called "XmlConfigurator" described here. In resume, you can create a section in your App.config and map it to any Type you want. For example. Suppose you have the following class:

public class MySettings
{
    public int Setting1 { get; set; }

    public string Setting2 { get; set; }
}

In your app.config, you just have to add:

<configuration>
<configSections>
    <section name="MySettings" type="MyApp.XmlConfigurator, MyApp" />
</configSections>

<MySettings type="MyApp.MySettings, MyApp">
    <Setting1>10</Setting1>
    <Setting2>MyValue</Setting2>
</MySettings>
</configuration>

When you initialize you application, you can easily load it:

var settings = (MyApp.MySettings)ConfigurationManager.GetSection("MySettings");

The XmlConfigurator:

public sealed class XmlConfigurator : IConfigurationSectionHandler
{
    public XmlConfigurator()
    {
    }

    //<?xml version="1.0" encoding="utf-8" ?>
    //<configuration>
    //    <configSections>
    //        <section name="DispatchSettings" type="MyNamespace.XmlConfigurator, MyNamespace.Core" />
    //    </configSections>

    //    <DispatchSettings type="MyNamespace.DispatchSettings, MyNamespace.Core">
    //        <ServiceIsActive>True</ServiceIsActive>
    //        <DispatchProcessBatchSize>100</DispatchProcessBatchSize>
    //    </DispatchSettings>
    public object Create(object parent, object configContext, XmlNode section)
    {
        XPathNavigator navigator = null;
        String typeName = null;
        Type sectionType = null;
        XmlSerializer xs = null;
        XmlNodeReader reader = null;

        try
        {
            Object settings = null;

            if (section == null)
                return settings;

            navigator = section.CreateNavigator();
            typeName = (string)navigator.Evaluate("string(@type)");
            sectionType = Type.GetType(typeName);

            if (sectionType == null)
                throw new ArgumentException("Could not find the specified type: " + typeName);

            xs = new XmlSerializer(sectionType);
            reader = new XmlNodeReader(section);

            settings = xs.Deserialize(reader);

            return settings;
        }
        finally
        {
            xs = null;
        }
    }
}
Community
  • 1
  • 1
Arthur Nunes
  • 6,718
  • 7
  • 33
  • 46