为什么SQL Server存储过程的表值参数需要输入READONLY?

K. *_*tes 9 sql-server

任何人都可以解释防止表值参数被设置为存储过程的输出参数背后的设计决策吗?

我无法计算我开始构建数据模型的次数,希望完全锁定我的表到外部访问(你知道......实现细节),只允许应用程序通过存储过程访问数据库(你知道...数据接口)并与TVP来回沟通只是为了让SSMS打电话让我顽皮地认为我可以使用用户定义的表类型作为我的数据服务和我的应用程序之间的传输对象.

所以有人请给我一个很好的理由为什么TVP被设计为只读输入参数.

Mik*_*son 11

他说,在Michael Rys 使用表值参数,XML和MERGE优化Microsoft SQL Server 2008应用程序的演示中.(在32:52)

请注意,在SQL Server 2008中,表值参数是只读的.但是你注意到我们实际上要求你写READONLY.所以这实际上就意味着在未来的某个时刻,如果你说请,请经常请我们在某些时候能够真正使它们成为可写的.但目前他们只读.

这是您应该用来添加"请"的连接项.放松限制,当SP相互调用时,表参数必须是只读的.

Srini Acharya对连接项进行了评论.

允许表值参数读/写涉及SQL Engine端和客户端协议的相当多的工作.由于时间/资源限制以及其他优先级,我们将无法将此工作作为SQL Server 2008发行版的一部分.但是,我们已经对此问题进行了调查,并将其牢牢地放在我们的雷达中,以作为下一版SQL Server的一部分来解决.


Pரத*_*ீப் 5

表值参数有以下限制(来源 MSDN):

  • SQL Server 不维护表值参数列的统计信息。
  • 表值参数必须作为输入 READONLY
    参数传递给 Transact-SQL 例程。不能 对例程主体中的
    表值
    参数执行 DML操作,例如 UPDATE、DELETE 或 INSERT 。
  • 不能使用表值参数作为 SELECT INTO 或 INSERT EXEC 语句的目标。表值参数可以位于 SELECT INTO 的 FROM 子句中,也可以位于 INSERT EXEC 字符串或存储过程中。

克服这个限制的选择很少

CREATE TYPE RTableType AS TABLE(id INT, NAME VARCHAR )

go

CREATE PROCEDURE Rproc @Rtable RTABLETYPE READONLY,
                       @id     INT
AS
  BEGIN
      SELECT *
      FROM   @Rtable
      WHERE  ID = @id
  END

go

DECLARE @Rtable RTABLETYPE
DECLARE @Otable RTABLETYPE

INSERT INTO @Rtable
VALUES      (1,'a'),
            (2,'b')

INSERT @Otable
EXEC Rproc
  @Rtable,
  2

SELECT *
FROM   @Otable 
Run Code Online (Sandbox Code Playgroud)

通过这个你可以得到表值