splatnet2statink.py でスプラトゥーン2の試合結果を stat.ink へ自動送信しようの巻【転載】

オリジナルのサイトにアクセスできなくなっていたので、キャッシュからの転載です

イカのために WiiU を買い、イカのために Switch を買ったエンジョイナワバリ勢 Aqraf です。(本ブログ2回目)
前回はGUIが用意されたわかりやすいやつだったけど、スプラトゥーン遊ぶたびにパソコン立ち上げてソフト動かさなきゃだし、外で遊ぶならずっとパソコン起動しっぱなしかよ!ってなるので、じゃあサーバー用意してやってやるかーってのか今回紹介する Python スクリプトです。
2017/09/03 追記: git stash pop したら config.txt が CONFLICT したので対処方法を付け加えました。
2017/09/13 追記: config.txt 周りの説明を変えました。
2017/09/18 追記: API周りの変更のせいで “Invalid token.” エラーが出る問題の対策として mitmproxy の使い方を付け加えました。
なお、9月15日以前に取得した iksm_session は有効期限が無いようで、そのまま使えます。

概要

splatnet2statink.py
はスプラトゥーン2の試合結果を任天堂のイカリング2から取得して stat.ink
に送信してくれる、UNIX 系サーバーで動く Python スクリプトです。
今回は自宅の Mastodon インスタンスと同居させたいので、Ubuntu 16.04 で動かしてみます。

用意するもの

・Nintendo Switch と Splatoon2
・自分の Windows/Mac パソコン
・自宅かモバイルルーター等の Wi-Fi 環境
・Nintendo Switch Online アプリが入った iPhone/Android 端末
・Ubuntu 16.04 以降が入ったサーバー

まってサーバーって?

このスクリプトはサーバーで動かすやつなので、持ってないひとはクラウドサーバーを借りましょう。
おすすめはこのブログのサーバーとしても使ってる清楚かわいい ConoHaのVPS
です。
1ヶ月630円〜でブログ建てたりマイクラサーバー作ったりと色々できるのでお勉強にぜひどうぞ。
サーバーの建て方は他のブログの記事なりを参考にしてください。OS は Ubuntu 16.04  (64bit) を使ってみましょう。
黒い画面に文字打つなんてそんなの無理やわーってひとは Mac と Windows 対応の SquidTracks (前回の記事) をどうぞー

環境をつくる

git と python 2.7 と pip が使える環境が必要らしいので、いい感じにインストールしていきます。
git のインストールはこの記事が参考になります。(丸投げ)
UbuntuにGitをインストールする
python はOSにはじめからインストールされているようです。バージョン確認は大文字で -V を付けます。
$ python -V
Python 2.7.12
pip が入ってるか確認します
$ pip --version
The program 'pip' is currently not installed. You can install it by typing:
sudo apt install python-pip
バージョンが返ってこないので apt-get してインストールします。
$ sudo apt-get install python-pip
...
Do you want to continue? [Y/n] Y
インストールするか聞かれるので Y を入力してエンターします。
終わったらもう一度バージョンを確認してみます。
$ pip --version
pip 9.0.1 from /usr/lib/python2.7/dist-packages (python 2.7)

ライブラリのインストール

動作に必要なライブラリをインストールしていきます。
requests っていうのを入れます。自分の環境ではすでに入っていたようです。
$ pip install requests
Requirement already satisfied: requests in /usr/lib/python2.7/dist-packages
msgpack-python を入れます。
そのままの権限でやると Permission denied されてしまったので、sudo つけて実行します。
$ sudo pip install msgpack-python
...
Successfully installed msgpack-python-0.4.8
パーミッションとかいろいろ確認してーって黄色い文字が出るかもしれませんが、とりあえず気にせず。
Succcess って出たらOKです。

splatnet2statink のインストール

