← 記事一覧

デザインハーネスとは

UIの大半をAIが書く時代に、デザインシステムが静かに壊れるのを防ぐ、小さくて地味な仕組みの話。なぜ地味に見える部分こそが効くのか。

約7分

デザインシステムは、静かに壊れる

見覚えがあるはずです。エージェントが color.primary トークンを使わず、#3b82f6 を直接書き込みます。レビューで気づいて直し、次へ進みます。翌週、同じ値が別のファイルで戻ってきます。誰も雑なわけではありません。それぞれのエージェントが、直前の判断を知らないまま、単独で「良さそうなもの」を作っているだけです。そのゆっくりとした乖離には名前があります——デザイントークン・ドリフトです。

そして積み重なります。3つのセッションがそれぞれボタンを発明し、同じボタンが3種類できます。スペーシングが2ピクセルずれます。diffはGitに残りますが、その背後にあった理由は残りません。6週間後に「なぜこのpaddingは14pxなの?」と聞かれ、正直な答えは「誰も分からない」になります。

これはAIの失敗ではありません。文脈が欠けているという失敗です。モデルは、このプロジェクトで「一貫している」とは何を意味するのかを、作業中に実際に読める形で一度も渡されていません。私たちはその欠けている成果物を デザインハーネス と呼びます。ここから先は、それが何であり、なぜ地味な部分が効くのか、という話です。

デザインハーネスとは何か

デザインハーネスとは、トークン・コンポーネント仕様・品質ゲートを、AIエージェントと人間の双方が読める単一のソースにまとめたものです。

これが必要なのは、AIエージェントが人間のレビュー速度を超える速さと規模でUIを書くようになり、人の記憶や散文ドキュメントにしか存在しない設計意図では、その速度に耐えられないからです。従来のデザインシステムが人間向けのドキュメントであるのに対し、ハーネスは同じ意図を、人間もエージェントもその中で実装し、そこからの逸脱(ドリフト)を自動で捉えられる形で表現したものです。

この言葉は馬具から借りています。ハーネスは馬を遅くするためのものではありません。乗り手が、大きな力と争わずにその向きを定めるための仕組みです。手綱は檻ではありません。AI駆動開発では、力も速さも本物です。欠けていたのは、その力と、あなたの意図とを結ぶ、軽くて意識的な接点だった。ハーネスはその接点です——口うるさい規則集ではなく、エージェントがUIを一行書く前に参照する、共有された契約です。一度書けば全員が読みます。コンポーネントを生成するエージェントも、PRをレビューする同僚も、ドリフトを指摘する検査も、同じ一つのソースを読みます。単一ソース・複数の読み手。

一つの機械可読なソースを、人間とエージェントの双方が読みます。ゲートが、後から発見されるのを待たずにドリフトを捉えます。

3つの構成要素と、地味なディテールがなぜ効くか

ハーネスには3つの可動部があります。

  1. トークン——語彙。色・スペーシング・角丸・書体を、リテラルではなく名前付きの値で表します。#0a0a0a ではなく color.accent。その参照が壊れると、トークン・ドリフトになります。
  2. コンポーネント仕様——文法。Buttonとは何か、そのバリアントと状態、使ってよいトークン、破ってはいけない規則。書き留めれば、それがコンポーネント契約です。
  3. 品質ゲート——校正者。生のhex禁止、スケール外のスペーシング禁止といった機械判定可能な規則。人間向けドキュメントと同じ定義から生成されるので、読む規則と走る規則が食い違うことがありません。

重さを支える2つの判断

静かな仕事の大半は、2つの設計判断が担っています。1つ目は 安定ID。すべてのトークン・コンポーネント・ゲートは、名前が変わっても変わらない識別子を持ちます。color.brandcolor.accent に改名しても、あらゆる参照・記録された判断・過去のドリフトが紐付いたまま残ります。名前で紐付ける仕組みは名前が動いた瞬間に壊れます。IDで紐付ける仕組みは覚えています。

2つ目は 二層記録 です。「何が・どのファイルで変わったか」という事実を、「なぜ変えたか・他に何を検討したか」という文脈とは別に保ちます。事実層は決定論的で、モデルが説明を覚えているかに依存しません。文脈層は、理由があるときにそれを添えます。分けておけば、説明が欠けても変更の記録は失われません。一緒にすれば、雑なコミット一つで両方が消えます。

デザインツールでいいのでは?

多くのチームはデザインツールでデザインを管理していて、ハーネスはその競合ではありません。ただ、デザインファイルは人が眺めるために描かれたもので、エージェントが深夜2時に button.tsx を編集しながら読むために構造化されてはいません。エージェントが必要とする情報——正確なトークン、破ってはいけない規則、過去の判断がそう決まった理由——は、キャンバスが運ぶようにはできていません。

だからハーネスはゼロから、テキストで、あなたのリポジトリの中で始めます。Harnd が、エージェントが既に作ったアプリを読んでトークンとコンポーネントを抽出します——デザインツールを前提とせず、アカウントも要らず——そしてエージェントがコンポーネントに触れる前に、必要な仕様だけを数百トークンで引ける成果物を生みます。すでにデザインツールを使っているなら、それで構いません。ハーネスは機械可読な契約として隣に共存します。使っていなくても、失うものはありません。ハーネスは最初からそれを必要としていません。

私たちはHarnd自身のハーネスの下でHarndを作っている

ここにあるものはすべてドッグフーディングです。HarndはHarnd自身のハーネスの下で作られています。この記事の色は私たち自身のソースの中のトークンであり、コンポーネントは仕様化され、私たちが出荷しているのと同じゲートが私たち自身のPRに対して走ります。上の考え方が抽象的に聞こえたなら、そうではありません——それは、このページそのものが書かれた際の規則です。

もし、このページ冒頭の問題が少しでも他人事に思えなかったなら、それがこの記事の狙いです。まず最初に壊れる2つの部分から始めてほしい——デザイントークン・ドリフトコンポーネント契約——あるいは早期アクセスに登録して、エージェントが既に作ったアプリにHarndを向けてください。

エージェントがUIを書いても、デザインの一貫性を保つ。