jsoup
Javaで HTML のパースを行うためのライブラリ。
公式サイトの Cookbook がシンプルで分かりやすいです。
CSS, jQuery のセレクタっぽい探索が可能なので比較的使いやすそう。
作ってみたコード
Yahoo!ニュースのトピックス一覧ページから指定した日付のトピックス一覧を取得。
利用価値ない気がしますがJSON形式で出力もします。
Topic.java
package ksugimori.sample.jsoup;
public class Topic {
private String title;
private String url;
private String category;
private String date;
/**
* Constructor
*/
public Topic(String title, String url, String category, String date) {
this.title = title;
this.url = url;
this.category = category;
this.date = date;
}
public String toString() {
StringBuilder s = new StringBuilder();
s.append(String.format(" Title : %s%n", this.title));
s.append(String.format(" Category: %s%n", this.category));
s.append(String.format(" Date : %s%n", this.date));
s.append(String.format(" URL : %s%n", this.url));
return s.toString();
}
public String toJSON() {
String keyValFormat = "\"%s\": \"%s\"";
StringBuilder s = new StringBuilder();
s.append("{");
s.append(String.format(keyValFormat, "title" , this.title )).append(", ");
s.append(String.format(keyValFormat, "url" , this.url )).append(", ");
s.append(String.format(keyValFormat, "category", this.category)).append(", ");
s.append(String.format(keyValFormat, "date", this.date ));
s.append("}");
return s.toString();
}
}
YahooTopicsParser.java
package ksugimori.sample.jsoup;
import java.io.IOException;
import java.text.SimpleDateFormat;
import java.util.ArrayList;
import java.util.Collections;
import java.util.Date;
import java.util.List;
import org.jsoup.Jsoup;
import org.jsoup.nodes.Document;
import org.jsoup.nodes.Element;
import org.jsoup.select.Elements;
public class YahooTopicsParser {
public static final String DATE_FORMAT = "yyyyMMdd";
public static final String URL = "http://news.yahoo.co.jp/list/";
/**
* 指定した日付の Topics を取得します
*
* @param date 対象日付
* @return Topic のリスト
*/
public static List<Topic> parseAll(Date date) {
String dateStr = new SimpleDateFormat(DATE_FORMAT).format(date);
try {
Document doc = Jsoup.connect(URL).data("d", dateStr).get(); // リクエストパラメータを Connection.data() で指定
Elements topicElements = doc.select("ul.list li"); // Topics のリストを抽出
List<Topic> topicList = new ArrayList<Topic>();
for (Element element : topicElements) {
topicList.add(parse(element));
}
return topicList;
} catch (IOException e) {
System.out.println("Something wrong.");
return Collections.emptyList();
}
}
/**
* 1トピックの内容を取得します
*
* @param element
* @return Topic オブジェクト
*/
private static Topic parse(Element element) {
String title = element.select("span.ttl").first().text();
String url = element.select("a").first().attr("href");
String category = element.select("span.cate").first().text();
String date = element.select("span.date").first().text();
return new Topic(title, url, category, date);
}
}
Main.java
package ksugimori.sample.jsoup;
import java.util.Date;
public class Main {
public static void main(String[] args) {
Date today = new Date();
for (Topic topic : YahooTopicsParser.parseAll(today)) {
System.out.println(topic.toJSON());
System.out.println(topic);
}
}
}
出力例
{"title": "野生トキ 今季初の抱卵始まる", "url": "http://news.yahoo.co.jp/pickup/6195256", "category": "科学", "date": "2016年3月21日 22時21分"}
Title : 野生トキ 今季初の抱卵始まる
Category: 科学
Date : 2016年3月21日 22時21分
URL : http://news.yahoo.co.jp/pickup/6195256
...