UUUM攻殻機動隊(エンジニアブログ)

UUUMのエンジニアによる技術ブログです

UUUM System Meetup #2

f:id:chibiProgrammer:20191224133138j:plain こんにちは、エンジニアの中村です。

12月13日にUUUM System Meet Up#2を開催したので、その様子を書いてみました!

今回も前回に引き続き沢山の人がきてくださいました。

前回よりもかなり盛り上がってとてもいい会になりました。

今回のイベントは、社内外の技術者たちと交流を深めたいということと、 社外の人に自社のシステムを紹介しようという目的の元開催いたしました!

今回のイベントの発表内容はこちらです。 今回は元UUUMエンジニアのnazoさんをお呼びして、発表していただきました!

発表者 役職 タイトル
obara_t エンジニア UUUMエンジニアの日常
ishihara_k エンジニア UUUM攻殻機動隊に入隊しました
fujisawa_y エンジニア CREAS
nazo エンジニア レガシープロダクトを改善していくための戦い方

最初の会社説明の後に、 obara_tさんの発表「UUUMエンジニアの日常」

f:id:chibiProgrammer:20191224134605j:plain
UUUMエンジニアの日常

obara_tさんは、社内システムについてと、UUUMエンジニアの日常を紹介してくださいました。 技術選定の話や、技術的なチャレンジは責任持ってやってくれればOKなど、自由なシステムの雰囲気を紹介してくださいました。

社内外で勉強会もよくしていて、 直近だと「お前らはDockerを1mmも理解していない」という勉強会が開かれ、 ピザパや焼肉をみんなで食べに行ったりなど、とても楽しそうな雰囲気が参加者に伝わったように思います。

次は、 ishihara_kさんの「UUUM攻殻機動隊に入隊しました」

f:id:chibiProgrammer:20191224141316j:plain
UUUM攻殻機動隊に入隊しました

ishihara_kさんはUUUMに入ってまだ2ヶ月目ですが、入ってすぐの目線で見たシステムについて話してくださいました。

ishihara_kさんの1つ前の会社がとてもブラックで、1年で300日オフィスで寝泊まりで作業していたという話を聞いて恐ろしいなぁと思いました。

UUUMはめちゃめちゃホワイトなので安心してくださいね!

次に、fujisawa_yさんの「UUUMと開発の話」

f:id:chibiProgrammer:20191224160429j:plain
UUUMと開発の話

fujisawa_yさんはCREASという、UUUMクリエイター限定サイトの紹介と、エンジニア×YouTuberについて発表してくださいました。

CREASを支える技術や、実際の作業内容を話してくださいました。CREASについて詳しく知りたい方は、「UUUM限定サイト」と検索してみてください!

また、エンジニア×YouTuberの話では、Githubのフォロワー数7位はエンジニアであったり、海外ではエンジニアでYouTuberの人のチャンネルがとても伸びていることを初めて知りました。

最後は、nazoさんの「レガシープロダクトを改善していくための戦い方」

f:id:chibiProgrammer:20191224145532j:plain
レガシープロダクトを改善していくための戦い方

nazoさんは元UUUMエンジニアの方で、初期からずっとシステムを支えてくださった方です(とてもすごい人です)。

今回は、レガシーコードとの向き合い方・心構えについて発表してくださいました。

レガシープロダクトを悪い状態を続けないために、CI/CDの設備、Lintの導入、環境構築をしやすい状態にしておくなど、 気をつけておかないといけない部分を紹介してくださり、自分が見えていない部分を色々と学ばさせていただきました。

とてもためになりました!登壇してくださり、本当にありがとうございました!

懇談会では、ケータリングを囲んでわいわい技術の話で盛り上がりました。 今回のイベントでUUUMに興味を持ってくださった方も沢山いて、とても楽しかったです。

f:id:chibiProgrammer:20191224151744j:plain
懇談会での様子

f:id:chibiProgrammer:20191224152651j:plain
ケータリング

f:id:chibiProgrammer:20191224153107j:plain
ケータリング

f:id:chibiProgrammer:20191224152404j:plain
全体写真

イベント参加者の皆さま本当にありがとうございました。1回目よりもとてもいいイベントになりました。 第3回も行いますので、その際はぜひ遊びにきてください!

プロダクトマネージャーカンファレンス2019

こんにちは。PMチームのしだです。
会社のカンファレンス参加精度を利用して、2019年11月12、13日に行われたプロダクトマネージャーカンファレンス2019に参加してきました。

2019.pmconf.jp

参加した9つのセッションの中から、
「PMが学ぶべき、最低限のデータ活用スキルとは」
についてレポートします。

レポート

セッション概要

『PMが学ぶべき、最低限のデータ活用スキルとは』
株式会社Hakali代表取締役
小川 晋一郎

データは分析するだけでは意味がなく、ユーザーのために活用されてはじめて価値が生まれます。ですのでユーザーのことを日々真剣に考え、新たな価値提供を生みたいと常に思っているPMの人たちこそデータ活用スキルを身につけるべきです。しかし、かといって統計学を一から学んで、、、とか、機械学習の講座を受けて、、、では遠すぎます。必要最低限のデータ活用スキルを身につけて、ユーザーへの価値提供力を高めましょう。

https://2019.pmconf.jp/sessions/2019/11/13/S2-003/

