2010-12-29 16 views
3

deadhorseには当てはまりませんが、インストールされている.NETフレームワークを検出する方法を探しています。提供されたソリューション(リンク内)は、フレームワークの新しいバージョンがリリースされてからすべての賭けが解除されるまでは、すべてうまくいくようです。この理由は、検出がレジストリキーに依存しているため、フレームワークのv4が規約を破っているように見えるため、v4を検出するために追加の手順が必要です。.NETバージョンの検出を将来的に証明する

.NET v5が表示されても動作する.NETフレームワークを検出する方法はありますか?

EDIT:OK、イライラ.NETバージョン求職者の将来の世代のために、ここでそれを実現するためのコードは次のとおりです。

using System; 
using System.Collections.Generic; 
using System.Linq; 
using System.Text; 
using System.Text.RegularExpressions; 
using System.Diagnostics; 
using Microsoft.Win32; 

private List<string> GetInstalledDotNetFrameworks() 
{ 
    string key = string.Empty; 
    string version = string.Empty; 
    List<string> frameworks = new List<string>(); 

    var matches = Registry.LocalMachine 
       .OpenSubKey(@"SOFTWARE\Microsoft\NET Framework Setup\NDP") 
       .GetSubKeyNames().Where(keyname => Regex.IsMatch(keyname, @"^v\d")); 


    // special handling for v4.0 (deprecated) and v4 (has subkeys with info) 
    foreach (var item in matches) 
    { 
     switch (item) 
     { 
      case "v4.0": // deprecated - ignore 
       break; 

      case "v4":// get more info from subkeys 

       key = @"SOFTWARE\Microsoft\NET Framework Setup\NDP\" + item; 
       string[] subkeys = Registry.LocalMachine 
        .OpenSubKey(key) 
        .GetSubKeyNames(); 


       foreach (var subkey in subkeys) 
       { 
        key = @"SOFTWARE\Microsoft\NET Framework Setup\NDP\" + item + @"\" + subkey; 
        version = Registry.LocalMachine 
          .OpenSubKey(key) 
          .GetValue("Version").ToString(); 

        version = string.Format("{0} ({1})", version, subkey); 
        frameworks.Add(version); 
       } 


       break; 
      case "v1.1.4322": // special case, as the framework does not follow convention 
       frameworks.Add(item); 
       break; 
      default: 

       try 
       { 
        // get the Version value 
        key = @"SOFTWARE\Microsoft\NET Framework Setup\NDP\" + item; 
        version = Registry.LocalMachine 
          .OpenSubKey(key) 
          .GetValue("Version").ToString(); 

        frameworks.Add(version); 

       } 
       catch 
       { 
        // most likely new .NET Framework got introduced and broke the convention 
       } 

       break; 

     } 

    } 

    // sort the list, just in case the registry was not sorted 
    frameworks.Sort(); 

    return frameworks; 
} 

答えて

4

、あなたはおよそこの(より完全なソリューションについては下記を参照)を使用することができます:私のマシン上で

Microsoft.Win32.Registry.LocalMachine 
    .OpenSubKey(@"SOFTWARE\Microsoft\NET Framework Setup\NDP") 
    .GetSubKeyNames().Where(keyname=>Regex.IsMatch(keyname,@"^v\d")) 

を、これが返されます:v2.0.50727の、V3.0、V3.5、V4、V4を.0。サブキーは、おそらく関連するサービスパックを検出するために使用できます。また、SOFTWARE\Microsoft\.NETFrameworkキーを使用すると、v2.0.50727、v3.0、v4.0.30319が返されます。

このパターンが保障される保証はありませんが、それはかなり妥当な賭けです:-)。 http://support.microsoft.com/kb/318785には、バージョン管理について説明するレジストリの詳細に関する情報がいくつかあります。特にInstallを確認する必要がありますが、それはv4.0のように難解です。

編集:私は正しくV4クライアントとフルプロファイルを検出するように、任意のサブキーのインストール情報を含めるレジストリのを検出するために、これを拡張しました。また、RegistryKeyタイプはIDisposableであり、Disposeメソッドが本当に何かをしているように見えます(レジストリキーのロック解除)。

