読者です 読者をやめる 読者になる 読者になる

mackerelで室温を監視して、お部屋をいい感じの温度にキープする

ライフハック

前回の記事ではSiri + Raspberry Pi + IRKitで
お部屋の家電を操作するところまで作りました。

takanamito.hateblo.jp

今回は、その続編として
室温を計測し、規定の温度を外れた場合に自動でエアコンを操作して
お部屋の温度を快適に保つ方法を実践していきます。

先日、会社の勉強会で発表した際に使った資料がこちら

この発表で「エアコンの自動設定に任せられないのか」「そもそも目指す温度に設定しておけばいいんじゃないのか」という意見がありましたが

  • うちのエアコンに温度の「自動」設定がなかった
  • そもそも実家でも学校でも「自動」で快適な温度になったことがない
  • 温度上げる時はさっさと上げたい
  • なんかたまに謎判定でエアコンサボるからめっちゃ寒かったりする

みたいな理由から今回の自作温度調節機能の開発がスタートしました。

お金がある人は最新モデルの霧ヶ峰とかを買うといいかもしれません。

システム構成

前回までに登場した

  • Raspberry Pi
    • homebridge
    • homebridge-irkit
  • IRKit (API付き学習リモコン)
  • エアコン

に加えて、ラズパイにUSB温度計のTemperを接続します。
接続する際は、本体に直接挿すと熱伝導でUSBスティック自体が熱くなるため
延長ケーブルなどで本体の熱が伝わらないように接続するのがコツです。

USB温度計! USB thermometer-528018

USB温度計! USB thermometer-528018

また、設置する位置が高かったり低かったり、当たり前ですが熱を放つ機械のそばにあるだけで計測結果が変わります。
自分の体感値と照らし合わせながら最適な設置場所を探してみてください。

我が家ではこれを「百葉箱ポジション」と呼んでいます。

室温自動調節の仕組み

  • Temperで温度を取得
  • ラズパイで稼働中のmackerel-agent経由で温度をメトリクス化
  • Alert設定で10分継続してしきい値を上回る/下回る温度が続いた場合Alert発火
  • ラズパイから定期的にmackerelのAlert APIを叩いてCRITICAL状態の場合はエアコンの設定温度を操作

f:id:takanamito:20170212002428p:plain:w300

こんな流れです。
発表スライドにも載っているのですが、開発中はmackerelを使わずに
毎分温度を取得して、低ければ設定温度を上げるようにしていたのですが
室温はすぐに上がらないため、ラズパイが温度を上げようとして
毎分エアコンの「ピッ」という音を聞かされることになりました。

また部屋がちょうどいい温度にもかかわらず
トイレに行くために一瞬だけ廊下へのドアを開けただけで冷気が入り込み
その冷気を拾ってラズパイが過剰に反応してしまうこともありました。

そこでmackerelを使って「○○分継続して温度が規定値を外れたら」という
webの外形監視っぽい仕組みを導入することで回避しています。

温度を取得

ラズパイにTemperを接続して温度を取得します。
商品にwindows用のインストーラーがついていますが、ラズパイ用にコマンドをビルドします。

【Raspberry Pi】USB温度計を付けてみる – Happy Life Hacking

mackerelに投げる

mackerel-agentもgithubにarm版が公開されています。

Releases · mackerelio/mackerel-agent · GitHub

この中から mackerel-agent_linux_arm.tar.gzをDLし、展開して利用します。

mackerel-agentのARM版バイナリーはRaspberry PI 2でもさくっと動く - Qiita

temperから取得できる温度を整形してmackerelに渡すためのスクリプトを用意

#!/bin/bash

name="temper"
monitor_time=`date +%s`
temperature=`/opt/temper/temper | sed -e 's/.*,\(.*\)/\1/'`
echo -e "${name}\t${temperature}\t${monitor_time}"

mackerelの設定ファイルに上のスクリプトを叩くように追記してagentを再起動

[plugin.metrics.process]
command="sudo /home/pi/temper.sh"
type="metric"

Monitorを設定

ここまでの手順でmackerelにメトリクスが表示されるようになったと思います。 f:id:takanamito:20170211232917p:plain

Monitorの設定画面から

  • 温度上限
  • 温度下限

の設定をしたMonitorを作成しましょう。
我が家では 上限 23℃, 下限 21℃で、10分間既定値を外れた場合にAlertを発火するようにしています。

f:id:takanamito:20170211233807p:plain

Alertを監視するスクリプトを用意

mackerelのmonitorがalert状態になったのを取得する必要があります。
今回は手軽にやりたかったので「cronで15分おきにAlert APIを叩く」という方法で確認を行っています。

アラート - Mackerel API ドキュメント (v0)

雑スクリプトで取得して、IRKitにリクエストを送ります。

#!/bin/bash

cd `dirname $0`

check_alerts () {
  curl https://mackerel.io/api/v0/alerts -H 'X-Api-Key:xxxxx' -H 'Content-Type: application/json' | jq '.alerts[]'
}

# 自動調節モードのOn/Offを確認
if [ ! -e /tmp/check.txt ]; then
  echo 'Auto control is off'
  exit 0
fi

JSON=`check_alerts`

ID=`echo $JSON | jq '.monitorId'`
STATUS=`echo $JSON | jq '.status'`
echo $ID
echo $STATUS

