目次

前のトピックへ

19. 構造化マークアップツール

次のトピックへ

19.2. sgmllib — 単純な SGML パーザ

このページ

19.1. HTMLParser — HTML および XHTML のシンプルなパーザ

ノート

HTMLParser モジュールは Python 3.0 で html.parser に改名されました。ソースを 3.0 用に移行する際には 2to3 がインポートを自動的に直してくれます。

バージョン 2.2 で追加.

このモジュールでは HTMLParser クラスを定義します。このクラスは HTML (ハイパーテキスト記述言語、 HyperText Mark-up Language) および XHTML で書式化されているテキストファイルを解釈するための基礎となります。 htmllib にあるパーザと違って、このパーザは sgmllib の SGML パーザに基づいてはいません。

class HTMLParser.HTMLParser

HTMLParser クラスは引数なしでインスタンス化します。

HTMLParser インスタンスに HTML データが入力されると、タグが開始したとき、及び終了したときに関数を呼び出します。 HTMLParser クラスは、ユーザが行いたい動作を提供するために上書きできるようになっています。

htmllib のパーザと違い、このパーザは終了タグが開始タグと一致しているか調べたり、外側のタグ要素が閉じるときに内側で明示的に閉じられていないタグ要素のタグ終了ハンドラを呼び出したりはしません。

例外も定義されています:

exception HTMLParser.HTMLParseError

パーズ中にエラーに遭遇した場合に HTMLParser クラスが送出する例外です。この例外は三つの属性を提供しています: msg はエラーの内容を説明する簡単なメッセージ、 lineno は壊れたマークアップ構造を検出した場所の行番号、 offset は問題のマークアップ構造の行内での開始位置を示す文字数です。

HTMLParser インスタンスは以下のメソッドを提供します:

HTMLParser.reset()

インスタンスをリセットします。未処理のデータは全て失われます。インスタンス化の際に非明示的に呼び出されます。

HTMLParser.feed(data)

パーザにテキストを入力します。入力が完全なタグ要素で構成されている場合に限り処理が行われます; 不完全なデータであった場合、新たにデータが入力されるか、 close() が呼び出されるまでバッファされます。

HTMLParser.close()

全てのバッファされているデータについて、その後にファイル終了マークが続いているとみなして強制的に処理を行います。このメソッドは入力データの終端で行うべき追加処理を定義するために派生クラスで上書きすることができますが、再定義を行ったクラスでは常に、 HTMLParser 基底クラスのメソッド close() を呼び出さなくてはなりません。

HTMLParser.getpos()

現在の行番号およびオフセット値を返します。

HTMLParser.get_starttag_text()

最も最近開かれた開始タグのテキスト部分を返します。このテキストは必ずしも元データを構造化する上で必須ではありませんが、 “広く知られている (as deployed)” HTML を扱ったり、入力を最小限の変更で再生成 (属性間の空白をそのままにする、など) したりする場合に便利なことがあります。

HTMLParser.handle_starttag(tag, attrs)

このメソッドはタグの開始部分を処理するために呼び出されます。派生クラスで上書きするためのメソッドです; 基底クラスの実装では何も行いません。

tag 引数はタグの名前で、小文字に変換されています。 attrs 引数は (name, value) のペアからなるリストで、タグの <> 括弧内にある属性が収められています。 name は小文字に変換され、 value 内の引用符は取り除かれ、文字参照とエンティティ参照は置換されます。例えば、タグ <A HREF="http://www.cwi.nl/"> を処理する場合、このメソッドは handle_starttag('a', [('href', 'http://www.cwi.nl/')]) として呼び出されます。

バージョン 2.6 で変更: 属性中の htmlentitydefs の全てのエンティティ参照が置換されるようになりました。

HTMLParser.handle_startendtag(tag, attrs)

handle_starttag() と似ていますが、パーザが XHTML 形式の空タグ (<a .../>) に遭遇した場合に呼び出されます。この特定の語彙情報 (lexical information) が必要な場合、このメソッドをサブクラスで上書きすることができます; 標準の実装では、単に handle_starttag() および handle_endtag() を呼ぶだけです。

HTMLParser.handle_endtag(tag)

このメソッドはあるタグ要素の終了タグを処理するために呼び出されます。派生クラスで上書きするためのメソッドです; 基底クラスの実装では何も行いません。 tag 引数はタグの名前で、小文字に変換されています。

HTMLParser.handle_data(data)

このメソッドは、他のメソッドに当てはまらない任意のデータを処理するために呼び出されます。派生クラスで上書きするためのメソッドです; 基底クラスの実装では何も行いません。

HTMLParser.handle_charref(ref)

このメソッドはタグ外の &#ref; 形式の文字参照 (character reference) を処理するために呼び出されます。 ref には、先頭の &# および末尾の ; は含まれません。派生クラスで上書きするためのメソッドです; 基底クラスの実装では何も行いません。

HTMLParser.handle_entityref(name)

このメソッドはタグ外の &name; 形式の一般のエンティティ参照 (entity reference) name を処理するために呼び出されます。 name には、先頭の & および末尾の ; は含まれません。派生クラスで上書きするためのメソッドです; 基底クラスの実装では何も行いません。

HTMLParser.handle_comment(data)

このメソッドはコメントに遭遇した場合に呼び出されます。 comment 引数は文字列で、 -- および -- デリミタ間の、デリミタ自体を除いたテキストが収められています。例えば、コメント <!--text--> があると、このメソッドは引数 'text' で呼び出されます。派生クラスで上書きするためのメソッドです; 基底クラスの実装では何も行いません。

HTMLParser.handle_decl(decl)

パーザが SGML の doctype 宣言を読み出した際に呼び出されるメソッドです。 decl パラメタは <!...> 記述内の宣言内容全体になります。派生クラスで上書きするためのメソッドです; 基底クラスの実装では何も行いません。

HTMLParser.unknown_decl(data)

パーザが認識できない SGML 宣言を読み出した際に呼び出されるメソッドです。 data パラメタは <!...> 記述内の宣言内容全体になります。派生クラスで上書きすると良いかもしれません。基底クラスの実装では HTMLParseError を送出します。

HTMLParser.handle_pi(data)

処理指令に遭遇した場合に呼び出されます。 data には、処理指令全体が含まれ、例えば <?proc color='red'> という処理指令の場合、 handle_pi("proc color='red'") のように呼び出されます。このメソッドは派生クラスで上書きするためのメソッドです; 基底クラスの実装では何も行いません。

ノート

The HTMLParser クラスでは、処理指令に SGML の構文を使用します。末尾に '?' がある XHTML の処理指令では、 '?' が data に含まれることになります。

exception HTMLParser.HTMLParseError

HTML の構文に沿わないパターンを発見したときに送出される例外です。 HTML 構文法上の全てのエラーを発見できるわけではないので注意してください。

19.1.1. HTML パーザアプリケーションの例

基礎的な例として、 HTMLParser クラスを使い、発見したタグを出力する、非常に基礎的な HTML パーザを以下に示します。

from HTMLParser import HTMLParser

class MyHTMLParser(HTMLParser):

    def handle_starttag(self, tag, attrs):
        print "Encountered the beginning of a %s tag" % tag

    def handle_endtag(self, tag):
        print "Encountered the end of a %s tag" % tag