Merge branch 'lavoro/goldrake-i8' into lavoro/goldrake

This commit is contained in:
2026-09-26 13:06:22 +00:00
4 changed files with 350 additions and 0 deletions
@@ -0,0 +1,82 @@
---
// Crea l'accesso al sito per un cliente che ha già il fascicolo: il trainer sceglie
// l'username, la password la genera il sistema e si mostra UNA volta sola, qui, mai
// via redirect (finirebbe nella query string dell'URL e nella cronologia del browser).
// ⚠️ Questa pagina non apre mai il database anagrafico da sé: passa solo da
// anagrafica.ts e accesso.ts, gli unici moduli autorizzati (li sorveglia un test).
import Longevity from '../../../../../layouts/Longevity.astro';
import { accessoDelCliente } from '../../../../../lib/longevity/anagrafica';
import { creaAccessoCliente } from '../../../../../lib/longevity/accesso';
export const prerender = false;
const { code } = Astro.params as { code: string };
// La password passa da qui una volta sola: niente cache, né del browser né di un proxy
// davanti a Node, che altrimenti la servirebbe di nuovo a chi ripete la stessa GET.
Astro.response.headers.set('Cache-Control', 'no-store');
const fascicolo = accessoDelCliente(code);
if (!fascicolo) Astro.response.status = 404;
let errore = '';
let creato: { username: string; password: string } | null = null;
if (fascicolo && fascicolo.userId === null && Astro.request.method === 'POST') {
const form = await Astro.request.formData();
const username = String(form.get('username') ?? '');
const esito = creaAccessoCliente(undefined, { code, username });
if (esito.ok) creato = { username: esito.username, password: esito.password };
else errore = esito.errore;
}
---
<Longevity title="Crea accesso" crumbs={['Gestionale', code, 'Accesso']} variante="gestionale">
{!fascicolo && (
<div class="lg-card">
<p>Nessun fascicolo con codice <strong>{code}</strong>.</p>
</div>
)}
{fascicolo && fascicolo.userId !== null && (
<div class="lg-card">
<p>Questo fascicolo ha già un accesso collegato: non se ne crea un secondo.</p>
</div>
)}
{fascicolo && fascicolo.userId === null && creato && (
<div class="lg-card">
<p><strong>Accesso creato.</strong> Comunicala al cliente: non verrà mostrata di nuovo.</p>
<p>Utente: <strong>{creato.username}</strong></p>
<p>Password: <strong>{creato.password}</strong></p>
</div>
)}
{fascicolo && fascicolo.userId === null && !creato && (
<form method="post" class="lg-form lg-form--accesso">
{errore && <p class="lg-form__errore">{errore}</p>}
<div class="lg-field">
<span>Nome utente</span>
<input
type="text"
name="username"
required
minlength="3"
maxlength="64"
pattern="[a-z0-9._@-]+"
value={fascicolo.email ?? ''}
/>
</div>
<div class="lg-form__nav">
<button type="submit">Crea accesso</button>
</div>
</form>
)}
<style>
/* .lg-field in longevity.css stila solo input[type="number"] e textarea (li usa il
questionario): qui serve un campo di testo, quindi lo stile arriva da qui. */
.lg-form--accesso .lg-field input[type="text"] {
border: 1px solid var(--lg-line); padding: 9px 11px; font: inherit; background: var(--lg-surface);
}
</style>
</Longevity>