はじめに

  • よくある事例

    • 数字を今すぐ見たいPM VS 忙しいエンジニア
    • 説明をしたいPM(ユーザーに嫌がられるのでユーザーへのメール数を減らしたい) VS 話の通じない上司(減らして売上あがるの?)
    • 自分でデータを扱えればこんな事例に対応できる
  • 実際に対応した事例

    • Before:機能ベースのKPI設定で現場が疲弊
    • After:意味ベースのKPIを設定したことで、中長期的な目線での戦略が打てるように
  • =受注の背景には何があるのかを見つけて意味ある指標を設定する

  • ふまえて今回のテーマは

    • 意思決定のためのデータ活用手順
    • 具体的なスキルとその身につけ方

意思決定のためのデータ活用手順

f:id:shidm00:20191122114032j:plain

  • データ活用に最も大切なテーマ
    • データというコミュニケーション言語をつかって、解くべき「課題」をチームで合意する
      • 事業インパクト
      • 解決コスト
      • 戦略の方向性
      • 部門ごとの視点
      • 組織のcapability

指標が相手や営業に刺さらない場合はだいたい「課題の設定」がずれている
そのためにPMとしては
解くべき「課題」を決めるための合意形成プロセスに責任をもち、
議論が進むための素材を準備する

  • おすすめのデータ活用モデル
    • OODAループ
      • Observe 見る
      • Orient わかる
      • Decide きめる
      • Act うごく
    • PDCAだとPlanが先にくるが、Planを立てるということは難しいこと
    • なので、まずは観察することから始める
    • 先の読めない、リーンな開発には特に合う

f:id:shidm00:20191122114102j:plain

Observe(見る)
  • 現場感覚(インタビュー) と 生データ
  • ユーザー(顧客)と接点ある人達から課題感を聞いて整理
  • 現場のモヤモヤはだいたい正しい
  • モヤモヤ会議で課題を集めてみる

代案のない提案をするなとか代案出さずに不満だけ言うななどと言われがちだが、モヤモヤにある課題が何なのかの見極めも、その解決も難易度はとても高い
代案が出せない場合ずっとももやもやを抱えている状態が続くことになる
なのでまずは現場のモヤモヤを吸い上げて整理するのが大事
モヤモヤ集めで課題認識が擦り合うだけで、現場の協力が得られるようになり、その後の議論がスムーズになるケースもある

  • 生データを見てみる
    • 分析手法をつかってかっこよく鮮やかな正解を出す…とかいうよりも、とにかく生データを見ること
    • エクセルでの数値管理はつまりサマリなので、生データからあたってみるだけでもかなり違う
Orient(分かる)
  • モデル化
    • 現実の見方や捉え方を言語化、可視化してKPIツリーに紐付けること

KPIツリーに出てきにくいが「スピード」が重要な指標となることは多い(例えばマッチング後の面接設定メールなど)
スピードを加味したモデル作りをする

  • 総数問題のモデル化
    • 一般的に「総数」が増えると「次のファネルへの移行期待値」が上がるが、閾値がある
      • 増やせば増える、には限界がある
    • 適切なところを指標に設定する必要がある

f:id:shidm00:20191122114121j:plain

  • 総数問題に関連して…
  • 冒頭ちらっと出したユーザーへのメール爆打ち問題のモデル化

    • それが起きやすいのは、送れば送るほどKPIツリーの数字が増えるモデルにしているから
    • そういう状態にしないために、KPIの中にネガティブ要素を含める必要がある
    • 例えば、数打ちすぎると退会率があがる、開封率が下がるなどが考えられるので、退会率や開封率も組み合わせるなど
    • トータルの売上を意識している人と同じ言語でデータで語る必要がある
  • 細分化の罠

    • 細かいパターン分類に走っても、打ち手を細かく打つコストが高いことが多い
    • KPIツリーのマクロデータのみで思考すると起こりがち
Decide(きめる)
  • マクロで見たときの施策インパクトは常に確認する
    • PMが「やりたい」ことが、案外マクロでみたらインパクトが小さいことは少なくない
    • 率改善が売上にどうインパクトするのかという視点を常に持つ
  • 比較

    • 比較がないと良い悪いの判断ができないが、比較するものによって見える結論は変わることを自覚する必要がある
  • WEBサービスの外のモデルが大切なこともあって見落としやすい

    • WEBサービスのことばかり見ていて、一連の作業の流れなど大きなところをみることを忘れると見落としが発生しがち
    • ユーザーの行動全体をみる
  • その他気をつけること

    • 普段会議にいないキーマンの観点を考慮できていないと意思決定できないこともあるので注意
    • 常に視座を高く持っておくことが大切
まとめ
  • チームでデータを扱いながらOODAループを回すことで、事業クリティカルな課題を1つずつクリアしていく
    • OODAループ
      • Observe 見る
      • Orient わかる
      • Decide きめる
      • Act うごく

具体的なスキルとその身につけ方

たくさん覚えるのではなく、必要最低限で生き延びること
=サバイバル

データ活用のために押さえること

