GIS奮闘記

現役GISエンジニアの技術紹介ブログ。主にPythonを使用。

PythonでRSSを使用してアンテナサイトを作る

本日はアンテナサイトを作ってみます。アンテナサイトを作るにはRSSを利用します。RSS - Wikipedia
こんなものを用意してくれているなんて便利な世の中ですね。アンテナサイトといえば2ちゃんねるのまとめを対象としたものが多い気がしますが、本ブログはGISをメインとしてますので、GIS関連ニュースのアンテナサイトを作ってみようと思います。まったく需要がないと思うのですが(笑)

まず、RSS解析には「feedparser」というライブラリを使用しますので、pip install feedparser をお願いします。それと「pandas」もインストールをお願いします(←今回の例では使用しましたが、これを使わなくても全然実装可能です)。

また、本ブログでは以下のようなことは考慮していませんので、実際にサイトを立ち上げたりする場合はご注意願います。
・ページ読込時にRSSを取得してる
→本来はRSS取得用のプログラムを定期的に実行してデータを格納しておき、ページ読込時にそのデータを取得した方がいいと思います。そうしないと読込が重くなってしまう可能性があるので。

まずは、サーバーを立ち上げる必要があります。

■cgiserver.py

import CGIHTTPServer
CGIHTTPServer.test()

これだけで開発用サーバーの立ち上げができます。便利ですね!
詳細は以下サイトをご参照ください。
Pythonで学ぶWebアプリ開発のABC みんなのPython Webアプリ編 HTML版(無料) | TRIVIAL TECHNOLOGIES 4 @ats のイクメン日記

RSS対象サイト

以下がRSS対象サイトです。うーん、マニアックですね(笑)

What's New 更新情報 --- GISA 地理情報システム学会
国土地理院ホームページ:新着情報
ESRIジャパン
日本海洋データセンター 新着情報
NPO法人 全国GIS技術研究会

RSS.py

# -*- coding: utf-8 -*-
import feedparser
import time
import pandas as pd

def main():

    #RSSデータ取得
    pds = getRss()

    html_body = u"""<html>
                    <head><meta http-equiv="content-type" content="text/html;charset=utf-8">
                    <link href="../css/sample.css" rel="stylesheet" type="text/css"/>
                    <title>GISアンテナ</title>
                    </head>
                    <body>
                    <div id="pagebody">
                    	<!-- ヘッダ -->
                    	<div id="header"><h1>GISアンテナ</h1></div>
                    	<!-- メインメニュー -->
                    	<ul id="menu">
                    		<li id="menu01"><a href="https://www.google.co.jp/maps" target="_blank">GoogleMap</a></li>
                    		<li id="menu02"><a href="https://www.google.co.jp/intl/ja/earth/" target="_blank">GoogleEarth</a></li>
                    		<li id="menu03"><a href="http://user.numazu-ct.ac.jp/~tsato/webmap/map/gmap.html?data=history" target="_blank">地理院地図</a></li>
                    		<li id="menu04"><a href="http://www.mapion.co.jp/route/" target="_blank">距離測</a></li>
                    		<li id="menu05"><a href="http://www.its-mo.com/" target="_blank">いつもNAVI</a></li>
                    	</ul>
                        <div id="news"><h2>最新記事一覧</h2>
                        <div id="scr"><ul id>
                        """
    cnt = 0
    #最新記事一覧を作成
    for i,row in pds.sort("time",ascending=False).iterrows():
        #表示件数を絞る
        if cnt == 10:
            break
        if row.flg == "0":
            html_body += "<li id =" + "inline" + ">" + row.time + "   " + "<a href=" + row.link + " target" + "=_blank>" + row.title + "</a></li>"
        cnt += 1
    html_body += "</div></div></ul><div id=" + "content" + "><ul id=" + "list" + ">"

    for i,row in pds.iterrows():
        if row.flg == "1":
            html_body += u"<h2><a class=" + "feed-link href=" + row.link + " target" + "=_blank>"  + row.title + "</a></h2>"

        elif row.flg == "0":
            html_body += u"<li id= " + "inline" + "><a href=" + row.link + " target" + "=_blank>"  + row.title + "</a></li>"

    html_body += u"""</ul></div><div id="footer">
                     <address>Copyright (c) GISアンテナ All Rights Reserved.</address></div></div></body></html>
                     """
    print 'Content-type: text/html\n'
    print html_body.encode('utf-8')

def getRss():
    lists =[]

    #対象のRSS
    lists.append("https://www.gisa-japan.org/news/rss.xml")
    lists.append("http://www.gsi.go.jp/index.rdf")
    lists.append("http://www.esrij.com/feed/")
    lists.append("http://www.jodc.go.jp/jodcweb/cgi-bin/public/newsrss1.cgi?lang=ja")
    lists.append("http://www.npo-zgis.or.jp/rss.xml")

    rssList = []
    for i,l in enumerate(lists):
        rss = feedparser.parse(l)
        rssList.append([rss.feed.title,rss.feed.link,"",i,"1"])
        #RSS情報をリストに格納
        for entry in rss.entries:
            #RSS情報をリストに格納
            rssList.append([entry.title,entry.link,time.strftime('%Y/%m/%d %X',entry.updated_parsed),i,"0"])

    #RSS情報をデータフレームに格納
    pds = pd.DataFrame(rssList)
    pds.columns = ["title","link","time","category","flg"]
    return pds

