やあ。HHVMの深淵へようこそ。Hackのコアを知り尽くした者として、君に「真の型安全性」の入り口を案内しよう。
多くの開発者がPHPからHackへ移行する際、最も陥りやすい罠がある。それは「プリミティブな型(stringやint)に依存しすぎる」という甘えだ。
`string`型は便利だが、それは単なる「文字の羅列」に過ぎない。君が扱いたいのは「メールアドレス」であり、「ユーザーID」であり、「注文番号」であるはずだ。これらをすべて`string`で管理するのは、安全装置を外した拳銃を振り回しているのと同じだよ。
今日は、Hackの真骨頂である「Newtypeパターン」を使って、君のドメインモデルを鉄壁にする方法を伝授しよう。
—
1. なぜ「型」にこだわるのか?(静的解析の重み)
PHPでは、関数に「ただのID」を渡すとき、誤って「名前」を渡しても実行時までエラーは出ない。しかし、Hackでは違う。型チェッカー(`hh_client`)が、コンパイル(厳密には型チェック)の段階で、君のコードの矛盾をすべて暴き出す。
「Newtype(不透明な型エイリアス)」とは、型チェッカーに対して「これは内部的にはstringだが、君たち開発者は別のものとして扱え」と命令する呪文のようなものだ。
2. Newtypeパターンの実装:型に魂を宿す
まずは、単なる`string`を「意味のある型」に変えてみよう。
namespace App;
// `newtype` を使うと、外部からは中身が見えない「不透明な型」になる
// これにより、UserIdをintや他のstringと混同することが物理的に不可能になる
newtype UserId = string;
class User {
public function __construct(private UserId $id) {}
public function getId(): UserId {
return $this->id;
}
}
function processUser(UserId $id): void {
// ここでは $id が UserId であることが保証されている
}
ここが重要:型の透明度
- `type`:単なる別名。`type UserId = string` と書くと、`UserId`はどこでも`string`として扱えてしまう。
- `newtype`:「不透明」。定義したファイルの外からは、これが`string`なのか何なのかを知ることはできない。これがドメイン駆動設計における「カプセル化」の究極形だ。
3. 陥りやすい罠と解決策
初学者がよくやるミスは、「不透明ゆえに、どうやって値を生成すればいいかわからない」というものだ。
❌ 間違った例
function createId(): UserId {
return “user_123”; // エラー!
// HHVM: “string” は “UserId” として扱えません
}
✅ 正解:コンストラクタ(構築関数)を用意する
`newtype`を定義したファイル内であれば、中身が`string`であることを知っている。だから、そのファイル内に「型を生成する関数」を置くのが定石だ。
// User.hack 内
newtype UserId = string;
// このファイル内でのみ、stringからUserIdを作れるようにする
function userIdFromString(string $val): UserId {
return $val;
}
これで、他のモジュールからは「`userIdFromString`を通さない限り、`UserId`を作ることはできない」という強力なバリデーションルールが完成する。
4. ドメインモデルの強化:視覚化
君のコードは、プリミティブな海から、意味のある構造体へと進化する。
- Before (PHP的)
`func(string $id, string $email, string $address)`
→ どれがどれだかわからない。引数の順序を間違えてもエラーにならない。
- After (Hack的)
`func(UserId $id, Email $email, Address $address)`
→ 型チェッカーが「君、Emailの場所にUserIdを突っ込もうとしてるよ」と即座に教えてくれる。
—
先輩からのアドバイス:ここをクリアすれば「マスター」だ
Hackの型システムは、君の自由を奪うものではない。「将来の自分やチームメンバーが、コードの意図を誤解してバグを埋め込むリスク」から解放してくれる最強のツールなんだ。
1. まずは「ID」から切り出せ: `UserId`, `OrderId`, `ProductId`。これらを`newtype`にするだけで、コードの可読性は飛躍的に上がる。
2. HSL (Hack Standard Library) を活用せよ: HSLは型安全に特化したライブラリだ。プリミティブな関数を使う前に、HSLに同等の関数がないか探してみよう。
Hackは、厳格な静的型検査と、HHVMの驚異的な実行速度が融合した、極めて洗練された言語だ。一度この「型に守られた安心感」を覚えたら、もうPHPの緩い世界には戻れないはずだよ。
さあ、君のドメインモデルに魂(型)を吹き込んでみてくれ。何か詰まったら、いつでも聞いてほしい。コードの裏側まで、すべて教えよう。