如何检查同义词后面的表是否存在

Tom*_*Tom 5 sql sql-server rdbms synonym

我正在尝试创建一个简单的脚本,将复杂视图的结果转储到表中以进行报告.我使用同义词来简化视图和表名的调整.

我们的想法是,脚本的用户可以将他们想要用作的视图的名称作为源,并将目标报告表的名称放在它们开始和离开的位置.如果该表不存在,那么脚本应该创建它.如果表已经存在,那么脚本应该只复制视图中尚未包含在表中的记录.

下面的脚本涵盖了所有这些要求,但我找不到一种很好的方法来检查同义词后面的表是否已经存在:

CREATE SYNONYM SourceView FOR my_view
CREATE SYNONYM TargetReportingTable FOR my_table

-- Here's where I'm having trouble, how do I check if the underlying table exists?
IF (SELECT COUNT(*) FROM information_schema.tables WHERE table_name = TargetReportingTable) = 0
  BEGIN
    -- Table does not exists, so insert into.
    SELECT * INTO TargetReportingTable FROM SourceView
  END
ELSE
  BEGIN
    -- Table already exists so work out the last record which was copied over
    -- and insert only the newer records.
    DECLARE @LastReportedRecordId INT;
    SET @LastReportedRecordId = (SELECT MAX(RecordId) FROM TargetReportingTable)
    INSERT INTO TargetReportingTable SELECT * FROM SourceView WHERE RecordId > @LastReportedRecordId
  END

DROP SYNONYM SourceView
DROP SYNONYM TargetReportingTable
Run Code Online (Sandbox Code Playgroud)

我知道我可以让脚本的用户将表名复制到'information_schema'行以及顶部的同义词,但这会留下错误的范围.

我也知道我可以做一些肮脏的事情,比如将表名放入一个变量中并将SQL作为一个字符串进行调整,但这让我觉得有点不舒服!

有一个很好的优雅的SQL方式让我检查同义词后面的表是否存在?还是一种完全不同的解决问题的方法?

Mar*_*tin 4

这不是最优雅的解决方案,但您可以将sys.synonyms表连接到sys.tables表以检查该表是否存在。

如果表不存在,连接将失败并且您将得到 0 行(因此IF EXISTS将为 false)。如果该表确实存在,则连接将成功,您将获得 1 行(且为 true):

IF EXISTS(  SELECT  *
              FROM  sys.synonyms s
                INNER JOIN sys.tables t ON REPLACE(REPLACE(s.base_object_name, '[', ''), ']', '') = t.name
              WHERE s.name = 'TargetReportingTable')
BEGIN
    -- Does exist
END
ELSE
BEGIN
    -- Does not exist
END
Run Code Online (Sandbox Code Playgroud)

替换'TargetReportingTable'为您要检查的任何同义词。