Bagaimana cara memeriksa apakah kunci appSettings ada?

146

Bagaimana saya memeriksa untuk melihat apakah Pengaturan Aplikasi tersedia?

yaitu app.config

<?xml version="1.0" encoding="utf-8" ?>
<configuration>
  <appSettings>
    <add key ="someKey" value="someValue"/>
  </appSettings>
</configuration>

dan di filefile

if (ConfigurationManager.AppSettings.ContainsKey("someKey"))
{
  // Do Something
}else{
  // Do Something Else
}
bitcycle
sumber

Jawaban:

223

MSDN: Configuration Manager.AppSettings

if (ConfigurationManager.AppSettings[name] != null)
{
// Now do your magic..
}

atau

string s = ConfigurationManager.AppSettings["myKey"];
if (!String.IsNullOrEmpty(s))
{
    // Key exists
}
else
{
    // Key doesn't exist
}

sumber
2
Kami memiliki fungsi IsNull SQL-like di perpustakaan kami yang membuat mengambil pengaturan sangat berguna:Dim configValue As String = Util.IsNull(ConfigurationManager.AppSettings.Get("SettingName"), String.Empty)
Eirik H
10
Itu melempar "Referensi objek tidak diatur ke turunan dari suatu objek"
Waqar Alamgir
Tidak, itu salah. Jika "myKey" tidak ada di node xml pengaturan aplikasi, kode dilemparkan pengecualian.
Gionata
jika Anda memeriksa IsNullOrEmpty maka logika Anda untuk "kunci tidak ada" akan berjalan ketika Anda benar-benar memiliki kunci dengan nilai string kosong sebagai pengaturan yang valid
nrjohnstone
3
bukan jawaban terbaik karena ini melempar pengecualian. Divyesh Patel adalah solusi yang lebih baik.
VRPF
81
if (ConfigurationManager.AppSettings.AllKeys.Contains("myKey"))
{
    // Key exists
}
else
{
    // Key doesn't exist
}
Divyesh Patel
sumber
Ini mungkin akan sedikit lebih efisien (?) Jika Anda tidak ingin menggunakan nilai setelahnya. Pertanyaan tersebut secara spesifik menyebutkan pengujian 'jika Pengaturan Aplikasi tersedia'. Karena Ketersediaan menyiratkan keinginan untuk menggunakannya dalam pikiran saya, saya akan mengatakan jawaban yang diberikan oleh user195488 akan lebih bermanfaat bagi orang-orang yang datang ke sini - tetapi secara tegas, jawaban Anda juga benar.
Code Jockey
10
Ini adalah solusi yang jauh lebih baik untuk fakta sederhana yang sebenarnya memeriksa apakah kuncinya ada. Jika saya memiliki nilai kosong untuk kunci saya, solusi yang diberikan oleh user195488 akan memberi saya false positive.
dyslexicanaboko
6
Solusi ini salah. AppSettings adalah NameValueCollection yang secara default tidak peka huruf besar-kecil jika menyangkut pencarian kunci. Namun, LINQ. Berisi metode ekstensi yang Anda gunakan di sini akan menjadi standar untuk perbandingan case-sensitive .
Jax
9

Nilai default yang dikembalikan dengan aman melalui obat generik dan LINQ.

public T ReadAppSetting<T>(string searchKey, T defaultValue, StringComparison compare = StringComparison.Ordinal)
{
    if (ConfigurationManager.AppSettings.AllKeys.Any(key => string.Compare(key, searchKey, compare) == 0)) {
        try
        { // see if it can be converted.
            var converter = TypeDescriptor.GetConverter(typeof(T));
            if (converter != null) defaultValue = (T)converter.ConvertFromString(ConfigurationManager.AppSettings.GetValues(searchKey).First());
        }
        catch { } // nothing to do just return the defaultValue
    }
    return defaultValue;
}

Digunakan sebagai berikut:

