Заменить атрибут ширины тега <img>в SQL - PullRequest
0 голосов
/ 30 августа 2018

У меня есть таблица в базе данных, которая содержит HTML 500 страниц. Весь этот контент содержит <img width="100%".....

Я хочу удалить width = "100%" из всех изображений, не затрагивая остальную часть содержимого.

например. Текущая строка

<img width="100%" src="/images/skyline.jpg" alt="Image showing sky line" />

или

<img src="/images/skyline.jpg" width="100%" alt="Image showing sky line" />

Проверка W3C обнаруживает это как ошибку - «Неверное значение 100% для ширины атрибута в элементе img: ожидаемая цифра, но вместо этого видел%.»

Ожидаемая строка

<img src="/images/skyline.jpg" alt="Image showing sky line" />

Ответы [ 2 ]

0 голосов
/ 01 сентября 2018

Это будет работать для сервера sql. Я включил несколько примеров тегов img, чтобы показать, как это работает.

Однако имейте в виду, что он переформатирует HTML, который может быть не идеальным. Это будет тот же HTML, но без лишних пробелов и разрывов строк. Это может быть не то, что вы хотите.

Причина, по которой я должен это сделать, заключается в том, что когда я конвертирую в xml, а затем нахожу узлы, результаты обрезаются из лишних пробелов, и их невозможно найти обратно в исходной строке. Если в вашем html нет лишних пробелов внутри тегов img, вы можете пропустить этот шаг:

select convert(varchar(max),convert(xml,x)) as trimmed from @t

Если это не работает для вас, то, надеюсь, идентификация подходящих узлов, по крайней мере, поможет. Просто добавьте select * from matching после соответствующего cte, чтобы увидеть, что у вас есть.

Он также работает для каждого документа отдельно, поэтому вам, возможно, придется поместить его в цикл для работы с вашими документами. Или обновите его так, чтобы он работал во всей партии, но я предполагаю, что это разовая операция, поэтому, вероятно, не требуется.

declare @t table(x varchar(max))
insert @t values ('<html><div><img width="50%" /><img    width="100%" src="foo" alt="bar" />
<span class="c">sometext</span>
<div><img src="foo" alt="bah" width="100%"  /></div></div>
</html>')

;with [xml] as (
    --- convert the string to xml
    select convert(xml,x) as x from @t
)
,matching as (
    -- Find all the img nodes that have width=100%
    select convert(varchar(max),c.query('.')) as matches
    from [xml]
    cross apply x.nodes('//img[@width="100%"]') as t(c)
) 
,source as (
    -- Tidy up the source, as it has multiple spaces that prevent the matches from finding the nodes
    select convert(varchar(max),convert(xml,x)) as trimmed from @t
)
,replaced as (
    -- Work through recursively removing the 100% from matching nodes
    select trimmed from source
    union all
    select replace(trimmed,matches,replace(matches,'width="100%"','')) as replaced from matching
    cross join replaced
    where charindex(matches,replaced.trimmed)>0
)
-- Get the shortest (or last) string from above
select top 1 * from replaced order by len(trimmed) 

Выход:

<html><div><img width="50%"/><img  src="foo" alt="bar"/><span class="c">sometext</span><div><img src="foo" alt="bah" /></div></div></html>
0 голосов
/ 30 августа 2018

Решение для БД Oracle, так как неясно, какую СУБД ищет решение

Если width всегда после тега img, вы можете сделать это в базе данных Oracle с помощью функции Replace, например

replace (<column>,'<img width="100%" ','<img ');

оператор обновления может выглядеть как

update <table>
set <column> = replace (<column>,'<img width="100%" ','<img ')

Если атрибут width не идет сразу после тега img, тогда сначала нужно найти тег IMG. Это можно сделать с помощью регулярного выражения. Как найти теги img обсуждалось здесь не раз.

проверьте этот вопрос

Это измененное регулярное выражение пользователя sln может быть полезно для вас:

 <img\s[^>]*?(width\s*=\s*[''\"]([^''\"]*?)[''\"])([^>]*?)>

Сначала вы должны найти теги img и отфильтровать информацию

replace(REGEXP_SUBSTR(txt,'<img\s[^>]*?width\s*=\s*[''\"]([^''\"]*?)[''\"][^>]*?>'),'width="100%" ','') 

тогда вы можете заменить теги img отфильтрованными тегами во всем html, которые могут выглядеть следующим образом:

REGEXP_REPLACE(txt
             , '<img\s[^>]*?(width\s*=\s*[''\"]([^''\"]*?)[''\"])([^>]*?)>'
             , replace(REGEXP_SUBSTR(txt,'<img\s[^>]*?width\s*=\s*[''\"]([^''\"]*?)[''\"][^>]*?>'),'width="100%" ','')          
             )

Тест SQLFiddel

Возможно, это не оптимальный вариант, но может быть полезным

...