我们有一些 SQL“普通”表和图表,一个在它们之间同步信息的脚本。
SSMS 一切正常,但是在 Visual Studio 中使用 msbuild 构建数据库项目时,我们会收到警告(请参阅下面的代码和警告详细信息)。
如果我们设置TreatTSqlWarningsAsErrors
为 True,这些警告就会变成错误。
我们不想忽略警告,但不清楚我们为什么会收到警告。这些警告是否正确?
为什么它们只显示在 Visual Studio 中而不显示在 SSMS 中?
我们如何在不忽略它们的情况下解决它们?
细节:
我们有以下两个“正常”的 SQL 表:
CREATE TABLE [dbo].[Currency]
(
[Id] [int] IDENTITY(1,1) NOT NULL,
[Name] [nvarchar](250) NOT NULL,
[UId] [uniqueidentifier] NOT NULL,
CONSTRAINT [PK_Currency]
PRIMARY KEY CLUSTERED ([Id] ASC)
WITH (PAD_INDEX = OFF, STATISTICS_NORECOMPUTE = OFF,
IGNORE_DUP_KEY = OFF, ALLOW_ROW_LOCKS = ON,
ALLOW_PAGE_LOCKS = ON, FILLFACTOR = 90, OPTIMIZE_FOR_SEQUENTIAL_KEY = OFF) ON [PRIMARY]
) ON [PRIMARY]
GO
ALTER TABLE [dbo].[Currency]
ADD CONSTRAINT [DF_Currency_UId] DEFAULT (NEWID()) FOR [UId]
GO
和
CREATE TABLE [dbo].[Portfolio]
(
[Id] [INT] IDENTITY(1,1) NOT NULL,
[Name] [NVARCHAR](250) NULL,
[CurrencyId] [INT] NOT NULL,
[UId] [UNIQUEIDENTIFIER] NOT NULL,
CONSTRAINT [PK_Portfolio]
PRIMARY KEY CLUSTERED ([Id] ASC)
WITH (PAD_INDEX = OFF, STATISTICS_NORECOMPUTE = OFF,
IGNORE_DUP_KEY = OFF, ALLOW_ROW_LOCKS = ON,
ALLOW_PAGE_LOCKS = ON, FILLFACTOR = 90, OPTIMIZE_FOR_SEQUENTIAL_KEY = OFF) ON [PRIMARY]
) ON [PRIMARY]
GO
ALTER TABLE [dbo].[Portfolio]
ADD CONSTRAINT [DF_Portfolio_UId] DEFAULT (NEWID()) FOR [UId]
GO
ALTER TABLE [dbo].[Portfolio] WITH CHECK
ADD CONSTRAINT [FK_Portfolio_Currency]
FOREIGN KEY([CurrencyId]) REFERENCES [dbo].[Currency] ([Id])
GO
ALTER TABLE [dbo].[Portfolio] CHECK CONSTRAINT [FK_Portfolio_Currency]
GO
我们创建了以下 SQL 图形模式以及两个 SQL 节点表和一个 SQL 边:
CREATE SCHEMA [graph] ;
CREATE TABLE [graph].[Currency]
(
[Id] UNIQUEIDENTIFIER NOT NULL,
PRIMARY KEY CLUSTERED ([Id] ASC),
INDEX [GRAPH_UNIQUE_INDEX_4FFC60C0FCBE4843A7F4B9AB0729FF78] UNIQUE NONCLUSTERED ($node_id)
) AS NODE;
CREATE TABLE [graph].[Portfolio]
(
[Id] UNIQUEIDENTIFIER NOT NULL,
PRIMARY KEY CLUSTERED ([Id] ASC),
INDEX [GRAPH_UNIQUE_INDEX_F39F92BE8DD34DD791D6CA955DA0DA9A] UNIQUE NONCLUSTERED ($node_id)
) AS NODE;
CREATE TABLE [graph].[isOf]
(
[IsActive] BIT CONSTRAINT [DF_isOf_IsActive] DEFAULT ((1)) NOT NULL,
INDEX [GRAPH_UNIQUE_INDEX_AD8C5B40D277413580EDD943AC192869] UNIQUE NONCLUSTERED ($edge_id)
) AS EDGE;
CREATE UNIQUE NONCLUSTERED INDEX [UQ_FromTo]
ON [graph].[isOf] ($from_id, $to_id) ON [PRIMARY];
GO
一个同步存储过程,它将从每天执行的“正常”表中填充节点和边缘。
附上部分:
PRINT ( 'Sync graph.[Portfolio]' );
INSERT INTO graph.Portfolio ( Id )
SELECT P.[UId]
FROM dbo.Portfolio P
WHERE NOT EXISTS ( SELECT 1
FROM graph.Portfolio G
WHERE G.Id = P.[UId] );
PRINT ( 'Sync graph.[Currency]' );
INSERT INTO graph.Currency ( Id )
SELECT C.[UId]
FROM dbo.Currency C
WHERE NOT EXISTS ( SELECT 1
FROM graph.Currency G
WHERE G.Id = C.[UId] );
PRINT('Sync Portfolio isOf Currency edge');
;
WITH UidCTE
AS ( SELECT P.[UId] AS PortfolioUid ,
C.[UId] AS CurrencyUid
FROM dbo.Portfolio P
JOIN dbo.Currency C ON C.Id = P.CurrencyId )
MERGE graph.isOf AS TGT
USING graph.[Portfolio] AS SourceFrom
JOIN UidCTE CTE ON SourceFrom.Id = CTE.PortfolioUid
JOIN graph.[Currency] AS SourceTo ON CTE.CurrencyUid = SourceTo.Id
ON MATCH(SourceFrom-(TGT)->SourceTo)
WHEN NOT MATCHED BY TARGET THEN
INSERT ( $from_id , $to_id )
VALUES ( SourceFrom.$node_id, SourceTo.$node_id)
WHEN MATCHED AND TGT.[IsActive] = 0 THEN
UPDATE SET TGT.[IsActive] = 1;
以及以下脚本更新边缘的 IsActive 列,以防“正常”表中不再存在关系(我们不想从图形节点/边缘中删除它)
;WITH PortfolioIsOfCurrency
AS ( SELECT P.[UId] AS PortfolioUid ,
C.[UId] AS CurrencyUid
FROM dbo.Portfolio P
JOIN dbo.Currency C ON C.Id = P.CurrencyId ) ,
NodeCTE
AS ( SELECT P.$node_id AS FromNode ,
C.$node_id AS ToNode
FROM PortfolioIsOfCurrency CTE
JOIN graph.Portfolio P ON P.Id = CTE.PortfolioUid
JOIN graph.Currency C ON C.Id = CTE.CurrencyUid )
UPDATE ISOF
SET isOf.IsActive = 0
FROM graph.isOf ISOF
WHERE NOT EXISTS ( SELECT 1
FROM NodeCTE N
WHERE N.FromNode = ISOF.$from_id
AND N.ToNode = ISOF.$to_id );
我们在 VS 2019 中创建了一个数据库项目,设置如下:
<DSP>Microsoft.Data.Tools.Schema.Sql.Sql150DatabaseSchemaProvider</DSP>
<TargetFrameworkVersion>v4.5</TargetFrameworkVersion>
<TreatWarningsAsErrors>False</TreatWarningsAsErrors>
<TreatTSqlWarningsAsErrors>False</TreatTSqlWarningsAsErrors>
从 SSMS 开始,一切都很完美。
问题在于最后一个语法(UPDATE isof.active)我收到以下警告:
警告 SQL71502:过程:[graph].[SyncEngagementContentGraphs] 对对象 [graph].[isOf].[N] 的引用未解析。图\存储过程\SyncEngagementContentGraphs.sql 57
警告 SQL71502:过程:[graph].[SyncEngagementContentGraphs] 对对象 [graph].[isOf].[N] 的引用未解析。图\存储过程\SyncEngagementContentGraphs.sql 58
警告 SQL71509:模型已经有一个同名的元素 NodeCTE.$node_id。图\存储过程\SyncEngagementContentGraphs.sql 47
警告 SQL71509:模型已经有一个同名的元素 NodeCTE.$node_id。图\存储过程\SyncEngagementContentGraphs.sql 48
如果我们将 TreatTSqlWarningsAsErrors 设置为 True,这些警告就会变成错误,从长远来看,我们不能这样(设置为 False)。