所以我有一个触发器,可以使XML"事务"数据更改为客户端人口统计数据 它在大多数情况下工作,但我无法使节点结构非常正确 一个客户端最多可以拥有3个电话记录,我试图让每个电话记录都嵌入到一个客户端节点下,而不是重复整个客户端节点,同时使用带电话的subquerys会遇到一些麻烦
--sample tables
DECLARE @phone TABLE ( MPIID int, phoneTypeNm VARCHAR(MAX), Phone VARCHAR(MAX), PhoneID int )
DECLARE @province TABLE ( provinceID INT, provinceCd VARCHAR(MAX) )
DECLARE @client TABLE ( FirstName VARCHAR(MAX), LastName VARCHAR(MAX), clientID INT )
DECLARE @inserted TABLE ( provinceID int, address VARCHAR(MAX), addressid int, MPIID int )
DECLARE @deleted TABLE ( provinceID int, address VARCHAR(MAX), addressid int, MPIID int )
INSERT INTO @phone (MPIID, phoneTypeNm, Phone, PhoneID)
VALUES
(4 , 'School' , '123-4567', 123),
(3 , 'Home' , '123-4567', 124),
(3 , 'Work' , '765-4321', 2352),
(1 , 'Cell' , '012-3654', 23672);
INSERT INTO @province (provinceID, provinceCd)
VALUES
(1, 'ON'),
(3, 'AB'),
(4, 'PI'),
(2, 'BC');
INSERT INTO @client (FirstName, LastName, clientID)
VALUES ('james', 'elroy', 1),
('andrew', 'lucy', 4),
('adam,', 'trevor', 3);
INSERT INTO @inserted (provinceID, address, addressid, MPIID)
VALUES (2, '123 fake st', 11, 1),
(4, '123 none st', 14, 4),
(1, '123 inserted st', 13, 3);
INSERT INTO @deleted (provinceID, address, addressid, MPIID)
VALUES (1, '123 old st', 11, 1),
(4, '123 none st', 14, 4),
(3, '123 deleted st', 12, 2);
下面的代码使xml的数据发生了变化,这将在触发器上运行以访问插入和删除的表
DECLARE @NewTransaction XML;
SET @NewTransaction = ( SELECT * FROM (
SELECT
c.ClientID AS [@UniqueIdentifier]
,[@Type] = CASE WHEN new.MPIID IN (SELECT new.MPIID FROM @inserted) THEN 'U' END
,[FirstName] = CASE when new.MPIID = old.MPIID THEN NULL ELSE c.FirstName END
,[LastName] = CASE when new.MPIID = old.MPIID THEN NULL ELSE c.LastName END
,[Address/@UniqueIdentifier] = CASE when new.addressid = old.addressid THEN NULL ELSE new.addressid END
,[Address/@Type] = CASE WHEN new.addressid IN (SELECT new.addressid FROM @inserted) THEN 'U' END
,[Address/Street] = CASE when new.address = old.address THEN NULL ELSE new.address END
,[Address/Province] = CASE when new.provinceID = old.provinceID THEN NULL ELSE p.provinceCd END
,CASE when new.MPIID = old.MPIID THEN NULL ELSE ph.PhoneID END AS [Phone/@UniqueIdentifier]
,[Phone/@Type] = CASE WHEN new.MPIID IN (SELECT new.MPIID FROM @inserted) THEN 'U' END
,[Phone/PhoneType] = CASE when new.MPIID = old.MPIID THEN NULL ELSE ph.phoneTypeNm END
,[Phone/PhoneValue] = CASE when new.MPIID = old.MPIID THEN NULL ELSE ph.Phone END
FROM @inserted [new]
LEFT JOIN @deleted [old] ON new.addressid = old.addressid
LEFT JOIN @client [c] ON new.MPIID = c.clientID
LEFT JOIN @phone [ph] ON new.MPIID = ph.MPIID
LEFT JOIN @province [p] ON new.provinceID = p.provinceID
UNION
SELECT MPIID, 'D',
NULL, NULL, NULL, NULL, NULL,
NULL, NULL, NULL, NULL, NULL
FROM @deleted
WHERE MPIID NOT IN (SELECT MPIID FROM @inserted)
) AS temp FOR XML PATH('Client'), ROOT('Root'), TYPE, ELEMENTS)
SELECT @NewTransaction
- 代码生成
<Root>
<Client UniqueIdentifier="433979" Type="U">
<FirstName>Herwigaaa</FirstName>
<LastName>Farm</LastName>
<Address Type="U" UniqueIdentifier="357653">
<Street>asddrdsslkdjf</Street>
<Province>Qing</Province>
</Address>
<Phone Type="U">
<PhoneType>Cellular</PhoneType>
<PhoneValue>(166) 857-4648</PhoneValue>
</Phone>
</Client>
<Client UniqueIdentifier="433979" Type="U">
<FirstName>Herwigaaa</FirstName>
<LastName>Farm</LastName>
<Address Type="U" UniqueIdentifier="357653">
<Street>asddrdsslkdjf</Street>
<Province>Qing</Province>
</Address>
<Phone Type="U">
<PhoneType>Home</PhoneType>
<PhoneValue>(136) 371-8774</PhoneValue>
</Phone>
</Client>
</Root>
我希望在
下面实现xml结构<Root>
<Client UniqueIdentifier="433979" Type="U">
<FirstName>Herwigaaa</FirstName>
<LastName>Farm</LastName>
<Address Type="U" UniqueIdentifier="357653">
<Street>asddrdsslkdjf</Street>
<Province>Qing</Province>
</Address>
<Phone Type="U" UniqueIdentifier="124">
<PhoneType>Cellular</PhoneType>
<PhoneValue>(166) 857-4648</PhoneValue>
</Phone>
<Phone Type="U" UniqueIdentifier="2352">
<PhoneType>Home</PhoneType>
<PhoneValue>(136) 371-8774</PhoneValue>
</Phone>
</Client>
</Root>
答案 0 :(得分:0)
DECLARE @NewTransaction XML;
SET @NewTransaction = ( SELECT * FROM (
SELECT
c.ClientID AS [@UniqueIdentifier]
,[@Type] = CASE WHEN new.MPIID IN (SELECT new.MPIID FROM @inserted) AND new.MPIID IN (SELECT new.MPIID FROM @deleted) THEN 'U' END
,[FirstName] = CASE when new.MPIID = old.MPIID THEN NULL ELSE c.FirstName END
,[LastName] = CASE when new.MPIID = old.MPIID THEN NULL ELSE c.LastName END
,[Addresses] = ( SELECT
CASE when new.addressid = old.addressid THEN NULL ELSE new.addressid END AS [@UniqueIdentifier]
,CASE WHEN new.addressid IN (SELECT new.addressid FROM @inserted) THEN 'U' END AS [@Type]
,CASE when new.address = old.address THEN NULL ELSE new.address END AS [Street]
,CASE when new.provinceID = old.provinceID THEN NULL ELSE p.provinceCd END AS [Province]
FROM @province p
WHERE new.provinceID = p.provinceID
FOR XML PATH('Address'), TYPE, ELEMENTS )
,[Phones] = ( SELECT
CASE when new.MPIID = old.MPIID THEN NULL ELSE ph.PhoneID END AS [@UniqueIdentifier]
,CASE WHEN new.MPIID IN (SELECT new.MPIID FROM @inserted) THEN 'U' END AS [@Type]
,CASE when new.MPIID = old.MPIID THEN NULL ELSE ph.phoneTypeNm END AS [PhoneType]
,CASE when new.MPIID = old.MPIID THEN NULL ELSE ph.Phone END AS [PhoneValue]
FROM @phone ph
WHERE new.MPIID = ph.MPIID
FOR XML PATH('Phone'), TYPE, ELEMENTS )
FROM @inserted [new]
LEFT JOIN @deleted [old] ON new.addressid = old.addressid
LEFT JOIN @client [c] ON new.MPIID = c.clientID
)AS temp
FOR XML PATH('Client'), ROOT('Root'), TYPE, ELEMENTS)
SELECT @NewTransaction
out put to
<Root>
<Client UniqueIdentifier="3" Type="U">
<FirstName>adam,</FirstName>
<LastName>trevor</LastName>
<Addresses>
<Address UniqueIdentifier="13" Type="U">
<Street>123 inserted st</Street>
<Province>ON</Province>
</Address>
</Addresses>
<Phones>
<Phone UniqueIdentifier="124" Type="U">
<PhoneType>Home</PhoneType>
<PhoneValue>123-4567</PhoneValue>
</Phone>
<Phone UniqueIdentifier="2352" Type="U">
<PhoneType>Work</PhoneType>
<PhoneValue>765-4321</PhoneValue>
</Phone>
</Phones>
</Client>
</Root>