Это выполнимо без создания Табличной Функции, но НЕ довольно
При перекрестном применении B будет "Очистить строку", для этого может потребоваться некоторое обслуживание.
Перекрестное применение C разделит / проанализирует строку, уменьшит ее до значений между > ... <
и затем агрегирует строку.
Вы можете заметить, что char (13) и char (10) НЕ удаляются, а заменяются пробелом. Это должно гарантировать, что замена не разрушительна.
Пример
Declare @YourTable table (ID int, [Message] varchar(max))
Insert Into @YourTable values
(1,'<br /><h1><span style="font-size: x-small"><span style="font-family: Verdana"><u><i><b>test</b></i></u></span></span><u><i><b><br /></b></i></u></h1><div contenteditable="false"><a href="dsi://OpenPatientFolder.671">George C Test2</a> </div><br /><br />')
,(2,'<div><h1>This is the Title</hr><br >The content<br >Extra Spaces will be trapped. The End</div>')
,(3,'No HTML Tags')
Select A.id
,NewValue = ltrim(rtrim(replace(replace(replace(TxtOnly,' ','†‡'),'‡†',''),'†‡',' ')))
From @YourTable A
Cross Apply ( values ( replace(
replace(
replace('<fake>'+[Message]+'</fake>'
,char(13),' ')
,char(10),' ')
,' ',' ') -- May want to add items like — as - and ™ as TM etc...
)
) B(CleanString)
Cross Apply (
Select TxtOnly = stuff((Select ' ' +RetVal
From (
Select RetSeq
,RetVal = left(RetVal,charindex('<',RetVal+RetVal)-1)
From (
Select RetSeq = row_number() over (order by 1/0)
,RetVal = ltrim(rtrim(B.i.value('(./text())[1]', 'varchar(max)')))
From ( values (cast('<x>' + replace((Select replace(CleanString,'>','§§Split§§') as [*] For XML Path('')),'§§Split§§','</x><x>')+'</x>' as xml).query('.'))) as A(x)
Cross Apply x.nodes('x') AS B(i)
) C1
Where charindex('<',RetVal)>1
) C2
Order By RetSeq
For XML Path(''),TYPE).value('(./text())[1]','varchar(max)')
,1,1,'')
) C
Возвращает
id NewValue
1 test George C Test2
2 This is the Title Extra Spaces will be trapped. The End
3 No HTML Tags