Files
SmartReports/docs/superpowers/specs/2026-03-23-dividend-section-design.md

149 lines
5.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.
# Dividend Section — Design Spec
**Data:** 2026-03-23
**Progetto:** SmartReports / CertReports.Syncfusion
**Stato:** Approvato
---
## Obiettivo
Aggiungere il supporto ai dati dividendi dei sottostanti nel report PDF, attivabile tramite il parametro query `?dividend=true`. Quando attivo, i dati dividendi (già presenti nella SP `rpt_Details_UL_ISIN`) vengono visualizzati in una pagina landscape dedicata con tabella unificata Sottostanti+Dividendi a header raggruppati.
---
## Parametro API
```
?dividend=true → attiva la pagina dividendi
?dividend=false → comportamento invariato (default)
```
Disponibile su tutti gli endpoint report esistenti (`/by-isin/{isin}`, `?p=`, `?alias=`, `/download`).
---
## Comportamento
### Con `dividend=false` (default)
Il report è identico a quello attuale. Nessuna modifica visibile.
### Con `dividend=true`
1. La tabella Sottostanti **non viene renderizzata** in Sezione 1 (né in `AnagraficaSectionRenderer` né in `ExpiredAnagraficaSectionRenderer`).
2. Dopo la Sezione 1 (Anagrafica) e prima della Sezione 2 (Eventi) viene inserita una **pagina landscape dedicata** con la tabella unificata Sottostanti+Dividendi.
3. Il resto del report (Eventi, Scenario, Grafico) rimane invariato.
---
## Struttura tabella landscape
Pagina A4 orizzontale (landscape), margini standard (`PdfTheme.PageMargin`).
Larghezza utile: ~770pt. Font: `PdfTheme.TableFont` (7pt).
### Header a 2 livelli (colspan)
| Riga 1 | Nome | SOTTOSTANTE (×3) | BARRIERE (×5) | DIVIDENDI (×6) |
|--------|------|------------------|---------------|----------------|
| Riga 2 | — | Strike, Last, % Perf. | Barr.Cap., Buf.Cap., Trig.CPN, Buf.CPN, Trig.AC | Data Stacco, Data Pag., Importo, Rend., Imp.Fut., Rend.Fut. |
- Gruppo **SOTTOSTANTE** + **BARRIERE**: sfondo `#1565C0` (AccentBlue)
- Gruppo **DIVIDENDI**: sfondo `#0A3880` (blu scuro) per differenziazione visiva
- Separatore verticale blu (`#64B5F6`) tra colonna T.AC e colonna Data Stacco
- Colori performance: negativi `NegativeRed`, positivi `PositiveGreen`
- Righe alternate: `TableAltRow`
### Larghezze colonne indicative (totale ~770pt)
| Colonna | Width (pt) |
|---------|-----------|
| Nome | 90 |
| Strike | 50 |
| Last | 50 |
| % Perf. | 46 |
| Barr.Cap. | 50 |
| Buf.Cap. | 46 |
| Trig.CPN | 50 |
| Buf.CPN | 46 |
| Trig.AC | 46 |
| Data Stacco | 54 |
| Data Pag. | 54 |
| Importo | 40 |
| Rend. | 40 |
| Imp.Fut. | 40 |
| Rend.Fut. | 40 |
| **Totale** | **742** |
Le larghezze vengono scalate proporzionalmente a `w / total` per adattarsi alla larghezza utile esatta.
---
## Mapping dati
I campi dividendi sono già nel modello `Sottostante` (da SP `rpt_Details_UL_ISIN`):
| Colonna PDF | Campo modello |
|-------------|--------------|
| Data Stacco | `DividendExDate` |
| Data Pag. | `DividendPayDate` |
| Importo | `DividendAmount` |
| Rend. | `DividendYield` |
| Imp.Fut. | `DividendFutAmount` |
| Rend.Fut. | `DividendFutYield` |
Nessuna modifica al data service o alle stored procedure.
---
## Componenti da modificare / creare
### 1. `CertificateReportData` (Models/CertificateModels.cs)
Aggiungere proprietà:
```csharp
public bool ShowDividend { get; set; } = false;
```
### 2. `ReportController` (Controllers/ReportController.cs)
Leggere il parametro `dividend` da query string e impostare `data.ShowDividend`.
### 3. `PdfCacheService`
La chiave cache deve includere il flag dividend per evitare collisioni:
- `{isin}` — no branding, no dividend
- `{isin}:branded` — branding, no dividend
- `{isin}:dividend` — no branding, dividend
- `{isin}:branded:dividend` — branding + dividend
### 4. `AnagraficaSectionRenderer`
Condizione nel metodo `Render()`: se `data.ShowDividend == true`, saltare il blocco "SEZIONE C: SOTTOSTANTI".
### 5. `ExpiredAnagraficaSectionRenderer`
Stessa condizione: se `data.ShowDividend == true`, saltare il blocco "SEZIONE C: SOTTOSTANTI".
### 6. `DividendSectionRenderer` (nuovo file)
- Classe: `DividendSectionRenderer`
- **Non** implementa `IPdfSectionRenderer` (non partecipa al ciclo ordinato)
- Registrazione: `AddScoped<DividendSectionRenderer>()` in `Program.cs`
- Metodo: `PdfDocument Render(CertificateReportData data)`
- Pagina landscape A4, titolo "Sottostanti e Dividendi", tabella con header a 2 livelli
- Footer: `PdfTheme.DrawFooter(g, w, h, 1, data.ShowBranding)`
### 7. `ReportOrchestrator`
- Iniettare `DividendSectionRenderer` nel costruttore
- In entrambi i flussi (attivo ed expired): se `data.ShowDividend == true`, chiamare `DividendSectionRenderer.Render(data)` e aggiungerlo alla lista documenti da mergiare, subito dopo la Sezione 1 (Anagrafica)
---
## Note implementative
- **Header colspan su PdfGrid**: Syncfusion `PdfGrid` non supporta nativamente colspan negli header. Implementare i due livelli di header come righe manuali disegnate con `DrawRectangle` + `DrawString`, poi la griglia dati sotto. Questa è la stessa tecnica usata per altri header complessi nel progetto.
- **Colori negativi/positivi**: applicare `ColorPerformanceCell` su % Perf., Buf.Cap., Buf.CPN, Rend., Rend.Fut. — stessa logica di `AnagraficaSectionRenderer`.
- **Valori assenti**: celle dividendo vuote mostrano `"—"`.
- Il parametro `dividend` è indipendente da `branding` — entrambi possono essere attivi contemporaneamente.
---
## Non in scope
- Modifiche alle stored procedure o al data service
- Nuove colonne nel modello `Sottostante`
- Modifiche al grafico o agli eventi
- Paginazione automatica della tabella dividendi (assumiamo max ~20 sottostanti per certificato)