if __name__ == '__main__':
    main()

http://localhost:8000/cgi-bin/RSS.py にアクセスしたときにhtmlを生成するプログラムです。
一応CSSものせます。

■sample.css

/*============================================
全般的なスタイル
============================================*/
* {
	margin:0; padding:0; 	/*全要素のマージン・パディングをリセット*/
	line-height:1.5;	/*全要素の行の高さを1.5倍にする*/
	color:#333333;		/*文字色*/

} 
body {
	background-color:#999999;	/*ページ全体の背景色*/
	text-align:center;		/*IE6以下でセンタリングするための対策*/
}
div#pagebody {
	width:920px; margin:0 auto;	/*内容全体をセンタリング*/
	text-align:left;	        /*テキストの配置を左揃えにする*/
	background-color:#ffffff;	/*内容全体の背景色*/
        
}

/*============================================
ヘッダ
============================================*/
div#header {
	height:77px;	
	background-color:#cccccc;		        /*ヘッダ部分の背景色*/
}
h1 {
	padding:20px 0px 0px 30px;		        /*見出し内容の位置調整*/
	font-family:Arial, Helvetica, sans-serif;	/*フォントの種類*/
}


/*============================================
メインメニュー
============================================*/
ul#menu {
	height:42px; background-color:#eeeeee; font-weight:bold;
}
li#menu01,li#menu02,li#menu03,li#menu04,li#menu05 {
	float:left;			/*リスト項目を横に並べる*/
	display:inline;			/*リスト項目をインライン表示にする*/
	list-style-type:none;		/*リストマーカー無しにする*/
}

ul#menu a {
	display:block;				        /*リンクをブロック表示にする*/
	height:42px; padding-top:4px; text-align:center;
	font-family:Arial, Helvetica, sans-serif;	/*フォントの種類*/
}
/*ボタン01~05にはそれぞれ異なる背景画像を指定する*/
li#menu01 {
	width:164px; height:42px;	                
}
li#menu02 {
	width:156px; height:42px;	
}
li#menu03 {
	width:156px; height:42px;	
}
li#menu04 {
	width:156px; height:42px;	
}
li#menu05 {
	width:164px; height:42px;	
}
ul#menu a {
	display:block;				/*リンクをブロック表示にする*/
	height:42px; padding-top:4px; text-align:center;
	text-decoration:none; 			/*リンクの下線を無くす*/
	font-family:Arial, Helvetica, sans-serif;	/*フォントの種類*/
}


/*============================================
コンテンツ
============================================*/
div#content {
	width:860px; margin:10px 20px 10px 0px;	/*幅の指定と位置調整*/
	float:right;				/*2カラム全体を右寄せにする*/
}

li#inline {
width:800px; margin:10px 20px 10px 0px;	/*幅の指定と位置調整*/
float:right;			        /*2カラム全体を右寄せにする*/
display: inline;
margin: 0 10px;
}

div#scr {
  width: 860px;
  max-height: 200px;
  height: auto !important; /* IE6 max-height対応 */
  height: 100px; /* IE6 max-height対応 */
  overflow-x: hidden; /* 横スクロール非表示 */
  overflow-y: scroll; /* 縦スクロール */
}


div#news {
	width:860px; margin:10px 20px 10px 0px;	/*幅の指定と位置調整*/
	float:right;				/*2カラム全体を右寄せにする*/
}



/*見出し・段落・水平線のスタイル指定*/
h2 {
	font-size:100%; margin-bottom:10px; padding-left:25px;
	font-size:95%; border-bottom:solid 1px #cccccc;
	background-image:url("images/icon.gif");
	background-repeat:no-repeat; background-position:left center;
}

/*============================================
フッタ
============================================*/
div#footer {
	height:42px; text-align:center;
	clear:both;					/*回り込みを解除する*/
	background-color:#cccccc;			/*フッタ部分の背景色*/
}
address {
	font-style:normal;			 /*フォントスタイルを標準にする*/
	font-size:small;			 /*フォントサイズを小さくする*/
	padding:5px 0px 5px 0px;		 /*要素内容の位置調整*/
}

では結果を見てみましょう。

f:id:sanvarie:20151216105139p:plain

f:id:sanvarie:20151216105147p:plain

シンプルですが、アンテナサイトっぽいものができました!でも、地味ですね。もっとデザインセンスを磨かねば。。。
おまけでGoogleMapなどへのリンクも作っておきました。今回はローカルでの作成ですが、もう少しサイトを充実させたうえで公開してみたいですね。

以上、本日は「PythonRSSを使用してアンテナサイトを作る」でした。