スクリプト本体を GitHub から引っ張ってきます。
場所はホームディレクトリの下に置いてみます。
$ cd
$ git clone https://github.com/frozenpandaman/splatnet2statink.git
Cloning into 'splatnet2statink'...
remote: Counting objects: 453, done.
remote: Compressing objects: 100% (54/54), done.
remote: Total 453 (delta 42), reused 55 (delta 22), pack-reused 377
Receiving objects: 100% (453/453), 341.77 KiB | 0 bytes/s, done.
Resolving deltas: 100% (264/264), done.
ホームディレクトリの下に splatnet2statink ディレクトリができました。以降はこの中で作業するので、移動しておきます。
$ cd splatnet2statink
/splatnet2statink$

はじめの設定

これでスクリプトを動かす準備ができました。
起動すると初期設定が始まります。早速動かしてみましょう。
$ python splatnet2statink.py
splatnet2statink v0.0.47
Generating new config file.
stat.ink API key:
stat.ink のAPIキーをコピペしてエンターします。https://stat.ink/profile
から取得できます。
APIキーは試合結果を送信するためのパスワードのようなものです。絶対に他人に教えたりSNSに投稿しないようにしてください。
次に言語設定です。初期のままだと英語になっていますので、日本語に直します。日本語は “ja-JP” と入力します。
Default locale is en-US. Press Enter to accept, or enter your own (see readme for list).
ja-JP
なおこの設定は試合結果を送信するときに必要なだけなので、この後のメッセージも普通に英語です
続いて任天堂のイカリング2から試合結果を取得するためニンテンドーアカウントにログインを求められます。下の太文字部分のURLをブラウザに貼り付けて移動してログインします。
Pulling data from online...
Blank cookie. Trying to generate one given your session_token...
session_token is blank. Please log in to your Nintendo Account to obtain your session_token.

Navigate to this URL in your browser: 
https://accounts.nintendo.com/connect/1.0.0/authorize?state=......login_form
Log in, right click the "Use this account" button, copy the link address, and paste it here:
ログインしたら「これにする」ボタンを押さずに右クリックしてリンクのアドレスをコピーします。
2017-09-02 16.49.01
コピーしたリンクをそのままシェルに貼り付けます。
Wrote session_token to config.txt.
Pulling data from online...
Blank cookie. Trying to generate one given your session_token...
Error from Nintendo:
{
 "status": 9403, 
 "errorMessage": "Invalid token.", 
 "correlationId": "29bfe1d7-56dcefc4"
}
_人人人人人人_
> 突然の死 <
 ̄Y^Y^Y^Y^Y ̄
※2017/09/18 現在
ここで任天堂からあるデータを取得しようとして失敗し、エラーでスクリプトが終了してしまいます。
ここでは iksm_session と呼ばれる、任天堂に保存された自分の戦歴データ等にアクセスするために必要なパスワードのようなものを発行してもらうのですが、最近この仕組みが変更されたようで、このスクリプト含め大半のアプリ、ソフトで取得できなくなってしまい使い物にならなくなってしまいました。SquadTracks もダメなようです。
今回は、スマホの Nintendo Switch Online アプリが正規に取得した iksm_session をある方法を使って取得して流用します。

MITM (man-in-the-middle attack : 中間者攻撃) とは

いきなり物騒なワードを出しましたが、ある方法とは、スマホアプリと任天堂との通信を傍受(ぼうじゅ)して iksm_session を盗み見してしまおう、というやつです。
本来見ることができない暗号化された通信内容を盗み見するというわけですから、これは立派な中間者攻撃ということになります。が、傍受しているのは自分の通信なので、特に罪に問われるわけではありません。
でもやり方次第でいろんなことができるので、悪用厳禁でお願いしますね。

mitmproxy のダウンロード

自分のパソコンで動くプロキシソフトを導入します。
これを使うと、スマホとネットの間にパソコンを挟んで通信内容を見ることができます。
Windows/Mac/Linux に対応しています。ここでは Windows 版で話をすすめます。
↓ここから最新版をダウンロードします。
https://github.com/mitmproxy/mitmproxy/releases
今回は単体で動かせるやつを使います。ファイル名の末尾が「~windows.zip」ってやつです。installer じゃないですよ。
デスクトップ等、好きな場所にダウンロードしたら解凍しておきます。

