Testowalna konfiguracja

W wielu aplikacjach spotkałem się odwołaniami do konfiguracji zaszytymi w kodzie. Najczęściej było to realizowane przez obiekt Singleton, lub statyczne odwołanie do np. pliku XML. Z pozoru wydaje się to wygodnym rozwiązaniem, pozwalającym na łatwy dostęp do zmiennych konfiguracyjnych.

Niestety powoduje to że nasz kod przestaje być testowalny. Nie możemy przy pomocy testów jednostkowych sprawdzić przepływów kodu dla różnych ustawień.

Istnieje bardzo proste rozwiązanie pomagające ten problem łatwo rozwiązać.

  1. Dostęp do konfiguracji powinien być realizowany poprzez interfejs np. IConfig.
  2. Interfejs ten może definiować np. metodę object GetValue(string valueName), lub podobną.
  3. W kontenerze aplikacji rejestrujemy implementację interfejsu pobierającą konfiguracje np. z pliku.
  4. Dla każdej klasy definiujemy interfejs dostarczający dla niej konfigurację:
    public interface ILoggerConfig
    {
        string GetLogDir();
    }
  5. W kontenerze rejestrujemy implementację interfejsu adaptera korzystającą z IConfig:
    class LoggerConfig : ILoggerConfig
    {
        private LoggerConfig config;
    
        public LoggerConfig(IConfig config)
        {
            this.config = config;
        }
    
        public string GetLogDir()
        {
            return (string)config.GetValue("logDir");
        }
    }
  6. Teraz już wystarczy tylko dostarczyć z kontenera interfejs ILoggerConfig i korzystać.

W testach natomiast możemy wygodnie dostarczyć implementację testową (Mock, Stub, Test double) interfejsu i przetestować klasę dla wybranej konfiguracji. Dodatkowy zysk z takiego rozwiązania jest taki, że interfejs ILoggerConfig, informuje na o tym jaka konfiguracja jest potrzebna aby klasa Logger mogła poprawnie działać. Wiemy dzięki temu co testować bez czytania kodu klasy Logger.

Comments:0

Leave a Reply

Your email address will not be published. Required fields are marked *