5

私のドメインモデルは、例えば次の object を提供しますReport : IEntity<Report>。私は通常、ストアド プロシージャから Oracle ユーザー定義型オブジェクト (またはコレクション型) を取得します。すべてのタイプについて、C# クラスは ODP.NET Visual Studio カスタム クラス ウィザードによって生成されます。したがって、次のクラスがあります。

public class UDT_REPORT : INullable, IOracleCustomType, IXmlSerializable {
    private bool m_IsNull;
    private decimal m_REPORT_ID;
    private decimal m_VALUE;                
    // etc
}

現在、C# アプリケーション用の新しいデータ アクセス レイヤーを作成しようとしています。この場合、疎結合とより良いテスト容易性を実現するために、リポジトリ パターンを適用したいと思います。しかし、これらの生成されたクラスをリポジトリに統合するにはどうすればよいでしょうか? ReportRepositoryクラスをどのように設計するか?

public interface IReportRepository
{         
    Report Find(ReportId id);
    IList<Report> FindAll();
    void Store(Report Report);
}

次のアプローチを使用する必要がありますか?Read<T>()たとえば、データの取得とマッピングのために特定のデリゲートを使用してジェネリック メソッドを公開する静的 DB プロキシ クラス。そして、db プロバイダーを作成するためのファクトリー。

public static T Read<T>(string sql, Func<IDataReader, T> fetch, object[] parms = null)
{
    using (var connection = factory.CreateConnection())
    {
        connection.ConnectionString = connectionString;

        using (var command = factory.CreateCommand())
        {
            // Add connection; sql command text; 
                     // add parameters via some extension method   
            // Open and close connection                                                                         
            T t = default(T);
            var reader = command.ExecuteReader();
            if (reader.Read()) {
                t = fetch(reader);
            }
            return t;
        }
    }
}

次のデリゲートは、関連する UDT オブジェクトをフェッチし、それをドメイン オブジェクトにマッピングするために使用されますReport

private static Func<IDataReader, Customer> Fetch = reader =>
{                                             
            UDT_REPORT report = reader.GetValue(reader.GetOrdinal("out_param_report"));
            Report report = Mapping.Map(reportEntity);          
            return report;
};

このアプローチについてどう思いますか?ODP.NETタイプをリポジトリに統合するためのより良いアプローチはありますか? または、生成された UDT クラスを避けて、代わりに ORM フレームを追加する必要がありますか?

4

1 に答える 1

0

私が最初に EF を採用したとき、インターフェイスとリポジトリを使用しましたが、ほとんど価値がないことがわかりました。これは、スタックが現在どのように見えるかの例です。

環境:

Imports System.Configuration
Imports System.Data.Entity
Imports System.Collections.Specialized

Imports Oracle.DataAccess.Client
Imports System.Reflection

Public Class MyContext
    Inherits System.Data.Entity.DbContext

    Public Property MyTables As DbSet(Of MyTable)

    Public Sub New()
        MyBase.New(
            New OracleConnection(
                ConfigurationManager.ConnectionStrings(
                    "Entities").ConnectionString
                ),
            True
        )
    End Sub

End Class

サンプル エンティティ:

Imports System.ComponentModel.DataAnnotations
Imports System.ComponentModel.DataAnnotations.Schema

Public Class MyTable

    <Key()>
    <Required()>
    Public Property KeyColumn As Int64

    <StringLength(50)>
    <Column("LegacyColumnName")>
    Public Property Name As String

    <StringLength(1000)>
    Public Property Description As String

    <Required()>
    Public Property IsActive As Int64

    Public Property DateCreated As DateTime?

End Class

サンプル LINQ:

Public Function GetMyTables()
    Try
        Using MCTX As New MyContext()
            Return (
                From T In MCTX.MyTables
                Order By T.Name
                Select New With {
                    T.KeyColumn,
                    T.Name,
                    T.IsActive
                }).ToArray
        End Using
    Catch ex As Exception
        Return ReportException(
            "An error occurred trying to retrieve the table list", ex)
    End Try
End Function

補足として、取得を行うためにプロシージャを作成する理由がわかりません。それは EF を使用する目的に反することではありませんか。それはあなたのためにそれをします。

于 2013-04-07T22:54:32.803 に答える