我在 varchar 列中存储了一些有效和无效的 xml 值。
我想将有效的 xml 值转换为实际的 xml 数据类型,而对 null 无效。
这样做的好方法是什么?
就像是:
SELECT
CASE WHEN dbo.isValidXML(xml_data) THEN CAST(xml_data as XML)
ELSE null
END
我在 varchar 列中存储了一些有效和无效的 xml 值。
我想将有效的 xml 值转换为实际的 xml 数据类型,而对 null 无效。
这样做的好方法是什么?
就像是:
SELECT
CASE WHEN dbo.isValidXML(xml_data) THEN CAST(xml_data as XML)
ELSE null
END
仅针对此:
是的,但我的问题是我如何首先检查 XML 是否有效?
从某种意义上说,您的 XML 是否无效,您将在下面的第二行中得到一个中断:
SELECT CAST('<xml>Yep this is xml</xml>' AS XML)
SELECT CAST('<xml>Nope, not xml</x' AS XML)
我看到的一种解决方案是逐行方法,您尝试CAST
将一行作为XML
,如果它XML
成功转换为将有效行插入具有有效值的表中XML
,如果它不能正确转换,则该值是' t 插入。 有关示例,请参见此线程。
尝试使用sp_xml_preparedocument
-
SET NOCOUNT ON;
DECLARE @XML NVARCHAR(MAX)
SELECT @XML = '<t>test</'
DECLARE @hDoc INT
BEGIN TRY
EXEC sys.sp_xml_preparedocument @hDoc OUTPUT, @XML
SELECT '"' + @XML + '" is valid'
EXEC sys.sp_xml_removedocument @hDoc
END TRY
BEGIN CATCH
SELECT '"' + @XML + '" is invalid'
END CATCH
SELECT @XML = '<t>test</t>'
BEGIN TRY
EXEC sys.sp_xml_preparedocument @hDoc OUTPUT, @XML
SELECT '"' + @XML + '" is valid'
EXEC sys.sp_xml_removedocument @hDoc
END TRY
BEGIN CATCH
SELECT '"' + @XML + '" is invalid'
END CATCH
输出 -
-------------------------
"<t>test</" is invalid
-------------------------
"<t>test</t>" is valid
如果您需要保持XML有效或无效,您可以在表上设置一个标志IsValid (bit)
,例如. 然后,加载过程可以对该数据进行一次性检查,以检查 XML 是否有效并根据结果设置标志。这样,您可以使用查询获取有效的 XML:
SELECT
CASE WHEN IsValid = 1 THEN CAST(xml_data as XML)
ELSE null
END
如果您不需要保留无效的 XML,则只需在加载期间拒绝它,将字段设置为NULL
,因此查询如下所示:
SELECT
CASE WHEN xml_data IS NOT NULL THEN CAST(xml_data as XML)
ELSE null
END
两种方式都将提供更好的性能,通过 a SQL function
for each query。