我有一个带有文本数据类型的列,但它是一个xml字段。当我尝试执行一个简单的语句,如
SELECT columnname,
CONVERT(xml,coloumnname)
FROM employee
这在QA中运行良好,因为它的数据量很小。当我在生产中运行时,异常即将发生。有没有办法可以绕过所有具有非法xml字符的记录,以便我可以成功执行代码。使用sql sever 2005/2008。
有没有人有这方面的手册?
答案 0 :(得分:4)
严肃地说,你应该清理你的数据。这里合法指定了一组合法的XML字符:http://www.w3.org/TR/xml/#charsets。
在XML中使用任何非法字符都是坏消息。而不是试图“跳过”这些数据,你需要解决根本问题,这是一个糟糕的数据。
你能编写一个脚本来清理数据库中的数据吗?
我认为您的实时应用程序可以读取数据并对其进行预处理,在调用CONVERT之前查找错误的字符,但这不能解决根本问题而且效率不高。
答案 1 :(得分:1)
即时验证数据足够慢。
如果您确实不想使用错误数据,则应向表中添加列(例如“Is_Validated”)。
然后运行将检查数据的脚本,如果它无异常转换为xml,则将列更新为1,否则为0.
运行语句时,应限制转换为仅使用Is_Validated = 1的xml。
插入新行时,请检查是否为有效的XML(使用TRY / CATCH逻辑或CLR)并仅插入有效行。
当您保持逻辑稳定时,您可以开始验证您的错误数据。
<强>更新强>
由于来自#2的脚本应该只运行一次,它可以是简单的TSQL: 假设您的主键ID为int,而xml列由MySchema验证的表Employee中的Columnname
Declare @id int=0,@xml XML(MySchema)
WHILE EXISTS(SELECT * FROM Employee WHERE Id>@Id)
BEGIN
SELECT TOP 1 @Id=Id FROM Employee WHERE Id>@Id ORDER BY Id
BEGIN TRY
SET @xml=(SELECT columnname FROM Employee WHERE id=@Id)
UPDATE Employee SET Is_Validated=1 WHERE Id=@Id
END TRY
BEGIN CATCH
UPDATE Employee SET Is_Validated=0 WHERE Id=@Id
END CATCH
END