if [ $STATUS = '"CRITICAL"' ]; then
  echo `date`
  echo 'Status is CRITICAL'

  if [ $ID = '"xxxxx"' ]; then # 上限アラート
    sh ./22.sh
    sleep 1
    sh ./21.sh
  elif [ $ID = '"xxxxx"' ]; then # 下限アラート
    sh ./22.sh
    sleep 1
    sh ./23.sh
  else
    echo 'Unknown Alerts'
  fi
else
  echo `date`
  echo 'Status is not CRITICAL'
fi

やっていることは単純で

  • Alert APIを叩いてjqでjsonをみる
  • ステータスがCRITICALかつ
    • 上限Monitorのidと一致すれば
    • 下限Monitorのidと一致すれば
    • ※各MonitorのidはmackerelのMonitor画面URLに付与されています
  • IRKitにHTTPリクエストを送るスクリプトを実行
    • ※今回はそれぞれ2℃ずつ変更すべくスクリプトを実行しています

また序盤で「自動調節モードのOn/Offを確認」とコメントがありますが
ファイルの有無を自動調節モードの起動フラグとして利用しているだけです。

このファイルの作成/削除はhomebridge-cmdで管理しているため
「Hey Siri エアコン調節オン」みたいに声で自動調節モードを起動できるところがちょっとかっこよくて気に入ってます。

結果

f:id:takanamito:20170211235420p:plain

ある日のグラフです

  • 20:00ごろ 帰宅
    • エアコンを起動
    • 自動調節モードもON
    • 既に21℃を下回っているためalert状態
  • 数分後
    • alert状態がわかりラズパイが自動的に設定温度をアップ
  • 20:30すぎ
    • 20℃を突破
  • 22:00前
    • 今度は上限のAlertに引っかかる
    • ラズパイが設定温度を下げる

という挙動で、その後いい感じに温度がキープできているのがわかるかと思います。
この日、ぼくは普通に暮らしており、温度に関することを一切意識していません。

このように、考えないといけないことが1つ減らせたのがとてもうれしいです。
今後はスマートコンセントを使って、加湿器も制御して湿度をコントロールできればと思っています。

今度からは、霧ヶ峰を買って解決できるようになりたいです。

「Hey Siri 電気つけて!」でRaspberry PiとIRKitを経由して電気をオンオフ

ライフハック

ベッドでだらだらしていると、だんだんウトウトしてくる。

あーもうこのまま意識飛んで寝そう。っていう時に、電気とテレビを消すために
わざわざテーブルに置いてあるリモコンを取りに行きたくない。


「Hey Siri 電気つけて!」で電気をつけたり消したり

続編としてエアコンの温度調整を自動化するところまでやりました。

takanamito.hateblo.jp

システム構成

  • iPhone7
    • Siri
    • HomeKit
  • Raspberry Pi
    • homebridge
    • homebridge-irkit
  • IRKit (API付き学習リモコン)
  • 家電製品
    • 照明
    • テレビ
    • エアコン

この中でも今回の要はhomebridge

homebridge

github.com

github.com

homebridge-irkitをラズパイで動かします。
このサーバーはHomeKit互換なため、設定ファイルにjsonで各家電の赤外線情報を定義することで
IRKitにHTTPリクエストを飛ばして、家電製品に赤外線信号を送ることができる。

{
    "bridge": {
        "name": "Homebridge",
        "username": "CC:22:3D:ED:CE:30",
        "port": 51826,
        "pin": "000-00-000"
    },
    "description": "IRKit Control",
    "accessories": [
        {
            "accessory": "IRKit",
            "name": "電気",
            "irkit_host": "IRKit1B4D.local",
            "on_form": {"format":"raw","freq":38,"data":[19991,10047,1413,3579,1413,3579,1413,3579,1413,1111,1413,1111,1413,3579,1413,3579,1413,3579,1413,1111,1413,1111,1413,3579,1413,3579,1413,1111,1413,1111,1413,1111,1413,1111,1413,3579,1413,3579,1413,1111,1413,1111,1413,3579,1413,1111,1413,1111,1413,3579,1413,1111,1413,1111,1413,3579,1413,3579,1413,1111,1413,3579,1413,3579,1413,1111,1413]},
            "off_form": {"format":"raw","freq":38,"data":[19991,10047,1319,3704,1319,3704,1319,3704,1319,1190,1366,1190,1366,3704,1319,3704,1319,3704,1319,1190,1319,1190,1319,3704,1319,3704,1319,1190,1319,1190,1319,1190,1319,1190,1319,3704,1319,3704,1319,1190,1319,3704,1319,1190,1319,1190,1319,1190,1319,3704,1319,1190,1319,1190,1319,3704,1366,1150,1319,3704,1319,3704,1319,3704,1319,1190,1319,65535,0,24574,19991,4878,1366]}        
        }
    ]
}

またIRKitに以下のHTTPリクエストを送ることで
1番最後に受信した赤外線情報をjsonで吐き出してくれます。

$ curl -i "http://10.0.1.2/messages" -H "X-Requested-With: curl"
HTTP/1.0 200 OK
Access-Control-Allow-Origin: *
Server: IRKit/2.1.3.13.gbe33d36
Content-Type: text/plain

