Skip to content

Commit 09b56c0

Browse files
Swann HERRERAjunglerobba
andcommitted
Add config option for listing worktrees for bare repositories
Also adds a check to set_up_tmux_env so that when opening a worktree directly, the main repo's other worktrees won't be opened as windows. Since we're opening one directly, the assumption is that we specificially want only the one selected. Co-authored-by: junglerobba <junglerobba@jngl.one>
1 parent 128f6bb commit 09b56c0

File tree

6 files changed

+83
-20
lines changed

6 files changed

+83
-20
lines changed

README.md

Lines changed: 16 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -67,7 +67,7 @@ a provided `session_name`.
6767
Use `tms --help`
6868

6969
```
70-
Scan for all git folders in specified directorires, select one and open it as a new tmux session
70+
Scan for all git folders in specified directories, select one and open it as a new tmux session
7171
7272
Usage: tms [COMMAND]
7373
@@ -98,6 +98,11 @@ Options:
9898
Configure the defaults for search paths and excluded directories
9999
100100
Usage: tms config [OPTIONS]
101+
tms config <COMMAND>
102+
103+
Commands:
104+
list List current config including all default values
105+
help Print this message or the help of the given subcommand(s)
101106
102107
Options:
103108
-p, --paths <search paths>...
@@ -121,15 +126,23 @@ Options:
121126
--picker-highlight-color <#rrggbb>
122127
Background color of the highlighted item in the picker
123128
--picker-highlight-text-color <#rrggbb>
124-
Text color of the hightlighted item in the picker
129+
Text color of the highlighted item in the picker
125130
--picker-border-color <#rrggbb>
126131
Color of the borders between widgets in the picker
127132
--picker-info-color <#rrggbb>
128133
Color of the item count in the picker
129134
--picker-prompt-color <#rrggbb>
130135
Color of the prompt in the picker
131-
--session-sort-order <Alphabetical | LastAttach>
136+
--session-sort-order <Alphabetical | LastAttached>
132137
Set the sort order of the sessions in the switch command [possible values: Alphabetical, LastAttached]
138+
--clone-repo-switch <Always | Never | Foreground>
139+
Whether to automatically switch to the new session after the `clone-repo` command finishes
140+
`Always` will always switch tmux to the new session
141+
`Never` will always create the new session in the background
142+
When set to `Foreground`, the new session will only be opened in the background if the active
143+
tmux session has changed since starting the clone process (for long clone processes on larger repos) [possible values: Always, Never, Foreground]
144+
--enable-list-worktrees <true | false>
145+
Enable listing of woktrees for bare repositories [possible values: true, false]
133146
-h, --help
134147
Print help
135148
```

src/cli.rs

Lines changed: 9 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -26,7 +26,7 @@ use ratatui::style::Color;
2626

