feat: status + queue updates, filters e UI

- Status renomeados e cores (Em andamento azul, Pausado amarelo)
- Transições automáticas: iniciar=Em andamento, pausar=Pausado
- Fila padrão: Chamados ao criar ticket
- Admin/Empresas: renomeia ‘Slug’ → ‘Apelido’ + mensagens
- Dashboard: últimos tickets priorizam sem responsável (mais antigos)
- Tickets: filtro por responsável + salvar filtro por usuário
- Encerrar ticket: adiciona botão ‘Cancelar’
- Strings atualizadas (PDF, relatórios, badges)
This commit is contained in:
codex-bot 2025-10-20 14:57:22 -03:00
parent e91192a1f6
commit 5535ba81e6
19 changed files with 399 additions and 86 deletions

View file

@ -91,13 +91,17 @@ export function RecentTicketsPanel() {
const [enteringId, setEnteringId] = useState<string | null>(null)
const previousIdsRef = useRef<string[]>([])
const tickets = useMemo(
() =>
mapTicketsFromServerList((ticketsRaw ?? []) as unknown[])
.filter((ticket) => ticket.status !== "RESOLVED")
.slice(0, 6),
[ticketsRaw]
)
const tickets = useMemo(() => {
const all = mapTicketsFromServerList((ticketsRaw ?? []) as unknown[]).filter((t) => t.status !== "RESOLVED")
// Unassigned first (no assignee), oldest first among unassigned; then the rest by updatedAt desc
const unassigned = all
.filter((t) => !t.assignee)
.sort((a, b) => a.createdAt.getTime() - b.createdAt.getTime())
const assigned = all
.filter((t) => !!t.assignee)
.sort((a, b) => b.updatedAt.getTime() - a.updatedAt.getTime())
return [...unassigned, ...assigned].slice(0, 6)
}, [ticketsRaw])
useEffect(() => {
if (ticketsRaw === undefined) {