refactor: convert to bun-workspaces monorepo (desktop/ + www/)
- Move the Tauri app (React frontend + Rust backend) into desktop/ via git mv — configs unchanged (relative paths: tauri.conf.json, vite.config.ts) - Root package.json becomes a private bun workspace container with orchestration scripts; desktop package renamed gridline-desktop - Scaffold www/ with Astro 7 + Tailwind v4 (hand-wired vite plugin, static output, ready for Dokploy) - Update release.yml for the new layout: projectPath: desktop, desktop/src-tauri resource paths, rust-cache workspace path - Update README + AGENTS.md structure trees and dev commands - Verified: vitest (1074), cargo test (354), desktop build, tauri dev (window launches), tauri build (dmg + app bundles), Astro build
This commit is contained in:
@@ -0,0 +1,98 @@
|
||||
import {
|
||||
Boxes,
|
||||
Clock,
|
||||
Database,
|
||||
DatabaseBackup,
|
||||
Home,
|
||||
Settings,
|
||||
Share2,
|
||||
} from "lucide-react";
|
||||
import { Tooltip } from "../ui/Tooltip";
|
||||
import { DB_CAPABILITIES, type DbCapabilities } from "../../lib/dbCapabilities";
|
||||
|
||||
export interface DbViewerSidebarProps {
|
||||
currentView: string;
|
||||
onNavigate: (view: string) => void;
|
||||
capabilities?: DbCapabilities;
|
||||
}
|
||||
|
||||
export const NAV_CAPABILITY_KEY: Record<string, keyof DbCapabilities> = {
|
||||
"db-viewer": "explorer",
|
||||
queries: "queries",
|
||||
"schema-visualizer": "visualizer",
|
||||
objects: "objects",
|
||||
tools: "tools",
|
||||
};
|
||||
|
||||
interface NavItem {
|
||||
id: string;
|
||||
label: string;
|
||||
icon: React.ReactNode;
|
||||
stub?: boolean;
|
||||
}
|
||||
|
||||
export function DbViewerSidebar({
|
||||
currentView,
|
||||
onNavigate,
|
||||
capabilities = DB_CAPABILITIES.postgresql,
|
||||
}: DbViewerSidebarProps) {
|
||||
const topItems: NavItem[] = [
|
||||
{ id: "db-viewer", label: "Explorer", icon: <Database size={16} /> },
|
||||
{
|
||||
id: "queries",
|
||||
label: "Queries",
|
||||
icon: <Clock size={16} />,
|
||||
},
|
||||
{
|
||||
id: "schema-visualizer",
|
||||
label: "Schema Visualizer",
|
||||
icon: <Share2 size={16} />,
|
||||
},
|
||||
{ id: "objects", label: "Objects", icon: <Boxes size={16} /> },
|
||||
{ id: "tools", label: "Tools", icon: <DatabaseBackup size={16} /> },
|
||||
];
|
||||
|
||||
const visibleTopItems = topItems.filter(
|
||||
(item) => capabilities[NAV_CAPABILITY_KEY[item.id]]
|
||||
);
|
||||
|
||||
const bottomItems: NavItem[] = [
|
||||
{ id: "home", label: "Home", icon: <Home size={16} /> },
|
||||
{ id: "settings", label: "Settings", icon: <Settings size={16} /> },
|
||||
];
|
||||
|
||||
function renderItem(item: NavItem) {
|
||||
const isActive = currentView === item.id;
|
||||
const baseClass =
|
||||
"w-8 h-8 flex items-center justify-center rounded-lg transition-colors focus:outline-none focus:ring-2 focus:ring-accent/50";
|
||||
const activeClass = "text-accent";
|
||||
const inactiveClass =
|
||||
"text-text-muted hover:text-text hover:bg-surface-raised";
|
||||
const stubClass = "opacity-40 cursor-not-allowed";
|
||||
|
||||
return (
|
||||
<Tooltip key={item.id} content={item.label} side="right">
|
||||
<button
|
||||
type="button"
|
||||
aria-label={item.label}
|
||||
disabled={item.stub}
|
||||
onClick={() => onNavigate(item.id)}
|
||||
className={`${baseClass} ${isActive ? activeClass : inactiveClass} ${item.stub ? stubClass : ""}`}
|
||||
>
|
||||
{item.icon}
|
||||
</button>
|
||||
</Tooltip>
|
||||
);
|
||||
}
|
||||
|
||||
return (
|
||||
<div className="w-14 h-full bg-canvas border-r border-border flex flex-col items-center py-3 gap-2 shrink-0">
|
||||
<div className="flex flex-col gap-2 flex-1">
|
||||
{visibleTopItems.map(renderItem)}
|
||||
</div>
|
||||
<div className="flex flex-col gap-2">
|
||||
{bottomItems.map(renderItem)}
|
||||
</div>
|
||||
</div>
|
||||
);
|
||||
}
|
||||
Reference in New Issue
Block a user