- html - 出于某种原因,IE8 对我的 Sass 文件中继承的 html5 CSS 不友好?
- JMeter 在响应断言中使用 span 标签的问题
- html - 在 :hover and :active? 上具有不同效果的 CSS 动画
- html - 相对于居中的 html 内容固定的 CSS 重复背景?
我一直在寻找一种在 BeforeSaveEntity 方法中组织验证规则的好方法,我在文件中找到了此注释:项目中的 TodoContextProvider.cs:BreezeMvcSPATemplate:
// A second DbContext for db access during custom save validation.
// "this.Context" is reserved for Breeze save only!
最佳答案
很好的问题。答案并不明显,也不容易简要介绍。我会尝试。EFContextProvider
从客户端获取保存数据并(最终)将这些数据转换为 EFContextProvider.Context
中的实体。 .当保存被批准时,EFContextProvider
调用 SaveChanges
此 EF 上的方法 Context
并且其所有内容都保存为单个事务。
有两个潜在的问题。
1. 数据完整性和安全性
客户端数据永远无法完全信任 .如果您的业务规则限制了授权用户可以看到或更改的内容,则必须将客户端派生实体与数据库中的相应实体进行比较。
英孚 Context
不能包含“同一实体”的两个副本。它不能容纳具有相同 key 的两个实体。所以你不能使用 EFContextProvider.Context
既可以从数据库中获取干净的副本,也可以保存带有更改的副本。
您将需要第二个 Context
要获得干净的副本,您必须编写逻辑来比较 EFContextProvider.Context
中要保存的实体的临界值使用第二个 Context
中干净实体的值.
2. 跨实体验证
许多验证不需要将值与干净的实体进行比较。
例如,开箱即用的 System.ComponentModel.DataAnnotations
属性,例如 Required
和 MaxLength
是简单的数据验证,用于确定实体是否为 自洽 .要么有,要么没有。该值小于或不小于最大长度。对于此类测试,您不需要比较实体。
您可以编写自己的自定义 System.ComponentModel.DataAnnotations
比较单个实体内的数据值的属性。您可能有一条规则说 order.InvoiceDate
必须在或之前 order.ShipDate
.那也是自洽测试,您也不需要该比较实体。
如果这些是您唯一关心的验证类型 - 并且您正在使用 EF DbContext
- 您可以让 EF 在保存过程中为您运行它们。您不需要第二个 Context
.
但是跨实体验证 是另一个故事。在跨实体验证中,实体“A”仅在实体“B”(可能还有“C”、“D”、“E”……)的某些条件为真时才有效。例如,您可能要求订单项目具有数据库中已存在的父订单。
父订单很有可能不在 EFContextProvider.Context
中。在您验证订单项目时。
“没问题,”你说。 “我将使用 someItem.Order
导航到父级。”
你不能。首先,它不起作用,因为 EFContextProvider.Context
的延迟加载被禁用了。 . EFContextProvider
禁用延迟加载主要是为了在序列化期间中断循环引用,但也为了防止性能下降 "n+1" bugs在服务器上。
您可以通过随意加载任何实体或相关实体来解决这个问题。但是随后您遇到了第二个问题:您为验证加载的实体可能与您尝试在此批次中保存的另一个实体发生冲突。EFContextProvider
不填充其 Context
一次全部。它开始一一验证实体,将它们添加到 Context
就这样。
继续我们的例子,假设我们已经加载了 someItem
的父订单。验证期间。该订单现在在 EFContextProvider.Context
.
保存过程继续到下一个实体,并且……出人意料,出人意料……下一个实体恰好是相同的父订单。 EFContextProvider
尝试将此副本附加到 Context
它已经有一个副本(我们刚刚加载的那个)......它不能。
有冲突。两个订单中的哪个属于EFContextProvider
?我们刚刚为验证目的加载的干净副本......还是来自客户端的修改后要保存的副本?
也许你认为你知道答案。也许我同意。但事实是,EFContextProvider
抛出异常,因为在 Context
中已经有一个带有该键的订单.
结论
如果您所有的验证都是 自我一致性检查 , EFContextProvider.Context
是你所需要的全部。您不必创建第二个 Context
但是如果您有涉及其他实体的数据安全问题和/或业务逻辑,您需要第二个 Context
...并且您需要足够的 EF 技能才能使用该 Context
.
这是不是 Breeze 或 Entity Framework 的限制 .无论您选择哪种技术,重要的业务逻辑都需要类似的服务器端复杂性。这就是野兽的本性。
关于breeze - 在 BeforeSaveEntity 中使用 this.Context,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/14517945/
我的应用程序允许用户创建产品及其 UOM(测量单位)和条形码在创建过程中,API会检查如果没有输入条形码,则会自动生成。在我决定添加需要 7 位秤条形码的重量产品之前,这种方法一直运行良好。 Befo
我的应用程序允许用户创建产品及其 UOM(测量单位)和条形码创建过程中,API会检查是否没有输入条码,会自动生成。在我决定添加需要 7 位数字秤条形码的重量产品之前,它一直运行良好。 BeforeSa
我一直在寻找一种在 BeforeSaveEntity 方法中组织验证规则的好方法,我在文件中找到了此注释:项目中的 TodoContextProvider.cs:BreezeMvcSPATemplat
我是一名优秀的程序员,十分优秀!