我正在设计一个应用程序,其中Order
个对象需要具有顺序且用户友好的Id
字段。我正在避免使用HiLo
算法,因为它产生了相当大的间隙(参见here)。当然,Guid
值会使我的公司用户成为香蕉。我也避免使用Oracle序列,因为它的主要缺点是:
(来自:NHibernate POID Generators revealed)
后插入生成器,作为名称 建议,在之后分配id 实体存储在数据库中。一个 执行select语句 数据库。它们有许多缺点, 在我看来,他们必须被使用 仅限棕地项目。的那些 发电机是我们不建议的 作为NH团队。
>一些缺点是 以下
- 工作单位被打破了 那些策略。无论如何 你正在使用FlushMode.Commit 将结果保存在insert语句中 反对DB。作为最佳实践,我们 应该将插入推迟到提交, 但使用后插入生成器 让它在保存时提交(这是什么 UoW不这样做)。
- 那些策略 取消batcher,你不能采取 发送多个查询的优点 立刻(因为它必须到数据库) 保存时间。
有关实施用户友好ID的任何想法/经验,它们之间没有重大差距吗?
修改
Id
字段是我的公司用户可以记住的字段,甚至可以通过其代码讨论和/或通过电话交谈来讨论特定的Order
字段。 “我打算知道为什么订单#1625被拒绝了。”。Id
不需要严格无间隙,但我担心我的用户在看到100,201,305等差距时会感到困惑。对于我以前的项目,我目前使用Oracle序列实现NHibernate,在抛出异常时偶尔会丢失一些序列,但是对它们保持相当整齐的顺序。它们的缺点是它们如何打破工作单元,无论是否有Save
,每个Session.Flush
命令都会对数据库产生额外的命中。答案 0 :(得分:1)
一种选择是保留一个只存储递增值的键表。这可能会引入一些问题,即可能的锁定问题以及对数据库的额外命中。
另一种选择可能是通过“用户友好ID”来改进您的意思。这可以包括日期/时间和客户特定序列(或包括客户ID)的组合。此外,您的订单ID不一定必须是表格上的实际密钥。没有什么可以说你不能使用一个单独的“计算”列代表订单ID的代理键。
底线是听起来你想要使用代理键,但有自然键的好处。两种方式都很难实现,很多方面都取决于您实际计划如何使用数据,用户如何解释数据以及个人偏好。