2013-02-23 13 views
8

次のように見えること、私はApp.configファイルを持っているWPFとエンティティフレームワークを使用して:私は実行すると接続文字列内の%APPDATA%は実際のフォルダに代わるものではありませんか?

System.Data.EntityException: The underlying provider failed on Open. ---> System.Data.SqlServerCe.SqlCeException: The path is not valid. Check the directory for the database. [ Path = %APPDATA%\Folder\Database.sdf ] 

:このコードを使用している場合

<?xml version="1.0" encoding="utf-8"?> 
<configuration> 
    <connectionStrings> 
    <add name="DatabaseEntities" connectionString="metadata=res://*/Model.csdl|res://*/Model.ssdl|res://*/Model.msl;provider=System.Data.SqlServerCe.4.0;provider connection string=&quot;Data Source=%APPDATA%\Folder\Database.sdf&quot;" providerName="System.Data.EntityClient" /> 
    </connectionStrings> 
</configuration> 

それは常に次のようなエラーがスローされますコマンドプロンプトからパス "%APPDATA%\ Folder \ Database.sdf"を削除し、 "%APPDATA%"を削除してパスをハードコーディングすると、%APPDATA%のように見えます実際のフォルダの場合...

ありがとう、

+1

'%APPDATA% 'の代わりにあなたの接続文字列に' | DataDirectory | 'を使用してくださいあなたの問題を解決するかどうか教えてください。 –

答えて

21

すでにご了承いただいているように、%APPDATA%またはその他の環境変数は接続文字列のそれぞれの値に置き換えられません。環境変数は、オペレーティングシステムのシェルに関連するものです。コマンドプロンプトは入力された値を明示的に解析し、環境変数を代用するため、コマンドプロンプトで動作します。これは、.NET Framworkが通常実行するものではありません。

これを実現するには、%APPDATA%Environment.GetFolderPath(Environment.SpecialFolder.ApplicationData)またはEnvironment.GetEnvironmentVariable("APPDATA")を使用)の値を手動で入力する必要があります。 2つのオプションがあります。

  1. は、あなたの接続文字列を変更し、|DataDirectory|を使用

    <connectionStrings> 
        <add name="DatabaseEntities" connectionString="metadata=res://*/Model.csdl|res://*/Model.ssdl|res://*/Model.msl;provider=System.Data.SqlServerCe.4.0;provider connection string=&quot;Data Source=|DataDirectory|\Database.sdf&quot;" providerName="System.Data.EntityClient" /> 
    </connectionStrings> 
    

    (データベースファイルへのパスに|DataDirectory|の使用を注意してください。)

    を次に価値を提供しますアプリケーションのメインメソッドで|DataDirectory|の場合:

    AppDomain.CurrentDomain.SetData("DataDirectory", 
        Environment.GetFolderPath(Environment.SpecialFolder.ApplicationData)); 
    

    this MSDN page for more informationを参照してください。

  2. ObjectContextクラスの接続文字列を手動で指定します。あなたは、接続文字列を解析し、変更することができますこの方法:

    public static string GetConnectionString() 
    { 
        var conStr = System.Configuration.ConfigurationManager.ConnectionStrings["DatabaseEntities"].ConnectionString; 
        return conStr.Replace("%APPDATA%", 
         Environment.GetFolderPath(Environment.SpecialFolder.ApplicationData)); 
    } 
    

    以降:

    var db = new DatabaseEntities(GetConnectionString()); 
    

    またはサブクラスあなたはObjectContextクラス、常に新しい接続文字列を使用します。

    public class MyDatabaseEntities : DatabaseEntities 
    { 
        public MyDatabaseEntities() 
         : base(GetConnectionString()) 
        { 
        } 
    
        public static string GetConnectionString() 
        { 
         var conStr = System.Configuration.ConfigurationManager.ConnectionStrings["DatabaseEntities"].ConnectionString; 
         return conStr.Replace("%APPDATA%", 
          Environment.GetFolderPath(Environment.SpecialFolder.ApplicationData)); 
        } 
    } 
    

    と使用をどこでも新しいクラス。

+0

これは初めてエンティティフレームワークを使用しています。正直なところ、ConnectionStringが読み込まれるCODEを見つけることができないため、APPDATAの.Replaceをどこで行うのかわかりません。開始時に私はConfigurationManagerを使ってそれを読み込み、それを元に戻すことを見ていますが、\ Program Files \の下にあるファイルを見ると変更する権利はありません...? – JSchwartz

+0

@JSwwartz必要な情報をすべて追加しました。 –

+0

こんにちは私はVisual Studio 2013を使用していますが、 'ConfigurationManager'という名前空間は 'System.Configuration'という名前空間に存在しません。アセンブリの参照がありませんか? – Cyberguille

1

あなたは相対パスでのコードで%APPDATA%を交換する必要が -

var connectionString = ConfigurationManager.ConnectionStrings["DatabaseEntities"] 
                  .ConnectionString;  
connectionString.Replace("%APPDATA%", 
    Environment.GetFolderPath(Environment.SpecialFolder.ApplicationData); 
4

私は別のオプションを持っています。私たちは何も交換する必要はありません。私は以下の接続文字列を置換せずに使用しており、うまくいきます。

<connectionStrings> 
    <add name="ProjectManagementDBEntities" connectionString="metadata=res://*/Models.ProjectManagementModels.csdl|res://*/Models.ProjectManagementModels.ssdl|res://*/Models.ProjectManagementModels.msl;provider=System.Data.SqlClient;provider connection string=&quot;data source=(LocalDB)\MSSQLLocalDB;attachdbfilename=|DataDirectory|\ProjectManagementDB.mdf;integrated security=True;MultipleActiveResultSets=True;App=EntityFramework&quot;" providerName="System.Data.EntityClient"/> 
    </connectionStrings> 

主な変更点は、私はこれが誰かを救うことを願っていますdata source=(LocalDB)\MSSQLLocalDB;attachdbfilename=|DataDirectory|\ProjectManagementDB.mdf;integrated security=True;

です。

関連する問題