Считать конфигурацию в коллекцию объектов базового класса как объектов дочернего класса - PullRequest
0 голосов
/ 30 октября 2019

У меня есть основное приложение .Net, которое использует файл appsettigs.json для хранения конфигурации. Мне нужно загрузить раздел конфигурации в коллекцию, не просматривая их. Я знаю, что могу использовать метод Bind (), чтобы связать коллекцию в коллекцию того же типа. Но здесь я пытаюсь получить объекты типа дочернего класса в коллекции вместо базового типа класса.

"Sections": [
{
  "Name": "Section 1",
  "Type":"type1"

},
{
  "Name": "Section 2",
  "Type":"type2"

},
{
  "Name": "Section 3",
  "Type":"type1"

},
{
  "Name": "Section 4",
  "Type":"type1"

},
{
  "Name": "Section 5",
  "Type":"type2"

}]

Я использую приведенный ниже код для чтения файла конфигурации.

var configBuilder = new ConfigurationBuilder()
            .SetBasePath(Directory.GetCurrentDirectory())
            .AddJsonFile("appsettings.json");

        var Configuration = configBuilder.Build();

Я знаю, что могу использовать Configuration.Bind ()

Классы:

    Public abstract class BaseSection:ISection
    {
    public string Name;
    ..
    }


Public class Type1:BaseSection
{
public string Name;
..
}

Public class Type2:BaseSection
{
public string Name;
..
}

Мне нужно прочитать конфигурацию из файла appsettings.json в List, чтобызапись в файле конфигурации с "type = type1" будет иметь тип в объекте Type1, а "type = type2" будет иметь тип в объекте Type2.

Так что моя коллекция из указанных выше записей конфигурации должна иметь

[
    Object Of Type1
    Object Of Type2
    Object Of Type1
    Object Of Type1
    Object Of Type2
]

Я не хочу читать данные один раз, а затем набирать их.

Пожалуйста, поделитесь мнениями и мнениями. Заранее спасибо.

1 Ответ

1 голос
/ 30 октября 2019

Вы можете использовать промежуточный список с привязкой, но вам нужно проделать определенную работу, чтобы создать правильный тип. Вы можете сделать что-то вроде этого:

 namespace CoreApp1
 {
    public class ConfigSectionItem: BaseSection
    {
        public string Type { get; set; }
    }

    class Program
    {
        static void Main(string[] args)
        {
            var configBuilder = new ConfigurationBuilder()
            .SetBasePath(Directory.GetCurrentDirectory())
            .AddJsonFile("appsettings.json");

            var configuration = configBuilder.Build();
            var confList = new List<ConfigSectionItem>();

            configuration.GetSection("Sections").Bind(confList);

            foreach (var confItem in confList)
            {
                var typeToBuild = Type.GetType($"CoreApp1.{confItem.Type}"); // Remember to do some checks with typeToBuild (not null, ...)
                var newInstance = (BaseSection)Activator.CreateInstance(typeToBuild);

                newInstance.Name = confItem.Name; // Use automapper or reflexion

                // do what you want here with your newInstance
                Console.WriteLine(newInstance.GetType().FullName + " " + newInstance.Name);
            }
        }
    }

    public abstract class BaseSection
    {
        public string Name;
    }

    public class Type1 : BaseSection
    {
    }

    public class Type2 : BaseSection
    {
    }
 }

Обязательно используйте Microsoft.Extensions.Configuration.Binder И, пожалуйста, будьте внимательны с учетом регистра в .json или поработайте с заглавными буквами:

  "Type": "Type1"
  "Type": "Type2"
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...