p-hone p-hone.info

Annict APIを活用し、見たアニメ一覧を出力する

アニメ好きな人と会話していると過去に見たアニメの思い出が話題にあがることがよくある。 そうなると大抵(あの時期は何見てたっけ?)と自分が過去に見たアニメの一覧が欲しくなる。

アニメの視聴を記録するにはAnnictというサービスが便利だ。 このサービスに記録しておけば「見たアニメ」というメニューから自分が見たアニメを列挙できる。

これは大変便利なのだが、少し不便な点がある。

よって過去視聴作品を一発ですべて一覧する、ということができない。 そこでAnnictの開発者向けAPIを利用して、プレーンテキストで、コンパクトに、TVシリーズのみ、見たアニメの一覧を出力するプログラムを書いた。

import os
from gql import gql, Client
from gql.transport.aiohttp import AIOHTTPTransport
from collections import defaultdict

SEASONS = ["WINTER", "SPRING", "SUMMER", "AUTUMN"]


class Annict:

    def __init__(self, api_key: str):
        transport = AIOHTTPTransport(url="https://api.annict.com/graphql", headers={
            "authorization": f"Bearer {api_key}"
        })
        self._client = Client(transport=transport, fetch_schema_from_transport=True)

    def list_watched_works(self):
        query = gql("""
query {
  viewer {
    libraryEntries(states: [WATCHED]) {
      nodes {
        work { title, seasonYear, seasonName, media }
      }
    }
  }
}
""")
        return [node["work"] for node in self._client.execute(query)["viewer"]["libraryEntries"]["nodes"]]


if __name__ == '__main__':
    api_key = os.getenv("ANNICT_API_KEY", None)
    if api_key is None:
        raise RuntimeError("env: ANNICT_API_KEY is missing")
    annict = Annict(api_key)
    works = annict.list_watched_works()

    works_by_season = defaultdict(lambda: defaultdict(list))
    for work in works:
        works_by_season[work["seasonYear"]][work["seasonName"]].append(work)
    for year in sorted(works_by_season.keys()):
        for season in SEASONS:
            works = [work for work in works_by_season[year][season] if work["media"] == "TV"]
            if len(works) > 0:
                print(f"## {year} {season}")
                print()
                for work in works:
                    print(f" * {work['title']}")
                print()

自身のアカウントで試したい場合は以下の手順で実行できる。

これを @p__hone のアカウントで実行した結果は次のようになる。 プレーンテキスト(Markdown)形式なので表示領域的にもファイルサイズ的にもコンパクトで、持ち運びも容易。コピーすればすぐに共有できて扱いやすい1

https://hackmd.io/@9OkUVY44Q2OwZRA88mLyFA/Syk_ip3P5

Annictは個人で開発されているサービスだが、2014年からずっと続いていてすごい。 個人でサービスを作ろうとした経験を持つプログラマーならよくわかると思うが、個人サービスを外部公開して正常に動く状態で何年も運用するというのは(技術的にも、やる気的にも)めちゃくちゃ難しいので本当に偉業だと思っている。

その上に開発者フレンドリーなAPIまで用意してくれているのが素晴らしくて、Annictを応援したい!という気持ちが高まったので少し前にAnnictサポーターに登録した。 お世話になっているサービスに支援できる…つまりpixiv FANBOXのような仕組みが開発者に対してもできるというのは面白いな〜と感じた。

脚注

  1. プレーンテキストを好んでいるのは『達人プログラマー』 という本に強く影響されたからです