LoginSignup
13
10

More than 3 years have passed since last update.

はじめてのISUCON7

Last updated at Posted at 2019-07-13

ISUCONの過去問で毎回毎回セットアップをするのはめんどくさいのでまとめてみた。ISUCONは初心者なので色々わかり次第追記していく。

参考: https://github.com/isucon/isucon7-qualify

AMIを自前で準備


# ubuntu@16.04 LSTで作成 sshでログイン

# nginxとmysql(RootUserで実行)
sudo su
apt-get update
apt-get install mysql-server nginx # Password設定するの勧めてくるけど全部OK

# Apllicationを設定
sudo adduser isucon
gpasswd -a isucon sudo
sudo su - isucon
cd ~
git clone https://github.com/isucon/isucon7-qualify.git isubata

# xbuild関連をInstall
sudo apt install -y git curl libreadline-dev pkg-config autoconf automake build-essential libmysqlclient-dev libssl-dev python3 python3-dev python3-venv openjdk-8-jdk-headless libxml2-dev libcurl4-openssl-dev libxslt1-dev re2c bison libbz2-dev libreadline-dev libssl-dev gettext libgettextpo-dev libicu-dev libmhash-dev libmcrypt-dev libgd-dev libtidy-dev
git clone https://github.com/tagomoris/xbuild.git

# GolangのインストールとPath設定
mkdir local
xbuild/go-install -f 1.9 /home/isucon/local/go

mkdir go
echo 'export GOROOT=/home/isucon/local/go' >> ~/.bashrc
echo 'export GOPATH=/home/isucon/go' >> ~/.bashrc
echo 'export PATH=/home/isucon/local/go/bin:$PATH' >> ~/.bashrc
echo 'export PATH=/home/isucon/go/bin:$PATH' >> ~/.bashrc
source ~/.bashrc

# ベンチマーカーのBuild
go get github.com/constabulary/gb/...
cd /home/isucon/isubata/bench
gb vendor restore
make

# 初期データを準備
cd /home/isucon/isubata/bench
./bin/gen-initial-dataset

# DBのセットアップ
sudo /home/isucon/isubata/db/init.sh
sudo mysql
# mysqlの内部
CREATE USER isucon@'%' IDENTIFIED BY 'isucon';
GRANT ALL on *.* TO isucon@'%';
CREATE USER isucon@'localhost' IDENTIFIED BY 'isucon';
GRANT ALL on *.* TO isucon@'localhost';
exit;

# データの投入
zcat /home/isucon/isubata/bench/isucon7q-initial-dataset.sql.gz | sudo mysql isubata

# nginx設定
sudo cp /home/isucon/isubata/files/app/nginx.* /etc/nginx/sites-available
cd /etc/nginx/sites-enabled
sudo unlink default
sudo ln -s ../sites-available/nginx.conf
sudo systemctl restart nginx

