gpt4 book ai didi

c# - 使用 Nhibernate 静默插入失败

转载 作者:太空宇宙 更新时间:2023-11-03 23:17:52 24 4
gpt4 key购买 nike

我的 NHibernate 插入有问题

交易开始顺利,我的选择正确完成,我也从序列中选择下一个值,并提交交易,但是我的 NHprofiler 中没有插入内容,也没有出现错误。我使用 Session.OpenSession(ReadCommited) & Transaction知道会发生什么吗?

代码

class NHUnitOfWok : INHibernateUnitOfWork
{
private readonly ISession _session;
private bool _isDisposed;
private IsolationLevel _isolationLevel;

public NHUnitOfWok(ISession session)
{
_session = session;
_session.FlushMode = FlushMode.Never;
_isolationLevel = IsolationLevel.ReadCommitted;
}

internal ISession Session
{
get { return _session; }
}

public void SaveChanges()
{
Session.Flush();
}

public void CancelChanges()
{
Session.Clear();
}

public void Commit()
{
Session.Transaction.Commit();
}

public void Rollback()
{
Session.Transaction.Rollback();
}


public void WithinNewSession(Action<ISession> actionToExecute, IsolationLevel? isolationLevel = null)
{
using (var tempSession = Session.SessionFactory.OpenSession())
{
using (var transaction = tempSession.BeginTransaction(isolationLevel ?? _isolationLevel))
{
actionToExecute(tempSession);
transaction.Commit();
}
}
}

public void WithinTransaction(Action action, IsolationLevel? isolationLevel = null)
{
Enforce.NotNull(action, "action");

WithinTransaction<object>(() =>
{
action();
return null;
});
}

public T WithinTransaction<T>(Func<T> func, IsolationLevel? isolationLevel = null)
{
Enforce.NotNull(func, "func");

if (Session.Transaction != null && Session.Transaction.IsActive)
{
return func.Invoke();
}

using (var localTran = Session.BeginTransaction(isolationLevel ?? _isolationLevel))
{
try
{
var funcRes = func.Invoke();
localTran.Commit();

return funcRes;
}
catch (TransactionException ex)
{
throw new DataException(Resource.TransactionException, ex);
}
catch (Exception ex)
{
if (Session.Transaction.IsActive)
localTran.Rollback();
throw new DataException(Resource.TransactionException, ex);
}
}
}

public bool IsStarted()
{
return Session.Transaction != null && Session.Transaction.IsActive;
}

public void Start()
{
if (Session.Transaction == null || !Session.Transaction.IsActive)
{
Session.BeginTransaction(_isolationLevel);
}
}

private void Dispose(bool disposing)
{
if (!disposing || _isDisposed)
{
return;
}
_isDisposed = true;
}

#region IDisposable Members

public void Dispose()
{
Dispose(true);
GC.SuppressFinalize(this);
}

#endregion
}

最佳答案

FlushMode.Never 可能适用于只读事务,但可能不适用于其他任何事务。它的 xml 文档指出:

The ISession is never flushed unless Flush() is explicitly called by the application. This mode is very efficient for read only transactions.

所以不要默认使用它。
至少这是我的建议。我知道出于“性能”的原因,有一些潜伏的建议可以使用它,但是通过注释掉它来检查你是否仍然有问题。
无论如何,我从不首先优化运行时性能,我认为开发人员性能应该是优先考虑的。 (除非应用程序有实际的、经过验证的和相应的运行时性能问题。或者,当然,当代码在运行时执行复杂性方面是一个明显的编码恐怖时,例如无动机的 O(n²) 算法或最差。)

如果您想坚持使用该模式,请在提交事务之前在 session 中调用 Flush(或者按照 here by Andrew 的描述,选择 FlushMode.Commit)。但实际上,这种选择是开发人员不得不使用它的陷阱。

查看默认模式文档,Auto:

The ISession is sometimes flushed before query execution in order to ensure that queries never return stale state. This is the default flush mode.

您是否愿意冒因在某些数据更改后同一 session 中发生的查询中出现意外过时数据而出现细微错误的风险?

旁注:为什么使用 Invoke 使代码“复杂化”?参见 this .

关于c# - 使用 Nhibernate 静默插入失败,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/36651678/

24 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com