スト5の勝敗数、LPを自動取得、更新するシステムを作ってみた Ver. 2021/4/2

1. インストール環境と解説

まずはメインのスクリプトのソースね。コメントとかもすげー適当版。

#!/usr/bin/perl

use strict;
use warnings;
use utf8;
use LWP::UserAgent;

my $agent_text = "Mozilla/5.0 (Linux; Android 6.0; Nexus 5 Build/MRA58N) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/88.0.4324.192 Mobile Safari/537.36";
my $default_fid = "TnT8801";
my $cookie_file = "/var/tmp/sfv-cookie.txt";
my $result_file = "/var/tmp/sfv-result.txt";
my $fuel_csrf_token;
my $scirid;
my $next_fuel_csrf_token = "";
my $next_scirid = "";
my $lp = "";
my $wins = "";
my $losses = "";
my $last_wins = "";
my $last_losses = "";
my $lp_flag = 0;
my $wins_flag = 0;
my $losses_flag = 0;

# Fighter's ID
my $fid = $default_fid;
if (defined $ARGV[0] && $ARGV[0] ne "") {
 $fid = $ARGV[0];
}
my $url = 'https://game.capcom.com/cfn/sfv/profile/'.$fid;

# Cookie file read
open(COOKIE_READ, "<".$cookie_file) or die("Error:$!");
while(my $line = <COOKIE_READ>){
 chomp($line);
 my($key,$value) = split(/:/,$line);
 if ( $key eq "scirid" ) {
   $scirid = $value;
 }
 if ( $key eq "fuel_csrf_token" ) {
   $fuel_csrf_token = $value;
 }
}
close COOKIE_READ;

# Result file read
open(READ, "<".$result_file) or die("Error:$!");
while(my $line = <READ>){
 chomp($line);
 my($key,$value) = split(/:/,$line);
 $value =~ s/\s+//g;
 if ( $key eq "Wins") {
   $last_wins = $value;
 }
 if ( $key eq "Losses") {
   $last_losses = $value;
 }
}
close READ;

# Create a user agent object
my $ua = LWP::UserAgent->new;
my $res = $ua->get(
 $url,
 "User-Agent" => $agent_text,
 "Cookie" => "language=ja; afc2021=1; notification_ja=%7B%22133144%22%3A0%2C%22133142%22%3A0%2C%22133140%22%3A0%2C%22133138%22%3A0%2C%22133137%22%3A0%2C%22133135%22%3A0%2C%22133132%22%3A0%2C%22133130%22%3A0%2C%22133129%22%3A0%2C%22133124%22%3A0%7D; fuel_csrf_token=".$fuel_csrf_token."; scirid=".$scirid."; path=/cfn/sfv/; secure",
);

# Check the outcome of the response
if (!$res->is_success) {
 print $res->status_line, "\n";
 exit 1;
}

my $cookie = $res->header('set-cookie');
my @cookies = split(/;/,$cookie);
foreach my $line (@cookies) {
 if ($line =~ /fuel_csrf_token=(.+)/) {
   $next_fuel_csrf_token = $1;
 }
 if ($line =~ /scirid=(.+)/) {
   $next_scirid = $1;
 }
}
if ($next_fuel_csrf_token ne "" && $next_scirid ne "") {
 open(COOKIE_WRITE, ">".$cookie_file) or die("Error:$!");
 print COOKIE_WRITE "fuel_csrf_token:".$next_fuel_csrf_token."\n";
 print COOKIE_WRITE "scirid:".$next_scirid."\n";
 close COOKIE_WRITE;
}

# Contents check
my @content = split(/\n/,$res->content);
foreach my $line (@content) {
 # LP check
 if ($lp eq "" && !$lp_flag && $line =~ /<dt>League Points<\/dt>/) {
   $lp_flag = 1;
 }
 if ($lp eq "" && $lp_flag && $line =~ /<dd>(\d+)<span>LP/) {
   $lp = $1;
   $lp_flag = 0;
 }
 # Wins check
 if ($wins eq "" && !$wins_flag && $line =~ /<dt>Wins<\/dt>/) {
   $wins_flag = 1;
 }
 if ($wins eq "" && $wins_flag && $line =~ /<dd>(\d+)<\/dd>/) {
   $wins = $1;
   $wins_flag = 0;
 }
 # Losses check
 if ($losses eq "" && !$losses_flag && $line =~ /<dt>Losses<\/dt>/) {
   $losses_flag = 1;
 }
 if ($losses eq "" && $losses_flag && $line =~ /<dd>(\d+)<\/dd>/) {
   $losses = $1;
   $losses_flag = 0;
 }
}