# ApplicationのBuildと設定
sudo cp /home/isucon/isubata/files/app/*.service /etc/systemd/system
sudo vim /home/isucon/isubata/files/app/env.sh #DBのHostをlocalhostに書き換える
sudo cp /home/isucon/isubata/files/app/env.sh /home/isucon/
cd /home/isucon/isubata/webapp/go
make

sudo systemctl enable isubata.golang
sudo systemctl enable nginx

セットアップ

初期設定

SSH設定
メンバーの分のSSHを設定する。
/home/isucon/.ssh/authorized_keys にPublicKeyを追記。

pbcopy < ~/.ssh/id_rsa.pub
mkdir /home/isucon/.ssh
touch /home/isucon/.ssh/authorized_keys
echo '[PUBLIC_KEY]' >> /home/isucon/.ssh/authorized_keys

Processの確認


ps auxwf # | grep Nginx

Github
GithubにPrivate Repositoryを作成してPushしておく。ついでにDeployスクリプトも作成しておく。


cd /home/isucon/isubata
rm -fr .git
git init
git add .
git commit -m "first commit"
git remote add origin [git repository]
git push -u origin master
deploy.sh

# ブランチを最新に
git checkout master
git fetch
git pull origin master


# build
cd /home/isucon/isubata/webapp/go
make

# confファイルと環境変数を更新
cp /home/isucon/isubata/files/app/env.sh /home/isucon/
cp /home/isucon/isubata/files/app/nginx.* /etc/nginx/sites-available
cp /home/isucon/isubata/files/db/mysqld.cnf /etc/mysql/my.cnf

#/home/isucon/isubata/files/db/mysqld.cnfのlog_slow_queriesは間違いなので気をつける。
# 参考: https://dev.mysql.com/doc/refman/5.6/ja/server-system-variables.html

# ログを削除
rm -fr /var/log/nginx/access.log
rm -fr /var/log/mysql/access.log

# Restart
systemctl restart mysql
systemctl restart nginx
systemctl restart isubata.golang

chmod 777 /home/isucon/isubata/deploy.sh
/home/isucon/isubata/deploy.sh

監視系ツール

ボトルネックを特定するために必須。全ての参加者が導入していると思われるので、サクッとやりたい。大きく分けて3種類。

CPリソース監視系
CPU, RAMなどの使用量を監視するもの。

htop


sudo apt-get install htop

Nginx監視系
Nginxなどのログを監視する。特定のPathに対して負荷がかかってい他場合の特定に役に立つ。

alp

/etc/nginx/site-enabled/nginx.conf

# nginx設定のLog設定
log_format ltsv "time:$time_local"
                "\thost:$remote_addr"
                "\tforwardedfor:$http_x_forwarded_for"
                "\treq:$request"
                "\tstatus:$status"
                "\tmethod:$request_method"
                "\turi:$request_uri"
                "\tsize:$body_bytes_sent"
                "\treferer:$http_referer"
                "\tua:$http_user_agent"
                "\treqtime:$request_time"
                "\tcache:$upstream_http_x_cache"
                "\truntime:$upstream_http_x_runtime"
                "\tapptime:$upstream_response_time"
                "\tvhost:$host";

access_log  /var/log/nginx/access.log  ltsv;

wget https://github.com/tkuchiki/alp/releases/download/v0.3.1/alp_linux_amd64.zip
apt install unzip
unzip alp_linux_amd64.zip

mv alp /usr/local/bin/
alp -f /var/log/nginx/access.log

Application監視系
pt-query-digest

参考: https://www.percona.com/doc/percona-toolkit/LATEST/pt-query-digest.html


wget https://www.percona.com/downloads/percona-toolkit/3.0.13/binary/debian/xenial/x86_64/percona-toolkit_3.0.13-1.xenial_amd64.deb
sudo dpkg -i percona-toolkit_3.0.13-1.xenial_amd64.deb
sudo dpkg -s pt-query-digest
# Pattern1
tcpdump -s 65535 -x -nn -q -tttt -i any -c 10000 port 3306 > mysql.tcp.txt
pt-query-digest --type tcpdump mysql.tcp.txt >> query-report.txt

# Pattern2
mysql
# mysqlの内部
SHOW VARIABLES;
SET GLOBAL slow_query_log_file='/var/log/mysql/access.log';
SET GLOBAL slow_query_log=1;
SET GLOBAL log-queries-not-using-indexes=1;
exit;
pt-query-digest --type genlog /var/log/mysql/access.log
mysqld.conf

slow_query_log_file     = /var/log/mysql/mysql-slow.log
slow_query_log
# long_query_time = 2
log-queries-not-using-indexes

pprof

import (
  _ "net/http/pprof"
  "net/http"
)

func main() {
  // DefaultはCPU計測
  go http.ListenAndServe(":3000", nil)
  ...
}
sudo apt-get install graphviz gv
# ./bin/main = 実行ファイル cpu.pprof = pprofファイル
go tool pprof -png ./bin/main cpu.pprof > out.png

ISUCONでやれそうなこと

ブログなどの情報を見ながらこれなら自分にもできそうと思ったものをまとめてみる。

N+1問題
基本形。どれだけ早く特定できるかが鍵。見つけるだけでなく、多く叩かれているところを優先的に潰す。重いQueryなども発見して潰せるようなら潰していきたい。

DB周り
Index(複合Indexまで視野に入れて)などを貼ってみる。

Nginx設定
静的ファイルをCacheするなど。他にもConnectionsやWorkerの数を増やすなど。色々いじれる。

Redis導入/オンメモリ化
重いQueryなどをメモリに載せたい。

複数台構成
Nginxをロードバランサーとして用いて複数台構成にする。複数にすることで発生する問題もあるので行う場合には慎重にやりたい。

DBの非正規化
これも多少ハードルが高い。時間の短いisuconであれば、難しいかも。サマーインターンのもので時間があるものであれば試そうかと思う。

参考

ISUCON7 予選
https://blog.bitjourney.com/entry/2017/11/09/101740

13
10
0

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
13
10