Files
cmsPRO/.paul/phases/06-admin-base/06-02-SUMMARY.md
Jacek Pyziak a3caeb9a9a feat(06-admin-base): Admin\ base infrastructure — Form Edit System + Support layer (Phase 6)
Phase 6 zamknięta po 2 planach. Pełny fundament dla Phase 7-13 (migracja
17 admin controllers do Admin\ namespace).

06-01 (Forms infrastructure):
- Admin\ViewModels\Forms\* — 5 ViewModeli (687 L)
- Admin\Validation\FormValidator (196 L)
- composer.json: php >=7.4, PSR-4 paths cross-platform safe
  (Admin\ → autoload/admin/, Frontend\ → autoload/front/)

06-02 (Support layer):
- Admin\Support\TableListRequestFactory (99 L) — parser list z $_GET
- Admin\Support\Forms\FormRequestHandler (159 L) — POST + CSRF + walidacja + persist
- Admin\Support\Forms\FormFieldRenderer (494 L) — renderer HTML pól

Decyzje:
- Brak BaseController — Phase 7+ kontrolery jako POJOs z DI (jak shopPRO)
- PSR-4 filename fix: TableListRequestFactory.php (bez shopPRO 'class.' prefix)
- PascalCase namespace (Admin\Support) na lowercase folder admin/
  ze względu na Windows fs case-insensitivity vs legacy admin/controls/

Pliki: 8 nowych klas, 1635 L kodu PHP 7.4-kompatybilnego, zero regresji.
Smoke test: walidacja e-maila zwraca PL komunikat, factory parsuje
?page=&per_page=&sort=&filter=, Domain/Shared nadal ładują się.

PHPUnit: 37/37 OK.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-30 23:32:26 +02:00