string LogFileName = ReadAppSetting("LogFile","LogFile");
double DefaultWidth = ReadAppSetting("Width",1280.0);
double DefaultHeight = ReadAppSetting("Height",1024.0);
Color DefaultColor = ReadAppSetting("Color",Colors.Black);
codebender
sumber
ConfigurationManager.AppSettingstidak case-sensitive, Any(key => key == MyKeynamun
janv8000
@ janv8000 Saya ingin sensitivitas huruf, tetapi memperbarui contoh untuk menanganinya.
codebender
Perbandingan kasus-sensitif yang tepat lebih cepat dengan ToUpper (lihat stackoverflow.com/a/12137/389424 ). Bahkan lebih baik adalah dengan menggunakan string.Equals () kelebihan melewati StringComparisonType.
janv8000
Ini adalah solusi yang sangat bagus untuk masalah ini. Saya telah memodifikasi implementasi sedikit untuk mendukung konsep pengaturan yang diperlukan. Hanya satu hal - ingatlah untuk menambahkan using System.ComponentModel;pernyataan ke kelas Anda untuk mendukung penggunaan TypeDescriptorkelas.
STLDev
3
var isAlaCarte = 
    ConfigurationManager.AppSettings.AllKeys.Contains("IsALaCarte") && 
    bool.Parse(ConfigurationManager.AppSettings.Get("IsALaCarte"));
Johnny Trinh
sumber
2

Jika kunci yang Anda cari tidak ada dalam file konfigurasi, Anda tidak akan dapat mengonversinya menjadi string dengan .ToString () karena nilainya akan nol dan Anda akan mendapatkan "Referensi objek tidak disetel ke instance dari objek "kesalahan. Yang terbaik adalah pertama-tama melihat apakah nilainya ada sebelum mencoba untuk mendapatkan representasi string.

if (!String.IsNullOrEmpty(ConfigurationManager.AppSettings["myKey"]))
{
    String myKey = ConfigurationManager.AppSettings["myKey"].ToString();
}

Atau, seperti yang disarankan Code Monkey:

if (ConfigurationSettings.AppSettings["myKey"] != null)
{
// Now do your magic..
}
John Craft
sumber
2

Opsi atas memberi keleluasaan untuk segala hal, jika Anda tahu tipe kunci, coba parsing bool.TryParse(ConfigurationManager.AppSettings["myKey"], out myvariable);

sam
sumber
2

Saya pikir ungkapan LINQ mungkin yang terbaik:

   const string MyKey = "myKey"

   if (ConfigurationManager.AppSettings.AllKeys.Any(key => key == MyKey))
          {
              // Key exists
          }
mikrofon emas
sumber
yakin ... tapi idunno - apakah ada manfaat untuk metode ini? Jika saya BENAR-BENAR fasih dalam Linq (yang sebagian besar programmer C # akhirnya mungkin akan), maka mungkin akan mudah untuk membaca contoh ini, tapi saya tidak berpikir itu akan lebih mudah - jadi kecuali ada keuntungan efisiensi ... kenapa
Code Jockey
tidak ada keuntungan efisiensi dan sintaksis verbose imo.
John Nicholas
1
ConfigurationManager.AppSettingstidak case-sensitive, Any(key => key == MyKeynamun
janv8000
1

Saya menyukai jawaban codebender , tetapi membutuhkannya untuk bekerja di C ++ / CLI. Inilah yang akhirnya saya lakukan. Tidak ada penggunaan LINQ, tetapi berfungsi.

generic <typename T> T MyClass::ReadAppSetting(String^ searchKey, T defaultValue) {
  for each (String^ setting in ConfigurationManager::AppSettings->AllKeys) {
    if (setting->Equals(searchKey)) { //  if the key is in the app.config
      try {                           // see if it can be converted
        auto converter = TypeDescriptor::GetConverter((Type^)(T::typeid)); 
        if (converter != nullptr) { return (T)converter->ConvertFromString(ConfigurationManager::AppSettings[searchKey]); }
      } catch (Exception^ ex) {} // nothing to do
    }
  }
  return defaultValue;
}
nimchimpsky
sumber
0

Menggunakan sintaks c # baru dengan TryParse bekerja dengan baik untuk saya:

  // TimeOut
  if (int.TryParse(ConfigurationManager.AppSettings["timeOut"], out int timeOut))
  {
     this.timeOut = timeOut;
  }
Reinier van de Wetering
sumber
Selamat datang di SO! Ketika Anda memposting jawaban, coba jelaskan solusi Anda sedikit. Dalam hal ini, ada beberapa jawaban lagi, cobalah untuk mengekspos kelebihan dalam diri Anda.
David García Bodego