我正在建立一个新的MVC支付站点,在一个单独的项目中使用依赖注入的数据库连接,并像我一样尝试一些新的东西。目前,我正在尝试从数据库加载现有事务,授权卡支付,然后将结果保存回数据库。简单明了,但是当我打电话给SaveChanges()
时,没有任何东西得到保存,而且我已经没有什么可以尝试了。
此数据库交互由CheckoutDataProvider
:
public class CheckoutDataProvider : ICheckoutDataProvider
{
private readonly CheckoutEntities _context;
public CheckoutDataProvider(CheckoutEntities _context)
{
this._context = _context;
}
public ITransaction GetTransactionDetails(Guid transactionId)
{
var trans = _context.Transactions.FirstOrDefault(x => x.CheckoutTransactionId == transactionId);
return trans; // It's OK if trans == null, because the caller will expect that.
}
public void AddAuthorization(ITransaction transaction, IAuthorizationHistory history)
{
try
{
var trans = (Transaction)transaction;
var hist = (AuthorizationHistory)history;
trans.AuthorizationHistories.Add(hist);
_context.SaveChanges();
}
catch (DbEntityValidationException ex)
{
throw new InvalidDataException(ex.EntityValidationErrors.First().ValidationErrors.First().ErrorMessage, ex);
}
}
}
Transaction
和AuthorizationHistory
是EF对象,直接对应于数据库表。 CheckoutEntities
是Ninject注入的上下文。
GetTransactionDetails()
完美无瑕。我给它transactionId,我得到了对象,然后我使用该数据来运行卡并生成AuthorizationHistory
类。然后我调用AddAuthorization()
将它附加到事务并将其保存到数据库。但是新的AuthorizationHistory
对象和原始Transaction
的任何更改都无法保存。
我可以通过检查_context
对象,它不知道任何更改,如果我使用GetTransactionDetails()
进行更改(在它作为接口返回之前),他们将坚持。所以它看起来像是一个问题(无论如何这让我觉得很蠢,所以我很想知道这就是问题所在。)
我错过了一些明显的东西吗?有什么东西不能让这个工作吗?有没有办法避免在AddAuthorization()
中投射?
答案 0 :(得分:1)
可能您没有在GetTransactionDetails和AddAuthoritzation之间共享相同的DBContext。由于这个原因,实体框架无法跟踪更改。
为Web请求设置DBContext的范围生命周期,您可以使用带有.InRequestScope()
https://github.com/ninject/ninject/wiki/Object-Scopes的Ninject执行此操作,使用此选项将在Web请求期间使用相同的DBContext。