はい、おはようございます。
6月24日、月曜日ですね。
地獄は朝9時を回りました。
今日は東京めちゃめちゃいい日ですね。
今日も暑くなる日だそうです。
最高気温は37度以下らしいですからね。
はい、おはようございます。kkeethことくわはらです。
じゃあ、本日も朝活を始めていきたいかなと思います。
月曜日一発目ですね。
すごくちょっと昨日の夜、サーバーサブレンダリングのソースコードを書いていて、
なんかもう深夜なのに気になって仕方がなくて書き始めたら、
深夜3時半までソースコードを書いていたので、めっちゃ眠いですね。
おはようございます。
たくさんの方がいきなり参加したりですごくありがとうございます。
今日はですね、タイトルがありますね。
Notes on maintaining an internal React component library っていうところで、
今、React Componentのライブラリを作っている人たちがいて、
その人の知見であったりとか、設計思想みたいなところを書いてくださった記事があるので、
それをちょっと読んでいこうかなと思います。
Reactの記事ばっかり読むんじゃ遠くないっていう話はあるんですけども、
なんとなく読んでいこうと思います。
今回の記事はめちゃめちゃ長いので、多分何回かに分かれていくと思いますけども、
ゆるーくお付き合いいただければなというところです。
じゃあ早速入っていきましょう。
2021年11月からデジタルオーシャンの、デジタルオーシャンという会社ですかねこれは。
UIインフラストラクチャーチームに所属していますと。
UIインフラストラクチャーチームというのがあるんですね。
UIの設計構造だけのチームがあるんですね。
すごいな。
この秘書の方ですね、私の主な職務の一つというのは、
社内のReactコンポーネントライブラリであるウォラスっていうのがあるらしいですね。
の主要なメンテナーとして行動することです。
このライブラリは私が参加する数年前から存在しており、
以前のデザインの選択がどのように展開されたかを見るのはちょっと興味深いことです。
こちらのライブラリのドキュメントっていうのは、
多くのフロントエンドアプリケーションで使用されている既存のデザインシステムの一部として、
コンポーネントライブラリをメンテナーすることについての私の考えをまとめたものになります。
私はビジュアルデザインには実は特に興味なく、実装は得意ですけども。
ビジュアルデザインの実装は得意なんだけど興味ないらしいですね。
むしろ大規模なコンポーネントライブラリを構築する際の
ソフトエンジニアリングや社会的なチャレンジの方に興味がありますと。
今回のノートブログではさらに詳しい情報をお伝えしていきたいなと思っています。
じゃあ早速中入っていきましょうか。
最初のセクションはフィロソフィーですね。
フィロソフィーに行きましょう。
このようなライブラリをメンテナーする際、
私はインターフェースを通じて提供される微妙なインセンティブを理解しようと努めています。
もし開発者がレバーを引くことができれば、それは最終的に引かれることになります。
外国人の言い回しとか例えってちょっと難しいな。
収書度高くて難しいですね。
その開発者っていうのはチームの中で最も年長の人のある可能性もあります。
ブートキャンプから出たばっかりの人であることももちろんあります。
何十万行ものコードがあり、完成すべきタスクがあり、
正しいことを知るための必要なコンテキストが多すぎるのです。
状況とかは千差万別ですかね。
この問題は大規模なチームの力学から生まれ、どの組織にも存在します。
もしレバーが存在するならばそれは引っ張られます。
もうちょっといいんじゃないですかね。
It gets pulledって書いてるから直訳するとそうなるんでしょうね。
しかしその責任はレバーを見た開発者に全てかかっているわけではなくて、
それを提供した開発者にも責任があるのです。
良いデザインっていうのはライブラリーの消費者が成功の落とし穴に落ちる結果になる。
なる、あるって。
これはそういう記事がありますね。
Falling into the Pit of Successっていうのがありますね。
そういう記事があるのでそれを見てください。
ところですね。
成功の落とし穴っていうタイトルが結構面白いですね。
その良いデザインっていうのは果たしてただただ良いっていうかというわけではなさそうですね。
この結果を計測するには急がないで忍耐強く強い考察が必要になってくります。
一般的に言ってドキュメントに書かれていることは全て私が次のことを最大化することに決しますということですね。
大きく4つの話が挙げられていて。
1つ目ですね。デザインをUIコードに変更するのは簡単であるべきです。
いろんなチップスであったり小道具みたいなものはフィグマなどの設計システムやドキュメントに直感的マッピングできるようにしています。
コンポーネントはオーバーライドを適用しなくても正しく見えるようにしますというのが1つ目のフィロソフィーですね。
2つ目はコンポーネントというのはほとんどの場合それを消費する親に対して不透明なボックスとして動作する必要があります。
これそうですね。内部に関する詳細を漏らしていけませんし任意の構成スタイルを注入することも許されません。
データは中にマークアップは外にということですね。
なかなか面白いですね。
設計もしっかり分けるのとスコープを分けるのを意識しましょうということですね。
親がしっかり中身まで知って使うような感じの設計になっている。
要は依存度が高いのでそれは利用性が悪いよねって話だと思っています。
続いて3つ目ですね。
当たり前のことおよび簡単なこと正しいことっていうのはほとんどの場合重なり合うはずですと。
あーはいはいはいはい。
確かにそうかもしれないですね。
時間に追われていかない発車っていうのは通常最も簡単な回帰施策に手を伸ばそうとしています。
はい失礼しました。
すごく当てはまるのでなんとも言えないですね。
理想を言えば最も簡単な回帰施策は明白なものであることですと。
それは理想です。
そしてその当たり前のこととは私が開発者に最初にさせたかったことであるべきですと。
あーなるほどですね。
なるべくコンポーネントとか設計するときは明白にして分かりやすくしておきましょうということですね。
ラストのヒロソフィーとしては間違ったことをするのは少なくとも不快で最悪の場合不可能であるべきですと。
うーんなんかちょっと難しいですね言い方が。
Doing the wrong thing should be at least uncomfortable, at worst impossibleって言ってますね。
あーでも直訳するとそうなっちゃいますね。
最悪の場合そうですね。
はい、必要であれば逃げ道を用意して、しかし彼らもコンポーネントに嫌な思いをさせましょうと。
嫌な思いをさせましょうって面白い。
開発者は二度とこんなことはしなくて済むように石を開くべきだと思うはずです。
あーまあまあそういうことね。
なるほど。
これちょっとチームビルディングに近い思想かなって感じはしましたけど、なかなか面白い言い回しです。
あえて嫌な思いをさせようと。
もちろん逃げ道も用意してもいいですけど。
とはいえこのドキュメントに書かれているルールはどれも厳密なものではないですと。
それらはトレードオフの関係にあって、結局のところ私はスタイル上の柔軟性よりもデザインシステムの一貫性を優先していますと。
そのことを念頭に置きながらこのドキュメントを読み進めてくださいということでした。
ちょっと癖のありそうな人感が正直ここはありますけど。
最後に汎用的なオープンソースのコンポーネントライブラリーでは動機っていうか発端というところがやっぱり違うことになってくるので、
ここで挙げたトレードオフっていうのは必ずしも適用されるべきではないと思います。
もしかしたら適用されるかもしれないですけど、
本当にこれが必ずしも正しいというわけではないよという形ですね。
私の場合は今回作っているエルゼウォーラっていうのですね。
ライブラリーっていうのは私の会社のように見える必要があり、
コンポーネントライブラリーが私の会社のように見えることから逃れられることを望んでいませんと。
このライブラリーは我々の会社のものですよっていうふうな一つの顔として動いてもらうことを希望したいというか望んでいる感じですね。
でもやっぱり会社の名前を使って公にしているライブラリーなのでそれは素晴らしいかもしれないですね。
次のセクションです。
When everyone owns it, nobody owns itって言ってますね。
みんなが所有しているってことは逆に言うと誰も所有しなくなるってことになりますっていう意味ですね。
私の強い意見ですが、コンポーネントやライブラリーっていうのは誰かが所有しなければなりません。
所有者がいないとそのコンポーネントライブラリーっていうのはこれだけは必要だっていう単発の変更がどんどん蓄積されていて、
グループ化されたとしても設計システムの全体像を映し出すことはできません。
少なくとも一人の開発者はそのコンポーネントライブラリーのメンテナンスが仕事でなければなりません。
気持ちはわかるが僕としてはちょっともやった感じがしますね。
課題ってじゃあ明確にこの人っていうのがいなくなるとぐちゃぐちゃになったりカオスったりするのはよくある話なので、
メンテナンスチームがあったとしても最終的に温度を取る人は交代だとしても一人で決めとくってことがこの人にとっては重要だっていうふうな意見があると思いますね。
そこに関しては同意だと思います。
なるほどね。
続けていきましょうか。
例えばある製品、クリエイトエンジニアが実装しなければならない新しい設計を受けたとしましょうと。
その中には設計システムにはあるかもしれないがコンポーネントライブラリーにはまだ実装されていないコンポーネントのバリエーションが含まれているかもしれません。
この不完全性っていうのは大きな問題です。
なぜならそのエンジニアっていうのは自分たちが保守する責任のないコンポーネントライブラリに対して何かをしなければならないからです。
SNEのオーナーがいない場合、実装された開発者は解決策が通常簡単なこと、一般的には間違ったことになってしまいます。
いわゆる突貫作業になってしまいますよねみたいな話ですね。
これはよくある話だと思います。
コンポーネントを必要な分だけ更新しそれ以上のことはしない。
インターフェースに存在する様々な端末のプロプスを理解するためにしばしばコンポーネントの内部を検査しなければならないので将来の開発者の速度を低下させることになります。
まあそうねって感じですね。
必要なことだけをやってそれ以上のことはしない。
とにかく必要なときに必要だと思う人はやってくださいってことですね。
よくある話ですよね。
インターフェースに存在する端末のプロプスをどんどん理解するために中身をばーって見なきゃいけなくてそれは確かに開発者の速度を低下させるという事実ですよね。
続いてコンポーネントを更新せず、スタイルズコンポーネントなのでラップするみたいなこともあります。
このような変更がコンポーネントライブラリに戻ることはほとんどないため断片化を生み出します。
その経験は僕もすごくしましたね。
スタイルズコンポーネントは便利なんですけど、みんながみんな何か好き勝手にコンポーネント化したり、
結局似たようなやつを誰かが他の人も作ってプルリク出してて若干の名前の違いがあって結局どっち使うのみたいなのが荒れた瞬間にカオスですよね。
この話もよくある話です。
あとはゼロから別のものを実装するというところですね。
ライブラリに既に存在する可能性のあるエッジケースを考慮しないことが多い。
この辺も結構シュラパーくぐった感じの人だな。
これもすごく同意です。
このような解決策って結構複合的になりがちで、コンポーネントに変更を加える場合、既存のオーバーライドがビジュアルを壊す場所になる可能性があります。
そのために余計な注意も必要になってくるということですね。
そしてこのような状態が結構続いてしまうよということでした。
オーバーライドが増えれば増えるほど、スタイリスティックな変更を完全に安全に適応するのはリスクが高くなります。
いわゆる負の遺産というのが重なっていくということですね。
現在誰も所有していないコンポーネントライブラリがある会社で働いている人はこの痛みを感じていると確信しています。
TLDRとしてコンポーネントライブラリがクソなら誰かが職を失う必要が理想でなければおそらくクソになる。
急に親近感湧いてきたな、こういう汚い言葉を使うと。
私もあんまり出自が良くない人なので。
では続いてのセクションですね。
もうちょっと具体的な話に今後入っていきますね。
続いてですけども、ちょっとタイトル長いですね。
設計システムのバリエーションを簡潔に表現するコンポーネントインタフェースが使いやすいものである。
タイトル的にはアーコンポーネントインタフェース。
僕は英語読めないんですけど、コンシスリーですかね。
Representing the variants of the design system is easier to use。
私は設計書を読みながら全てのバリエーションをNG空間の軸のように可視化して、
各次元が一つのプロパティに相関しているかどうかを確認することにしています。
なんか数学的な人だな。
いわゆるデザインシステムのカラーだったりピッカーみたいなやつですけど、
あれのような表示の仕方をしていますね。
記事中には図があるんですけど、ボタンコンポーネント例とかをやって、
縦軸にプライマリ、セカンダリ、ターシャリーですかこれ。
横軸にディスエイブレットとかウィズアイコンみたいなのとかデフォルトみたいな感じで、
縦軸と横軸でパターンとかのバリエーションを見ているという感じですね。
もうちょっと記事入ってきます。
どの視覚的差異が独立して動作し、どの視覚的差異が独立して動作しないかを理解することが結構慣用です。
例えばボタンのタイプとディスエイブレットのプロプスっていうのは互いに独立しています。
直行しているっていうことも言えるかもしれないですね。
デザイナーとしてはできればセカンダリボタンを無効にすることはできないと提案することはないでしょう。
この2つは確かに直行していると思いますね。
タイプとディスエイブレットですね。
タイプっていうのはさっき言ったプライマリ、セカンダリなんちゃらみたいなことですけど。
で、ソースコードが若干出てきて、タイププロプスとエクスポートボタンでリアクトFCみたいな感じだって書いてますけど。
タイププロプスの方の型定義としてタイプ、今回はオプショナルですね。
このコロンでプライマリ、セカンダリ、ダーシャリと。
ディスエイブレットがブリアンで、アイコンもアイコンっていう型ですね。
が渡されるようになります。
で、この場合、それがさっきの話ですね。
逆にですね、互いに依存し合う差分っていうのは単一のプロップに統合して、
その単一のプロプスは独自の次元として動作させる必要がありますと言ってますね。
例えばオプションでラベルを持つテキストインプットでは、ラベルはオプションでツールチップを持つことができます。