WebサービスのPMであればまずはSQLを覚えるべし

  • 実践がないと頑張れないので、準備より本番
    • データ定例を作って関係者を週次であつめる
    • もやもやを話してもらって宿題化する
    • 宿題を解くことで力をつけていく
  • 試行錯誤しやすい環境を構築することも必要

  • 概念的に理解すべきポイント

    • データをDatabaseとして「テーブル」の概念で扱えるかどうかは大きな分岐点
    • 人間が読むことではなく、システムが読める形で扱う
  • おすすめのSQL修業ステップ

    • ちゃんとした人(エンジニア、データサイエンティスト)が書いたクエリを読み込み、一部だけいじって出してみる
    • 自分で簡単な文法で書いて抽出したものを、BIツール等外で加工して利用
    • WINDOW関数やサブクエリ等、ある程度複雑なものもSQLで表現
  • DBのテーブルにどんなデータが入っているのかを読みとけるようになると自走力は上がる
分析手法として 何をしっておくと良いのか

分析はrawdataの意味を取りやすくしたもの

  • rawdata

    • 量が多い
    • 全体の意味が読み取りづらい
    • 予算のモデルにしづらい
  • 統計処理

    • 全体の意味を読みやすく集計しているにすぎない
    • データ全体を一言で表現;代表値(平均値、中央値)
    • まとまったパターンに集約:クラスタリング
    • 可視化:各種グラフ
  • 分析手法:分布

    • 平均値より中央値
    • でも意味を考えるならまずは「分布」を眺めたほうがいい
  • クラスタリング

    • タイプごとの中央値みたいなイメージ
    • 共有するときには、データの裏付けを元に「意味」ベースでラベリングすると議論しやすい

まとめ

とにかくやり続けられる環境を作ることが大事
やり続ければいつかスキルは上がる

データ抽出スキルがあることで世界は広がる
Web業界であればまずはSQLを学ぶこと

生情報(インタビュー、rawdata)を元に事象をモデル化して、チームでOODAループを回す

カンファレンス全体通しての感想

  • 会社の状況や文化、事業の内容、一緒に仕事をする人やチームの体制によってPMがやらなければならないことにはかなり差がある
  • 共通しているのは『担当プロダクトの価値を上げること』がミッションで、そのためにできることは何でもするという点(解像度低め)
  • 一般的に定義されているPMの役割について知っておくのは、考える糸口として必要
  • ただ、それにむりやり当てはめるとうまく行かない場合が多そう
  • たくさんの事例を知っておくのは臨機応変な対応をする上で重要

初参加でしたが、普段知ることができないたくさんの企業の様々な事例とその対応を知ることができ、大変有意義な勉強をさせて頂きました。

LEGOブロックで スクラム入門勉強会

10月25日(金)にワイクル株式会社の角 征典様( @kdmsnr )をお招きし、LEGOブロックでスクラム入門の勉強会を行いました。
弊社ではスクラム開発しているプロダクトとそうでいないプロダクト双方あり、私が担当しているプロダクトではスクラムを導入していなかったため、いろいろ発見のある勉強会でした。

第1部:スクラムの歴史〜基礎の説明

第1部ではアジャイル開発の歴史から始まり、現在の複雑化したシステム開発の実態、スクラム開発とはどういったものなのか、わかり易く説明がありました。
その中でアジャイルとは傘に喩えられるように骨組みであり、特に中身は無いものであると言うこと。それを補完すために様々な開発手法が存在し、スクラムもその中の一種であると説明がありました。
また、スクラムをすることでチーム内の知識・経験を蓄積することができ、より強固なチームへ進化させていくものだということがわかりました。

第2部:LEGOで街づくりをしながらスクラム体験

座学終了後、レゴを使用してのスクラム開発の体験です!
この勉強会では開発側・顧客側を体験できるように設計してあるため、自分たちが設計した街を他チームが、他チームが設計した街を自分たちが作っていきます。

まず各チームが家族という設定で欲しい建造物をカードに書き出していき、模造紙を使い理想の街の設計図を作っていきます。
設計図作りが終わったらカード毎に優先度をつけて並び替えていきます。その後、開発者として他のチームへ移動します。

f:id:a-hiro35:20191031172047j:plain
私達チームの街は商店街は駅近に、公共施設は自然の近くに配置しました。

f:id:a-hiro35:20191031172015j:plain
他のチームのイラストレベルが高すぎてびっくりしたり。。。

移動したら、他チームの設計図を元に、①見積もり、②スプリント、③レビュー・振返りを繰りを繰り返して街を完成させていきます。

まずはプランニングポーカーでざっくりと工数見積もりをします。見積もる際に出てきた疑問点は相手チームのプロダクトオーナーに相談して進めていきます。
その後、3回のスプリントで全てを完成できるように、Velocityを算出。
予想値ピッタリになるように、プロダクトバックログの上から順番に実現できそうなころまでストーリーを引き、開発していきます。

1回目のスプリントでは顧客の要望をきちんと把握できておらず、顧客の望む通りの建物をうまく作り上げることができない人が出てきました(私です)。
その結果、Velocityの予想値をかなり下回り、不本意な結果に終わってしまいました。

2回目のスプリントでは1回目の振り返りを基に再見積もりをし、新たにVelocityを設定していきます。
前回の反省を踏まえ、工数が大きなものは複数人で開発するように変更しました。

f:id:a-hiro35:20191031171729j:plain

前回中途半端に終ってしまったモノは顧客が求める建物としての要素を追加していき、また工数が大きいモノも複数人で開発することで時間内に完成することができました。
顧客レビューでは全ての建物に対して合格をいただき、予想値通りの開発をおこなうことができました。

