Harumi

Widgets

Todos os tipos de widget do dashboard.toml — chaves obrigatórias e opcionais, um exemplo funcional e um render ao vivo para cada um.

Todo widget é uma entrada [[widgets]]

Um arquivo de dashboard (dashboard/<nome>.toml, ou o dashboard.toml legado na raiz) renderiza uma view por tabela [[widgets]]. Toda entrada, de qualquer tipo abaixo, precisa das mesmas três chaves:

Prop

Type

Todo o resto é específico do tipo — coberto por tipo abaixo, cada um com um render ao vivo produzido pelos mesmos componentes que o produto usa. Um widget com um type desconhecido, ou sem uma chave obrigatória do seu tipo, é descartado do dashboard renderizado e reportado por harumi dashboard validate em vez de quebrar a página.

Além dos widgets

dashboard.toml também pode declarar datasets reutilizáveis, definir novos KPIs como SQL, e adicionar playback controlado por clock — nada disso é coberto aqui. Veja Datasets, métricas e o clock do dashboard. Para o que um valor color/colors abaixo pode ser, e a paleta completa de nomes, veja Cores.

Layout

Você não posiciona widgets. O dashboard os organiza em linhas, na ordem em que aparecem em [[widgets]], de acordo com o espaço de que cada tipo precisa:

  • Cards metric que vêm em sequência dividem uma linha, lado a lado. Só quebram em mais linhas quando o dashboard é estreito demais para eles.
  • chart, treemap e heatmap ocupam meia linha: dois em sequência ficam lado a lado (em um dashboard estreito, ficam empilhados). Um que sobra sem par ocupa a linha inteira.
  • table, timeline, gantt-chart e map ocupam uma linha só para si.

Declare widgets relacionados um ao lado do outro: três widgets metric em sequência formam uma faixa, mas um table entre dois deles divide a faixa em duas.

layout.columns é ignorado

Dashboards antigos podem ainda ter uma tabela [layout] com columns. Ela continua sendo lida, mas não muda mais nada; você pode removê-la.

Card de KPI

metric

O único widget de KPI: um título, o valor em destaque e, opcionalmente, uma linha embaixo com uma descrição à esquerda e uma tendência à direita. Escreva um metric por número; cards em sequência dividem uma linha. Um detalhamento por entidade (por máquina, por turno) não é um card de KPI: coloque-o em uma table ou em um gráfico.

Prop

Type

[[widgets]]
type = "metric"
id = "utilization"
title = "Machine utilization"
value_key = "totals.utilization"
delta_key = "totals.utilization_delta"
format = "percent"
description = "4 machines, 480 min"

Preview ao vivo, renderizado com os componentes reais do dashboard:

Machine utilization
87%
4 machines, 480 min+4%

Quando menos é melhor, defina good_direction = "down": uma alta fica vermelha e uma queda verde. Aqui os jobs atrasados subiram em um, então a tendência é vermelha, e a linha de descrição é lida do output do run com description_key:

[[widgets]]
type = "metric"
id = "late-jobs"
title = "Late jobs"
value_key = "totals.late_jobs"
delta_key = "totals.late_jobs_delta"
good_direction = "down"
description_key = "totals.late_jobs_note"
Late jobs
1
1 of 6 jobs+1

kpi-rail foi removido

O widget kpi-rail, que agrupava vários tiles em um só widget, não existe mais: escreva um metric por número. Um dashboard que ainda o usa continua mostrando seus tiles de valor único como cards metric separados, mas o harumi dashboard validate o reporta como tipo desconhecido e suas listas rows_key por entidade não são mais desenhadas.

Tabela

table

Uma grade de dados ordenável ligada a um array de objetos-linha.

Prop

Type

[[widgets]]
type = "table"
id = "jobs"
title = "Jobs"
rows_key = "jobs"
columns = [
  { key = "job", label = "Job" },
  { key = "priority", label = "Priority" },
  { key = "due", label = "Due (min)" },
  { key = "completed", label = "Completed (min)" },
  { key = "slack", label = "Slack (min)" },
  { key = "cost", label = "Cost" },
  { key = "status", label = "Status" },
]

Preview ao vivo, renderizado com os componentes reais do dashboard:

Jobs
JobPriorityDue (min)Completed (min)Slack (min)CostStatus
Job AStandard3603303026800On time
Job BRush4003802024100On time
Job CStandard4804404021500On time
Job DStandard4804602019900On time
Job ERush420470-5022700Late
Job FStandard4804503013400On time

Gráficos

chart

Um widget para todo tipo de gráfico, escolhido por variant: line, bar, area, scatter, pie ou donut. Trocar a forma de desenhar os dados nunca exige trocar de widget, e as fontes, a grade, os cinzas e o espaçamento são os do próprio produto, então todo gráfico parece fazer parte dele.

Prop

Type

[[widgets]]
type = "chart"
id = "convergence"
title = "Solver convergence"
variant = "line"
data_key = "convergence"
x_key = "t"
series = [
  { key = "best", label = "Best makespan" },
  { key = "bound", label = "Lower bound" },
]

Preview ao vivo, renderizado com os componentes reais do dashboard:

Solver convergence

O mesmo tipo com variant = "bar", comparando categorias em vez de uma tendência:

[[widgets]]
type = "chart"
id = "machine-time"
title = "Machine time by state"
variant = "bar"
data_key = "machine_hours"
x_key = "machine"
series = [
  { key = "busy", label = "Busy" },
  { key = "setup", label = "Setup" },
  { key = "idle", label = "Idle" },
]

Escolhendo uma variante

Sua perguntaUse
Como isso muda ao longo do tempo?line (ou area para destacar o volume)
Qual categoria é maior?bar, com orientation = "horizontal" quando os rótulos são longos
Que fatia do todo cada parte representa?pie ou donut, só para umas seis fatias ou menos
Como dois números se relacionam?scatter

Um pie/donut mostra apenas valores positivos, na ordem de origem a menos que você defina sort, e acima de oito fatias as menores são reunidas em uma única fatia Other — um pie de uma dúzia de fatias finas não diz nada, então prefira um bar ordenado nesse caso.

[[widgets]]
type = "chart"
id = "cost-share"
title = "Where the cost goes"
variant = "donut"
data_key = "cost_by_machine"
x_key = "machine"
series = [{ key = "cost", label = "Cost" }]
sort = "desc"
format = "currency"

Vários grupos: group_key, stack e series[].mark

Quando cada linha é uma categoria em um grupo (formato longo), group_key transforma cada grupo distinto em uma série colorida própria, sem precisar listá-los à mão. Adicione stack para empilhá-los:

[[widgets]]
type = "chart"
id = "cost-mix"
title = "Cost by machine and shift"
variant = "bar"
stack = "stacked"
data_key = "cost_by_shift"
x_key = "machine"
group_key = "shift"
series = [{ key = "cost", label = "Cost" }]
format = "currency"

stack = "percent" normaliza cada categoria para 100% (só barras e áreas; uma série de linha faz voltar para stacked). Para misturar desenhos no mesmo eixo, dê a uma série seu próprio mark:

[[widgets]]
type = "chart"
id = "output-vs-target"
title = "Output against target"
variant = "bar"
data_key = "daily"
x_key = "day"
series = [
  { key = "output", label = "Output" },
  { key = "target", label = "Target", mark = "line" },
]

line-chart e bar-chart continuam funcionando

Dashboards escritos com line-chart ou bar-chart continuam renderizando: a plataforma os lê como chart com variant = "line" ou "bar". Escreva chart em qualquer coisa nova.

Linhas do tempo e agendas

timeline

Um timeline com linhas por recurso em um eixo de tempo numérico — o tipo atual e recomendado para resultados de scheduling/job-shop (uma linha por máquina/recurso, uma barra por tarefa). Substitui gantt-chart (abaixo): trabalho interrompido se agrupa em um único item desenhado com lacunas, períodos de não-trabalho renderizam como faixas de fundo, o eixo é drag-to-zoom, e um [clock] (veja Datasets, métricas e o clock do dashboard) coloca sua barra de reprodução no topo do card e aparece como um marcador de "agora".

Prop

Type

[[widgets]]
type = "timeline"
id = "schedule"
title = "Machine schedule"
items_key = "schedule"
id_key = "op"
color_key = "job"
colors = { "Job E" = "red-600" }
regions_key = "breaks"
region_label_key = "label"
region_resource_key = "resource"
time_unit = "min"

Preview ao vivo, renderizado com os componentes reais do dashboard:

Machine schedule
CNC 1
CNC 2
Lathe
Press