2727
#[derive(Debug, Parser)]
2828
#[command(author, version)]
29-
///Scan for all git folders in specified directorires, select one and open it as a new tmux session
29+
///Scan for all git folders in specified directories, select one and open it as a new tmux session
3030
pub struct Cli {
3131
#[command(subcommand)]
3232
command: Option<CliCommand>,
@@ -120,7 +120,7 @@ pub struct ConfigArgs {
120120
/// Background color of the highlighted item in the picker
121121
picker_highlight_color: Option<Color>,
122122
#[arg(long, value_name = "#rrggbb")]
123-
/// Text color of the hightlighted item in the picker
123+
/// Text color of the highlighted item in the picker
124124
picker_highlight_text_color: Option<Color>,
125125
#[arg(long, value_name = "#rrggbb")]
126126
/// Color of the borders between widgets in the picker
@@ -141,6 +141,9 @@ pub struct ConfigArgs {
141141
/// When set to `Foreground`, the new session will only be opened in the background if the active
142142
/// tmux session has changed since starting the clone process (for long clone processes on larger repos)
143143
clone_repo_switch: Option<CloneRepoSwitchConfig>,
144+
#[arg(long, value_name = "true | false")]
145+
/// Enable listing of woktrees for bare repositories
146+
enable_list_worktrees: Option<bool>,
144147
}
145148

146149
#[derive(Debug, Args)]
@@ -428,6 +431,10 @@ fn config_command(cmd: &ConfigCommand, mut config: Config) -> Result<()> {
428431
config.switch_filter_unknown = Some(switch_filter_unknown.to_owned());
429432
}
430433

434+
if let Some(enable_list_worktrees) = args.enable_list_worktrees {
435+
config.list_worktrees = Some(enable_list_worktrees.to_owned());
436+
}
437+
431438
if let Some(dirs) = &args.excluded_dirs {
432439
let current_excluded = config.excluded_dirs;
433440
match current_excluded {

src/configs.rs

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -54,6 +54,7 @@ pub struct Config {
5454
pub marks: Option<HashMap<String, String>>,
5555
pub clone_repo_switch: Option<CloneRepoSwitchConfig>,
5656
pub vcs_providers: Option<Vec<VcsProviders>>,
57+
pub list_worktrees: Option<bool>,
5758
}
5859

5960
pub const DEFAULT_VCS_PROVIDERS: &[VcsProviders] = &[VcsProviders::Git];

src/repos.rs

Lines changed: 53 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -10,7 +10,7 @@ use jj_lib::{
1010
workspace::{WorkingCopyFactories, Workspace},
1111
};
1212
use std::{
13-
collections::{HashMap, VecDeque},
13+
collections::{HashMap, HashSet, VecDeque},
1414
fs::{self},
1515
path::{Path, PathBuf},
1616
process::{self, Stdio},
@@ -240,22 +240,20 @@ impl RepoProvider {
240240
.collect()),
241241

242242
RepoProvider::Jujutsu(workspace) => {
243+
let repo = workspace
244+
.repo_loader()
245+
.load_at_head()
246+
.change_context(TmsError::GitError)?;
247+
let mut workspaces: HashSet<&str> = HashSet::from_iter(
248+
repo.view()
249+
.wc_commit_ids()
250+
.keys()
251+
.filter(|name| name.as_str() != workspace.workspace_name().as_str())
252+
.map(|buf| buf.as_str()),
253+
);
243254
let mut repos: Vec<RepoProvider> = Vec::new();
244255

245-
search_dirs(config, |_, repo| {
246-
if !repo.is_worktree() {
247-
return Ok(());
248-
}
249-
let Some(path) = repo.main_repo() else {
250-
return Ok(());
251-
};
252-
if workspace.repo_path() == path {
253-
repos.push(repo);
254-
}
255-
Ok(())
256-
})?;
257-
258-
if self.is_bare() {
256+
if self.is_bare() && !workspaces.is_empty() {
259257
if let Ok(read_dir) = fs::read_dir(self.path()) {
260258
let mut sub = read_dir
261259
.filter_map(|entry| entry.ok())
@@ -268,10 +266,30 @@ impl RepoProvider {
268266
.is_some_and(|main| main == self.path().join(".jj/repo"))
269267
})
270268
.collect::<Vec<_>>();
269+
for repo in &sub {
270+
if let RepoProvider::Jujutsu(ws) = repo {
271+
workspaces.remove(ws.workspace_name().as_str());
272+
}
273+
}
271274
repos.append(&mut sub);
272275
}
273276
}
274277

278+
if !workspaces.is_empty() {
279+
search_dirs(config, |_, repo| {
280+
if !repo.is_worktree() {
281+
return Ok(());
282+
}
283+
let Some(path) = repo.main_repo() else {
284+
return Ok(());
285+
};
286+
if workspace.repo_path() == path {
287+
repos.push(repo);
288+
}
289+
Ok(())
290+
})?;
291+
}
292+
275293
let repos = repos
276294
.into_iter()
277295
.filter_map(|repo| match repo {
@@ -302,6 +320,26 @@ pub fn find_repos(config: &Config) -> Result<HashMap<String, Vec<Session>>> {
302320
})?
303321
.to_string()?;
304322

323+
if let Some(true) = config.list_worktrees {
324+
for worktree in repo.worktrees(config)?.iter() {
325+
let Ok(sub) = worktree
326+
.path()
327+
.and_then(|path| RepoProvider::open(&path, config))
328+
else {
329+
continue;
330+
};
331+
let session = Session::new(
332+
format!("{}#{}", session_name, worktree.name()),
333+
SessionType::Git(sub),
334+
);
335+
if let Some(list) = repos.get_mut(&session.name) {
336+
list.push(session);
337+
} else {
338+
repos.insert(session.name.clone(), vec![session]);
339+
}
340+
}
341+
}
342+
305343
let session = Session::new(session_name, SessionType::Git(repo));
306344
if let Some(list) = repos.get_mut(&session.name) {
307345
list.push(session);

src/tmux.rs

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -255,6 +255,9 @@ impl Tmux {
255255
repo_name: &str,
256256
config: &Config,
257257
) -> Result<()> {
258+
if repo.is_worktree() {
259+
return Ok(());
260+
}
258261
let worktrees = repo.worktrees(config).change_context(TmsError::GitError)?;
259262
let worktrees = worktrees
260263
.iter()

tests/cli.rs

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -69,6 +69,7 @@ fn tms_config() -> anyhow::Result<()> {
6969
clone_repo_switch: Some(CloneRepoSwitchConfig::Always),
7070
vcs_providers: None,
7171
input_position: None,
72+
list_worktrees: None,
7273
};
7374

7475
let mut tms = Command::cargo_bin("tms")?;

0 commit comments

Comments
 (0)