Googleカレンダーの読み書きとiCalインポート


戻る一つ前のメニューに戻る

目次

ソフトウエアのダウンロード

soft-ico-download.gif PythonソースコードをSubversionブラウザよりダウンロード

機能の概略

Google Data APIsPython Client Libraryを使うサンプルプログラム。

Googleカレンダーから予定を読み出すスクリプトと、予定を書き込むスクリプトはgtkのGUIを実装。iCalファイルをGoogleカレンダーにインポートするスクリプトはコマンドライン版と、そのスクリプトを用いるWebインターフェース(Perlスクリプト)。

動作環境

Python 2.7以降
gtk GUI版
Ubuntu 12.04 LTSで動作確認済み
Web版
Apache Webサーバ
Ubuntu 12.04 LTSおよびFreeBSD 9.1で動作確認済み


Googleカレンダーからの読み出し

soft-googlecalendar-python-reader.jpg
読み出し条件の設定

soft-googlecalendar-python-reader2.jpg
結果表示

ソースコードより主要部分の抜粋

#!/usr/bin/env python
# -*- coding: utf-8 -*-
 
import sys
import gtk
import re
import datetime
import gdata.calendar.client
import os
 
def print_event(user, password):
 
    # Googleサーバに接続し、カレンダー イベントを読み出す
    try:
        list_schedules = read_event_google_calendar(datetime_start, datetime_end, max_results, user, password)
    except:
        # 読み出し失敗のメッセージボックスを表示
        dlg = gtk.MessageDialog(type=gtk.MESSAGE_INFO, buttons=gtk.BUTTONS_OK, message_format='Googleカレンダーから読み出せません')
        dlg.set_title("GoogleカレンダーReader")
        dlg.show_all()
        ret = dlg.run()
        dlg.destroy()
        return
 
    # カレンダー イベントをダイアログに表示する
    dlg = gtk.MessageDialog(type=gtk.MESSAGE_WARNING, buttons=gtk.BUTTONS_OK, message_format='Googleカレンダー')
    str_message = ""
    for list_item in list_schedules:
        time_start_date = parse_datetime_str(list_item["start"])
        str_start_date = "%4d/%02d/%02d" % (time_start_date.year, time_start_date.month, time_start_date.day)
        str_message += (str_start_date + " : " + list_item["title"] + "\n")
    dlg.format_secondary_text(str_message)
    dlg.run()
    dlg.destroy()
 
# Googleサーバに接続し、カレンダー イベントを読み出す
def read_event_google_calendar(datetime_start, datetime_end, max_results, login_user, login_password):
 
    list_schedules = []
 
    str_date_start = '%4d-%02d-%02d' % (datetime_start.year, datetime_start.month, datetime_start.day)
    str_date_end = '%4d-%02d-%02d' % (datetime_end.year, datetime_end.month, datetime_end.day)
 
    calendar_service = gdata.calendar.client.CalendarClient()
    calendar_service.ssl = True
    calendar_service.ClientLogin(login_user, login_password, "test python script");
 
    query = gdata.calendar.client.CalendarEventQuery(start_min=str_date_start, start_max=str_date_end,
                max_results=max_results, orderby='starttime', sortorder='ascending')
    feed = calendar_service.GetCalendarEventFeed(q=query)
 
    for i,ev in enumerate(feed.entry):
        for e in ev.when:
            dict_schedule = {"title":ev.title.text, "start":e.start, "end":e.end, "updated":ev.updated.text}
            list_schedules.append(dict_schedule)
            break
 
    return list_schedules
 