gantt-chart

Um gráfico de Gantt com linhas por recurso em um eixo de tempo numérico — o mesmo formato que timeline cobre, mantido para que dashboards escritos antes da existência do timeline continuem renderizando. Prefira timeline para um dashboard novo.

Prop

Type

[[widgets]]
type = "gantt-chart"
id = "schedule"
title = "Machine schedule"
tasks_key = "schedule"
color_key = "job"
time_unit = "min"

Preview ao vivo, renderizado com os componentes reais do dashboard:

Machine schedule
0 min100 min200 min300 min400 min
CNC 1
A1 · Mill
C1 · Mill
E1 · Mill
E1 · Mill
B3 · Finish
D3 · Finish
CNC 2
B1 · Mill
D1 · Mill
A3 · Finish
F1 · Mill
C3 · Finish
Lathe
A2 · Turn
C2 · Turn
E2 · Turn
F2 · Turn
Press
B2 · Press
D2 · Press
A4 · Press
E3 · Press

Breakdowns

treemap

Um treemap plano — um retângulo por linha, com área proporcional a value_key, rotulado a partir de name_key. Bom para um breakdown onde o tamanho relativo importa mais do que valores exatos (ex. custo por máquina).

Prop

Type

[[widgets]]
type = "treemap"
id = "machine-load"
title = "Busy minutes by machine"
items_key = "machine_hours"
value_key = "busy"
name_key = "machine"
capacity_key = "totals.capacity"

Preview ao vivo, renderizado com os componentes reais do dashboard:

Busy minutes by machine

heatmap

Uma grade entidade x bucket-de-tempo, sombreada por intensidade — uma linha por recurso, uma coluna por bucket (ex. hora do dia). Um par (resource, bucket) sem linha correspondente renderiza como uma célula distinta de "indisponível", em vez de zero.

Prop

Type

[[widgets]]
type = "heatmap"
id = "hourly-cycles"
title = "Cycles per hour"
items_key = "hourly_cycles"
resource_key = "resource"
bucket_key = "bucket"
value_key = "value"
unit = "cycles"

Preview ao vivo, renderizado com os componentes reais do dashboard:

Cycles per hour
 678910111213
CNC 13844474522414643
CNC 23541391218404437
Lathe–28333615313430
Press526158602755––

Mapas

map

Pontos e/ou rotas geocodificados sobre um mapa real — paradas de entrega, rotas de veículos, localização de instalações. Defina points_key, routes_key, ou ambos: uma camada de paradas mais os caminhos que as ligam. Um widget sem nenhum dos dois renderiza um estado vazio. Clicar em um ponto o alterna na seleção do dashboard, ligado por id_key do mesmo jeito que o timeline.

Prop

Type

[[widgets]]
type = "map"
id = "deliveries"
title = "Delivery run"
points_key = "stops"
label_key = "label"
id_key = "id"
color_key = "van"
routes_key = "routes"
route_color_key = "van"

Preview ao vivo, renderizado com os componentes reais do dashboard:

Delivery run

Tiles em produção

Os servidores públicos de tiles do OpenStreetMap servem para experimentar o widget, mas são um serviço compartilhado e com limite de uso. Para um dashboard com tráfego real, defina tile_url para o seu próprio servidor de tiles ou um provedor pago, e attribution para o crédito dele.

Tipos de gráfico legados

line-chart e bar-chart são anteriores a chart, que une os dois em um único tipo escolhido por variant. Ambos continuam totalmente suportados — um dashboard escrito antes de chart existir continua renderizando, porque a plataforma lê cada um como um chart — mas deixaram de ser widgets separados, então prefira chart para qualquer coisa nova.

Tipo legadoEquivale a
type = "line-chart"type = "chart" com variant = "line"
type = "bar-chart"type = "chart" com variant = "bar"

Eles aceitam as mesmas chaves data_key, x_key e series que chart; um variant que você mesmo definir prevalece sobre o que o nome antigo sugere.

Verificando seus widgets antes de commitar

harumi dashboard widgets imprime essa mesma referência no seu terminal (opcionalmente filtrada com --type), e harumi dashboard validate verifica um dashboard.toml real contra ela — sinalizando um tipo desconhecido, uma chave obrigatória ausente, ou (dado --against, --run, ou --latest) um dot-path que não resolve contra um output.json real.

On this page