跨存储过程连接范围临时表

时间:2013-01-23 04:10:12

标签: sql-server tsql stored-procedures database-connection temp-tables

我正在研究数据虚拟化解决方案。用户可以将自己的SQL查询编写为我所做查询的过滤器。我希望每次从数据库中选择一些东西时都不必运行此过滤器查询(这可能是一系列复杂的连接)。

我的想法是在脚本级别使用#temp表并保持连接活动。然后将从中选择此#temp表,但仅在用户更改过滤器时更新。我的想法实际上可以从存储过程中使用它,并且表的范围限定为该连接。

我从建议使用动态sql和使用连接进程ID命名的##全局临时表的人那里得到了这个想法,以便使每个连接都有一个唯一的全局临时表。这是为了克服跨存储过程共享临时表。但它看起来有点笨拙。

我使用以下代码进行了快速测试,似乎工作正常

-- Run script at connection open from some app
SELECT * INTO #test
FROM   dataTable

-- Now we can use stored procedures with #test table
EXECUTE selectFromTempTable

EXECUTE updateTempTable @sqlFilterString

EXECUTE selectFromTempTable

我能看到的唯一真正的问题是连接必须保持活动,持续时间可能是几个小时。单个用户可以同时运行多个连接。单个数据库服务器上的用户数量最多为20。 如果它是一个巨大的问题我可以做到这样应用程序可以关闭并根据需要打开它们,这样每个用户一次只能打开一个连接。甚至可能在不使用时将其关闭,并在需要时再次重新打开,并且必须等待查询运行。

这会是不好的做法吗?或者从不运行过滤查询中获取任何性能优势?这是在SQL Server 2008及更高版本上。

1 个答案:

答案 0 :(得分:0)

我想我会创建一个永久表,使用spid(进程ID)作为键值。每个连接都有自己的进程ID,因此任何人都可以使用它来识别表中的条目:

create table filter( 
  spid int, 
  filternum int, 
  filterstring varchar(255), 
  <other cols> );
create unique index filterindx on filter(spid, filternum);

然后当用户创建过滤条目时:

delete from filter where spid = @@spid
insert into filter(spid, filternum, filterstring) select @@spid, 1, 'some sql thing'
insert into filter(spid, filternum, filterstring) select @@spid, 2, 'some other sql thing'

然后,您可以通过选择where spid = @@spid

来访问每个用户的过滤器值