# Wins and Losses check
if ($wins eq "" || $losses eq "") {
 print "Wins or Losses count is not get from contents.\n";
 exit 1;
}

# Result file write
$wins = int($wins);
$losses = int($losses);
$last_wins = int($last_wins);
$last_losses = int($last_losses);
if ($wins > $last_wins || $losses > $last_losses) {
 open(WRITE, ">".$result_file) or die("Error:$!");
 print WRITE "LP: ".$lp."\n";
 print WRITE "Wins: ".$wins."\n";
 print WRITE "Losses: ".$losses."\n";
 close WRITE;
}

LinuxのPerlが動く環境なら、多分大丈夫。

概念図は以下

図1

で、ここから環境準備。
/var/tmp/sfv-result.txtに、今のLPと勝敗数を保存

LP: 8686
Wins: 9140
Losses: 8811

同様にクッキー情報を2つの変数だけchromeからコピペ
保存ファイルは/var/tmp/sfv-cookie.txt

fuel_csrf_token:b4f4fscirid:uHdXwWZbm8

って感じ。

必要なモジュール、PROXY(squid)のインストール方法は以下。
わかんなかったらググって…

dnf install perl-libwww-perl perl-LWP-Protocol-https squid

って感じ。Redhat8系のコマンドだけど、わかるよね?
squidは、この環境下ではacl allow allにして、firewalldでポートの穴を開けて、AWSのセキュリティグループで制限をかけた。

あ、ちゃんと動いたら、crontabにしかけてね。俺は/etc/crontab派。

*/2 * * * * root /usr/local/bin/sfv-check.pl

2. PCからCookieを取り出す方法について

同じサーバにsquidを建てて、そいつをPROXY使用したPCでシャドルー研究所にアクセス。ブラウザのCookie情報を持ってくる。

スクリーンショット 2021-03-08 21.53.11

URLの左のところをクリックするとCookie情報が取れるから、探してみて。

AWSにPROXYを建てるって危険だから、セキュリティグループで自分の家のIPだけを許すようにしておかないとね。Cookieの用事が済んだら穴を塞いで、squidのサービスも落としておいて。ここだけ要注意

念の為。ここだけ要注意!
念の為。ここだけ要注意!
念の為。ここだけ要注意!

こんだけ注意したら大丈夫かな。

3. Cookieって何やってるの?

これは認証とか認可とかわからないと理解できないかも。

とりあえず、ログインしたってのがsciridって変数。シングルサインオンの認可済みってやつ。
前回のトークンがfuel_csrf_token。このトークンは、アクセスしたhttpのレスポンスヘッダに最新が入って来るから、次回のhttpアクセス時にまた最新のトークンを使うって感じ。

4. このシステムって、結局、何やってるの?

俗に言うスクレイピング。シャドルー研究所で表示されるHTMLから適当に文字列取得してるだけ。

スクレイピングって、ブラウザアクセスをロボットにやらせて、必要情報を定期的に取得するってテクニック。

興味があったら「スクレイピング Cookie」とかで検索してみて。

5. このページに書いてる技術的な情報が意味不明だったら

うーん、基本的にググっては欲しいんだけど。
もしどうしても詰まるようなら、Twitterの@TnT8801にDMとかで聞いてみて。暇だったら返事できると思う。

6. 既知の問題

ゲームをしばらくしてないと/var/tmp/sfv-result.txtが消えるかも。ってか消えるはず。/var/tmpだが問題ってだけだし、場所を変えればOK。

あと、Twitterで指摘されたけど、Fighter's IDがソース固定で書かれてる。
ここは第一引数で指定できるし、適宜書き換えてくれればいいけど、複数IDの情報が取りたくなったら呼び出し元とかで工夫して欲しいかも。

7. 次の構想

/var/tmp/sfv-result.txtをDBに格納してグラフ化したいね。

実は、3/9の午前中にはMySQLにINSERT/SELECTするように変更した。でもPerlでDBアクセスなんてもう情報が溢れててドヤれないwwww

いいなと思ったら応援しよう!