Wybór wzorca dostępu do danych
2.5.x ✅ 4.0.x ✅
Jaki wzorzec powinienem używać? To drzewo decyzyjne pomaga wybrać między bezpośrednimi handlerami, wzorcem Repository, warstwą usług i CQRS.
Szybkie drzewo decyzyjne
Dział zatytułowany „Szybkie drzewo decyzyjne”flowchart TD START([Zacznij tutaj]) --> Q1{Jaka jest złożoność<br/>twojego modułu?}
Q1 -->|Proste CRUD<br/>1-3 jednostki| Q2{Potrzebujesz testowania<br/>lub mockowania?} Q1 -->|Umiarkowane<br/>4-10 jednostek| Q3{Wiele źródeł<br/>danych?} Q1 -->|Złożone<br/>10+ jednostek| Q4{Wysoki ruch lub<br/>asymetria odczyt/zapis?}
Q2 -->|Nie| HANDLER[✅ Bezpośredni Handler] Q2 -->|Tak| REPO[✅ Wzorzec Repository]
Q3 -->|Nie, tylko DB| REPO Q3 -->|Tak, API/cache| SERVICE[✅ Warstwa usług]
Q4 -->|Nie| SERVICE Q4 -->|Tak, potrzebujesz<br/>oddzielnego skalowania| CQRS[✅ Wzorzec CQRS]
HANDLER --> DONE([Wybierz wzorzec]) REPO --> DONE SERVICE --> DONE CQRS --> DONE
style HANDLER fill:#c8e6c9,stroke:#2e7d32 style REPO fill:#bbdefb,stroke:#1565c0 style SERVICE fill:#fff9c4,stroke:#f9a825 style CQRS fill:#ffcdd2,stroke:#c62828Porównanie wzorców
Dział zatytułowany „Porównanie wzorców”| Kryteria | Bezpośredni Handler | Repository | Warstwa usług | CQRS |
|---|---|---|---|---|
| Złożoność | ⭐ | ⭐⭐ | ⭐⭐⭐ | ⭐⭐⭐⭐⭐ |
| Testowość | ❌ Trudne | ✅ Dobre | ✅ Świetne | ✅ Świetne |
| Elastyczność | ❌ Niska | ✅ Średnia | ✅ Wysoka | ✅ Bardzo wysoka |
| XOOPS 2.5.x | ✅ Natywne | ✅ Działa | ✅ Działa | ⚠️ Złożone |
| XOOPS 4.0 | ⚠️ Przestarzałe | ✅ Zalecane | ✅ Zalecane | ✅ Do skalowania |
| Rozmiar zespołu | 1 dev | 1-3 devs | 2-5 devs | 5+ devs |
| Konserwacja | ❌ Wyższa | ✅ Umiarkowana | ✅ Niższa | ⚠️ Wymaga doświadczenia |
Kiedy używać każdego wzorca
Dział zatytułowany „Kiedy używać każdego wzorca”✅ Bezpośredni Handler (XoopsPersistableObjectHandler)
Dział zatytułowany „✅ Bezpośredni Handler (XoopsPersistableObjectHandler)”Najlepszy dla: Prostych modułów, szybkich prototypów, nauki XOOPS
// Prosty i bezpośredni - dobry dla małych modułów$handler = xoops_getModuleHandler('article', 'news');$articles = $handler->getObjects(new Criteria('status', 1));Wybierz to gdy:
- Budujesz prosty moduł z 1-3 tabelami bazy danych
- Tworzysz szybki prototyp
- Jesteś jedynym deweloperem i nie potrzebujesz testów
- Moduł nie będzie się znacznie rozwijać
Ograniczenia:
- Trudne do testowania jednostkowego (zależność globalna)
- Ścisłe sprzężenie do warstwy bazy danych XOOPS
- Logika biznesowa ma tendencję do wyciekania do kontrolerów
✅ Wzorzec Repository
Dział zatytułowany „✅ Wzorzec Repository”Najlepszy dla: Większości modułów, zespołów chcących testowości
// Abstrakcja pozwala na mockowanie do testówinterface ArticleRepositoryInterface { public function findPublished(): array; public function save(Article $article): void;}
class XoopsArticleRepository implements ArticleRepositoryInterface { private $handler;
public function __construct() { $this->handler = xoops_getModuleHandler('article', 'news'); }
public function findPublished(): array { return $this->handler->getObjects(new Criteria('status', 1)); }}Wybierz to gdy:
- Chcesz pisać testy jednostkowe
- Możesz zmienić źródła danych później (DB → API)
- Pracujesz z 2+ deweloperami
- Budujesz moduły do dystrybucji
Ścieżka ulepszenia: To jest zalecany wzorzec dla przygotowania XOOPS 4.0.
✅ Warstwa usług
Dział zatytułowany „✅ Warstwa usług”Najlepszy dla: Modułów ze złożoną logiką biznesową
// Usługa koordynuje wiele repozytoriów i zawiera reguły biznesoweclass ArticlePublicationService { public function __construct( private ArticleRepositoryInterface $articles, private NotificationServiceInterface $notifications, private CacheInterface $cache ) {}
public function publish(int $articleId): void { $article = $this->articles->find($articleId); $article->setStatus('published'); $article->setPublishedAt(new DateTime());
$this->articles->save($article); $this->notifications->notifySubscribers($article); $this->cache->invalidate("article:{$articleId}"); }}Wybierz to gdy:
- Operacje obejmują wiele źródeł danych
- Reguły biznesowe są złożone
- Potrzebujesz zarządzania transakcjami
- Wiele części aplikacji robi to samo
Ścieżka ulepszenia: Połącz z Repository dla solidnej architektury.
⚠️ CQRS (Command Query Responsibility Segregation)
Dział zatytułowany „⚠️ CQRS (Command Query Responsibility Segregation)”Najlepszy dla: Modułów dużej skali z asymetrią odczyt/zapis
// Polecenia modyfikują stanclass PublishArticleCommand { public function __construct( public readonly int $articleId, public readonly int $publisherId ) {}}
// Zapytania czytają stan (mogą używać denormalizowanych modeli odczytu)class GetPublishedArticlesQuery { public function __construct( public readonly int $limit = 10 ) {}}Wybierz to gdy:
- Odczyty znacznie przewyższają zapisy (100:1 lub więcej)
- Potrzebujesz innego skalowania dla odczytów vs zapisów
- Złożone wymagania raportowania/analityki
- Event sourcing byłby korzystny dla Twojej domeny
Ostrzeżenie: CQRS dodaje znaczną złożoność. Większość modułów XOOPS tego nie potrzebuje.
Zalecana ścieżka ulepszenia
Dział zatytułowany „Zalecana ścieżka ulepszenia”flowchart LR H0["Bezpośredni Handler<br/>(XOOPS 2.5.x dzisiaj)"] R["Wzorzec Repository<br/>(Zalecany następny krok)"] S["+ Warstwa usług<br/>(Gdy złożoność rośnie)"] C["+ CQRS<br/>(Tylko jeśli skalowanie wymaga)"]
H0 -->|"Krok 1"| R R -->|"Krok 2"| S S -->|"Krok 3<br/>(rzadko)"| C
style H0 fill:#ffcdd2 style R fill:#c8e6c9 style S fill:#bbdefb style C fill:#fff9c4Krok 1: Zawiń handlery w repozytorium (2-4 godziny)
Dział zatytułowany „Krok 1: Zawiń handlery w repozytorium (2-4 godziny)”- Utwórz interfejs dla twoich potrzeb dostępu do danych
- Zaimplementuj go korzystając z istniejącego handlera
- Wstrzyknij repozytorium zamiast wywoływać
xoops_getModuleHandler()bezpośrednio
Krok 2: Dodaj warstwę usług gdy potrzeba (1-2 dni)
Dział zatytułowany „Krok 2: Dodaj warstwę usług gdy potrzeba (1-2 dni)”- Gdy logika biznesowa pojawia się w kontrolerach, wyciągnij do usługi
- Usługa używa repozytoriów, nie handlerów bezpośrednio
- Kontrolery stają się cienkie (trasa → usługa → odpowiedź)
Krok 3: Rozważ CQRS tylko jeśli (rzadko)
Dział zatytułowany „Krok 3: Rozważ CQRS tylko jeśli (rzadko)”- Masz miliony odczytów dziennie
- Modele odczytu i zapisu są znacznie różne
- Potrzebujesz event sourcingu do dziennika audytu
- Masz zespół doświadczony w CQRS
Karta szybkiego odniesienia
Dział zatytułowany „Karta szybkiego odniesienia”| Pytanie | Odpowiedź |
|---|---|
| ”Potrzebuję tylko zapisać/załadować dane” | Bezpośredni Handler |
| ”Chcę pisać testy” | Wzorzec Repository |
| ”Mam złożone reguły biznesowe” | Warstwa usług |
| ”Potrzebuję skalować odczyty oddzielnie” | CQRS |
| ”Przygotowuję się na XOOPS 4.0” | Repository + Warstwa usług |
Powiązana dokumentacja
Dział zatytułowany „Powiązana dokumentacja”- Przewodnik wzorca Repository
- Przewodnik wzorca Service Layer
- Przewodnik wzorca CQRS (zaawansowany)
- Umowa trybu hybrydowego
#patterns #data-access #decision-tree #best-practices #xoops