Wzorzec projektowy Registry w PHP

Registry to wzorzec projektowy, który ma za zadanie przechowywać i udostępniać dane w obrębie aplikacji. Implementacja wzorca zastępuje globalny zasięg wartości zarejestrowanych w przestrzeni klasy. Różnicą globalnego zasięgu zmiennych oraz wartości ujętych w Registry jest to, że można je ściśle kontrolować (dostęp w aplikacji itd.). W tej publikacji przedstawię jedną z najprostszego wykorzystania wzorca Registry.

Głównym założeniem Registry jest globalny zasięg (pomijając już zabezpieczenia dostępowe, którymi się nie zajmujemy). Język PHP od wersji 5 obsługuje statyczne static wywołania metod klas, czyniąc tym samym ich globalny zasięg wraz z połączeniem ze słowem kluczowym public. Dla wygody – nie trzeba tworzyć instancji klasy, więc wywołanie jest bardzo proste i nie zajmuje dużo miejsca w naszym kodzie.

Podstawowymi funkcjonalnościami Registry będzie:

  • dodawanie i usuwanie,
  • pobieranie

…zmiennych z rejestru. Pojęcie zmienna jest bardzo względne. Przechowywać w rejestrze możemy praktycznie wszystkie typy zmiennych dostępnych w PHP, włączając w to typ resource (zasoby). Registry to nic innego, jak przechowywanie zmiennych w przestrzeni jednej klasy, więc nie mamy wobec tego żadnych ograniczeń.

Zajmiemy się teraz bardziej rozbudowanym przykładem wzorca. Wykonamy następujące operacje:

  1. Nowa klasa RegistryAdvenced będzie dziedziczyła z RegistrySimple na potrzeby metody Registry().
  2. Zaimplementujemy interfejsy:
  3. Dodamy prywatny konstruktor, skorzystamy ze wzorca Singleton.

Gotowy kod klasy RegistryAdvenced.

Interpretacja i rozwijanie swojego wzorca Registry jest szeroka, można na przykład zastosowac przestrzenie rejestrów, tj. tworzyć wiele rejestrów na podstawie ich instancji. Ile programistów, tyle pomysłów, ale zasada działania nie zmienia się. Zainteresowanych zapraszam do manuala, jak problem został rozwiązany w Zend_Registry.



5 Responses to “Wzorzec projektowy Registry w PHP”

  1. tiraeth says:

    Po pierwsze, namieszałeś. Nie powinieneś łączyć wzorca Registry (który jest wzorcem-kontenerem) ze wzorcami czynnościowymi (do których należy Iterator). Nie ma to żadnego sensu, bo Registry to zwykłe przeimplementowanie dostępu do zmiennych globalnych.

    Po drugie, ponownie, jak w przypadku wpisu o Singletonie, rozwodzisz się nad rozlanym mlekiem. Każdy programista, korzystający z dobrodziejstw obiektówki zna te podstawowe wzorce. Notabene, wzorzec Rejestru, jest IMHO prymitywny. Oczywiście, bardzo usprawnia pracę, ale nie jest czymś nad zwyczajnym, o czym wypada pisać.

    Po trzecie, jaki sens ma rozszerzanie Registry o Singleton?

    Po czwarte, skąd ta nazwa Registry? To, co tutaj pokazałeś to przecież wzorzec Property…

  2. Athlan says:

    Rozszerzenie przykładu z singletonem jest potrzebne tylko po to, aby uzyskać dostęp do kontenera z poziomu tablicy, czy iteratora w pętli. To taki “bajer”, gdyby komuś przyszło do głowy zaglądać do kontenera, tak jak tu (Zend_Registry), co jest wg mnie absolutnie niedopuszczalne. Jeżeli wiemy, że dodaliśmy do rejestru jakiś obiekt/wartość, to możemy ją w każdej chwili wyciągnąć.

    Property jest ładnie opisane w phpedii, kod w definicji jest praktycznie identyczny z moim (po co tam singleton?). ZF nazywa wzorzec Property zamiennie z Registry:

    The registry is a container for storing objects and values in the application space. By storing the value in the registry, the same object is always available throughout your application. This mechanism is an alternative to using global storage.

    Czyli to o czym piszę.

    The typical usage of the registry is through static methods in the Zend_Registry class. [...]

    Statyczne wywołania jak w RegistrySimple (jestem tego zwolennikiem – i tylko tego).

    [...]Alternatively, the class is an array object, so you can access elements stored within it with a convenient array-like interface.

    Ale można przeglądać Registry (czego nie trawię, ale pokazuję taką możliwość).

    Czyli warto było jednak napisać.

  3. Raven says:

    Opera 9.6 @ Linux. Rozjeżdża się Twój komentarz Athlanie.

  4. tiraeth says:

    A ja nadal twierdzę, że to, co napisałeś, to nie Registry, tylko Property. Popatrz nawet na Zend_Registry.

    Nie interesuje mnie, że Zend używa zamiennie Registry i Property. Przypomnę Twoją notkę:

    Registry to nic innego jak zbiór instancji klas w klasie. Mapa registry to zapisywanie instancji klasy pod pewnym identyfikatorem, po czym wybieranie DOKſADNIE takiej samej instacji jaka została zapisana w dowolnym momencie działania aplikacji.

    Rozumiem, że Iterator użyłeś, by wykluczyć dostęp do kontenera danych. Ale chwila, nie po to tworzy się Property, żeby mieć dostęp do wszystkich tam umieszczonych danych? Jaki byłby sens? Przecież wyłuskując dane, można spokojnie utworzyć nowy obiekt iteratora.

    I powtórzę jeszcze raz, namieszałeś w tym wpisie. Łączenie kilku różnych wzorców w jedną klasę jest absurdem. Nie widzę żadnej użyteczności z doimplementowania Iteratora, ArrayAccess, Countable i Serializable.

  5. gnysek says:

    @tiraeth – dla Ciebie oczywiste, ale może nie każdy posiada Twoją wiedzę?

Leave a Reply