创建分布式分区视图

在实现分区视图之前,必须先对表进行水平分区。设计分区方案时,每个成员表所包含的数据必须是明确的。原表将被替换为若干较小的成员表。每个成员表与原表包含相同数量的列,并且每一列与原表中的相应列具有相同的属性,如数据类型、大小和排序规则。如果正在创建分布式分区视图,则每个成员表分别位于不同的成员服务器上。为了获得最大程度的位置透明度,各个成员服务器上的成员数据库的名称应当相同,但这并不是必需的。例如:Server1.CustomerDBServer2.CustomerDBServer3.CustomerDB

创建成员表

设计成员表,使每个表基于键值范围存储原表的一块水平区域。键值范围取决于分区列中的数据值。每个成员表中的值范围通过分区列上的 CHECK 约束强制执行,并且范围之间不能重叠。例如,不能使一个表的值范围为从 1 到 200000,而另一个表的值范围为从 150000 到 300000,因为这样将不清楚哪个表包含 150000 到 200000 之间的值。

例如,若要将一个 Customer 表分区为三个表,针对这些表的 CHECK 约束如下:

-- On Server1:
CREATE TABLE Customers_33
  (CustomerID   INTEGER PRIMARY KEY
                CHECK (CustomerID BETWEEN 1 AND 32999),
  ... -- Additional column definitions)

-- On Server2:
CREATE TABLE Customers_66
  (CustomerID   INTEGER PRIMARY KEY
                CHECK (CustomerID BETWEEN 33000 AND 65999),
  ... -- Additional column definitions)

-- On Server3:
CREATE TABLE Customers_99
  (CustomerID   INTEGER PRIMARY KEY
                CHECK (CustomerID BETWEEN 66000 AND 99999),
  ... -- Additional column definitions)

定义分布式分区视图

创建成员表之后,在每个成员服务器上定义一个分布式分区视图,并且各个视图具有相同的名称。这样,引用该分布式分区视图名的查询就可以在一个或多个成员服务器上执行。系统将像每个成员服务器上都有原表的一个副本那样进行操作,但其实每个服务器上只有一个成员表和一个分布式分区视图。数据的位置对应用程序是透明的。

通过执行下列任务来创建分布式分区视图:

  • 在每个包含着在其他成员服务器上执行分布式查询所需的连接信息的成员服务器上添加链接服务器定义。这使得分布式分区视图能够访问其他服务器上的数据。

  • 对于在分布式分区视图中使用的每个链接服务器定义,使用 sp_serveroption 设置 lazy schema validation 选项。这就确保了只有在真正需要远程成员表的数据时,查询处理器才会请求任一链接表的元数据,从而使性能得到优化。

  • 在每个成员服务器上创建分布式分区视图。这些视图使用分布式 SELECT 语句访问链接成员服务器上的数据,并将分布式行与本地成员表的行合并。

若要为上述示例创建分布式分区视图,必须执行下列操作:

  • 使用 Server2 连接信息添加一个名为 Server2 的链接服务器定义,并添加一个名为 Server3 的链接服务器定义以访问 Server3。

  • 创建以下分布式分区视图:

    CREATE VIEW Customers AS
       SELECT * FROM CompanyDatabase.TableOwner.Customers_33
    UNION ALL
       SELECT * FROM Server2.CompanyDatabase.TableOwner.Customers_66
    UNION ALL
       SELECT * FROM Server3.CompanyDatabase.TableOwner.Customers_99
    
  • 在 Server2 和 Server3 上执行相同的步骤。

表规则

成员表在视图定义中每个 SELECT 语句的 FROM 子句中定义。每个成员表必须符合下列规则:

  • 每个成员表在视图中只能引用一次。

  • 成员表不能有对任何计算列创建的索引。

  • 各个成员表中具有 PRIMARY KEY 约束的列数必须相同。

  • 各个成员表的 ANSI 填充设置必须相同。有关 ANSI 填充设置的详细信息,请参阅 SET ANSI_PADDING

列规则

列在视图定义中每个 SELECT 语句的选择列表中定义。每个列必须遵循下列规则:

  • 每个成员表中的所有列都必须包括在选择列表中。可接受的语法为 SELECT * FROM <member table>。

  • 列在选择列表中只能引用一次。

  • 列必须位于选择列表中的相同序号位置。

  • 每个 SELECT 语句的选择列表中的列必须为同一类型。包括数据类型、精度、小数位数和排序规则。例如,以下视图定义失败,这是因为两个 SELECT 语句中首列的数据类型不同:

    CREATE VIEW NonUpdatable
    AS
    SELECT IntPrimaryKey, IntPartNmbr
    FROM FirstTable
      UNION ALL
    SELECT NumericPrimaryKey, IntPartNmbr
    FROM SecondTable
    

分区列规则

只有一列可以用于分区,并且每个成员表中必须都存在该列。CHECK 约束可识别每个成员表中可用的数据。应遵循下列附加规则:

  • 各个表的 CHECK 约束的键范围不能相互重叠。分区列的任一特定值必须只映射到一个表。CHECK 约束只能使用下列运算符:BETWEEN、IN、AND、OR、<、<=、>、>= 和 =。

  • 分区列不能是标识、默认值或 timestamp 列。

  • 在视图中,分区列必须位于每个 SELECT 语句的选择列表中相同的序号位置。例如,分区列要么始终是每个选择列表中的首列,要么始终是每个选择列表中的第二列,依此类推。

  • 分区列不允许为空。

  • 分区列必须是表的主键的一部分。

  • 分区列不能是计算列。

  • 分区列上必须只有一个约束。如果有多个约束,SQL Server 将会忽略所有约束并且在确定视图是否为分区视图时不考虑这些约束。

  • 对分区列的可更新性没有限制。

符合上述所有规则的分区列将支持查询优化器所支持的所有优化。有关详细信息,请参阅解析分布式分区视图

一般规则

注意注意

下列条件不适用于在同一计算机上创建的本地分区视图。包含这一项功能是为了向后兼容。

下面是一些需要考虑的其他规则:

  • 不能使用 EXCEPT 或 INTERSECT 运算符来形成分布式分区视图。

  • 将启动分布式事务以保证受更新影响的所有节点之间的原子性。

  • XACT_ABORT SET 选项必须设置为 ON。

  • 远程表中的 smallmoneysmalldatetime 列分别被映射为 moneydatetime。因此,本地表中的相应列也应为 moneydatetime

  • 任何链接服务器都不能是环回链接服务器,即指向同一 SQL Server 实例的链接服务器。

如果视图上存在 INSTEAD OF 触发器,则不遵循上述所有规则而引用分区表的视图仍然可能是可更新的。但是,查询优化器为带有 INSTEAD OF 触发器的视图生成的执行计划并不总能与遵循所有规则的分区视图的执行计划一样有效。