てくすた

ピクスタ株式会社のエンジニア・デザイナーがつづるよもやまテクニカルブログです

エンジニアの力でサービス・組織をスケール化させるには?〜Web現場MeetUP #2〜 レアジョブ×ピクスタ を開催しました。

f:id:kaibadash:20171108193553j:plain

こんにちは、開発部の @kaiba です。ひやおろしが出て来る時期になり、日本酒好きには良い季節になってきましたね。

Web現場MeetUP #1に引き続き、エンジニアの力でサービス・組織をスケール化させるには?〜Web現場MeetUP #2 〜を開催しました。

今回はレアジョブさんと一緒です。ピクスタでは外国語学習の補助を受ける事ができ、私を含めレアジョブ英会話を利用している社員も多く、馴染み深いサービスです。

ピクスタもレアジョブさんも10年を超える企業で、スケール化に立ち向かっている企業です。 そんな私達が「エンジニアの力でサービス・組織をスケール化させるには?」というテーマについて話し合ったので紹介させてください。

発表概要

5年しかもたない最高のシステムとの向き合い方

www.slideshare.net

レアジョブ 岩村 淳平さん (@iwason_jp) による発表でした。 技術的負債に向き合ってきた5年間の話でした。うまくいったこと、うまくいかなかったこと、まさに現場でしかわからない知見です。

組織と個人の成長環境のつくり方

www.slideshare.net

私、@kaiba の発表です。 勉強会への参加・開催、OSSへの貢献、開発合宿のいろは、などで成長しよう!という話をさせていただきました。

WebRTCで実現する次世代英会話と旧世代式開発手法

speakerdeck.com

レアジョブ 羽田 健太郎さん (@jumboOrNot) によるWebRTCを使用したモバイルアプリの話をご紹介いただきました。

サービスのスケール化のための検索システム改善

www.slideshare.net

弊社、星 直史の発表です。 AWSのCloudSearchのスケール化とコスト削減についての発表でした。

懇親会

発表の後は、ご参加いただいた皆さんと懇親会を開催しました。

f:id:kaibadash:20171108205519j:plain

f:id:kaibadash:20171108213040j:plain

f:id:kaibadash:20171108213138j:plain

おわりに

早くも「Web現場Meetup #3」も予定しております。 Webサービスの開発現場ついてざっくばらんに情報交換したい方、弊社connpassページをフォローしてみてください!

* * * * *

ピクスタでは、「ユーザーに価値を速く継続的に届けるために技術をどう使うか」というテーマに興味のあるエンジニアを募集しています!

www.wantedly.com

音楽素材販売プロジェクトで React を小さく導入した話

エンジニアの id:cheezenaan です。いよいよ秋本番ですね。私は近ごろ映画鑑賞して過ごすことが多いのですが、なかでも『劇場版 響け!ユーフォニアム〜届けたいメロディ〜』はこの数年で一二を争うアニメ映画ではないかと絶賛しております。

さてピクスタでは先日のプレスリリースの通り、新たに音楽素材の販売を開始いたしました。昨今需要の高まりつつある動画やアプリをはじめとするコンテンツの制作等、さまざまな用途にご利用いただけます。

f:id:cheezenaan:20171023124622p:plain

pixta.co.jp

この記事では、プロジェクトの舞台裏のひとつとして、音楽素材の検索ページのフロントエンドに React を小さく導入した話をご紹介します。

経緯と導入の方針

ピクスタでは、フロントエンドの JavaScript 開発に Knockout.js や jQuery といったライブラリを採用していますが、昨年冬より一部の機能・ページに対して、React による UI 構築、Redux による状態管理、そして Flow による静的型チェックの導入をはじめています。

React を導入した理由は以下の通りです。

  • メンテナンスの容易さ
    • コンポーネント単位で UI を構築するので、再利用性が高い
    • 外部から渡されるパラメータが同じであれば同じ UI が生成されるため、テストもしやすい
  • ライブラリのエコシステムの活発さ
    • Storybook や Enzyme など、コンポーネントのデザイン確認やテスト用のライブラリがOSSで公開されており、かつ頻繁にアップデートが行われている

