::class-exe

Wunderlistの完了タスクをグラフにした

July 31, 2017

ToDoリストアプリのWunderlist1から完了タスクを取得してグラフにしてみました。Pythonをつかって、直近7日間の完了タスク数をグラフにしています。

環境は以下の通りです。

$ python -V
Python 2.7.10
$ pip freeze
matplotlib==2.0.0
python-dateutil==2.6.0
pytz==2016.10
requests-oauthlib==0.8.0

手順

  1. アプリを登録して、APIに必要なアクセストークン等を取得する(詳細は割愛)
  2. 全リストのIDを取得
  3. IDから完了タスクを取得
  4. 日付ごとに完了タスクをカウント
  5. matplotlibでグラフ化

コード

# coding:utf-8

import json
from requests_oauthlib import OAuth2Session
from dateutil import parser
from datetime import timedelta, datetime
import matplotlib.pyplot as plt
from pytz import timezone


class Wunderlist:
    def __init__(self):
        self.api = OAuth2Session()
        self.api.headers['X-Client-ID'] = 'your_client_id'
        self.api.headers['X-Access-Token'] = 'your_access_token'

    def fetch_list_id(self):
        req = self.api.get('https://a.wunderlist.com/api/v1/lists',
                           params={})

        if req.status_code != 200:
            print ('Error: %d' % req.status_code)
            return []

        lists = json.loads(req.text)
        id = [l['id'] for l in lists]
        return id

    def fetch_completed_at(self, id):
        req = self.api.get('https://a.wunderlist.com/api/v1/tasks',
                           params={'completed': 'true', 'list_id': id})

        if req.status_code != 200:
            print ("Error: %d" % req.status_code)
            return []

        tasks = json.loads(req.text)
        completed_at = [t['completed_at'] for t in tasks]
        return completed_at

    def fetch_completed_at_all(self):
        list_id = self.fetch_list_id()
        completed_at = []
        for id in list_id:
            completed_at.extend(self.fetch_completed_at(id))
        return completed_at


def make_complete_counts(completed_at, start_date, x):
    dates = [parser.parse(date).astimezone(timezone('Asia/Tokyo')).date() for date in completed_at]
    dates = [date for date in dates if date >= start_date]

    diff_dates = [(date - start_date).days for date in dates]

    result = [diff_dates.count(days) for days in x]
    return result


def make_date_ticks(start_date, x):
    dates = [(start_date + timedelta(days=var)).strftime('%m/%d') for var in x]
    return dates


def main():
    today = datetime.now(timezone('Asia/Tokyo')).date()
    start_date = today - timedelta(days=6)

    wunderlist = Wunderlist()
    completed_at = wunderlist.fetch_completed_at_all()

    x = range(7)
    y = make_complete_counts(completed_at, start_date, x)
    x_ticks = make_date_ticks(start_date, x)

    plt.xkcd()
    plt.bar(x, y)
    plt.xticks(x, x_ticks)
    plt.savefig('wunder_graph.png')


if __name__ == '__main__':
    main()

できました

wunder_graph

参考ページ