2011-06-24 9 views
10

このコードを各リポジトリクラスで使用すると、SQLプロファイリングが機能するようになりますが、そのコードを各クラスからStructureMapがDBを処理するクラスに移動する必要があります。リポジトリクラスのStructureMap DBServiceRegistryとMVC-mini-profiler?

例:

public DB CreateNewContext() 
    { 
     var sqlConnection = new SqlConnection(ConfigurationManager.ConnectionStrings["connection"].ConnectionString); 
     var profiledConnection = ProfiledDbConnection.Get(sqlConnection); 
     return DataContextUtils.CreateDataContext<DB>(profiledConnection); 
    } 

    public SqlRecipeRepository(DB dataContext) 
    {   
     _db = CreateNewContext(); 
    } 

今私はDataContextの変数はプロファイルバージョンであるので、私のDBServiceRegistryクラスから来てほしいです。ここで

がDBServiceRegistryクラスです:

public class DBServiceRegistry : Registry 
{ 
    public DBServiceRegistry() 
    { 
     var sqlConnection = new SqlConnection(ConfigurationManager.ConnectionStrings["GetMeCooking.Data.Properties.Settings.server"].ConnectionString); 
     var profiledConnection = ProfiledDbConnection.Get(sqlConnection); 
     For<DB>().HybridHttpOrThreadLocalScoped().Use(() => DataContextUtils.CreateDataContext<DB>(profiledConnection)); 

     //Original method just had this: 
     //For<DB>().HybridHttpOrThreadLocalScoped().Use(() => new DB()); 

    } 
} 

このコードにエラーが発生することはありませんが、私は、SQLプロファイリングを得ることはありません、私が間違って何をやっていますか?

+0

私がすることができますプロファイリングの部分がうまくいかない理由を本当に教えてください。しかし、コードに深刻な問題が1つあります。すべてのDbContextに使用される1つの接続インスタンスをレジストリに作成しています。 – PHeiberg

+1

LINQ-to-SQL接続の '.Log'パラメータはどこに割り当てられていますか?また、 'ObjectFactory.GetInstance ()'はどこに行っていますか? –

答えて

1

コメントは正しいです.Sql接続をOut行とともに作成すると、scopeコマンドがオーバーライドされます。

はるかに良い匿名デリゲートに全体の多くをカプセル化する

using System.Configuration; 
using System.Data.SqlClient; 
using System.Threading.Tasks; 

using StructureMap; 
using StructureMap.Configuration.DSL; 

using Xunit; 

public class DBServiceRegistry : Registry 
{ 
    private string connString = ConfigurationManager.ConnectionStrings["GetMeCooking.Data.Properties.Settings.server"].ConnectionString; 

    public DBServiceRegistry() 
    { 
     For<DB>().HybridHttpOrThreadLocalScoped().Use(
      () => 
       { 
        var sqlConnection = new SqlConnection(connString); 
        var profiledConnection = new StackExchange.Profiling.Data.ProfiledDbConnection(sqlConnection, MiniProfiler.Current); 
        return DataContextUtils.CreateDataContext<DB>(profiledConnection); 
       }); 
    } 
} 

あなたはスコープが正しいことを確認するためにユニットテストを使用することができます(テスト構文はxunit.netある)

public class DBRegistryTests : IDisposable 
{ 
    private Container container; 

    public DBRegistryTests() 
    { 
     // Arrange (or test setup) 
     container = new Container(new DBServiceRegistry()); 
    } 

    [Fact] 
    public void ConnectionsAreSameInThread() 
    { 
     // Create two connections on same thread 
     var conn1 = container.GetInstance<DB>(); 
     var conn2 = container.GetInstance<DB>(); 

     // Assert should be equal because hybrid thread is scope 
     // and test executes on same thread 
     Assert.Equal(conn1, conn2); 

     // Other assertions that connection is profiled 
    } 

    [Fact] 
    public void ConnectionAreNotSameInDifferentThreads() 
    { 
     var conn1 = container.GetInstance<DB>(); 

     // Request second connection from a different thread 
     // (for < c# 4.0 use Thread instead of task) 
     var conn2 = new Task<DB>(() => this.container.GetInstance<DB>()); 
     conn2.Start(); 
     conn2.Wait(); 

     // Assert that request from two different threads 
     // are not the same 
     Assert.NotEqual(conn1, conn2.Result); 
    } 

    public void Dispose() 
    { 
     // Test teardown 
     container.Dispose(); 
    } 
}