html.parser
— Simple HTML and XHTML parser¶
Вихідний код: Lib/html/parser.py
Цей модуль визначає клас HTMLParser
, який служить основою для аналізу текстових файлів, відформатованих у HTML (HyperText Mark-up Language) і XHTML.
- class html.parser.HTMLParser(*, convert_charrefs=True)¶
Створіть екземпляр парсера, здатний аналізувати недійсну розмітку.
Якщо convert_charrefs має значення
True
(за замовчуванням), усі посилання на символи (крім тих, що містяться в елементахscript
/style
) автоматично перетворюються на відповідні символи Unicode.Екземпляр
HTMLParser
отримує дані HTML і викликає методи обробки, коли зустрічаються початкові теги, кінцеві теги, текст, коментарі та інші елементи розмітки. Користувач повинен створити підкласHTMLParser
і перевизначити його методи для реалізації бажаної поведінки.Цей синтаксичний аналізатор не перевіряє відповідність кінцевих тегів початковим тегам і не викликає обробник кінцевих тегів для елементів, які закриваються неявно шляхом закриття зовнішнього елемента.
Змінено в версії 3.4: Додано аргумент ключового слова convert_charrefs.
Змінено в версії 3.5: Значення за замовчуванням для аргументу convert_charrefs тепер
True
.
Приклад програми аналізатора HTML¶
As a basic example, below is a simple HTML parser that uses the
HTMLParser
class to print out start tags, end tags, and data
as they are encountered:
from html.parser import HTMLParser
class MyHTMLParser(HTMLParser):
def handle_starttag(self, tag, attrs):
print("Encountered a start tag:", tag)
def handle_endtag(self, tag):
print("Encountered an end tag :", tag)
def handle_data(self, data):
print("Encountered some data :", data)
parser = MyHTMLParser()
parser.feed('<html><head><title>Test</title></head>'
'<body><h1>Parse me!</h1></body></html>')
Результат буде таким:
Encountered a start tag: html
Encountered a start tag: head
Encountered a start tag: title
Encountered some data : Test
Encountered an end tag : title
Encountered an end tag : head
Encountered a start tag: body
Encountered a start tag: h1
Encountered some data : Parse me!
Encountered an end tag : h1
Encountered an end tag : body
Encountered an end tag : html
HTMLParser
Методи¶
Екземпляри HTMLParser
мають такі методи:
- HTMLParser.feed(data)¶
Подати текст до синтаксичного аналізатора. Він обробляється, оскільки складається з повних елементів; неповні дані буферизуються, поки не буде подано більше даних або не буде викликано
close()
. data має бутиstr
.
- HTMLParser.close()¶
Примусова обробка всіх буферизованих даних так, ніби за ними стоїть позначка кінця файлу. Цей метод може бути перевизначений похідним класом, щоб визначити додаткову обробку в кінці введення, але перевизначена версія завжди повинна викликати метод базового класу
HTMLParser
close()
.
- HTMLParser.reset()¶
Скинути примірник. Втрачає всі необроблені дані. Це викликається неявно під час створення екземпляра.
- HTMLParser.getpos()¶
Повернути поточний номер рядка та зсув.
- HTMLParser.get_starttag_text()¶
Повертає текст останнього відкритого початкового тегу. Зазвичай це не потрібно для структурованої обробки, але може бути корисним для роботи з HTML «у розгорнутому стані» або для повторного створення вхідних даних із мінімальними змінами (можна зберегти пробіли між атрибутами тощо).
Наступні методи викликаються, коли зустрічаються дані або елементи розмітки, і вони призначені для перевизначення в підкласі. Реалізації базового класу нічого не роблять (крім handle_startendtag()
):
- HTMLParser.handle_starttag(tag, attrs)¶
Цей метод викликається для обробки початкового тегу елемента (наприклад,
<div id="main">
).Аргумент тег — це назва тегу, перетворена в нижній регістр. Аргумент attrs — це список пар
(ім’я, значення)
, що містить атрибути, що містяться в дужках<>
тегу. Ім’я буде перекладено на нижній регістр, а лапки в значенні видалено, а посилання на символи та сутності замінено.Наприклад, для тегу
<A HREF="https://www.cwi.nl/">
цей метод буде називатисяhandle_starttag('a', [('href', 'https://www.cwi.nl/')])
.Усі посилання на сутності з
html.entities
замінюються в значеннях атрибутів.
- HTMLParser.handle_endtag(tag)¶
Цей метод викликається для обробки кінцевого тегу елемента (наприклад,
</div>
).Аргумент тег — це назва тегу, перетворена в нижній регістр.
- HTMLParser.handle_startendtag(tag, attrs)¶
Подібно до
handle_starttag()
, але викликається, коли аналізатор зустрічає порожній тег у стилі XHTML (<img ... />
). Цей метод може бути замінений підкласами, які потребують саме цієї лексичної інформації; стандартна реалізація просто викликаєhandle_starttag()
іhandle_endtag()
.
- HTMLParser.handle_data(data)¶
Цей метод викликається для обробки довільних даних (наприклад, текстових вузлів і вмісту
<script> ... </script>
і<style> ... </style>
).
- HTMLParser.handle_entityref(name)¶
Цей метод викликається для обробки іменованого посилання на символ у формі
&name;
(наприклад,>
), де name є загальним посиланням на сутність (наприклад'gt'
). Цей метод ніколи не викликається, якщо convert_charrefs має значенняTrue
.
- HTMLParser.handle_charref(name)¶
This method is called to process decimal and hexadecimal numeric character references of the form
&#NNN;
and&#xNNN;
. For example, the decimal equivalent for>
is>
, whereas the hexadecimal is>
; in this case the method will receive'62'
or'x3E'
. This method is never called if convert_charrefs isTrue
.
- HTMLParser.handle_comment(data)¶
Цей метод викликається, коли зустрічається коментар (наприклад,
<!--comment-->
).Наприклад, коментар
<!-- comment -->
призведе до виклику цього методу з аргументом' comment ''
.Вміст умовних коментарів Internet Explorer (condcoms) також буде надіслано цьому методу, тому для
<!--[if IE 9]> IE9-специфічного вмісту <![endif]-->
цей метод отримає'[if IE 9]>IE9-специфічний вміст< ![endif]''
.
- HTMLParser.handle_decl(decl)¶
Цей метод викликається для обробки декларації типу документа HTML (наприклад,
<!DOCTYPE html>
).Параметр decl буде повним вмістом оголошення всередині розмітки
<!...>
(наприклад,'DOCTYPE html'
).
- HTMLParser.handle_pi(data)¶
Метод викликається, коли зустрічається інструкція обробки. Параметр data міститиме всю інструкцію обробки. Наприклад, для інструкції обробки
<?proc color='red'>
, цей метод мав би викликатися якhandle_pi("proc color='red'")
. Він призначений для перевизначення похідним класом; реалізація базового класу нічого не робить.Примітка
Клас
HTMLParser
використовує синтаксичні правила SGML для обробки інструкцій. Інструкція з обробки XHTML із використанням кінцевого'?''
призведе до включення'?''
до даних.
- HTMLParser.unknown_decl(data)¶
Цей метод викликається, коли аналізатор читає нерозпізнану декларацію.
Параметр data буде повним вмістом оголошення всередині розмітки
<![...]>
. Іноді корисно бути перевизначеним похідним класом. Реалізація базового класу нічого не робить.
Приклади¶
The following class implements a parser that will be used to illustrate more examples:
from html.parser import HTMLParser
from html.entities import name2codepoint
class MyHTMLParser(HTMLParser):
def handle_starttag(self, tag, attrs):
print("Start tag:", tag)
for attr in attrs:
print(" attr:", attr)
def handle_endtag(self, tag):
print("End tag :", tag)
def handle_data(self, data):
print("Data :", data)
def handle_comment(self, data):
print("Comment :", data)
def handle_entityref(self, name):
c = chr(name2codepoint[name])
print("Named ent:", c)
def handle_charref(self, name):
if name.startswith('x'):
c = chr(int(name[1:], 16))
else:
c = chr(int(name))
print("Num ent :", c)
def handle_decl(self, data):
print("Decl :", data)
parser = MyHTMLParser()
Parsing a doctype:
>>> parser.feed('<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01//EN" '
... '"http://www.w3.org/TR/html4/strict.dtd">')
Decl : DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01//EN" "http://www.w3.org/TR/html4/strict.dtd"
Parsing an element with a few attributes and a title:
>>> parser.feed('<img src="python-logo.png" alt="The Python logo">')
Start tag: img
attr: ('src', 'python-logo.png')
attr: ('alt', 'The Python logo')
>>>
>>> parser.feed('<h1>Python</h1>')
Start tag: h1
Data : Python
End tag : h1
The content of script
and style
elements is returned as is, without
further parsing:
>>> parser.feed('<style type="text/css">#python { color: green }</style>')
Start tag: style
attr: ('type', 'text/css')
Data : #python { color: green }
End tag : style
>>> parser.feed('<script type="text/javascript">'
... 'alert("<strong>hello!</strong>");</script>')
Start tag: script
attr: ('type', 'text/javascript')
Data : alert("<strong>hello!</strong>");
End tag : script
Parsing comments:
>>> parser.feed('<!--a comment-->'
... '<!--[if IE 9]>IE-specific content<![endif]-->')
Comment : a comment
Comment : [if IE 9]>IE-specific content<![endif]
Parsing named and numeric character references and converting them to the
correct char (note: these 3 references are all equivalent to '>'
):
>>> parser = MyHTMLParser()
>>> parser.feed('>>>')
Data : >>>
>>> parser = MyHTMLParser(convert_charrefs=False)
>>> parser.feed('>>>')
Named ent: >
Num ent : >
Num ent : >
Feeding incomplete chunks to feed()
works, but
handle_data()
might be called more than once
(unless convert_charrefs is set to True
):
>>> for chunk in ['<sp', 'an>buff', 'ered', ' text</s', 'pan>']:
... parser.feed(chunk)
...
Start tag: span
Data : buff
Data : ered
Data : text
End tag : span
Parsing invalid HTML (e.g. unquoted attributes) also works:
>>> parser.feed('<p><a class=link href=#main>tag soup</p ></a>')
Start tag: p
Start tag: a
attr: ('class', 'link')
attr: ('href', '#main')
Data : tag soup
End tag : p
End tag : a