f:id:a-hiro35:20191031172115j:plain

f:id:a-hiro35:20191031171817j:plain
最後に、チームで作成した傑作の油田です。

まとめ

勉強会を終えて、1回目ではバラバラだったチームに一体感が生まれるのを感じ、開発スピードも上がっているのを実感することができました。
また、顧客の要望を適切に理解する必要性、どう叶えるかをチームで考えることで一体感が生まれたのを感じました。
メリットを多く感じたので、自分のチームでもスクラム開発をしたい!と思える会でした!

Docker + MeCab + JupyterLabによる分析環境の構築

こんにちは、分析チームの門脇です。

日頃クリエイターに関するデータ分析業務を行う際、環境ごとのライブラリの管理が面倒だったり、形態素解析エンジンの導入、notebookの設定をやり直す必要があるなど何かと不便でした。

そこで今回は、Dockerを利用して、簡単にクリエイター分析環境を構築してみました。

Dockerについて

Dockerはコンテナ型の仮想化環境のことで、Dockerfileに仮想環境に取り入れたいものの処理を記述することで、簡単に同一環境を再現でき、環境ごとに設定をやり直さなくて済むといったメリットがあります。

Dockerによる環境構築ついて詳しく知りたい方はこちらにわかりやすくまとめられています。

今回は記事の中でも紹介されているKaggleが提供しているDockerイメージをベースにDokerfileを作成していきます。

MeCabについて

クリエイターについて分析を行う際に、テキストデータを単語ごとに分割して関連ワードを取得したいことがあります。

MeCabは日本語の形態素解析エンジンの中では最もよく使用されていて、mecab-ipadic-NEologdというシステム辞書があり、新語・固有表現に強い単語を分割する際に有効です。

例として、『 ブンブンハローYouTube、どうもヒカキンです!』を調べてみます。

  • MeCab標準辞書のとき f:id:guajfv:20191017141259p:plain

『ブンブンハローYouTube』について

  • ブンブン
  • ハロー
  • YouTube

それぞれ別の単語として認識されてしまいます。

  • mecab-ipadic-NEologdのとき f:id:guajfv:20191017141223p:plain

『ブンブンハローYouTube』として固有名詞として分割でき、『ヒカキン』も固有名詞として認識されます。

日々新しい用語が生まれるYouTubeにおいて、mecab-ipadic-NEologdを使うことで、簡単に対応することができます。

JupyterLabについて

みんな大好き『Jupyter notebook』の後継機のIDEで、オープンソースとして公開されています。

『Jupyter notebook』をより使いやすくしたものであり、こちらで便利機能が詳しく紹介されています。また、自分好みに拡張機能を追加することができ、作業効率を上げることができます。実際にDockerfileへ拡張機能の導入を取り入れてみました。

作成したDockerfile + docker-compose.yml

Dockerfile

# Kaggleが提供しているDockerイメージをベース
FROM gcr.io/kaggle-images/python:v67


RUN pip install -U pip && \
    pip install fastprogress japanize-matplotlib

# mecabとmecab-ipadic-NEologdの導入
RUN apt-get update \
    && apt-get install -y mecab \
    && apt-get install -y libmecab-dev \
    && apt-get install -y mecab-ipadic-utf8 \
    && apt-get install -y git \
    && apt-get install -y make \
    && apt-get install -y curl \
    && apt-get install -y xz-utils \
    && apt-get install -y file \
    && apt-get install -y sudo


RUN git clone --depth 1 https://github.com/neologd/mecab-ipadic-neologd.git \
    && cd mecab-ipadic-neologd \
    && bin/install-mecab-ipadic-neologd -n -y

RUN pip install mecab-python3

# nodejsの導入
RUN curl -sL https://deb.nodesource.com/setup_12.x | sudo -E bash - \
    && sudo apt-get install -y nodejs

## JupyterLabの拡張機能

# 変数や行列の中身を確認
RUN jupyter labextension install @lckr/jupyterlab_variableinspector

# 自動整形
RUN pip install autopep8 \
    && pip install jupyterlab_code_formatter \
    && jupyter labextension install @ryantam626/jupyterlab_code_formatter \
    && jupyter serverextension enable --py jupyterlab_code_formatter
  • Kaggleが提供しているDockerイメージは最新のものを指定しています。(2019/10/17時点)
    また、こちらから適宜最新のイメージを確認していただければと思います。

  • mecab-ipadic-NEologdのインストールはこちらに記載されているライブラリを入れます。また、PythonからMeCabを使用するために mecab-python3もインストールします。

  • JupyterLabの拡張機能の利用についてはNode.jsが必要となるのでインストールします。また、今回は個人的に便利だと思ったものを拡張機能としてインストールしています。

docker-compose.yml

version: "3"
services:
  jupyterlab:
    build: .
    volumes:
      - $PWD:/content
    working_dir: /content
    ports:
      - 8888:8888
    command: jupyter lab --ip=0.0.0.0 --allow-root --no-browser

ここでは、コンテナ起動時にjupyter labが起動するよう設定しています。

下記コマンドで、コンテナを作成して、起動します。--buildを指定することで事前にイメージを作成してくれます。

$ docker-compose up --build

するとコンソール上に結果が表示されます。

