ConfigurationManager.AppSettings Renvoie Null Dans Le Projet De Test Unitaire

j'ai un projet de test C # unit avec des paramètres d'application dans le app.config fichier. Je teste une classe qui existe dans un autre projet. Cette classe dépend à la fois, ConfigurationManager.AppSettings et ConfigurationManager.ConnectionStrings.

le projet dans lequel réside la classe testée n'a pas d'application.fichier de configuration. J'aurais pensé que, puisque la classe est instanciée dans le contexte du projet de test unitaire, elle utiliserait l'application du projet de test unitaire.fichier de configuration. En effet, il semble que ce soit le cas de la chaîne de connexion.

La classe récupère la chaîne de connexion, sans aucun problème. Cependant, lorsque la classe essaie de récupérer des paramètres d'application, le gestionnaire de configuration renvoie toujours null. Ce qui se passe ici?

Edit 1

je pensais que ce serait peut-être une bonne idée d'essayer de charger certains paramètres dans le projet de test pour voir ce qui se passe. J'ai essayé de charger le réglage de l'unité de test immédiatement avant l'appel le code qui instancie la classe dans le projet externe. Même résultat, rien. Je suppose que je peux exclure l'autre projet de l'équation pour le moment.

Voici un extrait de mon fichier de config:

<configSections>
  <sectionGroup name="applicationSettings"
                type="System.Configuration.ApplicationSettingsGroup, System, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089" >
    <section name="MyNamespace.Properties.Settings"
             type="System.Configuration.ClientSettingsSection, System, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089"
             requirePermission="false" />
  </sectionGroup>
</configSections>

...

<applicationSettings>
  <MyNamespace.Properties.Settings>
    <setting name="Bing_Key"
             serializeAs="String">
      <value>...</value>
    </setting>
  </MyNamespace.Properties.Settings>
</applicationSettings>

et voici comment je m'y suis essayer de charger le paramètre:

string test = System.Configuration.ConfigurationManager.AppSettings["Bing_Key"];
18
demandé sur Jason Boyd 2014-06-19 17:21:33

3 réponses

Vous avez mentionné les paramètres dans les propriétés du projet. Voir si vous pouvez accéder au réglage de cette façon:

string test = Properties.Settings.Default.Bing_Key;

vous pouvez avoir besoin d'obtenir l'assemblage d'exécution de l'endroit où le fichier de paramètres de projet est défini, mais essayez ceci en premier.

EDIT

lorsque vous utilisez le fichier project settings de Visual Studio, il ajoute des choses à votre application.config et crée l'application.la configuration, si elle n'est pas présente. ConfigurationManager ne peut pas toucher ces paramètres! Vous ne pouvez obtenir de ces généré projet.paramètres de fichier de l'aide de la méthode statique. Si vous souhaitez utiliser ConfigurationManager, vous aurez besoin de main écrire votre application.config. Ajoutez vos paramètres comme ceci:

<appSettings>
  <add key="bing_api" value="whatever"/>
</appSettings>
6
répondu Bill Sambrone 2014-06-19 16:16:49

envisagez de refactoriser votre code qui accède à la config pour utiliser un wrapper. Ensuite, vous pouvez écrire mocks pour la classe wrapper et ne pas avoir à gérer l'importation du fichier de configuration pour le test.

Dans une bibliothèque qui leur est commun, quelque chose comme ceci:

public interface IConfigurationWrapper {

    string GetValue(string key);
    bool HasKey(string key);
}

Ensuite, dans vos bibliothèques qui ont besoin d'accéder config, injecter une instance de ce type d'interface dans la classe qui a besoin de lire config.

public class MyClassOne {

    private IConfigurationWrapper _configWrapper;

    public MyClassOne(IConfigurationWrapper wrapper) {
        _configWrapper = wrapper;
    } // end constructor

    public void MethodThatDependsOnConfiguration() {
        string configValue = "";
        if(_configWrapper.HasKey("MySetting")) {
            configValue = _configWrapper.GetValue("MySetting");
        }
    } // end method

} // end class MyClassOne

puis, dans l'un des vos bibliothèques, créez une implémentation qui dépend du fichier de configuration.

public class AppConfigWrapper : IConfigurationWrapper {

    public string GetValue(string key) {
        return ConfigurationManager.AppSettings(key);
    }

    public bool HasKey(string key) {
       return ConfigurationManager.AppSettings.AllKeys.Select((string x) => x.ToUpperInvariant()).Contains(key.ToUpperInvariant());
    }
}

Ensuite, dans le code qui appelle votre classe.

//Some method container
MyClassOne dataClass = new MyClassOne(new AppConfigWrapper());

dataClass.MethodThatDependsOnConfiguration();

alors dans votre test, vous êtes libre de l'esclavage de dépendance. :) Vous pouvez soit créer une fausse version qui implémente IConfigurationWrapper et la passer pour votre test, où vous codez dur les valeurs de retour de la GetValue et HasKey fonctions, ou si vous utilisez une bibliothèque moqueuse comme Moq:

Mock<IConfigurationWrapper> fakeWrapper = new Mock<IConfigurationWrapper>();

fakeWrapper.Setup((x) => x.GetValue(It.IsAny<string>)).Returns("We just bypassed config.");

MyClassOne testObject = new MyClassOne(fakeWrapper.Object);
testObject.MethodThatDependsOnConfiguration();

Voici un article qui couvre le concept (bien que, pour les formulaires web, mais les concepts sont les mêmes): http://www.schwammysays.net/how-to-unit-test-code-that-uses-appsettings-from-web-config/

10
répondu xDaevax 2014-06-19 15:50:27

Et puis il cria: "NOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOO".

Cite: j'ai un projet de test C# unit avec des paramètres d'application dans l'application.fichier de configuration. Je teste une classe qui existe dans un autre projet. Cette classe dépend des deux, ConfigurationManager.AppSettings and ConfigurationManager.ConnectionStrings.

Vous ne le faites pas. JAMAIS!!!! Pourquoi? parce que vous avez créé une dépendance. Utilisez plutôt l'injection de dépendances pour que la classe puisse faire son travail sans avoir à pic dans le fichier de configuration qui appartient à la demande.

0
répondu Gregory A Beamer 2018-07-13 21:38:57