I found a solution to this problem, where a unit of work will only be executed if no errors are thrown.
Register unit of work as InstancePerLifetimeScope in Autofac
builder.RegisterType(typeof (UnitOfWork)) .As(typeof (IUnitOfWork)).InstancePerLifetimeScope();
Then I created a combined EndpointBehavior and ErrorHandler.
public class UnitOfWorkEndpointBehavior : BehaviorExtensionElement, IEndpointBehavior { public void Validate(ServiceEndpoint endpoint) { } public void AddBindingParameters(ServiceEndpoint endpoint, BindingParameterCollection bindingParameters) { } public void ApplyDispatchBehavior(ServiceEndpoint endpoint, EndpointDispatcher endpointDispatcher) { var unitOfWorkInstanceHandler = new UnitOfWorkInstanceHandler(); endpointDispatcher.ChannelDispatcher.ErrorHandlers.Add(unitOfWorkInstanceHandler); endpointDispatcher.DispatchRuntime.InstanceContextInitializers.Add(unitOfWorkInstanceHandler); } public void ApplyClientBehavior(ServiceEndpoint endpoint, ClientRuntime clientRuntime) { } protected override object CreateBehavior() { return new UnitOfWorkEndpointBehavior(); } public override Type BehaviorType { get { return typeof (UnitOfWorkEndpointBehavior); } } } public class UnitOfWorkInstanceHandler : IInstanceContextInitializer, IErrorHandler { private bool _doCommit = true; public void Initialize(InstanceContext instanceContext, Message message) { instanceContext.Closing += CommitUnitOfWork; } void CommitUnitOfWork(object sender, EventArgs e) {
Register endpoint behavior in web.config
<system.serviceModel> ... <extensions> <behaviorExtensions> <add name="UnitOfWork" type="Namespace.UnitOfWorkBehavior, Namespace"/> </behaviorExtensions> </extensions> <behaviors> <endpointBehaviors> <behavior name=""> <UnitOfWork/> </behavior> </endpointBehaviors> ... </behaviors> ... </system.serviceModel>
source share