jupyterlab_1  |     Copy/paste this URL into your browser when you connect for the first time,
jupyterlab_1  |     to login with a token:
jupyterlab_1  |         http://7147a0639219:8888/?token=××××××××××××××

あとはホスト名をlocalhostにして、ブラウザでログインするだけです。

  • MeCabをPythonで使うとき
    • 辞書のインストール先はJupyterLab上で下記コマンドにより確認できます。
      !echo `mecab-config --dicdir`"/mecab-ipadic-neologd"
    • 今回は、/usr/lib/x86_64-linux-gnu/mecab/dic/mecab-ipadic-neologdにインストールされたことが確認できたのでコードを書く際は、インストール先を指定します。
import MeCab

tagger = MeCab.Tagger(
    '-d /usr/lib/x86_64-linux-gnu/mecab/dic/mecab-ipadic-neologd'
)
print(tagger.parse('ブンブンハローYouTube、どうもヒカキンです!'))

すると、先ほど示した例のようなmecab-ipadic-NEologdを使用したときの結果が出力されます。

まとめ

Dockerを利用することで自分好みの分析環境をサクッと作れちゃいます。環境構築という煩わしいことに時間をかけずに分析に集中できるのでとってもオススメです!

みなさんも自分好みの環境を作成してみてはいかがでしょうか!!!

参考文献

UUUM System Meetup #1

f:id:chibiProgrammer:20190919015916j:plain こんにちは、エンジニアの中村です。

9月6日にUUUM System Meet Upを開催したので、 その様子を書いてみました。

uuum.connpass.com

今回は約30人以上もの人がイベントに参加してくださいました。

攻殻機動隊の初イベントにも関わらず

たくさん集まってくださって嬉しかったです!

今回のイベントは、UUUMを支えるテクノロジーや

普段から学んでいることをアウトプットし、

社内外の技術者たちと交流を深めたい!という目的の元開催いたしました。

イベントの発表内容はこんな感じです。 今回は発表者を何人かピックアップしてご紹介したいと思います。

発表内容

発表者 役職 タイトル
nakatsuka_d マネージャー UUUM満開~なんで私が登壇に!?~
myaunraitau エンジニア プラットフォームのデータを解析するお話
sabomasa エンジニア 再生回数のデータを予測するお話
btomasato CTO ぼくのかんがえたさいきょうの GAS かいはつかんきょう
killyishuguro PM デザイン思考と初心者PM
MaxYasuda エンジニア インフラ勉強初めて1ヶ月なのでECS FARGATEでrails構築した

まず最初はnakatsuka_dさんの「UUUM満開~なんで私が登壇に!?~ 」

f:id:chibiProgrammer:20190917193124j:plain
UUUM満開~なんで私が登壇に!?~

オタサーの姫を作ると営業と仲良くなれるという話や、UUUMのことを面白おかしく紹介してくださったりと、会場もとても盛り上がりました。

次はmyaunraitauさんの「プラットフォームのデータを解析するお話」

f:id:chibiProgrammer:20190918112052j:plain
プラットフォームのデータを解析するお話

機械学習を用いてクリエイター間の類似度算出を行うという発表でした。

機械学習をあまり知らない私でも雰囲気を掴めるようなわかりやすいスライドで、機械学習って色んなことに使えるんだなぁという気付きにもなり、とても楽しかったです。

次はsabomasaさんの「再生回数のデータを予測するお話」

f:id:chibiProgrammer:20190918112048j:plain
再生回数のデータを予測するお話

sabomasaさんもmyaunraitauさんに続いて、機械学習を用いたデータ解析の発表でした。

内容は機械学習を用いてYouTubeの再生回数を予測するという感じでした。 再生回数を予測することが出来るなんてびっくりしたし、機械学習やってみたくなりました笑

次に我らがCTO、BTOさんの「ぼくのかんがえたさいきょうの GAS かいはつかんきょう」

f:id:chibiProgrammer:20190919013324j:plain
ぼくのかんがえたさいきょうの GAS かいはつかんきょう

今UUUMに入って業務改善でGASを使っていますが、いつも自分がやっていることよりもっと踏み込んだ話で 私もGASマスターしたいと切実に思いました!

懇談会はピザを囲んでわいわい技術の話などで盛り上がりました。 UUUM以外のエンジニアやPM、デザイナーの方とお話ができて本当に楽しかったです。

f:id:chibiProgrammer:20190919014511j:plain
懇談会の様子

f:id:chibiProgrammer:20190917192721j:plain
全体写真

とても楽しいイベントとなり、本当に良かったです。 イベントに参加して下さった皆様本当にありがとうございました!

第2回も12月頃に行いますので、是非遊びにきてください!

秋の開発合宿を開催しました!

f:id:c14043:20190930155209j:plain

こんにちは!今回開発合宿のブログ担当する、インターンの鷲見です!

システムユニットでは年2回、開発合宿を行なっています。

今回行なった場所は湯川原にある「おんやど恵」という旅館です。開発合宿(旅行)ではよくお世話になっているのでところです。

  • 都内から二時間ほどで行ける
  • 開発合宿用のプランがある
  • 24時間使える会議室がある
  • Wi-fi環境が整っている
  • 温泉と足湯

といった環境がおんやど恵は整っているので、開発合宿をするのにとても便利です。

www.onyadomegumi.co.jp

旅館紹介

実際にどんな旅館なのか紹介していきます!

会議室