mitmproxy の起動

mitmweb.exe を起動します。
初回起動時はファイアウォールの警告画面が出てくるので、「アクセスを許可する」してください。
黒い画面と、色々できるブラウザ画面が自動で起動します。

IPアドレスをしらべる

パソコンのIPアドレスを調べます。
「Winキー」+「R」同時押しして「cmd」と打ち込み OK を押してコマンドプロンプトを立ち上げます。
「ipconfig」と打ち込みエンターします。
IPv4アドレス… の右側にある 192.168.11.13 みたいなやつが、そのパソコンのIPアドレスです。メモに控えておきます。

スマホのプロキシ設定

スマホ側のプロキシ設定をします。
ネットへの通信をパソコン経由にするための設定です。
Android は、設定 → Wi-Fi → 接続済みの自宅Wi-Fi名を長押し → ネットワークを変更 → 詳細設定項目 右横の矢印 → プロキシ なしを手動に変更 → プロキシのホスト名に控えておいたIPアドレスを入力 → プロキシポートは「8080」を入力 → 保存する
iPhone は、設定 → Wi-Fi → 左横にチェックマークがついているWi-Fi名の右横にある青い i マークを押す → 一番下の HTTPプロキシ を手動にする → サーバに控えておいたIPアドレスを入力 → ポートは「8080」 → 認証はオフ → 左上<Wi-Fi で戻る
バージョンによって表示内容が違ったりする場合があるので、似たような設定を探してやってみてください。それでもわからんときは「Android プロキシ 設定」みたいな感じでググってください(丸投げ)

スマホへCA証明書を入れる

スマホに証明書をインストールします。
暗号化された通信を読むので、スマホを騙すためのニセの証明書をインストールしていきます。
スマホのブラウザで http://mitm.it/ にアクセスします。頑張って手打ちして。
iPhone のひとは Safari ブラウザでアクセスしてください。
iPhone のひとはりんごを、Android のひとはドロイド君をタップして、証明書をインストールします。
iPhone でのインストールの際、「”証明書信頼設定”で有効にするまで、この証明書はWebサイト用には信頼されません」みたなことを途中で言われたら、インストールしたあと、設定 → 一般 → 情報 → 証明書信頼設定 に mitmproxy が追加されているのでオンにします。

Nintendo Switch Online アプリでイカリング2へアクセス

これで、すべての通信がパソコンで傍受できるようになりました。
Nintendo Switch Online アプリを開いて、イカリング2へアクセスしてみましょう。ログインしていないひとはログインしてください。
実は、イカリング2へアクセスする瞬間、あの iksm_session データが任天堂とやり取りされています。パソコンに戻ってブラウザで開かれている mitmproxy を見てみましょう。

mitmproxy で iksm_session を盗み見する

Cookie (クッキー) のところに、
 iksm_session=ef01......f77d; ...
みたいなやつがありますが、太字で囲んだ部分が iksm_session です。
めちゃめちゃ大事なデータなので、SNSとかにアップしたり他人に教えないよう気をつけてください。このデータはこのあとコピペします。

splatnet2statink サーバーに戻って config.txt を編集

スクリプトの設定ファイルを編集します。
テキストエディタを起動します。
$ nano config.txt
カーソルキーで cookie まで移動して、”と”の間に iksm_session データをコピペします。こんな感じになればOKです。
{
 "api_key": "9C7r......aBoQ",
 "cookie": "ef01......f77d",
 "session_token": "eyJh......iYXV"
 "user_lang": "ja-JP"
}
「Ctrl」+「O」同時押ししてエンターして上書き保存します。
「Ctrl」+「X」でエディタを終了します。

splatnet2statink 起動確認

ではスクリプトを動かしてみましょう。
$ python splatnet2statink.py
splatnet2statink v0.0.47
Pulling data from online...
Number of recent battles to upload (0-50)?
ここまで表示されれば設定完了です!
リアルタイム送信オプション -M を付けずに起動したので、過去何試合分送信するか聞かれています。ここではとりあえず 0 と打ってエンターして、スクリプトを終了させます。

