2

データベースへの呼び出し回数が減ったためにアプリケーションのパフォーマンスが向上するように、ブラウザーごとに1つのデータベース接続のみが作成されるようにするはずのこのコードに出くわしました。

私はこれがどのように保証されるかという論理を理解していると信じていますが、これについての私の理解が正しく完全であることを確認する必要があります。なので、説明の詳細を教えてください。

また、データベース接続/呼び出しを行う場合、これよりも優れた方法はありますか?

class Database {
    private static $dsn = 'mysql:host=localhost;dbname=mydatabase';
    private static $username = 'dbuser';
    private static $password = 'dbpass';
    private static $db;

    private function __construct() {}

    public static function getDB ()
    {
        if (!isset(self::$db)) {
            try {
                self::$db = new PDO(self::$dsn,
                                 self::$username,
                                 self::$password);
            } catch (PDOException $e) {
                $error_message = $e->getMessage();
                include('../errors/database_error.php');
                exit();
            }
        }
        return self::$db;
    }
}
4

1 に答える 1

4

@ raina77owがコメントで指摘しているように、これはシングルトンパターンと呼ばれます。ここにいくつかの説明があります:

シングルトンであることのポイントは、呼び出し元のコードで複数のを作成できないことです$db。また、コード内のどこからでも作成されたにグローバルアクセスを提供します$db

静的クラス変数は、クラスごとに1つのインスタンスとして存在します。$dbしたがって、このクラスをオブジェクトとしてインスタンス化できたとしても、複数の接続を作成することはできません。

クラスをオブジェクトとしてインスタンス化する目的はないため(これは、クラスにオブジェクトインスタンスごとに存在する非静的変数がある場合にのみ役立ちます)、クラスコンストラクターは必要ありません。呼び出し元のコードが呼び出されないようにするためnewに、コンストラクターはプライベートになっています。(厳密に言えば、クラス変数のみが静的であるため、そうしても害はありません。)

__clone実装には魔法と__wakeupメソッドが欠けていることに注意してください。これらがなくても、シングルトンのクローンを作成したり、シリアル化を解除したりできます。したがって、技術的には、シングルトンは特異点を適切に適用していません。

ここにいくつかの追加の考えがあります:

  • シングルトンクラス(または静的に使用されるクラス)は、自動テストに統合するのが難しいことで有名です。それらは静的であるため、一度初期化することができ、テストスイートの期間中それらの状態を保持します。new非静的クラスを使用する場合は、新しいオブジェクトをインスタンス化するために使用するたびに、それらを再初期化できます。

  • 別の設計は、レジストリパターンと、非静的dbインスタンスを作成してレジストリに格納するアプリケーション用のある種のブートストラップを使用することです。

  • finalシングルトンを使用する場合は、サブクラスが動作をオーバーライドしたり、プライベートデータにアクセスしたりできないように、シングルトンクラスを宣言することをお勧めします。

  • データベースのクレデンシャルは、クラス定義でプライベートデータとしてハードコーディングされています。私はそれをしません。Apache PHPハンドラーが誤って構成された場合、ユーザーはPHPソースコードを見ることができ、データベースパスワードを入手できます。データベース接続パラメーターを構成ファイルに入れ、構成ファイルをApacheドキュメントルートの外部に保存します。

  • データベース接続エラーメッセージを逐語的に出力すると、ユーザーに情報を明らかにすることができます。PDOエラーメッセージをログに記録しますが、「問題が発生しています。サイト管理者に通知してください」などのわかりやすいメッセージをユーザーに送信します。

  • ?>クラス定義ファイルでPHPブロックを終了する必要はありません。これにより、閉じた後にスペースまたは改行が作成され、アプリケーションの空白になり、レイアウトが失われる可能性があります。これらのタイプのエラーは、追跡するのが面倒です。

于 2012-11-21T17:54:35.597 に答える