こちらが会議室です。一人、一人スペースが用意されているので、場所に困ることはありません。また成果発表用にプロジェクターも用意してもらいました!

f:id:c14043:20190930122526j:plain

温泉

温泉は夜、早朝といつでも入ることができるので最高ですね!

f:id:c14043:20190930122402j:plain

中庭には足湯があり、入りながら開発もできるのでとても快適です!

f:id:c14043:20190930122103j:plain

食事

食事はコースで出てきます。味もボリュームも十分あるので大満足です。

f:id:c14043:20190930123726j:plain

このお肉と味噌組み合わせはとても美味でした!

f:id:c14043:20190930123737j:plain

開発は何をしたのか?

今回の開発合宿はテーマは「自由開発」です。

日頃業務ではやらないことに挑戦したり、技術をより理解すること、PMの方達はチームが力を最大限発揮するための研究にたくさんの時間を使うことができました。

f:id:c14043:20190930125118j:plain

お昼の2時ごろから着々と取り掛かっていきます。

深夜の追い込み

食事をした後、会議室組は深夜の追い込みをかけてきます。

f:id:c14043:20190930125905j:plain

支給品も届き、仕上げに取り掛かっていきます。

f:id:c14043:20190930143758j:plain

翌朝

朝に少し作業した後、成果発表を順番にしていきます。中には徹夜して限界を迎えてしまう人も。。。

f:id:c14043:20190930154959j:plain

皆さん短い時間の中で高い成果を上げていました。。。

日頃の業務外の技術を使って作られた作品が多かったので、発表はとても面白いものとなりました。

f:id:c14043:20190930160150j:plain

まとめ

2日間に渡り開発に集中できる素晴らしい環境を整えてくださったおんやど恵の皆様ありがとうございました。

すばらしい環境だからこそ、短い時間の中でもそれぞれ成果を出すことができました。

開発と発表を通して、それぞれ知識を共有できたのでとても有意義な時間を過ごせてよかったです。

最後は集合写真終わろうと思います。

f:id:c14043:20190930160745j:plain

Athena + Glue + (Terraform)でいい感じにファイル上のデータを集計しよう

システムユニットのt_u_a_kです。ブログ登場は初めてです。私は業務で少々大きめのデータの集計ということをやっていますが、その際にはAWSのAthenaとGlueを試しました。手軽でよかったので紹介します。

AthenaとGlueについて

まずAthenaについてですが、これはS3上のデータに対するクエリサービスです。データベースに対するクエリサービスではなく、S3上のテキストファイル(もしくはそれらを圧縮したりしたもの)に対してデータ構造を定義し、いわゆるSQLを使って普通にクエリが書けます。この時点でAthenaのようなサービスや仕組みに触れたことがない人にとっては「は?」って感じですね。AthenaはPrestoというFacebookが開発したクエリエンジンを使っていて、大きなデータでも爆速で結果が返ってきます。Presto公式ではFacebook自身が300PB以上のデータの分析に利用していると書いています。ここまで来るとでかすぎて想像もつきませんが、通常の利用であれば本当に驚くほどのスピードでクエリの結果が返ってきます。

aws.amazon.com

次にGlueです。GlueはいわゆるETLサービスというやつです。最近だとデータウェアハウスを構築するところも多いと思いますが、いろんなところにいろんな形で存在しているデータを変換したり移動させたりいい感じに集めるときに使うサービスというのが非常に雑な説明です。Glueにはデータカタログという機能があり、これがAthenaと一緒に使える機能です。Athenaはクエリサービスと書きましたが、Glueで定義したデータカタログをいわゆるデータベースやテーブルと見てクエリをすることができます。これではわかりにくいと思うので下で説明していきます。

aws.amazon.com

今回使うデータ

例えばこんなデータがあったとします。

# hikakin.csv
video_id,title,channel_id,views,date
zW4HJkuFFtc,【ランキング】ヒカキンがガチでウマいと思うセブンの商品トップ3!【2019年5月編】,UCZf__ehlCEBPop-_sldpBUQ,1826863,20190518
VY0EXQqSeRc,顔面が大変なことになりました…,UCZf__ehlCEBPop-_sldpBUQ,1650048,20190517
MgeD8MB6fyg,金属アレルギー検査したらまさかの結果が…【1900万円の時計のその後】,UCZf__ehlCEBPop-_sldpBUQ,1906878,20190515

