feat(domain): Domain\Scontainers + Domain\Banners repositories z wrapper delegation
Phase 3 complete: - ScontainersRepository: containerDetails, containerSave, containerDelete, scontainerByLang - BannersRepository: bannerDetails, bannerSave, bannerDelete, activeBanners, mainBanner - 4 legacy factories converted to thin wrappers delegating to Domain repos Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
This commit is contained in:
198
.paul/phases/03-domain-scontainers-banners/03-01-PLAN.md
Normal file
198
.paul/phases/03-domain-scontainers-banners/03-01-PLAN.md
Normal file
@@ -0,0 +1,198 @@
|
||||
---
|
||||
phase: 03-domain-scontainers-banners
|
||||
plan: 01
|
||||
type: execute
|
||||
wave: 1
|
||||
depends_on: []
|
||||
files_modified:
|
||||
- autoload/Domain/Scontainers/ScontainersRepository.php
|
||||
- autoload/Domain/Banners/BannersRepository.php
|
||||
- autoload/admin/factory/class.Scontainers.php
|
||||
- autoload/admin/factory/class.Banners.php
|
||||
- autoload/front/factory/class.Scontainers.php
|
||||
- autoload/front/factory/class.Banners.php
|
||||
autonomous: true
|
||||
delegation: auto
|
||||
---
|
||||
|
||||
<objective>
|
||||
## Goal
|
||||
Create Domain\Scontainers\ScontainersRepository and Domain\Banners\BannersRepository, then convert legacy factory classes to wrapper delegation.
|
||||
|
||||
## Purpose
|
||||
Continue DDD refactoring — migrate Scontainers and Banners data access from static factory methods (global $mdb) to injected-dependency Domain repositories. Establishes wrapper delegation pattern for the first time in the project.
|
||||
|
||||
## Output
|
||||
- 2 new Domain repository files
|
||||
- 4 legacy factory files converted to wrappers
|
||||
</objective>
|
||||
|
||||
<context>
|
||||
## Project Context
|
||||
@.paul/PROJECT.md
|
||||
@.paul/ROADMAP.md
|
||||
@.paul/STATE.md
|
||||
|
||||
## Source Files
|
||||
@autoload/admin/factory/class.Scontainers.php
|
||||
@autoload/admin/factory/class.Banners.php
|
||||
@autoload/front/factory/class.Scontainers.php
|
||||
@autoload/front/factory/class.Banners.php
|
||||
@autoload/Domain/Languages/LanguagesRepository.php (pattern reference)
|
||||
</context>
|
||||
|
||||
<acceptance_criteria>
|
||||
|
||||
## AC-1: ScontainersRepository exists with all methods
|
||||
```gherkin
|
||||
Given the autoloader is configured for Domain\ namespace
|
||||
When ScontainersRepository is instantiated with $db (Medoo)
|
||||
Then it provides containerDetails(), containerSave(), containerDelete(), scontainerByLang() methods
|
||||
And all methods use $this->db instead of global $mdb
|
||||
```
|
||||
|
||||
## AC-2: BannersRepository exists with all methods
|
||||
```gherkin
|
||||
Given the autoloader is configured for Domain\ namespace
|
||||
When BannersRepository is instantiated with $db (Medoo)
|
||||
Then it provides bannerDetails(), bannerSave(), bannerDelete(), activeBanners(), mainBanner() methods
|
||||
And all methods use $this->db instead of global $mdb
|
||||
```
|
||||
|
||||
## AC-3: Legacy admin factories delegate to repositories
|
||||
```gherkin
|
||||
Given admin\factory\Scontainers and admin\factory\Banners exist
|
||||
When their static methods are called (e.g. container_save(), banner_delete())
|
||||
Then they instantiate the Domain repository with global $mdb
|
||||
And delegate the call to the corresponding repository method
|
||||
And return the same result as before
|
||||
```
|
||||
|
||||
## AC-4: Legacy front factories delegate to repositories
|
||||
```gherkin
|
||||
Given front\factory\Scontainers and front\factory\Banners exist
|
||||
When their static methods are called (e.g. scontainer_details(), banners())
|
||||
Then they delegate to the Domain repository
|
||||
And caching behavior is preserved (Cache::fetch/store in repository)
|
||||
```
|
||||
|
||||
</acceptance_criteria>
|
||||
|
||||
<tasks>
|
||||
|
||||
<task type="auto">
|
||||
<name>Task 1: Create ScontainersRepository and BannersRepository</name>
|
||||
<files>autoload/Domain/Scontainers/ScontainersRepository.php, autoload/Domain/Banners/BannersRepository.php</files>
|
||||
<action>
|
||||
Create Domain\Scontainers\ScontainersRepository following LanguagesRepository pattern:
|
||||
- namespace Domain\Scontainers
|
||||
- Constructor: __construct($db) storing Medoo instance
|
||||
- containerDetails($containerId): get from pp_scontainers + pp_scontainers_langs (all langs)
|
||||
- containerSave($containerId, $title, $text, $status, $showTitle, $src, $html): insert/update pp_scontainers + pp_scontainers_langs with multi-language support. Handle single-lang vs multi-lang arrays exactly as current factory does. Call \S::delete_cache() after.
|
||||
- containerDelete($containerId): delete from pp_scontainers, call \S::delete_cache()
|
||||
- scontainerByLang($scontainerId, $langId): get container + single lang translation, use \Shared\Cache\CacheHandler::fetch/store (migrate from \Cache:: to \Shared\Cache\CacheHandler::)
|
||||
|
||||
Create Domain\Banners\BannersRepository following same pattern:
|
||||
- namespace Domain\Banners
|
||||
- Constructor: __construct($db)
|
||||
- bannerDetails($bannerId): get from pp_banners + pp_banners_langs (all langs)
|
||||
- bannerSave($bannerId, $name, $status, $dateStart, $dateEnd, $homePage, $src, $url, $html, $text): insert/update pp_banners + pp_banners_langs. Handle single/multi lang arrays. Call \S::delete_cache().
|
||||
- bannerDelete($bannerId): delete from pp_banners, call \S::delete_cache()
|
||||
- activeBanners($langId): active non-homepage banners with date filtering, use \Shared\Cache\CacheHandler for caching
|
||||
- mainBanner($langId): single active homepage banner with date filtering, cached
|
||||
|
||||
IMPORTANT:
|
||||
- PHP < 8.0 compatible (no match, no named args, no union types, no str_contains)
|
||||
- Use $this->db->query() for complex SQL (date filtering in Banners) — keep raw SQL identical to current factory
|
||||
- Multi-language save pattern: query pp_langs for active languages, loop and insert translations
|
||||
- Status/checkbox conversion ('on' → 1, else 0) stays in repository methods
|
||||
</action>
|
||||
<verify>php -l autoload/Domain/Scontainers/ScontainersRepository.php && php -l autoload/Domain/Banners/BannersRepository.php</verify>
|
||||
<done>AC-1 and AC-2 satisfied: Both repositories exist with all methods, use injected $db</done>
|
||||
</task>
|
||||
|
||||
<task type="auto">
|
||||
<name>Task 2: Convert legacy factories to wrapper delegation</name>
|
||||
<files>autoload/admin/factory/class.Scontainers.php, autoload/admin/factory/class.Banners.php, autoload/front/factory/class.Scontainers.php, autoload/front/factory/class.Banners.php</files>
|
||||
<action>
|
||||
Convert all 4 factory files to thin wrappers that delegate to Domain repositories.
|
||||
|
||||
Pattern for each static method:
|
||||
```php
|
||||
public static function method_name($args)
|
||||
{
|
||||
global $mdb;
|
||||
$repo = new \Domain\Scontainers\ScontainersRepository($mdb);
|
||||
return $repo->methodName($args);
|
||||
}
|
||||
```
|
||||
|
||||
admin\factory\Scontainers:
|
||||
- container_delete($id) → $repo->containerDelete($id)
|
||||
- container_save(...) → $repo->containerSave(...)
|
||||
- container_details($id) → $repo->containerDetails($id)
|
||||
|
||||
admin\factory\Banners:
|
||||
- banner_delete($id) → $repo->bannerDelete($id)
|
||||
- banner_save(...) → $repo->bannerSave(...)
|
||||
- banner_details($id) → $repo->bannerDetails($id)
|
||||
|
||||
front\factory\Scontainers:
|
||||
- scontainer_details($id) → $repo->scontainerByLang($id, $lang[0]) — note: use global $lang
|
||||
|
||||
front\factory\Banners:
|
||||
- banners() → $repo->activeBanners($lang[0])
|
||||
- main_banner() → $repo->mainBanner($lang[0])
|
||||
|
||||
IMPORTANT:
|
||||
- Keep namespace declarations unchanged (admin\factory, front\factory)
|
||||
- Keep method signatures identical (same parameter names and order)
|
||||
- For front factories: pass $lang[0] explicitly to repository (repo does NOT use global $lang)
|
||||
</action>
|
||||
<verify>php -l autoload/admin/factory/class.Scontainers.php && php -l autoload/admin/factory/class.Banners.php && php -l autoload/front/factory/class.Scontainers.php && php -l autoload/front/factory/class.Banners.php</verify>
|
||||
<done>AC-3 and AC-4 satisfied: All legacy factories delegate to Domain repositories, signatures unchanged</done>
|
||||
</task>
|
||||
|
||||
</tasks>
|
||||
|
||||
<boundaries>
|
||||
|
||||
## DO NOT CHANGE
|
||||
- autoload/autoloader.php (autoloader stable)
|
||||
- composer.json (PSR-4 mapping already includes Domain\)
|
||||
- autoload/admin/controls/class.Scontainers.php (admin controllers — Phase 10)
|
||||
- autoload/admin/controls/class.Banners.php (admin controllers — Phase 10)
|
||||
- autoload/admin/view/ (admin views — later phases)
|
||||
- autoload/front/view/ (front views — later phases)
|
||||
- autoload/class.Scontainer.php (legacy ArrayAccess entity — separate concern)
|
||||
- Any existing Domain\ repositories (Articles, Languages, Layouts, Pages, Settings, User)
|
||||
|
||||
## SCOPE LIMITS
|
||||
- Only factory → repository migration, NOT admin controllers or views
|
||||
- No new Composer dependencies
|
||||
- No database schema changes
|
||||
- Do not refactor the multi-language save pattern (keep it working as-is)
|
||||
|
||||
</boundaries>
|
||||
|
||||
<verification>
|
||||
Before declaring plan complete:
|
||||
- [ ] php -l passes for all 6 files (2 new + 4 modified)
|
||||
- [ ] ScontainersRepository has: containerDetails, containerSave, containerDelete, scontainerByLang
|
||||
- [ ] BannersRepository has: bannerDetails, bannerSave, bannerDelete, activeBanners, mainBanner
|
||||
- [ ] All 4 factory files are thin wrappers (no direct $mdb usage, only delegation)
|
||||
- [ ] No PHP 8.0+ syntax used
|
||||
- [ ] \S::delete_cache() calls preserved in repository methods
|
||||
- [ ] Caching (\Shared\Cache\CacheHandler) used in front-facing repository methods
|
||||
</verification>
|
||||
|
||||
<success_criteria>
|
||||
- All tasks completed
|
||||
- All verification checks pass
|
||||
- Zero regression — factory method signatures unchanged
|
||||
- Domain repositories follow established pattern (constructor DI, $this->db)
|
||||
</success_criteria>
|
||||
|
||||
<output>
|
||||
After completion, create `.paul/phases/03-domain-scontainers-banners/03-01-SUMMARY.md`
|
||||
</output>
|
||||
Reference in New Issue
Block a user