2017-02-03 3 views
0

とサガリポジトリを登録masstransitのドキュメントは、NHiberbateのための例を持っている人は、同じ例を持っていないが、エンティティフレームワーク(SagaDbContextFactory、SagaDbContext)の代わりに、NHibernateのautofac

 
// do not forget registering saga repositories (example for NHibernate) 
var mappings = mappingsAssembly 
    .GetTypes() 
    .Where(t => t.BaseType != null && t.BaseType.IsGenericType && 
     (t.BaseType.GetGenericTypeDefinition() == typeof(SagaClassMapping<>) || 
     t.BaseType.GetGenericTypeDefinition() == typeof(ClassMapping<>))) 
    .ToArray(); 
builder.Register(c => new SqlServerSessionFactoryProvider(connString, mappings).GetSessionFactory()) 
    .As<ISessionFactory>() 
    .SingleInstance(); 
builder.RegisterGeneric(typeof(NHibernateSagaRepository<>)) 
    .As(typeof(ISagaRepository<>)); 
+0

GitHubで問題を開くと修正されます。 –

+0

追加:https://github.com/MassTransit/MassTransit/issues/790 –

+0

これは実際のドキュメントの問題ではありません。 1つのインスタンス/マッピング/リポジトリ登録は簡単ですが、NH 1と同じレベルの一般化ではありません。 –

答えて

1

を使用しているときEntity Frameworkのための例が必要私はこのような鉱山を登録しました:

builder.RegisterAssemblyTypes(typeof(SomeType).Assembly).AsImplementedInterfaces().AsSelf(); 

builder.RegisterGeneric(typeof(SagaRepository<,>)).As(typeof(ISagaRepository<,>)); 

builder.RegisterGeneric(typeof(SagaDbContext<,>)); 

そしてSagaRepositoryインタフェース実装:

internal class SagaRepository<TSaga, TSagaClassMapping> : EntityFrameworkSagaRepository<TSaga>, ISagaRepository<TSaga, TSagaClassMapping> 
    where TSaga : class, ISaga where TSagaClassMapping : SagaClassMapping<TSaga>, new() 
{ 
    public SagaRepository(
     IWorkerConfiguration workerConfiguration) 
     : base(() => new SagaDbContext<TSaga, TSagaClassMapping>(workerConfiguration.ConnectionStrings["SagaRepository"])) 
    { 
    } 
} 

私はその後、私のマッピングごとに継承
internal abstract class BaseInstanceStateMap<TInstance> : SagaClassMapping<TInstance>, IInstanceStateMap<TInstance> where TInstance : BaseSagaInstance 
{ 
    protected BaseInstanceStateMap() 
    { 
     this.Property(x => x.CorrelationId); 
     this.Property(x => x.CurrentState).HasMaxLength(64); 

     this.Property(x => x.Initiated).HasColumnType("datetime2").IsRequired(); 
     this.Property(x => x.Created).HasColumnType("datetime2").IsRequired(); 
     this.Property(x => x.StateChanged).HasColumnType("datetime2").IsOptional(); 
    } 
} 

::私は、基本クラスを使用してマッピングするため

internal class ProductIndexingStateMap : BaseInstanceStateMap<ProductIndexingSagaInstance> 
{ 
    public ProductIndexingStateMap() 
    { 
     this.Property(x => x.ProductId); 
     this.Property(x => x.ProductCorrelation); 
     this.Property(x => x.EncryptedConnectionString); 
    } 
} 
0

あなたが実際にジェネリックとしてEntityFrameworkSagaRepository<T>登録することができますが、それは登録する必要がします DbContextSagaDbContextを使用する場合は、アプリケーションに複数のサガを使用することはできません。そこに行く唯一の方法はカスタムリポジトリ実装とSagaDbContextを汎用タイプのパラメータでバインドすることです。これは@slinzerthegodが彼の例で行っていることです。

また、すべてのタイプを登録する独自のコンテキストを作成することもできます。たとえば、次のように

public class AssemblyScanningSagaDbContext : DbContext 
{ 
    readonly Assembly _mappingAssembly; 

    public AssemblyScanningSagaDbContext(Assembly mappingAssembly, string nameOrConnectionString) 
     : base(nameOrConnectionString) 
    { 
     _mappingAssembly = mappingAssembly; 
    } 

    public AssemblyScanningSagaDbContext(Assembly mappingAssembly, ObjectContext objectContext, bool dbContextOwnsObjectContext) 
     : base(objectContext, dbContextOwnsObjectContext) 
    { 
     _mappingAssembly = mappingAssembly; 
    } 

    public AssemblyScanningSagaDbContext(Assembly mappingAssembly, DbConnection existingConnection, bool contextOwnsConnection) 
     : base(existingConnection, contextOwnsConnection) 
    { 
     _mappingAssembly = mappingAssembly; 
    } 

    public AssemblyScanningSagaDbContext(Assembly mappingAssembly, string nameOrConnectionString, DbCompiledModel model) 
     : base(nameOrConnectionString, model) 
    { 
     _mappingAssembly = mappingAssembly; 
    } 

    public AssemblyScanningSagaDbContext(Assembly mappingAssembly, DbConnection existingConnection, DbCompiledModel model, bool contextOwnsConnection) 
     : base(existingConnection, model, contextOwnsConnection) 
    { 
     _mappingAssembly = mappingAssembly; 
    } 

    protected AssemblyScanningSagaDbContext(Assembly mappingAssembly) 
    { 
     _mappingAssembly = mappingAssembly; 
    } 

    protected AssemblyScanningSagaDbContext(Assembly mappingAssembly, DbCompiledModel model) 
     : base(model) 
    { 
     _mappingAssembly = mappingAssembly; 
    } 

    protected override void OnModelCreating(DbModelBuilder modelBuilder) => 
     modelBuilder.Configurations.AddFromAssembly(_mappingAssembly); 
} 

あなたは、このようなクラスを持っている場合は、次の操作を行うことができます

builder.Register(c => new AssemblyScanningSagaDbContext(typeof(MySagaMapping).Assembly, 
    connectionString).As<DbContext>(); 
builder.RegisterGeneric(typeof(EntityFrameworkSagaRepository<>)) 
    .As(typeof(ISagaRepository<>)) 
    .SingleInstance(); 
builder.RegisterStateMachineSagas(typeof(MySaga).Assembly); 

Autofacは、自動的に工場出荷時のデリゲートを構成することが可能であり、リポジトリコンストラクタにそれを注入します。

Here is the scanning context as gist