皆様ご存知のヒカキンさんのチャンネルHikakinTVの動画について、2019年5月のある時点でのデータです。1行目が動画IDや動画タイトルといったヘッダー、2行目以降がデータになっています。他にもこのような似たデータを用意しました。0214mexはじめしゃちょーさんでtsuriyoka釣りよかでしょうさんの動画に関するデータです。釣りよかでしょうさんに関してはサブチャンネルのデータも混ざっています。これらがそれぞれhikakin.csvhajime.csvtsuriyoka.csvという名前で存在している、もっというとUUUM所属の各チャンネルごとにこのようなデータがあると仮定して、Athenaでクエリをかける準備をしていきます。 (※0214mexなどを見ても何のこと?と思う方もいらっしゃるかもしれませんが、はじめしゃちょーさんのYouTubeチャンネルについてはhttps://www.youtube.com/user/0214mexというURLでもアクセスできるようになっており、他のチャンネルでもこれに似た形でURLが表記されることがあります。)

# 0214mex.csv
video_id,title,channel_id,views,date
dmpYE9u3cr4,"【50,000枚】3年間集めた遊戯王カード全部売ったら金持ちになったwwwww",UCgMPP6RRjktV7krOfyUewqw,1280160,20190520
xUFNcNQ24Ho,家に隠されたドラゴンボールがガチで見つからない件。,UCgMPP6RRjktV7krOfyUewqw,1055697,20190519
STA6C9ftvmw,コンビニ弁当をミキサーでドロドロにしても味が分かる説,UCgMPP6RRjktV7krOfyUewqw,969160,20190517
# tsuriyoka.csv
video_id,title,channel_id,views,date
d0XrWwauyQY,むねお船は初心者に優しいらしい,UC4QadOSsJu54Qs8z99shRiQ,136100,20190521
dwXSckt1lM4,庭でイカを料理してたら変なの来た,UC4QadOSsJu54Qs8z99shRiQ,215405,20190520
1AuvYVUMNGs,リフォームした家の壁に缶スプレーでらくがきしてみた!,UCD7-Ocp4InwPKzwiq_U-Abg,230155,20190519
ew0HdXG3SKQ,ドラム缶でオリジナルBBQコンロを作る!,UCD7-Ocp4InwPKzwiq_U-Abg,168260,20190521
j5aQ_Y3_I_U,新居キッチンの紹介します!,UCRT-74ovdMKOFBC96w_gfyQ,105864,20190521
YC1OnPK2fWE,ミルフィーユカツで新潟のB級グルメ作ってみた!,UCRT-74ovdMKOFBC96w_gfyQ,73117,20190520

S3へのデータの保存

AthenaはS3上のデータに対するクエリサービスなので、まずはデータをS3に置かなければいけません。今回は

  • 2019年5月のデータ
  • チャンネルごとに別ファイル

となっているので、仮にデータが増えるとすれば別の月のデータだったり、違うチャンネルでファイルが作られるということが考えられます。このような場合にはS3に保存する際に

  • s3://my-bucket/year=2019/month=5/channel=hikakintv/hikakin.csv
  • s3://my-bucket/year=2019/month=5/channel=0214mex/hajime.csv
  • s3://my-bucket/year=2019/month=5/channel=tsuriyoka/tsuriyoka.csv

というふうに/key=value/のパーティションを作ってあげることで、Athenaでクエリをかける際にまるでyearchannelといったカラムがあるようにクエリをすることができます。channelのカラムが1チャンネル1つに対応していないじゃないかとかchannelキーに対するvalueのルールがおかしいんじゃないかといった意見もあるかと思いますが、今回tsuriyoka.csvに複数チャンネルのデータが入ってしまっているため、ファイルの中を見る前はパーティションを厳密にチャンネル単位で分割することができません。パーティションについては細かくすればするほどクエリの条件を細かく設定できるので料金面で有利になる一方、ファイルをS3に設置するコストが高くなってしまうなどもあるので、どの程度の粒度で分析や集計を行いたいかによってパーティション設計は考えていくべきだと思います。自動的にS3にファイルが流れてくるような状況から作るのであれば、パーティション設計はますます重要です。

docs.aws.amazon.com

データ構造を定義する

今回のデータを見たときに、どういうクエリがかけるでしょうか。(本来はどういうことを知りたいかが先に来るべきですが今回はちょっと置いておきます。) 例えば、

select sum(views) as total_views
from s3上のデータ
where year = 2019 and month = 5 
and channel in ('hikakintv`, 'mex0214`)

とか

select videoid, views
from s3上のデータ
where year = 2019 and month = 5 
order by views desc
limit 5

などがあるでしょうか。別の年月やチャンネルが増えればもっといろんなパターンが出てくるとは思いますが、共通しているのはs3上のデータをテーブルとして、CSVの各カラムやパーティションをselect文に入れたいということです。これをやるためのデータ構造をGlueで定義してみましょう。

Glueでデータカタログを定義する

AthenaでクエリをするためにGlueでデータカタログを定義しますが、データカタログを定義するとはデータベースとテーブル(およびその中のカラム)を定義することです。Glueにおけるデータベースとはいろんな場所にあるデータを統一的に扱うためのメタデータストアになりますが、データベースが必ずどこかのバケットと紐づくなどは無いので、実際あまり意識する必要はありません。必要に応じて作っておけばいいものになります。今回作成したデータベースについても名前以外は何も決めていない状態です。

f:id:xxuxa_k:20190928063135p:plain

次はテーブルです。今回のようにAthenaでのクエリを目的としたテーブル作成においては、テーブルとバケットが1:1だと思っておくのがよいと思います。テーブルに指定する内容は大きくわけてスキーマとそれ以外のオプションになります。オプションの項目としてはどのようにデータを解釈させるかを決めるHadoopのフォーマットなどがあります。かなり細かく指定できるようですが、私もすべては把握できていません。いろんな形式のデータを使ってみたりすることでだんだんわかるようになってくるのだと思います。今回作ってみたblog_test_tableは以下のようなデータカタログ設定になっています。

f:id:xxuxa_k:20190929052618p:plain

f:id:xxuxa_k:20190928063532p:plain

Terraformの利用

↑の画像に出したデータカタログの内容をAWSコンソール上から設定することは可能です。しかし、設定の初期などはパーティションを変えることがあったり、なぜかAthena側でデータカタログのロードにうまくいかなかったりと、最初から作り直したほうがいろいろと楽な場合が多いです。(個人的にはHadoopだったり分散処理に関する知識が足りないと十分にエラー調査していくことが難しいのかなと思っています。) 作り直すたびにAWSコンソール上でポチポチやっていたこともあったのですがつらすぎるので、データカタログはTerraform化してしまいましょう。テーブルの追加も作り直しもterraform apply一撃で済むようになることでかなり作業が楽になるのと、クエリを書いて調査・分析をするという本質的な作業に時間を割くことができるようになります。もちろんTerraformの代わりにCloud Formationもありだと思います。 データカタログ部分のterraformコードはこのような感じです。もともとはv0.11系で動くように書いていたのですが、今回ブログを書くにあたってv0.12.9で動作するように書き換えました。(terraform 0.12updateコマンドがあるので基本的には自動で書き換えてくれましたが、一部自分で直すような感じになりました。) ポイントとしてはstorage_descriptor.ser_de_infoかなと思います。S3に保存してあるファイルの形式によってここが変わってきます。今回はCSVを使っていますが、TSV、JSON、Hadoop形式などにも対応していて、形式に合わせてSerDeというシリアライズ/デシリアライズライブラリにオプションを与えることになります。

locals {
  blog_database_name   = "test_catalog_db"
  blog_bucket_location = "s3://xxx/yyyy/..../"
}

resource "aws_glue_catalog_database" "test_catalog_db" {
  name         = local.blog_database_name
  description  = ""
  location_uri = ""
  parameters   = {}
}

resource "aws_glue_catalog_table" "blog_test_table" {
  name          = "blog_test_table"
  description   = ""
  database_name = local.blog_database_name

  table_type = "EXTERNAL_TABLE"

  parameters = {
    EXTERNAL                 = "TRUE"
    has_encrypted_data       = "false"
    classification           = "csv"
    "skip.header.line.count" = "1"
  }

  partition_keys {
    name    = "year"
    type    = "int"
    comment = ""
  }
  partition_keys {
    name    = "month"
    type    = "int"
    comment = ""
  }
  partition_keys {
    name    = "channel"
    type    = "string"
    comment = ""
  }

  storage_descriptor {
    input_format  = "org.apache.hadoop.mapred.TextInputFormat"
    location      = local.blog_bucket_location
    output_format = "org.apache.hadoop.hive.ql.io.HiveIgnoreKeyTextOutputFormat"

    ser_de_info {
      name                  = "blog_test_ser_de"
      serialization_library = "org.apache.hadoop.hive.serde2.OpenCSVSerde"

      parameters = {
        quoteChar     = "\""
        separatorChar = ","
      }
    }

    columns {
      name    = "video_id"
      type    = "string"
      comment = ""
    }
    columns {
      name    = "title"
      type    = "string"
      comment = ""
    }
    columns {
      name    = "channel_id"
      type    = "string"
      comment = ""
    }
    columns {
      name    = "views"
      type    = "int"
      comment = ""
    }
    columns {
      name    = "date"
      type    = "string"
      comment = ""
    }
  }
}

データカタログ部分についてはこれだけです。CSVの形式の変更などがあったときもコード変更とterraformの適用だけです。S3バケットもterraform化できていればより完璧です。 docs.aws.amazon.com

Athenaでクエリする

あとはAthenaでクエリをするだけです。AWS CLIからだと結構柔軟に設定できますが、今回はAthenaのコンソール上からやります。忘れてはいけないことですが、S3にデータを追加したら、MSCK REPAIR TABLE test_catalog_db.blog_test_table;というSQLを流しておきましょう。これをやらないとAthenaが新たに追加されたファイルを認識できなくなります。

f:id:xxuxa_k:20190928065421p:plain

select * from blog_test_tableをしてみると、3.22秒と出ました。仮にこれがRDSであればどう考えても遅すぎますが、Athenaはあまりに小さいデータに対してはRDBMSよりもパフォーマンスが悪くなります。逆に大きいデータに対してはとんでもないスピードで結果を返してきます。今回についてはクエリを投げられるようになることが目的なのでここまでにしておきますが、実際にやったことはバケットとデータカタログの設定だけなのでかなり簡単にCSVのようなデータに対してもクエリが投げられることがわかったと思います。もちろん形式はCSVだけでなく、多様な形式をサポートしています。

f:id:xxuxa_k:20190928080139p:plain

料金について

Athenaはスキャンしたデータに対する従量課金のため、スキャンデータを減らすことが利用料金を減らす一番の近道です。同時にスキャンデータを減らすことは処理速度を上げることにもつながります。 データは圧縮形式でも扱えるため圧縮してS3に入れる、Parquetなどの列形式へ変換するなどの方法も役に立つと思います。

まとめ

AthenaとGlueのデータ集計での利用について書いてみました。今回ほど小さいファイルであればSQLiteを使うのもありだと思いますが、実際にはそこそこのサイズがあると思うので、ファイル上のデータについて単純なクエリをしたいということだとこれが一番簡単な気がします。AWSマネージドなので管理コストも最小限です。

最後に

やっと1回ブログ書けた、、、。システムユニットでは一緒に働いてくれる方を募集中です。

recruit.uuum.co.jp