97 lines
5.2 KiB
Markdown
97 lines
5.2 KiB
Markdown
## Context
|
|
|
|
`WeddingPackage` já cobre cards ordenados + CTA WhatsApp/briefing (change `restructure-home-weddings-corporate`, capability ainda só no delta completo). Campos atuais: `name`, `level`, `summary`, `scope_items` (json), `cta_label`, `sort_order`, `published_at`. Sem slug, sem corpo de detalhe, sem imagens. Portfólio (`portfolio.show`, `FindPublishedPortfolioCaseBySlug`, PageMeta, sitemap) é o padrão de detalhe a espelhar. Mock visual: `/home/manoelfreitas/Downloads/amare-assessoria-completa.html`. Tokens: `DESIGN.md` / `resources/css/tokens.css` (Heritage Editorial) — não Cormorant/Inter do HTML estático.
|
|
|
|
## Goals / Non-Goals
|
|
|
|
**Goals:**
|
|
|
|
- Detalhe CMS-driven `/pacotes/{slug}` para as 3 modalidades, publish-gated.
|
|
- Composição mock → tokens do projeto (olive accent, EB Garamond via stack existente, bg cream).
|
|
- CTA final = mesmo canal contextual dos cards (`wa.me` ou `/briefing?servico_interesse=`).
|
|
- SEO mínimo: meta por registro, canonical, OG image (hero ou default), entrada no sitemap.
|
|
- Admin Filament editável sem deploy de copy.
|
|
|
|
**Non-Goals:**
|
|
|
|
- Rota índice `/pacotes`; substituir cards da home; WhatsApp Business API; preços; multi-idioma; Livewire público; gallery multi-imagem além de hero + audience.
|
|
|
|
## Decisions
|
|
|
|
### Estender `WeddingPackage`, não criar modelo novo
|
|
|
|
Uma entidade comercial já existe e é o que home/serviços já consomem. Detalhe é projeção do mesmo agregado. Modelo paralelo geraria sync de publicação/slug e viola YAGNI.
|
|
|
|
### Slug único + publicação por `published_at`
|
|
|
|
Igual portfólio: URL estável, scope `published()`, query Application `FindPublishedWeddingPackageBySlug`. Draft/inexistente → 404 HTTP, sem vazar campos internos.
|
|
|
|
### Campos de detalhe (additive)
|
|
|
|
| Campo | Uso |
|
|
|-------|-----|
|
|
| `slug` | string unique |
|
|
| `eyebrow` | ex. "Assessoria" |
|
|
| `title_line` | parte romana do H1 |
|
|
| `title_emphasis` | parte itálica do H1 |
|
|
| `hero_lead` | parágrafo do hero |
|
|
| `hero_image_path` / `hero_image_alt` | foto hero |
|
|
| `benefits` | jsonb `[{icon_key,label}]` — faixa escura |
|
|
| `included_items` | jsonb `[{icon_key,title,description}]` — grid 3 col |
|
|
| `audience_heading` | default editorial se vazio ok |
|
|
| `audience_intro` | texto |
|
|
| `audience_points` | jsonb `string[]` checklist |
|
|
| `audience_image_path` / `audience_image_alt` | foto 50/50 |
|
|
| `final_cta_heading` / `final_cta_body` | bloco final |
|
|
| `meta_title` / `meta_description` | SEO opcional |
|
|
|
|
Manter `summary` + `scope_items` para cards. Não migrar cards para `included_items` neste ciclo.
|
|
|
|
### Catálogo fechado de ícones (`PackageIconCatalog`)
|
|
|
|
Select Filament → `icon_key` string. Map PHP/Blade para SVGs inline (ou partials). Sem upload de SVG arbitrário (XSS/ops). Chaves mínimas cobrem mock (ex.: calendar, checklist, users, map, heart, spark — nomes estáveis kebab).
|
|
|
|
### Hero de pacote vs `photo-hero` genérico
|
|
|
|
Mock exige H1 bipartido (linha + ênfase itálica), divisor vertical, CTA outline no hero e foto. Preferir componente dedicado `x-public.package-hero` (ou estender `photo-hero` só se API ficar genérica sem branching feio). Seções: `package-benefits`, `package-included`, `package-audience`, reutilizar `final-cta` se encaixar.
|
|
|
|
### CTA WhatsApp
|
|
|
|
Reutilizar VO/helper já usado nos cards (digits de `SiteSetting.whatsapp_number`, mensagem com nome da modalidade). Mesma regra de fallback briefing. Não duplicar lógica de normalização.
|
|
|
|
### Links a partir dos cards
|
|
|
|
Card: título/área → `route('packages.show', $package)` quando slug presente; botão CTA continua WhatsApp/briefing. Sem quebrar testes de CTA existentes.
|
|
|
|
### Imagens
|
|
|
|
`PublicImageUploadRules` + disk público existente + `x-media.image`. Paths nullable; se hero ausente, layout degrada (omitir slot de imagem).
|
|
|
|
### Camada Application
|
|
|
|
- `FindPublishedWeddingPackageBySlug`
|
|
- Estender `GetSitemapEntries` com slugs de pacotes publicados
|
|
- PageMeta no controller (espelhar PortfolioCaseController)
|
|
|
|
Sem repository genérico / BaseAction.
|
|
|
|
## Risks / Trade-offs
|
|
|
|
- [Capability `wedding-packages` ainda não está em `openspec/specs/`] → delta ADDED nesta change; ao arquivar, consolidar com requirements de cards do change completo ou arquivar ambos em ordem.
|
|
- [Copy das 3 modalidades incompleta] → seeder: Essenza = mock; Conduzione/Grand Jour estrutura paralela adaptada; admin pode editar.
|
|
- [Ícones insuficientes no catálogo] → adicionar chave no map + opção Filament; sem free-text SVG.
|
|
- [Cards sem slug durante migrate] → migration backfill slug a partir do name; seeder garante os 3 oficiais.
|
|
- [Duplicação visual mock vs tokens] → testes de tokens existentes + asserts de classes/roles; não copiar hex do HTML.
|
|
|
|
## Migration Plan
|
|
|
|
1. Deploy migration additive + código + assets Blade juntos.
|
|
2. Rodar seeder/update das 3 modalidades (slug + detalhe).
|
|
3. Verificar `/pacotes/essenza` (etc.), 404 draft, sitemap, CTA WA.
|
|
4. Rollback: remover rota/views; colunas additive podem permanecer; unpublish pacotes se necessário.
|
|
|
|
## Open Questions
|
|
|
|
- Nenhuma bloqueante (decisões de produto já confirmadas: detalhe-only, extend model, 3 modalidades, WA CTA).
|
|
- WEB-ID dedicado a package detail: não existe no SPEC; rastrear via WEB-02 + padrão WEB-03 até SPEC ganhar ID explícito.
|