jj_repository.rs

 1use std::path::Path;
 2use std::sync::Arc;
 3
 4use anyhow::Result;
 5use gpui::SharedString;
 6use jj_lib::config::StackedConfig;
 7use jj_lib::repo::StoreFactories;
 8use jj_lib::settings::UserSettings;
 9use jj_lib::workspace::{self, DefaultWorkspaceLoaderFactory, WorkspaceLoaderFactory};
10
11#[derive(Debug, Clone)]
12pub struct Bookmark {
13    pub ref_name: SharedString,
14}
15
16pub trait JujutsuRepository: Send + Sync {
17    fn list_bookmarks(&self) -> Vec<Bookmark>;
18}
19
20pub struct RealJujutsuRepository {
21    repository: Arc<jj_lib::repo::ReadonlyRepo>,
22}
23
24impl RealJujutsuRepository {
25    pub fn new(cwd: &Path) -> Result<Self> {
26        let workspace_loader_factory = DefaultWorkspaceLoaderFactory;
27        let workspace_loader = workspace_loader_factory.create(Self::find_workspace_dir(cwd))?;
28
29        let config = StackedConfig::with_defaults();
30        let settings = UserSettings::from_config(config)?;
31
32        let workspace = workspace_loader.load(
33            &settings,
34            &StoreFactories::default(),
35            &workspace::default_working_copy_factories(),
36        )?;
37
38        let repo_loader = workspace.repo_loader();
39        let repository = repo_loader.load_at_head()?;
40
41        Ok(Self { repository })
42    }
43
44    fn find_workspace_dir(cwd: &Path) -> &Path {
45        cwd.ancestors()
46            .find(|path| path.join(".jj").is_dir())
47            .unwrap_or(cwd)
48    }
49}
50
51impl JujutsuRepository for RealJujutsuRepository {
52    fn list_bookmarks(&self) -> Vec<Bookmark> {
53        self.repository
54            .view()
55            .bookmarks()
56            .map(|(ref_name, _target)| Bookmark {
57                ref_name: ref_name.as_str().to_string().into(),
58            })
59            .collect()
60    }
61}
62
63pub struct FakeJujutsuRepository {}
64
65impl JujutsuRepository for FakeJujutsuRepository {
66    fn list_bookmarks(&self) -> Vec<Bookmark> {
67        Vec::new()
68    }
69}