ModelState
UnitOfWorkを作成して使用する前に、とHttpContext.Error
プロパティをチェックする新しいアクションフィルターを作成します。
public class TransactionalAttribute : ActionFilterAttribute
{
private IUnitOfWork _unitOfWork;
public override void OnActionExecuting(ActionExecutingContext filterContext)
{
if (filterContext.Controller.ViewData.ModelState.IsValid && filterContext.HttpContext.Error == null)
_unitOfWork = DependencyResolver.Current.GetService<IUnitOfWork>();
base.OnActionExecuting(filterContext);
}
public override void OnActionExecuted(ActionExecutedContext filterContext)
{
if (filterContext.Controller.ViewData.ModelState.IsValid && filterContext.HttpContext.Error == null && _unitOfWork != null)
_unitOfWork.SaveChanges();
base.OnActionExecuted(filterContext);
}
}
UnitOfWorkのサンプルnhibernate実装(IoCに登録):
public class NhibernateUnitOfWork : IUnitOfWork
{
private readonly ISession _session;
private ITransaction _transaction;
public NhibernateUnitOfWork(ISession session)
{
_session = session;
_transaction = session.BeginTransaction();
}
public void Dispose()
{
if (_transaction == null)
return;
if (!_transaction.WasCommitted)
_transaction.Rollback();
_transaction.Dispose();
_transaction = null;
}
public void SaveChanges()
{
_transaction.Commit();
}
}
使用法:
[HttpPost, Transactional]
public virtual ActionResult Create(CreateModel model)
{
if (!ModelState.IsValid)
return View(model);
var instruction = new Instruction(CurrentUser);
Mapper.Map(model, instruction);
_repository.Save(instruction);
return RedirectToAction("Details", new {id = instruction.Id});
}
ソース: http: //blog.gauffin.org/2012/06/how-to-handle-transactions-in-asp-net-mvc3/