@bluemarble/bi 0.4.0 → 0.6.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -0,0 +1 @@
1
+ {"version":3,"file":"DashboardDevtools-SCewfQGR.js","names":["KEYWORDS","inputSx","MIN_HEIGHT","ToggleButton"],"sources":["../src/devtools/sqlHighlight.tsx","../src/devtools/ui.tsx","../src/devtools/FiltersPanel.tsx","../src/devtools/DevtoolsWindow.tsx","../src/devtools/Inspector.tsx","../src/devtools/lineDiff.ts","../src/devtools/LayoutPanel.tsx","../src/devtools/modelCode.ts","../src/devtools/SqlEditor.tsx","../src/devtools/modelFields.tsx","../src/devtools/DimensionPicker.tsx","../src/devtools/ModelDiagram.tsx","../src/devtools/ModelPanel.tsx","../src/devtools/PlaygroundPanel.tsx","../src/devtools/QueriesPanel.tsx","../src/devtools/RegressionPanel.tsx","../src/devtools/DashboardDevtools.tsx"],"sourcesContent":["import { type CSSProperties, type ReactNode, useMemo } from 'react'\n\n/**\n * Destaque de sintaxe do SQL do modelo (sem dependência de editor): um tokenizador pequeno que\n * reconhece o que aparece nos modelos — palavras-chave, funções, textos, números, comentários,\n * `tabela.coluna` e os marcadores `{keys}` / `{medida}`.\n */\n\nexport type TokenKind =\n | 'keyword'\n | 'function'\n | 'string'\n | 'number'\n | 'comment'\n | 'placeholder'\n | 'qualifier'\n | 'quoted'\n | 'plain'\n\nexport type Token = { kind: TokenKind; text: string }\n\nconst KEYWORDS = new Set(\n `SELECT FROM WHERE AND OR NOT IN IS NULL JOIN LEFT RIGHT INNER OUTER CROSS ON AS GROUP BY ORDER\n HAVING LIMIT OFFSET UNION ALL DISTINCT CASE WHEN THEN ELSE END WITH ASC DESC BETWEEN LIKE EXISTS\n INTERVAL TRUE FALSE USING OVER PARTITION ROLLUP`.split(/\\s+/)\n)\n\nconst PATTERN =\n /(--[^\\n]*|\\/\\*[\\s\\S]*?(?:\\*\\/|$))|('(?:[^'\\\\]|\\\\.)*'?|\"(?:[^\"\\\\]|\\\\.)*\"?)|(`[^`]*`?)|(\\{[A-Za-z_]\\w*\\})|(\\b\\d+(?:\\.\\d+)?\\b)|([A-Za-z_]\\w*)/g\n\nexport function tokenizeSql(sql: string): Token[] {\n const tokens: Token[] = []\n let last = 0\n for (const match of sql.matchAll(PATTERN)) {\n const index = match.index ?? 0\n if (index > last) tokens.push({ kind: 'plain', text: sql.slice(last, index) })\n const [text, comment, string, quoted, placeholder, number, word] = match\n let kind: TokenKind = 'plain'\n if (comment) kind = 'comment'\n else if (string) kind = 'string'\n else if (quoted) kind = 'quoted'\n else if (placeholder) kind = 'placeholder'\n else if (number) kind = 'number'\n else if (word) {\n const after = sql.slice(index + text.length)\n // Palavra-chave antes de função: `IN (`, `EXISTS (`, `OVER (`\n if (after.startsWith('.')) kind = 'qualifier'\n else if (KEYWORDS.has(word.toUpperCase())) kind = 'keyword'\n else if (/^\\s*\\(/.test(after)) kind = 'function'\n }\n tokens.push({ kind, text })\n last = index + text.length\n }\n if (last < sql.length) tokens.push({ kind: 'plain', text: sql.slice(last) })\n return tokens\n}\n\n// `style` em vez de `sx` (um span por token). Sem negrito nem itálico: no editor o texto colorido fica por\n// baixo do campo e precisa ter exatamente a mesma largura\nconst COLORS: Record<TokenKind, CSSProperties> = {\n keyword: { color: '#c792ea' },\n function: { color: '#82aaff' },\n string: { color: '#c3e88d' },\n number: { color: '#f78c6c' },\n comment: { color: '#697098' },\n placeholder: { color: '#ffcb6b' },\n qualifier: { color: '#89ddff' },\n quoted: { color: '#eeffff' },\n plain: {}\n}\n\n/** Os tokens como `<span>` coloridos (para dentro de um `<pre>`). */\nexport function HighlightedSql({ code }: { code: string }) {\n const parts = useMemo(() => tokenizeSql(code), [code])\n return (\n <>\n {parts.map((token, index): ReactNode =>\n token.kind === 'plain' ? (\n token.text\n ) : (\n // biome-ignore lint/suspicious/noArrayIndexKey: tokens recalculados a cada texto\n <span key={index} style={COLORS[token.kind]}>\n {token.text}\n </span>\n )\n )}\n </>\n )\n}\n","import {\n Box,\n Button,\n Table,\n TableBody,\n TableCell,\n TableContainer,\n TableHead,\n TableRow,\n TableSortLabel,\n Typography\n} from '@mui/material'\nimport { type ReactNode, useState } from 'react'\nimport type { RowDiff } from '../compare'\nimport type { DashboardRow } from '../types'\nimport type { DiffLine } from './lineDiff'\nimport { HighlightedSql } from './sqlHighlight'\nimport type { RunStatus } from './store'\n\nexport const MONO = 'ui-monospace, SFMono-Regular, Menlo, Consolas, monospace'\n\nexport const STATUS_COLOR: Record<RunStatus, string> = {\n loading: '#4dabf7',\n success: '#51cf66',\n error: '#ff6b6b',\n cancelled: '#868e96'\n}\n\nexport const STATUS_LABEL: Record<RunStatus, string> = {\n loading: 'carregando',\n success: 'ok',\n error: 'erro',\n cancelled: 'cancelada'\n}\n\nexport function StatusDot({ status }: { status: RunStatus }) {\n return (\n <Box\n component=\"span\"\n title={STATUS_LABEL[status]}\n sx={{\n width: 8,\n height: 8,\n flexShrink: 0,\n borderRadius: '50%',\n display: 'inline-block',\n bgcolor: STATUS_COLOR[status]\n }}\n />\n )\n}\n\n/**\n * Copia para a área de transferência. Com o devtools em janela separada, o clipboard tem que ser o\n * dela (o da página não está em foco e recusa): passe o elemento clicado.\n */\nexport async function copyText(text: string, from?: Element | null) {\n try {\n const view = from?.ownerDocument.defaultView ?? window\n await view.navigator.clipboard.writeText(text)\n return true\n } catch {\n return false\n }\n}\n\nexport function CopyButton({ text, label = 'Copiar' }: { text: string; label?: string }) {\n const [copied, setCopied] = useState(false)\n return (\n <Button\n size=\"small\"\n onClick={async (event) => {\n if (await copyText(text, event.currentTarget)) {\n setCopied(true)\n setTimeout(() => setCopied(false), 1200)\n }\n }}\n >\n {copied ? 'Copiado!' : label}\n </Button>\n )\n}\n\nconst COLLAPSED_KEY = 'bm-dashboard-devtools:collapsed'\n\nfunction loadCollapsed(): string[] {\n try {\n const saved = JSON.parse(localStorage.getItem(COLLAPSED_KEY) ?? '[]')\n return Array.isArray(saved) ? saved : []\n } catch {\n return []\n }\n}\n\n/** Seção recolhida (lembrada entre recargas, pela chave). */\nfunction useCollapsed(key: string | undefined) {\n const [collapsed, setCollapsed] = useState(() => !!key && loadCollapsed().includes(key))\n const toggle = () => {\n if (!key) return\n const next = !collapsed\n setCollapsed(next)\n try {\n const others = loadCollapsed().filter((item) => item !== key)\n localStorage.setItem(COLLAPSED_KEY, JSON.stringify(next ? [...others, key] : others))\n } catch {}\n }\n return [collapsed, toggle] as const\n}\n\nexport function Section({\n title,\n actions,\n collapseKey,\n children\n}: {\n title: ReactNode\n actions?: ReactNode\n /** Com chave, o título recolhe/expande a seção (a escolha fica salva no navegador). */\n collapseKey?: string\n children: ReactNode\n}) {\n const [collapsed, toggle] = useCollapsed(collapseKey)\n return (\n <Box sx={{ mb: collapsed ? 0.5 : 2 }}>\n <Box sx={{ display: 'flex', alignItems: 'center', gap: 1, mb: 0.5, minHeight: 30 }}>\n <Typography\n variant=\"overline\"\n component={collapseKey ? 'button' : 'span'}\n {...(collapseKey && {\n type: 'button',\n onClick: toggle,\n 'aria-expanded': !collapsed,\n title: collapsed ? 'Expandir' : 'Recolher'\n })}\n sx={{\n color: 'text.secondary',\n lineHeight: 1.5,\n fontWeight: 700,\n ...(collapseKey && {\n display: 'flex',\n alignItems: 'center',\n gap: 0.5,\n p: 0,\n border: 0,\n bgcolor: 'transparent',\n cursor: 'pointer',\n textAlign: 'left',\n '&:hover': { color: 'text.primary' }\n })\n }}\n >\n {collapseKey && (\n <Box\n component=\"span\"\n aria-hidden\n sx={{\n display: 'inline-block',\n fontSize: 9,\n transition: 'transform .15s',\n transform: collapsed ? 'rotate(-90deg)' : 'none'\n }}\n >\n ▼\n </Box>\n )}\n {title}\n </Typography>\n {!collapsed && <Box sx={{ ml: 'auto', display: 'flex', gap: 0.5 }}>{actions}</Box>}\n </Box>\n {!collapsed && children}\n </Box>\n )\n}\n\nexport function CodeBlock({\n code,\n maxHeight = 260,\n sql = false\n}: {\n code: string\n maxHeight?: number\n /** Colore como SQL. */\n sql?: boolean\n}) {\n return (\n <Box sx={{ position: 'relative' }}>\n <Box\n component=\"pre\"\n sx={{\n m: 0,\n p: 1.25,\n pr: 9,\n maxHeight,\n overflow: 'auto',\n fontFamily: MONO,\n fontSize: 12,\n lineHeight: 1.5,\n bgcolor: 'rgba(0,0,0,.35)',\n borderRadius: 1,\n whiteSpace: 'pre'\n }}\n >\n {sql ? <HighlightedSql code={code} /> : code}\n </Box>\n <Box sx={{ position: 'absolute', top: 4, right: 4 }}>\n <CopyButton text={code} />\n </Box>\n </Box>\n )\n}\n\n/** Substitui os `?` pelos parâmetros, para colar o SQL direto num cliente de banco. */\nexport function inlineParams(sql: string, params: (string | number)[]) {\n let index = 0\n return sql.replace(/\\?/g, () => {\n const value = params[index++]\n if (value === undefined) return '?'\n return typeof value === 'number' ? String(value) : `'${value.replaceAll(\"'\", \"''\")}'`\n })\n}\n\nconst MAX_ROWS = 500\n\n/** Ordena linhas de resultado por uma coluna; `null` sempre no fim. */\nfunction compareCells(\n a: DashboardRow,\n b: DashboardRow,\n { column, direction }: { column: string; direction: 'asc' | 'desc' }\n) {\n const [x, y] = [a[column], b[column]]\n if (x === null || x === undefined) return y === null || y === undefined ? 0 : 1\n if (y === null || y === undefined) return -1\n const order =\n typeof x === 'number' && typeof y === 'number'\n ? x - y\n : String(x).localeCompare(String(y), 'pt-BR', { numeric: true })\n return direction === 'asc' ? order : -order\n}\n\nexport function ResultTable({\n rows,\n maxHeight = 320\n}: {\n rows: DashboardRow[]\n maxHeight?: number\n}) {\n const [sort, setSort] = useState<{ column: string; direction: 'asc' | 'desc' } | null>(null)\n if (!rows.length)\n return <Typography sx={{ color: 'text.secondary', fontSize: 12 }}>Nenhuma linha.</Typography>\n const columns = Object.keys(rows[0])\n const sorted = sort ? [...rows].sort((a, b) => compareCells(a, b, sort)) : rows\n // Clique alterna crescente → decrescente → ordem original\n const toggleSort = (column: string) =>\n setSort((current) =>\n current?.column !== column\n ? { column, direction: 'asc' }\n : current.direction === 'asc'\n ? { column, direction: 'desc' }\n : null\n )\n return (\n <>\n <TableContainer sx={{ maxHeight, border: 1, borderColor: 'divider', borderRadius: 1 }}>\n <Table size=\"small\" stickyHeader>\n <TableHead>\n <TableRow>\n {columns.map((column) => (\n <TableCell\n key={column}\n sortDirection={sort?.column === column ? sort.direction : false}\n sx={{ fontFamily: MONO, fontWeight: 700, whiteSpace: 'nowrap' }}\n >\n <TableSortLabel\n active={sort?.column === column}\n direction={sort?.column === column ? sort.direction : 'asc'}\n onClick={() => toggleSort(column)}\n >\n {column}\n </TableSortLabel>\n </TableCell>\n ))}\n </TableRow>\n </TableHead>\n <TableBody>\n {sorted.slice(0, MAX_ROWS).map((row, index) => (\n // biome-ignore lint/suspicious/noArrayIndexKey: linhas de resultado não têm id\n <TableRow key={index} hover>\n {columns.map((column) => (\n <TableCell\n key={column}\n align={typeof row[column] === 'number' ? 'right' : 'left'}\n sx={{ fontFamily: MONO, whiteSpace: 'nowrap' }}\n >\n {row[column] === null ? (\n <Box component=\"span\" sx={{ color: 'text.disabled' }}>\n null\n </Box>\n ) : (\n String(row[column])\n )}\n </TableCell>\n ))}\n </TableRow>\n ))}\n </TableBody>\n </Table>\n </TableContainer>\n {rows.length > MAX_ROWS && (\n <Typography sx={{ color: 'text.secondary', fontSize: 12, mt: 0.5 }}>\n Mostrando {MAX_ROWS} de {rows.length} linhas.\n </Typography>\n )}\n </>\n )\n}\n\nexport function Empty({ children }: { children: ReactNode }) {\n return (\n <Box\n sx={{\n height: '100%',\n minHeight: 120,\n display: 'flex',\n alignItems: 'center',\n justifyContent: 'center',\n color: 'text.secondary',\n fontSize: 13,\n textAlign: 'center',\n p: 2\n }}\n >\n {children}\n </Box>\n )\n}\n\nconst DIFF_LINE_COLOR = {\n same: 'transparent',\n added: 'rgba(81, 207, 102, .18)',\n removed: 'rgba(255, 107, 107, .18)'\n} as const\n\n/** Diff de arquivo; linhas iguais longe de mudanças ficam recolhidas. */\nexport function FileDiff({ lines, context = 3 }: { lines: DiffLine[]; context?: number }) {\n const near = lines.map((_, index) =>\n lines\n .slice(Math.max(0, index - context), index + context + 1)\n .some((line) => line.kind !== 'same')\n )\n const output: ReactNode[] = []\n let skipped = 0\n lines.forEach((line, index) => {\n if (!near[index]) {\n skipped++\n return\n }\n if (skipped) {\n output.push(\n // biome-ignore lint/suspicious/noArrayIndexKey: posição do trecho recolhido no diff\n <Box key={`skip-${index}`} sx={{ color: 'text.disabled', px: 1 }}>\n ⋯ {skipped} linhas iguais\n </Box>\n )\n skipped = 0\n }\n output.push(\n // biome-ignore lint/suspicious/noArrayIndexKey: linhas de um diff fixo, sem id próprio\n <Box key={index} sx={{ bgcolor: DIFF_LINE_COLOR[line.kind], px: 1, whiteSpace: 'pre' }}>\n {line.kind === 'added' ? '+ ' : line.kind === 'removed' ? '- ' : ' '}\n {line.text}\n </Box>\n )\n })\n if (skipped)\n output.push(\n <Box key=\"skip-end\" sx={{ color: 'text.disabled', px: 1 }}>\n ⋯ {skipped} linhas iguais\n </Box>\n )\n return (\n <Box\n sx={{\n fontFamily: MONO,\n fontSize: 12,\n lineHeight: 1.5,\n bgcolor: 'rgba(0,0,0,.35)',\n borderRadius: 1,\n py: 1,\n overflow: 'auto',\n maxHeight: 420\n }}\n >\n {lines.some((line) => line.kind !== 'same') ? (\n output\n ) : (\n <Box sx={{ px: 1 }}>Sem mudanças.</Box>\n )}\n </Box>\n )\n}\n\nconst DIFF_KIND_LABEL: Record<RowDiff['kind'], string> = {\n missing: 'sumiu',\n extra: 'nova',\n changed: 'mudou'\n}\n\n/** Linhas que diferem entre dois resultados (esperado x atual). */\nexport function RowDiffTable({\n diffs,\n expectedLabel = 'esperado',\n actualLabel = 'atual'\n}: {\n diffs: RowDiff[]\n expectedLabel?: string\n actualLabel?: string\n}) {\n if (!diffs.length)\n return <Typography sx={{ color: 'success.main', fontSize: 12 }}>Resultados iguais.</Typography>\n return (\n <TableContainer sx={{ maxHeight: 320, border: 1, borderColor: 'divider', borderRadius: 1 }}>\n <Table size=\"small\" stickyHeader>\n <TableHead>\n <TableRow>\n <TableCell>linha</TableCell>\n <TableCell>dimensões</TableCell>\n <TableCell>medida</TableCell>\n <TableCell align=\"right\">{expectedLabel}</TableCell>\n <TableCell align=\"right\">{actualLabel}</TableCell>\n <TableCell align=\"right\">diferença</TableCell>\n </TableRow>\n </TableHead>\n <TableBody>\n {diffs.flatMap((diff) => {\n const where = JSON.stringify(diff.dimensions)\n if (diff.kind !== 'changed')\n return (\n <TableRow key={where}>\n <TableCell sx={{ color: diff.kind === 'missing' ? 'error.main' : 'info.main' }}>\n {DIFF_KIND_LABEL[diff.kind]}\n </TableCell>\n <TableCell sx={{ fontFamily: MONO }} colSpan={5}>\n {where}\n </TableCell>\n </TableRow>\n )\n return diff.changes.map((change) => (\n <TableRow key={`${where}-${change.measure}`}>\n <TableCell sx={{ color: 'warning.main' }}>{DIFF_KIND_LABEL.changed}</TableCell>\n <TableCell sx={{ fontFamily: MONO }}>{where}</TableCell>\n <TableCell sx={{ fontFamily: MONO }}>{change.measure}</TableCell>\n <TableCell align=\"right\" sx={{ fontFamily: MONO }}>\n {String(change.expected)}\n </TableCell>\n <TableCell align=\"right\" sx={{ fontFamily: MONO }}>\n {String(change.actual)}\n </TableCell>\n <TableCell align=\"right\" sx={{ fontFamily: MONO }}>\n {typeof change.expected === 'number' && typeof change.actual === 'number'\n ? (change.actual - change.expected).toFixed(4)\n : ''}\n </TableCell>\n </TableRow>\n ))\n })}\n </TableBody>\n </Table>\n </TableContainer>\n )\n}\n","import { Alert, Box, Button, Chip, TextField, Typography } from '@mui/material'\nimport { useEffect, useState } from 'react'\nimport type { DashboardDevtoolsContext } from '../client/DashboardProvider'\nimport { useDashboard } from '../client/DashboardProvider'\nimport type { DashboardFilters } from '../types'\nimport { MONO, Section } from './ui'\n\nfunction parseFilters(text: string): DashboardFilters {\n const parsed: unknown = JSON.parse(text)\n if (typeof parsed !== 'object' || parsed === null || Array.isArray(parsed))\n throw new Error('Esperado um objeto { dimensão: [valores] }')\n for (const [name, values] of Object.entries(parsed)) {\n const valid =\n Array.isArray(values) &&\n values.every((value) => typeof value === 'string' || typeof value === 'number')\n if (!valid) throw new Error(`\"${name}\" precisa ser uma lista de textos/números`)\n }\n return parsed as DashboardFilters\n}\n\n/** Estado dos filtros do `DashboardProvider`, editável como JSON. */\nexport function FiltersPanel({ devtools }: { devtools: DashboardDevtoolsContext }) {\n const { filters, setFilter } = useDashboard()\n const current = JSON.stringify(filters, null, 2)\n const [text, setText] = useState(current)\n const [error, setError] = useState<string | null>(null)\n\n // Filtro alterado na página: o texto acompanha (descarta edição não aplicada)\n useEffect(() => {\n setText(current)\n setError(null)\n }, [current])\n\n const active = Object.entries(filters).filter(([, values]) => values.length)\n\n const apply = () => {\n try {\n devtools.setFilters(parseFilters(text))\n setError(null)\n } catch (err) {\n setError((err as Error).message)\n }\n }\n\n return (\n <Box sx={{ p: 1.5, overflow: 'auto', height: '100%' }}>\n <Section\n title=\"Filtros ativos\"\n actions={\n <>\n <Button size=\"small\" onClick={() => devtools.setFilters(devtools.defaultFilters)}>\n Restaurar padrão\n </Button>\n <Button size=\"small\" onClick={() => devtools.setFilters({})}>\n Limpar tudo\n </Button>\n </>\n }\n >\n <Box sx={{ display: 'flex', gap: 1, flexWrap: 'wrap' }}>\n {active.map(([name, values]) => (\n <Chip\n key={name}\n size=\"small\"\n label={`${name}: ${values.join(', ')}`}\n onDelete={() => setFilter(name, [])}\n sx={{ fontFamily: MONO }}\n />\n ))}\n {!active.length && (\n <Typography sx={{ fontSize: 12, color: 'text.secondary' }}>\n Nenhum filtro: tudo aparece como \"Todos\".\n </Typography>\n )}\n </Box>\n </Section>\n\n <Section\n title=\"Editar como JSON\"\n actions={\n <Button size=\"small\" variant=\"contained\" disabled={text === current} onClick={apply}>\n Aplicar\n </Button>\n }\n >\n <TextField\n fullWidth\n multiline\n minRows={6}\n maxRows={18}\n value={text}\n onChange={(e) => setText(e.target.value)}\n error={!!error}\n sx={{ '& .MuiInputBase-input': { fontFamily: MONO, fontSize: 12 } }}\n />\n {error && (\n <Alert severity=\"error\" sx={{ mt: 1 }}>\n {error}\n </Alert>\n )}\n </Section>\n\n <Section title=\"Padrão do provider (defaultFilters)\">\n <Typography sx={{ fontFamily: MONO, fontSize: 12 }}>\n {JSON.stringify(devtools.defaultFilters)}\n </Typography>\n </Section>\n </Box>\n )\n}\n","import { createTheme, type Theme, ThemeProvider } from '@mui/material'\nimport { type ReactNode, useEffect, useMemo, useRef, useState } from 'react'\nimport { createPortal } from 'react-dom'\n\n/**\n * Devtools numa janela separada do navegador (popup), para usar com a página em tela cheia ou em\n * outro monitor. O painel continua sendo renderizado pela árvore React da página (mesmo contexto,\n * mesmo store), só que via portal no `document` do popup:\n *\n * - os estilos do emotion/MUI vão para o `<head>` da página; aqui eles são espelhados no popup;\n * - menus, tooltips e diálogos do MUI montam no `body` da página por padrão: o tema da janela\n * aponta o `container` deles para o popup.\n *\n * Recarregar a página derruba o vínculo (o popup é de outra árvore): o popup avisa e o botão do\n * devtools na página reconecta (abrir popup exige um clique, o navegador bloqueia sem gesto).\n */\n\nconst WINDOW_NAME = 'bm-bi-devtools'\n\n/** Abre (ou reaproveita, se ainda estiver aberta) a janela do devtools. `null` = bloqueada. */\nexport function openDevtoolsWindow(): Window | null {\n const width = Math.min(1100, window.screen.availWidth)\n const height = Math.min(720, window.screen.availHeight)\n return window.open('', WINDOW_NAME, `popup,width=${width},height=${height}`)\n}\n\nconst isStyleNode = (node: Node): node is HTMLStyleElement | HTMLLinkElement =>\n node instanceof HTMLStyleElement || (node instanceof HTMLLinkElement && node.rel === 'stylesheet')\n\n/** Cópia de um `<style>`/`<link>`; estilo inserido por `insertRule` (sem texto) vai pelas regras. */\nfunction cloneStyle(node: HTMLStyleElement | HTMLLinkElement, target: Document) {\n const clone = target.importNode(node, true)\n if (node instanceof HTMLStyleElement && !node.textContent && node.sheet?.cssRules.length)\n clone.textContent = [...node.sheet.cssRules].map((rule) => rule.cssText).join('\\n')\n return clone\n}\n\n/** Copia os estilos da página para o popup e acompanha os que entrarem/saírem depois. */\nfunction mirrorStyles(source: Document, target: Document) {\n const clones = new Map<Node, Node>()\n const add = (node: Node) => {\n if (!isStyleNode(node) || clones.has(node)) return\n const clone = cloneStyle(node, target)\n clones.set(node, clone)\n target.head.appendChild(clone)\n }\n for (const node of source.head.querySelectorAll('style, link[rel=\"stylesheet\"]')) add(node)\n\n const observer = new MutationObserver((mutations) => {\n for (const mutation of mutations) {\n if (mutation.type === 'characterData' || mutation.target !== source.head) {\n // Texto de um <style> mudou: recopia\n const style = (\n mutation.target instanceof Element ? mutation.target : mutation.target.parentElement\n )?.closest('style')\n const clone = style && clones.get(style)\n if (style && clone) {\n const next = cloneStyle(style, target)\n target.head.replaceChild(next, clone)\n clones.set(style, next)\n }\n continue\n }\n for (const node of mutation.addedNodes) add(node)\n for (const node of mutation.removedNodes) {\n clones.get(node)?.parentNode?.removeChild(clones.get(node) as Node)\n clones.delete(node)\n }\n }\n })\n observer.observe(source.head, { childList: true, subtree: true, characterData: true })\n return () => observer.disconnect()\n}\n\n/** Tema com os portais do MUI (menus, tooltips, diálogos) dentro do popup. */\nfunction windowTheme(base: Theme, container: HTMLElement) {\n return createTheme(base, {\n components: {\n MuiModal: { defaultProps: { container } },\n MuiPopover: { defaultProps: { container } },\n MuiPopper: { defaultProps: { container } },\n MuiDialog: { defaultProps: { container } },\n MuiMenu: { defaultProps: { container } }\n }\n })\n}\n\nexport function DevtoolsWindow({\n popup,\n title,\n theme,\n onClosed,\n children\n}: {\n popup: Window\n title: string\n theme: Theme\n /** O usuário fechou a janela. */\n onClosed: () => void\n children: ReactNode\n}) {\n const [root, setRoot] = useState<HTMLElement | null>(null)\n const onClosedRef = useRef(onClosed)\n onClosedRef.current = onClosed\n\n useEffect(() => {\n const doc = popup.document\n doc.title = title\n // Reaproveitada depois de recarregar a página: limpa o que a árvore anterior deixou\n doc.head.replaceChildren()\n doc.body.replaceChildren()\n const meta = doc.createElement('meta')\n meta.setAttribute('charset', 'utf-8')\n doc.head.appendChild(meta)\n const base = doc.createElement('style')\n base.textContent = `html, body { height: 100%; margin: 0; background: ${theme.palette.background.paper}; color-scheme: dark; } body { font-family: ${theme.typography.fontFamily}; } #${WINDOW_NAME} { height: 100%; display: flex; flex-direction: column; }`\n doc.head.appendChild(base)\n const container = doc.createElement('div')\n container.id = WINDOW_NAME\n doc.body.appendChild(container)\n const stopMirror = mirrorStyles(document, doc)\n setRoot(container)\n\n // Janela fechada pelo usuário (o `pagehide` do popup não é confiável em todos os navegadores)\n const poll = setInterval(() => {\n if (popup.closed) onClosedRef.current()\n }, 400)\n // A página saiu (recarregou/navegou): o popup fica órfão, avisa como reconectar\n const onPageHide = () => {\n stopMirror()\n doc.body.innerHTML = `<p style=\"font: 14px sans-serif; color: #ccc; padding: 24px\">A página do dashboard recarregou. Clique no botão <b style=\"color: #F58220\">◆ BI</b> da página para reconectar o devtools a esta janela.</p>`\n }\n window.addEventListener('pagehide', onPageHide)\n return () => {\n clearInterval(poll)\n window.removeEventListener('pagehide', onPageHide)\n stopMirror()\n setRoot(null)\n }\n }, [popup, title, theme])\n\n const localTheme = useMemo(() => root && windowTheme(theme, root), [theme, root])\n\n if (!root || !localTheme) return null\n return createPortal(<ThemeProvider theme={localTheme}>{children}</ThemeProvider>, root)\n}\n","import { Box } from '@mui/material'\nimport { useEffect, useState } from 'react'\nimport { INSPECT_ATTRIBUTE } from '../client/useModelQuery'\n\n/**\n * Liga componente da página <-> consulta do devtools. Os componentes marcam o elemento raiz com\n * `inspectProps` do `useModelQuery` (`data-bm-dashboard-query=\"<instanceId>\"`).\n */\n\n/** Marca os elementos do próprio painel, que o modo de inspeção ignora. */\nexport const DEVTOOLS_ATTRIBUTE = 'data-bm-devtools'\n\nexport const findQueryElement = (instanceId: string) =>\n document.querySelector<HTMLElement>(`[${INSPECT_ATTRIBUTE}=\"${CSS.escape(instanceId)}\"]`)\n\nexport function scrollToQuery(instanceId: string) {\n findQueryElement(instanceId)?.scrollIntoView({ behavior: 'smooth', block: 'center' })\n}\n\n/** Retângulo do elemento, acompanhando scroll/resize. */\nfunction useElementRect(instanceId: string | null) {\n const [rect, setRect] = useState<DOMRect | null>(null)\n useEffect(() => {\n if (!instanceId) {\n setRect(null)\n return\n }\n let frame = 0\n const update = () => {\n setRect(findQueryElement(instanceId)?.getBoundingClientRect() ?? null)\n frame = requestAnimationFrame(update)\n }\n update()\n return () => cancelAnimationFrame(frame)\n }, [instanceId])\n return rect\n}\n\nexport function HighlightOverlay({\n instanceId,\n label,\n zIndex\n}: {\n instanceId: string | null\n label?: string\n zIndex: number\n}) {\n const rect = useElementRect(instanceId)\n if (!rect) return null\n return (\n <Box\n sx={{\n position: 'fixed',\n top: rect.top,\n left: rect.left,\n width: rect.width,\n height: rect.height,\n zIndex,\n pointerEvents: 'none',\n outline: '2px solid #F58220',\n bgcolor: 'rgba(245, 130, 32, .12)',\n borderRadius: 0.5\n }}\n >\n {label && (\n <Box\n sx={{\n position: 'absolute',\n left: -2,\n bottom: '100%',\n px: 0.75,\n py: 0.25,\n bgcolor: '#F58220',\n color: '#111',\n fontSize: 11,\n fontWeight: 700,\n whiteSpace: 'nowrap',\n fontFamily: 'ui-monospace, monospace'\n }}\n >\n {label}\n </Box>\n )}\n </Box>\n )\n}\n\n/**\n * Modo de inspeção: passar o mouse num componente do dashboard destaca a consulta dele; clicar\n * seleciona no painel. O clique é engolido para não acionar o componente.\n */\nexport function useInspectMode({\n active,\n onHover,\n onPick\n}: {\n active: boolean\n onHover: (instanceId: string | null) => void\n onPick: (instanceId: string) => void\n}) {\n useEffect(() => {\n if (!active) return\n const target = (event: Event) => {\n const element = event.target as Element | null\n if (!element?.closest || element.closest(`[${DEVTOOLS_ATTRIBUTE}]`)) return null\n return element.closest(`[${INSPECT_ATTRIBUTE}]`)?.getAttribute(INSPECT_ATTRIBUTE) ?? null\n }\n const move = (event: MouseEvent) => onHover(target(event))\n const click = (event: MouseEvent) => {\n const instanceId = target(event)\n if (!instanceId) return\n event.preventDefault()\n event.stopPropagation()\n onPick(instanceId)\n }\n // O Select do MUI abre no mousedown, antes do click\n const press = (event: MouseEvent) => {\n if (!target(event)) return\n event.preventDefault()\n event.stopPropagation()\n }\n const previousCursor = document.body.style.cursor\n document.body.style.cursor = 'crosshair'\n document.addEventListener('mousemove', move, true)\n document.addEventListener('mousedown', press, true)\n document.addEventListener('click', click, true)\n return () => {\n document.body.style.cursor = previousCursor\n document.removeEventListener('mousemove', move, true)\n document.removeEventListener('mousedown', press, true)\n document.removeEventListener('click', click, true)\n onHover(null)\n }\n }, [active, onHover, onPick])\n}\n","export type DiffLine = { kind: 'same' | 'added' | 'removed'; text: string }\n\n/** Diff de linhas por LCS. Suficiente para arquivos de modelo (centenas de linhas). */\nexport function lineDiff(before: string, after: string): DiffLine[] {\n const a = before.split('\\n')\n const b = after.split('\\n')\n const lcs: number[][] = Array.from({ length: a.length + 1 }, () =>\n new Array(b.length + 1).fill(0)\n )\n for (let i = a.length - 1; i >= 0; i--)\n for (let j = b.length - 1; j >= 0; j--)\n lcs[i][j] = a[i] === b[j] ? lcs[i + 1][j + 1] + 1 : Math.max(lcs[i + 1][j], lcs[i][j + 1])\n\n const lines: DiffLine[] = []\n let i = 0\n let j = 0\n while (i < a.length && j < b.length) {\n if (a[i] === b[j]) {\n lines.push({ kind: 'same', text: a[i++] })\n j++\n } else if (lcs[i + 1][j] >= lcs[i][j + 1]) lines.push({ kind: 'removed', text: a[i++] })\n else lines.push({ kind: 'added', text: b[j++] })\n }\n while (i < a.length) lines.push({ kind: 'removed', text: a[i++] })\n while (j < b.length) lines.push({ kind: 'added', text: b[j++] })\n return lines\n}\n","import {\n Alert,\n Box,\n Button,\n Checkbox,\n Dialog,\n DialogActions,\n DialogContent,\n DialogTitle,\n FormControlLabel,\n IconButton,\n ListSubheader,\n Menu,\n MenuItem,\n Popover,\n TextField,\n Tooltip,\n Typography\n} from '@mui/material'\nimport {\n type ChangeEvent,\n type DragEvent,\n type ReactNode,\n useEffect,\n useMemo,\n useRef,\n useState,\n useSyncExternalStore\n} from 'react'\nimport type { DashboardDevtoolsContext } from '../client/DashboardProvider'\nimport { useDashboard } from '../client/DashboardProvider'\nimport { formatMeasure } from '../client/format'\nimport { INSPECT_ATTRIBUTE } from '../client/useModelQuery'\nimport { canonicalJson } from '../codegen'\nimport {\n type FormatRule,\n NUMERIC_OPERATORS,\n RULE_OPERATOR_LABEL,\n RULE_OPERATORS,\n type RuleOperator,\n UNARY_OPERATORS\n} from '../formatRules'\nimport {\n BUILTIN_CHART_TYPES,\n CANVAS_PRESETS,\n type CanvasDef,\n CARD_FIELDS,\n CARDS_FIELDS,\n type CardsStyle,\n type CardStyle,\n type ChartDef,\n type ChartNumberFormat,\n type ChartsLayout,\n type ChartTypes,\n COLUMN_ALIGNS,\n COLUMN_VERTICAL_ALIGNS,\n type ColumnAlign,\n type ColumnVerticalAlign,\n chartColumns,\n chartOfType,\n chartReferences,\n FILTER_FIELDS,\n type FieldSpec,\n type FilterDef,\n filterReferences,\n LAYOUT_COLUMNS,\n layoutFileContent,\n layoutModelWarnings,\n PERCENT_PREFIX,\n percentColumn,\n tableColumns,\n validateLayout\n} from '../layout'\nimport { type ModelDef, VALUE_FORMATS } from '../model'\nimport type { DevtoolsCapabilities, SaveModelResult } from '../types'\nimport {\n LAYOUT_ITEM_ATTRIBUTE,\n type LayoutItem,\n layoutItemKey,\n parseLayoutItemKey\n} from './layoutStore'\nimport { lineDiff } from './lineDiff'\nimport { errorMessage } from './store'\nimport { CopyButton, Empty, FileDiff, MONO, Section } from './ui'\n\ntype Props = {\n devtools: DashboardDevtoolsContext\n /** Modelo em vigor (rascunho, se houver), para listar dimensões e medidas. */\n model: ModelDef\n capabilities: DevtoolsCapabilities | null\n /** Item escolhido pelo inspetor (`layoutItemKey`); objeto novo a cada clique. */\n picked: { item: string } | null\n /** Destaca a consulta do gráfico na página. */\n onHover: (instanceId: string | null) => void\n}\n\nconst inputSx = { '& .MuiInputBase-input': { fontFamily: MONO, fontSize: 12 } }\n\nconst itemElement = (layoutId: string, item: LayoutItem) =>\n document.querySelector<HTMLElement>(\n `[${LAYOUT_ITEM_ATTRIBUTE}=\"${CSS.escape(layoutItemKey(layoutId, item))}\"]`\n )\n\nconst itemQueryId = (layoutId: string, item: LayoutItem) =>\n itemElement(layoutId, item)\n ?.querySelector(`[${INSPECT_ATTRIBUTE}]`)\n ?.getAttribute(INSPECT_ATTRIBUTE) ?? null\n\n/** Item escolhido na lista: a tela (`layout.canvas`), os cards (`layout.cards`), um filtro ou um gráfico. */\ntype Selection = LayoutItem | { kind: 'canvas' } | { kind: 'cards' }\n\ntype DragState = { kind: LayoutItem['kind']; from: number; to: number }\n\nconst SIDEBAR_KEY = 'bm-dashboard-devtools:layout-sidebar'\n\n/** Abaixo disso a lista vai para cima do formulário, em vez de ficar ao lado. */\nconst STACK_WIDTH = 640\n\nfunction loadSidebar() {\n try {\n return localStorage.getItem(SIDEBAR_KEY) !== 'closed'\n } catch {\n return true\n }\n}\n\n/** Largura do elemento, acompanhando o redimensionamento do devtools. */\nfunction useWidth() {\n const [element, setElement] = useState<HTMLElement | null>(null)\n const [width, setWidth] = useState(Number.POSITIVE_INFINITY)\n useEffect(() => {\n if (!element) return\n // O da janela do elemento: com o devtools em janela separada, o da página não vê o elemento\n const Observer = element.ownerDocument.defaultView?.ResizeObserver ?? ResizeObserver\n const observer = new Observer(([entry]) => entry && setWidth(entry.contentRect.width))\n observer.observe(element)\n return () => observer.disconnect()\n }, [element])\n return [setElement, width] as const\n}\n\n/** Move o item `from` para antes da posição `to` (`to === list.length` = fim). */\nfunction moveTo<T>(list: T[], from: number, to: number) {\n const next = [...list]\n const [item] = next.splice(from, 1)\n next.splice(to > from ? to - 1 : to, 0, item as T)\n return next\n}\n\nconst uniqueId = (charts: ChartDef[], base: string) => {\n const ids = new Set(charts.map((chart) => chart.id))\n if (!ids.has(base)) return base\n let n = 2\n while (ids.has(`${base}-${n}`)) n++\n return `${base}-${n}`\n}\n\n/** Objeto sem nenhum campo sai do JSON. */\nconst nonEmpty = <T extends object>(object: T) => (Object.keys(object).length ? object : undefined)\n\n/** Campos do card de um gráfico, com o padrão do layout (`cards`) no lugar do padrão da lib. */\nconst chartCardFields = (cards: CardsStyle | undefined) =>\n Object.fromEntries(\n Object.entries(CARD_FIELDS).map(([key, spec]) => [\n key,\n { ...spec, default: cards?.[key as keyof CardStyle] ?? spec.default } as FieldSpec\n ])\n )\n\nconst cardsSummary = (cards: CardsStyle | undefined) => {\n const { gap, ...style } = cards ?? {}\n const custom = Object.keys(style).length\n return `espaço ${String(gap ?? CARDS_FIELDS.gap?.default)}px · ${custom ? `${custom} ajuste(s) de estilo` : 'estilo padrão'}`\n}\n\n/** Campo opcional vazio sai do objeto, para o JSON ficar só com o que foi definido. */\nfunction withField<T extends object>(object: T, key: keyof T, value: unknown): T {\n const next = { ...object }\n if (value === undefined || value === '') delete next[key]\n else (next as Record<keyof T, unknown>)[key] = value\n return next\n}\n\nconst NEW_CHART: Record<string, { id: string; title: string; span: number }> = {\n kpi: { id: 'kpi', title: 'Novo KPI', span: 3 },\n combo: { id: 'grafico', title: 'Novo gráfico', span: 6 },\n bar: { id: 'grafico', title: 'Novo gráfico', span: 6 },\n donut: { id: 'grafico', title: 'Novo gráfico', span: 6 },\n table: { id: 'tabela', title: 'Nova tabela', span: 12 }\n}\n\nconst newChart = (type: string, model: ModelDef, charts: ChartDef[], types: ChartTypes) => {\n // Tipo do app: id pelo nome do tipo, meia largura\n const { id, ...rest } = NEW_CHART[type] ?? {\n id: type,\n title: `Novo ${types[type]?.label ?? type}`,\n span: 6\n }\n return chartOfType(type, model, { id: uniqueId(charts, id), ...rest }, types)\n}\n\nconst chartSummary = (chart: ChartDef, types: ChartTypes) => {\n const { dimensions, measures } = chartReferences(chart, types)\n return `${chart.type} · ${dimensions.join(', ') || '—'} · ${measures.join(', ')}`\n}\n\n/**\n * Editor dos layouts da página (filtros do `<DashboardFilters>` e gráficos do `<DashboardCharts>`).\n * Como no modelo: as edições ficam no editor até \"Aplicar na página\" (vira rascunho e a página\n * re-renderiza com ele); \"Salvar no arquivo\" grava o JSON do layout com o que está no editor.\n */\nexport function LayoutPanel({ devtools, model, capabilities, picked, onHover }: Props) {\n const { layouts } = devtools\n const { fetcher, model: modelName, chartTypes } = useDashboard()\n const entries = useSyncExternalStore(layouts.subscribe, layouts.getSnapshot, layouts.getSnapshot)\n const [layoutId, setLayoutId] = useState<string | null>(null)\n const entry = entries.find((item) => item.registered.id === layoutId) ?? entries[0] ?? null\n const reference = entry ? (entry.draft ?? entry.registered) : null\n\n // Edições não aplicadas (guardadas no store: trocar de aba desmonta o painel)\n const pendingOrReference = () => (entry && layouts.pendingOf(entry.registered.id)) ?? reference\n const [editing, setEditingState] = useState<ChartsLayout | null>(pendingOrReference)\n const [selection, setSelection] = useState<Selection | null>(null)\n const [sidebar, setSidebar] = useState(loadSidebar)\n const [drag, setDrag] = useState<DragState | null>(null)\n const [rootRef, rootWidth] = useWidth()\n const [editorRef, editorWidth] = useWidth()\n const [busy, setBusy] = useState(false)\n const [actionError, setActionError] = useState<string | null>(null)\n const [save, setSave] = useState<SaveModelResult | null>(null)\n const [addMenu, setAddMenu] = useState<HTMLElement | null>(null)\n\n const referenceKey = canonicalJson(reference)\n /** Muda o editor e guarda como pendente o que difere do que a página mostra. */\n const setEditing = (next: ChartsLayout | null) => {\n setEditingState(next)\n if (entry)\n layouts.setPending(\n entry.registered.id,\n next && canonicalJson(next) !== referenceKey ? next : null\n )\n }\n // Rascunho descartado, arquivo recarregado ou outro layout: o editor acompanha (mantendo as\n // edições pendentes daquele layout)\n const firstRun = useRef(true)\n useEffect(() => {\n if (firstRun.current) {\n firstRun.current = false\n return\n }\n setEditingState(pendingOrReference())\n }, [referenceKey])\n\n // Inspetor clicou num gráfico\n useEffect(() => {\n const parsed = picked && parseLayoutItemKey(picked.item)\n if (!parsed) return\n setLayoutId(parsed.layoutId)\n setSelection(parsed.item)\n }, [picked])\n\n const errors = useMemo(\n () => (editing ? validateLayout(editing, chartTypes) : []),\n [editing, chartTypes]\n )\n const warnings = useMemo(() => {\n if (!editing || errors.length) return []\n const list = layoutModelWarnings(editing, model, chartTypes)\n const { charts: chartFormatters = [], filters: filterFormatters } = entry?.parts ?? {}\n const serverTypes = new Set(capabilities?.chartTypes ?? [])\n for (const type of new Set(editing.charts.map((chart) => chart.type)))\n if (capabilities?.saveLayout && !BUILTIN_CHART_TYPES[type] && !serverTypes.has(type))\n list.push(\n `Tipo \"${type}\" não foi passado ao \\`devtools.chartTypes\\` do endpoint: \"Salvar no arquivo\" vai recusar.`\n )\n for (const chart of editing.charts)\n for (const name of chartReferences(chart, chartTypes).formatters)\n if (!chartFormatters.includes(name))\n list.push(\n `\"${chart.title || chart.id}\": formatter \"${name}\" não foi passado ao <DashboardCharts formatters>`\n )\n if (editing.canvas && !entry?.parts.canvas)\n list.push(\n 'A página não usa <DashboardCanvas layout={...}>: o tamanho fixo da tela não é aplicado.'\n )\n if (editing.filters?.length && !filterFormatters)\n list.push(\n 'A página não usa <DashboardFilters layout={...}>: os filtros do layout não aparecem.'\n )\n for (const filter of editing.filters ?? [])\n for (const name of filterReferences(filter).formatters)\n if (filterFormatters && !filterFormatters.includes(name))\n list.push(\n `filtro \"${filter.dimension}\": formatter \"${name}\" não foi passado ao <DashboardFilters formatters>`\n )\n return list\n }, [editing, errors, model, entry, chartTypes, capabilities])\n\n if (!entry || !editing)\n return (\n <Empty>\n Nenhum <code>{'<DashboardCharts layout={...} />'}</code> ou{' '}\n <code>{'<DashboardFilters layout={...} />'}</code> nesta página. Os gráficos e filtros\n editáveis pelo devtools vêm de um layout em JSON (ex.:{' '}\n <code>src/dashboard/layouts/&lt;id&gt;.json</code>\n ).\n </Empty>\n )\n\n const charts = editing.charts\n const filters = editing.filters ?? []\n const selectedFilter =\n selection?.kind === 'filter'\n ? (filters.find((filter) => filter.dimension === selection.key) ?? null)\n : null\n const selected =\n selection?.kind === 'filter' || selection?.kind === 'canvas' || selection?.kind === 'cards'\n ? null\n : (charts.find((chart) => chart.id === selection?.key) ?? charts[0] ?? null)\n const layoutKey = entry.registered.id\n const differsFromFile = canonicalJson(editing) !== canonicalJson(entry.registered)\n // Edições ainda não aplicadas (a página mostra o rascunho aplicado ou o arquivo)\n const dirty = canonicalJson(editing) !== referenceKey\n\n // Como no modelo: as edições ficam no editor até \"Aplicar na página\"\n const update = (next: ChartsLayout) => {\n setEditing(next)\n setSave(null)\n }\n const apply = () => {\n if (validateLayout(editing, chartTypes).length) return\n devtools.store.expectRefetch()\n layouts.setPending(entry.registered.id, null)\n layouts.setDraft(entry.registered.id, editing)\n }\n const setCharts = (next: ChartDef[]) => update({ ...editing, charts: next })\n const patchChart = (id: string, change: (chart: ChartDef) => ChartDef) =>\n setCharts(charts.map((chart) => (chart.id === id ? change(chart) : chart)))\n\n const setCanvas = (next: CanvasDef | undefined) => update(withField(editing, 'canvas', next))\n const setCards = (key: string, value: unknown) =>\n update(\n withField(\n editing,\n 'cards',\n nonEmpty(withField((editing.cards ?? {}) as Record<string, unknown>, key, value))\n )\n )\n\n const setFilters = (next: FilterDef[]) => update({ ...editing, filters: next })\n const patchFilter = (dimension: string, change: (filter: FilterDef) => FilterDef) =>\n setFilters(filters.map((filter) => (filter.dimension === dimension ? change(filter) : filter)))\n\n const toggleSidebar = () => {\n const next = !sidebar\n setSidebar(next)\n try {\n localStorage.setItem(SIDEBAR_KEY, next ? 'open' : 'closed')\n } catch {}\n }\n\n // Arrastar para reordenar: só dentro da mesma lista (filtros ou gráficos)\n const dragProps = (kind: LayoutItem['kind'], index: number, length: number) => ({\n dropBefore: drag?.kind === kind && drag.from !== index && drag.to === index,\n dropAfter: drag?.kind === kind && index === length - 1 && drag.to === length,\n onDragStart: () => setDrag({ kind, from: index, to: index }),\n onDragOver: (e: DragEvent<HTMLElement>) => {\n if (drag?.kind !== kind) return\n e.preventDefault()\n const rect = e.currentTarget.getBoundingClientRect()\n const to = e.clientY < rect.top + rect.height / 2 ? index : index + 1\n if (to !== drag.to) setDrag({ ...drag, to })\n },\n onDrop: () => {\n if (drag?.kind !== kind) return\n if (drag.to !== drag.from && drag.to !== drag.from + 1)\n if (kind === 'chart') setCharts(moveTo(charts, drag.from, drag.to))\n else setFilters(moveTo(filters, drag.from, drag.to))\n setDrag(null)\n },\n onDragEnd: () => setDrag(null)\n })\n\n const addFilter = () => {\n // Primeira dimensão que ainda não tem filtro\n const used = new Set(filters.map((filter) => filter.dimension))\n const dimension = Object.keys(model.dimensions).find((name) => !used.has(name))\n if (!dimension) return\n setFilters([...filters, { dimension }])\n setSelection({ kind: 'filter', key: dimension })\n }\n\n const focus = (item: LayoutItem) => {\n setSelection(item)\n // Lista empilhada sobre o formulário: fecha para o formulário ter espaço\n if (stacked) setSidebar(false)\n itemElement(layoutKey, item)?.scrollIntoView({ behavior: 'smooth', block: 'center' })\n }\n const stacked = rootWidth < STACK_WIDTH\n const formColumns = editorWidth < 420 ? 1 : editorWidth < 720 ? 2 : 4\n const selectedTitle =\n selection?.kind === 'canvas'\n ? 'Tela'\n : selection?.kind === 'cards'\n ? 'Cards'\n : selectedFilter\n ? selectedFilter.label ||\n model.dimensions[selectedFilter.dimension]?.label ||\n selectedFilter.dimension\n : selected\n ? selected.title || selected.id\n : ''\n const hover = (item: LayoutItem | null) => onHover(item && itemQueryId(layoutKey, item))\n\n const add = (type: string, base?: ChartDef) => {\n setAddMenu(null)\n const chart = base\n ? { ...base, id: uniqueId(charts, base.id), title: `${base.title} (cópia)` }\n : newChart(type, model, charts, chartTypes)\n const index = base ? charts.findIndex((item) => item.id === base.id) + 1 : charts.length\n setCharts([...charts.slice(0, index), chart, ...charts.slice(index)])\n setSelection({ kind: 'chart', key: chart.id })\n setTimeout(() =>\n itemElement(layoutKey, { kind: 'chart', key: chart.id })?.scrollIntoView({ block: 'center' })\n )\n }\n\n const saveFile = async (mode: 'preview' | 'write') => {\n setBusy(true)\n setActionError(null)\n try {\n const result = await fetcher({\n model: modelName,\n devtools: { saveLayout: { layout: editing, mode } }\n })\n setSave(mode === 'write' ? null : (result.devtools?.save ?? null))\n // Gravado: a página passa a mostrar o que foi salvo (mesmo sem ter aplicado); o Next recarrega\n // o JSON e o rascunho some sozinho quando bater com o arquivo\n if (mode === 'write' && editing && entry) {\n devtools.store.expectRefetch()\n layouts.setPending(entry.registered.id, null)\n layouts.setDraft(entry.registered.id, editing)\n }\n } catch (error) {\n setActionError(errorMessage(error))\n } finally {\n setBusy(false)\n }\n }\n\n return (\n <Box\n ref={rootRef}\n sx={{ display: 'flex', flexDirection: 'column', height: '100%', minHeight: 0 }}\n >\n <Box\n sx={{\n display: 'flex',\n alignItems: 'center',\n gap: 1,\n px: 1,\n py: 0.5,\n borderBottom: 1,\n borderColor: 'divider'\n }}\n >\n <SmallButton\n title={sidebar ? 'Recolher a lista' : 'Mostrar a lista'}\n onClick={toggleSidebar}\n >\n {sidebar ? '«' : '☰'}\n </SmallButton>\n <Typography noWrap sx={{ fontSize: 12, fontWeight: 700 }}>\n {stacked && sidebar ? `Layout ${layoutKey}` : selectedTitle}\n </Typography>\n </Box>\n <Box sx={{ flex: 1, minHeight: 0, display: 'flex' }}>\n {sidebar && (\n <Box\n sx={{\n overflow: 'auto',\n p: 1.5,\n ...(stacked\n ? { flex: 1 }\n : { width: 280, flexShrink: 0, borderRight: 1, borderColor: 'divider' })\n }}\n >\n {entries.length > 1 && (\n <TextField\n select\n size=\"small\"\n fullWidth\n label=\"Layout\"\n value={entry.registered.id}\n onChange={(e) => setLayoutId(e.target.value)}\n sx={{ ...inputSx, mb: 1.5 }}\n >\n {entries.map((item) => (\n <MenuItem key={item.registered.id} value={item.registered.id}>\n {item.registered.id}\n {item.draft ? ' · rascunho' : ''}\n </MenuItem>\n ))}\n </TextField>\n )}\n <Section title=\"Tela\" collapseKey=\"layout:lista:tela\">\n <ItemRow\n title={editing.canvas ? 'Tamanho fixo' : 'Responsiva'}\n subtitle={\n editing.canvas ? presetLabel(editing.canvas) : 'reorganiza conforme a largura'\n }\n selected={selection?.kind === 'canvas'}\n onSelect={() => {\n setSelection({ kind: 'canvas' })\n if (stacked) setSidebar(false)\n }}\n />\n <ItemRow\n title=\"Cards\"\n subtitle={cardsSummary(editing.cards)}\n selected={selection?.kind === 'cards'}\n onSelect={() => {\n setSelection({ kind: 'cards' })\n if (stacked) setSidebar(false)\n }}\n />\n </Section>\n <Section\n title={`Filtros (${filters.length})`}\n collapseKey=\"layout:lista:filtros\"\n actions={\n <Button\n size=\"small\"\n onClick={addFilter}\n disabled={filters.length >= Object.keys(model.dimensions).length}\n >\n + Novo\n </Button>\n }\n >\n {!filters.length && (\n <Typography sx={{ fontSize: 12, color: 'text.disabled', mb: 1 }}>\n Nenhum filtro no layout.\n </Typography>\n )}\n {filters.map((filter, index) => {\n const item: LayoutItem = { kind: 'filter', key: filter.dimension }\n return (\n <ItemRow\n key={filter.dimension}\n title={\n filter.label || model.dimensions[filter.dimension]?.label || filter.dimension\n }\n subtitle={`${filter.dimension}${filter.formatLabel ? ` · ${filter.formatLabel}` : ''}`}\n selected={selectedFilter?.dimension === filter.dimension}\n onSelect={() => focus(item)}\n onHover={(on) => hover(on ? item : null)}\n {...dragProps('filter', index, filters.length)}\n onRemove={() =>\n setFilters(filters.filter((other) => other.dimension !== filter.dimension))\n }\n />\n )\n })}\n </Section>\n <Section\n title={`Gráficos (${charts.length})`}\n collapseKey=\"layout:lista:graficos\"\n actions={\n <>\n <Button size=\"small\" onClick={(e) => setAddMenu(e.currentTarget)}>\n + Novo\n </Button>\n <Menu anchorEl={addMenu} open={!!addMenu} onClose={() => setAddMenu(null)}>\n {Object.entries(chartTypes).map(([type, { label }]) => (\n <MenuItem key={type} dense onClick={() => add(type)}>\n {label}\n </MenuItem>\n ))}\n </Menu>\n </>\n }\n >\n {charts.map((chart, index) => {\n const item: LayoutItem = { kind: 'chart', key: chart.id }\n return (\n <ItemRow\n key={chart.id}\n title={chart.title || '(sem título)'}\n subtitle={`${chartSummary(chart, chartTypes)} · ${chart.span ?? LAYOUT_COLUMNS}/${LAYOUT_COLUMNS}`}\n selected={chart.id === selected?.id}\n onSelect={() => focus(item)}\n onHover={(on) => hover(on ? item : null)}\n {...dragProps('chart', index, charts.length)}\n onDuplicate={() => add(chart.type, chart)}\n onRemove={() => setCharts(charts.filter((other) => other.id !== chart.id))}\n />\n )\n })}\n </Section>\n </Box>\n )}\n\n {!(stacked && sidebar) && (\n <Box ref={editorRef} sx={{ flex: 1, minWidth: 0, overflow: 'auto' }}>\n <Box sx={{ p: 1.5 }}>\n {entry.draft && (\n <Alert severity=\"warning\" sx={{ mb: 1.5 }}>\n Rascunho aplicado: a página mostra o layout editado, não o arquivo{' '}\n <code>{entry.registered.id}.json</code>.\n {capabilities?.saveLayout\n ? ' Use \"Salvar no arquivo\" quando terminar.'\n : ' Copie o JSON para o arquivo quando terminar.'}\n </Alert>\n )}\n {!!errors.length && (\n <Alert severity=\"error\" sx={{ mb: 1.5 }}>\n Layout inválido — as edições não foram aplicadas na página:\n {errors.map((error) => (\n <div key={error}>{error}</div>\n ))}\n </Alert>\n )}\n {!!warnings.length && (\n <Alert severity=\"warning\" sx={{ mb: 1.5 }}>\n {warnings.map((warning) => (\n <div key={warning}>{warning}</div>\n ))}\n </Alert>\n )}\n {actionError && (\n <Alert severity=\"error\" sx={{ mb: 1.5, fontFamily: MONO, fontSize: 12 }}>\n {actionError}\n </Alert>\n )}\n {selection?.kind === 'canvas' ? (\n <CanvasForm canvas={editing.canvas} columns={formColumns} onChange={setCanvas} />\n ) : selection?.kind === 'cards' ? (\n <>\n <Typography sx={{ fontSize: 12, color: 'text.secondary', mb: 1 }}>\n Estilo padrão dos cards de todos os gráficos; cada gráfico pode sobrepor na\n seção Card dele. Vazio = padrão do componente.\n </Typography>\n <FieldsForm\n fields={CARDS_FIELDS}\n values={(editing.cards ?? {}) as Record<string, unknown>}\n onSet={setCards}\n model={model}\n formatters={[]}\n columns={[]}\n formColumns={formColumns}\n chosenDimensions={[]}\n />\n </>\n ) : selectedFilter ? (\n <FilterForm\n key={`filter:${selectedFilter.dimension}`}\n filter={selectedFilter}\n model={model}\n formatters={entry.parts.filters ?? []}\n columns={formColumns}\n onChange={(change) => {\n patchFilter(selectedFilter.dimension, change)\n setSelection({ kind: 'filter', key: change(selectedFilter).dimension })\n }}\n />\n ) : selected ? (\n <ChartForm\n key={`chart:${selected.id}`}\n chart={selected}\n cards={editing.cards}\n types={chartTypes}\n model={model}\n formatters={entry.parts.charts ?? []}\n columns={formColumns}\n onChange={(change) => {\n patchChart(selected.id, change)\n setSelection({ kind: 'chart', key: change(selected).id })\n }}\n />\n ) : (\n <Empty>Escolha a tela, um filtro ou um gráfico, ou use \"+ Novo\".</Empty>\n )}\n </Box>\n </Box>\n )}\n </Box>\n\n <Box\n sx={{\n display: 'flex',\n flexWrap: 'wrap',\n gap: 1,\n justifyContent: 'flex-end',\n alignItems: 'center',\n px: 1.5,\n py: 1,\n borderTop: 1,\n borderColor: 'divider'\n }}\n >\n {dirty && (\n <Typography sx={{ fontSize: 12, color: 'warning.main', mr: 'auto' }}>\n Edições não aplicadas\n </Typography>\n )}\n <CopyButton text={layoutFileContent(editing)} label=\"Copiar JSON\" />\n <Button\n size=\"small\"\n disabled={!dirty}\n onClick={() => setEditing(reference)}\n title=\"Desfaz as edições ainda não aplicadas\"\n >\n Desfazer\n </Button>\n <Button\n size=\"small\"\n color=\"warning\"\n disabled={!entry.draft}\n onClick={() => {\n devtools.store.expectRefetch()\n layouts.setPending(entry.registered.id, null)\n layouts.setDraft(entry.registered.id, null)\n setEditingState(entry.registered)\n }}\n title=\"Volta a página e o editor ao layout do arquivo\"\n >\n Descartar rascunho\n </Button>\n {capabilities?.saveLayout && (\n <Button\n size=\"small\"\n variant=\"outlined\"\n disabled={!differsFromFile || !!errors.length || busy}\n onClick={() => saveFile('preview')}\n title={`Reescreve ${entry.registered.id}.json com o que está no editor`}\n >\n {busy ? 'Gerando…' : 'Salvar no arquivo'}\n </Button>\n )}\n <Button\n size=\"small\"\n variant=\"contained\"\n disabled={!dirty || !!errors.length}\n onClick={apply}\n title=\"Mostra as edições na página (sem gravar o arquivo)\"\n >\n Aplicar na página\n </Button>\n </Box>\n\n <Dialog open={!!save} onClose={() => setSave(null)} maxWidth=\"lg\" fullWidth>\n <DialogTitle>Salvar layout no arquivo</DialogTitle>\n <DialogContent>\n <Typography sx={{ fontFamily: MONO, fontSize: 12, mb: 1 }}>{save?.path}</Typography>\n {save?.warnings.map((warning) => (\n <Alert key={warning} severity=\"warning\" sx={{ mb: 1 }}>\n {warning}\n </Alert>\n ))}\n {save && <FileDiff lines={lineDiff(save.previous, save.content)} />}\n <Typography sx={{ fontSize: 12, color: 'text.secondary', mt: 1 }}>\n O Next recarrega o JSON sozinho; o rascunho some quando a página receber o arquivo novo.\n </Typography>\n </DialogContent>\n <DialogActions>\n <Button onClick={() => setSave(null)}>Cancelar</Button>\n <Button\n variant=\"contained\"\n disabled={!save || save.previous === save.content || busy}\n onClick={() => saveFile('write')}\n >\n Gravar\n </Button>\n </DialogActions>\n </Dialog>\n </Box>\n )\n}\n\nconst presetLabel = ({ width, height }: CanvasDef) => `${width}×${height ?? 'auto'}`\n\n/** Tamanho fixo da tela (`layout.canvas`): desligado = responsivo. */\nfunction CanvasForm({\n canvas,\n columns,\n onChange\n}: {\n canvas: CanvasDef | undefined\n columns: number\n onChange: (next: CanvasDef | undefined) => void\n}) {\n const preset = canvas && CANVAS_PRESETS.find((item) => presetLabel(item) === presetLabel(canvas))\n const number = (value: string) => (value === '' ? undefined : Number(value))\n return (\n <Section title=\"Tela\" collapseKey=\"layout:form:Tela\">\n <Box sx={formGrid(columns)}>\n <Box sx={{ gridColumn: '1 / -1' }}>\n {withHint(\n <FormControlLabel\n control={\n <Checkbox\n size=\"small\"\n checked={!!canvas}\n onChange={(e) =>\n onChange(e.target.checked ? (CANVAS_PRESETS[0] as CanvasDef) : undefined)\n }\n />\n }\n label={<Typography sx={{ fontSize: 12 }}>Tamanho fixo</Typography>}\n />,\n 'Desenha o dashboard nesse tamanho e escala para caber na tela, mantendo a proporção, em vez de reorganizar os gráficos. A página precisa do <DashboardCanvas>.'\n )}\n </Box>\n {canvas && (\n <>\n {field(\n 'Predefinido',\n <TextField\n select\n size=\"small\"\n fullWidth\n value={preset ? presetLabel(preset) : ''}\n onChange={(e) =>\n onChange(CANVAS_PRESETS.find((item) => presetLabel(item) === e.target.value))\n }\n sx={inputSx}\n >\n {CANVAS_PRESETS.map((item) => (\n <MenuItem key={presetLabel(item)} value={presetLabel(item)}>\n {presetLabel(item)}\n </MenuItem>\n ))}\n </TextField>\n )}\n {field(\n 'Largura',\n <TextField\n size=\"small\"\n fullWidth\n type=\"number\"\n value={canvas.width ?? ''}\n onChange={(e) => onChange(withField(canvas, 'width', number(e.target.value)))}\n sx={inputSx}\n />\n )}\n {field(\n 'Altura mín.',\n <TextField\n size=\"small\"\n fullWidth\n type=\"number\"\n value={canvas.height ?? ''}\n placeholder=\"auto\"\n onChange={(e) => onChange(withField(canvas, 'height', number(e.target.value)))}\n sx={inputSx}\n />\n )}\n </>\n )}\n </Box>\n </Section>\n )\n}\n\nfunction ItemRow({\n title,\n subtitle,\n selected,\n onSelect,\n onHover,\n onDuplicate,\n onRemove,\n dropBefore,\n dropAfter,\n onDragStart,\n onDragOver,\n onDrop,\n onDragEnd\n}: {\n title: string\n subtitle: string\n selected: boolean\n onSelect: () => void\n onHover?: (hovering: boolean) => void\n onDuplicate?: () => void\n /** Ausente = item fixo (a tela). */\n onRemove?: () => void\n /** Marca onde o item arrastado vai cair. */\n dropBefore?: boolean\n dropAfter?: boolean\n /** Presente = item arrastável. */\n onDragStart?: () => void\n onDragOver?: (e: DragEvent<HTMLElement>) => void\n onDrop?: () => void\n onDragEnd?: () => void\n}) {\n const marker = {\n content: '\"\"',\n position: 'absolute',\n left: 0,\n right: 0,\n height: 2,\n bgcolor: 'primary.main'\n }\n return (\n <Box\n onClick={onSelect}\n onMouseEnter={() => onHover?.(true)}\n onMouseLeave={() => onHover?.(false)}\n draggable={!!onDragStart}\n onDragStart={(e) => {\n if (!onDragStart) return\n e.dataTransfer.effectAllowed = 'move'\n // Firefox só arrasta com algum dado\n e.dataTransfer.setData('text/plain', title)\n onDragStart()\n }}\n onDragOver={onDragOver}\n onDrop={(e) => {\n e.preventDefault()\n onDrop?.()\n }}\n onDragEnd={onDragEnd}\n sx={{\n position: 'relative',\n display: 'flex',\n alignItems: 'center',\n gap: 0.5,\n px: 1,\n py: 0.5,\n mb: 0.5,\n borderRadius: 1,\n cursor: onDragStart ? 'grab' : 'pointer',\n border: 1,\n borderColor: selected ? 'primary.main' : 'divider',\n '&:hover .item-actions': { visibility: 'visible' },\n '&::before': dropBefore ? { ...marker, top: -4 } : undefined,\n '&::after': dropAfter ? { ...marker, bottom: -4 } : undefined\n }}\n >\n {onDragStart && (\n <Box\n component=\"span\"\n aria-hidden\n sx={{ color: 'text.disabled', fontSize: 12, lineHeight: 1, userSelect: 'none' }}\n >\n ⋮⋮\n </Box>\n )}\n <Box sx={{ minWidth: 0, flex: 1 }}>\n <Typography noWrap sx={{ fontSize: 12, fontWeight: 700 }}>\n {title}\n </Typography>\n <Typography noWrap sx={{ fontSize: 11, color: 'text.secondary', fontFamily: MONO }}>\n {subtitle}\n </Typography>\n </Box>\n {(onDuplicate || onRemove) && (\n <Box\n className=\"item-actions\"\n onClick={(e) => e.stopPropagation()}\n sx={{ display: 'flex', visibility: selected ? 'visible' : 'hidden' }}\n >\n {onDuplicate && (\n <SmallButton title=\"Duplicar\" onClick={onDuplicate}>\n ⧉\n </SmallButton>\n )}\n {onRemove && (\n <SmallButton title=\"Remover\" onClick={onRemove}>\n ×\n </SmallButton>\n )}\n </Box>\n )}\n </Box>\n )\n}\n\nfunction SmallButton({\n title,\n disabled,\n onClick,\n children\n}: {\n title: string\n disabled?: boolean\n onClick: () => void\n children: ReactNode\n}) {\n return (\n <Tooltip title={title}>\n <span>\n <IconButton\n size=\"small\"\n disabled={disabled}\n onClick={onClick}\n aria-label={title}\n sx={{ p: 0.25, fontSize: 13 }}\n >\n {children}\n </IconButton>\n </span>\n </Tooltip>\n )\n}\n\nfunction ChartForm({\n chart,\n cards,\n types,\n model,\n formatters,\n columns,\n onChange\n}: {\n chart: ChartDef\n /** Estilo padrão dos cards do layout (placeholder da seção Card). */\n cards: CardsStyle | undefined\n types: ChartTypes\n model: ModelDef\n formatters: string[]\n /** Colunas do formulário (encolhe com a largura do devtools). */\n columns: number\n onChange: (change: (chart: ChartDef) => ChartDef) => void\n}) {\n const set = (key: string, value: unknown) =>\n onChange((current) => withField(current as Record<string, unknown>, key, value) as ChartDef)\n // Vários campos numa mudança só (ex.: dimensões, medidas e a ordem das colunas juntas)\n const setMany = (changes: Record<string, unknown>) =>\n onChange(\n (current) =>\n Object.entries(changes).reduce(\n (chart, [key, value]) => withField(chart, key, value),\n current as Record<string, unknown>\n ) as ChartDef\n )\n const setCard = (key: string, value: unknown) =>\n onChange((current) =>\n withField(\n current,\n 'card',\n nonEmpty(withField((current.card ?? {}) as Record<string, unknown>, key, value))\n )\n )\n return (\n <>\n <FieldsForm\n fields={types[chart.type]?.fields ?? {}}\n values={chart as unknown as Record<string, unknown>}\n onSet={set}\n onSetMany={setMany}\n model={model}\n formatters={formatters}\n columns={chartColumns(chart, types)}\n formColumns={columns}\n chosenDimensions={chartReferences(chart, types).dimensions}\n chosenMeasures={chartReferences(chart, types).measures}\n header={\n <>\n {field(\n 'Tipo',\n <TextField\n select\n size=\"small\"\n fullWidth\n value={chart.type}\n // Troca de tipo: mantém id, título, largura e o que der de dimensões/medidas\n onChange={(e) =>\n onChange((current) => chartOfType(e.target.value, model, current, types))\n }\n sx={inputSx}\n >\n {Object.entries(types).map(([type, { label }]) => (\n <MenuItem key={type} value={type}>\n {label}\n </MenuItem>\n ))}\n {!types[chart.type] && (\n <MenuItem value={chart.type} disabled>\n {chart.type} (não registrado)\n </MenuItem>\n )}\n </TextField>\n )}\n {field(\n 'id',\n <TextField\n size=\"small\"\n fullWidth\n value={chart.id}\n error={!/^[A-Za-z0-9_-]{1,80}$/.test(chart.id)}\n onChange={(e) => set('id', e.target.value)}\n sx={inputSx}\n />,\n 'Identificador no JSON (letras, números, \"-\" e \"_\")'\n )}\n </>\n }\n />\n <FieldsForm\n fields={chartCardFields(cards)}\n values={(chart.card ?? {}) as Record<string, unknown>}\n onSet={setCard}\n model={model}\n formatters={[]}\n columns={[]}\n formColumns={columns}\n chosenDimensions={[]}\n />\n </>\n )\n}\n\nfunction FilterForm({\n filter,\n model,\n formatters,\n columns,\n onChange\n}: {\n filter: FilterDef\n model: ModelDef\n formatters: string[]\n columns: number\n onChange: (change: (filter: FilterDef) => FilterDef) => void\n}) {\n return (\n <FieldsForm\n fields={FILTER_FIELDS}\n values={filter as unknown as Record<string, unknown>}\n onSet={(key, value) =>\n onChange(\n (current) => withField(current as Record<string, unknown>, key, value) as FilterDef\n )\n }\n model={model}\n formatters={formatters}\n columns={[]}\n formColumns={columns}\n chosenDimensions={[filter.dimension]}\n />\n )\n}\n\n/** Formulário gerado dos `FieldSpec` (campos do tipo de gráfico ou do filtro). */\nfunction FieldsForm({\n fields,\n values,\n onSet: set,\n onSetMany,\n model,\n formatters,\n columns,\n formColumns,\n chosenDimensions,\n chosenMeasures = [],\n header\n}: {\n fields: Record<string, FieldSpec>\n values: Record<string, unknown>\n onSet: (key: string, value: unknown) => void\n /** Vários campos numa mudança só (sem ele, um `onSet` por campo). */\n onSetMany?: (changes: Record<string, unknown>) => void\n model: ModelDef\n formatters: string[]\n /** Opções dos campos `column` (ex.: `sortBy`). */\n columns: string[]\n formColumns: number\n /** Dimensões já escolhidas (campos `formatters`). */\n chosenDimensions: string[]\n /** Medidas já escolhidas (campos `formats`). */\n chosenMeasures?: string[]\n /** Campos fixos no começo da primeira seção (tipo, id). */\n header?: ReactNode\n}) {\n const dimensions = Object.entries(model.dimensions).map(([name, dim]) => ({\n name,\n label: dim.label\n }))\n const measures = Object.entries(model.measures).map(([name, measure]) => ({\n name,\n label: measure.label\n }))\n const entries = Object.entries(fields)\n const columnLabel = (name: string) =>\n name.startsWith(PERCENT_PREFIX)\n ? `% ${fieldLabelOf(model, name.slice(PERCENT_PREFIX.length))}`\n : fieldLabelOf(model, name)\n const columnOptionsOf = (names: string[]): Option[] =>\n names.map((name) => ({ name, label: columnLabel(name) }))\n // Colunas do gráfico e, agrupadas depois, o resto do modelo (campos `column` com `outside`, regras)\n const fieldOptions: Option[] = [\n ...columnOptionsOf(columns).map((option) => ({ ...option, group: 'Colunas do gráfico' })),\n ...dimensions\n .filter((option) => !columns.includes(option.name))\n .map((option) => ({ ...option, group: 'Dimensões fora do gráfico' })),\n ...measures\n .filter((option) => !columns.includes(option.name))\n .map((option) => ({ ...option, group: 'Medidas fora do gráfico' }))\n ]\n\n // Opções de cada dimensão/medida (rótulo, formato, formatter) num ícone à direita do campo, em vez\n // de campos soltos. Vale quando o tipo tem `labels` ou `formats`.\n const keyOf = (kind: FieldSpec['kind']) => entries.find(([, spec]) => spec.kind === kind)?.[0]\n const labelsKey = keyOf('labels')\n const formatsKey = keyOf('formats')\n const alignsKey = keyOf('aligns')\n const verticalKey = keyOf('verticalAligns')\n const columnOptions = !!(labelsKey || formatsKey || alignsKey || verticalKey)\n const formattersKey = columnOptions ? keyOf('formatters') : undefined\n // `formatter` avulso só é da dimensão quando há uma dimensão e um formatter no tipo\n const single = (kind: FieldSpec['kind']) => entries.filter(([, spec]) => spec.kind === kind)\n const formatterKey =\n columnOptions && single('dimension').length === 1 && single('formatter').length === 1\n ? single('formatter')[0]?.[0]\n : undefined\n const labels = (labelsKey && (values[labelsKey] as Record<string, string>)) || {}\n const formats = (formatsKey && (values[formatsKey] as Record<string, ChartNumberFormat>)) || {}\n const aligns = (alignsKey && (values[alignsKey] as Record<string, ColumnAlign>)) || {}\n const verticals =\n (verticalKey && (values[verticalKey] as Record<string, ColumnVerticalAlign>)) || {}\n // Alinhamentos de uma coluna (chave `%:medida` no percentual)\n const alignProps = (column: string, defaultAlign: ColumnAlign) => ({\n align: alignsKey ? (aligns[column] ?? '') : undefined,\n defaultAlign,\n onAlign: (next: ColumnAlign | undefined) =>\n alignsKey && set(alignsKey, pruned(withField(aligns, column, next), columns)),\n verticalAlign: verticalKey ? (verticals[column] ?? '') : undefined,\n onVerticalAlign: (next: ColumnVerticalAlign | undefined) =>\n verticalKey && set(verticalKey, pruned(withField(verticals, column, next), columns))\n })\n const resetAligns = (column: string, changes: Record<string, unknown>) => {\n if (alignsKey) changes[alignsKey] = pruned(withField(aligns, column, undefined), columns)\n if (verticalKey) changes[verticalKey] = pruned(withField(verticals, column, undefined), columns)\n }\n const setChanges = (changes: Record<string, unknown>) => {\n if (onSetMany) onSetMany(changes)\n else for (const [key, value] of Object.entries(changes)) set(key, value)\n }\n const dimensionFormatters =\n (formattersKey && (values[formattersKey] as Record<string, string>)) || {}\n\n const optionsButton = (kind: ColumnKind, name: string | undefined) => {\n if (!columnOptions || !name) return null\n // Percentual: só o alinhamento (a chave da coluna é `%:medida`)\n if (kind === 'percent') {\n if (!alignsKey && !verticalKey) return null\n const column = percentColumn(name)\n return (\n <ColumnOptions\n kind={kind}\n name={name}\n model={model}\n label={undefined}\n onLabel={() => {}}\n format={undefined}\n onFormat={() => {}}\n formatter={undefined}\n formatters={formatters}\n onFormatter={() => {}}\n {...alignProps(column, 'right')}\n onReset={() => {\n const changes: Record<string, unknown> = {}\n resetAligns(column, changes)\n setChanges(changes)\n }}\n />\n )\n }\n const canFormatter = kind === 'dimension' && !!(formattersKey || formatterKey)\n return (\n <ColumnOptions\n kind={kind}\n name={name}\n model={model}\n {...alignProps(name, kind === 'dimension' ? 'left' : 'right')}\n label={labelsKey ? (labels[name] ?? '') : undefined}\n onLabel={(text) =>\n labelsKey && set(labelsKey, pruned(withField(labels, name, text), columns))\n }\n format={kind === 'measure' && formatsKey ? (formats[name] ?? {}) : undefined}\n onFormat={(format) => {\n if (!formatsKey) return\n const map = { ...formats }\n if (Object.keys(format).length) map[name] = format\n else delete map[name]\n set(formatsKey, pruned(map, chosenMeasures))\n }}\n formatter={\n !canFormatter\n ? undefined\n : formattersKey\n ? (dimensionFormatters[name] ?? '')\n : ((formatterKey && (values[formatterKey] as string)) ?? '')\n }\n formatters={formatters}\n onFormatter={(formatter) => {\n if (formattersKey)\n set(\n formattersKey,\n pruned(withField(dimensionFormatters, name, formatter), chosenDimensions)\n )\n else if (formatterKey) set(formatterKey, formatter || undefined)\n }}\n onReset={() => {\n // Uma mudança só: chamadas seguidas de `set` partiriam do mesmo estado\n const changes: Record<string, unknown> = {}\n if (labelsKey) changes[labelsKey] = pruned(withField(labels, name, undefined), columns)\n resetAligns(name, changes)\n if (formatsKey && kind === 'measure')\n changes[formatsKey] = pruned(withField(formats, name, undefined), chosenMeasures)\n if (canFormatter && formattersKey)\n changes[formattersKey] = pruned(\n withField(dimensionFormatters, name, undefined),\n chosenDimensions\n )\n else if (canFormatter && formatterKey) changes[formatterKey] = undefined\n if (onSetMany) onSetMany(changes)\n else for (const [key, value] of Object.entries(changes)) set(key, value)\n }}\n />\n )\n }\n\n // Dimensões e medidas da mesma seção viram uma lista só, com um adicionar para os dois; com um\n // campo `columnOrder` no tipo, a ordem pode misturar (medida antes de dimensão)\n const merged = (() => {\n for (const [dimensionsKey, spec] of entries) {\n if (spec.kind !== 'dimensions') continue\n const pair = entries.find(\n ([, other]) => other.kind === 'measures' && !other.percent && other.section === spec.section\n )\n if (!pair) continue\n const order = entries.find(([, other]) => other.kind === 'columnOrder')?.[0]\n // Com a ordem no tipo, o % do total também entra na lista (posicionável como as colunas)\n const percents = order\n ? entries.find(\n ([, other]) =>\n other.kind === 'measures' && other.percent && other.section === spec.section\n )\n : undefined\n return {\n dimensions: dimensionsKey,\n dimensionsSpec: spec,\n measures: pair[0],\n measuresSpec: pair[1],\n percents: percents?.[0],\n percentsSpec: percents?.[1],\n order\n }\n }\n return undefined\n })()\n\n const mergedInput = (pair: NonNullable<typeof merged>) => {\n const dimensionNames = (values[pair.dimensions] as string[] | undefined) ?? []\n const measureNames = (values[pair.measures] as string[] | undefined) ?? []\n const percentNames = pair.percents\n ? ((values[pair.percents] as string[] | undefined) ?? [])\n : []\n const all: ColumnItem[] = [\n ...dimensionNames.map((name) => ({ kind: 'dimension' as const, name })),\n ...measureNames.map((name) => ({ kind: 'measure' as const, name })),\n ...percentNames.map((name) => ({ kind: 'percent' as const, name }))\n ]\n const order = pair.order ? (values[pair.order] as string[] | undefined) : undefined\n const sortedColumns = tableColumns([...dimensionNames, ...measureNames], percentNames, order)\n // Nome repetido entre dimensão e medida: cada item é usado uma vez só\n const pool = [...all]\n const items = sortedColumns.map((column) => {\n const index = pool.findIndex((item) => itemColumn(item) === column)\n return pool.splice(index, 1)[0] as ColumnItem\n })\n const required = !!pair.dimensionsSpec.required || !!pair.measuresSpec.required\n return (\n <ColumnList\n items={items}\n options={{\n dimension: options(pair.dimensionsSpec),\n measure: options(pair.measuresSpec),\n ...(pair.percentsSpec && { percent: options(pair.percentsSpec) })\n }}\n extra={(item) => optionsButton(item.kind, item.name)}\n error={\n (!!pair.measuresSpec.required && !measureNames.length) ||\n (!!pair.dimensionsSpec.required && !dimensionNames.length) ||\n (required && !items.length)\n }\n onChange={(next) => {\n const dimensionList = next.filter((item) => item.kind === 'dimension')\n const measureList = next.filter((item) => item.kind === 'measure')\n const percentList = next.filter((item) => item.kind === 'percent').map((i) => i.name)\n const names = next.map(itemColumn)\n const standard = tableColumns(\n [...dimensionList, ...measureList].map((item) => item.name),\n percentList\n )\n const changes: Record<string, unknown> = {\n [pair.dimensions]:\n dimensionList.length || pair.dimensionsSpec.required\n ? dimensionList.map((item) => item.name)\n : undefined,\n [pair.measures]:\n measureList.length || pair.measuresSpec.required\n ? measureList.map((item) => item.name)\n : undefined\n }\n if (pair.percents) changes[pair.percents] = percentList.length ? percentList : undefined\n // Ordem padrão (dimensões, medidas, cada % depois da medida) não precisa ir para o JSON\n if (pair.order)\n changes[pair.order] =\n names.join('\\u0000') === standard.join('\\u0000') ? undefined : names\n if (onSetMany) onSetMany(changes)\n else for (const [key, value] of Object.entries(changes)) set(key, value)\n }}\n />\n )\n }\n\n const options = (spec: FieldSpec): Option[] => {\n switch (spec.kind) {\n case 'dimension':\n case 'dimensions':\n return dimensions\n case 'measure':\n case 'measures':\n return measures\n case 'formatter':\n return formatters.map((name) => ({ name }))\n case 'column':\n return spec.outside ? fieldOptions : columnOptionsOf(columns)\n case 'enum':\n return spec.values.map((name) => ({ name, label: spec.labels?.[name] }))\n default:\n return []\n }\n }\n\n const input = (key: string, spec: FieldSpec): ReactNode => {\n const value = values[key]\n switch (spec.kind) {\n case 'text':\n return (\n <TextField\n size=\"small\"\n fullWidth\n value={(value as string | undefined) ?? ''}\n placeholder={labelPlaceholder(key, values, model)}\n onChange={(e) => set(key, e.target.value)}\n sx={inputSx}\n />\n )\n case 'color':\n return (\n <ColorInput\n value={value as string | undefined}\n fallback={spec.default as string}\n onCommit={(color) => set(key, color)}\n />\n )\n case 'boolean': {\n const fallback = spec.default as boolean\n return (\n <FormControlLabel\n control={\n <Checkbox\n size=\"small\"\n checked={(value as boolean | undefined) ?? fallback}\n // Igual ao padrão do componente: sai do JSON\n onChange={(e) =>\n set(key, e.target.checked === fallback ? undefined : e.target.checked)\n }\n />\n }\n label={<Typography sx={{ fontSize: 12 }}>{spec.label}</Typography>}\n />\n )\n }\n case 'integer':\n // Largura: lista fechada, mais rápida que digitar\n if (key === 'span')\n return (\n <TextField\n select\n size=\"small\"\n fullWidth\n value={(value as number | undefined) ?? spec.default}\n onChange={(e) => {\n const span = Number(e.target.value)\n set(key, span === spec.default ? undefined : span)\n }}\n sx={inputSx}\n >\n {Array.from({ length: spec.max }, (_, i) => i + 1).map((span) => (\n <MenuItem key={span} value={span}>\n {span}/{spec.max}\n </MenuItem>\n ))}\n </TextField>\n )\n return (\n <TextField\n size=\"small\"\n fullWidth\n type=\"number\"\n value={(value as number | undefined) ?? ''}\n placeholder={spec.default === undefined ? '' : String(spec.default)}\n error={\n typeof value === 'number' &&\n (!Number.isInteger(value) || value < spec.min || value > spec.max)\n }\n onChange={(e) =>\n set(key, e.target.value.trim() === '' ? undefined : Number(e.target.value))\n }\n sx={inputSx}\n />\n )\n case 'dimensions':\n case 'measures': {\n const kind = spec.kind === 'dimensions' ? 'dimension' : 'measure'\n if (merged?.dimensions === key) return mergedInput(merged)\n const names = (value as string[] | undefined) ?? []\n return (\n <ColumnList\n items={names.map((name) => ({ kind, name }))}\n options={{ [kind]: options(spec) }}\n extra={(item) => optionsButton(item.kind, item.name)}\n error={!!spec.required && !names.length}\n onChange={(next) => {\n const list = next.map((item) => item.name)\n set(key, list.length || spec.required ? list : undefined)\n }}\n />\n )\n }\n case 'formatRules':\n return (\n <FormatRulesInput\n rules={(value as FormatRule[] | undefined) ?? []}\n fieldOptions={fieldOptions}\n columnOptions={columnOptionsOf(columns)}\n model={model}\n onChange={(rules) => set(key, rules.length ? rules : undefined)}\n />\n )\n case 'formatters': {\n const map = (value as Record<string, string> | undefined) ?? {}\n if (!chosenDimensions.length)\n return (\n <Typography sx={{ fontSize: 12, color: 'text.disabled' }}>sem dimensões</Typography>\n )\n return (\n <Box sx={{ display: 'flex', flexDirection: 'column', gap: 0.5 }}>\n {chosenDimensions.map((dimension) => (\n <Box key={dimension} sx={{ display: 'flex', gap: 0.5, alignItems: 'center' }}>\n <Typography sx={{ fontFamily: MONO, fontSize: 12, minWidth: 90 }}>\n {dimension}\n </Typography>\n <NameSelect\n value={map[dimension] ?? ''}\n options={formatters.map((name) => ({ name }))}\n onChange={(name) => {\n const next = withField(map, dimension, name)\n set(key, Object.keys(next).length ? next : undefined)\n }}\n />\n </Box>\n ))}\n </Box>\n )\n }\n default: {\n const select = (\n <NameSelect\n value={(value as string | undefined) ?? ''}\n options={options(spec)}\n required={spec.required}\n emptyLabel={\n spec.kind === 'enum' && spec.default\n ? `padrão (${spec.labels?.[spec.default as string] ?? spec.default})`\n : undefined\n }\n onChange={(name) => set(key, name === spec.default ? undefined : name)}\n />\n )\n const button =\n spec.kind === 'dimension' || spec.kind === 'measure'\n ? optionsButton(spec.kind, value as string | undefined)\n : null\n return button ? (\n <Box sx={{ display: 'flex', gap: 0.25, alignItems: 'center' }}>\n {select}\n {button}\n </Box>\n ) : (\n select\n )\n }\n }\n }\n\n // Campos que não aparecem sozinhos: as medidas do par e a ordem (editadas na lista junta) e os\n // rótulos/formatos/formatters (no ícone de cada coluna)\n const hidden = new Set(\n [\n merged?.measures,\n merged?.percents,\n ...entries.filter(([, spec]) => spec.kind === 'columnOrder').map(([key]) => key),\n labelsKey,\n formatsKey,\n alignsKey,\n verticalKey,\n formattersKey,\n formatterKey\n ].filter(Boolean)\n )\n // Seções na ordem em que aparecem nos campos (só as que têm campo visível)\n const sections = [\n ...new Set(entries.filter(([key]) => !hidden.has(key)).map(([, spec]) => spec.section))\n ]\n // Listas (dimensões/medidas) ocupam a linha toda: uma embaixo da outra, nunca lado a lado\n const fullRow = (spec: FieldSpec) =>\n spec.kind === 'dimensions' ||\n spec.kind === 'measures' ||\n spec.kind === 'formatters' ||\n spec.kind === 'formatRules'\n const gridColumn = (spec: FieldSpec, key: string) =>\n fullRow(spec) ? '1 / -1' : key === 'title' && formColumns > 1 ? 'span 2' : undefined\n\n return (\n <>\n {sections.map((section) => {\n const inSection = entries.filter(([, spec]) => spec.section === section)\n return (\n <Section key={section} title={section} collapseKey={`layout:form:${section}`}>\n <Box sx={formGrid(formColumns)}>\n {section === sections[0] && header}\n {inSection\n .filter(([key]) => !hidden.has(key))\n .map(([key, spec]) => (\n <Box\n key={key}\n sx={{\n gridColumn: gridColumn(spec, key),\n alignSelf: spec.kind === 'boolean' ? 'end' : undefined\n }}\n >\n {spec.kind === 'boolean'\n ? withHint(input(key, spec), spec.hint)\n : merged?.dimensions === key\n ? field(\n merged.percents ? 'Dimensões, medidas e %' : 'Dimensões e medidas',\n input(key, spec),\n `${merged.order ? 'Em qualquer ordem: é a ordem das colunas. ' : ''}${[spec.hint, merged.measuresSpec.hint, merged.percentsSpec?.hint && `% do total: ${merged.percentsSpec.hint}`].filter(Boolean).join(' · ')}`\n )\n : field(spec.label, input(key, spec), spec.hint)}\n </Box>\n ))}\n </Box>\n </Section>\n )\n })}\n </>\n )\n}\n\n/** `group`: subtítulo da lista (opções do mesmo grupo vêm juntas). */\ntype Option = { name: string; label?: string; group?: string }\n\nconst fieldLabelOf = (model: ModelDef, name: string) =>\n model.dimensions[name]?.label ?? model.measures[name]?.label ?? name\n\n/** Exemplo de célula com o estilo de uma regra. */\nconst RULE_SAMPLE = 'Exemplo'\n\nconst DEFAULT_RULE_BACKGROUND = '#ffe3e3'\n\n/**\n * Regras de formatação condicional, uma por cartão: \"se <campo> <operador> <valor>, pinta <a célula\n * de uma coluna | a linha toda> com <texto, fundo, negrito>\". A ordem importa (a de baixo ganha):\n * reordena com ↑/↓.\n */\nfunction FormatRulesInput({\n rules,\n fieldOptions,\n columnOptions,\n model,\n onChange\n}: {\n rules: FormatRule[]\n fieldOptions: Option[]\n columnOptions: Option[]\n model: ModelDef\n onChange: (rules: FormatRule[]) => void\n}) {\n const update = (index: number, change: (rule: FormatRule) => FormatRule) =>\n onChange(rules.map((rule, i) => (i === index ? change(rule) : rule)))\n const columns = columnOptions.map((option) => option.name)\n // Texto digitado -> valor da regra: número quando o operador ou o campo pedem\n const parseValue = (rule: FormatRule, text: string): number | string | undefined => {\n const trimmed = text.trim()\n if (!trimmed) return undefined\n const number = Number(trimmed.replace(',', '.'))\n if (NUMERIC_OPERATORS.includes(rule.operator))\n return Number.isFinite(number) ? number : undefined\n if (rule.operator === 'contains') return trimmed\n const textField = model.dimensions[rule.field]?.type === 'string'\n return !textField && Number.isFinite(number) ? number : trimmed\n }\n const withOperator = (rule: FormatRule, operator: RuleOperator): FormatRule => {\n const { value, to, ...rest } = rule\n if (UNARY_OPERATORS.includes(operator)) return { ...rest, operator }\n const numeric = NUMERIC_OPERATORS.includes(operator)\n const next: FormatRule = {\n ...rest,\n operator,\n value: numeric ? (Number.isFinite(Number(value)) ? Number(value) : 0) : (value ?? '')\n }\n if (operator === 'between') next.to = to ?? (next.value as number)\n return next\n }\n\n return (\n <Box sx={{ display: 'flex', flexDirection: 'column', gap: 0.75, maxWidth: 760 }}>\n {rules.map((rule, index) => {\n const painted = rule.target === 'row' ? undefined : (rule.column ?? rule.field)\n const lost = painted !== undefined && !columns.includes(painted)\n return (\n <Box\n // biome-ignore lint/suspicious/noArrayIndexKey: regras não têm id\n key={index}\n sx={{\n border: 1,\n borderColor: 'divider',\n borderRadius: 1,\n p: 0.75,\n display: 'flex',\n flexDirection: 'column',\n gap: 0.5,\n '&:hover .row-actions': { visibility: 'visible' }\n }}\n >\n <Box sx={{ display: 'flex', gap: 0.5, alignItems: 'center', flexWrap: 'wrap' }}>\n <Typography sx={{ fontSize: 12, color: 'text.secondary' }}>\n {index + 1}. Se\n </Typography>\n <Box sx={{ flex: '2 1 140px' }}>\n <NameSelect\n value={rule.field}\n options={fieldOptions}\n required\n onChange={(field) => update(index, (current) => ({ ...current, field }))}\n />\n </Box>\n <TextField\n select\n size=\"small\"\n value={rule.operator}\n onChange={(e) =>\n update(index, (current) => withOperator(current, e.target.value as RuleOperator))\n }\n sx={{ ...inputSx, flex: '1 1 110px' }}\n >\n {RULE_OPERATORS.map((operator) => (\n <MenuItem key={operator} value={operator}>\n {RULE_OPERATOR_LABEL[operator]}\n </MenuItem>\n ))}\n </TextField>\n {!UNARY_OPERATORS.includes(rule.operator) && (\n <Box sx={{ flex: '1 1 80px' }}>\n <CommitText\n value={rule.value === undefined ? '' : String(rule.value)}\n placeholder=\"valor\"\n error={rule.value === undefined}\n onCommit={(text) =>\n update(index, (current) => ({ ...current, value: parseValue(current, text) }))\n }\n />\n </Box>\n )}\n {rule.operator === 'between' && (\n <>\n <Typography sx={{ fontSize: 12, color: 'text.secondary' }}>e</Typography>\n <Box sx={{ flex: '1 1 80px' }}>\n <CommitText\n value={rule.to === undefined ? '' : String(rule.to)}\n placeholder=\"até\"\n error={rule.to === undefined}\n onCommit={(text) =>\n update(index, (current) => {\n const to = parseValue(current, text)\n return { ...current, to: typeof to === 'number' ? to : undefined }\n })\n }\n />\n </Box>\n </>\n )}\n <Box className=\"row-actions\" sx={{ display: 'flex', visibility: 'hidden' }}>\n <SmallButton\n title=\"Subir\"\n disabled={index === 0}\n onClick={() => onChange(moveTo(rules, index, index - 1))}\n >\n ↑\n </SmallButton>\n <SmallButton\n title=\"Descer\"\n disabled={index === rules.length - 1}\n onClick={() => onChange(moveTo(rules, index, index + 2))}\n >\n ↓\n </SmallButton>\n <SmallButton\n title=\"Remover\"\n onClick={() => onChange(rules.filter((_, i) => i !== index))}\n >\n ×\n </SmallButton>\n </Box>\n </Box>\n <Box sx={{ display: 'flex', gap: 0.5, alignItems: 'center', flexWrap: 'wrap' }}>\n <Typography sx={{ fontSize: 12, color: 'text.secondary' }}>pinta</Typography>\n <TextField\n select\n size=\"small\"\n value={rule.target === 'row' ? 'row' : 'cell'}\n onChange={(e) =>\n update(index, ({ target: _target, column: _column, ...rest }) =>\n e.target.value === 'row' ? { ...rest, target: 'row' } : rest\n )\n }\n sx={{ ...inputSx, flex: '1 1 110px' }}\n >\n <MenuItem value=\"cell\">a célula de</MenuItem>\n <MenuItem value=\"row\">a linha toda</MenuItem>\n </TextField>\n {rule.target !== 'row' && (\n <Box sx={{ flex: '2 1 140px' }}>\n <NameSelect\n value={rule.column ?? ''}\n options={columnOptions}\n emptyLabel={`o próprio campo${columns.includes(rule.field) ? '' : ' (fora do gráfico)'}`}\n onChange={(column) =>\n update(index, (current) => withField(current, 'column', column || undefined))\n }\n />\n </Box>\n )}\n <Box\n sx={{\n px: 1,\n py: 0.25,\n fontSize: 12,\n border: 1,\n borderColor: 'divider',\n color: rule.color,\n bgcolor: rule.background,\n fontWeight: rule.bold ? 700 : undefined\n }}\n >\n {RULE_SAMPLE}\n </Box>\n </Box>\n {lost && (\n <Typography sx={{ fontSize: 11, color: 'warning.main' }}>\n \"{painted}\" não é coluna do gráfico: escolha a coluna a pintar ou a linha toda\n </Typography>\n )}\n <Box\n sx={{\n display: 'grid',\n gap: 0.5,\n gridTemplateColumns: 'repeat(auto-fit, minmax(150px, 1fr))',\n alignItems: 'end'\n }}\n >\n {field(\n 'Cor do texto',\n <ColorInput\n value={rule.color}\n fallback=\"#000000\"\n onCommit={(color) =>\n update(index, (current) => withField(current, 'color', color))\n }\n />\n )}\n {field(\n 'Fundo',\n <ColorInput\n value={rule.background}\n fallback=\"#ffffff\"\n onCommit={(color) =>\n update(index, (current) => withField(current, 'background', color))\n }\n />\n )}\n {field(\n 'Alinhamento',\n <TextField\n select\n size=\"small\"\n fullWidth\n value={rule.align ?? ''}\n onChange={(e) =>\n update(index, (current) =>\n withField(current, 'align', e.target.value || undefined)\n )\n }\n slotProps={{ select: { displayEmpty: true } }}\n sx={inputSx}\n >\n <MenuItem value=\"\">\n <em>não muda</em>\n </MenuItem>\n {COLUMN_ALIGNS.map((option) => (\n <MenuItem key={option} value={option}>\n {ALIGN_LABEL[option]}\n </MenuItem>\n ))}\n </TextField>\n )}\n {field(\n 'Vertical',\n <TextField\n select\n size=\"small\"\n fullWidth\n value={rule.verticalAlign ?? ''}\n onChange={(e) =>\n update(index, (current) =>\n withField(current, 'verticalAlign', e.target.value || undefined)\n )\n }\n slotProps={{ select: { displayEmpty: true } }}\n sx={inputSx}\n >\n <MenuItem value=\"\">\n <em>não muda</em>\n </MenuItem>\n {COLUMN_VERTICAL_ALIGNS.map((option) => (\n <MenuItem key={option} value={option}>\n {VERTICAL_ALIGN_LABEL[option]}\n </MenuItem>\n ))}\n </TextField>\n )}\n <FormControlLabel\n control={\n <Checkbox\n size=\"small\"\n checked={!!rule.bold}\n onChange={(e) =>\n update(index, (current) =>\n withField(current, 'bold', e.target.checked || undefined)\n )\n }\n />\n }\n label={<Typography sx={{ fontSize: 12 }}>Negrito</Typography>}\n />\n </Box>\n </Box>\n )\n })}\n <Button\n size=\"small\"\n variant=\"outlined\"\n disabled={!fieldOptions.length}\n onClick={() =>\n onChange([\n ...rules,\n {\n field: columns.find((name) => !name.startsWith(PERCENT_PREFIX)) ?? '',\n operator: '>',\n value: 0,\n background: DEFAULT_RULE_BACKGROUND\n }\n ])\n }\n sx={{ alignSelf: 'flex-start', textTransform: 'none' }}\n >\n + regra\n </Button>\n </Box>\n )\n}\n\n/** Campo de texto que só manda o valor no Enter ou ao sair (número parcial não vira valor). */\nfunction CommitText({\n value,\n placeholder,\n error,\n onCommit\n}: {\n value: string\n placeholder?: string\n error?: boolean\n onCommit: (text: string) => void\n}) {\n const [typing, setTyping] = useState<string | null>(null)\n const commit = () => {\n if (typing === null) return\n setTyping(null)\n if (typing !== value) onCommit(typing)\n }\n return (\n <TextField\n size=\"small\"\n fullWidth\n value={typing ?? value}\n placeholder={placeholder}\n error={error && typing === null}\n onChange={(e) => setTyping(e.target.value)}\n onBlur={commit}\n onKeyDown={(e) => {\n if (e.key === 'Enter') commit()\n if (e.key === 'Escape') setTyping(null)\n }}\n sx={inputSx}\n />\n )\n}\n\n/**\n * Cor com o seletor nativo. Mexer no seletor só muda a amostra: o valor vai para o editor quando\n * ele fecha — o `change` nativo; o `onChange` do React dispara a cada movimento. O texto entra no\n * Enter ou ao sair do campo.\n */\nfunction ColorInput({\n value,\n fallback,\n onCommit\n}: {\n value: string | undefined\n fallback: string\n onCommit: (color: string | undefined) => void\n}) {\n const [picking, setPicking] = useState<string | null>(null)\n const [typing, setTyping] = useState<string | null>(null)\n const picker = useRef<HTMLInputElement>(null)\n const commit = useRef(onCommit)\n useEffect(() => {\n commit.current = onCommit\n })\n useEffect(() => {\n const input = picker.current\n if (!input) return\n const listener = () => {\n commit.current(input.value)\n setPicking(null)\n }\n input.addEventListener('change', listener)\n return () => input.removeEventListener('change', listener)\n }, [])\n\n const commitText = () => {\n if (typing === null) return\n const text = typing.trim()\n setTyping(null)\n if (text !== (value ?? '')) onCommit(text || undefined)\n }\n\n return (\n <Box sx={{ display: 'flex', gap: 0.5, alignItems: 'center' }}>\n <Box\n component=\"input\"\n type=\"color\"\n ref={picker}\n value={picking ?? value ?? fallback}\n onChange={(e: ChangeEvent<HTMLInputElement>) => setPicking(e.target.value)}\n sx={{\n width: 32,\n height: 30,\n p: 0,\n border: 0,\n bgcolor: 'transparent',\n cursor: 'pointer'\n }}\n />\n <TextField\n size=\"small\"\n fullWidth\n value={typing ?? picking ?? value ?? ''}\n placeholder={fallback}\n onChange={(e) => setTyping(e.target.value)}\n onBlur={commitText}\n onKeyDown={(e) => {\n if (e.key === 'Enter') commitText()\n if (e.key === 'Escape') setTyping(null)\n }}\n sx={inputSx}\n />\n </Box>\n )\n}\n\n/** Sem as chaves de colunas que saíram do gráfico; vazio = `undefined` (sai do JSON). */\nfunction pruned<T>(map: Record<string, T>, keep: string[]) {\n const next = Object.fromEntries(Object.entries(map).filter(([key]) => keep.includes(key)))\n return Object.keys(next).length ? next : undefined\n}\n\nconst ALIGN_LABEL: Record<ColumnAlign, string> = {\n left: 'à esquerda',\n center: 'centralizado',\n right: 'à direita'\n}\n\nconst VERTICAL_ALIGN_LABEL: Record<ColumnVerticalAlign, string> = {\n top: 'em cima',\n middle: 'no meio',\n bottom: 'embaixo'\n}\n\nconst FORMAT_LABEL: Record<string, string> = {\n number: 'número',\n integer: 'inteiro',\n currency: 'R$',\n percent: '%'\n}\n\n/** Número de exemplo da prévia do formato. */\nconst SAMPLE = 1234567.891\n\n/**\n * Ícone à direita de uma dimensão/medida que abre as opções dela no gráfico: rótulo, formatter\n * (dimensão) e formato (medida). Vazio = o do dicionário do modelo (que aparece como placeholder).\n * Opção ausente (`undefined`) = o tipo do gráfico não tem esse campo.\n */\nfunction ColumnOptions({\n kind,\n name,\n model,\n label,\n onLabel,\n format,\n onFormat,\n formatter,\n formatters,\n onFormatter,\n align,\n defaultAlign,\n onAlign,\n verticalAlign,\n onVerticalAlign,\n onReset\n}: {\n kind: ColumnKind\n name: string\n model: ModelDef\n label: string | undefined\n onLabel: (label: string) => void\n format: ChartNumberFormat | undefined\n onFormat: (format: ChartNumberFormat) => void\n formatter: string | undefined\n formatters: string[]\n onFormatter: (formatter: string) => void\n /** Alinhamento horizontal; `''` = padrão (`defaultAlign`). */\n align: ColumnAlign | '' | undefined\n defaultAlign: ColumnAlign\n onAlign: (align: ColumnAlign | undefined) => void\n /** Alinhamento vertical; `''` = padrão (no meio). */\n verticalAlign: ColumnVerticalAlign | '' | undefined\n onVerticalAlign: (align: ColumnVerticalAlign | undefined) => void\n /** Volta rótulo, formato, formatter e alinhamento da coluna ao padrão (numa mudança só). */\n onReset: () => void\n}) {\n const [anchor, setAnchor] = useState<HTMLElement | null>(null)\n const fromModel = kind === 'measure' ? model.measures[name] : model.dimensions[name]\n const measureMeta = kind === 'measure' ? model.measures[name] : undefined\n const customized =\n !!label ||\n !!formatter ||\n !!align ||\n !!verticalAlign ||\n (format !== undefined && Object.keys(format).length > 0)\n const setFormat = (key: keyof ChartNumberFormat, next: unknown) =>\n onFormat(withField(format ?? {}, key, next))\n const decimals = format?.decimals\n const resolved: ChartNumberFormat = {\n ...(measureMeta?.format !== undefined && { format: measureMeta.format }),\n ...(measureMeta?.decimals !== undefined && { decimals: measureMeta.decimals }),\n ...format\n }\n const small = { ...inputSx, '& .MuiInputBase-input': { fontFamily: MONO, fontSize: 12, px: 1 } }\n\n return (\n <>\n <Tooltip title={customized ? 'Opções da coluna (personalizada)' : 'Opções da coluna'}>\n <IconButton\n size=\"small\"\n aria-label={`Opções de ${name}`}\n onClick={(e) => setAnchor(e.currentTarget)}\n sx={{\n p: 0.25,\n fontSize: 14,\n color: customized ? 'primary.main' : 'text.secondary'\n }}\n >\n ⚙\n </IconButton>\n </Tooltip>\n <Popover\n open={!!anchor}\n anchorEl={anchor}\n onClose={() => setAnchor(null)}\n anchorOrigin={{ vertical: 'bottom', horizontal: 'right' }}\n transformOrigin={{ vertical: 'top', horizontal: 'right' }}\n slotProps={{ paper: { sx: { p: 1.5, width: 320 } } }}\n >\n <Typography sx={{ fontSize: 12, fontWeight: 700, mb: 1 }}>\n <Box component=\"span\" sx={{ color: KIND_STYLE[kind].color, mr: 0.75 }}>\n {KIND_STYLE[kind].icon}\n </Box>\n <Box component=\"span\" sx={{ fontFamily: MONO }}>\n {name}\n </Box>\n <Box component=\"span\" sx={{ color: 'text.secondary', fontWeight: 400, ml: 1 }}>\n {KIND_STYLE[kind].noun}\n </Box>\n </Typography>\n <Box sx={{ display: 'flex', flexDirection: 'column', gap: 1.25 }}>\n {label !== undefined &&\n field(\n 'Rótulo',\n <TextField\n size=\"small\"\n fullWidth\n autoFocus\n value={label}\n placeholder={fromModel?.label ?? name}\n onChange={(e) => onLabel(e.target.value)}\n sx={inputSx}\n />,\n 'Legenda, tooltip e cabeçalho, só neste gráfico; vazio = rótulo do dicionário'\n )}\n {align !== undefined &&\n field(\n 'Alinhamento',\n <TextField\n select\n size=\"small\"\n fullWidth\n value={align}\n onChange={(e) => onAlign((e.target.value as ColumnAlign) || undefined)}\n slotProps={{ select: { displayEmpty: true } }}\n sx={small}\n >\n <MenuItem value=\"\">\n <em>padrão ({ALIGN_LABEL[defaultAlign]})</em>\n </MenuItem>\n {COLUMN_ALIGNS.map((option) => (\n <MenuItem key={option} value={option}>\n {ALIGN_LABEL[option]}\n </MenuItem>\n ))}\n </TextField>,\n 'Horizontal: cabeçalho, células e total da coluna'\n )}\n {verticalAlign !== undefined &&\n field(\n 'Alinhamento vertical',\n <TextField\n select\n size=\"small\"\n fullWidth\n value={verticalAlign}\n onChange={(e) =>\n onVerticalAlign((e.target.value as ColumnVerticalAlign) || undefined)\n }\n slotProps={{ select: { displayEmpty: true } }}\n sx={small}\n >\n <MenuItem value=\"\">\n <em>padrão ({VERTICAL_ALIGN_LABEL.middle})</em>\n </MenuItem>\n {COLUMN_VERTICAL_ALIGNS.map((option) => (\n <MenuItem key={option} value={option}>\n {VERTICAL_ALIGN_LABEL[option]}\n </MenuItem>\n ))}\n </TextField>,\n 'Aparece quando a linha tem texto em mais de uma linha'\n )}\n {formatter !== undefined &&\n field(\n 'Formatter',\n <NameSelect\n value={formatter}\n options={formatters.map((option) => ({ name: option }))}\n onChange={onFormatter}\n />,\n 'Formatters passados ao <DashboardCharts formatters={{ ... }}> da página'\n )}\n {format !== undefined && (\n <>\n <Box sx={{ display: 'grid', gridTemplateColumns: '1fr 1fr', gap: 1 }}>\n {field(\n 'Formato',\n <TextField\n select\n size=\"small\"\n fullWidth\n value={format.format ?? ''}\n onChange={(e) => setFormat('format', e.target.value || undefined)}\n slotProps={{ select: { displayEmpty: true } }}\n sx={small}\n >\n <MenuItem value=\"\">\n <em>\n padrão\n {measureMeta?.format ? ` (${FORMAT_LABEL[measureMeta.format]})` : ''}\n </em>\n </MenuItem>\n {VALUE_FORMATS.map((option) => (\n <MenuItem key={option} value={option}>\n {FORMAT_LABEL[option]}\n </MenuItem>\n ))}\n </TextField>\n )}\n {field(\n 'Casas decimais',\n <TextField\n size=\"small\"\n fullWidth\n type=\"number\"\n value={decimals ?? ''}\n placeholder={\n measureMeta?.decimals === undefined ? 'padrão' : String(measureMeta.decimals)\n }\n error={\n decimals !== undefined &&\n (!Number.isInteger(decimals) || decimals < 0 || decimals > 10)\n }\n onChange={(e) =>\n setFormat(\n 'decimals',\n e.target.value.trim() === '' ? undefined : Number(e.target.value)\n )\n }\n slotProps={{ htmlInput: { min: 0, max: 10 } }}\n sx={small}\n />\n )}\n {field(\n 'Prefixo',\n <TextField\n size=\"small\"\n fullWidth\n value={format.prefix ?? ''}\n placeholder=\"ex.: ~\"\n onChange={(e) => setFormat('prefix', e.target.value)}\n sx={small}\n />\n )}\n {field(\n 'Sufixo',\n <TextField\n size=\"small\"\n fullWidth\n value={format.suffix ?? ''}\n placeholder=\"ex.: t\"\n onChange={(e) => setFormat('suffix', e.target.value)}\n sx={small}\n />\n )}\n </Box>\n <FormControlLabel\n sx={{ m: 0 }}\n control={\n <Checkbox\n size=\"small\"\n sx={{ p: 0.25, mr: 0.5 }}\n checked={format.compact ?? false}\n onChange={(e) => setFormat('compact', e.target.checked || undefined)}\n />\n }\n label={\n <Typography sx={{ fontSize: 12 }}>Notação curta (1,2 mil / 3,4 mi)</Typography>\n }\n />\n <Typography sx={{ fontSize: 11, color: 'text.secondary' }}>\n Exemplo:{' '}\n <Box component=\"span\" sx={{ fontFamily: MONO, color: 'text.primary' }}>\n {formatMeasure(SAMPLE, resolved, 2)}\n </Box>\n </Typography>\n </>\n )}\n <Box sx={{ display: 'flex', justifyContent: 'flex-end' }}>\n <Button size=\"small\" disabled={!customized} onClick={onReset}>\n Restaurar padrão\n </Button>\n </Box>\n </Box>\n </Popover>\n </>\n )\n}\n\nconst formGrid = (columns: number) => ({\n display: 'grid',\n gap: 1.5,\n gridTemplateColumns: `repeat(${columns}, minmax(0, 1fr))`\n})\n\n/** Rótulo padrão (do dicionário) como placeholder do `label` do filtro. */\nfunction labelPlaceholder(key: string, values: Record<string, unknown>, model: ModelDef) {\n if (key === 'label' && typeof values.dimension === 'string')\n return model.dimensions[values.dimension]?.label ?? values.dimension\n return undefined\n}\n\nfunction field(label: string, input: ReactNode, hint?: string) {\n return (\n <Box>\n <Typography sx={{ fontSize: 11, color: 'text.secondary', mb: 0.25 }}>\n {label}\n {hint && (\n <Tooltip title={hint}>\n <Box component=\"span\" sx={{ ml: 0.5, cursor: 'help' }}>\n ⓘ\n </Box>\n </Tooltip>\n )}\n </Typography>\n {input}\n </Box>\n )\n}\n\nfunction withHint(input: ReactNode, hint?: string) {\n return hint ? (\n <Tooltip title={hint} placement=\"top-start\">\n <Box>{input}</Box>\n </Tooltip>\n ) : (\n input\n )\n}\n\nfunction OptionText({ option }: { option: Option }) {\n return (\n <>\n {option.name}\n {option.label && option.label !== option.name && (\n <Box component=\"span\" sx={{ color: 'text.secondary', ml: 1 }}>\n {option.label}\n </Box>\n )}\n </>\n )\n}\n\nfunction NameSelect({\n value,\n options,\n required,\n emptyLabel,\n onChange\n}: {\n value: string\n options: Option[]\n required?: boolean\n /** Texto da opção vazia (padrão: \"(nenhum)\"). */\n emptyLabel?: string\n onChange: (value: string) => void\n}) {\n const known = !value || options.some((option) => option.name === value)\n return (\n <TextField\n select\n size=\"small\"\n fullWidth\n value={value}\n error={!known || (!!required && !value)}\n onChange={(e) => onChange(e.target.value)}\n sx={inputSx}\n >\n {!required && (\n <MenuItem value=\"\">\n <em>{emptyLabel ?? '(nenhum)'}</em>\n </MenuItem>\n )}\n {!known && <MenuItem value={value}>{value} (não existe)</MenuItem>}\n {options.flatMap((option, index) => [\n ...(option.group && option.group !== options[index - 1]?.group\n ? [<ListSubheader key={`h:${option.group}`}>{option.group}</ListSubheader>]\n : []),\n <MenuItem key={option.name} value={option.name}>\n <OptionText option={option} />\n </MenuItem>\n ])}\n </TextField>\n )\n}\n\ntype ColumnKind = 'dimension' | 'measure' | 'percent'\n/** `percent`: coluna de % do total da medida `name` (`%:name` no `columnOrder`). */\ntype ColumnItem = { kind: ColumnKind; name: string }\n\nconst itemColumn = (item: ColumnItem) =>\n item.kind === 'percent' ? percentColumn(item.name) : item.name\n\nconst KIND_STYLE: Record<ColumnKind, { icon: string; color: string; noun: string; group: string }> =\n {\n dimension: { icon: '◇', color: '#4dabf7', noun: 'dimensão', group: 'Dimensões' },\n measure: { icon: 'Σ', color: '#F58220', noun: 'medida', group: 'Medidas' },\n percent: { icon: '%', color: '#9775fa', noun: '% do total', group: '% do total (da medida)' }\n }\n\n/**\n * Lista ordenada, uma linha por item: a ordem é a das séries/colunas. Reordena arrastando pela alça\n * (⋮⋮) ou com ↑/↓; um único \"+ adicionar\" no fim (já com o nome escolhido, sem linha vazia). Com\n * dois tipos (dimensões e medidas juntas), o adicionar agrupa as opções por tipo e a ordem mistura\n * os dois.\n */\nfunction ColumnList({\n items,\n options,\n extra,\n error,\n onChange\n}: {\n items: ColumnItem[]\n /** Fica à direita de cada linha, sempre visível (ex.: o ícone de opções da coluna). */\n extra?: (item: ColumnItem) => ReactNode\n /** Opções por tipo; só os tipos presentes aqui entram no adicionar. */\n options: Partial<Record<ColumnKind, Option[]>>\n /** Marca o adicionar (campo obrigatório vazio). */\n error?: boolean\n onChange: (items: ColumnItem[]) => void\n}) {\n const [drag, setDrag] = useState<{ from: number; to: number } | null>(null)\n // Só a alça arrasta: a linha inteira arrastável atrapalharia o select\n const [grabbed, setGrabbed] = useState<number | null>(null)\n const kinds = Object.keys(options) as ColumnKind[]\n const mixed = kinds.length > 1\n const used = (kind: ColumnKind, name: string) =>\n items.some((item) => item.kind === kind && item.name === name)\n const free = (kind: ColumnKind, keep?: string) =>\n (options[kind] ?? []).filter((option) => option.name === keep || !used(kind, option.name))\n const replace = (index: number, name: string) =>\n onChange(items.map((item, i) => (i === index ? { ...item, name } : item)))\n const marker = {\n content: '\"\"',\n position: 'absolute',\n left: 0,\n right: 0,\n height: 2,\n bgcolor: 'primary.main'\n }\n const addable = kinds.filter((kind) => free(kind).length)\n // Valor do adicionar: `tipo:nome` (dimensão e medida podem ter o mesmo nome)\n const addOptions = addable.flatMap((kind) => [\n ...(mixed ? [<ListSubheader key={`h:${kind}`}>{KIND_STYLE[kind].group}</ListSubheader>] : []),\n ...free(kind).map((option) => (\n <MenuItem key={`${kind}:${option.name}`} value={`${kind}:${option.name}`}>\n {mixed && (\n <Box component=\"span\" sx={{ color: KIND_STYLE[kind].color, mr: 0.75 }}>\n {KIND_STYLE[kind].icon}\n </Box>\n )}\n <OptionText option={option} />\n </MenuItem>\n ))\n ])\n const addNoun = mixed\n ? kinds.map((kind) => KIND_STYLE[kind].noun).join(' ou ')\n : KIND_STYLE[kinds[0] ?? 'measure'].noun\n\n return (\n // Ocupa a linha do formulário, mas sem esticar demais em telas largas\n <Box sx={{ display: 'flex', flexDirection: 'column', gap: 0.5, maxWidth: 760 }}>\n {items.map((item, index) => (\n <Box\n key={`${item.kind}:${item.name}`}\n draggable={grabbed === index}\n onDragStart={(e) => {\n e.dataTransfer.effectAllowed = 'move'\n // Firefox só arrasta com algum dado\n e.dataTransfer.setData('text/plain', item.name)\n setDrag({ from: index, to: index })\n }}\n onDragOver={(e) => {\n if (!drag) return\n e.preventDefault()\n const rect = e.currentTarget.getBoundingClientRect()\n const to = e.clientY < rect.top + rect.height / 2 ? index : index + 1\n if (to !== drag.to) setDrag({ ...drag, to })\n }}\n onDrop={(e) => {\n e.preventDefault()\n if (drag && drag.to !== drag.from && drag.to !== drag.from + 1)\n onChange(moveTo(items, drag.from, drag.to))\n setDrag(null)\n }}\n onDragEnd={() => {\n setDrag(null)\n setGrabbed(null)\n }}\n sx={{\n position: 'relative',\n display: 'flex',\n gap: 0.25,\n alignItems: 'center',\n opacity: drag?.from === index ? 0.4 : 1,\n '&:hover .row-actions': { visibility: 'visible' },\n '&::before':\n drag && drag.from !== index && drag.to === index ? { ...marker, top: -3 } : undefined,\n '&::after':\n drag && index === items.length - 1 && drag.to === items.length\n ? { ...marker, bottom: -3 }\n : undefined\n }}\n >\n <Box\n component=\"span\"\n title=\"Arraste para reordenar\"\n onMouseDown={() => setGrabbed(index)}\n onMouseUp={() => setGrabbed(null)}\n sx={{\n color: 'text.disabled',\n fontSize: 12,\n cursor: 'grab',\n userSelect: 'none',\n px: 0.25\n }}\n >\n ⋮⋮\n </Box>\n <Typography sx={{ fontFamily: MONO, fontSize: 11, color: 'primary.main', minWidth: 14 }}>\n {index + 1}\n </Typography>\n {mixed && (\n <Tooltip title={KIND_STYLE[item.kind].noun}>\n <Box\n component=\"span\"\n sx={{ color: KIND_STYLE[item.kind].color, fontSize: 12, minWidth: 12 }}\n >\n {KIND_STYLE[item.kind].icon}\n </Box>\n </Tooltip>\n )}\n <NameSelect\n value={item.name}\n options={free(item.kind, item.name)}\n required\n onChange={(next) => replace(index, next)}\n />\n <Box className=\"row-actions\" sx={{ display: 'flex', visibility: 'hidden' }}>\n <SmallButton\n title=\"Subir\"\n disabled={index === 0}\n onClick={() => onChange(moveTo(items, index, index - 1))}\n >\n ↑\n </SmallButton>\n <SmallButton\n title=\"Descer\"\n disabled={index === items.length - 1}\n onClick={() => onChange(moveTo(items, index, index + 2))}\n >\n ↓\n </SmallButton>\n <SmallButton\n title=\"Remover\"\n onClick={() => onChange(items.filter((_, i) => i !== index))}\n >\n ×\n </SmallButton>\n </Box>\n {extra?.(item)}\n </Box>\n ))}\n {addable.length > 0 && (\n <TextField\n select\n size=\"small\"\n fullWidth\n value=\"\"\n error={error}\n onChange={(e) => {\n const [kind, ...rest] = e.target.value.split(':')\n const name = rest.join(':')\n if (name) onChange([...items, { kind: kind as ColumnKind, name }])\n }}\n slotProps={{\n select: {\n displayEmpty: true,\n renderValue: () => (\n <Box component=\"span\" sx={{ color: 'text.secondary' }}>\n + adicionar {addNoun}\n </Box>\n )\n }\n }}\n sx={inputSx}\n >\n {addOptions}\n </TextField>\n )}\n </Box>\n )\n}\n","import {\n type Aggregation,\n type DiagramPosition,\n type DimensionDef,\n type FieldMeta,\n isAggregate,\n type MeasureDef,\n type MeasureMeta,\n type ModelDef,\n type TableDef,\n type ValueFormat,\n validateModel\n} from '../model'\nimport { parseColumnRef } from '../star'\n\n/**\n * Conversão entre o modelo (objetos indexados por nome) e as linhas da tabela do editor. As linhas\n * têm `uid` próprio para que renomear uma dimensão/medida não perca o foco nem a posição. Os\n * metadados ficam como texto (vazio = ausente) e só viram o formato do modelo em `fromEditor`.\n */\n\ntype MetaFields = { label: string; description: string }\n\nexport type DimensionRow = MetaFields & {\n uid: string\n name: string\n type: 'number' | 'string'\n sql: string\n}\nexport type MeasureRow = MetaFields & {\n uid: string\n name: string\n type: Aggregation | 'ratio' | 'formula'\n /** Expressão agregada (`sum`, `count`, `avg`...). */\n sql: string\n /** Fórmula (`{medida}`). */\n expression: string\n numerator: string\n denominator: string\n format: ValueFormat | ''\n decimals: string\n}\nexport type TableRow = MetaFields & {\n uid: string\n name: string\n key: string\n sql: string\n}\n/** Lado N (`from`) e lado 1 (`to`); a tabela vai pelo `uid`, para renomear sem quebrar. */\nexport type RelationshipRow = {\n uid: string\n fromTable: string\n fromColumn: string\n toTable: string\n toColumn: string\n inner: boolean\n}\n\nexport type EditorModel = {\n name: string\n dimensions: DimensionRow[]\n measures: MeasureRow[]\n tables: TableRow[]\n relationships: RelationshipRow[]\n /**\n * Posições do diagrama pelo `uid` da tabela: renomear não perde a posição, e o que foi removido\n * some do arquivo sozinho.\n */\n positions: Record<string, DiagramPosition>\n}\n\nlet uidCounter = 0\nexport const newUid = () => `row-${++uidCounter}`\n\nconst metaFields = (field: FieldMeta): MetaFields => ({\n label: field.label ?? '',\n description: field.description ?? ''\n})\n\nexport function toEditor(model: ModelDef): EditorModel {\n const tables: TableRow[] = Object.entries(model.tables).map(([name, table]) => ({\n uid: newUid(),\n name,\n key: table.key ?? '',\n sql: table.sql,\n ...metaFields(table)\n }))\n const uidOf = (name: string) => tables.find((table) => table.name === name)?.uid ?? ''\n const positions = Object.fromEntries(\n Object.entries(model.diagram ?? {}).flatMap(([name, point]) => {\n const uid = uidOf(name)\n return uid ? [[uid, { ...point }]] : []\n })\n )\n return {\n name: model.name,\n tables,\n relationships: (model.relationships ?? []).map((relationship) => {\n const from = parseColumnRef(relationship.from)\n const to = parseColumnRef(relationship.to)\n return {\n uid: newUid(),\n fromTable: uidOf(from?.table ?? ''),\n fromColumn: from?.column ?? '',\n toTable: uidOf(to?.table ?? ''),\n toColumn: to?.column ?? '',\n inner: relationship.inner === true\n }\n }),\n dimensions: Object.entries(model.dimensions).map(([name, dimension]) => ({\n uid: newUid(),\n name,\n type: dimension.type,\n sql: dimension.sql,\n ...metaFields(dimension)\n })),\n measures: Object.entries(model.measures).map(([name, measure]) => ({\n uid: newUid(),\n name,\n type: measure.type,\n sql: isAggregate(measure) ? measure.sql : '',\n expression: measure.type === 'formula' ? measure.expression : '',\n numerator: measure.type === 'ratio' ? measure.numerator : '',\n denominator: measure.type === 'ratio' ? measure.denominator : '',\n format: measure.format ?? '',\n decimals: measure.decimals === undefined ? '' : String(measure.decimals),\n ...metaFields(measure)\n })),\n positions\n }\n}\n\nconst fieldMeta = (row: MetaFields): FieldMeta => ({\n ...(row.label.trim() && { label: row.label.trim() }),\n ...(row.description.trim() && { description: row.description.trim() })\n})\n\nexport const dimensionOf = (row: DimensionRow): DimensionDef => ({\n sql: row.sql,\n type: row.type,\n ...fieldMeta(row)\n})\n\nexport function measureOf(row: MeasureRow): MeasureDef {\n const meta: MeasureMeta = {\n ...fieldMeta(row),\n ...(row.format && { format: row.format }),\n // Texto inválido vira NaN e a validação do modelo acusa\n ...(row.decimals.trim() && { decimals: Number(row.decimals) })\n }\n if (isAggregate(row)) return { type: row.type, sql: row.sql, ...meta }\n if (row.type === 'formula') return { type: 'formula', expression: row.expression, ...meta }\n return { type: 'ratio', numerator: row.numerator, denominator: row.denominator, ...meta }\n}\n\nexport const tableOf = (row: TableRow): TableDef => ({\n ...(row.key.trim() && { key: row.key.trim() }),\n sql: row.sql,\n ...fieldMeta(row)\n})\n\nexport function relationshipOf(editor: EditorModel, row: RelationshipRow) {\n const name = (uid: string) => editor.tables.find((table) => table.uid === uid)?.name ?? '?'\n return {\n from: `${name(row.fromTable)}.${row.fromColumn}`,\n to: `${name(row.toTable)}.${row.toColumn}`,\n ...(row.inner && { inner: true })\n }\n}\n\nexport function fromEditor(editor: EditorModel): ModelDef {\n const diagram = diagramOf(editor)\n return {\n name: editor.name,\n tables: Object.fromEntries(editor.tables.map((row) => [row.name, tableOf(row)])),\n ...(editor.relationships.length && {\n relationships: editor.relationships.map((row) => relationshipOf(editor, row))\n }),\n dimensions: Object.fromEntries(editor.dimensions.map((row) => [row.name, dimensionOf(row)])),\n measures: Object.fromEntries(editor.measures.map((row) => [row.name, measureOf(row)])),\n ...(Object.keys(diagram).length && { diagram })\n }\n}\n\n/** Posições (e tamanhos) pelo nome, na ordem dos cards; arredonda (o arquivo não precisa de frações). */\nfunction diagramOf(editor: EditorModel): Record<string, DiagramPosition> {\n return Object.fromEntries(\n editor.tables.flatMap(({ uid, name }) => {\n const point = editor.positions[uid]\n if (!point || !name) return []\n const { x, y, width, height } = point\n return [\n [\n name,\n {\n x: Math.round(x),\n y: Math.round(y),\n ...(width !== undefined && { width: Math.round(width) }),\n ...(height !== undefined && { height: Math.round(height) })\n }\n ]\n ]\n })\n )\n}\n\n/** O modelo sem as posições do diagrama: o que muda as consultas. */\nexport const withoutDiagram = ({ diagram: _, ...model }: ModelDef): ModelDef => model\n\n/** Erros do editor: nomes repetidos (que o objeto do modelo esconderia) + validação do modelo. */\nexport function validateEditor(editor: EditorModel): string[] {\n const repeated = (names: string[]) => [\n ...new Set(names.filter((name, index) => names.indexOf(name) !== index))\n ]\n const names = [...editor.dimensions, ...editor.measures].map((row) => row.name)\n const tables = editor.tables.map((row) => row.name)\n return [\n ...repeated(names).map((name) => `nome repetido: \"${name}\"`),\n ...repeated(tables).map((name) => `tabela repetida: \"${name}\"`),\n ...validateModel(fromEditor(editor)).filter((error) => !error.startsWith('nome repetido'))\n ]\n}\n\nconst escapeRegex = (text: string) => text.replace(/[.*+?^${}()|[\\]\\\\]/g, '\\\\$&')\n\n/**\n * Renomeia uma tabela e as referências `antigo.coluna` nas dimensões e medidas (os\n * relacionamentos e as posições do diagrama apontam pelo `uid` e acompanham sozinhos).\n */\nexport function renameTable(editor: EditorModel, uid: string, name: string): EditorModel {\n const previous = editor.tables.find((row) => row.uid === uid)?.name\n if (!previous || previous === name) return editor\n const pattern = new RegExp(`(?<![\\\\w.\\`])${escapeRegex(previous)}\\\\.`, 'g')\n const replace = (sql: string) => sql.replace(pattern, `${name}.`)\n return {\n ...editor,\n tables: editor.tables.map((table) => (table.uid === uid ? { ...table, name } : table)),\n dimensions: editor.dimensions.map((row) => ({ ...row, sql: replace(row.sql) })),\n measures: editor.measures.map((row) => ({ ...row, sql: replace(row.sql) }))\n }\n}\n\nexport const emptyMeasure = (changes: Partial<MeasureRow> = {}): MeasureRow => ({\n uid: newUid(),\n name: '',\n type: 'sum',\n sql: '',\n expression: '',\n numerator: '',\n denominator: '',\n format: '',\n decimals: '',\n label: '',\n description: '',\n ...changes\n})\n\nexport const emptyDimension = (changes: Partial<DimensionRow> = {}): DimensionRow => ({\n uid: newUid(),\n name: '',\n type: 'string',\n sql: '',\n label: '',\n description: '',\n ...changes\n})\n\n/** Nome livre a partir de `prefixo`, `prefixo2`, `prefixo3`... */\nexport function freeName(prefix: string, taken: string[]) {\n if (!taken.includes(prefix)) return prefix\n for (let index = 2; ; index++)\n if (!taken.includes(`${prefix}${index}`)) return `${prefix}${index}`\n}\n","import {\n Box,\n Button,\n Dialog,\n DialogActions,\n DialogContent,\n DialogTitle,\n MenuItem,\n MenuList,\n Paper,\n Popper,\n TextField\n} from '@mui/material'\nimport { createContext, useContext, useRef, useState } from 'react'\nimport type { SchemaTable } from '../types'\nimport { HighlightedSql } from './sqlHighlight'\nimport { MONO } from './ui'\n\n/**\n * Campo de SQL com destaque de sintaxe e autocomplete de tabelas e colunas. As colunas vêm do\n * `information_schema` (tabelas/views do banco) e das colunas de cada tabela do modelo (lidas do banco).\n * O ⤢ abre o mesmo SQL num editor grande.\n *\n * O destaque é um `<pre>` colorido por baixo do `<textarea>` de texto transparente: mesma fonte,\n * mesmo recuo e mesma quebra de linha, com a rolagem sincronizada. O cursor, a seleção e o\n * autocomplete continuam sendo do textarea.\n */\n\n// Recuo do texto dentro do campo (o lado direito abre espaço para o ⤢)\nconst PAD = { top: 8.5, right: 30, bottom: 8.5, left: 12 }\nconst LINE_HEIGHT = '18px'\n\nexport type SqlCompletions = {\n tables: SchemaTable[]\n /** Colunas de cada tabela do modelo (`tabela.` completa com elas). */\n modelColumns: Record<string, string[]>\n}\n\nexport const SqlCompletionsContext = createContext<SqlCompletions>({\n tables: [],\n modelColumns: {}\n})\n\ntype Suggestion = { text: string; detail: string }\n\nconst KEYWORDS = new Set(\n 'WHERE ON LEFT RIGHT INNER OUTER JOIN GROUP ORDER LIMIT USING AND OR AS SET HAVING UNION'.split(\n ' '\n )\n)\n\n/** `alias -> tabela` a partir dos `FROM x a` / `JOIN x AS a` do texto. */\nfunction aliases(sql: string) {\n const map = new Map<string, string>()\n for (const match of sql.matchAll(/\\b(?:FROM|JOIN)\\s+`?(\\w+)`?(?:\\s+(?:AS\\s+)?`?(\\w+)`?)?/gi)) {\n const [, table, alias] = match\n map.set(table.toLowerCase(), table)\n if (alias && !KEYWORDS.has(alias.toUpperCase())) map.set(alias.toLowerCase(), table)\n }\n return map\n}\n\nfunction suggest(sql: string, caret: number, completions: SqlCompletions) {\n const before = sql.slice(0, caret)\n const tables = new Map(completions.tables.map((table) => [table.name.toLowerCase(), table]))\n const columnsOf = (table: string): Suggestion[] =>\n tables.get(table.toLowerCase())?.columns.map((column) => ({\n text: column.name,\n detail: column.type\n })) ?? []\n\n let prefix: string\n let candidates: Suggestion[]\n const qualified = /([A-Za-z_]\\w*)\\.(\\w*)$/.exec(before)\n if (qualified) {\n const [, qualifier, typed] = qualified\n prefix = typed\n if (completions.modelColumns[qualifier])\n candidates = completions.modelColumns[qualifier].map((text) => ({ text, detail: qualifier }))\n else candidates = columnsOf(aliases(sql).get(qualifier.toLowerCase()) ?? qualifier)\n } else {\n const word = /[A-Za-z_]\\w*$/.exec(before)\n if (!word || word[0].length < 2) return null\n prefix = word[0]\n const referenced = [...new Set(aliases(sql).values())]\n candidates = [\n ...Object.keys(completions.modelColumns).map((text) => ({\n text,\n detail: 'tabela do modelo'\n })),\n ...completions.tables.map((table) => ({ text: table.name, detail: table.type })),\n ...referenced.flatMap(columnsOf)\n ]\n }\n\n const lower = prefix.toLowerCase()\n const seen = new Set<string>()\n const items = candidates\n .filter((item) => {\n const text = item.text.toLowerCase()\n if (seen.has(text) || text === lower || !text.includes(lower)) return false\n seen.add(text)\n return true\n })\n .sort(\n (a, b) =>\n Number(!a.text.toLowerCase().startsWith(lower)) -\n Number(!b.text.toLowerCase().startsWith(lower)) || a.text.localeCompare(b.text)\n )\n .slice(0, 8)\n return items.length ? { from: caret - prefix.length, items } : null\n}\n\ntype Props = {\n value: string\n onChange: (value: string) => void\n label?: string\n placeholder?: string\n minRows?: number\n maxRows?: number\n /** Erro do banco (validação). */\n error?: string\n warning?: string\n /** Mostra o ⤢ que abre o editor grande (desligado dentro do próprio editor grande). */\n expandable?: boolean\n}\n\nexport function SqlEditor({\n value,\n onChange,\n label,\n placeholder = 'SQL',\n minRows,\n maxRows = 6,\n error,\n warning,\n expandable = true\n}: Props) {\n const completions = useContext(SqlCompletionsContext)\n const anchor = useRef<HTMLDivElement>(null)\n const input = useRef<HTMLTextAreaElement>(null)\n const highlight = useRef<HTMLPreElement>(null)\n const [expanded, setExpanded] = useState(false)\n const [state, setState] = useState<{ from: number; items: Suggestion[]; index: number } | null>(\n null\n )\n\n const accept = (item: Suggestion) => {\n const element = input.current\n if (!element || !state) return\n const caret = element.selectionStart\n const next = value.slice(0, state.from) + item.text + value.slice(caret)\n onChange(next)\n setState(null)\n const position = state.from + item.text.length\n requestAnimationFrame(() => {\n element.focus()\n element.setSelectionRange(position, position)\n })\n }\n\n return (\n <>\n <TextField\n ref={anchor}\n inputRef={input}\n size=\"small\"\n fullWidth\n multiline\n label={label}\n minRows={minRows}\n maxRows={maxRows}\n value={value}\n placeholder={placeholder}\n error={!value.trim() || !!error}\n helperText={error ?? warning}\n onChange={(event) => {\n onChange(event.target.value)\n const found = suggest(event.target.value, event.target.selectionStart ?? 0, completions)\n setState(found && { ...found, index: 0 })\n }}\n onKeyDown={(event) => {\n if (!state) return\n if (event.key === 'ArrowDown' || event.key === 'ArrowUp') {\n event.preventDefault()\n const step = event.key === 'ArrowDown' ? 1 : -1\n setState({\n ...state,\n index: (state.index + step + state.items.length) % state.items.length\n })\n } else if (event.key === 'Enter' || event.key === 'Tab') {\n event.preventDefault()\n accept(state.items[state.index])\n } else if (event.key === 'Escape') {\n event.stopPropagation()\n setState(null)\n }\n }}\n onBlur={() => setState(null)}\n slotProps={{\n htmlInput: {\n spellCheck: false,\n onScroll: (event: React.UIEvent<HTMLTextAreaElement>) => {\n if (highlight.current) highlight.current.scrollTop = event.currentTarget.scrollTop\n }\n },\n input: {\n endAdornment: (\n <>\n <Box\n component=\"pre\"\n ref={highlight}\n aria-hidden\n sx={{\n ...textSx,\n // Exatamente sobre a caixa do textarea: recorta a rolagem no mesmo lugar\n m: 0,\n p: 0,\n position: 'absolute',\n top: PAD.top,\n right: PAD.right,\n bottom: PAD.bottom,\n left: PAD.left,\n overflow: 'hidden',\n pointerEvents: 'none',\n color: 'text.primary'\n }}\n >\n <HighlightedSql code={value} />\n {/* Linha final vazia: o textarea mostra, o <pre> sem isso esconderia */}\n {'\\n'}\n </Box>\n {expandable && (\n <Box\n component=\"button\"\n type=\"button\"\n title=\"Expandir o SQL\"\n aria-label=\"Expandir o SQL\"\n onClick={() => setExpanded(true)}\n sx={{\n position: 'absolute',\n top: 4,\n right: 4,\n zIndex: 2,\n border: 0,\n borderRadius: 0.5,\n bgcolor: 'transparent',\n color: 'text.secondary',\n cursor: 'pointer',\n fontSize: 14,\n lineHeight: 1,\n p: 0.25,\n '&:hover': { color: 'primary.main', bgcolor: 'rgba(255,255,255,.08)' }\n }}\n >\n ⤢\n </Box>\n )}\n </>\n )\n }\n }}\n sx={{\n '& .MuiInputBase-root': { ...padSx, position: 'relative', alignItems: 'flex-start' },\n '& textarea': {\n ...textSx,\n position: 'relative',\n zIndex: 1,\n color: 'transparent',\n caretColor: (theme) => theme.palette.text.primary,\n '&::placeholder': { color: 'text.disabled', opacity: 1 },\n '&::selection': { bgcolor: 'rgba(245,130,32,.35)' }\n },\n '& .MuiFormHelperText-root': {\n fontFamily: MONO,\n color: error ? 'error.main' : 'warning.main'\n }\n }}\n />\n {expandable && (\n <Dialog open={expanded} onClose={() => setExpanded(false)} maxWidth=\"lg\" fullWidth>\n <DialogTitle sx={{ fontSize: 14 }}>{label ?? 'SQL'}</DialogTitle>\n <DialogContent>\n <Box sx={{ pt: 1 }}>\n <SqlEditor\n value={value}\n onChange={onChange}\n placeholder={placeholder}\n minRows={20}\n maxRows={36}\n error={error}\n warning={warning}\n expandable={false}\n />\n </Box>\n </DialogContent>\n <DialogActions>\n <Button onClick={() => setExpanded(false)}>Fechar</Button>\n </DialogActions>\n </Dialog>\n )}\n <Popper\n open={!!state}\n anchorEl={anchor.current}\n placement=\"bottom-start\"\n sx={{ zIndex: 1400 }}\n >\n <Paper elevation={8}>\n <MenuList dense>\n {state?.items.map((item, index) => (\n <MenuItem\n key={item.text}\n selected={index === state.index}\n // mousedown: antes do blur do campo fechar a lista\n onMouseDown={(event) => {\n event.preventDefault()\n accept(item)\n }}\n sx={{ gap: 2, fontFamily: MONO, fontSize: 12 }}\n >\n {item.text}\n <Box component=\"span\" sx={{ ml: 'auto', color: 'text.secondary', fontSize: 11 }}>\n {item.detail}\n </Box>\n </MenuItem>\n ))}\n </MenuList>\n </Paper>\n </Popper>\n </>\n )\n}\n\n/** Tudo que muda a posição dos caracteres: igual no textarea e no <pre> colorido. */\nconst textSx = {\n fontFamily: MONO,\n fontSize: 12,\n lineHeight: LINE_HEIGHT,\n letterSpacing: 0,\n whiteSpace: 'pre-wrap',\n overflowWrap: 'break-word',\n wordBreak: 'normal',\n tabSize: 2,\n // Mesma largura útil com ou sem barra de rolagem\n scrollbarGutter: 'stable'\n} as const\n\nconst padSx = {\n padding: `${PAD.top}px ${PAD.right}px ${PAD.bottom}px ${PAD.left}px`\n}\n","import { Box, MenuItem, TextField, Typography } from '@mui/material'\nimport { AGGREGATION_LABEL, AGGREGATIONS, isAggregate, VALUE_FORMATS } from '../model'\nimport type { MeasureRow } from './modelCode'\nimport { SqlEditor } from './SqlEditor'\nimport { MONO } from './ui'\n\n/** Campos do editor do modelo, usados pela tabela e pelo painel de propriedades do diagrama. */\n\nexport const inputSx = { '& .MuiInputBase-input': { fontFamily: MONO, fontSize: 12 } }\n\nexport const MEASURE_TYPES: { value: MeasureRow['type']; label: string }[] = [\n ...AGGREGATIONS.map((value) => ({ value, label: `${value} · ${AGGREGATION_LABEL[value]}` })),\n { value: 'ratio', label: 'ratio · Razão' },\n { value: 'formula', label: 'formula · Fórmula' }\n]\n\nexport function NameField({\n value,\n onChange,\n onBlur,\n label\n}: {\n value: string\n onChange: (value: string) => void\n onBlur?: () => void\n label?: string\n}) {\n return (\n <TextField\n size=\"small\"\n fullWidth\n label={label}\n value={value}\n placeholder=\"nome\"\n error={!/^[A-Za-z_][A-Za-z0-9_]*$/.test(value)}\n onChange={(e) => onChange(e.target.value)}\n onBlur={onBlur}\n onKeyDown={(e) => {\n if (e.key === 'Enter') (e.target as HTMLInputElement).blur()\n }}\n sx={inputSx}\n />\n )\n}\n\nexport function MeasureSelect({\n value,\n options,\n onChange\n}: {\n value: string\n options: string[]\n onChange: (value: string) => void\n}) {\n return (\n <TextField\n select\n size=\"small\"\n value={options.includes(value) ? value : ''}\n error={!options.includes(value)}\n onChange={(e) => onChange(e.target.value)}\n sx={{ ...inputSx, minWidth: 140, flex: 1 }}\n >\n {options.map((name) => (\n <MenuItem key={name} value={name}>\n {name}\n </MenuItem>\n ))}\n </TextField>\n )\n}\n\nexport function MeasureTypeSelect({\n value,\n onChange\n}: {\n value: MeasureRow['type']\n onChange: (value: MeasureRow['type']) => void\n}) {\n return (\n <TextField\n select\n size=\"small\"\n fullWidth\n value={value}\n onChange={(e) => onChange(e.target.value as MeasureRow['type'])}\n sx={inputSx}\n >\n {MEASURE_TYPES.map((type) => (\n <MenuItem key={type.value} value={type.value}>\n {type.label}\n </MenuItem>\n ))}\n </TextField>\n )\n}\n\n/** Definição da medida conforme o tipo: SQL da soma, as duas medidas da razão ou a fórmula. */\nexport function MeasureDefinition({\n row,\n measureNames,\n error,\n onPatch\n}: {\n row: MeasureRow\n measureNames: string[]\n error?: string\n onPatch: (changes: Partial<MeasureRow>) => void\n}) {\n const others = measureNames.filter((name) => name !== row.name)\n if (isAggregate(row))\n return (\n <SqlEditor\n value={row.sql}\n placeholder={\n row.type === 'count' || row.type === 'countDistinct'\n ? 'tabela.coluna (conta os valores não nulos)'\n : 'tabela.coluna'\n }\n error={error}\n onChange={(sql) => onPatch({ sql })}\n />\n )\n if (row.type === 'formula')\n return (\n <SqlEditor\n value={row.expression}\n placeholder=\"COALESCE({medidaA}, 0) + COALESCE({medidaB}, 0)\"\n error={error}\n warning={others.length ? `medidas: ${others.map((name) => `{${name}}`).join(' ')}` : ''}\n onChange={(expression) => onPatch({ expression })}\n />\n )\n return (\n <Box sx={{ display: 'flex', alignItems: 'center', gap: 1 }}>\n <MeasureSelect\n value={row.numerator}\n options={others}\n onChange={(numerator) => onPatch({ numerator })}\n />\n <Typography sx={{ fontFamily: MONO }}>/</Typography>\n <MeasureSelect\n value={row.denominator}\n options={others}\n onChange={(denominator) => onPatch({ denominator })}\n />\n </Box>\n )\n}\n\nexport function FormatFields({\n row,\n onPatch\n}: {\n row: MeasureRow\n onPatch: (changes: Partial<MeasureRow>) => void\n}) {\n return (\n <Box sx={{ display: 'flex', gap: 0.5 }}>\n <TextField\n select\n size=\"small\"\n value={row.format}\n onChange={(e) => onPatch({ format: e.target.value as MeasureRow['format'] })}\n sx={{ ...inputSx, flex: 1 }}\n slotProps={{ select: { displayEmpty: true } }}\n >\n <MenuItem value=\"\">\n <em>padrão</em>\n </MenuItem>\n {VALUE_FORMATS.map((format) => (\n <MenuItem key={format} value={format}>\n {format}\n </MenuItem>\n ))}\n </TextField>\n <TextField\n size=\"small\"\n placeholder=\"casas\"\n value={row.decimals}\n error={!!row.decimals.trim() && !/^\\d+$/.test(row.decimals.trim())}\n onChange={(e) => onPatch({ decimals: e.target.value })}\n sx={{ ...inputSx, width: 64 }}\n />\n </Box>\n )\n}\n\nexport function DictionaryFields({\n row,\n onPatch\n}: {\n row: { label: string; description: string }\n onPatch: (changes: { label?: string; description?: string }) => void\n}) {\n return (\n <Box sx={{ display: 'flex', flexDirection: 'column', gap: 0.5 }}>\n <TextField\n size=\"small\"\n placeholder=\"rótulo\"\n value={row.label}\n onChange={(e) => onPatch({ label: e.target.value })}\n sx={inputSx}\n />\n <TextField\n size=\"small\"\n placeholder=\"descrição\"\n multiline\n maxRows={4}\n value={row.description}\n onChange={(e) => onPatch({ description: e.target.value })}\n sx={inputSx}\n />\n </Box>\n )\n}\n","import {\n Box,\n Checkbox,\n MenuItem,\n TextField,\n ToggleButton,\n ToggleButtonGroup,\n Typography\n} from '@mui/material'\nimport { useState } from 'react'\nimport type { ModelColumns } from '../types'\nimport { type DimensionRow, type EditorModel, emptyDimension, freeName } from './modelCode'\nimport { inputSx } from './modelFields'\nimport { SqlEditor } from './SqlEditor'\nimport { MONO } from './ui'\n\n/**\n * Modo simples das dimensões: marcar as colunas da tabela que viram dimensão. Marcar cria\n * `tabela.coluna` (tipo pelo valor lido do banco); desmarcar remove a dimensão que é exatamente\n * essa coluna. Dimensão com SQL próprio (`YEAR(tabela.data)`) não aparece marcada aqui — essa se\n * edita no painel dela.\n */\n\n/** `tabela.coluna` puro (o que o modo simples sabe editar). */\nexport const SIMPLE_DIMENSION = /^\\s*([A-Za-z_][A-Za-z0-9_]*)\\.([A-Za-z_][A-Za-z0-9_]*)\\s*$/\n\ntype Props = {\n editor: EditorModel\n setEditor: (update: (current: EditorModel) => EditorModel) => void\n columns: ModelColumns | null\n table: string\n /** Abre a dimensão no painel. */\n onOpen: (uid: string) => void\n}\n\nexport function DimensionPicker({ editor, setEditor, columns, table, onOpen }: Props) {\n const [search, setSearch] = useState('')\n const loaded = columns?.tables[table]\n if (!loaded)\n return (\n <Typography sx={{ fontSize: 12, color: 'text.disabled' }}>\n Colunas ainda não lidas: use \"Recarregar colunas\".\n </Typography>\n )\n\n const numeric = new Set(columns?.numeric ?? [])\n const dimensionsOf = (column: string) =>\n editor.dimensions.filter((row) => {\n const match = SIMPLE_DIMENSION.exec(row.sql)\n return match?.[1] === table && match[2] === column\n })\n\n const toggle = (column: string, checked: boolean) =>\n setEditor((current) => {\n if (!checked) {\n const removed = new Set(dimensionsOf(column).map((row) => row.uid))\n return { ...current, dimensions: current.dimensions.filter((row) => !removed.has(row.uid)) }\n }\n const taken = [...current.dimensions, ...current.measures].map((row) => row.name)\n // Nome da coluna; se já existir, com a tabela na frente\n const name = taken.includes(column) ? freeName(`${table}_${column}`, taken) : column\n const dimension = emptyDimension({\n name,\n type: numeric.has(`${table}.${column}`) ? 'number' : 'string',\n sql: `${table}.${column}`\n })\n return { ...current, dimensions: [...current.dimensions, dimension] }\n })\n\n const visible = loaded.filter((column) => column.toLowerCase().includes(search.toLowerCase()))\n return (\n <Box sx={{ display: 'flex', flexDirection: 'column' }}>\n {loaded.length > 10 && (\n <TextField\n size=\"small\"\n placeholder=\"filtrar colunas\"\n value={search}\n onChange={(e) => setSearch(e.target.value)}\n sx={{ ...inputSx, mb: 0.5 }}\n />\n )}\n {visible.map((column) => {\n const existing = dimensionsOf(column)\n return (\n <Box\n key={column}\n component=\"label\"\n sx={{\n display: 'flex',\n alignItems: 'center',\n gap: 0.5,\n fontSize: 12,\n fontFamily: MONO,\n cursor: 'pointer',\n borderRadius: 0.5,\n '&:hover': { bgcolor: 'rgba(255,255,255,.05)' }\n }}\n >\n <Checkbox\n size=\"small\"\n sx={{ p: 0.25 }}\n checked={!!existing.length}\n onChange={(e) => toggle(column, e.target.checked)}\n />\n <Box component=\"span\" sx={{ flex: 1 }}>\n {column}\n {numeric.has(`${table}.${column}`) && (\n <Box component=\"span\" sx={{ color: 'text.disabled', ml: 0.5 }}>\n Σ\n </Box>\n )}\n </Box>\n {existing.map((row) => (\n <Box\n key={row.uid}\n component=\"button\"\n type=\"button\"\n title=\"Abrir a dimensão\"\n onClick={(event) => {\n event.preventDefault()\n onOpen(row.uid)\n }}\n sx={{\n border: 0,\n bgcolor: 'transparent',\n color: '#a5d8ff',\n cursor: 'pointer',\n fontFamily: MONO,\n fontSize: 11,\n p: 0\n }}\n >\n ◇ {row.name || 'sem nome'}\n </Box>\n ))}\n </Box>\n )\n })}\n </Box>\n )\n}\n\nconst PARTIAL = /^\\s*([A-Za-z_][A-Za-z0-9_]*)\\.([A-Za-z0-9_]*)\\s*$/\n\n/**\n * Origem de uma dimensão: no modo simples, tabela + coluna (vira `tabela.coluna`); no modo SQL, a\n * expressão livre (`YEAR(tabela.data)`, `CONCAT(...)`). Abre no simples quando o SQL é só a coluna.\n */\nexport function DimensionSource({\n row,\n editor,\n columns,\n error,\n warning,\n onPatch\n}: {\n row: DimensionRow\n editor: EditorModel\n columns: ModelColumns | null\n error?: string\n warning?: string\n onPatch: (changes: Partial<DimensionRow>) => void\n}) {\n const [mode, setMode] = useState<'simple' | 'sql'>(() =>\n !row.sql.trim() || PARTIAL.test(row.sql) ? 'simple' : 'sql'\n )\n const parsed = PARTIAL.exec(row.sql)\n const table = parsed?.[1] ?? ''\n const column = parsed?.[2] ?? ''\n const tableColumns = columns?.tables[table] ?? []\n const numeric = new Set(columns?.numeric ?? [])\n\n const choose = (nextTable: string, nextColumn: string) => {\n const changes: Partial<DimensionRow> = { sql: `${nextTable}.${nextColumn}` }\n if (nextColumn) {\n changes.type = numeric.has(`${nextTable}.${nextColumn}`) ? 'number' : 'string'\n // Nome ainda automático: acompanha a coluna\n if (!row.name || /^novaDimensao\\d*$/.test(row.name)) {\n const taken = [...editor.dimensions, ...editor.measures]\n .filter((item) => item.uid !== row.uid)\n .map((item) => item.name)\n changes.name = freeName(nextColumn, taken)\n }\n }\n onPatch(changes)\n }\n\n return (\n <Box sx={{ display: 'flex', flexDirection: 'column', gap: 1 }}>\n <ToggleButtonGroup\n size=\"small\"\n exclusive\n value={mode}\n onChange={(_, next: 'simple' | 'sql' | null) => next && setMode(next)}\n >\n <ToggleButton value=\"simple\" sx={{ textTransform: 'none', py: 0.25, flex: 1 }}>\n Tabela e coluna\n </ToggleButton>\n <ToggleButton value=\"sql\" sx={{ textTransform: 'none', py: 0.25, flex: 1 }}>\n SQL\n </ToggleButton>\n </ToggleButtonGroup>\n {mode === 'simple' ? (\n <>\n {!parsed && row.sql.trim() && (\n <Typography sx={{ fontSize: 11, color: 'warning.main' }}>\n O SQL atual ({row.sql.trim()}) não é uma coluna só; escolher aqui substitui ele.\n </Typography>\n )}\n <Box sx={{ display: 'flex', gap: 1 }}>\n <TextField\n select\n size=\"small\"\n label=\"tabela\"\n value={editor.tables.some((item) => item.name === table) ? table : ''}\n onChange={(e) =>\n choose(\n e.target.value,\n columns?.tables[e.target.value]?.includes(column) ? column : ''\n )\n }\n sx={{ ...inputSx, flex: 1 }}\n >\n {editor.tables.map((item) => (\n <MenuItem key={item.uid} value={item.name}>\n {item.name}\n </MenuItem>\n ))}\n </TextField>\n {tableColumns.length ? (\n <TextField\n select\n size=\"small\"\n label=\"coluna\"\n value={tableColumns.includes(column) ? column : ''}\n error={!!error}\n onChange={(e) => choose(table, e.target.value)}\n sx={{ ...inputSx, flex: 1 }}\n >\n {tableColumns.map((name) => (\n <MenuItem key={name} value={name}>\n {name}\n </MenuItem>\n ))}\n </TextField>\n ) : (\n // Colunas ainda não lidas: digita\n <TextField\n size=\"small\"\n label=\"coluna\"\n value={column}\n disabled={!table}\n onChange={(e) => choose(table, e.target.value)}\n sx={{ ...inputSx, flex: 1 }}\n />\n )}\n </Box>\n {(error || warning) && (\n <Typography\n sx={{ fontSize: 11, fontFamily: MONO, color: error ? 'error.main' : 'warning.main' }}\n >\n {error ?? warning}\n </Typography>\n )}\n </>\n ) : (\n <SqlEditor\n label=\"sql\"\n value={row.sql}\n error={error}\n warning={warning}\n onChange={(sql) => onPatch({ sql })}\n />\n )}\n </Box>\n )\n}\n","import {\n Alert,\n Box,\n Button,\n Checkbox,\n Dialog,\n DialogActions,\n DialogContent,\n DialogTitle,\n Divider,\n FormControlLabel,\n IconButton,\n MenuItem,\n TextField,\n Tooltip,\n Typography\n} from '@mui/material'\nimport {\n type MouseEvent as ReactMouseEvent,\n type ReactNode,\n useEffect,\n useMemo,\n useRef,\n useState,\n type WheelEvent\n} from 'react'\nimport { isAggregate } from '../model'\nimport { measureHome, modelEdges, referencedTables } from '../star'\nimport type { ModelColumns } from '../types'\nimport { DimensionPicker, DimensionSource } from './DimensionPicker'\nimport {\n type DimensionRow,\n type EditorModel,\n emptyDimension,\n emptyMeasure,\n freeName,\n fromEditor,\n type MeasureRow,\n newUid,\n type RelationshipRow,\n renameTable,\n type TableRow\n} from './modelCode'\nimport {\n DictionaryFields,\n FormatFields,\n inputSx,\n MeasureDefinition,\n MeasureTypeSelect,\n NameField\n} from './modelFields'\nimport { SqlEditor } from './SqlEditor'\nimport { MONO } from './ui'\n\n/**\n * Diagrama do modelo, no estilo da \"Exibição de modelo\" do Power BI: um card por tabela (colunas,\n * dimensões e medidas que saem dela) e uma linha por relacionamento, com `*` no lado N e `1` no\n * lado 1. Edita o mesmo rascunho da tabela do editor.\n *\n * - arrastar o cabeçalho move o card; arrastar o fundo move a tela; Ctrl+roda dá zoom;\n * - arrastar uma coluna até a coluna de outra tabela cria o relacionamento (quem foi arrastado é o\n * lado N; de dimensão para fato, inverte sozinho);\n * - clicar num card, linha, dimensão ou medida abre as propriedades à direita; Delete remove;\n * - os botões `+◇`/`+Σ` de uma coluna criam a dimensão/medida dela.\n *\n * As posições dos cards fazem parte do modelo (`diagram`) e vão para o arquivo ao salvar.\n */\n\ntype Props = {\n editor: EditorModel\n setEditor: (update: (current: EditorModel) => EditorModel) => void\n columns: ModelColumns | null\n /** Pedaços que o banco recusou (`table:<nome>`, `relationship:<i>`, `dimension:<nome>`...). */\n errors: Record<string, string>\n warnings: Record<string, string>\n loadingColumns: boolean\n onLoadColumns: () => void\n onTry: (selection: { dimensions: string[]; measures: string[] }) => void\n /** Consultas ativas que usam cada nome. */\n usage: Map<string, number>\n}\n\n/**\n * Papel da tabela, tirado dos relacionamentos (não é configurado): `one` só aparece no lado 1\n * (cadastro que filtra), `many` tem relacionamento saindo (lançamentos), `alone` não tem nenhum.\n */\ntype NodeRole = 'one' | 'many' | 'alone'\n\ntype ColumnItem = {\n kind: 'column'\n name: string\n numeric: boolean\n isKey: boolean\n linked: boolean\n /** Citada no modelo, mas a tabela (já lida do banco) não tem. */\n missing: boolean\n}\ntype FieldItem = { kind: 'dimension' | 'measure'; uid: string; name: string; icon: string }\ntype Item = ColumnItem | FieldItem\n\ntype DiagramNode = {\n /** Chave das posições: `uid` da tabela. */\n id: string\n uid: string\n name: string\n role: NodeRole\n /** Coluna única da tabela (`key`). */\n key: string\n items: Item[]\n error?: string\n}\n\ntype Selection =\n | { kind: 'table'; uid: string }\n | { kind: 'relationship'; uid: string }\n | { kind: 'dimension'; uid: string }\n | { kind: 'measure'; uid: string }\n | null\n\ntype Point = { x: number; y: number }\ntype View = { x: number; y: number; zoom: number }\n\nconst CARD_WIDTH = 230\nconst HEADER = 34\nconst ROW = 22\nconst MAX_BODY = 264\nconst PADDING = 4\n/** Limites do redimensionamento do card. */\nconst MIN_WIDTH = 160\nconst MAX_WIDTH = 800\nconst MIN_HEIGHT = HEADER + ROW + PADDING * 2\nconst MAX_HEIGHT = 1600\n\ntype Size = { width: number; height: number }\n\nconst ROLE_STYLE: Record<NodeRole, { color: string; label: string; title: string }> = {\n one: { color: '#4dabf7', label: 'lado 1', title: 'Só aparece no lado 1: filtra outras tabelas' },\n many: { color: '#F58220', label: 'lado N', title: 'Tem relacionamento saindo (lado N)' },\n alone: { color: '#868e96', label: 'solta', title: 'Sem relacionamentos' }\n}\n\nconst PANEL_KEY = 'bm-dashboard-devtools:diagram-panel'\nconst PANEL_MIN = 260\nconst PANEL_MAX = 720\n\ntype PanelState = { open: boolean; width: number }\n\nfunction loadPanel(): PanelState {\n try {\n const saved = JSON.parse(localStorage.getItem(PANEL_KEY) ?? 'null')\n if (typeof saved?.width === 'number')\n return {\n open: saved.open !== false,\n width: Math.min(PANEL_MAX, Math.max(PANEL_MIN, saved.width))\n }\n } catch {}\n return { open: true, width: 340 }\n}\n\n/** Acompanha o mouse até soltar o botão. */\nfunction track(\n event: ReactMouseEvent,\n onMove: (dx: number, dy: number, event: MouseEvent) => void,\n onUp?: (event: MouseEvent, moved: boolean) => void\n) {\n event.preventDefault()\n event.stopPropagation()\n const start = { x: event.clientX, y: event.clientY }\n // Janela do elemento: com o devtools em janela separada, o mouse se move nela, não na página\n const win = event.currentTarget.ownerDocument.defaultView ?? window\n let moved = false\n const move = (moveEvent: MouseEvent) => {\n const dx = moveEvent.clientX - start.x\n const dy = moveEvent.clientY - start.y\n if (Math.abs(dx) + Math.abs(dy) > 3) moved = true\n if (moved) onMove(dx, dy, moveEvent)\n }\n const up = (upEvent: MouseEvent) => {\n win.removeEventListener('mousemove', move)\n win.removeEventListener('mouseup', up)\n onUp?.(upEvent, moved)\n }\n win.addEventListener('mousemove', move)\n win.addEventListener('mouseup', up)\n}\n\n/** Colunas citadas como `tabela.coluna` no SQL das dimensões/medidas. */\nfunction citedColumns(sql: string, table: string) {\n const code = sql.replace(/'(?:[^'\\\\]|\\\\.)*'/g, \"''\")\n const pattern = new RegExp(`(?<![\\\\w.\\`])${table}\\\\.([A-Za-z_][A-Za-z0-9_]*)`, 'g')\n return [...code.matchAll(pattern)].map((match) => match[1])\n}\n\n/** Ícone de cada agregação no card (a soma fica com o Σ). */\nconst MEASURE_ICON: Partial<Record<MeasureRow['type'], string>> = {\n count: '#',\n countDistinct: '#',\n avg: 'x̄',\n min: '↓',\n max: '↑'\n}\n\nconst fieldItems = (\n dimensions: DimensionRow[],\n measures: MeasureRow[],\n belongs: (sql: string) => boolean\n): FieldItem[] => [\n ...dimensions\n .filter((row) => belongs(row.sql))\n .map((row) => ({ kind: 'dimension' as const, uid: row.uid, name: row.name, icon: '◇' })),\n ...measures\n .filter((row) => isAggregate(row) && belongs(row.sql))\n .map((row) => ({\n kind: 'measure' as const,\n uid: row.uid,\n name: row.name,\n icon: MEASURE_ICON[row.type] ?? 'Σ'\n }))\n]\n\nfunction buildNodes(\n editor: EditorModel,\n columns: ModelColumns | null,\n errors: Record<string, string>\n): DiagramNode[] {\n const numeric = new Set(columns?.numeric ?? [])\n const columnItems = (\n node: string,\n loaded: string[] | undefined,\n extra: string[],\n key: string,\n linked: Set<string>\n ): ColumnItem[] => {\n const names = [...(loaded ?? []), ...extra.filter((name) => !loaded?.includes(name))]\n return [...new Set(names)].map((name) => ({\n kind: 'column',\n name,\n numeric: numeric.has(`${node}.${name}`),\n isKey: name === key,\n linked: linked.has(name),\n missing: !!loaded?.length && !loaded.includes(name)\n }))\n }\n\n const tableNames = editor.tables.map((table) => table.name)\n const edges = modelEdges(fromEditor(editor))\n // Tabela onde a medida/dimensão agrega (a que alcança as outras que ela cita)\n const homeOf = (sql: string) => measureHome(referencedTables(sql, tableNames), edges)\n return editor.tables.map((table) => {\n const linked = new Set(\n editor.relationships.flatMap((row) => [\n ...(row.fromTable === table.uid ? [row.fromColumn] : []),\n ...(row.toTable === table.uid ? [row.toColumn] : [])\n ])\n )\n const cited = [...editor.dimensions, ...editor.measures].flatMap((row) =>\n citedColumns(row.sql, table.name)\n )\n return {\n id: table.uid,\n uid: table.uid,\n name: table.name,\n role: editor.relationships.some((row) => row.fromTable === table.uid)\n ? ('many' as const)\n : editor.relationships.some((row) => row.toTable === table.uid)\n ? ('one' as const)\n : ('alone' as const),\n key: table.key,\n error: errors[`table:${table.name}`],\n items: [\n ...columnItems(\n table.name,\n columns?.tables[table.name],\n [...(table.key ? [table.key] : []), ...linked, ...cited],\n table.key,\n linked\n ),\n ...fieldItems(editor.dimensions, editor.measures, (sql) => homeOf(sql) === table.name)\n ]\n }\n })\n}\n\n/** Altura do conteúdo (sem tamanho salvo): até `MAX_BODY` de linhas, o resto rola. */\nconst contentHeight = (node: DiagramNode) =>\n HEADER + Math.min(node.items.length * ROW, MAX_BODY) + PADDING * 2\n\nconst clamp = (value: number, min: number, max: number) => Math.min(max, Math.max(min, value))\n\n/** Quem só filtra (lado 1) em cima, o resto embaixo (como costuma ficar no Power BI). */\nfunction autoLayout(nodes: DiagramNode[], sizes: Map<string, Size>) {\n const top = nodes.filter((node) => node.role === 'one')\n const bottom = nodes.filter((node) => node.role !== 'one')\n const positions: Record<string, Point> = {}\n const gap = 60\n const row = (list: DiagramNode[], y: number) => {\n let x = 40\n for (const node of list) {\n positions[node.id] = { x, y }\n x += (sizes.get(node.id)?.width ?? CARD_WIDTH) + gap\n }\n }\n row(top, 40)\n const topHeight = Math.max(0, ...top.map((node) => sizes.get(node.id)?.height ?? HEADER))\n row(bottom, 40 + topHeight + 140)\n return positions\n}\n\nexport function ModelDiagram({\n editor,\n setEditor,\n columns,\n errors,\n warnings,\n loadingColumns,\n onLoadColumns,\n onTry,\n usage\n}: Props) {\n const nodes = useMemo(() => buildNodes(editor, columns, errors), [editor, columns, errors])\n // Card sendo arrastado/redimensionado: a posição e o tamanho só vão para o modelo ao soltar\n const [moving, setMoving] = useState<{ id: string; point: Point } | null>(null)\n const [resizing, setResizing] = useState<({ id: string } & Size) | null>(null)\n const [collapsed, setCollapsed] = useState<Record<string, boolean>>({})\n const [scrolls, setScrolls] = useState<Record<string, number>>({})\n const [view, setView] = useState<View>({ x: 0, y: 0, zoom: 1 })\n const [selection, setSelection] = useState<Selection>(null)\n const [panel, setPanel] = useState<PanelState>(loadPanel)\n const [picking, setPicking] = useState<string | null>(null)\n\n useEffect(() => {\n try {\n localStorage.setItem(PANEL_KEY, JSON.stringify(panel))\n } catch {}\n }, [panel])\n\n // Selecionou algo com o painel recolhido: abre para mostrar as propriedades\n useEffect(() => {\n if (selection) setPanel((current) => (current.open ? current : { ...current, open: true }))\n }, [selection])\n\n const startPanelResize = (event: ReactMouseEvent) => {\n const start = panel.width\n track(event, (dx) =>\n setPanel((current) => ({\n ...current,\n width: Math.min(PANEL_MAX, Math.max(PANEL_MIN, start - dx))\n }))\n )\n }\n const [linking, setLinking] = useState<{ node: DiagramNode; column: string; to: Point } | null>(\n null\n )\n const [hoveredEdge, setHoveredEdge] = useState<string | null>(null)\n const canvas = useRef<HTMLDivElement>(null)\n\n // Colunas do banco: carrega uma vez ao abrir o diagrama\n const requested = useRef(false)\n useEffect(() => {\n if (requested.current || columns) return\n requested.current = true\n onLoadColumns()\n }, [columns, onLoadColumns])\n\n // Tamanho de cada card: o salvo no modelo (redimensionado) ou o padrão; recolhido, só o cabeçalho\n const sizes = useMemo(\n () =>\n new Map(\n nodes.map((node): [string, Size] => {\n const saved = resizing?.id === node.id ? resizing : editor.positions[node.id]\n const width = saved?.width ?? CARD_WIDTH\n if (collapsed[node.id]) return [node.id, { width, height: HEADER }]\n return [node.id, { width, height: saved?.height ?? contentHeight(node) }]\n })\n ),\n [nodes, collapsed, editor.positions, resizing]\n )\n const sizeOf = (node: DiagramNode): Size =>\n sizes.get(node.id) ?? { width: CARD_WIDTH, height: HEADER }\n // Card sem posição salva entra no layout automático (sem mexer nos que já foram arrumados)\n const fallback = useMemo(() => autoLayout(nodes, sizes), [nodes, sizes])\n const placed = (node: DiagramNode): Point => {\n if (moving?.id === node.id) return moving.point\n const saved = editor.positions[node.id]\n return saved ? { x: saved.x, y: saved.y } : (fallback[node.id] ?? { x: 0, y: 0 })\n }\n const setPositions = (update: (current: EditorModel['positions']) => EditorModel['positions']) =>\n setEditor((current) => ({ ...current, positions: update(current.positions) }))\n\n const nodeOf = (uid: string) => nodes.find((node) => node.uid === uid)\n\n /** Ponto da linha na coluna do card (lado esquerdo ou direito). */\n const anchor = (node: DiagramNode, column: string, side: 'left' | 'right'): Point => {\n const { x, y } = placed(node)\n const { width, height } = sizeOf(node)\n const index = node.items.findIndex((item) => item.kind === 'column' && item.name === column)\n let rowY = y + HEADER / 2\n if (!collapsed[node.id] && index >= 0) {\n const raw = y + HEADER + PADDING + index * ROW + ROW / 2 - (scrolls[node.id] ?? 0)\n rowY = Math.min(Math.max(raw, y + HEADER + 2), y + height - 2)\n }\n return { x: side === 'left' ? x : x + width, y: rowY }\n }\n\n const toWorld = (clientX: number, clientY: number): Point => {\n const rect = canvas.current?.getBoundingClientRect()\n return {\n x: (clientX - (rect?.left ?? 0) - view.x) / view.zoom,\n y: (clientY - (rect?.top ?? 0) - view.y) / view.zoom\n }\n }\n\n // --- edição ---\n\n const patchTable = (uid: string, changes: Partial<TableRow>) =>\n setEditor((current) => ({\n ...current,\n tables: current.tables.map((row) => (row.uid === uid ? { ...row, ...changes } : row))\n }))\n const patchRelationship = (uid: string, changes: Partial<RelationshipRow>) =>\n setEditor((current) => ({\n ...current,\n relationships: current.relationships.map((row) =>\n row.uid === uid ? { ...row, ...changes } : row\n )\n }))\n const patchDimension = (uid: string, changes: Partial<DimensionRow>) =>\n setEditor((current) => ({\n ...current,\n dimensions: current.dimensions.map((row) => (row.uid === uid ? { ...row, ...changes } : row))\n }))\n const patchMeasure = (uid: string, changes: Partial<MeasureRow>) =>\n setEditor((current) => ({\n ...current,\n measures: current.measures.map((row) => (row.uid === uid ? { ...row, ...changes } : row))\n }))\n\n /** Perto do centro da área visível (onde entra um card novo). */\n const visibleCenter = () => {\n const rect = canvas.current?.getBoundingClientRect()\n return toWorld(\n (rect?.left ?? 0) + (rect?.width ?? 600) / 2 - CARD_WIDTH / 2,\n (rect?.top ?? 0) + (rect?.height ?? 400) / 3\n )\n }\n\n const addTable = () => {\n const uid = newUid()\n const name = freeName(\n 'novaTabela',\n editor.tables.map((table) => table.name)\n )\n const center = visibleCenter()\n setEditor((current) => ({\n ...current,\n positions: { ...current.positions, [uid]: center },\n tables: [\n ...current.tables,\n {\n uid,\n name,\n key: '',\n sql: 'SELECT * FROM tabela',\n label: '',\n description: ''\n }\n ]\n }))\n setSelection({ kind: 'table', uid })\n }\n\n const removeTable = (uid: string) => {\n setEditor((current) => ({\n ...current,\n tables: current.tables.filter((row) => row.uid !== uid),\n relationships: current.relationships.filter(\n (row) => row.fromTable !== uid && row.toTable !== uid\n )\n }))\n setSelection(null)\n }\n\n // Corrige as referências `tabela.coluna` (a posição vai pelo uid)\n const commitRename = (uid: string, name: string) =>\n setEditor((current) => renameTable(current, uid, name))\n\n const connect = (from: DiagramNode, fromColumn: string, to: DiagramNode, toColumn: string) => {\n if (from.uid === to.uid) return\n // O lado 1 é quem entra pela própria chave: arrastou da chave para uma coluna comum, inverte\n const swap = fromColumn === from.key && toColumn !== to.key\n const [many, manyColumn, one, oneColumn] = swap\n ? [to, toColumn, from, fromColumn]\n : [from, fromColumn, to, toColumn]\n const uid = newUid()\n setEditor((current) => ({\n ...current,\n relationships: [\n ...current.relationships,\n {\n uid,\n fromTable: many.uid,\n fromColumn: manyColumn,\n toTable: one.uid,\n toColumn: oneColumn,\n inner: false\n }\n ]\n }))\n setSelection({ kind: 'relationship', uid })\n }\n\n /** Dimensão/medida nova a partir da tabela (ou de uma coluna dela, já preenchida). */\n const addField = (\n kind: 'dimension' | 'measure',\n table: string,\n column?: { name: string; numeric: boolean }\n ) => {\n const uid = newUid()\n const taken = [...editor.dimensions, ...editor.measures].map((row) => row.name)\n const sql = `${table}.${column?.name ?? ''}`\n if (kind === 'dimension')\n setEditor((current) => ({\n ...current,\n dimensions: [\n ...current.dimensions,\n emptyDimension({\n uid,\n name: freeName(column?.name ?? 'novaDimensao', taken),\n type: column?.numeric ? 'number' : 'string',\n sql\n })\n ]\n }))\n else\n setEditor((current) => ({\n ...current,\n measures: [\n ...current.measures,\n // Coluna de texto/data não soma: vira contagem\n emptyMeasure({\n uid,\n name: freeName(\n column ? `${column.numeric ? 'total' : 'qtd'}_${column.name}` : 'novaMedida',\n taken\n ),\n type: column && !column.numeric ? 'count' : 'sum',\n sql\n })\n ]\n }))\n setSelection({ kind, uid })\n }\n\n const removeSelection = () => {\n if (!selection) return\n if (selection.kind === 'table') removeTable(selection.uid)\n else {\n const list = (\n { relationship: 'relationships', dimension: 'dimensions', measure: 'measures' } as const\n )[selection.kind]\n setEditor((current) => ({\n ...current,\n [list]: (current[list] as { uid: string }[]).filter((row) => row.uid !== selection.uid)\n }))\n setSelection(null)\n }\n }\n\n // --- mouse ---\n\n const startPan = (event: ReactMouseEvent) => {\n if (event.button !== 0) return\n const start = view\n track(\n event,\n (dx, dy) => setView((current) => ({ ...current, x: start.x + dx, y: start.y + dy })),\n (_, moved) => {\n if (!moved) setSelection(null)\n }\n )\n }\n\n const startMove = (event: ReactMouseEvent, node: DiagramNode) => {\n if (event.button !== 0) return\n const start = placed(node)\n const { zoom } = view\n let point = start\n track(\n event,\n (dx, dy) => {\n point = { x: start.x + dx / zoom, y: start.y + dy / zoom }\n setMoving({ id: node.id, point })\n },\n (_, moved) => {\n setMoving(null)\n // Mantém o tamanho salvo do card\n if (moved)\n setPositions((current) => ({ ...current, [node.id]: { ...current[node.id], ...point } }))\n else selectNode(node)\n }\n )\n }\n\n /** Arrasta a borda direita (`width`), a de baixo (`height`) ou o canto (as duas). */\n const startResize = (\n event: ReactMouseEvent,\n node: DiagramNode,\n edges: { width: boolean; height: boolean }\n ) => {\n if (event.button !== 0) return\n const start = sizeOf(node)\n const { zoom } = view\n let size = start\n track(\n event,\n (dx, dy) => {\n size = {\n width: edges.width ? clamp(start.width + dx / zoom, MIN_WIDTH, MAX_WIDTH) : start.width,\n height: edges.height\n ? clamp(start.height + dy / zoom, MIN_HEIGHT, MAX_HEIGHT)\n : start.height\n }\n setResizing({ id: node.id, ...size })\n },\n (_, moved) => {\n setResizing(null)\n if (!moved) return\n const point = placed(node)\n setPositions((current) => ({\n ...current,\n [node.id]: {\n ...point,\n ...current[node.id],\n ...(edges.width && { width: size.width }),\n ...(edges.height && { height: size.height })\n }\n }))\n }\n )\n }\n\n /** Duplo clique na alça: volta ao tamanho automático (largura padrão, altura do conteúdo). */\n const resetSize = (node: DiagramNode) =>\n setPositions((current) => {\n const saved = current[node.id]\n if (!saved) return current\n return { ...current, [node.id]: { x: saved.x, y: saved.y } }\n })\n\n const startLink = (event: ReactMouseEvent, node: DiagramNode, column: string) => {\n if (event.button !== 0) return\n track(\n event,\n (_, __, moveEvent) =>\n setLinking({ node, column, to: toWorld(moveEvent.clientX, moveEvent.clientY) }),\n (upEvent, moved) => {\n setLinking(null)\n if (!moved) {\n selectNode(node)\n return\n }\n const target = (canvas.current?.ownerDocument ?? document)\n .elementFromPoint(upEvent.clientX, upEvent.clientY)\n ?.closest<HTMLElement>('[data-diagram-column]')\n const targetNode = nodes.find((item) => item.id === target?.dataset.diagramNode)\n const targetColumn = target?.dataset.diagramColumn\n if (targetNode && targetColumn) connect(node, column, targetNode, targetColumn)\n }\n )\n }\n\n const onWheel = (event: WheelEvent) => {\n if (!event.ctrlKey && !event.metaKey) {\n setView((current) => ({\n ...current,\n x: current.x - event.deltaX,\n y: current.y - event.deltaY\n }))\n return\n }\n const rect = canvas.current?.getBoundingClientRect()\n const px = event.clientX - (rect?.left ?? 0)\n const py = event.clientY - (rect?.top ?? 0)\n setView((current) => {\n const zoom = Math.min(2, Math.max(0.3, current.zoom * (event.deltaY > 0 ? 0.9 : 1.1)))\n const ratio = zoom / current.zoom\n return { zoom, x: px - (px - current.x) * ratio, y: py - (py - current.y) * ratio }\n })\n }\n\n // Ctrl+roda não pode dar zoom na página inteira\n useEffect(() => {\n const element = canvas.current\n if (!element) return\n const prevent = (event: globalThis.WheelEvent) => event.preventDefault()\n element.addEventListener('wheel', prevent, { passive: false })\n return () => element.removeEventListener('wheel', prevent)\n }, [])\n\n const fitToScreen = (layout?: Record<string, Point>) => {\n const rect = canvas.current?.getBoundingClientRect()\n if (!rect || !nodes.length) return\n const boxes = nodes.map((node) => ({\n ...(layout?.[node.id] ?? placed(node)),\n w: sizeOf(node).width,\n h: sizeOf(node).height\n }))\n const minX = Math.min(...boxes.map((box) => box.x))\n const minY = Math.min(...boxes.map((box) => box.y))\n const maxX = Math.max(...boxes.map((box) => box.x + box.w))\n const maxY = Math.max(...boxes.map((box) => box.y + box.h))\n const zoom = Math.min(\n 1.2,\n Math.max(0.3, Math.min((rect.width - 60) / (maxX - minX), (rect.height - 60) / (maxY - minY)))\n )\n setView({ zoom, x: 30 - minX * zoom, y: 30 - minY * zoom })\n }\n\n const selectNode = (node: DiagramNode) => setSelection({ kind: 'table', uid: node.uid })\n\n const isSelected = (node: DiagramNode) =>\n selection?.kind === 'table' && selection.uid === node.uid\n\n // --- linhas ---\n\n type Line = {\n id: string\n from: Point\n to: Point\n selected: boolean\n inner?: boolean\n error?: string\n onClick?: () => void\n }\n const lines: Line[] = []\n const pushLine = (\n id: string,\n many: DiagramNode,\n manyColumn: string,\n one: DiagramNode,\n oneColumn: string,\n extra: Partial<Line>\n ) => {\n const manyX = placed(many).x + sizeOf(many).width / 2\n const oneX = placed(one).x + sizeOf(one).width / 2\n const rightward = manyX <= oneX\n lines.push({\n id,\n from: anchor(many, manyColumn, rightward ? 'right' : 'left'),\n to: anchor(one, oneColumn, rightward ? 'left' : 'right'),\n selected: false,\n ...extra\n })\n }\n editor.relationships.forEach((row, index) => {\n const many = nodeOf(row.fromTable)\n const one = nodeOf(row.toTable)\n if (!many || !one) return\n pushLine(row.uid, many, row.fromColumn, one, row.toColumn, {\n inner: row.inner,\n selected: selection?.kind === 'relationship' && selection.uid === row.uid,\n error: errors[`relationship:${index}`],\n onClick: () => setSelection({ kind: 'relationship', uid: row.uid })\n })\n })\n\n // Dimensões/medidas que não caem em nenhum card (SQL sem `tabela.coluna` conhecido)\n const shown = new Set(\n nodes.flatMap((node) => node.items.map((item) => 'uid' in item && item.uid))\n )\n const unplaced = fieldItems(editor.dimensions, editor.measures, () => true).filter(\n (item) => !shown.has(item.uid)\n )\n\n const linkPreview =\n linking &&\n (() => {\n const start = anchor(\n linking.node,\n linking.column,\n linking.to.x < placed(linking.node).x ? 'left' : 'right'\n )\n return curve(start, linking.to)\n })()\n\n return (\n <Box sx={{ display: 'flex', height: '100%', minHeight: 0 }}>\n <Box\n ref={canvas}\n tabIndex={-1}\n onMouseDown={startPan}\n // O arrastar cancela o mouse down; o foco é o que faz o Delete chegar aqui\n onMouseDownCapture={() => canvas.current?.focus({ preventScroll: true })}\n onKeyDown={(event) => {\n if (\n (event.key === 'Delete' || event.key === 'Backspace') &&\n event.target === canvas.current\n )\n removeSelection()\n }}\n onWheel={onWheel}\n sx={{\n outline: 'none',\n flex: 1,\n position: 'relative',\n overflow: 'hidden',\n cursor: 'grab',\n bgcolor: '#15171b',\n backgroundImage: 'radial-gradient(rgba(255,255,255,.07) 1px, transparent 1px)',\n backgroundSize: `${20 * view.zoom}px ${20 * view.zoom}px`,\n backgroundPosition: `${view.x}px ${view.y}px`\n }}\n >\n <Box\n sx={{\n position: 'absolute',\n left: 0,\n top: 0,\n transformOrigin: '0 0',\n transform: `translate(${view.x}px, ${view.y}px) scale(${view.zoom})`\n }}\n >\n <svg\n width={1}\n height={1}\n style={{ position: 'absolute', overflow: 'visible', pointerEvents: 'none' }}\n aria-hidden\n >\n {lines.map((line) => (\n <RelationshipLine\n key={line.id}\n line={line}\n hovered={hoveredEdge === line.id}\n onHover={(hovered) => setHoveredEdge(hovered ? line.id : null)}\n />\n ))}\n {linkPreview && (\n <path\n d={linkPreview}\n fill=\"none\"\n stroke=\"#F58220\"\n strokeWidth={2}\n strokeDasharray=\"5 4\"\n />\n )}\n </svg>\n\n {nodes.map((node) => (\n <TableCard\n key={node.id}\n node={node}\n position={placed(node)}\n size={sizeOf(node)}\n collapsed={!!collapsed[node.id]}\n selected={!!isSelected(node)}\n linking={!!linking && linking.node.id !== node.id}\n selectedField={\n selection?.kind === 'dimension' || selection?.kind === 'measure'\n ? selection.uid\n : null\n }\n onToggle={() =>\n setCollapsed((current) => ({ ...current, [node.id]: !current[node.id] }))\n }\n onScroll={(top) => setScrolls((current) => ({ ...current, [node.id]: top }))}\n onHeaderDown={(event) => startMove(event, node)}\n onResizeDown={(event, edges) => startResize(event, node, edges)}\n onResizeReset={() => resetSize(node)}\n onColumnDown={(event, column) => startLink(event, node, column)}\n onFieldClick={(item) => setSelection({ kind: item.kind, uid: item.uid })}\n onAddField={(kind, column) => addField(kind, node.name, column)}\n />\n ))}\n </Box>\n\n <Box\n onMouseDown={(event) => event.stopPropagation()}\n sx={{\n position: 'absolute',\n top: 8,\n left: 8,\n right: 8,\n display: 'flex',\n gap: 0.75,\n flexWrap: 'wrap',\n alignItems: 'center',\n pointerEvents: 'none',\n '& > *': { pointerEvents: 'auto' }\n }}\n >\n <Button size=\"small\" variant=\"outlined\" onClick={addTable}>\n + Tabela\n </Button>\n <Button\n size=\"small\"\n variant=\"outlined\"\n disabled={!editor.tables.length}\n onClick={() => setPicking(editor.tables[0]?.name ?? null)}\n title=\"Escolher a tabela e marcar as colunas que viram dimensão\"\n >\n + Dimensões\n </Button>\n <Button\n size=\"small\"\n onClick={onLoadColumns}\n disabled={loadingColumns}\n title=\"Lê uma linha de cada tabela para listar as colunas\"\n sx={{ bgcolor: '#1b1e23' }}\n >\n {loadingColumns ? 'Lendo colunas…' : 'Recarregar colunas'}\n </Button>\n <Box sx={{ ml: 'auto', display: 'flex', gap: 0.5, alignItems: 'center' }}>\n <Button\n size=\"small\"\n onClick={() => {\n const layout = autoLayout(nodes, sizes)\n // Troca as posições, mas mantém o tamanho de quem foi redimensionado\n setPositions((current) =>\n Object.fromEntries(\n Object.entries(layout).map(([id, point]) => [id, { ...current[id], ...point }])\n )\n )\n fitToScreen(layout)\n }}\n title=\"Dimensões em cima, fatos embaixo (troca as posições salvas)\"\n sx={{ bgcolor: '#1b1e23' }}\n >\n Organizar\n </Button>\n <Button size=\"small\" onClick={() => fitToScreen()} sx={{ bgcolor: '#1b1e23' }}>\n Ajustar à tela\n </Button>\n <IconButton\n size=\"small\"\n aria-label=\"Diminuir zoom\"\n onClick={() =>\n setView((current) => ({ ...current, zoom: Math.max(0.3, current.zoom - 0.1) }))\n }\n >\n −\n </IconButton>\n <Typography sx={{ fontSize: 11, fontFamily: MONO, width: 36, textAlign: 'center' }}>\n {Math.round(view.zoom * 100)}%\n </Typography>\n <IconButton\n size=\"small\"\n aria-label=\"Aumentar zoom\"\n onClick={() =>\n setView((current) => ({ ...current, zoom: Math.min(2, current.zoom + 0.1) }))\n }\n >\n +\n </IconButton>\n </Box>\n </Box>\n\n {!nodes.length && (\n <Box\n sx={{\n position: 'absolute',\n inset: 0,\n display: 'flex',\n alignItems: 'center',\n justifyContent: 'center',\n pointerEvents: 'none',\n color: 'text.secondary',\n fontSize: 13,\n textAlign: 'center',\n px: 4\n }}\n >\n Modelo vazio. Adicione as tabelas dimensão (cadastros: navio, calendário…) e fato\n (lançamentos: pesagens, custos…) e arraste a coluna da fato até a chave da dimensão para\n relacioná-las.\n </Box>\n )}\n {!!nodes.length && (\n <Typography\n sx={{\n position: 'absolute',\n left: 10,\n bottom: 6,\n fontSize: 11,\n color: 'text.disabled',\n pointerEvents: 'none'\n }}\n >\n Arraste uma coluna até a coluna de outra tabela para relacionar · +◇/+Σ na coluna cria\n dimensão/medida · Delete remove · Ctrl+roda: zoom\n </Typography>\n )}\n </Box>\n\n {panel.open ? (\n <Box\n sx={{\n width: panel.width,\n flexShrink: 0,\n borderLeft: 1,\n borderColor: 'divider',\n position: 'relative',\n display: 'flex',\n flexDirection: 'column',\n minHeight: 0\n }}\n >\n {/* Borda arrastável: redimensiona o painel */}\n <Box\n onMouseDown={startPanelResize}\n title=\"Arraste para redimensionar\"\n sx={{\n position: 'absolute',\n left: -3,\n top: 0,\n bottom: 0,\n width: 6,\n cursor: 'ew-resize',\n zIndex: 2,\n '&:hover': { bgcolor: 'primary.main', opacity: 0.4 }\n }}\n />\n <Box\n sx={{\n display: 'flex',\n alignItems: 'center',\n px: 1.5,\n py: 0.5,\n borderBottom: 1,\n borderColor: 'divider'\n }}\n >\n <Typography sx={{ fontSize: 12, fontWeight: 700, color: 'text.secondary', flex: 1 }}>\n Propriedades\n </Typography>\n <IconButton\n size=\"small\"\n aria-label=\"Recolher propriedades\"\n title=\"Recolher\"\n onClick={() => setPanel((current) => ({ ...current, open: false }))}\n >\n ⟩\n </IconButton>\n </Box>\n <Box sx={{ overflow: 'auto', flex: 1, p: 1.5 }}>\n <Properties\n editor={editor}\n selection={selection}\n columns={columns}\n errors={errors}\n warnings={warnings}\n usage={usage}\n onSelect={setSelection}\n onTry={onTry}\n setEditor={setEditor}\n patchTable={patchTable}\n patchRelationship={patchRelationship}\n patchDimension={patchDimension}\n patchMeasure={patchMeasure}\n removeTable={removeTable}\n commitRename={commitRename}\n addField={addField}\n unplaced={unplaced}\n />\n </Box>\n </Box>\n ) : (\n <Box\n component=\"button\"\n type=\"button\"\n title=\"Mostrar as propriedades\"\n onClick={() => setPanel((current) => ({ ...current, open: true }))}\n sx={{\n width: 28,\n flexShrink: 0,\n border: 0,\n borderLeft: 1,\n borderColor: 'divider',\n bgcolor: 'background.paper',\n color: 'text.secondary',\n cursor: 'pointer',\n writingMode: 'vertical-rl',\n fontSize: 12,\n py: 1,\n '&:hover': { color: 'primary.main' }\n }}\n >\n ⟨ Propriedades\n </Box>\n )}\n\n <Dialog open={picking !== null} onClose={() => setPicking(null)} maxWidth=\"xs\" fullWidth>\n <DialogTitle sx={{ fontSize: 14 }}>Dimensões</DialogTitle>\n <DialogContent>\n <Typography sx={{ fontSize: 12, color: 'text.secondary', mb: 1 }}>\n Marque as colunas que viram dimensão (filtro e eixo dos gráficos). Para expressões como{' '}\n <code>YEAR(tabela.data)</code>, use o modo SQL da dimensão.\n </Typography>\n <TextField\n select\n size=\"small\"\n fullWidth\n label=\"tabela\"\n value={picking ?? ''}\n onChange={(e) => setPicking(e.target.value)}\n sx={{ ...inputSx, mb: 1 }}\n >\n {editor.tables.map((table) => (\n <MenuItem key={table.uid} value={table.name}>\n {table.name}\n </MenuItem>\n ))}\n </TextField>\n {picking && (\n <DimensionPicker\n editor={editor}\n setEditor={setEditor}\n columns={columns}\n table={picking}\n onOpen={(uid) => {\n setPicking(null)\n setSelection({ kind: 'dimension', uid })\n }}\n />\n )}\n </DialogContent>\n <DialogActions>\n <Button onClick={() => setPicking(null)}>Fechar</Button>\n </DialogActions>\n </Dialog>\n </Box>\n )\n}\n\n/** Curva com tangentes horizontais (saída e chegada pelas laterais dos cards). */\nfunction curve(from: Point, to: Point) {\n const bend = Math.max(40, Math.abs(to.x - from.x) / 2)\n const out = to.x >= from.x ? 1 : -1\n return `M ${from.x} ${from.y} C ${from.x + bend * out} ${from.y}, ${to.x - bend * out} ${to.y}, ${to.x} ${to.y}`\n}\n\nfunction RelationshipLine({\n line,\n hovered,\n onHover\n}: {\n line: {\n from: Point\n to: Point\n selected: boolean\n inner?: boolean\n error?: string\n onClick?: () => void\n }\n hovered: boolean\n onHover: (hovered: boolean) => void\n}) {\n const { from, to } = line\n const d = curve(from, to)\n const color = line.error ? '#ff6b6b' : line.selected ? '#F58220' : hovered ? '#ced4da' : '#868e96'\n const out = to.x >= from.x ? 1 : -1\n // Ponto do meio da curva e a direção do filtro (do lado 1 para o lado N)\n const mid = { x: (from.x + to.x) / 2, y: (from.y + to.y) / 2 }\n const angle = (Math.atan2(from.y - to.y, from.x - to.x) * 180) / Math.PI\n return (\n <g style={{ pointerEvents: line.onClick ? 'auto' : 'none' }}>\n {line.error && <title>{line.error}</title>}\n {/* biome-ignore lint/a11y/noStaticElementInteractions: área de clique da linha; os relacionamentos também abrem pela lista do painel */}\n <path\n d={d}\n fill=\"none\"\n stroke=\"transparent\"\n strokeWidth={12}\n style={{ cursor: line.onClick ? 'pointer' : undefined, pointerEvents: 'stroke' }}\n onMouseDown={(event) => event.stopPropagation()}\n onClick={line.onClick}\n onMouseEnter={() => onHover(true)}\n onMouseLeave={() => onHover(false)}\n />\n <path\n d={d}\n fill=\"none\"\n stroke={color}\n strokeWidth={line.selected || line.inner ? 2.4 : 1.4}\n />\n <polygon\n points=\"-5,-4 5,0 -5,4\"\n fill={color}\n transform={`translate(${mid.x} ${mid.y}) rotate(${angle})`}\n />\n <text\n x={from.x + 8 * out}\n y={from.y - 5}\n fill={color}\n fontSize={14}\n fontWeight={700}\n textAnchor=\"middle\"\n >\n *\n </text>\n <text\n x={to.x - 8 * out}\n y={to.y - 5}\n fill={color}\n fontSize={12}\n fontWeight={700}\n textAnchor=\"middle\"\n >\n 1\n </text>\n </g>\n )\n}\n\nfunction TableCard({\n node,\n position,\n size,\n collapsed,\n selected,\n linking,\n selectedField,\n onToggle,\n onScroll,\n onHeaderDown,\n onResizeDown,\n onResizeReset,\n onColumnDown,\n onFieldClick,\n onAddField\n}: {\n node: DiagramNode\n position: Point\n size: Size\n collapsed: boolean\n selected: boolean\n linking: boolean\n selectedField: string | null\n onToggle: () => void\n onScroll: (top: number) => void\n onHeaderDown: (event: ReactMouseEvent) => void\n onResizeDown: (event: ReactMouseEvent, edges: { width: boolean; height: boolean }) => void\n onResizeReset: () => void\n onColumnDown: (event: ReactMouseEvent, column: string) => void\n onFieldClick: (item: FieldItem) => void\n onAddField: (kind: 'dimension' | 'measure', column: { name: string; numeric: boolean }) => void\n}) {\n const style = ROLE_STYLE[node.role]\n const columnActions = ['dimension', 'measure'] as const\n return (\n <Box\n onMouseDown={(event) => event.stopPropagation()}\n sx={{\n position: 'absolute',\n left: position.x,\n top: position.y,\n width: size.width,\n height: size.height,\n bgcolor: '#23272e',\n border: '1px solid',\n borderColor: node.error ? 'error.main' : selected ? style.color : '#3a3f47',\n borderTop: `3px solid ${style.color}`,\n borderRadius: 1,\n boxShadow: selected ? `0 0 0 2px ${style.color}55, 0 6px 18px rgba(0,0,0,.4)` : 3,\n display: 'flex',\n flexDirection: 'column',\n userSelect: 'none',\n cursor: 'default'\n }}\n >\n <Box\n onMouseDown={onHeaderDown}\n title={node.error}\n sx={{\n height: HEADER - 3,\n display: 'flex',\n alignItems: 'center',\n gap: 0.75,\n px: 1,\n cursor: 'move',\n borderBottom: collapsed ? 0 : '1px solid #3a3f47',\n flexShrink: 0\n }}\n >\n <Box component=\"span\" sx={{ color: style.color, fontSize: 13 }}>\n ▦\n </Box>\n <Typography\n sx={{\n fontWeight: 700,\n fontSize: 13,\n overflow: 'hidden',\n textOverflow: 'ellipsis',\n whiteSpace: 'nowrap',\n flex: 1\n }}\n >\n {node.name || <em>sem nome</em>}\n </Typography>\n <Box component=\"span\" title={style.title} sx={{ fontSize: 10, color: style.color }}>\n {style.label}\n </Box>\n {node.error && (\n <Box component=\"span\" sx={{ color: 'error.main', fontSize: 12 }}>\n ⚠\n </Box>\n )}\n <Box\n component=\"button\"\n type=\"button\"\n aria-label={collapsed ? 'Expandir' : 'Recolher'}\n onMouseDown={(event) => event.stopPropagation()}\n onClick={onToggle}\n sx={{\n border: 0,\n bgcolor: 'transparent',\n color: 'text.secondary',\n cursor: 'pointer',\n p: 0,\n fontSize: 11\n }}\n >\n {collapsed ? '▾' : '▴'}\n </Box>\n </Box>\n {!collapsed && (\n <Box\n onScroll={(event) => onScroll(event.currentTarget.scrollTop)}\n sx={{ overflow: 'auto', flex: 1, py: `${PADDING}px` }}\n >\n {!node.items.length && (\n <Typography\n sx={{ fontSize: 11, color: 'text.disabled', px: 1, lineHeight: `${ROW}px` }}\n >\n sem colunas lidas\n </Typography>\n )}\n {node.items.map((item) =>\n item.kind === 'column' ? (\n <Box\n key={`c:${item.name}`}\n data-diagram-node={node.id}\n data-diagram-column={item.name}\n onMouseDown={(event) => onColumnDown(event, item.name)}\n title={\n item.missing\n ? 'Citada no modelo, mas a tabela não devolve essa coluna'\n : 'Arraste até a coluna de outra tabela para relacionar'\n }\n sx={{\n height: ROW,\n display: 'flex',\n alignItems: 'center',\n gap: 0.75,\n px: 1,\n fontSize: 12,\n cursor: 'crosshair',\n '& .column-actions': { display: 'none' },\n '&:hover .column-actions': { display: linking ? 'none' : 'flex' },\n color: item.missing ? 'error.main' : item.linked ? 'text.primary' : '#adb5bd',\n fontWeight: item.linked ? 700 : 400,\n '&:hover': { bgcolor: linking ? 'rgba(245,130,32,.25)' : 'rgba(255,255,255,.06)' }\n }}\n >\n <Box\n component=\"span\"\n sx={{ width: 14, textAlign: 'center', color: 'text.secondary' }}\n >\n {item.isKey ? '🔑' : item.numeric ? 'Σ' : ''}\n </Box>\n <Box\n component=\"span\"\n sx={{ overflow: 'hidden', textOverflow: 'ellipsis', whiteSpace: 'nowrap' }}\n >\n {item.name}\n </Box>\n <Box className=\"column-actions\" sx={{ ml: 'auto', gap: 0.25 }}>\n {columnActions.map((kind) => (\n <Box\n key={kind}\n component=\"button\"\n type=\"button\"\n title={\n kind === 'dimension'\n ? `Nova dimensão com ${node.name}.${item.name}`\n : `Nova medida: ${item.numeric ? 'soma' : 'contagem'} de ${node.name}.${item.name}`\n }\n onMouseDown={(event) => event.stopPropagation()}\n onClick={() => onAddField(kind, item)}\n sx={{\n border: '1px solid #3a3f47',\n borderRadius: 0.5,\n bgcolor: '#1b1e23',\n color: kind === 'measure' ? '#ffd8a8' : '#a5d8ff',\n cursor: 'pointer',\n fontSize: 10,\n lineHeight: '14px',\n px: 0.5\n }}\n >\n {kind === 'dimension' ? '+◇' : '+Σ'}\n </Box>\n ))}\n </Box>\n </Box>\n ) : (\n <Box\n key={`f:${item.uid}`}\n onMouseDown={(event) => event.stopPropagation()}\n onClick={() => onFieldClick(item)}\n sx={{\n height: ROW,\n display: 'flex',\n alignItems: 'center',\n gap: 0.75,\n px: 1,\n fontSize: 12,\n cursor: 'pointer',\n color: item.kind === 'measure' ? '#ffd8a8' : '#a5d8ff',\n bgcolor: selectedField === item.uid ? 'rgba(245,130,32,.2)' : undefined,\n '&:hover': { bgcolor: 'rgba(255,255,255,.06)' }\n }}\n >\n <Box component=\"span\" sx={{ width: 14, textAlign: 'center' }}>\n {item.icon}\n </Box>\n <Box\n component=\"span\"\n sx={{ overflow: 'hidden', textOverflow: 'ellipsis', whiteSpace: 'nowrap' }}\n >\n {item.name || <em>sem nome</em>}\n </Box>\n </Box>\n )\n )}\n </Box>\n )}\n {/* Alças de redimensionar: borda direita, borda de baixo e o canto (recolhido, só a largura) */}\n <Box\n onMouseDown={(event) => onResizeDown(event, { width: true, height: false })}\n onDoubleClick={onResizeReset}\n title=\"Arraste para mudar a largura (duplo clique: tamanho automático)\"\n sx={{ ...resizeHandleSx, top: 0, right: -4, bottom: 8, width: 8, cursor: 'ew-resize' }}\n />\n {!collapsed && (\n <>\n <Box\n onMouseDown={(event) => onResizeDown(event, { width: false, height: true })}\n onDoubleClick={onResizeReset}\n title=\"Arraste para mudar a altura (duplo clique: tamanho automático)\"\n sx={{\n ...resizeHandleSx,\n left: 0,\n right: 8,\n bottom: -4,\n height: 8,\n cursor: 'ns-resize'\n }}\n />\n <Box\n onMouseDown={(event) => onResizeDown(event, { width: true, height: true })}\n onDoubleClick={onResizeReset}\n title=\"Arraste para redimensionar (duplo clique: tamanho automático)\"\n sx={{\n ...resizeHandleSx,\n right: -4,\n bottom: -4,\n width: 14,\n height: 14,\n cursor: 'nwse-resize',\n // Marquinha no canto, como as janelas\n '&::after': {\n content: '\"\"',\n position: 'absolute',\n right: 6,\n bottom: 6,\n width: 6,\n height: 6,\n borderRight: '2px solid #5c636e',\n borderBottom: '2px solid #5c636e'\n },\n '&:hover::after': { borderColor: ROLE_STYLE[node.role].color }\n }}\n />\n </>\n )}\n </Box>\n )\n}\n\nconst resizeHandleSx = { position: 'absolute', zIndex: 1 } as const\n\nfunction PropertyBlock({ title, children }: { title: string; children: ReactNode }) {\n return (\n <Box sx={{ display: 'flex', flexDirection: 'column', gap: 1, mb: 2 }}>\n <Typography\n variant=\"overline\"\n sx={{ color: 'text.secondary', fontWeight: 700, lineHeight: 1.5 }}\n >\n {title}\n </Typography>\n {children}\n </Box>\n )\n}\n\nfunction ColumnSelect({\n label,\n value,\n options,\n onChange\n}: {\n label: string\n value: string\n options: string[]\n onChange: (value: string) => void\n}) {\n // Sem colunas lidas, digita livre\n if (!options.length)\n return (\n <TextField\n size=\"small\"\n label={label}\n value={value}\n onChange={(e) => onChange(e.target.value)}\n sx={{ ...inputSx, flex: 1 }}\n />\n )\n return (\n <TextField\n select\n size=\"small\"\n label={label}\n value={options.includes(value) ? value : ''}\n error={!options.includes(value)}\n onChange={(e) => onChange(e.target.value)}\n sx={{ ...inputSx, flex: 1 }}\n >\n {options.map((name) => (\n <MenuItem key={name} value={name}>\n {name}\n </MenuItem>\n ))}\n </TextField>\n )\n}\n\nfunction TableSelect({\n label,\n value,\n tables,\n onChange\n}: {\n label: string\n value: string\n tables: TableRow[]\n onChange: (uid: string) => void\n}) {\n return (\n <TextField\n select\n size=\"small\"\n label={label}\n value={tables.some((table) => table.uid === value) ? value : ''}\n onChange={(e) => onChange(e.target.value)}\n sx={{ ...inputSx, flex: 1 }}\n >\n {tables.map((table) => (\n <MenuItem key={table.uid} value={table.uid}>\n {table.name}\n </MenuItem>\n ))}\n </TextField>\n )\n}\n\nfunction Properties({\n editor,\n selection,\n columns,\n errors,\n warnings,\n usage,\n onSelect,\n onTry,\n setEditor,\n patchTable,\n patchRelationship,\n patchDimension,\n patchMeasure,\n removeTable,\n commitRename,\n addField,\n unplaced\n}: {\n editor: EditorModel\n selection: Selection\n columns: ModelColumns | null\n errors: Record<string, string>\n warnings: Record<string, string>\n usage: Map<string, number>\n onSelect: (selection: Selection) => void\n onTry: Props['onTry']\n setEditor: Props['setEditor']\n patchTable: (uid: string, changes: Partial<TableRow>) => void\n patchRelationship: (uid: string, changes: Partial<RelationshipRow>) => void\n patchDimension: (uid: string, changes: Partial<DimensionRow>) => void\n patchMeasure: (uid: string, changes: Partial<MeasureRow>) => void\n removeTable: (uid: string) => void\n commitRename: (uid: string, name: string) => void\n addField: (kind: 'dimension' | 'measure', table: string) => void\n unplaced: FieldItem[]\n}) {\n const tableName = (uid: string) => editor.tables.find((table) => table.uid === uid)?.name ?? '?'\n const columnsOf = (uid: string) => columns?.tables[tableName(uid)] ?? []\n const measureNames = editor.measures.map((row) => row.name).filter(Boolean)\n const inUse = (name: string) => usage.get(name) ?? 0\n const addButtons = (table: string, kinds: ('dimension' | 'measure')[]) =>\n kinds.map((kind) => (\n <Button key={kind} size=\"small\" onClick={() => addField(kind, table)}>\n {kind === 'dimension' ? '+ Dimensão daqui' : '+ Medida daqui'}\n </Button>\n ))\n\n if (selection?.kind === 'table') {\n const table = editor.tables.find((row) => row.uid === selection.uid)\n if (!table) return null\n return (\n <>\n <PropertyBlock title=\"Tabela\">\n <RenameField\n key={table.uid}\n value={table.name}\n onCommit={(name) => commitRename(table.uid, name)}\n />\n <ColumnSelect\n label=\"chave (key)\"\n value={table.key}\n options={columnsOf(table.uid).length ? ['', ...columnsOf(table.uid)] : []}\n onChange={(key) => patchTable(table.uid, { key })}\n />\n <SqlEditor\n label=\"sql\"\n minRows={3}\n maxRows={12}\n value={table.sql}\n error={errors[`table:${table.name}`]}\n onChange={(sql) => patchTable(table.uid, { sql })}\n />\n </PropertyBlock>\n <PropertyBlock title=\"Dimensões (marque as colunas)\">\n <DimensionPicker\n editor={editor}\n setEditor={setEditor}\n columns={columns}\n table={table.name}\n onOpen={(uid) => onSelect({ kind: 'dimension', uid })}\n />\n </PropertyBlock>\n <PropertyBlock title=\"Dicionário\">\n <DictionaryFields row={table} onPatch={(changes) => patchTable(table.uid, changes)} />\n </PropertyBlock>\n <Box sx={{ display: 'flex', gap: 1, flexWrap: 'wrap' }}>\n {addButtons(table.name, ['dimension', 'measure'])}\n <Button size=\"small\" color=\"error\" onClick={() => removeTable(table.uid)}>\n Remover tabela\n </Button>\n </Box>\n </>\n )\n }\n\n if (selection?.kind === 'relationship') {\n const index = editor.relationships.findIndex((row) => row.uid === selection.uid)\n const row = editor.relationships[index]\n if (!row) return null\n return (\n <>\n <PropertyBlock title=\"Relacionamento\">\n <Typography sx={{ fontSize: 12, color: 'text.secondary' }}>\n Muitos para um (*:1). O filtro vai do lado 1 para o lado N: filtrar{' '}\n <b>{tableName(row.toTable)}</b> filtra as linhas de <b>{tableName(row.fromTable)}</b>.\n </Typography>\n {errors[`relationship:${index}`] && (\n <Alert severity=\"error\" sx={{ fontSize: 12 }}>\n {errors[`relationship:${index}`]}\n </Alert>\n )}\n <Typography sx={{ fontSize: 12, fontWeight: 700 }}>Lado N (*)</Typography>\n <Box sx={{ display: 'flex', gap: 1 }}>\n <TableSelect\n label=\"tabela\"\n value={row.fromTable}\n tables={editor.tables}\n onChange={(fromTable) => patchRelationship(row.uid, { fromTable })}\n />\n <ColumnSelect\n label=\"coluna\"\n value={row.fromColumn}\n options={columnsOf(row.fromTable)}\n onChange={(fromColumn) => patchRelationship(row.uid, { fromColumn })}\n />\n </Box>\n <Typography sx={{ fontSize: 12, fontWeight: 700 }}>Lado 1</Typography>\n <Box sx={{ display: 'flex', gap: 1 }}>\n <TableSelect\n label=\"tabela\"\n value={row.toTable}\n tables={editor.tables}\n onChange={(toTable) => patchRelationship(row.uid, { toTable })}\n />\n <ColumnSelect\n label=\"coluna\"\n value={row.toColumn}\n options={columnsOf(row.toTable)}\n onChange={(toColumn) => patchRelationship(row.uid, { toColumn })}\n />\n </Box>\n </PropertyBlock>\n <PropertyBlock title=\"Opções\">\n <FormControlLabel\n control={\n <Checkbox\n size=\"small\"\n checked={row.inner}\n onChange={(e) => patchRelationship(row.uid, { inner: e.target.checked })}\n />\n }\n label={\n <Typography sx={{ fontSize: 12 }}>\n Pressupor integridade referencial (INNER JOIN): linhas de {tableName(row.fromTable)}{' '}\n sem par em {tableName(row.toTable)} ficam de fora, em vez de virar um grupo em\n branco. A tabela do lado 1 entra sempre na consulta.\n </Typography>\n }\n />\n </PropertyBlock>\n <Box sx={{ display: 'flex', gap: 1 }}>\n <Button\n size=\"small\"\n onClick={() =>\n patchRelationship(row.uid, {\n fromTable: row.toTable,\n fromColumn: row.toColumn,\n toTable: row.fromTable,\n toColumn: row.fromColumn\n })\n }\n >\n Inverter lados\n </Button>\n <Button\n size=\"small\"\n color=\"error\"\n onClick={() => {\n setEditor((current) => ({\n ...current,\n relationships: current.relationships.filter((item) => item.uid !== row.uid)\n }))\n onSelect(null)\n }}\n >\n Remover\n </Button>\n </Box>\n </>\n )\n }\n\n if (selection?.kind === 'dimension') {\n const row = editor.dimensions.find((item) => item.uid === selection.uid)\n if (!row) return null\n return (\n <>\n <PropertyBlock title=\"Dimensão\">\n <NameField\n label=\"nome\"\n value={row.name}\n onChange={(name) => patchDimension(row.uid, { name })}\n />\n <TextField\n select\n size=\"small\"\n label=\"tipo\"\n value={row.type}\n onChange={(e) =>\n patchDimension(row.uid, { type: e.target.value as DimensionRow['type'] })\n }\n sx={inputSx}\n >\n <MenuItem value=\"string\">string</MenuItem>\n <MenuItem value=\"number\">number</MenuItem>\n </TextField>\n <DimensionSource\n key={row.uid}\n row={row}\n editor={editor}\n columns={columns}\n error={errors[`dimension:${row.name}`]}\n warning={warnings[`dimension:${row.name}`]}\n onPatch={(changes) => patchDimension(row.uid, changes)}\n />\n </PropertyBlock>\n <PropertyBlock title=\"Dicionário\">\n <DictionaryFields row={row} onPatch={(changes) => patchDimension(row.uid, changes)} />\n </PropertyBlock>\n <FieldActions\n name={row.name}\n uses={inUse(row.name)}\n onTry={() => onTry({ dimensions: [row.name], measures: [] })}\n onRemove={() => {\n setEditor((current) => ({\n ...current,\n dimensions: current.dimensions.filter((item) => item.uid !== row.uid)\n }))\n onSelect(null)\n }}\n />\n </>\n )\n }\n\n if (selection?.kind === 'measure') {\n const row = editor.measures.find((item) => item.uid === selection.uid)\n if (!row) return null\n return (\n <>\n <PropertyBlock title=\"Medida\">\n <NameField\n label=\"nome\"\n value={row.name}\n onChange={(name) => patchMeasure(row.uid, { name })}\n />\n <MeasureTypeSelect\n value={row.type}\n onChange={(type) => patchMeasure(row.uid, { type })}\n />\n <MeasureDefinition\n row={row}\n measureNames={measureNames}\n error={errors[`measure:${row.name}`]}\n onPatch={(changes) => patchMeasure(row.uid, changes)}\n />\n <FormatFields row={row} onPatch={(changes) => patchMeasure(row.uid, changes)} />\n </PropertyBlock>\n <PropertyBlock title=\"Dicionário\">\n <DictionaryFields row={row} onPatch={(changes) => patchMeasure(row.uid, changes)} />\n </PropertyBlock>\n <FieldActions\n name={row.name}\n uses={inUse(row.name)}\n onTry={() => onTry({ dimensions: [], measures: [row.name] })}\n onRemove={() => {\n setEditor((current) => ({\n ...current,\n measures: current.measures.filter((item) => item.uid !== row.uid)\n }))\n onSelect(null)\n }}\n />\n </>\n )\n }\n\n // Nada selecionado: resumo e a lista de relacionamentos (\"Gerenciar relações\")\n const formulas = editor.measures.filter((row) => !isAggregate(row))\n return (\n <>\n <PropertyBlock title=\"Modelo\">\n <Typography sx={{ fontSize: 12, color: 'text.secondary' }}>\n {`${editor.tables.length} tabela(s), ${editor.relationships.length} relacionamento(s), ${editor.dimensions.length} dimensão(ões), ${editor.measures.length} medida(s). Clique num card, linha ou campo para editar.`}\n </Typography>\n </PropertyBlock>\n <PropertyBlock title=\"Relacionamentos\">\n {!editor.relationships.length && (\n <Typography sx={{ fontSize: 12, color: 'text.disabled' }}>\n Nenhum. Arraste a coluna da fato até a chave da dimensão.\n </Typography>\n )}\n {editor.relationships.map((row, index) => (\n <Box\n key={row.uid}\n component=\"button\"\n type=\"button\"\n onClick={() => onSelect({ kind: 'relationship', uid: row.uid })}\n sx={{\n textAlign: 'left',\n border: 1,\n borderColor: errors[`relationship:${index}`] ? 'error.main' : 'divider',\n borderRadius: 1,\n bgcolor: 'transparent',\n color: 'text.primary',\n fontFamily: MONO,\n fontSize: 11,\n p: 0.75,\n cursor: 'pointer',\n '&:hover': { bgcolor: 'rgba(255,255,255,.05)' }\n }}\n >\n {tableName(row.fromTable)}.{row.fromColumn} * → 1 {tableName(row.toTable)}.\n {row.toColumn}\n </Box>\n ))}\n </PropertyBlock>\n {!!unplaced.length && (\n <PropertyBlock title=\"Fora dos cards\">\n <Typography sx={{ fontSize: 11, color: 'text.disabled' }}>\n O SQL não cita uma tabela do modelo (<code>tabela.coluna</code>).\n </Typography>\n {unplaced.map((item) => (\n <Button\n key={item.uid}\n size=\"small\"\n onClick={() => onSelect({ kind: item.kind, uid: item.uid })}\n sx={{ justifyContent: 'flex-start', fontFamily: MONO }}\n >\n {item.icon} {item.name || 'sem nome'}\n </Button>\n ))}\n </PropertyBlock>\n )}\n <PropertyBlock title=\"Medidas calculadas\">\n {formulas.map((row) => (\n <Button\n key={row.uid}\n size=\"small\"\n onClick={() => onSelect({ kind: 'measure', uid: row.uid })}\n sx={{ justifyContent: 'flex-start', fontFamily: MONO }}\n >\n {row.type === 'ratio' ? '÷' : 'ƒ'} {row.name}\n </Button>\n ))}\n <Button\n size=\"small\"\n onClick={() => {\n const uid = newUid()\n const taken = [...editor.dimensions, ...editor.measures].map((item) => item.name)\n setEditor((current) => ({\n ...current,\n measures: [\n ...current.measures,\n emptyMeasure({ uid, type: 'formula', name: freeName('novaMedida', taken) })\n ]\n }))\n onSelect({ kind: 'measure', uid })\n }}\n >\n + Medida calculada\n </Button>\n </PropertyBlock>\n <Divider sx={{ my: 1 }} />\n <Typography sx={{ fontSize: 11, color: 'text.disabled' }}>\n Razões e fórmulas não pertencem a uma tabela: aparecem em \"Medidas calculadas\".\n </Typography>\n </>\n )\n}\n\n/** Nome da tabela: renomeia (e corrige as referências `tabela.coluna`) ao sair do campo. */\nfunction RenameField({ value, onCommit }: { value: string; onCommit: (name: string) => void }) {\n const [text, setText] = useState(value)\n useEffect(() => setText(value), [value])\n return (\n <NameField\n label=\"nome (renomeia as referências ao sair do campo)\"\n value={text}\n onChange={setText}\n onBlur={() => {\n if (/^[A-Za-z_][A-Za-z0-9_]*$/.test(text)) onCommit(text)\n else setText(value)\n }}\n />\n )\n}\n\nfunction FieldActions({\n name,\n uses,\n onTry,\n onRemove\n}: {\n name: string\n uses: number\n onTry: () => void\n onRemove: () => void\n}) {\n return (\n <Box sx={{ display: 'flex', gap: 1, alignItems: 'center' }}>\n <Button size=\"small\" onClick={onTry} disabled={!name}>\n ▶ Testar no playground\n </Button>\n <Tooltip title={uses ? 'Em uso na página: as consultas que usam vão falhar' : ''}>\n <span>\n <Button size=\"small\" color=\"error\" onClick={onRemove}>\n Remover\n </Button>\n </span>\n </Tooltip>\n {!!uses && (\n <Typography sx={{ fontSize: 11, color: 'text.secondary' }}>\n {uses} consulta(s) usando\n </Typography>\n )}\n </Box>\n )\n}\n","import {\n Alert,\n Box,\n Button,\n Chip,\n Dialog,\n DialogActions,\n DialogContent,\n DialogTitle,\n Tooltip,\n Typography\n} from '@mui/material'\nimport { useEffect, useMemo, useState, useSyncExternalStore } from 'react'\nimport type { DashboardDevtoolsContext } from '../client/DashboardProvider'\nimport { useDashboard } from '../client/DashboardProvider'\nimport { canonicalJson, toModelCode } from '../codegen'\nimport type { ModelDef } from '../model'\nimport type {\n DevtoolsCapabilities,\n ModelColumns,\n ModelValidation,\n SaveModelResult,\n SchemaTable\n} from '../types'\nimport { lineDiff } from './lineDiff'\nimport { ModelDiagram } from './ModelDiagram'\nimport { type EditorModel, fromEditor, toEditor, validateEditor, withoutDiagram } from './modelCode'\nimport { SqlCompletionsContext } from './SqlEditor'\nimport { errorMessage } from './store'\nimport { CodeBlock, copyText, FileDiff, MONO } from './ui'\n\ntype Props = {\n devtools: DashboardDevtoolsContext\n /** Modelo registrado no servidor. */\n original: ModelDef\n capabilities: DevtoolsCapabilities | null\n /** Tabelas do banco, para o autocomplete (vazio enquanto carrega). */\n tables: SchemaTable[]\n /** Abre o playground com essa combinação. */\n onTry: (selection: { dimensions: string[]; measures: string[] }) => void\n /** O arquivo do modelo foi reescrito: recarregar o modelo registrado. */\n onSaved: () => void\n}\n\nconst same = (a: unknown, b: unknown) => canonicalJson(a) === canonicalJson(b)\n\n/**\n * Editor do modelo: o diagrama (cards e relacionamentos, como a exibição de modelo do Power BI) e o\n * painel de propriedades ao lado. As edições ficam locais até \"Aplicar\": aí o SQL de cada pedaço é\n * validado no banco e o rascunho vai junto de todas as consultas da página (o servidor usa ele no\n * lugar do modelo registrado). \"Salvar no arquivo\" reescreve `src/dashboard/models/<nome>.ts`.\n */\nexport function ModelPanel({ devtools, original, capabilities, tables, onTry, onSaved }: Props) {\n const { store, draft, setDraft } = devtools\n const { fetcher, model: modelName } = useDashboard()\n const [editor, setEditor] = useState<EditorModel>(() => toEditor(draft ?? original))\n const [showCode, setShowCode] = useState(false)\n const [checked, setChecked] = useState<{ structure: string; result: ModelValidation } | null>(\n null\n )\n const [columns, setColumns] = useState<ModelColumns | null>(null)\n const [columnErrors, setColumnErrors] = useState<Record<string, string>>({})\n const [busy, setBusy] = useState<string | null>(null)\n const [actionError, setActionError] = useState<string | null>(null)\n const [save, setSave] = useState<SaveModelResult | null>(null)\n\n // Rascunho descartado/aplicado ou modelo recarregado: o editor acompanha\n useEffect(() => setEditor(toEditor(draft ?? original)), [draft, original])\n const errors = useMemo(() => validateEditor(editor), [editor])\n const edited = useMemo(() => fromEditor(editor), [editor])\n // Erro de validação é do SQL validado; editou, deixa de valer (mover card no diagrama não conta)\n const structure = useMemo(() => canonicalJson(withoutDiagram(edited)), [edited])\n const validation = checked?.structure === structure ? checked.result : null\n const reference = draft ?? original\n const dirty = !same(edited, reference)\n const differsFromOriginal = !same(edited, original)\n\n // Quantas consultas ativas usam cada nome (dimensão, filtro ou medida)\n const snapshot = useSyncExternalStore(store.subscribe, store.getSnapshot, store.getSnapshot)\n const usage = useMemo(() => {\n const count = new Map<string, number>()\n for (const { last } of snapshot.instances) {\n const { dimensions = [], measures = [], filters = {} } = last.query\n for (const name of new Set([...dimensions, ...measures, ...Object.keys(filters)]))\n count.set(name, (count.get(name) ?? 0) + 1)\n }\n return count\n }, [snapshot])\n\n const removed = [\n ...Object.keys(original.dimensions).filter((name) => !edited.dimensions[name]),\n ...Object.keys(original.measures).filter((name) => !edited.measures[name]),\n ...Object.keys(original.tables).filter((name) => !edited.tables[name])\n ]\n\n // --- ações que vão ao servidor ---\n\n const validateSql = async () => {\n const result = await fetcher({ model: modelName, devtools: { validate: true, model: edited } })\n const next = result.devtools?.validation ?? null\n setChecked(next && { structure, result: next })\n if (next) setColumns(next.columns)\n return next\n }\n\n // Só as colunas (uma linha de cada tabela): o diagrama precisa delas para listar e relacionar\n const loadColumns = async () => {\n if (validateEditor(editor).length) {\n setActionError('Corrija os erros do modelo antes de ler as colunas.')\n return\n }\n await act('columns', async () => {\n const result = await fetcher({ model: modelName, devtools: { columns: true, model: edited } })\n setColumns(result.devtools?.columns ?? null)\n setColumnErrors(result.devtools?.columnErrors ?? {})\n })\n }\n\n const act = async (name: string, action: () => Promise<void>) => {\n setBusy(name)\n setActionError(null)\n try {\n await action()\n } catch (error) {\n setActionError(errorMessage(error))\n } finally {\n setBusy(null)\n }\n }\n\n const apply = () =>\n act('apply', async () => {\n // Só moveu cards: não há SQL novo para validar\n const onlyLayout = canonicalJson(withoutDiagram(reference)) === structure\n const result = onlyLayout ? null : await validateSql()\n if (result && Object.keys(result.errors).length) return\n setDraft(differsFromOriginal ? edited : null)\n })\n\n const previewSave = () =>\n act('save', async () => {\n const result = await fetcher({\n model: modelName,\n devtools: { save: 'preview', model: edited }\n })\n setSave(result.devtools?.save ?? null)\n })\n\n const writeSave = () =>\n act('save', async () => {\n await fetcher({ model: modelName, devtools: { save: 'write', model: edited } })\n setSave(null)\n setDraft(null)\n onSaved()\n })\n\n const completions = useMemo(\n () => ({\n tables,\n // `tabela.` completa as colunas da tabela do modelo\n modelColumns: Object.fromEntries(\n editor.tables.map((row) => [row.name, columns?.tables[row.name] ?? []])\n )\n }),\n [tables, columns, editor.tables]\n )\n\n const validationErrors = validation ? Object.entries(validation.errors) : []\n\n return (\n <SqlCompletionsContext.Provider value={completions}>\n <Box sx={{ display: 'flex', flexDirection: 'column', height: '100%', minHeight: 0 }}>\n <Box sx={{ px: 1.5, '& .MuiAlert-root': { my: 0.5, py: 0 } }}>\n {draft && (\n <Alert severity=\"warning\">\n Rascunho aplicado: as consultas desta página estão usando o modelo editado, não o\n registrado em <code>src/dashboard/models</code>.\n {capabilities?.saveModel\n ? ' Use \"Salvar no arquivo\" quando terminar.'\n : ' Copie o código para o arquivo quando terminar.'}\n </Alert>\n )}\n {actionError && (\n <Alert severity=\"error\" sx={{ fontFamily: MONO, fontSize: 12 }}>\n {actionError}\n </Alert>\n )}\n {!!validationErrors.length && (\n <Alert severity=\"error\">\n O banco recusou {validationErrors.length} pedaço(s) do modelo — veja os campos\n marcados. O rascunho não foi aplicado.\n {validation?.errors.model && <div>{validation.errors.model}</div>}\n </Alert>\n )}\n </Box>\n\n <Box sx={{ flex: 1, minHeight: 0, borderTop: 1, borderColor: 'divider' }}>\n <ModelDiagram\n editor={editor}\n setEditor={setEditor}\n columns={columns}\n errors={{ ...columnErrors, ...validation?.errors }}\n warnings={validation?.warnings ?? {}}\n loadingColumns={busy === 'columns'}\n onLoadColumns={loadColumns}\n onTry={onTry}\n usage={usage}\n />\n </Box>\n\n <Box\n sx={{\n borderTop: 1,\n borderColor: 'divider',\n p: 1,\n display: 'flex',\n alignItems: 'center',\n gap: 1,\n flexWrap: 'wrap'\n }}\n >\n {errors.length ? (\n <Tooltip title={<Box sx={{ whiteSpace: 'pre-line' }}>{errors.join('\\n')}</Box>}>\n <Chip color=\"error\" size=\"small\" label={`${errors.length} erro(s): ${errors[0]}`} />\n </Tooltip>\n ) : validation && !validationErrors.length ? (\n <Chip color=\"success\" size=\"small\" label=\"SQL validado no banco\" />\n ) : (\n <Chip color=\"success\" size=\"small\" variant=\"outlined\" label=\"modelo válido\" />\n )}\n {!!removed.length && (\n <Chip size=\"small\" color=\"warning\" label={`removidos: ${removed.join(', ')}`} />\n )}\n <Box sx={{ ml: 'auto', display: 'flex', gap: 1, flexWrap: 'wrap' }}>\n <Button size=\"small\" onClick={() => setShowCode(true)}>\n Ver código\n </Button>\n <Button size=\"small\" onClick={(e) => copyText(toModelCode(edited), e.currentTarget)}>\n Copiar TS\n </Button>\n <Button\n size=\"small\"\n disabled={!!errors.length || !!busy}\n onClick={() =>\n act('validate', async () => {\n await validateSql()\n })\n }\n title=\"Executa cada pedaço do modelo no banco com poucas chaves\"\n >\n {busy === 'validate' ? 'Validando…' : 'Validar SQL'}\n </Button>\n <Button\n size=\"small\"\n disabled={!dirty}\n onClick={() => setEditor(toEditor(reference))}\n title=\"Desfaz as edições ainda não aplicadas\"\n >\n Desfazer\n </Button>\n <Button\n size=\"small\"\n color=\"warning\"\n disabled={!draft}\n onClick={() => setDraft(null)}\n title=\"Volta a usar o modelo registrado no servidor\"\n >\n Descartar rascunho\n </Button>\n {capabilities?.saveModel && (\n <Button\n size=\"small\"\n variant=\"outlined\"\n disabled={!differsFromOriginal || !!errors.length || !!busy}\n onClick={previewSave}\n title={`Reescreve src/dashboard/models/${original.name}.ts`}\n >\n {busy === 'save' ? 'Gerando…' : 'Salvar no arquivo'}\n </Button>\n )}\n <Button\n size=\"small\"\n variant=\"contained\"\n disabled={!dirty || !!errors.length || !!busy}\n onClick={apply}\n >\n {busy === 'apply' ? 'Validando…' : 'Aplicar na página'}\n </Button>\n </Box>\n </Box>\n </Box>\n\n <Dialog open={showCode} onClose={() => setShowCode(false)} maxWidth=\"lg\" fullWidth>\n <DialogTitle>Código do modelo</DialogTitle>\n <DialogContent>\n <CodeBlock code={toModelCode(edited)} maxHeight={600} />\n </DialogContent>\n <DialogActions>\n <Button onClick={() => setShowCode(false)}>Fechar</Button>\n </DialogActions>\n </Dialog>\n\n <Dialog open={!!save} onClose={() => setSave(null)} maxWidth=\"lg\" fullWidth>\n <DialogTitle>Salvar no arquivo</DialogTitle>\n <DialogContent>\n <Typography sx={{ fontFamily: MONO, fontSize: 12, mb: 1 }}>{save?.path}</Typography>\n {save?.warnings.map((warning) => (\n <Alert key={warning} severity=\"warning\" sx={{ mb: 1 }}>\n {warning}\n </Alert>\n ))}\n {save && <FileDiff lines={lineDiff(save.previous, save.content)} />}\n <Typography sx={{ fontSize: 12, color: 'text.secondary', mt: 1 }}>\n O Next recarrega o modelo sozinho; o rascunho é descartado. O lint-staged formata o\n arquivo no commit.\n </Typography>\n </DialogContent>\n <DialogActions>\n <Button onClick={() => setSave(null)}>Cancelar</Button>\n <Button\n variant=\"contained\"\n disabled={!save || save.previous === save.content || !!busy}\n onClick={writeSave}\n >\n Gravar\n </Button>\n </DialogActions>\n </Dialog>\n </SqlCompletionsContext.Provider>\n )\n}\n","import {\n Alert,\n Autocomplete,\n Box,\n Button,\n Checkbox,\n Chip,\n FormControlLabel,\n TextField\n} from '@mui/material'\nimport { useEffect, useState } from 'react'\nimport { useDashboard } from '../client/DashboardProvider'\nimport type { ModelDef } from '../model'\nimport type { DashboardQueryDebug, DashboardRow } from '../types'\nimport { errorMessage } from './store'\nimport { CodeBlock, Empty, inlineParams, MONO, ResultTable, Section } from './ui'\n\nexport type PlaygroundSelection = { dimensions: string[]; measures: string[] }\n\ntype Props = {\n /** Modelo em vigor na página (rascunho aplicado ou o registrado). */\n model: ModelDef\n selection: PlaygroundSelection\n onSelectionChange: (selection: PlaygroundSelection) => void\n}\n\ntype Outcome = { rows: DashboardRow[]; debug?: DashboardQueryDebug; ms: number } | { error: string }\n\n/** Consulta avulsa ao modelo: qualquer combinação de dimensões e medidas, com ou sem os filtros. */\nexport function PlaygroundPanel({ model, selection, onSelectionChange }: Props) {\n const { model: modelName, filters, fetcher } = useDashboard()\n const [useFilters, setUseFilters] = useState(true)\n const [running, setRunning] = useState(false)\n const [outcome, setOutcome] = useState<Outcome | null>(null)\n\n const run = async () => {\n setRunning(true)\n const startedAt = Date.now()\n try {\n const result = await fetcher({\n model: modelName,\n dimensions: selection.dimensions,\n measures: selection.measures,\n filters: useFilters ? filters : {}\n })\n setOutcome({ rows: result.rows, debug: result.devtools?.debug, ms: Date.now() - startedAt })\n } catch (error) {\n setOutcome({ error: errorMessage(error) })\n } finally {\n setRunning(false)\n }\n }\n\n // \"Testar\" no editor chega aqui com a seleção pronta: já executa\n const key = JSON.stringify(selection)\n useEffect(() => {\n if (selection.dimensions.length || selection.measures.length) run()\n }, [key])\n\n const empty = !selection.dimensions.length && !selection.measures.length\n\n return (\n <Box sx={{ p: 1.5, overflow: 'auto', height: '100%' }}>\n <Box sx={{ display: 'flex', gap: 1, alignItems: 'flex-start', flexWrap: 'wrap', mb: 2 }}>\n <Autocomplete\n multiple\n size=\"small\"\n options={Object.keys(model.dimensions)}\n value={selection.dimensions}\n onChange={(_, dimensions) => onSelectionChange({ ...selection, dimensions })}\n renderInput={(params) => <TextField {...params} label=\"Dimensões\" />}\n sx={{ minWidth: 280, flex: 1 }}\n />\n <Autocomplete\n multiple\n size=\"small\"\n options={Object.keys(model.measures)}\n value={selection.measures}\n onChange={(_, measures) => onSelectionChange({ ...selection, measures })}\n renderInput={(params) => <TextField {...params} label=\"Medidas\" />}\n sx={{ minWidth: 280, flex: 1 }}\n />\n <FormControlLabel\n control={\n <Checkbox checked={useFilters} onChange={(e) => setUseFilters(e.target.checked)} />\n }\n label=\"Usar filtros da página\"\n />\n <Button variant=\"contained\" disabled={empty || running} onClick={run}>\n {running ? 'Executando…' : 'Executar'}\n </Button>\n </Box>\n\n {!outcome ? (\n <Empty>Escolha dimensões e/ou medidas e execute.</Empty>\n ) : 'error' in outcome ? (\n <Alert severity=\"error\" sx={{ fontFamily: MONO, fontSize: 12 }}>\n {outcome.error}\n </Alert>\n ) : (\n <>\n <Box sx={{ display: 'flex', gap: 1, mb: 1.5 }}>\n <Chip size=\"small\" label={`${outcome.rows.length} linhas`} />\n <Chip size=\"small\" label={`total ${outcome.ms} ms`} />\n {outcome.debug && (\n <Chip\n size=\"small\"\n label={outcome.debug.cached ? 'cache' : `banco ${outcome.debug.durationMs} ms`}\n />\n )}\n {outcome.debug?.draft && <Chip size=\"small\" color=\"warning\" label=\"rascunho\" />}\n </Box>\n <Section title=\"Resultado\">\n <ResultTable rows={outcome.rows} maxHeight={420} />\n </Section>\n {outcome.debug && (\n <Section title=\"SQL gerado\">\n <CodeBlock sql code={inlineParams(outcome.debug.sql, outcome.debug.params)} />\n </Section>\n )}\n </>\n )}\n </Box>\n )\n}\n","import {\n Alert,\n Box,\n Button,\n Checkbox,\n Chip,\n FormControlLabel,\n List,\n ListItemButton,\n MenuItem,\n TextField,\n ToggleButton,\n ToggleButtonGroup,\n Tooltip,\n Typography\n} from '@mui/material'\nimport { type ReactNode, useEffect, useState, useSyncExternalStore } from 'react'\nimport type { DashboardDevtoolsContext } from '../client/DashboardProvider'\nimport { useDashboard } from '../client/DashboardProvider'\nimport { diffRows, type RowDiff } from '../compare'\nimport type { DashboardQueryDebug, DashboardRow, DevtoolsCapabilities, ProfileStep } from '../types'\nimport { scrollToQuery } from './Inspector'\nimport { errorMessage, type QueryRun, type RunStatus } from './store'\nimport {\n CodeBlock,\n Empty,\n inlineParams,\n MONO,\n ResultTable,\n RowDiffTable,\n Section,\n STATUS_LABEL,\n StatusDot\n} from './ui'\n\nexport type QuerySelection = { instanceId: string; runId?: number }\n\ntype Props = {\n devtools: DashboardDevtoolsContext\n capabilities: DevtoolsCapabilities | null\n selected: QuerySelection | null\n onSelect: (selection: QuerySelection) => void\n /** Destaca o componente da consulta na página. */\n onHover: (instanceId: string | null) => void\n onClearServerCache: () => void\n}\n\nconst queryKey = (run: QueryRun) => JSON.stringify(run.query)\n\ntype SortKey = 'default' | 'label' | 'duration' | 'rows' | 'status'\n\nconst SORT_LABEL: Record<SortKey, string> = {\n default: 'ordem da página',\n label: 'nome',\n duration: 'mais lentas',\n rows: 'mais linhas',\n status: 'erros primeiro'\n}\n\nconst SORT_KEY = 'bm-dashboard-devtools:queries-sort'\n\n/** Problemas primeiro: erro, em andamento, cancelada, ok. */\nconst STATUS_ORDER: Record<RunStatus, number> = { error: 0, loading: 1, cancelled: 2, success: 3 }\n\nfunction loadSort(): SortKey {\n try {\n const saved = localStorage.getItem(SORT_KEY) as SortKey | null\n return saved && saved in SORT_LABEL ? saved : 'default'\n } catch {\n return 'default'\n }\n}\n\n/** Ordena a lista; empate mantém a ordem original (página ou mais recente primeiro). */\nfunction sortRuns(runs: QueryRun[], key: SortKey) {\n if (key === 'default') return runs\n const compare = (a: QueryRun, b: QueryRun) => {\n switch (key) {\n case 'label':\n return a.label.localeCompare(b.label, 'pt-BR', { numeric: true })\n case 'duration':\n // Em andamento conta o tempo até agora: consulta travada aparece no topo\n return (\n (b.durationMs ?? Date.now() - b.startedAt) - (a.durationMs ?? Date.now() - a.startedAt)\n )\n case 'rows':\n return (b.rows?.length ?? -1) - (a.rows?.length ?? -1)\n case 'status':\n return STATUS_ORDER[a.status] - STATUS_ORDER[b.status]\n }\n }\n return [...runs].sort(compare)\n}\n\n/** Consultas ativas na página (uma por componente) e o histórico de execuções. */\nexport function QueriesPanel({\n devtools,\n capabilities,\n selected,\n onSelect,\n onHover,\n onClearServerCache\n}: Props) {\n const { store, refresh } = devtools\n const snapshot = useSyncExternalStore(store.subscribe, store.getSnapshot, store.getSnapshot)\n const [view, setView] = useState<'active' | 'history'>('active')\n const [sort, setSort] = useState(loadSort)\n const changeSort = (next: SortKey) => {\n setSort(next)\n try {\n localStorage.setItem(SORT_KEY, next)\n } catch {}\n }\n\n const runs: QueryRun[] = sortRuns(\n view === 'active' ? snapshot.instances.map((instance) => instance.last) : snapshot.history,\n sort\n )\n const instanceById = new Map(snapshot.instances.map((item) => [item.instanceId, item]))\n\n // Mesma consulta pedida por mais de um componente: o cache do endpoint segura, mas vale saber\n const sameQuery = new Map<string, number>()\n for (const { last } of snapshot.instances)\n sameQuery.set(queryKey(last), (sameQuery.get(queryKey(last)) ?? 0) + 1)\n\n const storms = snapshot.instances.filter((item) => item.storm)\n\n // Na aba \"ativas\" a seleção acompanha a instância (cada nova execução substitui a anterior)\n const current =\n (view === 'history' && selected?.runId\n ? snapshot.history.find((run) => run.runId === selected.runId)\n : selected && instanceById.get(selected.instanceId)?.last) ?? runs[0]\n\n return (\n <Box sx={{ display: 'grid', gridTemplateColumns: '360px 1fr', height: '100%', minHeight: 0 }}>\n <Box\n sx={{\n borderRight: 1,\n borderColor: 'divider',\n display: 'flex',\n flexDirection: 'column',\n minHeight: 0\n }}\n >\n <Box\n sx={{\n display: 'flex',\n alignItems: 'center',\n gap: 1,\n p: 1,\n borderBottom: 1,\n borderColor: 'divider'\n }}\n >\n <ToggleButtonGroup\n size=\"small\"\n exclusive\n value={view}\n onChange={(_, value) => value && setView(value)}\n >\n <ToggleButton value=\"active\">Ativas ({snapshot.instances.length})</ToggleButton>\n <ToggleButton value=\"history\">Histórico ({snapshot.history.length})</ToggleButton>\n </ToggleButtonGroup>\n {view === 'history' && (\n <Button size=\"small\" onClick={store.clearHistory}>\n Limpar\n </Button>\n )}\n <TextField\n select\n size=\"small\"\n value={sort}\n onChange={(e) => changeSort(e.target.value as SortKey)}\n title=\"Ordenar a lista\"\n sx={{ ml: 'auto', minWidth: 0, '& .MuiSelect-select': { fontSize: 12, py: 0.5 } }}\n >\n {(Object.keys(SORT_LABEL) as SortKey[]).map((key) => (\n <MenuItem key={key} value={key} dense>\n {key === 'default' && view === 'history' ? 'mais recentes' : SORT_LABEL[key]}\n </MenuItem>\n ))}\n </TextField>\n </Box>\n <Box sx={{ display: 'flex', gap: 0.5, p: 1, borderBottom: 1, borderColor: 'divider' }}>\n <Button size=\"small\" variant=\"outlined\" onClick={refresh}>\n Re-executar tudo\n </Button>\n <Button\n size=\"small\"\n onClick={onClearServerCache}\n title=\"Esvazia o cache em memória do endpoint e refaz as consultas\"\n >\n Limpar cache\n </Button>\n </Box>\n {!!storms.length && (\n <Alert\n severity=\"warning\"\n sx={{ m: 1, py: 0 }}\n action={\n <Button size=\"small\" color=\"inherit\" onClick={store.resetStorms}>\n OK\n </Button>\n }\n >\n Consulta em loop: {storms.map((item) => item.label).join(', ')}. Algum componente está\n recriando dimensions/measures/filtros a cada render.\n </Alert>\n )}\n <List\n dense\n disablePadding\n sx={{ overflow: 'auto', flex: 1 }}\n onMouseLeave={() => onHover(null)}\n >\n {runs.map((run) => {\n const instance = instanceById.get(run.instanceId)\n const duplicated = view === 'active' && (sameQuery.get(queryKey(run)) ?? 0) > 1\n return (\n <ListItemButton\n key={run.runId}\n selected={current?.runId === run.runId}\n onClick={() => onSelect({ instanceId: run.instanceId, runId: run.runId })}\n onMouseEnter={() => onHover(instance ? run.instanceId : null)}\n sx={{ gap: 1, alignItems: 'center' }}\n >\n <StatusDot status={run.status} />\n <Box sx={{ minWidth: 0, flex: 1 }}>\n <Typography noWrap sx={{ fontSize: 12, fontFamily: MONO }}>\n {run.label}\n </Typography>\n <Typography noWrap sx={{ fontSize: 11, color: 'text.secondary' }}>\n {run.status === 'loading' ? 'carregando…' : `${run.durationMs} ms`}\n {run.rows && ` · ${run.rows.length} linhas`}\n {run.debug?.cached && ' · cache'}\n {view === 'active' && ` · ${instance?.runs ?? 1}×`}\n </Typography>\n </Box>\n {instance?.storm && view === 'active' && (\n <Chip label=\"loop\" size=\"small\" color=\"error\" />\n )}\n {duplicated && (\n <Tooltip title=\"Outro componente faz exatamente a mesma consulta\">\n <Chip label=\"duplicada\" size=\"small\" variant=\"outlined\" />\n </Tooltip>\n )}\n {run.debug?.draft && <Chip label=\"rascunho\" size=\"small\" color=\"warning\" />}\n </ListItemButton>\n )\n })}\n {!runs.length && <Empty>Nenhuma consulta.</Empty>}\n </List>\n </Box>\n\n <Box sx={{ overflow: 'auto', p: 1.5, minWidth: 0 }}>\n {current ? (\n <RunDetail\n key={current.runId}\n run={current}\n devtools={devtools}\n capabilities={capabilities}\n mounted={instanceById.has(current.instanceId)}\n />\n ) : (\n <Empty>Selecione uma consulta.</Empty>\n )}\n </Box>\n </Box>\n )\n}\n\nfunction RunDetail({\n run,\n devtools,\n capabilities,\n mounted\n}: {\n run: QueryRun\n devtools: DashboardDevtoolsContext\n capabilities: DevtoolsCapabilities | null\n mounted: boolean\n}) {\n const { debug } = run\n const { devtools: _, ...query } = run.query\n return (\n <>\n <Box sx={{ display: 'flex', alignItems: 'center', gap: 1, mb: 1.5, flexWrap: 'wrap' }}>\n <StatusDot status={run.status} />\n <Typography sx={{ fontFamily: MONO, fontWeight: 700 }}>{run.label}</Typography>\n <Chip size=\"small\" label={STATUS_LABEL[run.status]} />\n {run.durationMs !== undefined && (\n <Chip size=\"small\" label={`total ${run.durationMs} ms`} title=\"Ida e volta no browser\" />\n )}\n {debug && (\n <Chip\n size=\"small\"\n color={debug.cached ? 'info' : 'default'}\n label={\n debug.cached\n ? `cache (banco: ${debug.durationMs} ms)`\n : `banco ${debug.durationMs} ms`\n }\n />\n )}\n {debug?.draft && <Chip size=\"small\" color=\"warning\" label=\"rodou no rascunho\" />}\n {mounted && (\n <Button size=\"small\" onClick={() => scrollToQuery(run.instanceId)}>\n Localizar na página\n </Button>\n )}\n <Typography sx={{ ml: 'auto', fontSize: 11, color: 'text.secondary' }}>\n {new Date(run.startedAt).toLocaleTimeString('pt-BR')}\n </Typography>\n </Box>\n\n {run.error && (\n <Alert severity=\"error\" sx={{ mb: 2, fontFamily: MONO, fontSize: 12 }}>\n {run.error}\n </Alert>\n )}\n {run.status === 'error' && !debug && <FailedSql run={run} />}\n\n <Section title=\"Consulta\">\n <CodeBlock code={JSON.stringify(query, null, 2)} maxHeight={180} />\n </Section>\n\n {debug && (\n <Section title=\"SQL gerado\">\n <CodeBlock sql code={inlineParams(debug.sql, debug.params)} />\n {!!debug.params.length && (\n <Typography sx={{ fontSize: 11, color: 'text.secondary', mt: 0.5, fontFamily: MONO }}>\n params: {JSON.stringify(debug.params)}\n </Typography>\n )}\n </Section>\n )}\n {!debug && run.status === 'success' && (\n <Alert severity=\"info\" sx={{ mb: 2 }}>\n O servidor não devolveu debug. Confira se o endpoint chama{' '}\n <code>runQuery(..., {'{ devtools: true }'})</code> em desenvolvimento.\n </Alert>\n )}\n\n {debug && <RunTools run={run} devtools={devtools} capabilities={capabilities} />}\n\n {run.rows && (\n <Section title={`Resultado (${run.rows.length} linhas)`}>\n <ResultTable rows={run.rows} />\n </Section>\n )}\n </>\n )\n}\n\n/**\n * SQL de uma consulta que deu erro: o servidor não devolve debug junto com o erro, então pede só a\n * compilação (`devtools.compile`), sem executar. Se nem compilar, mostra por quê.\n */\nfunction FailedSql({ run }: { run: QueryRun }) {\n const { fetcher } = useDashboard()\n const [state, setState] = useState<ToolState<DashboardQueryDebug> | null>(null)\n useEffect(() => {\n let active = true\n setState({ loading: true })\n fetcher({ ...run.query, devtools: { compile: true } })\n .then((result) => {\n const debug = result.devtools?.debug\n if (active)\n setState(\n debug\n ? { loading: false, data: debug }\n : {\n loading: false,\n error:\n 'O endpoint não devolveu o SQL (precisa de runQuery(..., { devtools: true }) numa versão que aceite devtools.compile).'\n }\n )\n })\n .catch((error) => active && setState({ loading: false, error: errorMessage(error) }))\n return () => {\n active = false\n }\n }, [fetcher, run.query])\n\n return (\n <Section title=\"SQL gerado (não executou)\">\n <ToolResult state={state}>\n {(debug) => (\n <>\n <CodeBlock sql code={inlineParams(debug.sql, debug.params)} />\n <Typography sx={{ fontSize: 11, color: 'text.secondary', mt: 0.5 }}>\n Compilado de novo agora{debug.draft ? ', com o rascunho atual' : ''}, para depurar o\n erro acima.\n {!!debug.params.length && (\n <Box component=\"span\" sx={{ fontFamily: MONO }}>\n {' '}\n params: {JSON.stringify(debug.params)}\n </Box>\n )}\n </Typography>\n </>\n )}\n </ToolResult>\n </Section>\n )\n}\n\ntype ToolState<T> = { loading: boolean; error?: string; data?: T }\n\nfunction useTool<T>() {\n const [state, setState] = useState<ToolState<T> | null>(null)\n const run = async (load: () => Promise<T>) => {\n setState({ loading: true })\n try {\n setState({ loading: false, data: await load() })\n } catch (error) {\n setState({ loading: false, error: errorMessage(error) })\n }\n }\n return [state, run] as const\n}\n\nfunction ToolResult<T>({\n state,\n children\n}: {\n state: ToolState<T> | null\n children: (data: T) => ReactNode\n}) {\n if (!state) return null\n if (state.loading) return <Typography sx={{ fontSize: 12 }}>Executando…</Typography>\n if (state.error)\n return (\n <Alert severity=\"error\" sx={{ fontFamily: MONO, fontSize: 12 }}>\n {state.error}\n </Alert>\n )\n return state.data === undefined ? null : children(state.data)\n}\n\n/** EXPLAIN, perfil por join, comparação com o modelo registrado e snapshot da consulta. */\nfunction RunTools({\n run,\n devtools,\n capabilities\n}: {\n run: QueryRun\n devtools: DashboardDevtoolsContext\n capabilities: DevtoolsCapabilities | null\n}) {\n const { fetcher } = useDashboard()\n const query = run.query\n const [explain, runExplain] = useTool<DashboardRow[]>()\n const [profile, runProfile] = useTool<ProfileStep[]>()\n const [compare, runCompare] = useTool<RowDiff[]>()\n const [snapshot, runSnapshot] = useTool<string>()\n const [snapshotName, setSnapshotName] = useState('')\n const [overwrite, setOverwrite] = useState(false)\n\n const explainQuery = () =>\n runExplain(async () => {\n const result = await fetcher({ ...query, devtools: { explain: true } })\n return result.devtools?.explain ?? []\n })\n const profileQuery = () =>\n runProfile(async () => {\n const result = await fetcher({ ...query, devtools: { profile: true } })\n return result.devtools?.profile ?? []\n })\n const compareQuery = () =>\n runCompare(async () => {\n const registered = await devtools.rawFetcher(query)\n return diffRows(registered.rows, run.rows ?? [], query)\n })\n const saveSnapshot = () =>\n runSnapshot(async () => {\n const result = await devtools.rawFetcher({\n ...query,\n devtools: { snapshot: { name: snapshotName, overwrite } }\n })\n return result.devtools?.snapshot?.path ?? ''\n })\n\n const maxProfile = Math.max(1, ...(profile?.data ?? []).map((step) => step.durationMs))\n\n return (\n <Section\n title=\"Ferramentas\"\n actions={\n <>\n <Button size=\"small\" variant=\"outlined\" onClick={explainQuery}>\n EXPLAIN\n </Button>\n <Button\n size=\"small\"\n variant=\"outlined\"\n onClick={profileQuery}\n title=\"Mede a agregação de cada fato isoladamente (sem cache)\"\n >\n Perfil por join\n </Button>\n {devtools.draft && run.rows && (\n <Button size=\"small\" variant=\"outlined\" color=\"warning\" onClick={compareQuery}>\n Comparar com o registrado\n </Button>\n )}\n </>\n }\n >\n <Box sx={{ display: 'flex', flexDirection: 'column', gap: 1.5 }}>\n <ToolResult state={explain}>\n {(rows) => <ResultTable rows={rows} maxHeight={240} />}\n </ToolResult>\n\n <ToolResult state={profile}>\n {(steps) => (\n <Box sx={{ display: 'grid', gridTemplateColumns: '160px 1fr 90px 90px', gap: 0.5 }}>\n {steps.map((step) => (\n <Box key={step.name} sx={{ display: 'contents', fontFamily: MONO, fontSize: 12 }}>\n <Box sx={{ fontFamily: MONO }}>{step.name}</Box>\n <Box sx={{ display: 'flex', alignItems: 'center' }}>\n <Box\n sx={{\n height: 10,\n borderRadius: 1,\n width: `${(step.durationMs / maxProfile) * 100}%`,\n minWidth: 2,\n bgcolor: step.name === 'consulta' ? 'primary.main' : 'info.main'\n }}\n />\n </Box>\n <Box sx={{ textAlign: 'right', fontFamily: MONO }}>{step.durationMs} ms</Box>\n <Box sx={{ textAlign: 'right', fontFamily: MONO, color: 'text.secondary' }}>\n {step.rows ?? ''} {step.name === 'consulta' ? 'linhas' : 'chaves'}\n </Box>\n </Box>\n ))}\n </Box>\n )}\n </ToolResult>\n\n <ToolResult state={compare}>\n {(diffs) => (\n <RowDiffTable diffs={diffs} expectedLabel=\"registrado\" actualLabel=\"rascunho\" />\n )}\n </ToolResult>\n\n {capabilities?.snapshots && (\n <Box sx={{ display: 'flex', alignItems: 'center', gap: 1, flexWrap: 'wrap' }}>\n <TextField\n size=\"small\"\n label=\"Nome do snapshot\"\n placeholder=\"custo-mes-2024\"\n value={snapshotName}\n onChange={(e) => setSnapshotName(e.target.value)}\n sx={{ width: 240, '& input': { fontFamily: MONO, fontSize: 12 } }}\n />\n <FormControlLabel\n control={\n <Checkbox\n size=\"small\"\n checked={overwrite}\n onChange={(e) => setOverwrite(e.target.checked)}\n />\n }\n label=\"Sobrescrever\"\n />\n <Tooltip title=\"Grava o resultado do modelo REGISTRADO (não o rascunho) como referência para os testes de regressão. Prefira períodos fechados: dado que ainda muda quebra o teste.\">\n <span>\n <Button\n size=\"small\"\n variant=\"outlined\"\n disabled={!snapshotName}\n onClick={saveSnapshot}\n >\n Salvar snapshot\n </Button>\n </span>\n </Tooltip>\n <ToolResult state={snapshot}>\n {(path) => (\n <Typography sx={{ fontSize: 12, color: 'success.main', fontFamily: MONO }}>\n Salvo em {path}\n </Typography>\n )}\n </ToolResult>\n </Box>\n )}\n </Box>\n </Section>\n )\n}\n","import { Alert, Box, Button, Chip, Collapse, Typography } from '@mui/material'\nimport { useEffect, useState } from 'react'\nimport type { DashboardDevtoolsContext } from '../client/DashboardProvider'\nimport { useDashboard } from '../client/DashboardProvider'\nimport { diffRows, type RowDiff } from '../compare'\nimport type { DashboardQuery, DashboardSnapshot, DevtoolsCapabilities } from '../types'\nimport { errorMessage } from './store'\nimport { Empty, MONO, RowDiffTable, Section } from './ui'\n\ntype CheckItem = { id: string; label: string; query: DashboardQuery }\n\ntype Check = {\n id: string\n label: string\n query: DashboardQuery\n status: 'loading' | 'done' | 'error'\n diffs?: RowDiff[]\n rows?: number\n error?: string\n}\n\ntype Props = {\n devtools: DashboardDevtoolsContext\n capabilities: DevtoolsCapabilities | null\n}\n\nconst stripQuery = ({ model, dimensions, measures, filters }: DashboardQuery): DashboardQuery => ({\n model,\n dimensions,\n measures,\n filters\n})\n\n/** Executa as conferências uma a uma, atualizando a lista conforme terminam. */\nfunction useChecks() {\n const [checks, setChecks] = useState<Check[]>([])\n const run = async (\n items: CheckItem[],\n compare: (item: CheckItem) => Promise<{ diffs: RowDiff[]; rows: number }>\n ) => {\n setChecks(items.map((item) => ({ ...item, status: 'loading' })))\n for (const item of items) {\n let patch: Partial<Check>\n try {\n patch = { status: 'done', ...(await compare(item)) }\n } catch (error) {\n patch = { status: 'error', error: errorMessage(error) }\n }\n setChecks((current) =>\n current.map((check) => (check.id === item.id ? { ...check, ...patch } : check))\n )\n }\n }\n return [checks, run] as const\n}\n\n/**\n * Proteção dos números: (1) rascunho x modelo registrado em todas as consultas da página e\n * (2) snapshots salvos x modelo em vigor (o mesmo que o teste `tests/dashboard` faz no CI).\n */\nexport function RegressionPanel({ devtools, capabilities }: Props) {\n const { fetcher, model } = useDashboard()\n const [pageChecks, runPageChecks] = useChecks()\n const [snapshotChecks, runSnapshotChecks] = useChecks()\n const [snapshots, setSnapshots] = useState<DashboardSnapshot[] | null>(null)\n const [snapshotsError, setSnapshotsError] = useState<string | null>(null)\n\n const loadSnapshots = () =>\n devtools\n .rawFetcher({ model, devtools: { snapshots: true } })\n .then((result) => {\n setSnapshots(result.devtools?.snapshots ?? [])\n setSnapshotsError(null)\n })\n .catch((error) => setSnapshotsError(errorMessage(error)))\n\n useEffect(() => {\n if (capabilities?.snapshots) loadSnapshots()\n }, [capabilities?.snapshots])\n\n const comparePage = () => {\n // Uma conferência por consulta distinta (componentes com a mesma consulta contam uma vez)\n const unique = new Map<string, CheckItem>()\n for (const { last, label } of devtools.store.getSnapshot().instances) {\n const query = stripQuery(last.query)\n const id = JSON.stringify(query)\n if (!unique.has(id)) unique.set(id, { id, label, query })\n }\n runPageChecks([...unique.values()], async ({ query }) => {\n const [registered, draft] = await Promise.all([devtools.rawFetcher(query), fetcher(query)])\n return { diffs: diffRows(registered.rows, draft.rows, query), rows: draft.rows.length }\n })\n }\n\n const verifySnapshots = () => {\n const byName = new Map((snapshots ?? []).map((snapshot) => [snapshot.name, snapshot]))\n runSnapshotChecks(\n [...byName.values()].map((snapshot) => ({\n id: snapshot.name,\n label: snapshot.name,\n query: snapshot.query as DashboardQuery\n })),\n async ({ id, query }) => {\n const result = await fetcher(query)\n const expected = byName.get(id)?.rows ?? []\n return { diffs: diffRows(expected, result.rows, query), rows: result.rows.length }\n }\n )\n }\n\n return (\n <Box sx={{ p: 1.5, overflow: 'auto', height: '100%' }}>\n <Section\n title=\"Rascunho × modelo registrado\"\n actions={\n <Button size=\"small\" variant=\"contained\" disabled={!devtools.draft} onClick={comparePage}>\n Comparar consultas da página\n </Button>\n }\n >\n {!devtools.draft ? (\n <Typography sx={{ fontSize: 12, color: 'text.secondary' }}>\n Aplique um rascunho na aba Modelo para comparar: cada consulta da página roda nos dois\n modelos e as linhas são casadas pelas dimensões.\n </Typography>\n ) : (\n <CheckList checks={pageChecks} expectedLabel=\"registrado\" actualLabel=\"rascunho\" />\n )}\n </Section>\n\n <Section\n title=\"Snapshots de regressão\"\n actions={\n capabilities?.snapshots && (\n <>\n <Button size=\"small\" onClick={loadSnapshots}>\n Recarregar\n </Button>\n <Button\n size=\"small\"\n variant=\"contained\"\n disabled={!snapshots?.length}\n onClick={verifySnapshots}\n >\n Verificar todos {devtools.draft ? '(no rascunho)' : ''}\n </Button>\n </>\n )\n }\n >\n {!capabilities?.snapshots ? (\n <Alert severity=\"info\">\n O endpoint não configurou <code>snapshotsDir</code> no <code>runQuery</code>.\n </Alert>\n ) : snapshotsError ? (\n <Alert severity=\"error\">{snapshotsError}</Alert>\n ) : !snapshots ? (\n <Typography sx={{ fontSize: 12 }}>Carregando…</Typography>\n ) : !snapshots.length ? (\n <Empty>\n Nenhum snapshot. Salve um pela aba Consultas → Ferramentas → \"Salvar snapshot\".\n </Empty>\n ) : (\n <>\n <Typography sx={{ fontSize: 12, color: 'text.secondary', mb: 1 }}>\n {snapshots.length} snapshot(s). Os mesmos rodam nos testes do app (\n <code>tests/dashboard</code>).\n </Typography>\n {snapshotChecks.length ? (\n <CheckList checks={snapshotChecks} expectedLabel=\"snapshot\" actualLabel=\"agora\" />\n ) : (\n <Box sx={{ display: 'flex', gap: 0.5, flexWrap: 'wrap' }}>\n {snapshots.map((snapshot) => (\n <Chip\n key={snapshot.name}\n size=\"small\"\n label={`${snapshot.name} · ${snapshot.rows.length} linhas`}\n title={`${JSON.stringify(snapshot.query)}\\n${snapshot.createdAt}`}\n sx={{ fontFamily: MONO }}\n />\n ))}\n </Box>\n )}\n </>\n )}\n </Section>\n </Box>\n )\n}\n\nfunction CheckList({\n checks,\n expectedLabel,\n actualLabel\n}: {\n checks: Check[]\n expectedLabel: string\n actualLabel: string\n}) {\n const [open, setOpen] = useState<string | null>(null)\n if (!checks.length) return null\n const failed = checks.filter((check) => check.status === 'error' || check.diffs?.length).length\n const done = checks.every((check) => check.status !== 'loading')\n return (\n <Box>\n {done && (\n <Alert severity={failed ? 'warning' : 'success'} sx={{ mb: 1 }}>\n {failed ? `${failed} de ${checks.length} com diferença ou erro.` : 'Tudo igual.'}\n </Alert>\n )}\n {checks.map((check) => {\n const differs = !!check.diffs?.length\n return (\n <Box key={check.id} sx={{ borderBottom: 1, borderColor: 'divider', py: 0.5 }}>\n <Box\n sx={{ display: 'flex', alignItems: 'center', gap: 1, cursor: 'pointer' }}\n onClick={() => setOpen(open === check.id ? null : check.id)}\n >\n <Typography sx={{ fontFamily: MONO, fontSize: 12, flex: 1 }} noWrap>\n {check.label}\n </Typography>\n {check.status === 'loading' && <Chip size=\"small\" label=\"executando…\" />}\n {check.status === 'error' && <Chip size=\"small\" color=\"error\" label=\"erro\" />}\n {check.status === 'done' && (\n <Chip\n size=\"small\"\n color={differs ? 'warning' : 'success'}\n label={\n differs\n ? `${check.diffs?.length} linha(s) diferente(s)`\n : `igual · ${check.rows} linhas`\n }\n />\n )}\n </Box>\n <Collapse in={open === check.id}>\n <Box sx={{ pt: 1 }}>\n {check.error && (\n <Alert severity=\"error\" sx={{ fontFamily: MONO, fontSize: 12 }}>\n {check.error}\n </Alert>\n )}\n {check.diffs && (\n <RowDiffTable\n diffs={check.diffs}\n expectedLabel={expectedLabel}\n actualLabel={actualLabel}\n />\n )}\n </Box>\n </Collapse>\n </Box>\n )\n })}\n </Box>\n )\n}\n","import {\n Alert,\n Box,\n Chip,\n CircularProgress,\n createTheme,\n IconButton,\n Paper,\n Portal,\n Tab,\n Tabs,\n ThemeProvider,\n Tooltip,\n Typography\n} from '@mui/material'\nimport {\n type MouseEvent as ReactMouseEvent,\n type ReactNode,\n useCallback,\n useEffect,\n useRef,\n useState,\n useSyncExternalStore\n} from 'react'\nimport { useDashboard } from '../client/DashboardProvider'\nimport { ModelDictionary } from '../client/ModelDictionary'\nimport type { ModelDef } from '../model'\nimport type { DevtoolsCapabilities, SchemaTable } from '../types'\nimport { FiltersPanel } from './FiltersPanel'\nimport { DevtoolsWindow, openDevtoolsWindow } from './DevtoolsWindow'\nimport { DEVTOOLS_ATTRIBUTE, findQueryElement, HighlightOverlay, useInspectMode } from './Inspector'\nimport { LayoutPanel } from './LayoutPanel'\nimport { LAYOUT_ITEM_ATTRIBUTE } from './layoutStore'\nimport { ModelPanel } from './ModelPanel'\nimport { PlaygroundPanel, type PlaygroundSelection } from './PlaygroundPanel'\nimport { QueriesPanel, type QuerySelection } from './QueriesPanel'\nimport { RegressionPanel } from './RegressionPanel'\nimport { errorMessage } from './store'\nimport { MONO } from './ui'\n\n/**\n * Devtools do `@bluemarble/bi` (no estilo do TanStack Query Devtools): um botão flutuante que abre um\n * painel com as consultas da página, o modelo editável, um playground, regressão, dicionário e\n * filtros. Montado pelo próprio `DashboardProvider` em desenvolvimento.\n *\n * Modos: fixado (embaixo, à esquerda ou à direita), flutuante (janela que se arrasta pelo cabeçalho\n * e redimensiona pelo canto) ou numa janela separada do navegador (`DevtoolsWindow`). Fixado, o\n * painel ocupa espaço: a página encolhe para não ficar escondida atrás dele; só o modo flutuante\n * sobrepõe a página.\n * Atalhos: Alt+Shift+B abre/fecha o painel, Alt+Shift+F alterna entre fixado e flutuante,\n * Alt+Shift+I liga o inspetor, Esc sai do inspetor.\n */\n\n// Abaixo do Modal do MUI (1300) para os menus dos Selects do painel abrirem por cima dele\nconst Z_INDEX = 1250\nconst MIN_HEIGHT = 180\nconst MIN_SIDE_WIDTH = 360\nconst MIN_FLOAT_WIDTH = 420\nconst MIN_FLOAT_HEIGHT = 220\nconst FLOAT_MARGIN = 16\n\nconst theme = createTheme({\n palette: { mode: 'dark', primary: { main: '#F58220' }, background: { paper: '#1b1e23' } },\n typography: { fontSize: 12 },\n components: {\n MuiTableCell: { styleOverrides: { root: { fontSize: 12, padding: '4px 8px' } } },\n MuiButton: {\n defaultProps: { disableElevation: true },\n styleOverrides: { root: { textTransform: 'none' } }\n },\n MuiTab: { styleOverrides: { root: { textTransform: 'none', minHeight: 40 } } }\n }\n})\n\ntype TabKey =\n | 'queries'\n | 'model'\n | 'layout'\n | 'playground'\n | 'regression'\n | 'dictionary'\n | 'filters'\n\nconst STORAGE_KEY = 'bm-dashboard-devtools:ui'\n\ntype DockSide = 'bottom' | 'left' | 'right'\n\nconst DOCK_SIDES: { side: DockSide; icon: string; label: string }[] = [\n { side: 'left', icon: '◧', label: 'Fixar à esquerda' },\n { side: 'bottom', icon: '⬓', label: 'Fixar embaixo' },\n { side: 'right', icon: '◨', label: 'Fixar à direita' }\n]\n\ntype FloatRect = { x: number; y: number; width: number; height: number }\n\ntype UiState = {\n open: boolean\n /**\n * Fixado numa borda (ocupa espaço na página), `floating` (janela solta, por cima) ou `window`\n * (janela separada do navegador).\n */\n mode: DockSide | 'floating' | 'window'\n /** Última borda usada: para onde volta ao sair do flutuante. */\n dock: DockSide\n /** Altura fixado embaixo. */\n height: number\n /** Largura fixado na lateral. */\n width: number\n /** Posição e tamanho no modo flutuante. */\n float: FloatRect\n tab: TabKey\n}\n\n/** Mantém a janela flutuante inteira dentro da tela (encolhe se a tela ficou menor). */\nfunction clampFloat(rect: FloatRect): FloatRect {\n const maxWidth = Math.max(MIN_FLOAT_WIDTH, window.innerWidth - FLOAT_MARGIN * 2)\n const maxHeight = Math.max(MIN_FLOAT_HEIGHT, window.innerHeight - FLOAT_MARGIN * 2)\n const width = Math.min(Math.max(rect.width, MIN_FLOAT_WIDTH), maxWidth)\n const height = Math.min(Math.max(rect.height, MIN_FLOAT_HEIGHT), maxHeight)\n return {\n width,\n height,\n x: Math.min(Math.max(rect.x, 0), Math.max(0, window.innerWidth - width)),\n y: Math.min(Math.max(rect.y, 0), Math.max(0, window.innerHeight - height))\n }\n}\n\nfunction loadUi(): UiState {\n const width = Math.min(960, window.innerWidth - FLOAT_MARGIN * 2)\n const height = Math.min(560, window.innerHeight - FLOAT_MARGIN * 2)\n const fallback: UiState = {\n open: false,\n mode: 'bottom',\n dock: 'bottom',\n width: 520,\n height: 380,\n // Canto inferior direito, longe do botão (que fica à esquerda)\n float: {\n width,\n height,\n x: window.innerWidth - width - FLOAT_MARGIN,\n y: window.innerHeight - height - FLOAT_MARGIN\n },\n tab: 'queries'\n }\n try {\n const saved: UiState = {\n ...fallback,\n ...JSON.parse(localStorage.getItem(STORAGE_KEY) ?? '{}')\n }\n // Versão anterior gravava `docked` (só existia embaixo)\n if (!['bottom', 'left', 'right', 'floating', 'window'].includes(saved.mode))\n saved.mode = 'bottom'\n if (!['bottom', 'left', 'right'].includes(saved.dock)) saved.dock = 'bottom'\n // Popup só abre com um clique (o navegador bloqueia sem gesto): começa fechado\n if (saved.mode === 'window') saved.open = false\n return { ...saved, float: clampFloat({ ...fallback.float, ...saved.float }) }\n } catch {\n return fallback\n }\n}\n\n/**\n * Encolhe a página para o painel fixado caber ao lado dela. A raiz do Next (`#__next`) vira uma caixa\n * do tamanho da tela menos o painel, com rolagem própria; o `transform` faz os elementos `fixed` do\n * app (sidebar, appbar) ficarem dentro dessa caixa em vez de presos à janela — só um padding no\n * `body` deixaria eles atrás do painel. Sem `#__next` (App Router), cai no padding do `body`.\n */\nfunction reservePageSpace(side: DockSide, initialSize: number) {\n const root = document.getElementById('__next')\n if (!root) {\n const property = (\n { bottom: 'paddingBottom', left: 'paddingLeft', right: 'paddingRight' } as const\n )[side]\n const previous = document.body.style[property]\n const resize = (size: number) => {\n document.body.style[property] = `${size}px`\n }\n resize(initialSize)\n return {\n resize,\n release: () => {\n document.body.style[property] = previous\n }\n }\n }\n const previous = root.getAttribute('style')\n const scroll = { x: window.scrollX, y: window.scrollY }\n Object.assign(root.style, {\n position: 'fixed',\n inset: '0',\n overflow: 'auto',\n transform: 'translateZ(0)'\n })\n const resize = (size: number) => {\n root.style[side] = `${size}px`\n }\n resize(initialSize)\n // A rolagem passa da janela para a caixa: mantém onde a pessoa estava\n root.scrollTo(scroll.x, scroll.y)\n return {\n resize,\n release: () => {\n const inner = { x: root.scrollLeft, y: root.scrollTop }\n if (previous === null) root.removeAttribute('style')\n else root.setAttribute('style', previous)\n window.scrollTo(inner.x, inner.y)\n }\n }\n}\n\n/** Acompanha o mouse até soltar o botão, sem selecionar texto da página no caminho. */\nfunction trackMouse(event: ReactMouseEvent, onMove: (dx: number, dy: number) => void) {\n event.preventDefault()\n const startX = event.clientX\n const startY = event.clientY\n const previousSelect = document.body.style.userSelect\n document.body.style.userSelect = 'none'\n const move = (moveEvent: MouseEvent) =>\n onMove(moveEvent.clientX - startX, moveEvent.clientY - startY)\n const up = () => {\n document.body.style.userSelect = previousSelect\n window.removeEventListener('mousemove', move)\n window.removeEventListener('mouseup', up)\n }\n window.addEventListener('mousemove', move)\n window.addEventListener('mouseup', up)\n}\n\nconst devtoolsMarker = { [DEVTOOLS_ATTRIBUTE]: '' }\n\nexport default function DashboardDevtools() {\n const { model, fetcher, devtools } = useDashboard()\n const [ui, setUi] = useState(loadUi)\n const [original, setOriginal] = useState<ModelDef | null>(null)\n const [capabilities, setCapabilities] = useState<DevtoolsCapabilities | null>(null)\n const [describeError, setDescribeError] = useState<string | null>(null)\n const [tables, setTables] = useState<SchemaTable[] | null>(null)\n const [playground, setPlayground] = useState<PlaygroundSelection>({\n dimensions: [],\n measures: []\n })\n const [selected, setSelected] = useState<QuerySelection | null>(null)\n const [pickedItem, setPickedItem] = useState<{ item: string } | null>(null)\n const [hovered, setHovered] = useState<string | null>(null)\n const [inspecting, setInspecting] = useState(false)\n const [popup, setPopup] = useState<Window | null>(null)\n\n const store = devtools?.store\n const snapshot = useSyncExternalStore(\n store?.subscribe ?? (() => () => {}),\n () => store?.getSnapshot(),\n () => store?.getSnapshot()\n )\n const instances = snapshot?.instances ?? []\n\n useEffect(() => {\n try {\n localStorage.setItem(STORAGE_KEY, JSON.stringify(ui))\n } catch {}\n }, [ui])\n\n const loadModel = useCallback(\n (clearCache = false) =>\n fetcher({ model, devtools: { describe: true, clearCache } })\n .then((result) => {\n setOriginal(result.devtools?.model ?? null)\n setCapabilities(result.devtools?.capabilities ?? null)\n setDescribeError(result.devtools?.model ? null : 'O endpoint não devolveu o modelo.')\n })\n .catch((error) => setDescribeError(errorMessage(error))),\n [fetcher, model]\n )\n\n useEffect(() => {\n if (ui.open) loadModel()\n }, [ui.open, loadModel])\n\n // Schema do banco só quando alguém vai editar SQL\n useEffect(() => {\n if (!ui.open || ui.tab !== 'model' || tables) return\n fetcher({ model, devtools: { schema: true } })\n .then((result) => setTables(result.devtools?.schema ?? []))\n .catch(() => setTables([]))\n }, [ui.open, ui.tab, tables, fetcher, model])\n\n const setTab = (tab: TabKey) => setUi((current) => ({ ...current, open: true, tab }))\n\n // Na aba Layout, o inspetor escolhe o gráfico/filtro para editar; nas outras, a consulta\n const layoutTab = ui.tab === 'layout'\n const pick = useCallback(\n (instanceId: string) => {\n setInspecting(false)\n const item = findQueryElement(instanceId)\n ?.closest(`[${LAYOUT_ITEM_ATTRIBUTE}]`)\n ?.getAttribute(LAYOUT_ITEM_ATTRIBUTE)\n if (layoutTab && item) {\n setPickedItem({ item })\n return\n }\n setSelected({ instanceId })\n setUi((current) => ({ ...current, open: true, tab: 'queries' }))\n },\n [layoutTab]\n )\n useInspectMode({ active: inspecting, onHover: setHovered, onPick: pick })\n\n // Janela separada: abrir o popup precisa acontecer no clique/tecla (senão o navegador bloqueia)\n const closePopup = useCallback(() => {\n setPopup((current) => {\n if (current && !current.closed) current.close()\n return null\n })\n }, [])\n const openPanel = useCallback(() => {\n if (ui.mode !== 'window') {\n setUi((current) => ({ ...current, open: true }))\n return\n }\n const opened = popup && !popup.closed ? popup : openDevtoolsWindow()\n if (opened) {\n opened.focus()\n setPopup(opened)\n setUi((current) => ({ ...current, open: true }))\n } else {\n // Bloqueado: abre fixado na página\n setUi((current) => ({ ...current, open: true, mode: current.dock }))\n }\n }, [ui.mode, popup])\n const closePanel = useCallback(() => {\n closePopup()\n setUi((current) => ({ ...current, open: false }))\n }, [closePopup])\n const toWindow = () => {\n const opened = openDevtoolsWindow()\n if (!opened) return\n opened.focus()\n setPopup(opened)\n setUi((current) => ({ ...current, open: true, mode: 'window' }))\n }\n const onPopupClosed = useCallback(() => {\n setPopup(null)\n setUi((current) => ({ ...current, open: false }))\n }, [])\n\n const keyActions = useRef({ openPanel, closePanel, closePopup, open: ui.open, inspecting })\n keyActions.current = { openPanel, closePanel, closePopup, open: ui.open, inspecting }\n useEffect(() => {\n const onKey = (event: KeyboardEvent) => {\n const actions = keyActions.current\n if (event.key === 'Escape' && actions.inspecting) setInspecting(false)\n if (!event.altKey || !event.shiftKey) return\n if (event.code === 'KeyB') {\n event.preventDefault()\n if (actions.open) actions.closePanel()\n else actions.openPanel()\n } else if (event.code === 'KeyF') {\n event.preventDefault()\n actions.closePopup()\n setUi((current) => ({\n ...current,\n open: true,\n mode: current.mode === 'floating' ? current.dock : 'floating'\n }))\n } else if (event.code === 'KeyI') {\n event.preventDefault()\n setInspecting((value) => !value)\n }\n }\n // Com a janela separada em foco, os atalhos chegam nela\n const targets = popup && !popup.closed ? [window, popup] : [window]\n for (const target of targets) target.addEventListener('keydown', onKey)\n return () => {\n for (const target of targets) target.removeEventListener('keydown', onKey)\n }\n }, [popup])\n\n // Fixado, o painel ocupa espaço: a página encolhe em vez de ficar escondida atrás dele.\n // Flutuante, em janela separada ou fechado, a página volta ao normal.\n const reserved = ui.open && ui.mode !== 'floating' && ui.mode !== 'window' ? ui.mode : null\n const reservedSize = reserved === 'bottom' ? ui.height : ui.width\n const reservation = useRef<ReturnType<typeof reservePageSpace> | null>(null)\n const reservedSizeRef = useRef(reservedSize)\n reservedSizeRef.current = reservedSize\n useEffect(() => {\n if (!reserved) return\n const handle = reservePageSpace(reserved, reservedSizeRef.current)\n reservation.current = handle\n return () => {\n reservation.current = null\n handle.release()\n }\n }, [reserved])\n // Arrastar a borda só ajusta o tamanho, sem desfazer e refazer tudo\n useEffect(() => reservation.current?.resize(reservedSize), [reservedSize])\n\n // Tela redimensionada: a janela flutuante não pode ficar fora dela\n useEffect(() => {\n const onResize = () => setUi((current) => ({ ...current, float: clampFloat(current.float) }))\n window.addEventListener('resize', onResize)\n return () => window.removeEventListener('resize', onResize)\n }, [])\n\n if (!devtools || !store) return null\n\n const inWindow = ui.mode === 'window' && !!popup\n const floating = ui.mode === 'floating'\n const side = ui.mode === 'left' || ui.mode === 'right' ? ui.mode : null\n\n const startDockResize = (event: ReactMouseEvent) => {\n const { height, width } = ui\n trackMouse(event, (dx, dy) =>\n setUi((current) =>\n current.mode === 'bottom'\n ? {\n ...current,\n height: Math.min(Math.max(height - dy, MIN_HEIGHT), window.innerHeight - 40)\n }\n : {\n ...current,\n width: Math.min(\n Math.max(width + (current.mode === 'left' ? dx : -dx), MIN_SIDE_WIDTH),\n window.innerWidth - 80\n )\n }\n )\n )\n }\n\n const startFloatResize = (event: ReactMouseEvent) => {\n const start = ui.float\n trackMouse(event, (dx, dy) =>\n setUi((current) => ({\n ...current,\n float: clampFloat({ ...start, width: start.width + dx, height: start.height + dy })\n }))\n )\n }\n\n // Arrastar pelo cabeçalho; botões, abas e campos continuam clicáveis\n const startDrag = (event: ReactMouseEvent) => {\n if (!floating || event.button !== 0) return\n if ((event.target as Element).closest('button, [role=\"tab\"], input, a')) return\n const start = ui.float\n trackMouse(event, (dx, dy) =>\n setUi((current) => ({\n ...current,\n float: clampFloat({ ...start, x: start.x + dx, y: start.y + dy })\n }))\n )\n }\n\n const toggleMode = () => {\n closePopup()\n setUi((current) => ({\n ...current,\n mode: current.mode === 'floating' ? current.dock : 'floating'\n }))\n }\n const dockTo = (dock: DockSide) => {\n closePopup()\n setUi((current) => ({ ...current, mode: dock, dock }))\n }\n\n const clearServerCache = () => loadModel(true).then(devtools.refresh)\n\n const loading = instances.filter((item) => item.last.status === 'loading').length\n const errors = instances.filter((item) => item.last.status === 'error').length\n const storms = instances.filter((item) => item.storm).length\n const hoveredLabel = instances.find((item) => item.instanceId === hovered)?.label\n\n const needsModel = (content: (registered: ModelDef) => ReactNode) =>\n describeError ? (\n <Alert severity=\"error\" sx={{ m: 1.5 }}>\n Não foi possível carregar o modelo: {describeError}. O endpoint precisa chamar{' '}\n <code>runQuery(..., {'{ devtools: true }'})</code> em desenvolvimento.\n </Alert>\n ) : !original ? (\n <Box sx={{ p: 3, display: 'flex', justifyContent: 'center' }}>\n <CircularProgress size={20} />\n </Box>\n ) : (\n content(original)\n )\n\n const header = (\n <Box\n onMouseDown={startDrag}\n onDoubleClick={(event) => {\n if (floating && !(event.target as Element).closest('button, [role=\"tab\"]')) toggleMode()\n }}\n sx={{\n display: 'flex',\n alignItems: 'center',\n gap: 1.5,\n px: 1.5,\n borderBottom: 1,\n borderColor: 'divider',\n cursor: floating ? 'move' : undefined,\n // Na lateral não cabe tudo numa linha: as abas descem para a linha de baixo\n ...(side && { flexWrap: 'wrap', columnGap: 1, pt: 0.5 })\n }}\n >\n <Typography sx={{ fontWeight: 800, color: 'primary.main', whiteSpace: 'nowrap' }}>\n ◆ BI Devtools\n </Typography>\n <Chip size=\"small\" label={model} sx={{ fontFamily: MONO }} />\n <Tabs\n value={ui.tab}\n onChange={(_, tab: TabKey) => setTab(tab)}\n variant=\"scrollable\"\n scrollButtons=\"auto\"\n sx={{ minHeight: 40, ...(side && { order: 1, width: '100%' }) }}\n >\n <Tab\n value=\"queries\"\n label={\n <Box sx={{ display: 'flex', alignItems: 'center', gap: 0.75 }}>\n Consultas ({instances.length}){!!loading && <CircularProgress size={10} />}\n {!!(errors || storms) && (\n <Chip size=\"small\" color=\"error\" label={errors + storms} sx={{ height: 16 }} />\n )}\n </Box>\n }\n />\n <Tab value=\"model\" label=\"Modelo\" />\n <Tab value=\"layout\" label=\"Layout\" />\n <Tab value=\"playground\" label=\"Playground\" />\n <Tab value=\"regression\" label=\"Regressão\" />\n <Tab value=\"dictionary\" label=\"Dicionário\" />\n <Tab value=\"filters\" label=\"Filtros\" />\n </Tabs>\n {devtools.draft && <Chip size=\"small\" color=\"warning\" label=\"rascunho aplicado\" />}\n <Box sx={{ ml: 'auto', display: 'flex', alignItems: 'center', gap: 0.5 }}>\n <Tooltip title=\"Inspecionar componente (Alt+Shift+I)\">\n <IconButton\n size=\"small\"\n color={inspecting ? 'primary' : 'default'}\n onClick={() => setInspecting((value) => !value)}\n aria-label=\"Inspecionar componente\"\n >\n ⌖\n </IconButton>\n </Tooltip>\n {DOCK_SIDES.map(({ side: dock, icon, label }) => (\n <Tooltip key={dock} title={`${label} (ocupa espaço na página)`}>\n <IconButton\n size=\"small\"\n color={ui.mode === dock ? 'primary' : 'default'}\n onClick={() => dockTo(dock)}\n aria-label={label}\n >\n {icon}\n </IconButton>\n </Tooltip>\n ))}\n <Tooltip title=\"Janela flutuante, por cima da página (Alt+Shift+F) · arraste pelo cabeçalho\">\n <IconButton\n size=\"small\"\n color={floating ? 'primary' : 'default'}\n onClick={toggleMode}\n aria-label=\"Devtools flutuante\"\n >\n ⧉\n </IconButton>\n </Tooltip>\n <Tooltip title=\"Abrir numa janela separada do navegador (ex.: em outro monitor)\">\n <IconButton\n size=\"small\"\n color={inWindow ? 'primary' : 'default'}\n onClick={inWindow ? () => popup?.focus() : toWindow}\n aria-label=\"Devtools em janela separada\"\n >\n ↗\n </IconButton>\n </Tooltip>\n <Tooltip title=\"Fechar (Alt+Shift+B)\">\n <IconButton size=\"small\" onClick={closePanel} aria-label=\"Fechar devtools\">\n ✕\n </IconButton>\n </Tooltip>\n </Box>\n </Box>\n )\n\n const body = (\n <Box sx={{ flex: 1, minHeight: 0 }}>\n {ui.tab === 'queries' && (\n <QueriesPanel\n devtools={devtools}\n capabilities={capabilities}\n selected={selected}\n onSelect={setSelected}\n onHover={setHovered}\n onClearServerCache={clearServerCache}\n />\n )}\n {ui.tab === 'model' &&\n needsModel((registered) => (\n <ModelPanel\n devtools={devtools}\n original={registered}\n capabilities={capabilities}\n tables={tables ?? []}\n onTry={(selection) => {\n setPlayground(selection)\n setTab('playground')\n }}\n // O Next recompila a rota ao ver o arquivo novo; espera um pouco antes de reler\n onSaved={() => setTimeout(() => loadModel(), 1000)}\n />\n ))}\n {ui.tab === 'layout' &&\n needsModel((registered) => (\n <LayoutPanel\n devtools={devtools}\n model={devtools.draft ?? registered}\n capabilities={capabilities}\n picked={pickedItem}\n onHover={setHovered}\n />\n ))}\n {ui.tab === 'playground' &&\n needsModel((registered) => (\n <PlaygroundPanel\n model={devtools.draft ?? registered}\n selection={playground}\n onSelectionChange={setPlayground}\n />\n ))}\n {ui.tab === 'regression' && (\n <RegressionPanel devtools={devtools} capabilities={capabilities} />\n )}\n {ui.tab === 'dictionary' && (\n <Box sx={{ p: 1.5, overflow: 'auto', height: '100%' }}>\n <Typography sx={{ fontSize: 12, color: 'text.secondary', mb: 1.5 }}>\n O mesmo <code>{'<ModelDictionary />'}</code> pode ir numa página do dashboard como\n documentação para quem usa. Edite rótulos e descrições na aba Modelo.\n </Typography>\n <ModelDictionary />\n </Box>\n )}\n {ui.tab === 'filters' && <FiltersPanel devtools={devtools} />}\n </Box>\n )\n\n return (\n <Portal>\n <ThemeProvider theme={theme}>\n <HighlightOverlay instanceId={hovered} label={hoveredLabel} zIndex={Z_INDEX + 1} />\n\n {ui.open && inWindow && popup && (\n <DevtoolsWindow\n popup={popup}\n title={`BI Devtools · ${model}`}\n theme={theme}\n onClosed={onPopupClosed}\n >\n <Paper\n {...devtoolsMarker}\n square\n elevation={0}\n sx={{\n height: '100%',\n display: 'flex',\n flexDirection: 'column',\n color: 'text.primary',\n overflow: 'hidden'\n }}\n >\n {header}\n {body}\n </Paper>\n </DevtoolsWindow>\n )}\n\n {ui.open && !inWindow ? (\n <Paper\n {...devtoolsMarker}\n square={!floating}\n elevation={floating ? 16 : 12}\n sx={{\n position: 'fixed',\n zIndex: Z_INDEX,\n display: 'flex',\n flexDirection: 'column',\n color: 'text.primary',\n overflow: 'hidden',\n ...(floating\n ? {\n left: ui.float.x,\n top: ui.float.y,\n width: ui.float.width,\n height: ui.float.height,\n border: '1px solid #F58220',\n borderRadius: 1.5\n }\n : side\n ? {\n top: 0,\n bottom: 0,\n [side]: 0,\n width: ui.width,\n [side === 'left' ? 'borderRight' : 'borderLeft']: '2px solid #F58220'\n }\n : {\n left: 0,\n right: 0,\n bottom: 0,\n height: ui.height,\n borderTop: '2px solid #F58220'\n })\n }}\n >\n {floating ? (\n <Box\n onMouseDown={startFloatResize}\n title=\"Redimensionar\"\n sx={{\n position: 'absolute',\n right: 0,\n bottom: 0,\n width: 16,\n height: 16,\n zIndex: 1,\n cursor: 'nwse-resize',\n // Riscos diagonais no canto, como o \"grip\" de janela\n background:\n 'linear-gradient(135deg, transparent 0 55%, #F58220 55% 62%, transparent 62% 72%, #F58220 72% 79%, transparent 79%)'\n }}\n />\n ) : (\n <Box\n onMouseDown={startDockResize}\n sx={\n side\n ? {\n position: 'absolute',\n top: 0,\n bottom: 0,\n [side === 'left' ? 'right' : 'left']: -3,\n width: 8,\n zIndex: 1,\n cursor: 'ew-resize'\n }\n : {\n position: 'absolute',\n top: -5,\n left: 0,\n right: 0,\n height: 8,\n cursor: 'ns-resize'\n }\n }\n />\n )}\n {header}\n {body}\n </Paper>\n ) : (\n <ToggleButton\n draft={!!devtools.draft}\n loading={loading}\n problems={errors + storms}\n inspecting={inspecting}\n onOpen={inWindow ? () => popup?.focus() : openPanel}\n />\n )}\n\n {inspecting && (\n <Box\n {...devtoolsMarker}\n sx={{\n position: 'fixed',\n top: 12,\n left: '50%',\n transform: 'translateX(-50%)',\n zIndex: Z_INDEX + 2,\n bgcolor: '#1b1e23',\n color: '#fff',\n border: '1px solid #F58220',\n borderRadius: 1,\n px: 1.5,\n py: 0.75,\n fontSize: 12,\n boxShadow: 6\n }}\n >\n {layoutTab\n ? 'Inspetor: clique num gráfico ou filtro para editá-lo · Esc para sair'\n : 'Inspetor: clique num gráfico ou filtro do dashboard · Esc para sair'}\n </Box>\n )}\n </ThemeProvider>\n </Portal>\n )\n}\n\nfunction ToggleButton({\n draft,\n loading,\n problems,\n inspecting,\n onOpen\n}: {\n draft: boolean\n loading: number\n problems: number\n inspecting: boolean\n onOpen: () => void\n}) {\n return (\n <Tooltip title=\"BI Devtools (Alt+Shift+B)\" placement=\"right\">\n <Box\n {...devtoolsMarker}\n component=\"button\"\n type=\"button\"\n onClick={onOpen}\n aria-label=\"Abrir BI Devtools\"\n sx={{\n position: 'fixed',\n left: 12,\n bottom: 12,\n zIndex: Z_INDEX,\n display: 'flex',\n alignItems: 'center',\n gap: 0.75,\n px: 1.25,\n height: 32,\n border: '1px solid',\n borderColor: draft || inspecting ? 'warning.main' : '#F58220',\n borderRadius: 16,\n bgcolor: '#1b1e23',\n color: '#fff',\n fontSize: 12,\n fontWeight: 800,\n cursor: 'pointer',\n boxShadow: 4,\n opacity: 0.85,\n '&:hover': { opacity: 1 }\n }}\n >\n <Box component=\"span\" sx={{ color: '#F58220' }}>\n ◆\n </Box>\n BI\n {!!loading && <CircularProgress size={10} sx={{ color: '#4dabf7' }} />}\n {!!problems && (\n <Box component=\"span\" sx={{ bgcolor: 'error.main', borderRadius: 8, px: 0.75 }}>\n {problems}\n </Box>\n )}\n {draft && (\n <Box component=\"span\" sx={{ color: 'warning.main' }}>\n rascunho\n </Box>\n )}\n </Box>\n </Tooltip>\n )\n}\n"],"mappings":"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"}