LoginSignup
1
1

More than 3 years have passed since last update.

初心者でも無料でSplatoon2の戦績をstat.inkに定期投稿できるdisocrd bot

Posted at

はじめに

PC初心者でも、スマホしかない人でも、stat.inkにSplatoonの戦績を自動アップロードするdiscord botを作れるようにしたいなというのが、基本的な考えです。

とりあえず無料でstat.inkに戦績を投稿するDiscord Botを作りたい・使いたいという人は、準備方法や使い方についてはGitHub RepositoryのREADMEに詳しく書いたので、そちらをご確認ください。

この記事ではHerokuで稼働するDiscord Botについて工夫した点をお話します。

作成するdiscord botの機能

  • splatnet2stat.pyを利用してstat.inkに複数アカウントの戦績を自動アップロードする。
  • discord botを起動後にbotの機能だけでiksm_sessionの取得(自動アップロードの準備)ができる
  • bot起動準備を含めてスマホだけですべての作業が完結できる (PCを使える方が便利とはいえ)

問題点と解決策

Herokuではファイル作成・書き込みに制限があります。

  • 一時ファイル作成用の/tmpにしかファイルを作成できない。(※もともとのファイルは/app以下に入っている。)
    • さらに/tmpの中も一定時間(最大24時間)ごとにリセットされる。
  • つまりBot起動後に生成されるファイルを継続的に保存できる場所はない

これに付随する問題は2点あります。

iksm_sessionの保存場所

discord botを起動後にbotの機能だけでiksm_sessionの取得(自動アップロードの準備)ができる

上の機能の仕様上、iksm_session(厳密にはconfig.txtの中身)はbotをherokuで実行した後に取得されます。
それらのデータを永遠に保存しておくために、今回はHerokuの環境変数を利用しました。

Herokuの環境変数はHeroku管理画面から設定できますが、HerokuのREST APIからも更新できます。つまりHerokuで実行されているBot内から環境変数に出力し、データを継続的に保存することが可能です。
-> 詳しくはPlatform API Reference #config-vars-update

app_name=os.getenv("HEROKU_APP_NAME", "app-splat") #HEROKU_APP_NAME
if app_name=="":
    print("環境変数のHEROKU_APP_NAMEが定義されていません。")
    return
patch_url = f"https://api.heroku.com/apps/{app_name}/config-vars"
headers= {"Authorization": f"Bearer {os.getenv('HEROKU_APIKEY')}",
    "Content-Type":"application/json",
    "Accept":"application/vnd.heroku+json; version=3"}
res=requests.patch(patch_url, headers=headers, json=new_envs)

環境変数更新後にdynoは一度再起動されます。
また、注意点としてHerokuの環境変数は合計で32KBまでしか利用できません。

戦績アップロード実行時のconfig.txtの位置

splatnet2statink.pyはiksm_sessionなどが記されたconfig.txtが同じディレクトリに置かれていることを想定されています。
そのままですが、config_pathを書き換えます。

なお、localでの実験も想定して、環境変数はHerokuでデフォルトで設定されるos.getenv("DYNO")の有無で使い分けます。

splatnet2statink
## splatnet2statink/iksm.py
config_path="/tmp/config.txt" if os.getenv("DYNO", False) else f"{os.path.dirname(__file__)}/../tmp/config.txt"
## splatnet2statink/splatnet2statink.py
config_path=iksm.config_path

他の問題点として以下があります。

なぜかjson.loads()がstringになる

これは別記事に書きました。-> HerokuでPythonのjson.loads()がstrを返す問題
stringにならない場合もあるので、今はtypeの判別を挟んでいます。

Heroku
loaded_tmp=json.loads(dumped_string)
loaded_dict=eval(loaded_tmp) if (loaded_tmp)==str else loaded_tmp

GitHub Repository

1
1
3

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
1
1