Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 1 addition & 1 deletion src-tauri/capabilities/default.json
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@
"$schema": "../gen/schemas/desktop-schema.json",
"identifier": "default",
"description": "enables the default permissions",
"windows": ["main", "visual-explain", "er-diagram", "task-manager", "json-viewer-*", "results-window-*", "connection-window-*"],
"windows": ["main", "visual-explain", "er-diagram*", "task-manager", "json-viewer-*", "results-window-*", "connection-window-*"],
"permissions": [
"core:default",
"core:window:allow-set-title",
Expand Down
87 changes: 86 additions & 1 deletion src/components/ui/SchemaDiagram.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -16,7 +16,19 @@ import "@xyflow/react/dist/style.css";
import dagre from "dagre";
import { useEditor } from "../../hooks/useEditor";
import { SchemaTableNodeComponent } from "./SchemaTableNode";
import { Loader2, ArrowLeftRight, ArrowUpDown, Maximize2, Focus } from "lucide-react";
import {
Loader2,
ArrowLeftRight,
ArrowUpDown,
Maximize2,
Focus,
Download,
ChevronDown,
} from "lucide-react";
import { save } from "@tauri-apps/plugin-dialog";
import { writeTextFile } from "@tauri-apps/plugin-fs";
import { generateMermaidErDiagram, generateDbml } from "../../utils/schemaExport";
import { useAlert } from "../../hooks/useAlert";
import { useTranslation } from "react-i18next";
import { ContextMenu } from "./ContextMenu";
import { useSearchParams } from "react-router-dom";
Expand Down Expand Up @@ -89,6 +101,7 @@ const SchemaDiagramContent = ({
}: SchemaDiagramContentProps) => {
const { t } = useTranslation();
const { getSchema } = useEditor();
const { showAlert } = useAlert();
const { settings } = useSettings();
const [nodes, setNodes, onNodesChange] = useNodesState<Node>([]);
const [edges, setEdges, onEdgesChange] = useEdgesState<Edge>([]);
Expand All @@ -111,6 +124,9 @@ const SchemaDiagramContent = ({
y: number;
tableId: string;
} | null>(null);
const [exportMenu, setExportMenu] = useState<{ x: number; y: number } | null>(
null,
);
const [searchParams] = useSearchParams();

// Callback per gestire il click su una tabella
Expand Down Expand Up @@ -143,6 +159,41 @@ const SchemaDiagramContent = ({
});
}, [layoutDirectionFromSettings]);

// Export the full schema as a Mermaid erDiagram. Uses allNodes/allEdges
// rather than the rendered nodes so the export stays complete even while a
// single table is focused.
const handleExport = useCallback(
async (format: "mermaid" | "dbml") => {
if (allNodes.length === 0) return;

const isMermaid = format === "mermaid";
const extension = isMermaid ? "mmd" : "dbml";

try {
const filePath = await save({
filters: [
{
name: isMermaid ? "Mermaid" : "DBML",
extensions: [extension],
},
],
defaultPath: `schema_${new Date().toISOString().slice(0, 10)}.${extension}`,
});
if (!filePath) return;

const content = isMermaid
? generateMermaidErDiagram(allNodes, allEdges)
: generateDbml(allNodes, allEdges);

await writeTextFile(filePath, content);
showAlert(t("erDiagram.exportSuccess"), { kind: "info" });
} catch (err) {
showAlert(String(err), { kind: "error" });
}
},
[allNodes, allEdges, showAlert, t],
);

// Callback per tornare alla vista completa
const handleResetView = useCallback(() => {
setSelectedTable(null);
Expand Down Expand Up @@ -356,6 +407,20 @@ const SchemaDiagramContent = ({
)}
</button>

<button
onClick={(event) => {
const rect = event.currentTarget.getBoundingClientRect();
setExportMenu({ x: rect.left, y: rect.bottom + 4 });
}}
disabled={allNodes.length === 0}
className="flex items-center gap-2 px-3 py-2 bg-elevated hover:bg-surface-secondary text-primary rounded-lg border border-strong transition-colors shadow-lg text-sm font-medium disabled:opacity-50 disabled:cursor-not-allowed"
title={t("erDiagram.export")}
>
<Download size={16} />
<span>{t("erDiagram.export")}</span>
<ChevronDown size={14} />
</button>

{selectedTable && (
<button
onClick={handleResetView}
Expand Down Expand Up @@ -411,6 +476,26 @@ const SchemaDiagramContent = ({
</ReactFlow>

{/* Context Menu */}
{exportMenu && (
<ContextMenu
x={exportMenu.x}
y={exportMenu.y}
onClose={() => setExportMenu(null)}
items={[
{
label: t("erDiagram.exportMermaid"),
icon: Download,
action: () => handleExport("mermaid"),
},
{
label: t("erDiagram.exportDbml"),
icon: Download,
action: () => handleExport("dbml"),
},
]}
/>
)}

{contextMenu && (
<ContextMenu
x={contextMenu.x}
Expand Down
6 changes: 5 additions & 1 deletion src/i18n/locales/de.json
Original file line number Diff line number Diff line change
Expand Up @@ -1388,7 +1388,11 @@
"showAllTables": "Alle Tabellen anzeigen",
"showAll": "Alle anzeigen",
"focusedOn": "Fokussiert auf",
"focusOnTable": "Auf Tabelle fokussieren"
"focusOnTable": "Auf Tabelle fokussieren",
"exportMermaid": "Als Mermaid-Diagramm exportieren",
"exportSuccess": "Diagramm exportiert",
"exportDbml": "Als DBML exportieren",
"export": "Exportieren"
},
"views": {
"createView": "Ansicht erstellen",
Expand Down
6 changes: 5 additions & 1 deletion src/i18n/locales/en.json
Original file line number Diff line number Diff line change
Expand Up @@ -1432,7 +1432,11 @@
"showAllTables": "Show All Tables",
"showAll": "Show All",
"focusedOn": "Focused on",
"focusOnTable": "Focus on Table"
"focusOnTable": "Focus on Table",
"exportMermaid": "Export as Mermaid diagram",
"exportSuccess": "Diagram exported",
"exportDbml": "Export as DBML",
"export": "Export"
},
"views": {
"createView": "Create View",
Expand Down
6 changes: 5 additions & 1 deletion src/i18n/locales/es.json
Original file line number Diff line number Diff line change
Expand Up @@ -1403,7 +1403,11 @@
"showAllTables": "Mostrar Todas las Tablas",
"showAll": "Mostrar Todo",
"focusedOn": "Enfocado en",
"focusOnTable": "Enfocar en Tabla"
"focusOnTable": "Enfocar en Tabla",
"exportMermaid": "Exportar como diagrama Mermaid",
"exportSuccess": "Diagrama exportado",
"exportDbml": "Exportar como DBML",
"export": "Exportar"
},
"views": {
"createView": "Crear Vista",
Expand Down
6 changes: 5 additions & 1 deletion src/i18n/locales/fr.json
Original file line number Diff line number Diff line change
Expand Up @@ -1426,7 +1426,11 @@
"showAllTables": "Afficher toutes les tables",
"showAll": "Tout afficher",
"focusedOn": "Focalisé sur",
"focusOnTable": "Focaliser sur la table"
"focusOnTable": "Focaliser sur la table",
"exportMermaid": "Exporter en diagramme Mermaid",
"exportSuccess": "Diagramme exporté",
"exportDbml": "Exporter en DBML",
"export": "Exporter"
},
"views": {
"createView": "Créer une vue",
Expand Down
6 changes: 5 additions & 1 deletion src/i18n/locales/it.json
Original file line number Diff line number Diff line change
Expand Up @@ -1410,7 +1410,11 @@
"showAllTables": "Mostra Tutte le Tabelle",
"showAll": "Mostra Tutto",
"focusedOn": "Focus su",
"focusOnTable": "Focus su Tabella"
"focusOnTable": "Focus su Tabella",
"exportMermaid": "Esporta come diagramma Mermaid",
"exportSuccess": "Diagramma esportato",
"exportDbml": "Esporta come DBML",
"export": "Esporta"
},
"views": {
"createView": "Crea Vista",
Expand Down
6 changes: 5 additions & 1 deletion src/i18n/locales/ja.json
Original file line number Diff line number Diff line change
Expand Up @@ -1399,7 +1399,11 @@
"showAllTables": "すべてのテーブルを表示",
"showAll": "すべて表示",
"focusedOn": "フォーカス中",
"focusOnTable": "テーブルにフォーカス"
"focusOnTable": "テーブルにフォーカス",
"exportMermaid": "Mermaid 図としてエクスポート",
"exportSuccess": "図をエクスポートしました",
"exportDbml": "DBML としてエクスポート",
"export": "エクスポート"
},
"views": {
"createView": "ビューを作成",
Expand Down
6 changes: 5 additions & 1 deletion src/i18n/locales/ko.json
Original file line number Diff line number Diff line change
Expand Up @@ -1385,7 +1385,11 @@
"showAllTables": "모든 테이블 표시",
"showAll": "모두 표시",
"focusedOn": "포커스 대상",
"focusOnTable": "테이블에 포커스"
"focusOnTable": "테이블에 포커스",
"exportMermaid": "Mermaid 다이어그램으로 내보내기",
"exportSuccess": "다이어그램 내보내기 완료",
"exportDbml": "DBML로 내보내기",
"export": "내보내기"
},
"views": {
"createView": "뷰 생성",
Expand Down
6 changes: 5 additions & 1 deletion src/i18n/locales/ru.json
Original file line number Diff line number Diff line change
Expand Up @@ -1393,7 +1393,11 @@
"showAllTables": "Показать все таблицы",
"showAll": "Показать все",
"focusedOn": "Фокус на",
"focusOnTable": "Фокус на таблице"
"focusOnTable": "Фокус на таблице",
"exportMermaid": "Экспортировать как диаграмму Mermaid",
"exportSuccess": "Диаграмма экспортирована",
"exportDbml": "Экспортировать как DBML",
"export": "Экспорт"
},
"views": {
"createView": "Создать представление",
Expand Down
6 changes: 5 additions & 1 deletion src/i18n/locales/tl.json
Original file line number Diff line number Diff line change
Expand Up @@ -1418,7 +1418,11 @@
"showAllTables": "Ipakita ang Lahat ng Table",
"showAll": "Ipakita Lahat",
"focusedOn": "Nakatuon sa",
"focusOnTable": "Tumuon sa Table"
"focusOnTable": "Tumuon sa Table",
"exportMermaid": "I-export bilang Mermaid diagram",
"exportSuccess": "Na-export ang diagram",
"exportDbml": "I-export bilang DBML",
"export": "I-export"
},
"views": {
"createView": "Gumawa ng View",
Expand Down
6 changes: 5 additions & 1 deletion src/i18n/locales/zh.json
Original file line number Diff line number Diff line change
Expand Up @@ -1332,7 +1332,11 @@
"showAllTables": "显示所有表",
"showAll": "显示全部",
"focusedOn": "聚焦于",
"focusOnTable": "聚焦于表"
"focusOnTable": "聚焦于表",
"exportMermaid": "导出为 Mermaid 图表",
"exportSuccess": "图表已导出",
"exportDbml": "导出为 DBML",
"export": "导出"
},
"views": {
"createView": "创建视图",
Expand Down
Loading