2008年6月2日月曜日

CyberNeko HTML ParserでHTMLをSAXで読み込んでRSSのURLを取得してみた。(更 新ping受信サーバ作成その3)

更新pingだけでは、あるブログが更新されたというのはわかっても、何の記事が何時に更新されたのか? まではわかりません。
今回は更新pingを受信後に最新記事情報を取得する部分をやってみました。


まず何が最新か? なのですがブログですと大抵RSSで記事の要約を公開していますのでそれを取得します。
RSSの場所はHTMLのhead内のlinkタグでtypeがapplication/rss+xmlとなっているものから取得することにします。
まぁ、これが本当にどのブログもそうなってるのかまではちょっとわからなかったんですが、SeesaaブログとFC2ブログはそうなってたんでそれを前提にしています。
で、HTMLから情報を取り出す方法ですが今回はCyberNeko HTML Parserを使いました。このライブラリはHTMLをXMLの様にDOMやSAXで処理することの出来るものです。(まぁ、application/rss+xmlとなっている部分を探すだけなら単純にHTMLを取得して正規表現で取得するというのでもいい気はしますが)
まず準備としてはCyberNeko HTML Parserのライブラリをダウンロードして配置します。
今回はコードの受信部分のみ抜粋します。
SAXParserが
import org.cyberneko.html.parsers.SAXParser;
なぐらいで特に難しい点はありません。


private String getRssURL(String weblogurl) {
RSSHandler handler = new RSSHandler();
try {
URL url = new URL(weblogurl);
HttpURLConnection urlconn =
(HttpURLConnection) url.openConnection();
SAXParser parser = new SAXParser();
parser.setContentHandler(handler);
InputSource inputSource = new InputSource(urlconn.getInputStream());
parser.parse(inputSource);
} catch (Exception e) {
log.debug(e);
}
return handler.getRssURL();
}


RSSHandlerがHTMLを走査して該当データを探します。
typeがapplication/rss+xmlとなっているlinkタグのhref部分ですね。
見つけたらRSSHandlerがそのデータを保持します。
次にRSSHandlerの中身です。
net.ukauka.xmlrpc.handler.RSSHandler
package net.ukauka.xmlrpc.handler;
import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;
import org.xml.sax.SAXException;
public class RSSHandler extends org.xml.sax.helpers.DefaultHandler {
protected Log log = LogFactory.getLog(this.getClass());
private final static String RSS_TYPE = "application/rss+xml";
private final static String QNAME_LINK = "LINK";
private String rssURL = null;
/**
* エレメント開始
*
* @throws SAXException
*/
public void startElement(String uri, String localName, String qName,
org.xml.sax.Attributes attributes) throws SAXException {
// LINKタグでtypeがrssの場合。
if (qName.equals(QNAME_LINK)
&& RSS_TYPE.equals(attributes.getValue("type"))) {
rssURL = attributes.getValue("href");
throw new SAXException("RSSを発見した。");
}
}
public String getRssURL() {
return this.rssURL;
}
}


ここも特に難しいことは行っていません。
startElementがタグの開始が読み込まれた時に実行されるメソッドなので、
タグがLINKで属性のtypeがapplication/rss+xmlの場合にhrefを取得するという判定を行っているだけです。
その後に例外を発生させて無理やり処理を終了させています。(このやり方がいいのかはわかりませんが、それ以降を走査しても意味ありませんし)
これでRSSのURLを取得できました。
次回はRSSの中身を読み取る処理を行います。

0 件のコメント:

コメントを投稿