{"format":"raw","freq":38,"data":[18031,8755,1190,1190,1190,3341,1190,3341,1190,3341,1190,1190,1190,3341,1190,3341,1190,3341,1190,3341,1190,3341,1190,3341,1190,1190,1190,1190,1190,1190,1190,1190,1190,3341,1190,3341,1190,1190,1190,3341,1190,1190,1190,1190,1190,1190,1190,1190,1190,1190,1190,1190,1190,1190,1190,1190,1190,3341,1190,3341,1190,3341,1190,3341,1190,3341,1190,65535,0,9379,18031,4400,1190]}

IRKit - Open Source WiFi Connected Infrared Remote Controller

必要な家電製品の赤外線を設定ファイルに書いたら
homebridgeサーバーを起動

pi@raspberrypi:~ $ homebridge
*** WARNING *** The program 'node' uses the Apple Bonjour compatibility layer of Avahi.
*** WARNING *** Please fix your application to use the native API of Avahi!
*** WARNING *** For more information see <http://0pointer.de/avahi-compat?s=libdns_sd&e=node>
*** WARNING *** The program 'node' called 'DNSServiceRegister()' which is not supported (or only supported partially) in the Apple Bonjour compatibility layer of Avahi.
*** WARNING *** Please fix your application to use the native API of Avahi!
*** WARNING *** For more information see <http://0pointer.de/avahi-compat?s=libdns_sd&e=node&f=DNSServiceRegister>
[2017-02-08 23:42:24] Loaded plugin: homebridge-cmd
[2017-02-08 23:42:24] Registering accessory 'homebridge-cmd.CMD'
[2017-02-08 23:42:24] ---
[2017-02-08 23:42:24] Loaded plugin: homebridge-irkit
[2017-02-08 23:42:24] Registering accessory 'homebridge-irkit.IRKit'
[2017-02-08 23:42:24] ---
[2017-02-08 23:42:24] Loaded config.json with 7 accessories and 0 platforms.
[2017-02-08 23:42:24] ---
[2017-02-08 23:42:24] Loading 7 accessories...
[2017-02-08 23:42:24] [テレビ] Initializing IRKit accessory...
[2017-02-08 23:42:24] [電気] Initializing IRKit accessory...
[2017-02-08 23:42:24] [エアコン] Initializing IRKit accessory...
Scan this code with your HomeKit App on your iOS device to pair with Homebridge:

    ┌────────────┐
    │000-00-000 │
    └────────────┘

あとはiPhoneのホームアプリから接続設定をすると
HomeKit経由で各種デバイスのオンオフが可能。

Siriだけじゃなく、コントロールキットからも操作できて便利

f:id:takanamito:20170211221233p:plain:w300

参考URL

datahotel.io

ラズパイ3はけっこうメモリも豊富でよかった
常時起動の場合はヒートシンク要るとか聞いてたけど、今のとこなんとかなってる
冬だからかも?

青色LEDがちょっとまぶしいのが難点
後継機のNature Remoはちょっと値上がりして、動体センサーや湿度計もついてるらしい

AWSにVPNでつないでSteam Home StreamingでAstroneerをやりたい

AWS 日常

前回の記事で、手元にWindowsがなくてもAWS環境にWindowsマシンを用意し
リモートデスクトップを利用してAstroneerをプレイする方法を紹介しました。

takanamito.hateblo.jp

しかし、記事の最後にも書いてあるように
ドラッグが効かなかったりと、通常プレイにも支障が出てしまう状態でした。

今回はそれをクリアし快適にプレイすることができたので、その方法を書こうと思います。

きっかけ

前回の記事を投稿したところ知人からTwitterで
「Steam Home Streaming」なるものの存在を教えてもらいました。

Steam ホームストリーミング

LAN内にあるマシンでリモートプレイできる仕組みのようです。

今回はこれを利用してプレイしたいので
Mac - WindowsをVPNで接続してSteam Home Streamingが使える環境をつくります。

ちなみに前回紹介した海外の先駆者が公開している動画で、実際にどれくらいサクサクにプレイできるかが確認できます。

これだけなめらかに動けばAstroneerは余裕なはずです。


EC2 Steam streaming

手順

  • 前回の記事を参考にリモートデスクトップでAstroneerがプレイできる環境を用意する
  • WindowsサーバーにOpenVPNをインストールして設定
  • MacにTunnelblick(VPNクライアント)をインストールして設定
  • VPN接続
  • Steam Home Streamingの設定
  • Astroneerをやる

※VPN環境の構築をしていきます。試される方は自己責任でお願いします。

OpenVPNの設定

今回1番難しい作業です。Mac - Windows間のVPN環境を構築します。
基本的には前回紹介した海外の先駆者の記事に記載の8番の工程を進めます。

まずはWindows

  • OpenVPNのインストーラーをDL「Installer (64-bit), Windows Vista and later」 https://openvpn.net/index.php/open-source/downloads.html
  • インストーラーを起動し「select to install all components」を選択してあとはデフォルト設定でインストール
  • コマンドプロンプトを起動し、初期設定とVPNで使う各種鍵を生成する。詳細は上述の記事を参考に。
  • リモートサーバー用の設定ファイルを C:\Program Files\OpenVPN\config配下に置く。 設定サンプルはこちら
  • コントロールパネル -> システムとセキュリティ -> Windowsファイアウォール -> Windowsファイアウォールによるアプリケーションの許可 からOpenVPNの通信を許可する
  • OpenVPN GUIを起動し、右下のタスクバーから「接続」を選択