def parse_datetime_str(str_datetime):
    # Googleカレンダーの日時文字列("2013-01-01T12:59:59.000+09:00" or "2013-01-01")を
    # struct_time 形式に変換する
 
    datetime_ret = datetime.datetime(1990,1,1)
 
    # 末尾のTZ(+09:00)があれば除去する
    str_datetime = str_datetime.split("+")[0]
 
    try:
        # 最低限の変換をまず試してみる
        list_datetime = re.split("[\-/T:\.]", str_datetime)
        if len(list_datetime) >= 3:
            datetime_ret = datetime.datetime(int(list_datetime[0]),int(list_datetime[1]),int(list_datetime[2]))
 
        if len(str_datetime) == 23:
            # "2013-01-01T12:59:59.000" == 23文字
            datetime_ret = datetime.datetime.strptime(str_datetime, '%Y-%m-%dT%H:%M:%S.000')
        elif len(str_datetime) == 10:
            # "2013-01-01" == 10文字
            datetime_ret = datetime.datetime.strptime(str_datetime, '%Y-%m-%d')
        else:
            raise
    except:
        pass    # do nothing
 
    return datetime_ret


Googleカレンダーへの書き込み

soft-googlecalendar-python-insert.jpg
書き込み内容の入力画面

ソースコードより主要部分の抜粋

#!/usr/bin/env python
# -*- coding: utf-8 -*-
 
import sys
import gtk
import re
import datetime
import gdata.calendar.client
import os
import atom
 
# Googleサーバに接続し、カレンダー イベントを追加する
def insert_event_google_calendar(datetime_start, datetime_end, allday, title, place, content, login_user, login_password):
 
    calendar_service = gdata.calendar.client.CalendarClient()
    calendar_service.ssl = True
    calendar_service.ClientLogin(login_user, login_password, "test python script");
 
    event = gdata.calendar.data.CalendarEventEntry()
    event.title = atom.data.Title(text=title)
    event.content = atom.data.Content(text=content)
    event.where.append(gdata.calendar.data.CalendarWhere(value=place))
    if allday == True:
        start_time = '%d-%02d-%02d' % (datetime_start.year, datetime_start.month, datetime_start.day)
        end_time = '%d-%02d-%02d' % (datetime_end.year, datetime_end.month, datetime_end.day)
    else:
        start_time = '%d-%02d-%02dT%02d:%02d:00.000' % (datetime_start.year, datetime_start.month,
            datetime_start.day, datetime_start.hour, datetime_start.minute)
        end_time = '%d-%02d-%02dT%02d:%02d:00.000' % (datetime_end.year, datetime_end.month,
            datetime_end.day, datetime_end.hour, datetime_end.minute)
    event.when.append(gdata.data.When(start=start_time, end=end_time))
 
    calendar_service.InsertEvent(event)


iCalファイルのGoogleカレンダーへのインポート

soft-googlecalendar-python-web.jpg
Web画面

ソースコードより主要部分の抜粋(iCalファイルを読み込んで、リストに格納する部分)

#!/usr/bin/env python
# -*- coding: utf-8 -*-
 
import sys
import os
import pwd
import argparse
import time
import datetime
import atom
import icalendar
import gdata.calendar.client
 
#####
# iCalファイルよりEventを読み取り、リストに格納する
# 戻り値 : list_schedules
def read_ical_file(filename):
 
    # Eventリスト(戻り値)
    list_schedules = []
 
    # icalファイルをテキスト str_icsdata に格納する
    if 1:
#    try:
        fh = open(filename, "r")
        str_icsdata = fh.read()
        fh.close()
    #except:
        #if flag_silent_stdout == False:
            #print "iCal file open error"
        #return
 
    # icalファイル「テキスト」を解析し cal に取り込む
    cal = icalendar.Calendar.from_ical(str_icsdata)
 
    for e in cal.walk():
        if e.name == 'VEVENT' :
            # Eventを1つずつ、辞書形式dict_scheduleに一旦代入し、それをリストlist_schedulesに追加する
            dict_schedule = {"title":unicode(e.decoded("summary"),'utf8') if e.get("summary") else "",
                            "place":unicode(e.decoded("location"),'utf8') if e.get("location") else "",
                            "desc":unicode(e.decoded("description"),'utf8') if e.get("description") else "",
                            "start":e.decoded("dtstart"),
                            "end":e.decoded("dtend"),
                            "updated":e.decoded("dtstamp")
                            }
            list_schedules.append(dict_schedule)
 
    # 予定表Eventを格納したリストを返す
    return list_schedules


使用許諾条件

GNU GPL フリーソフトウエア

戻る一つ前のメニューに戻る