さあレッツイカゲー!

では最後に -M オプションを付けて起動しましょう。リアルタイムで監視して自動送信してくれるモードです。
$ python splatnet2statink.py -M
splatnet2statink v0.0.47
Waiting for new battles... (checking every 5 minutes)
Press Ctrl+C to exit. 294
5分毎にイカリング2へ新しい試合結果がないか確認してくれます。
新しい結果が見つかると、自動的にスクショとデータを stat.ink に送信してくれます。めっちゃ便利。
最近のバージョンでは過去のバトルで送信していないものを自動で送信してくれる機能がついたみたいです。こんな感じで表示され、次々送信されていきます。
Previously-unuploaded battles detected. Uploading now...
ではでは実際に遊んでみるぞい!
New battle result detected at 1:44:52 PM!
Battle #1 uploaded to https://stat.ink/@Aqraf/spl2/54271
Press Ctrl+C to exit. 294
こんな感じで表示されたらOK!めでたく自動送信してくれました。
あとはこのままほったらかしにしておけば全部やってくれます。自らの試合結果を研究して次なる一手を打て!

splatnet2statink のアップデート

splatnet2statink は開発途中なのでバグフィクスやあたらしいブキやステージが追加されたりして頻繁にアップデートされています。
というわけで、git を使ってアップデートしてみます。
まずはスクリプトを終了させます。Ctrl + C で終了できます。
新しいアップデートがあるか確認します。
$ git fetch
ここでずらずらっとなにか出てきたらアップデートがあります。何も出来なければここでおわりです。
あたらしいアップデートを引っ張ってきます。
$ git pull
差分が自動で書き換えられます。これでアップデート完了です。

イカとサーバーであそぼう

外で遊んでいても勝手に送信してくれるのほんと強いので、ますますイカライフが充実するんだよな!開発してくれたひとに感謝です!
これをきっかけにサーバーをいじるようになったりしたらもっとうれしいです
????
これより下は9月4日より古いバージョンの話になりました。
うまくいかなかったときの参考にどうぞ。

もし次のようなエラーが出てきたら、もう少しやることがあります。
$ git stash pop
CONFLICT (modify/delete): config.txt deleted in Updated upstream and modified in Stashed changes. Version Stashed changes of config.txt left in tree.

CONFLICT したら

コンフリクトとはざっくりいうと、引っ張ってきた (pull) ファイル群といまサーバーにあるファイルが噛み合ってないよ、同期できてないぞ、というエラーです。
原因を調べるため、今の状態を見てみます。
$ git status
On branch master
Your branch is up-to-date with 'origin/master'.
Unmerged paths:
 (use "git reset HEAD <file>..." to unstage)
 (use "git add/rm <file>..." as appropriate to mark resolution)

 deleted by us: config.txt

no changes added to commit (use "git add" and/or "git commit -a")
どうやら「新しいバーションには最初から config.txt は無いぞ!捨てるか?残すか?」って言っているようです。
でもスクリプトを動かすと config.txt が生成されるみたいで結局は必要なファイルなので、以前の config.txt を活かします。
このファイル残すことにするよってコマンドを打ちます。
$ git add config.txt
これでもう一度今の状態を見てみます。
$ git status
On branch master
Your branch is up-to-date with 'origin/master'.
Changes to be committed:
 (use "git reset HEAD <file>..." to unstage)

 new file: config.txt
「config.txt 残すんやな、ええで。」って感じになりました(雑)
とりあえずこれで動かせます。

よくわからんことになったら

全部消すってのありなので(自分もよくやる)消し方も書いておきます。
$ cd
$ sudo rm -r splatnet2statink
これでディレクトリごときれいさっぱりです。また clone して設定してみましょ。

“splatnet2statink.py でスプラトゥーン2の試合結果を stat.ink へ自動送信しようの巻【転載】” への1件のコメント

コメントを残す

メールアドレスが公開されることはありません。