Windows側の手順はここまで
今回、上述の記事を参考にOpenVPN設定を試みたが、記事内で公開されている設定ファイルをどこまで信用していいかわからなかったので自分で読んで、一部設定を変更した。
ただVPN設定自体が初めての経験だったので、ほんとにこれが正しい設定なのかは自信がない。危ない設定あれば指摘ください。

また拡張子表示設定をしていなかったため、編集後の server.ovpnファイルが実は server.ovpn.txtになっており、OpenVPNが設定ファイルを読み込んでくれないなど
非常にしょうもないハマり方をしたので、拡張子表示設定を先にやっとくとよさそうです。

つづいてMac

  • Windowsから ca.crt, client.crt, client.keyの3つのファイルをダウンロードし、ローカルに置いておく
  • クライアント用の設定ファイルを鍵を置いたディレクトリに配置。設定サンプルはこちら 5行目にWindowsサーバーのIPを埋める
  • TunnelblickをDL
  • 起動後、先程のcliend.ovpnファイルを読み込ませて接続

この設定でVPN接続が可能なはず。
Windows側に接続されたっぽいログが表示されていれば成功。

AWSのセキュリティグループを変更し、自宅などのIPからUDPのアクセスを通す設定をお忘れなく。

Steam Home Streamingの設定

Steamアプリからホームストリーミングの設定をします
ハードウェアエンコードに関する設定をONにしてください。

f:id:takanamito:20161224120645p:plain

この段階でMacとWindows双方の「ストリーミングを有効にする」チェックボックスがONになっていれば
上の欄にリモートサーバーが表示されているはずです。

表示されない場合は、チェックボックスのON/OFFを試すと表示されることが多かったです。

Astroneerをやる

MacのSteamからAstroneerを見てみると「プレイ」ボタンがあるはずの場所に「ストリーミング」ボタンが表示されているはずです。
これをクリックすれば、、、プレイ可能かと思いきや「画面はリモートコンピュータ上からロックされています」というエラーメッセージが表示され起動できません。

これはwindowsログインができておらず、ロックされていることが原因です。手軽に突破するにはChromeリモートデスクトップなどを利用しログインした状態をつくるのがおすすめ。
またログインするためには ctrl + alt + delete を要求されますが、Macからは ctrl + option + fn + deleteあたりで突破できたはずです。

その状態で「ストリーミングを」クリックすれば、、、

f:id:takanamito:20161224122601p:plain

ちょっと画質は悪いかも。でもサクサク動く。

f:id:takanamito:20161224121723p:plain

車とか作ると原付を手に入れた高校生くらい一気に移動範囲が広がる。

f:id:takanamito:20161224121728p:plain

「おおー。できてきたできてきた。」とか思って時計を見ると深夜3時になってたりして危険。

そのうち農業要素が追加されるらしいので、砂とうんこを混ぜた畑でジャガイモを育てたいです。

オデッセイ(字幕版)

オデッセイ(字幕版)

AstroneerがやりたくてAWS EC2でWindowsマシンを立ててリモートデスクトップでプレイ

AWS ライフハック

「Astroneer」がやりたかった。

ただ、うちには動作条件を満たすWindowsマシンがなくて困った。

ゲームはそんなに長く続かないタチなので100時間もやらないはず。
そのためにわざわざ何万も払ってWindowsマシンを買いたくもないし、大掃除でせっかく空けた家のスペースも使いたくない。

諦めきれずに同僚にslackでAstroneerやりたいと話していたら
「AWSでWindows使えばいいじゃん」と言われた。

その発想はなかった。

調べてみると、海外に同じ事をしている人がいた。

意を決して作業を始めると、1時間くらいでAstroneerがプレイできる環境が手に入った。
今回はパフォーマンスそっちのけで、とりあえず動かせるところまで。

※2016/12/24追記
より快適にプレイするためのVPN導入 takanamito.hateblo.jp

環境

手元にはMacしかない
Macbook 12インチ Early 2016 (macOS Sierra)

手順

  • EC2インスタンスの起動
  • Microsoft Remote Desktopでつなぐ
  • グラフィックボードのドライバを更新する
  • オーディオドライバをインストール
  • Steamをインストール
  • Astroneerをインストール

※破産の可能性があるので自己責任でお願いします

EC2インスタンスの起動

