123 lines
4.7 KiB
TypeScript
123 lines
4.7 KiB
TypeScript
import { Link } from '@inertiajs/react';
|
|
import { Frame, card, input, button } from '@/pages/investment/shared';
|
|
|
|
export default function Experiments({
|
|
installed,
|
|
states,
|
|
filters,
|
|
items,
|
|
page,
|
|
pages,
|
|
total,
|
|
}: {
|
|
installed: boolean;
|
|
states: Record<string, string>;
|
|
filters: { state: string };
|
|
items: {
|
|
id: string;
|
|
version: number;
|
|
state: string;
|
|
title: string;
|
|
hypothesis: string;
|
|
at: string;
|
|
}[];
|
|
page: number;
|
|
pages: number;
|
|
total: number;
|
|
}) {
|
|
const url = (p: number) =>
|
|
'/management/product-experiments?' +
|
|
new URLSearchParams({ state: filters.state, page: String(p) });
|
|
return (
|
|
<Frame title="Registo de experiências">
|
|
<Link className="underline" href="/management/product-usage">
|
|
Indicadores de utilização
|
|
</Link>
|
|
<p>
|
|
Documente planos, comparações observadas, evidências e decisões.
|
|
O estado é uma declaração do autor; registar um plano ou uma
|
|
decisão não publica alterações nem distribui visitantes por
|
|
variantes.
|
|
</p>
|
|
{!installed ? (
|
|
<p role="status">
|
|
O registo ainda não está disponível neste destino. Os
|
|
indicadores existentes continuam disponíveis.
|
|
</p>
|
|
) : (
|
|
<>
|
|
<Link
|
|
className={button}
|
|
href="/management/product-experiments/new"
|
|
>
|
|
Preparar experiência
|
|
</Link>
|
|
<form
|
|
className={card + ' flex flex-wrap gap-3'}
|
|
method="get"
|
|
action="/management/product-experiments"
|
|
>
|
|
<label>
|
|
Estado
|
|
<select
|
|
className={input}
|
|
name="state"
|
|
defaultValue={filters.state}
|
|
>
|
|
<option value="">Todos</option>
|
|
{Object.entries(states).map(([code, label]) => (
|
|
<option key={code} value={code}>
|
|
{label}
|
|
</option>
|
|
))}
|
|
</select>
|
|
</label>
|
|
<button className={button}>Filtrar</button>
|
|
</form>
|
|
<p>
|
|
{total} registos. Página {page} de {pages}.
|
|
</p>
|
|
{items.length === 0 && (
|
|
<p>Ainda não existem registos para este filtro.</p>
|
|
)}
|
|
{items.map((item) => (
|
|
<article className={card + ' space-y-2'} key={item.id}>
|
|
<h2 className="text-lg font-semibold">
|
|
<Link
|
|
className="underline"
|
|
href={
|
|
'/management/product-experiments/' +
|
|
item.id
|
|
}
|
|
>
|
|
{item.title || 'Experiência sem título'}
|
|
</Link>
|
|
</h2>
|
|
<p>
|
|
{states[item.state] ?? item.state} · versão{' '}
|
|
{item.version} · {item.at}
|
|
</p>
|
|
<p className="whitespace-pre-wrap">
|
|
{item.hypothesis ||
|
|
'Hipótese ainda por preencher.'}
|
|
</p>
|
|
</article>
|
|
))}
|
|
<nav aria-label="Páginas do registo" className="flex gap-4">
|
|
{page > 1 && (
|
|
<Link className="underline" href={url(page - 1)}>
|
|
Anterior
|
|
</Link>
|
|
)}
|
|
{page < pages && (
|
|
<Link className="underline" href={url(page + 1)}>
|
|
Seguinte
|
|
</Link>
|
|
)}
|
|
</nav>
|
|
</>
|
|
)}
|
|
</Frame>
|
|
);
|
|
}
|