var versionList = new List<string>(); 
using(var ndpKey=Registry.LocalMachine.OpenSubKey(@"SOFTWARE\Microsoft\NET Framework Setup\NDP")) { 
    Action<RegistryKey, Action<RegistryKey,string>> processKids = (node, action) => { 
     foreach(var childname in node.GetSubKeyNames()) 
      using(var child = node.OpenSubKey(childname)) 
       action(child,childname); 
    }; 

    Action<RegistryKey, Func<RegistryKey, bool>> visitDescendants = null; 
    visitDescendants = (regkey, isDone) => { 
     if(!isDone(regkey)) 
      processKids(regkey, (subkey, subkeyname)=>visitDescendants(subkey,isDone)); 
    }; 

    processKids(ndpKey, (versionKey, versionKeyName) => { 
     if(Regex.IsMatch(versionKeyName,@"^v\d")) { 
      visitDescendants(versionKey, key => { 
       bool isInstallationNode = Equals(key.GetValue("Install"), 1) && key.GetValue("Version") != null; 
       if(isInstallationNode) 
        versionList.Add(
         key.Name.Substring(ndpKey.Name.Length+1) 
         + (key.GetValue("SP")!=null ? ", service pack "+ key.GetValue("SP"):"") 
         + " ("+key.GetValue("Version") +") " 
        ); 
       return isInstallationNode; 
      }); 
     } 
    }); 
} 

versionListその後、含まれています

ポイントはありません
v2.0.50727, service pack 2 (2.0.50727.4927) 
v3.0, service pack 2 (3.0.30729.4926) 
v3.5, service pack 1 (3.5.30729.4926) 
v4\Client (4.0.30319) 
v4\Full (4.0.30319) 
+0

ありがとう、私はこのレジストリキーについて知りませんでした - 私はHKEY_LOCAL_MACHINE \ SOFTWARE \ Microsoft \ NET Framework Setup \ NDPに行かなければならないと思った。私はこれがちょうどトリックをするかもしれないと思う。 – AngryHacker

+0

申し訳ありませんが、実際には機能しませんでした。 Software/Microsoft/.NETFrameworkにv3.5が表示されない – AngryHacker

+0

修正済み - 現在、NDPレジストリキーを使用しています。 –

3

あなたは私たちがあなたの未来を伝えることができます期待していますか? :)なぜあなたは最初にそれが必要なのですか?つまり、v4用のアプリを書くと、v5がインストールされているかどうかはどうなるでしょうか? app.configでどのバージョンをサポートしているかを指定できますが、次のバージョンが何であるかを事前に知ることはできません。新しいフレームワークが出てきたら、アプリをテストして、移行するかどうかを決めなければなりません。移行する場合は、app.configと場合によってはコードを変更して、新しいバージョンをリリースします。そうしないと、古いフレームワークのバージョンがインストールされている必要があります。 v5が出てきたのではなく、人々は以前のすべてのフレームワークをアンインストールするでしょう。私はまだ私のマシンにv1.1とv2を持っていて、彼らはしばらく張り付いていると思います。

+0

- データが自分のアプリケーションで使用されていません。しかし、私のアプリケーションは組織内の膨大な数の人々によって使用されているので、ユーザのマシンの能力に関する情報を収集する方法としてアプリケーションを使用することに決定される権限(CPU、RAM、HD空間など) ..)、.NETフレームワークを含む。検出メカニズムが変わるので、毎年2回このルーチンを書き直さなければならないようです。私はそれを過去に置きたいと思っています。 – AngryHacker

3

私はfejesjocoと合意しています。なぜあなたのコードがコンパイルされていない将来のバージョンを検出したいのですか?

Frameworkフォルダ(C:\ Windows \ Microsoft.NET \ Framework)を見ると、以前のすべてのバージョンのFrameworkが最新のバージョンと共にインストールされていることがわかります。あなたのコードが4.0に対してコンパイルされていて5.0が出ても、それは4.0のフォルダを持っています。

今後のバージョンを検出したい理由について、私たちに少し詳しく説明していただければ、より良いお手伝いをすることができます。

+0

@ fejesjocoの答えについては、私のコメントのコンテキストを参照してください。 – AngryHacker

+0

もう少し意味が分かります。関連する.Netフォルダの下のレジストリキーをループして、インストールされているFrameworkのバージョンを取得しないのはなぜですか? HKEY_LOCAL_MACHINE \ SOFTWARE \ Microsoft \ .NETFramework \ [v2.0 | v3.0 | v4.0.30319]をクリックします。私はフレームワークの次のバージョンがv4.5を得るか、v5.0は十分に単純なものでなければならないと思いますが、どう思いますか? – Burt

0

検出ツールに自動更新機能が含まれていますか?要するに

関連する問題