我正在尝试执行此查询,但是由于Azure Data Warehouse中不支持用户定义(创建类型)类型。我想在存储过程中使用它。
CREATE TYPE DataTypeforCustomerTable AS TABLE(
PersonID int,
Name varchar(255),
LastModifytime datetime
);
GO
CREATE PROCEDURE usp_upsert_customer_table @customer_table DataTypeforCustomerTable READONLY
AS
BEGIN
MERGE customer_table AS target
USING @customer_table AS source
ON (target.PersonID = source.PersonID)
WHEN MATCHED THEN
UPDATE SET Name = source.Name,LastModifytime = source.LastModifytime
WHEN NOT MATCHED THEN
INSERT (PersonID, Name, LastModifytime)
VALUES (source.PersonID, source.Name, source.LastModifytime);
END
GO
CREATE TYPE DataTypeforProjectTable AS TABLE(
Project varchar(255),
Creationtime datetime
);
GO
CREATE PROCEDURE usp_upsert_project_table @project_table DataTypeforProjectTable READONLY
AS
BEGIN
MERGE project_table AS target
USING @project_table AS source
ON (target.Project = source.Project)
WHEN MATCHED THEN
UPDATE SET Creationtime = source.Creationtime
WHEN NOT MATCHED THEN
INSERT (Project, Creationtime)
VALUES (source.Project, source.Creationtime);
END
是否有其他方法可以做到这一点。
您在那里面临一些挑战,因为您要转换的大多数不是在ASDW上做事的方法。
首先,正如您指出的那样,不支持创建类型,也没有等效的替代方案。
接下来,该代码似乎正在对表进行单个插入。在ASDW上这真的很糟糕,性能会令人恐惧。
接下来,ASDW尚无合并语句。那是因为更新不是处理更改数据的最佳方法。
和最后一个存储的过程在ASDW上的工作方式有所不同,它们没有编译,但每次调用该过程时都会解释。存储过程非常适合大量的桌子级逻辑,但不建议使用单行操作的大量呼叫。
我需要更多地了解用例,以提出具体的建议,但是通常您需要在表中而不是行中思考。特别是,专注于(CTA)处理ELT的方法。
这是一个很好的链接,它显示了如何使用CTA来处理合并/UpSert的等效物:
https://learn.microsoft.com/en-us/azure/sql-data-warehouse/sql-data-warehouse-develop-develop-ctas#replace-replace-merge-statement
您会看到,它一次处理两个表,而不是一行。这意味着您需要查看称为存储过程示例的逻辑。
如果您四处走动在CTA中进行所有操作,并且分别围绕分发,那么您就可以使用高性能数据仓库。
Azure SQL数据仓库中的临时表与Box Product SQL Server或Azure SQL数据库具有略有不同的行为 - 它们存在于会话级别。因此,您要做的就是根据需要将CREATE TYPE
语句转换为临时表,然后将MERGE
分为单独的INSERT
/UPDATE
/DELETE
语句。
示例:
CREATE TABLE #DataTypeforCustomerTable (
PersonID INT,
Name VARCHAR(255),
LastModifytime DATETIME
)
WITH
(
DISTRIBUTION = HASH( PersonID ),
HEAP
)
GO
CREATE PROCEDURE usp_upsert_customer_table
AS
BEGIN
-- Add records which do not already exist
INSERT INTO customer_table ( PersonID, Name, LastModifytime )
SELECT PersonID, Name, LastModifytime
FROM #DataTypeforCustomerTable AS source
WHERE NOT EXISTS
(
SELECT *
FROM customer_table target
WHERE source.PersonID = target.PersonID
)
...
只需加载临时表并执行存储的proc。有关临时表范围的更多详细信息。
如果您要更改表的大部分,则应考虑CTAS
的方法来创建一个新表格,然后按RON建议重命名。