こんにちは
弊社は2019/03/13東証マザーズへ上場しました。
社員の中には、自社が市場でどう思われてるか気になる人もいたりするもんです。
というわけで、Slackへその日の株価(始値/高値/安値/終値)をお知らせしています。
構成
平日19時前にビルドを実行してSlackへ通知しています。
当初はLambda(Python)で通知していたのですが、どのライブラリもうまく動かず、終値を手動で通知していました。
検証してみるとRのquantmodというパッケージであれば当日の株価も取得できることが判明。
というわけでCodeBuildにて、Dockerコンテナを動かし、Rのスクリプトを実行して通知することにしました。
ナゼCodeBuildか?
ところで、なぜCodeBuildなのかというと。。。
DockerなのでFargateでもいいのですが、VPC内起動するがパブリックIPがつかない!なのでNAT Gatewayが必要になりますが、1日1回SlackへPOSTするだけなのにNAT Gatewayはコスパが悪いので却下。うそです、つけれます。
AutoScalingが便利になったECSでええやんと、検証しましたがEC2インスタンスの1台 → 0台のスケールインがうまくいかない(絶賛検証中)。
Lambdaのカスタムランタイムはやったことがないので却下。
というわけでCodeBuildになりました。
Dockerなので後々ECS/Fargateへの移行もできちゃいます。
スクリプト
用意してCodeCommitへpushしたファイルは以下の3つのみ。これらをCodeCommitのリポジトリにプッシュしておきます。
- buildspec.yml
- Dockerfile
- stock-price.R
1つずつみていきましょう。
buildspec.yml
CodeBuild のカスタム Docker イメージのサンプルちょっといじっただけです。
version: 0.2
phases:
install:
runtime-versions:
docker: 18
pre_build:
commands:
- docker build -t stock-price .
build:
commands:
- docker images
- docker run stock-price echo "Success post to slack"
Dockerfile
ksmn/stock-baseというイメージをあらかじめ作成し、Docker hubへpushしておきました。このイメージには必要なライブラリはインストール済み、Rのパッケージはquantmod, XML, httr, 後々なにかに使えるのでは?とforecastも、もちろんその他依存関係のあるパッケージもインストール済みです。
事前に用意したのはRのパッケージインストールのときにコンパイル等で時間がかかるためです。
FROM ksmn/stock-base
COPY stock-price.R /usr/local/src/
WORKDIR /usr/local/src/
ENTRYPOINT ["Rscript", "stock-price.R"]
stock-price.R
Dockerfile内でENTRYPOINTに指定してるstock-price.Rはこんな感じ。当日と前日の株価を取得し(1日だけとろうとするとエラーになる)、当日のもののみincoming webhookでSlackチャンネルへPOSTします。URLとチャンネル名べた書きなのはご愛敬。
library(httr)
library(quantmod)
today <- Sys.Date()
day <- weekdays(today)
if (day == "Monday") {
yesterday <- today - 3
} else {
yesterday <- today -1
}
today <- as.character(today)
yesterday <- as.character(yesterday)
getSymbols("4434",src="yahooj",from=yesterday, to=today)
data <- YJ4434[2,1:4]
text <- c("今日もお疲れ様です\n本日の株価をお知らせします\n始値: ", "\n高値: ", "\n安値: ", "\n終値: ")
text <- paste(text, data, collapse="")
text <- enc2utf8(text)
url <- "incoming webhookのURL"
channel <- "#Slackチャンネル名"
POST(url=url, body=list(channel=channel, text=text), encode="json")
CodeBuild
まあ大した設定はしてないですが、1つだけ注意点が。
Dockerイメージをビルドする場合は特権付与をTureにしないといけません。
結果
CodeBuildがCloudWatch Eventで発火すると以下のように投稿されます。以下の画像は2020/01/24のものです。
まとめ
いかがしたでしょうか。CodeBuildはCIツールというイメージが強いかもしれませんが、結構いろんなことができちゃうもんです。私もCodeBuildの利用は初めてでしたが設定も簡単なので、これからどんどん使っていこうと思います。
Yusuke Mine(書いた記事を見る)
I get drunk but it's not enough 'Cause the morning comes and you're not my baby.