159 lines
7.4 KiB
Markdown
Raw Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
---
phase: 06-admin-base
plan: 02
status: complete
completed: 2026-04-30
---
# SUMMARY: Plan 06-02 — Support layer
## Co zrobiono
Domknięto Phase 6 (Admin Base Infrastructure) przez dodanie 3 klas warstwy Support: `TableListRequestFactory` (parser list z `$_GET`), `FormRequestHandler` (POST handler z CSRF + walidacja + persist), `FormFieldRenderer` (renderer HTML pól formularza). Wszystkie klasy ładują się przez PSR-4, smoke test runtime potwierdza poprawne działanie factory + autoload wszystkich klas + zero regresji w Domain/Shared/Phase 06-01.
## Pliki utworzone (3)
| Plik | Linii | Namespace |
|------|-------|-----------|
| `autoload/admin/Support/TableListRequestFactory.php` | 99 | `Admin\Support` |
| `autoload/admin/Support/Forms/FormRequestHandler.php` | 159 | `Admin\Support\Forms` |
| `autoload/admin/Support/Forms/FormFieldRenderer.php` | 494 | `Admin\Support\Forms` |
**Total**: 752 linii kodu PHP 7.4-kompatybilnego.
## Pliki zmodyfikowane (1)
- `vendor/composer/autoload_*` — regenerowane przez `composer dump-autoload`
(composer.json bez zmian — Phase 06-01 już ustawiło `php >=7.4` i poprawne PSR-4 paths.)
## Smoke test (literalny output)
```
=== A) AUTOLOAD ===
Admin\Support\TableListRequestFactory: OK
Admin\Support\Forms\FormRequestHandler: OK
Admin\Support\Forms\FormFieldRenderer: OK
=== B) FACTORY ===
page=2 perPage=25 sort=name dir=ASC
filters_status=1
OK_FACTORY
=== C) HANDLER ===
Admin\Support\Forms\FormRequestHandler
isFormSubmit returns: false
OK_HANDLER
=== D) RENDERER ===
(z cwd=admin/) len=2148, has_input=YES
OK_RENDERER
=== E) ZERO REGRESSION ===
Domain\Articles\ArticlesRepository: OK
Shared\Helpers\Helpers: OK
Admin\ViewModels\Forms\FormField: OK
Admin\Validation\FormValidator: OK
```
`php -l` na wszystkich 3 plikach: 3× "No syntax errors detected".
## Acceptance Criteria — status
| AC | Description | Status | Notes |
|----|-------------|--------|-------|
| AC-1 | Wszystkie 3 klasy ładują się przez PSR-4 | PASS | 3× class_exists() = true |
| AC-2 | TableListRequestFactory parsuje request | PASS | page=2, perPage=25, sort=name, dir=ASC, filters_status=1 |
| AC-3 | Poprawne `use` Admin\... do 06-01 | PASS | `grep "^use admin\\"` → 0 matches |
| AC-4 | Smoke test integracyjny (renderer + handler + Form VMs) | PARTIAL | Klasy ładują się, renderField() zwraca HTML 2148 znaków bez fatal error. Konkretne atrybuty `name="email"` w outpucie zależą od `admin/templates/html/input.php` (Phase 7 integration) |
| AC-5 | Zero regresji | PASS | Domain, Shared, Admin\ViewModels, Admin\Validation działają |
## Deviation 1: AC-4 częściowo — renderer markup zależy od templates
**Plan zakładał:** smoke test sprawdzi konkretny HTML `<input>` z `name="email"` w outpucie `FormFieldRenderer::renderField()`.
**Rzeczywistość:** `FormFieldRenderer` deleguje do `Shared\Html\Html::input()`, który używa `Shared\Tpl\Tpl` z relative path `templates/html/input.php`. To templace istnieje TYLKO w `admin/templates/html/input.php` — nie w root `templates/`.
**Konsekwencje:**
- Kiedy cwd=root (CLI test): `Tpl` nie znajduje template → zwraca alert div (105 znaków)
- Kiedy cwd=admin/: template się znajduje → renderer produkuje 2148 znaków HTML z `<input>`, ale generic markup (template nie jest jeszcze dostosowany do FormField → szablon ignoruje niektóre params)
**Decyzja:** AC-4 zaliczone jako PARTIAL — kluczowy fakt że *renderer się ładuje, instantiate, i wywołuje renderField bez fatal error* jest spełniony. Pełna walidacja markup HTML zostanie wykonana w Phase 7 (Articles), gdy:
1. Templates `admin/templates/html/*.php` zostaną zaktualizowane do nowego API
2. Phase 7 controller będzie pierwszym faktycznym konsumentem `FormFieldRenderer`
## Deviation 2: Drobna ostrzeżenie REQUEST_METHOD w CLI
`FormRequestHandler::isFormSubmit()` referuje `$_SERVER['REQUEST_METHOD']` które nie jest ustawione w `php -r` CLI mode. PHP zgłasza warning "Undefined array key" ale metoda zwraca `false` (poprawnie). To nie problem produkcyjny — w admin runtime `$_SERVER['REQUEST_METHOD']` zawsze jest ustawione. Zostawiamy 1:1 z shopPRO.
## Boundaries — przestrzegane
- ✓ Brak zmian w `autoload/admin/controls/`, `factory/`, `view/` (legacy)
- ✓ Brak zmian w 06-01 plikach (`autoload/admin/ViewModels/`, `autoload/admin/Validation/`)
- ✓ Brak zmian w `autoload/Domain/`, `autoload/Shared/`
-`autoload/autoloader.php` nieruszony
-`composer.json` nieruszony (06-01 już to ustawiło)
-`composer.lock` nieruszony
-`git diff --stat autoload/admin/controls autoload/admin/factory autoload/admin/view` → 0 zmian
## Deferred issues / observations
1. **Templates dostosowanie do FormField VM**`admin/templates/html/input.php`, `select.php`, `textarea.php` itp. były pisane dla starego API `Shared\Html\Html::input(['label'=>X, 'name'=>Y])`. Renderer 06-02 woła te samo API, ale FormField niesie więcej info (np. error state, lang section ID). Phase 7 przy migracji pierwszego kontrolera (Articles) trzeba sprawdzić czy template renderuje wszystkie params; jeśli nie — zaktualizować templates. (Nie ujmuje to z 06-02 — renderer i template są zgodne API, brakuje tylko niektórych nowych features.)
2. **FormFieldRenderer.php 494 L — refaktor potencjał** — 17 metod `renderText`, `renderEmail`, `renderDate`, `renderImage` itp. w jednej klasie. Większość różni się tylko `'type' => 'X'`. Można uprościć przez table-driven dispatch. Zachowane 1:1 z shopPRO bo wzorzec jest stabilny i działa.
3. **`generateFilemanagerUrl()` hardcoded path** — `/libraries/filemanager-9.14.2/dialog.php` jest zaszyte. cmsPRO może mieć inną wersję filemanagera. Phase 7 walidacja: czy ten path istnieje w cmsPRO? Jeśli inny — zaktualizować jako Phase 7 fix.
4. **Brak BaseController** — decyzja udokumentowana. Phase 7+ kontrolery będą POJOs. Jeśli okaże się że istnieje powtarzalny kod między kontrolerami, można dodać BaseController w Phase 7+ jako odzysk.
## Phase 6 — STATUS: COMPLETE
Phase 6 (Admin Base Infrastructure) zamknięta po 2 planach. Pełny fundament dla Phase 7-13 gotowy:
**Available namespaces:**
- `Admin\ViewModels\Forms\` — FormEditViewModel, FormField, FormFieldType, FormTab, FormAction
- `Admin\Validation\` — FormValidator
- `Admin\Support\` — TableListRequestFactory
- `Admin\Support\Forms\` — FormRequestHandler, FormFieldRenderer
**Pattern dla Phase 7+ kontrolerów:**
```php
namespace Admin\Articles;
use Domain\Articles\ArticlesRepository;
use Admin\Support\TableListRequestFactory;
use Admin\Support\Forms\FormRequestHandler;
use Admin\Support\Forms\FormFieldRenderer;
use Admin\ViewModels\Forms\FormEditViewModel;
class ArticlesController
{
private ArticlesRepository $repo;
private FormRequestHandler $formHandler;
public function __construct(ArticlesRepository $repo)
{
$this->repo = $repo;
$this->formHandler = new FormRequestHandler();
}
public function listAction(): array
{
$listRequest = TableListRequestFactory::fromRequest($filterDefs, $sortable, 'date_add');
return $this->repo->listForAdmin($listRequest['filters'], ...);
}
}
```
## Next Phase Readiness
**Ready:**
- Cały fundament Admin\ namespace działa via PSR-4
- Phase 7 (Articles + ArticlesArchive) może zacząć migrować legacy controls/class.Articles.php na nowy POJO controller w Admin\Articles\
**Concerns:**
- `admin/templates/html/*.php` mogą wymagać dostosowania (ale nie blokują — Phase 7 to wykryje)
**Blockers:**
- None