Flow を導入したのは、コンポーネント内のデータや振る舞いの情報を説明するドキュメントして活用する意味合いが強いのですが、PropType による動的型チェックと比較して、静的型チェックではコードを実行しなくてもエラーやバグを検知できるため、「実装→確認→修正」のフィードバックをより素早く回せて非常に便利です。

JavaScript へ静的型チェックを導入する選択肢として TypeScript もよく挙げられますが、既存のコードベースへ段階的に展開しやすいこと、ESLint ら既存のツールチェインやライブラリとの相性がよいことから Flow を採用しています。

本プロジェクトのキックオフで「音楽素材の検索ページのフロントエンドでも React を導入しよう」という話が出た際、Redux に関しては業務要件や開発スケジュールを鑑みると、導入・学習コストに対してオーバーキルそうだと導入を見送り、React と Flow のみで UI を構築していく方針に決定しました。

検索ページへの React 導入

既存サービスの機能拡張とはいえ、UI やデザインを含めたフロントエンドの改修は新規開発の色合いが濃く、サーバサイドの修正に比べてコードの修正量が自然と多くなりがちです。

そこで、コードレビュー時におけるプルリクエストの差分が大きくならないように、段階を踏んで実装を進めていきました。

  1. デザインモックから React コンポーネントへの切り出し・分割
  2. React コンポーネントの状態管理

以下では各段階の補足事項や苦労話を解説していきます。

React コンポーネントの分割

f:id:cheezenaan:20171023143644p:plain f:id:cheezenaan:20171023173214p:plain

デザインモックの各要素を、UI の振る舞いの定義と props の受け渡しを行う Container Component と、受け取った props をもとに UI を描画する Presentational Component に大別しながら、React コンポーネントを作成していきました。これら2つのコンポーネントに関する解説は、Redux の作者である Dan Abramov 氏のブログ記事を参照ください。

medium.com

React コンポーネントの状態管理 〜素材の試聴機能を例に〜

音楽素材の検索ページでは、検索結果に表示された各素材の音源を試聴できます。

ピクスタでは、音源視聴ライブラリに mediaelement.js を採用しています。mediaelement.js とは、HTML5 の video / audio タグをラップして動画や音源の試聴プレイヤーをクロスブラウザで提供するライブラリで、ピクスタでも既に動画素材のプレビュー機能で利用しています。

このライブラリの内部では試聴プレイヤーの DOM 要素が React とは独立して生成・管理されており、「ライブラリ内部のプレイヤーの状態と、React コンポーネント内の状態をいかに同期するか」に頭を悩ませました。最終的には React で用意されている ref を用いて、ライブラリで生成した DOM 要素(mediaelement のプレイヤー)を React コンポーネントから呼び出して解決しています。

まとめと今後の展望

以上、駆け足ではありましたが、音楽素材の検索ページのフロントエンドに小さく React を導入した経緯や苦労話をご紹介しました。「要件を満たしつつも大げさになりすぎない構成で React を導入する」という当初の目標を達成できたのではと自認しています。

一方で「ページの構成要素が複雑化していった際、いかに各コンポーネントの状態を管理していけるか」が今後の課題として浮き彫りになりました。Flux の概念を導入して処理の流れを一方向に定めるのが、この手の課題に対する常套手段ですが、Flux 系のライブラリとして一部ページで先行導入している Redux を採用するか、また Flux を採用せず MobX や RxJS などのライブラリを用いて状態を管理するのがよいか、引きつづき検討・議論を深めていきたいです。

また、今回 React にガッツリ触れてみて、$(element).html(someSelector) などと jQuery で直接 DOM 要素を書き換えていた頃から時代の進歩を感じずにはいられませんでした。とはいえなんでもかんでも React で置き換えればいいという話ではありません。用法用量を守って適切にライブラリを選択する姿勢が肝要です。

* * * * *

ピクスタでは、新しい技術の導入にチャレンジしつつ、持続的にサービスを改善していくことに興味があるエンジニアを募集しています。

We are hiring!