From c105f414876d116db6a9ec311dd0071568b4241e Mon Sep 17 00:00:00 2001 From: Mikayla Maki Date: Thu, 27 Oct 2022 16:37:54 -0700 Subject: [PATCH] Started working on dock panes co-authored-by: kay@zed.dev --- crates/db/examples/serialize-pane.rs | 22 +++- crates/db/src/pane.rs | 158 +++++++++++++++------------ crates/db/src/workspace.rs | 3 +- 3 files changed, 109 insertions(+), 74 deletions(-) diff --git a/crates/db/examples/serialize-pane.rs b/crates/db/examples/serialize-pane.rs index b0744aa604..9448336be9 100644 --- a/crates/db/examples/serialize-pane.rs +++ b/crates/db/examples/serialize-pane.rs @@ -14,15 +14,25 @@ fn main() -> anyhow::Result<()> { let f = File::create(file)?; drop(f); - let workspace = db.workspace_for_roots(&["/tmp"]); + let workspace_1 = db.workspace_for_roots(&["/tmp"]); + let workspace_2 = db.workspace_for_roots(&["/tmp", "/tmp2"]); + let workspace_3 = db.workspace_for_roots(&["/tmp3", "/tmp2"]); - db.save_dock_pane(SerializedDockPane { - workspace: workspace.workspace_id, + db.save_dock_pane(&SerializedDockPane { + workspace_id: workspace_1.workspace_id, anchor_position: DockAnchor::Expanded, - shown: true, + visible: true, + }); + db.save_dock_pane(&SerializedDockPane { + workspace_id: workspace_2.workspace_id, + anchor_position: DockAnchor::Bottom, + visible: true, + }); + db.save_dock_pane(&SerializedDockPane { + workspace_id: workspace_3.workspace_id, + anchor_position: DockAnchor::Right, + visible: false, }); - - let _new_workspace = db.workspace_for_roots(&["/tmp"]); db.write_to(file).ok(); diff --git a/crates/db/src/pane.rs b/crates/db/src/pane.rs index 23423ed6f6..9a7dfd3b6e 100644 --- a/crates/db/src/pane.rs +++ b/crates/db/src/pane.rs @@ -1,9 +1,69 @@ use gpui::Axis; +use serde::{Deserialize, Serialize}; +use serde_rusqlite::to_params_named; + use crate::{items::ItemId, workspace::WorkspaceId}; use super::Db; +pub(crate) const PANE_M_1: &str = " +CREATE TABLE dock_panes( + dock_pane_id INTEGER PRIMARY KEY, + workspace_id INTEGER NOT NULL, + anchor_position TEXT NOT NULL, -- Enum: 'Bottom' / 'Right' / 'Expanded' + visible INTEGER NOT NULL, -- Boolean + FOREIGN KEY(workspace_id) REFERENCES workspaces(workspace_id) ON DELETE CASCADE +) STRICT; + +CREATE TABLE pane_groups( + group_id INTEGER PRIMARY KEY, + workspace_id INTEGER NOT NULL, + parent_group INTEGER, -- NULL indicates that this is a root node + axis TEXT NOT NULL, -- Enum: 'Vertical' / 'Horizontal' + FOREIGN KEY(workspace_id) REFERENCES workspaces(workspace_id) ON DELETE CASCADE, + FOREIGN KEY(parent_group) REFERENCES pane_groups(group_id) ON DELETE CASCADE +) STRICT; + +CREATE TABLE grouped_panes( + pane_id INTEGER PRIMARY KEY, + workspace_id INTEGER NOT NULL, + group_id INTEGER NOT NULL, + idx INTEGER NOT NULL, + FOREIGN KEY(workspace_id) REFERENCES workspaces(workspace_id) ON DELETE CASCADE, + FOREIGN KEY(group_id) REFERENCES pane_groups(group_id) ON DELETE CASCADE +) STRICT; + +CREATE TABLE items( + item_id INTEGER PRIMARY KEY, + workspace_id INTEGER NOT NULL, + kind TEXT NOT NULL, + FOREIGN KEY(workspace_id) REFERENCES workspaces(workspace_id) ON DELETE CASCADE +) STRICT; + +CREATE TABLE group_items( + workspace_id INTEGER NOT NULL, + pane_id INTEGER NOT NULL, + item_id INTEGER NOT NULL, + idx INTEGER NOT NULL, + PRIMARY KEY (workspace_id, pane_id, item_id) + FOREIGN KEY(workspace_id) REFERENCES workspaces(workspace_id) ON DELETE CASCADE, + FOREIGN KEY(pane_id) REFERENCES grouped_panes(pane_id) ON DELETE CASCADE, + FOREIGN KEY(item_id) REFERENCES items(item_id) ON DELETE CASCADE +) STRICT; + +CREATE TABLE dock_items( + workspace_id INTEGER NOT NULL, + dock_pane_id INTEGER NOT NULL, + item_id INTEGER NOT NULL, + idx INTEGER NOT NULL, + PRIMARY KEY (workspace_id, dock_pane_id, item_id) + FOREIGN KEY(workspace_id) REFERENCES workspaces(workspace_id) ON DELETE CASCADE, + FOREIGN KEY(dock_pane_id) REFERENCES dock_panes(dock_pane_id) ON DELETE CASCADE, + FOREIGN KEY(item_id) REFERENCES items(item_id)ON DELETE CASCADE +) STRICT; +"; + // We have an many-branched, unbalanced tree with three types: // Pane Groups // Panes @@ -74,64 +134,7 @@ pub struct SerializedPane { children: Vec, } -pub(crate) const PANE_M_1: &str = " -CREATE TABLE dock_panes( - dock_pane_id INTEGER PRIMARY KEY, - workspace_id INTEGER NOT NULL, - anchor_position TEXT NOT NULL, -- Enum: 'Bottom' / 'Right' / 'Expanded' - shown INTEGER NOT NULL, -- Boolean - FOREIGN KEY(workspace_id) REFERENCES workspaces(workspace_id) ON DELETE CASCADE -) STRICT; - -CREATE TABLE pane_groups( - group_id INTEGER PRIMARY KEY, - workspace_id INTEGER NOT NULL, - parent_group INTEGER, -- NULL indicates that this is a root node - axis TEXT NOT NULL, -- Enum: 'Vertical' / 'Horizontal' - FOREIGN KEY(workspace_id) REFERENCES workspaces(workspace_id) ON DELETE CASCADE, - FOREIGN KEY(parent_group) REFERENCES pane_groups(group_id) ON DELETE CASCADE -) STRICT; - -CREATE TABLE grouped_panes( - pane_id INTEGER PRIMARY KEY, - workspace_id INTEGER NOT NULL, - group_id INTEGER NOT NULL, - idx INTEGER NOT NULL, - FOREIGN KEY(workspace_id) REFERENCES workspaces(workspace_id) ON DELETE CASCADE, - FOREIGN KEY(group_id) REFERENCES pane_groups(group_id) ON DELETE CASCADE -) STRICT; - -CREATE TABLE items( - item_id INTEGER PRIMARY KEY, - workspace_id INTEGER NOT NULL, - kind TEXT NOT NULL, - FOREIGN KEY(workspace_id) REFERENCES workspaces(workspace_id) ON DELETE CASCADE -) STRICT; - -CREATE TABLE group_items( - workspace_id INTEGER NOT NULL, - pane_id INTEGER NOT NULL, - item_id INTEGER NOT NULL, - idx INTEGER NOT NULL, - PRIMARY KEY (workspace_id, pane_id, item_id) - FOREIGN KEY(workspace_id) REFERENCES workspaces(workspace_id) ON DELETE CASCADE, - FOREIGN KEY(pane_id) REFERENCES grouped_panes(pane_id) ON DELETE CASCADE, - FOREIGN KEY(item_id) REFERENCES items(item_id) ON DELETE CASCADE -) STRICT; - -CREATE TABLE dock_items( - workspace_id INTEGER NOT NULL, - dock_pane_id INTEGER NOT NULL, - item_id INTEGER NOT NULL, - idx INTEGER NOT NULL, - PRIMARY KEY (workspace_id, dock_pane_id, item_id) - FOREIGN KEY(workspace_id) REFERENCES workspaces(workspace_id) ON DELETE CASCADE, - FOREIGN KEY(dock_pane_id) REFERENCES dock_panes(dock_pane_id) ON DELETE CASCADE, - FOREIGN KEY(item_id) REFERENCES items(item_id)ON DELETE CASCADE -) STRICT; -"; - -#[derive(Default, Debug)] +#[derive(Default, Debug, PartialEq, Eq, Deserialize, Serialize)] pub enum DockAnchor { #[default] Bottom, @@ -139,11 +142,11 @@ pub enum DockAnchor { Expanded, } -#[derive(Default, Debug)] +#[derive(Default, Debug, PartialEq, Eq, Deserialize, Serialize)] pub struct SerializedDockPane { - pub workspace: WorkspaceId, + pub workspace_id: WorkspaceId, pub anchor_position: DockAnchor, - pub shown: bool, + pub visible: bool, } impl Db { @@ -204,7 +207,24 @@ impl Db { unimplemented!() } - pub fn save_dock_pane(&self, _dock_pane: SerializedDockPane) {} + pub fn save_dock_pane(&self, dock_pane: &SerializedDockPane) { + to_params_named(dock_pane) + .map_err(|err| dbg!(err)) + .ok() + .zip(self.real()) + .map(|(params, db)| { + // TODO: overwrite old dock panes if need be + let query = "INSERT INTO dock_panes (workspace_id, anchor_position, visible) VALUES (:workspace_id, :anchor_position, :visible);"; + db.connection + .lock() + .execute(query, params.to_slice().as_slice()) + .map(|_| ()) // Eat the return value + .unwrap_or_else(|err| { + dbg!(&err); + log::error!("Failed to insert new workspace into DB: {}", err); + }) + }); + } } #[cfg(test)] @@ -220,12 +240,16 @@ mod tests { let workspace = db.workspace_for_roots(&["/tmp"]); - db.save_dock_pane(SerializedDockPane { - workspace: workspace.workspace_id, + let dock_pane = SerializedDockPane { + workspace_id: workspace.workspace_id, anchor_position: DockAnchor::Expanded, - shown: true, - }); + visible: true, + }; - let _new_workspace = db.workspace_for_roots(&["/tmp"]); + db.save_dock_pane(&dock_pane); + + let new_workspace = db.workspace_for_roots(&["/tmp"]); + + assert_eq!(new_workspace.dock_pane.unwrap(), dock_pane); } } diff --git a/crates/db/src/workspace.rs b/crates/db/src/workspace.rs index cb2d4296c1..d7532b684e 100644 --- a/crates/db/src/workspace.rs +++ b/crates/db/src/workspace.rs @@ -1,5 +1,6 @@ use anyhow::Result; use rusqlite::{params, Connection, OptionalExtension}; +use serde::{Deserialize, Serialize}; use std::{ ffi::OsStr, @@ -30,7 +31,7 @@ CREATE TABLE worktree_roots( ) STRICT; "; -#[derive(Debug, PartialEq, Eq, Copy, Clone, Default)] +#[derive(Debug, PartialEq, Eq, Copy, Clone, Default, Deserialize, Serialize)] pub struct WorkspaceId(i64); #[derive(Default, Debug)]