Sql server 标识值硬编码的SQL最佳实践

Sql server 标识值硬编码的SQL最佳实践,sql-server,identity-column,Sql Server,Identity Column,首先,我知道这是一个相当主观的问题,但我需要一些正式的文档来帮助我教育我的客户 背景-一个大型企业应用程序,包含数百个表和SP,所有这些都使用规范化的表和使用标识列的外键进行了整洁的设计 我们的客户有几个员工在Crystal enterprise中使用生产数据库的复制副本编写复杂的报告 我们有一些表存储我将分类为“系统”的基本信息,例如办公室位置列表,或公司内的部门,用户的标准角色集,其他对象的状态(打开/关闭等),基本上是不经常更改的数据 问题-报表设计者和财务分析师正在编写带有硬编码标识值的

首先,我知道这是一个相当主观的问题,但我需要一些正式的文档来帮助我教育我的客户

背景-一个大型企业应用程序,包含数百个表和SP,所有这些都使用规范化的表和使用标识列的外键进行了整洁的设计

我们的客户有几个员工在Crystal enterprise中使用生产数据库的复制副本编写复杂的报告

我们有一些表存储我将分类为“系统”的基本信息,例如办公室位置列表,或公司内的部门,用户的标准角色集,其他对象的状态(打开/关闭等),基本上是不经常更改的数据

问题-报表设计者和财务分析师正在编写带有硬编码标识值的查询。像这样的

SELECT xxx FROM OFFICE WHERE OFFICE_ID = 6
我在这里大大简化了,但基本上他们在他们的过程中到处都使用这些硬编码的int值

对于SQL开发人员来说,看到这一点显然会让您感到非常惊讶,因为不这样做只是一种内在的本能

然而,令人惊讶的是,我找不到任何文档或最佳实践文章来解释为什么不应该这样做

他们会争辩说这样做很好,因为值永远不会改变,而且他们是对的,在单个系统中,这些值不会改变,但是在多个环境(staging/QA/Dev)中,这些值可以而且绝对不同,使他们的报告设计方法不可移植,只能在一个隔离的服务器环境中运行


是否有任何SQL专家有更深入的信息/文章等,我可以用来帮助我的客户了解为什么他们应该避免这种方法?

在我看来,报告作者最有力的论点是你的第二句话“……这些值可以而且绝对不同于[不同环境]”。这将是我对他们回应的要点

当然,任何问题都有灰色地带。标识列本质上是一个属性。他们对数据库的好处是

  • 小的
  • 连续的
  • 快速查找和加入、排序和创建
…但其缺点是完全没有意义,实际上是随机分配的(将插入项按一种方式排序到该表中,每行的标识与按另一种方式排序不同)。因此,在您必须查找类似的特定内容的情况下,它的常见用法还包括“业务/自然/备用”键(例如,可能(完全虚构的示例)
[CategoryName]
,其中CatgoryName是简短、唯一且人类可读的内容。
[CategoryId]
是一种身份,但不是用来寻找的东西)

如果你有一个网站,比如说,有一个下拉菜单,通常自然键会放在下拉菜单的可见部分,代理/标识键会在后端传递,最终用户看不见

当有人直接针对数据库编写查询时,这会变得有点棘手。如果他们是数据的所有者,他们可能知道更大的数据结构,他们可以通过“聪明”的方式利用这些数据结构。如果您知道这些键不会改变,并且您知道这些值是什么,那么可能需要引用这些值。但是,如果在查询不同的服务器时它们会有所不同,这也不是问题

当然,另一方面是,如果你不想让他们使用标识值,你必须给他们一个选择。如果您的表中还没有包含business/natural/alternate键,那么您必须在尚不存在的地方添加一个键


另外,备用键也是整数也没什么错(也许你已经有了公司范围内的1、2、3等办公室标识符),但关键是无论你在哪里运行查询,它都是确定的。

回答得好,我同意所有这些,事实上,我们已经有了您所描述的内容,即匹配的pairid/Name列。试图让他们明白,将“SELECT Id from Category WHERE Name='xxx''转换为变量并使用它,是他们不理解的事情,因此拒绝,所以我希望有一个可靠的引用,我可以从大型权威机构向他们提供,所以我可以说,不要这样做,因为这是:引用。启动一个新的Azure虚拟机并植入不同的表值,它们的报告会崩溃,而我们的应用程序不会,很难做到这一点。acrossI我明白你所说的缺乏权威文章是什么意思。这不完全是你的问题,但在这篇文章中也有一些很好的回答: