Le Singleton, permet d'avoir une classe qui sera instanciée qu'une seule fois tout au long de notre application. Par exemple, dans le cadre de notre application nous auront une seule et unique configuration. On va donc chercher à instancier cette objet une seule fois pour pouvoir ensuite récupérer l'instance à tout moment de notre application.

Pourquoi pas une classe statique ?

On peut tout de suite se poser la question de l'utilité d'un tel design pattern lorsque l'on a la possibilité de créer des attributs et des méthodes statiques. Il y a plusieurs problèmes à l'utilisation du statique :

  • On ne dispose d'aucun constructeur pour y placer la logique d'initialisation
  • Le code sera plus difficilement testable par la suite
  • Lhéritage est un véritable enfer

Comment marche le Singleton

Pour créer un singleton nous allons devoir utiliser plusieurs choses

  • Un attribut statique qui conservera l'instance unique de notre classe
  • Une méthode statique qui permet d'instancier l'objet ou de récupérer l'instance unique déjà créée
  • Un constructeur privé si on souhaite empêcher l'instanciation en dehors de la classe

Un petit exemple concret avec une classe de configuration.

<?php

namespace Core;

class Config
{

    private $settings = [];
    private static $_instance; // L'attribut qui stockera l'instance unique

    /**
    * La méthode statique qui permet d'instancier ou de récupérer l'instance unique
    **/
    public static function getInstance($file)
    {
        if (is_null(self::$_instance)) {
            self::$_instance = new Config($file);
        }
        return self::$_instance;
    }

    /**
    * Le constrcuteur avec sa logique est privé pour émpêcher l'instanciation en dehors de la classe
    **/
    private function __construct($file)
    {
        $this->settings = require($file);
    }

    /**
    *  Permet d'obtenir la valeur de la configuration
    *  @param $key string clef à récupérer
    *  @return mixed
    **/
    public function get($key)
    {
        if (!isset($this->settings[$key])) {
            return null;
        }
        return $this->settings[$key];
    }

}