fix: pannello contenuti — PUT ritorna value salvato, data-q aggiornato, guard hash, aria-label
This commit is contained in:
@@ -43,7 +43,7 @@ const allStyles = STYLE_GROUPS as Record<string, readonly string[]>;
|
|||||||
<h1>Contenuti</h1>
|
<h1>Contenuti</h1>
|
||||||
<a href="/?annotate=1" target="_blank">Vedi sito con tag ↗</a>
|
<a href="/?annotate=1" target="_blank">Vedi sito con tag ↗</a>
|
||||||
</div>
|
</div>
|
||||||
<input class="afield" id="csearch" type="search" placeholder="Cerca per tag o contenuto…" autocomplete="off" />
|
<input class="afield" id="csearch" type="search" placeholder="Cerca per tag o contenuto…" aria-label="Cerca per tag o contenuto" autocomplete="off" />
|
||||||
|
|
||||||
<div id="cgroups">
|
<div id="cgroups">
|
||||||
{GROUP_ORDER.map((g) => {
|
{GROUP_ORDER.map((g) => {
|
||||||
@@ -66,7 +66,7 @@ const allStyles = STYLE_GROUPS as Record<string, readonly string[]>;
|
|||||||
: <em>Nessun override: il sito usa l'immagine originale.</em>}
|
: <em>Nessun override: il sito usa l'immagine originale.</em>}
|
||||||
</p>
|
</p>
|
||||||
<p class="cactions">
|
<p class="cactions">
|
||||||
<input type="file" accept="image/*" data-file />
|
<input type="file" accept="image/*" aria-label={`Nuova immagine per ${it.tag}`} data-file />
|
||||||
<button class="abtn" type="button" data-upload>Carica</button>
|
<button class="abtn" type="button" data-upload>Carica</button>
|
||||||
<button class="abtn abtn--danger" type="button" data-restore>Ripristina originale</button>
|
<button class="abtn abtn--danger" type="button" data-restore>Ripristina originale</button>
|
||||||
</p>
|
</p>
|
||||||
@@ -74,8 +74,8 @@ const allStyles = STYLE_GROUPS as Record<string, readonly string[]>;
|
|||||||
) : (
|
) : (
|
||||||
<>
|
<>
|
||||||
{isLong(it.value)
|
{isLong(it.value)
|
||||||
? <textarea class="afield" rows="4" data-value>{it.value}</textarea>
|
? <textarea class="afield" rows="4" aria-label={`Contenuto ${it.tag}`} data-value>{it.value}</textarea>
|
||||||
: <input class="afield" value={it.value} data-value />}
|
: <input class="afield" value={it.value} aria-label={`Contenuto ${it.tag}`} data-value />}
|
||||||
{it.styleOptions.length > 0 && (
|
{it.styleOptions.length > 0 && (
|
||||||
<p class="cstyles">
|
<p class="cstyles">
|
||||||
{it.styleOptions.map((sg) => (
|
{it.styleOptions.map((sg) => (
|
||||||
@@ -185,9 +185,13 @@ const allStyles = STYLE_GROUPS as Record<string, readonly string[]>;
|
|||||||
headers: { 'Content-Type': 'application/json' },
|
headers: { 'Content-Type': 'application/json' },
|
||||||
body: JSON.stringify({ value, styles }),
|
body: JSON.stringify({ value, styles }),
|
||||||
}),
|
}),
|
||||||
() => {
|
(data) => {
|
||||||
|
const saved = typeof data.value === 'string' ? data.value : value;
|
||||||
|
const field = row.querySelector<HTMLInputElement | HTMLTextAreaElement>('[data-value]')!;
|
||||||
|
field.value = saved;
|
||||||
|
row.dataset.q = `${row.dataset.tag} ${saved}`.toLowerCase();
|
||||||
row.querySelector<HTMLElement>('.crow-snippet')!.textContent =
|
row.querySelector<HTMLElement>('.crow-snippet')!.textContent =
|
||||||
value.length > 60 ? `${value.slice(0, 60)}…` : value;
|
saved.length > 60 ? `${saved.slice(0, 60)}…` : saved;
|
||||||
},
|
},
|
||||||
'Salvato.', 'Salvataggio non riuscito.');
|
'Salvato.', 'Salvataggio non riuscito.');
|
||||||
} else if (btn.hasAttribute('data-upload')) {
|
} else if (btn.hasAttribute('data-upload')) {
|
||||||
@@ -226,7 +230,8 @@ const allStyles = STYLE_GROUPS as Record<string, readonly string[]>;
|
|||||||
|
|
||||||
// Ancore: #<tag> apre gruppo + riga, scrolla ed evidenzia.
|
// Ancore: #<tag> apre gruppo + riga, scrolla ed evidenzia.
|
||||||
function openHash(): void {
|
function openHash(): void {
|
||||||
const tag = decodeURIComponent(location.hash.slice(1));
|
let tag: string;
|
||||||
|
try { tag = decodeURIComponent(location.hash.slice(1)); } catch { return; }
|
||||||
if (!tag) return;
|
if (!tag) return;
|
||||||
const row = document.getElementById(tag);
|
const row = document.getElementById(tag);
|
||||||
if (!row || !row.classList.contains('crow')) return;
|
if (!row || !row.classList.contains('crow')) return;
|
||||||
|
|||||||
@@ -14,5 +14,8 @@ export const PUT: APIRoute = async ({ params, request, locals }) => {
|
|||||||
const r = applyContentUpdate(getDb(), params.tag ?? '', data, locals.user!.username);
|
const r = applyContentUpdate(getDb(), params.tag ?? '', data, locals.user!.username);
|
||||||
if (!r.ok) return json(r.status, { error: r.error });
|
if (!r.ok) return json(r.status, { error: r.error });
|
||||||
invalidateContentCache();
|
invalidateContentCache();
|
||||||
return json(200, { ok: true });
|
// Il value salvato può differire da quello inviato (sanitizeInline sui tag html):
|
||||||
|
// lo restituiamo così il pannello mostra il dato reale.
|
||||||
|
const row = getDb().prepare('SELECT value FROM content_blocks WHERE tag = ?').get(params.tag) as { value: string };
|
||||||
|
return json(200, { ok: true, value: row.value });
|
||||||
};
|
};
|
||||||
|
|||||||
Reference in New Issue
Block a user