2010-09-22 21 views
7

Así que obtuve una columna varbinary(max) en SQL Server 2005 y está llena de XML. Algunos registros en alguna parte tienen XML truncado por lo que no son válidos.XML no válido en una columna varbinary (max) en SQL Server 2005

Esto significa que si corro un

SELECT CAST(myVarbinaryColumn as XML) ... 

sopla trozos.

¿Cómo puedo filtrar/omitir xml no válido?

Cuando he hecho algo similar con un varchar que supuestamente tiene fechas, podría usar ISDATE(blah) = 1. Entonces, un equivalente ISVALIDXML() sería agradable.

Por favor, no comenten "Por qué no es el tipo de datos XML de columna de todos modos .." Esto sucedió en el pasado y no tengo una máquina del tiempo.

+0

Hmm interesante, los bytes finales siempre serán los mismos, así que podría filtrar los que no coinciden? Afortunadamente, en este escenario todos los xml usan el mismo esquema, por lo que todos deben tener un elemento raíz de cierre coincidente –

Respuesta

1

Creo que su mejor opción sería escribir una CLR function personalizada, tal vez usando XmlDocument.Load. En el CLR, podría atrapar el error en una carga fallida y devolver un resultado apropiado.

EDIT: El código siguiente también funcionaría aunque no es tan elegante como una UDF. Desafortunadamente, no podemos usar TRY/CATCH en un UDF.

create procedure dbo.usp_IsValidXML(@XMLCandidate varbinary(max), @Return bit output) 
as 
begin 
    declare @x xml 
    begin try 
     set @x = cast(@XMLCandidate as xml) 
     set @Return = 1 
    end try 
    begin catch 
     set @Return = 0 
    end catch 
end 
go 

declare @test1 varbinary(max) 
declare @test2 varbinary(max) 
set @test1 = cast('<data>asdf</data>' as varbinary(max)) 
set @test2 = cast('<data>asdf</da' as varbinary(max)) 

declare @IsValid bit 
exec dbo.usp_IsValidXML @test1, @IsValid output 
select @IsValid 
exec dbo.usp_IsValidXML @test2, @IsValid output 
select @IsValid 

drop procedure dbo.usp_IsValidXML 
+0

Sí y crear una columna calculada persistente basada en él, por lo que no se llama cada vez que vaya 'donde valid_xml = 1'. – GSerg

+0

¿Será determinista? –

1

Me gustaría tener que IsValidXML() función, también ..... por desgracia, no creo que no hay nada de eso .....

Es sólo una idea: ¿hay algo que se puede comprobar por a filtrar el XML no válido?

E.g. ¿Podría filtrar todas las cadenas que no terminan en .....</data> o algo así? (dado que usted dice que su XML no válido suele ser un XML truncado, entonces creo que la etiqueta de cierre - </data> o lo que sea - faltaría en esos casos).

Cuestiones relacionadas