BeautifulSoup очистка вложенных тегов

Всем привет!

Нужно взять из кода веб страницы только текст, который лежит в определенных тегах. Если в этих тегах, есть вложенные теги, их содержимое не нужно учитывать. Например, мы имеем html код

<div><p>Нужный мне текст  <a href="#">Не нужная мне ссылка</a> <span>данный текст также мне не нужен</span> </p> ТЕКСТ</div>

Как мне взять, все что есть в теге DIV и P, удалив при этом вложенные теги ?

Из оптимального, что получилось:

markup = '<div><p>Нужный мне текст  <a href="#">Не нужная мне ссылка</a> <span>данный текст также мне не нужен</span> </p> ТЕКСТ <a href="#">Не нужная мне ссылка 2</a><span>Спамный текст</span></div>'
root = BeautifulSoup(markup, 'html.parser')
div = root.select_one('div')
anchor_len = len ([ tag for tag in div.findAll() if tag.name == 'a'])
span_len = len ([ tag for tag in div.findAll() if tag.name == 'span'])
decomp_anchor = [ div.select_one('a').decompose() for i in range (anchor_len)]
decomp_span = [ div.select_one('span').decompose() for i in range (span_len)]
print(div.text)

Но насколько это оптимальный код? Просто decompose() удаляет первый тег в дереве, а нужно удалять все теги в дереве.


Ответы (1 шт):

Автор решения: gil9red

Используйте метод decompose для удаление тегов.

Пример:

from bs4 import BeautifulSoup

html = """
<div><p>Нужный мне текст  <a href="#">Не нужная мне ссылка</a> <span>данный текст также мне не нужен</span> </p> ТЕКСТ</div>
"""

root = BeautifulSoup(html, 'html.parser')
div = root.select_one('div')
div.select_one('a').decompose()
div.select_one('span').decompose()

print(root)
# <div><p>Нужный мне текст    </p> ТЕКСТ</div>

Если элементов несколько, то используйте метод select для получения списка элементов, после проходите в цикле по-элементно и у каждого элемента вызывайте decompose:

...
div = root.select_one('div')

for x in div.select('a'):
    x.decompose()

for x in div.select('span'):
    x.decompose()

print(root)
→ Ссылка