Использование настроек уровня приложения в моделях с расширенным набором доменов - PullRequest
0 голосов
/ 14 сентября 2018

Я хочу иметь глобальную настройку / уровень приложения, которую я хочу использовать в моих моделях доменных имен.

У меня есть метод, который делает некоторые вычисления на основе переданного аргумента.

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

public decimal Calculate(CalculationMethod calculationMethod)
{
    switch (calculationMethod)
    {
        case CalculationMethod.Multiply: 
            return _x * _y; // _x and _y are fields
        case CalculationMethod.Divide: 
            return _x / _y;
    }
}

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

Одним из решений будет чтение конфигурации каждый раз, когда я вызываю этот метод.

Интересно, есть ли какой-нибудь лучший способ, чтобы я мог установить CalculationMethod глобально и никогда не передавать его, а вместо этого иметь некоторую статическую переменную (singleton), которая содержит метод вычисления и считывать его непосредственно внутри моих методов, не передавая его. Но я думаю, что тогда возникнет проблема безопасности потоков.

public decimal Calculate()
{
    // or read it from file here?
    switch (GlobalSettings.CalculationMethod)
    {
        case CalculationMethod.Multiply: 
            return _x * _y; // _x and _y are fields
        case CalculationMethod.Divide: 
            return _x / _y;
    }
}

Я не могу передать это в конструкторе, потому что это не то, что принадлежит моей модели предметной области.

Как решить эту проблему? Есть ли способ лучше двух упомянутых мною?

Я задал этот вопрос в комментарии под ответом Марка Симанна: Настройки уровня приложения в DDD?

1 Ответ

0 голосов
/ 14 сентября 2018

Как объясняет Чистый код , передача флагов методам обычно считается неоптимальным дизайном. Я понимаю, что OP является заменой для другой, более сложной проблемы, но я был бы склонен рекомендовать рефакторинг к полиморфной объектной модели:

public interface ICalculator
{
    decimal Calculate();
}

Теперь вы можете определять реализации по мере необходимости:

public class Multiplier : ICalculator
{
    public decimal Calculate()
    {
        return _x * _y; // _x and _y are fields
    }
}

public class Divider : ICalculator
{
    public decimal Calculate()
    {
        return _x / _y;
    }
}

Вы можете внедрить объект ICalculator в любой класс, который в этом нуждается, используя Constructor Injection. В вашем Composition Root вы можете прочитать файл конфигурации или каким-либо другим способом решить, какую реализацию использовать, а затем создать только один экземпляр этого класса. Это дает объекту время жизни Singleton , так что метод расчета полностью выбирается во время запуска и распределяется между всеми объектами в приложении.

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