31
25

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

More than 5 years have passed since last update.

BEAR.SundayAdvent Calendar 2014

Day 8

PHPコーディングポリシー

Last updated at Posted at 2014-12-07

コーディングポリシー

以下はBEAR.Sundayフレームワーク開発でのコーディング原則をまとめたものです。

ゴール

  • クリーン
  • ハイパフォーマンス
  • No BC break

(柔軟性や拡張性、テスト可能性などは"クリーン"であれば自然に含まれます)

グローバル

  • グローバル定数(define)の禁止
  • スーパーグローバル変数の参照の禁止
  • グローバルなサービスロケータの参照の禁止
  • グローバルな設定の参照の禁止(prod/devモードなど)
  • グローバルなプロパティ参照の禁止(スタティックプロパティ)
  • グローバルなメソッド利用の禁止(スタティックメソッド)

依存

 

  • 基本全てDIで
  • newの禁止 (バリューオブジェクトを除く)
  • 実クラス名を使ったオブジェクトの取得(factoryメソッドなど)の禁止
  • インターフェイスにないメソッドの利用の禁止
  • 引数がオブジェクトでパブリックプロパティを使う場合、引数のタイプヒントはインターフェイス禁止。抽象クラスを使う。
  • include_path依存の禁止
  • 抽象クラス以外でのsetterインジェクションの原則禁止。
  • composerで依存ライブラリの最小バージョンの指定のみを行う。特定のバージョンにロックしない。

継承

  • 実クラスの継承の禁止 (finalキーワード付加)
  • 子クラスから親クラスのメソッド利用の禁止
  • 抽象クラス以外でのprotectedプロパティの禁止。

トレイト

  • 原則禁止
  • アプリケーションでDIのセッターメソッドのみ

引数、返り値

  • 引数の数は4つまで(4も例外的)
  • 引数にbool値を使用することを禁止
  • スカラー値よりバリューオブジェクトを好む
  • 特定の構造を期待する連想配列を使わない
  • 返り値のmixedを避ける
  • nullのデフォルト引数を避ける
  • クロージャの引数を避ける

構造

シリアライズ

  • オブジェクトはシリアライズ可能に

メトリクス

  • 1つのクラスのメソッドの数は10以下
  • 1つのクラスのプロパティの数は15以下
  • 1メソッドの平均ライン数は10行以下

phpmdのデフォルトそのままです。

CI

OOP

  • setter、getterを使わない
  • デメテルの法則
  • 小さなクラスを好む。
  • 早期バリデーション、遅延評価
  • サービスにオブジェクトを渡さない。オブジェクトにサービスを渡す。 (XXManagerクラスの禁止)
  • DRYをあまり重視しすぎない。

原則

  • 小さく。迷ったら簡素な方を。
  • 言い訳はあとで。まずは取り組んでみる。
  • 守るのが難しく見える時、そもそも取り組み方がそれでいいのか再考する。
  • 速度を犠牲にする方向で解決することを避ける。

説明

いくつか解説します。

グローバルな設定の参照の禁止

ymlの設定ファイルを直接参照したり、Config(コンテナ)クラスを作ってその値をgetしたりしません。必要な値は依存として注入します。

$foo = Configure::read("foo") // NG
public function __construct($foo)
{
  $this->foo = $foo; // OK
}

newの禁止

バリューオブジェクトなどは除きます。主にサービスオブジェクトの場合です。

$email = new Email('exmaple@example.com'); // OK
$http = new AnnotationReader() // NG

スーパーグローバル変数の直接参照の禁止

Foo::createFromGlobals(); //NG
Foo::create($GLOBALS) // OK

内部でスーパーグローバル変数を直接参照するのではなく依存として渡します。

elseの禁止

コンディションがboolの場合でelseの状態が1つに特定される場合は構いません。(=三項式はOK)
elseを文字通り「その他」として扱うようなelseを外します。(しかしその場合はガード節を使ってelseを簡単に外すことができます)

個別の意味をもたせた連想配列を引数で使わない

例えば引数にarray $locationと渡して$location['x']$location['y']と使用するのではなく$x, $yのpublicプロパティを持ったLocationクラスを用意します。

まとめ

様々なコーディングの原則は時に「現実的ではない」「PHP的ではない」と軽視されることがあります。しかし現在のPHPはこれらのOOP原則に従ったコーディングをする事は十分に可能です。クリーンなコードはむしろ簡素で、IDEやCIツールの利用で開発速度の犠牲も最初です。

クリーンなコードは開発速度やランタイムの実行速度とのトレードオフではないと考えます。

BEAR.Sundayが提供するのは、ライブラリの集合ではなく「フレームワーク」です。実装はその時その時に変化しますが、変わることのないHTTPアプリケーションの構造を継続的な進化と共に提供したいと考えています。ソフトウエアの設計原則に従う事はそのフレームワークを壊すことなく(後方互換性を犠牲にすることなく)進化を続けることを可能にするための土台です。

参考

31
25
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
31
25

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?