How to extract text without tags (between br)?

Question:

I am trying to store headings and paragraphs into different arrays, i can’t manage with text between <br>.

Here’s my HTML code and python below:

<p><strong>W Ognisku</strong><br>W londyńskim Ognisku Polskim odbyło się spotkanie z brytyjskim historykiem<br><br><strong>10 lat polskiej szkoły sobotniej Copernicus </strong><br>W Wielkiej Brytanii <br><br><strong>IV Bieg Pamięci Dywizjonu 303 w Londynie</strong><br>Już po raz czwarty w dzielnicy<br><br><strong>81 Liebermana</strong><br>21 majowym przeciwstawił się rządom Piłsudskiego. <br><strong><br>Londynem</strong><br>Był setki pełnymi garściami.</p>

and soup:

from bs4 import BeautifulSoup

with open('/Users/milek/Desktop/index.html', 'r') as f:
    contents = f.read()
    soup = BeautifulSoup(contents, 'lxml')
    headings = []
    txt = []

    for strong_tag in soup.find_all('strong'):
        headings.append(strong_tag.text)

print(headings)

I retrieved headings with full success but I have pretty hard time storing the rest – paragraphs.

@HedgeHog

Here’s the code in selenium which relies on this stored data which im trying to achieve. Headings are

#++++++++++++++++++++++ ADD VIDEO ++++++++++++++++++++++
def addVideo(titles):
    add_button = browser.find_element(By.CLASS_NAME, 'object-adder')
    add_button.click()
    chooseVIDEO = browser.find_element(By.CSS_SELECTOR, "a[value*='2']")
    chooseVIDEO.click()
    sleep(3)
    #   -------------- ADD HEADING --------------
    title = browser.find_element(By.NAME, 'title')
    title.send_keys(THIS IS THE PLACE FOR EACH HEADING)
    sleep(4)
    #   -------------- NO RESTRICTIONS ------------
    zone_restriction = browser.find_element(By.NAME,     'zoneRestriction')
    zone_restriction.click()
    sleep(4)
    typewrite('b')
    typewrite('e')
    press('enter')
    sleep(2)
    #   -------------- NO ADDS ---------------
    noAdv = browser.find_element(By.NAME, 'adsEnabled')
    noAdv.click()
    #   -------------  SAVE  -----------
    sleep(3)
    saveGoObj = browser.find_element(By.ID, 'saveButton')
    saveGoObj.click() 



#++++++++++++++++++++++  ADD PARAGRAPH +++++++++++++++++++++++
def addTXT(paras):
    add_button = browser.find_element(By.CLASS_NAME, 'object-adder')
    add_button.click()
    chooseParagraph = browser.find_element(By.CSS_SELECTOR, "a[value*='33']")
    chooseParagraph.click()
    sleep(3)
#     -------------- ADD TITLE --------------
    title = browser.find_element(By.NAME, 'title')
    title.send_keys('txt')
#     -------------- ADD PARAGRAPH -------------
    textPara = browser.find_element(By.XPATH, "//textarea[@name='text']")
    textPara.send_keys(THIS IS THE PLACE FOR EACH PARAGRAPH)
    sleep(6)
#     -------------  SAVE -----------
    saveGoObj = browser.find_element(By.ID, 'saveButton')
    saveGoObj.click()
    sleep(6)
Asked By: yerbaMatte

||

Answers:

from bs4 import BeautifulSoup
html = """<html>
 <body>
  <p>
   <strong>
    W Ognisku
   </strong>
   <br/>
   W londyńskim Ognisku Polskim odbyło się spotkanie z brytyjskim historykiem
   <br/>
   <br/>
   <strong>
    10 lat polskiej szkoły sobotniej Copernicus
   </strong>
   <br/>
   W Wielkiej Brytanii
   <br/>
   <br/>
   <strong>
    IV Bieg Pamięci Dywizjonu 303 w Londynie
   </strong>
   <br/>
   Już po raz czwarty w dzielnicy
   <br/>
   <br/>
   <strong>
    81 Liebermana
   </strong>
   <br/>
   21 majowym przeciwstawił się rządom Piłsudskiego.
   <br/>
   <strong>
    <br/>
    Londynem
   </strong>
   <br/>
   Był setki pełnymi garściami.
  </p>
 </body>
</html>"""


soup = BeautifulSoup(html, 'lxml')
goal = [x.next_element.strip() for x in soup.select('p strong + br')]
print(goal)

Output:

['W londyńskim Ognisku Polskim odbyło się spotkanie z brytyjskim historykiem', 'W Wielkiej 
Brytanii', 'Już po raz czwarty w dzielnicy', '21 majowym przeciwstawił się rządom Piłsudskiego.', 'Był setki pełnymi garściami.']

Just in addition to @αԋɱҽԃ αмєяιcαη precise answer for list – Instead of working with lists, that often causes mismatches of length, if elements are not available as expected, I would always recommend to use more structured constructs like dictionaries and extract all related data in one go:

{
    e.get_text(strip=True):e.find_next_sibling(text=True)
    for e in soup.select('p strong')
}

Example

from bs4 import BeautifulSoup

html = '''
<p><strong>W Ognisku</strong><br>W londyńskim Ognisku Polskim odbyło się spotkanie z brytyjskim historykiem<br><br><strong>10 lat polskiej szkoły sobotniej Copernicus </strong><br>W Wielkiej Brytanii <br><br><strong>IV Bieg Pamięci Dywizjonu 303 w Londynie</strong><br>Już po raz czwarty w dzielnicy<br><br><strong>81 Liebermana</strong><br>21 majowym przeciwstawił się rządom Piłsudskiego. <br><strong><br>Londynem</strong><br>Był setki pełnymi garściami.</p>
'''
soup = BeautifulSoup(html)

{
    e.get_text(strip=True):e.find_next_sibling(text=True)
    for e in soup.select('p strong')
}

Output

{'W Ognisku': 'W londyńskim Ognisku Polskim odbyło się spotkanie z brytyjskim historykiem',
 '10 lat polskiej szkoły sobotniej Copernicus': 'W Wielkiej Brytanii ',
 'IV Bieg Pamięci Dywizjonu 303 w Londynie': 'Już po raz czwarty w dzielnicy',
 '81 Liebermana': '21 majowym przeciwstawił się rządom Piłsudskiego. ',
 'Londynem': 'Był setki pełnymi garściami.'}​

EDIT

To get lists / tuples from dict:

headings, texts = zip(*{
    e.get_text(strip=True):e.find_next_sibling(text=True)
    for e in soup.select('p strong')
}.items())

To get lists only:

headings = [e.get_text(strip=True) for e in soup.select('p strong')]
texts = [e.find_next_sibling(text=True)  for e in soup.select('p strong')]
Answered By: HedgeHog