AWSマネジメントコンソールからEC2を起動します。
今回使うAMIは「Microsoft Windows Server 2012 R2 Base」
※最新のWindows Server 2016がありますが、あとでインストールするドライバの関係で2012じゃないと動きません

  • AMI: Microsoft Windows Server 2012 R2 Base
  • インスタンスサイズ: g2.2xlarge
  • ストレージ: EBS gp2 100GB
  • セキュリティグループ: 3389番(RDP)のみ開放(リモートデスクトップで使用

※2016/12/23追記 同僚から「Windows Server 2012 R2 with the NVIDIA Driver」のAMIを使ったほうが ドライバのインストールが楽になるとの情報を教えてもらいました。

Microsoft Remote Desktopでつなぐ

EC2インスタンスが起動しステータスチェックが通ったら、下記の手順を実行しパスワードを入手します。

docs.aws.amazon.com

次にMicrosoft Remote DesktopをDLし接続設定をします

Microsoft Remote Desktop

Microsoft Remote Desktop

  • Microsoft Corporation
  • ビジネス
  • 無料

  • Connection name: お好きに
  • PC name: EC2のIPアドレス
  • User name: Administrator
  • Password: さっき取得したやつ
  • Start session in full screenのチェックを入れる
  • Use all monitorsのチェックははずした方がいい

これで接続できるはず。
ここからは普通にWindows触るときと同じ感覚で操作可能

ただしセキュリティ設定が厳しくて、IEでいろんなサイトにアクセスするときに
「このドメインを信用しますか?」的なダイアログがひたすら出続けるのでその辺は僕はポチポチして回避しました。
もっといい方法があれば教えてください。

グラフィックボードのドライバを更新する

リモートデスクトップでログインしたら、グラフィックボード NVIDIA GRID K520用のドライバを更新します。

NVIDIA DRIVERS Quadro Desktop Driver Release 367 WHQL

※ちなみにWindows Server 2016を使っていると、ここで古いバージョンのドライバしか入らず
ゲーム起動時にエラーで強制終了されてしまいました。

デバイスマネージャからデフォルトのドライバである「Microsoft Basic Display Adapter」をオフにしたあとにアンインストール さらにドライバのファイル自体も削除しておくとよい模様。C:\Windows\System32\Drivers\BasicDisplay.sys
僕は権限を与えることができずに削除失敗しました。

オーディオドライバをインストール

オーディオドライバは入ってなかったぽいのでインストール

Razer Surround Personalized 7.1 Gaming Audio Software - Razer United States

これで右下のタスクバー?のボーリュームアイコンのバツ印が消えて
手元のMacから音が聞けるようになるはず

必要であれば言語設定も変更して
この辺で一度再起動しておくとよさそう。

Steamをインストール

あとはいつもどおり、Steamをインストールしたのちに
Astroneerをインストールすれば、、、

f:id:takanamito:20161220130231p:plain f:id:takanamito:20161220130237p:plain

コスト

今回使ったのが

  • CPU: 8コア
  • メモリ: 15GB
  • GPU: NVIDIA GRID K520

のg2.2xlargeインスタンス

東京リージョンで動かしても$1.01 / 1 時間

このスペックのパーツを買い揃えることを考えると 100時間やったとしても1万円強で、ものすごいコスパ

低レイテンシーを求められるゲームならまだしも、今のAstroneerのように
1人でのんびりとやるぶんには全く問題ない感じ。

所感

今の環境では完全互換とはいかず、なぜかマウスのドラッグアクションが効かずに
掃除機みたいなやつで吸うアクションがうまくできない。
この辺は別のリモートデスクトップクライアントも使って検証してみる予定。

公式ForumでもMac対応するってQ&Aに書いているので、気長に待ちます。

What about Mac users?
Eventually Astroneer will be supported on Mac. Not confirmed if it will be supported at Early Access launch yet though.

(Read First) Astroneer FAQ :: ASTRONEER General Discussions

2016年お買い物ランキング

日常

2016年によかったものを12個書きます

takanamito.hateblo.jp

12位 IPPO

IPPO 1 (ヤングジャンプコミックス)

IPPO 1 (ヤングジャンプコミックス)

会社の同僚からおすすめされて買ってみたマンガ。
若手ビスポーク革靴職人の話でとにかく職人最高という気分になれる。
インターネットのサービス作るのもいいけど、やっぱり実際に手に取れるものもつくりたいですわな。

11位ヨーグルティア

こちらも同僚のすすめで購入。
ヨーグルトを無限に食べたいので、せっせと作っている。
最近はドリンクタイプのR-1を使うと美味しくできるということを発見。
牛乳パックを直接セットするタイプよりも、温度設定やタイマー設定があるので使いやすい。
低温調理器としても活躍していて、よく鶏ハムをつくる。
生ギリギリを攻めたほうが美味しいので毎回ドキドキしながら仕上がりを見るのもまた楽しい。

10位 ガメラ 大怪獣空中決戦 4K上映(トークショー付き)

hobby.dengeki.com

豊洲であったイベント上映。
4K上映自体は去年の東京国際映画祭でも見てたけど、今回はトークショー付きということで仕事をさっさと切り上げて通った。
何より良かったのは長峰役の中山忍さんを見られたことで、自分の年だと明らかに浮くような高めの年齢層の観客みなが
中山忍登場で"息を呑む"瞬間を体感できたのがよかった。
女優すごい。別格に綺麗でした。

9位 赤めだか

赤めだか (扶桑社BOOKS文庫)

赤めだか (扶桑社BOOKS文庫)

この記事に影響されて読み始めた。 今どきの若手育成にひそむ3つの思いこみ

おかげで初めて落語の寄席にも行ったり、なかなかいいおでかけトリガーになったと思う。 スライドにも引用されている箇所はしっかり意識して実践してる。

8位 SCYE x URBANRESEARCH ダッフルコート

2016AW SCYE x URBAN RESEARCHの名作ダッフルコート - 社会人3年目の服選び

大学のときにHAREで買ったダッフルコートをずっと着てたけど
もうちょっといいやつを着たかったので後輩に譲って新しいのを買うことにした。
Scyeのダッフルコートは名作とのことで、たまたまURBANRESEARCHの別注モデルで黒があったので購入。
形は綺麗だし、肉厚で温かいのでとても気に入っている。

7位 nginx実践入門

nginx実践入門 (WEB+DB PRESS plus)

nginx実践入門 (WEB+DB PRESS plus)

普段の仕事でも使いまくってるnginx
前からちょくちょく触ることはあったけど、行きあたりばったりな設定ファイルを作ってしまうことが多いので
ここらでちゃんと知識入れとくかと購入。

今でも机に置いて、リファレンス的な使い方をしています。

6位 キャプテン・アメリカ シビルウォー

今までマーベルシリーズではキャプテンのウインターソルジャーが1番好きだったのが、さらにそれを上回ってくる感じで最高。
2016年における映画の才能を全て集めて映画撮ったらこれができました!
みたいな感覚すら覚える。
猛ダッシュバッキー追跡シーンと、スパイダーマンがAT-ATぐるぐる巻きのことしゃべり出すシーンが最強。

5位 iPhone7

Apple Pay最高。
もう財布をリュックから出さなくていい。 ただ防水が信用できないところはちょっとやだ。

takanamito.hateblo.jp

4位 星野源 Live Tour "YELLOW VOYAGE" (初回限定盤) <Blu-ray>

Live Tour “YELLOW VOYAGE" title="Live Tour “YELLOW VOYAGE" (初回限定盤) ">

Live Tour “YELLOW VOYAGE" (初回限定盤)

逃げ恥の恋ダンスもいいけど、スーダラ節の弾き語りとかニセ明さんの君は薔薇より美しいもいい。
DOWN TOWN 〜 ステップにつなぐところのドラムがババちびるくらいかっこいい。

3位 東京国際映画祭 アメイジング・スパイダーマン2 野外上映

2016.tiff-jp.net

毎年、東京に住んでてよかったと思えるイベントのひとつ。
ヒルズでアメスパ2が野外上映するとのことで行ってみると
SONYの謎巨大4Kディスプレイに、でかスピーカーが準備されてて非常に高まる。

12月の極寒の中観る、ガーフィールドとエマ・ストーンの公園再会シーンは最高だし
映像自体Ultra 4Kとかいう規格のものを流していたらしく、エレクトロの電流をかいくぐって街をぎゅんぎゅん行くシーンがとんでもないことになっていた。

どなたがチョイスしているのかわかりませんが、本当にありがとうございました。

2位 nasne

nasne 1TBモデル (CUHJ-15004)

nasne 1TBモデル (CUHJ-15004)

死ぬほどテレビを観るので、今まで買わなかったことを後悔した。
torneアプリを使ったリモート操作/視聴が神で、友達や家族に「この企画おもしろかった」って言いながらさっと録画を見せられるのが最高。
あとこの機能のおかげで会社で同僚と日本シリーズ見れたりして非常に満足度の高い買い物でした。

1位 ALDEN 990

初めて新品の高級靴を買いました。
値段が値段なのでお手入れの方法も勉強したり、リテラシーを引き上げるきっかけになった一足。10年履きたい。

合わせて買った本もすごくよかった。

靴磨きの本

靴磨きの本

この靴を履くときは、朝の段階で天気予報を死ぬほどチェックする。

この靴を買ったおかげで、あまり知り合わないような人とも仲良くなれた。 もっとこういう話ができる人たちと会ってみたい。

お金使うの気持ちいいですね。 来年もたくさん散財したい。

ちょこっとサーバーを立てたいときのTerraformの構成を考える

AWS

この記事は、「Speee Advent Calendar 2016」の5日目です。
4日目は、id:nisshieeより、「Turbolinks再考」です。

今日は、Terraformの構成について再度考えたいと思います。


先日書いたブログで、hashcorpが公開しているTerraformのbest-practiseについて読み解きました。

takanamito.hateblo.jp

ブコメでもいくつかあった「つらそう」という意見
つらさにも種類があるとは思うのですが
僕が実際にベストプラクティスを読んでいて思ったのは

  • モジュールが2階層構造になっており、抽象化されたモジュールを読み解くのがしんどい
  • モジュール単位で変数定義が必要なため、3回変数宣言をしなければならないのがめんどくさい

という2点。

ただこれも、多くのリソースを抽象化して管理したり、ファイルの肥大化を防ぐ意味では有用であろうという結論を出していました。

実際にはオーバースペックだった

いざ使ってみると、仕事である程度の規模のインフラを管理する場合には役立つこのベストプラクティスも
個人で数台のインスタンスを立てて、とりあえずwebサービスが動く構成にするには
少しオーバーだなと感じることが多かったのです。

そもそも、Terraformを使ってAWSのインフラ管理を楽にしたいと思って導入しているのに

  • まずは必要なリソースをmoduleに切り出して
  • 変数定義をmoduleの数だけ書いて
  • terraform getやplanで動作の確認をして

と、ちょこっとインスタンスを立ち上げるだけの作業が非常に大きくなっていき
結果Terraformの準備に時間がかかる本末転倒な結果になってしまいました。

例えばマイクロな構成でEC2インスタンスだけ立てるならブラウザでポチポチやればいいじゃん。とも思ったのですが

運用するサービスが分かれている場合、最低限ネットワークは分離したかったりするので EC2 1台立てるのに必要な VPC, subnet, route table, gateway...etcを考えるとやはりTerraformを使ってコマンド1発で構築したい。

軽量Terraformテンプレートを製作

そこで

  • hashcorpのベストプラクティスほど大きくなく
  • ありがちな構成を整えた

Terraformのテンプレートを作り始めました。

github.com

構成はこのような感じ

├── micro
│   ├── micro.tf
│   └── terraform.tfvars
└── modules
    ├── compute
    │   └── ec2
    │       └── ec2.tf
    └── network
        ├── route_table
        │   └── route_table.tf
        ├── security_group
        │   └── security_group.tf
        ├── subnet
        │   └── subnet.tf
        └── vpc
            └── vpc.tf

このテンプレートで生成可能なのは「80番ポートだけ空いた、インターネットに疎通可能な1台のEC2インスタンス」です。
各リソースを操作可能なIAMユーザーを用意して、EC2用のキーペアだけ作成しておけばコマンド一発で立ち上がります。

読み始める場合は /micro/micro.tfからスタートし、各moduleをのぞいてもらえるとわかりやすいと思います。
※これからいくつも構成のテンプレートを用意しようと思っているので、最小構成の意味でmicroと命名しています。

この構成の利点は

  • 階層が減ることで各moduleの見通しが良くなる
  • 変数定義の回数を減らせる (micro.tfと各moduleの2回)

の2点です。

ベストプラクティスでは存在したcomputeモジュールなどの、1段階リソースを抽象化したモジュールを廃止し、直接リソースを定義したモジュールに変数を渡すことで 構成を1階層減らしました。
これによって構成がシンプルになり、小規模な環境を準備する際のコストが減らせるかと思います。

またベストプラクティスに比べて、Terraform初心者に読んでもらうときにも非常に優しくなっていますね。

反面、この構成だとPRO/STG/DEVのような開発環境に分けてコードを記述することには対応させていないのですが
その場合はmicroディレクトリの下に環境ごとのディレクトリを作って、tfファイルとtfvarsファイルを置けば対応可能かと思います。

この先の展望

このリポジトリは「個人がAWSでWebサービスを始めるときに使えるよくある構成のテンプレート集」化していこうと思います。

仕事をしていても感じるのですが
Webサービスをつくるときに「絶対するであろう作業」が自動化されていないことで、各個人の時間が吸い取られていくので
これを解決することで、より価値提供のための開発に集中できるはずです。

まずはよくある構成を充実させて、そのうちコンテナを使った構成などにも対応できればと思っています。

入社して3年が経ちそうなので振り返り

日常

もうすぐ社会人になって丸3年。
いい機会なのでここまでやってきたことの棚卸しをしてみる。

1年目

同期より2ヶ月ほど早く入社し、いきなり新規サービスの立ち上げに参加させてもらった。
僕は2年目の先輩エンジニアの下について、ユーザーのコンテンツ投稿画面のフロントエンドを中心に開発をしていた。

このときAngularJSみたいなフレームワークの導入もできたのに「JSの勉強も兼ねてjQueryだけでやってみよっか」と大きなフレームワークなしで設計/実装にチャレンジさせてもらえたことにとても感謝している。
JSのオブジェクトや関数について理解を深めるきっかけになった。
この時期にJavaScriptパターンを読みまくっていた。

JavaScriptパターン ―優れたアプリケーションのための作法

JavaScriptパターン ―優れたアプリケーションのための作法

サーバーサイドもPHPJavaを使った基本的なwebサービス開発をしていて
学生時代には意識したことのなかったMySQLの基本的なクエリチューニング(といってもEXPLAIN程度のものだけど)も教わった。
ミドルウェアやインフラを意識した開発は初めてだったので新鮮なことが多くてすごく楽しかった記憶がある。

半年ほど経った9月頃には、チームを移ることになった。
次のチームでは海外向けメディアを扱っていて、僕は今に至るまでこのチームに在籍することになる。

1番最初のチームでは作業のほとんどがアプリケーション実装だったのに対し、今のチームではインフラ関連の作業をやることが多くなった。 少し責任範囲が広がった感じ。

当時、先輩が1人で6サイト運用しながら、さらに2サイトの新規開発をしていて 運用するだけで手一杯、アプリケーションにバグも埋もれていたりコードのコピペもあったりと直し放題の環境だったので 1チーム目のときに教わったことをそのままこのチームにも展開していった。

あげだすとキリがないけど
運用面ではJenkinsによる自動化やバッチ実行管理、リリースノートを含むドキュメントの整備、backlogで管理していたチケットの整理と、とにかく散らかってるものを全て整理していった。
アプリケーションに関してはまずコピペ脱却のために各種機能を役割ごとにクラスやモジュールに切り出していく作業をひたすらやっていた。またその過程で見つけた誰も知らないバグをひたすら潰してた。

チームメンバーが兼務だらけで、とにかく散らかっていて整理されてない状態だったことや
プロダクトマネージャーが(幸運なことに)裁量を与えて自由に動かせてくれるタイプの人だったことにより
開発/運用/その他もろもろのいろんな種類のタスクを自分で見つけ、優先順位をつけてつぶしていくコツをこの時期にかなり学べたと思う。

またミドルウェアを触る作業が増え、先輩からインフラ系作業を教わることができた。
MySQLのチューニングやLinuxカーネルチューニング、nginxの設定について勉強し始めたのがこの時期だった。
それ以来nginxが好きで、社内のQiita::Teamにnginxの設定に関する記事をよく書いていた。

また、この時期に勉強したことがISUCONでめちゃくちゃ役立っていて、教えてくれた先輩にはめちゃくちゃ感謝している。 takanamito.hateblo.jp

そういえば仕事をする上で相談することが苦手だった僕が下手なりに相談できるようになったのは、この時期にミドルウェアに関する相談をこの先輩が嫌がらず聞いてくれたおかげな気がする。

年が明けるころには大きなインフラ移設も行っていて
さくらVPSで動かしているメディアが成長していき、スケーラビリティと地理的な条件からAWSに移行することになった。

設計からサービス無停止での移行の実作業を1人でやることになった。
この作業はかなりきつくて、そもそもインフラはどうやって設計するものなのか、どう考えて組み立てていくのかなどなど
何がわからないのかもわからない状態だったと思う。
とにかく理解を深めるために、既存のインフラをAWS上で再現するために必要なリソースをリストアップして図に起こしていく作業をやっていた。

この時期にゼロからWebサービスを作る時に必要な

  • 自分の考える理想的な構成を描く
  • 現実的な条件をもとに松竹梅程度の選択肢に落とす
  • 選択肢のグラデーションの中から最適解を探す

みたいな考え方を学べた。

移行が終わってからは少し落ち着いたので、当時流行り始めていたリアクティブプログラミングの流れに乗ってriot.jsを触ってみたり
レコメンドエンジンに触れたりしていた。 takanamito.hateblo.jp

2年目

2年目はチームの開発サイドリーダーとなって、自分がメイン開発者としてサービス開発を進めることが多かった。 また会社がPHP, JavaからRubyScalaへ移行することになり、Railsでのアプリケーション開発の先陣を切ることになる。

全社的にテストの重要性を意識しはじめ、CircleCIの導入を始めたりとやっと少しナウみのある開発ができ始めた。
同時にmocha, chaiを使ったJSのテストも導入したりと、作ることに対しての余裕ができて
普段の開発に効果がありそうな、自分なりのプラスを取り入れることができるようになった気がする。

それまでどのチームもテストゼロ、誰が何を作ってるのかもわからないような状態だったので
この時の開発体制の大改革はとてもありがたかった。

チームの人数が増え始めたことで、イテレーション運用をより力を入れて回すことになり 開発スケジュール管理やディレクションに関して大きな時間を割いて関わることになる。

チームのエンジニアリーダーである自分が進捗管理をしつつ、ディレクションも手伝いつつ、自分でもアプリケーションを書いていたので
特にリリース間際の佳境に差し掛かった時期には仕事をする時間が増え、見事に腰を破壊された。

年末から年明けにかけてはFuelPHP -> Rails移行のプロジェクトもあり 数十万URLの301リダイレクト処理にビビりながらも特に大きな事故なく終えることができた。
このあたりから社内勉強会で話す機会を少し増やしたり、外の勉強会でLTをするようにした。 takanamito.hateblo.jp

3年目

2年目につくったサービスのトラフィックを伸ばすための改善、運用コストを下げるための施策を中心にやっている。

インフラ移設時に手動でコンソール画面をポチポチして立てていたAWSのインフラを TerraformとItamaeの導入を進めて自動化したり (Docker導入もやりたい) takanamito.hateblo.jp

A/Bテストをリリース速度重視で行うために
今まではmunin, nagiosでやっていた監視に加えて、Datadog, Sentryを使った監視や可視化の仕組みを導入したり

A/Bテストのためのログ解析要望も高まり、fluentdとelasticsearchを使ったログ蓄積基盤を作ってサービス改善のためのログを取り始めたり
その過程でけっこうメジャーなfluentdのプラグインやsunspotといったでかいgemにPR送ったりするOSSっぽいことも始めた。

効率化という文脈では、対象を自チームだけに絞らず
趣味で社内Gyazoサーバーを立てたり、サーバーレスHLS動画配信の仕組みを作ったりして
業務に関係ないことで新しい技術には触れるようにしている。(この取り組みが自分のチームに還元できるとうれしい) takanamito.hateblo.jp

所感

3年間webアプリケーション開発に関わってみて
新しい技術を学ぶのももちろんだけど、今ある環境や生活に非効率なものがないか見渡して
それを解決することが合っている気がしてきた。

  • nginx
  • S3, Lambdaなどのいわゆるサーバーレス系サービス
  • HLS

あたりの技術が自分の中ではしばらくホットで、全部に共通しているのが
「自分の実現したいことが楽に実現できる」ということ。

すごく頑張っていいコードが書けたときもうれしいけど、やりたいことに対して「◯◯使えば一瞬で終わるしみんなが楽だ」って気付いて実現できたときの喜びのほうが大きい。

チーム内でも、もっと効率化できるとこあるなぁと思いながらも
ここ1年くらいは開発以外の業務量が増えていたという事実もあり
最近はそういった仕事の量を相談して減らして、開発に集中させてもらっている。

インフラ作業が多く、特にサービスの特徴的にもフロントエンドの重要性が低いので
しばらく触れていないJSを中心にSPAにも触れていけると楽しくなりそう。