11use std:: process;
22
3+ use colored:: Colorize as _;
4+
35use crate :: {
46 commands:: help,
57 fail,
68 flags:: { is_valid_flag, Flag } ,
7- git_commands:: is_valid_branch_name,
9+ git_commands:: { fetch_branch, is_valid_branch_name, GIT } ,
10+ success,
811 types:: CommandArgs ,
912} ;
1013
@@ -29,23 +32,23 @@ pub struct Item {
2932 /// # Examples
3033 ///
3134 /// helix-editor/helix
32- repo : String ,
35+ pub repo : String ,
3336 /// # Examples
3437 ///
3538 /// master
36- branch : String ,
39+ pub branch : String ,
3740 /// If specified, use a custom branch name instead of a generated one
3841 ///
3942 /// # Examples
4043 ///
4144 /// my-custom-branch123
42- local_branch_name : Option < String > ,
45+ pub local_branch_name : Option < String > ,
4346 /// If specified, do a **hard reset** to this commit when fetching the branch
4447 ///
4548 /// # Examples
4649 ///
4750 /// 6049f2035
48- commit_hash : Option < String > ,
51+ pub commit_hash : Option < String > ,
4952}
5053
5154impl Item {
@@ -76,14 +79,25 @@ Valid format is: username/repo/branch. Example: helix-editor/helix/master",
7679
7780 Ok ( Self :: new ( repo. to_owned ( ) , branch. to_owned ( ) , None , hash) )
7881 }
82+
83+ #[ must_use]
84+ pub fn with_branch_name ( mut self , branch_name : Option < String > ) -> Self {
85+ self . local_branch_name = branch_name;
86+ self
87+ }
7988}
8089
81- pub fn branch_fetch ( args : & CommandArgs ) {
90+ pub async fn branch_fetch ( args : & CommandArgs ) -> anyhow:: Result < ( ) > {
91+ if args. is_empty ( ) {
92+ let _ = help ( Some ( "branch-fetch" ) ) ;
93+ process:: exit ( 1 ) ;
94+ }
95+
8296 let has_checkout_flag = BRANCH_FETCH_CHECKOUT_FLAG . is_in ( args) ;
8397
8498 let mut args = args. iter ( ) . peekable ( ) ;
8599
86- let mut branches_with_maybe_custom_names = vec ! [ ] ;
100+ let mut items = vec ! [ ] ;
87101
88102 let mut no_more_flags = false ;
89103
@@ -105,11 +119,7 @@ pub fn branch_fetch(args: &CommandArgs) {
105119 continue ;
106120 }
107121
108- let ( remote, hash) = parse_if_maybe_hash ( arg, "@" ) ;
109-
110- let Some ( ( repo, branch) ) = remote. rsplit_once ( '/' ) else {
111- fail ! ( "Invalid format: {}, skipping. Valid format is: username/repo/branch. Example: helix-editor/helix/master" , remote) ;
112-
122+ let Ok ( item) = Item :: create ( arg) . map_err ( |err| fail ! ( "{err}" ) ) else {
113123 continue ;
114124 } ;
115125
@@ -124,13 +134,51 @@ pub fn branch_fetch(args: &CommandArgs) {
124134 args. next ( ) ;
125135 } ;
126136
127- branches_with_maybe_custom_names. push ( Item :: new (
128- repo. to_owned ( ) ,
129- branch. to_owned ( ) ,
130- maybe_custom_branch_name,
131- hash,
132- ) ) ;
137+ let item = item. with_branch_name ( maybe_custom_branch_name) ;
138+
139+ items. push ( item) ;
133140 }
134141
135142 let client = reqwest:: Client :: new ( ) ;
143+
144+ for ( i, item) in items. into_iter ( ) . enumerate ( ) {
145+ let hash = item. commit_hash . clone ( ) ;
146+ let repo = item. repo . clone ( ) ;
147+ match fetch_branch ( item, & client) . await {
148+ Ok ( ( _, info) ) => {
149+ success ! (
150+ "Fetched branch {}/{} available at branch {}{}" ,
151+ repo,
152+ info. branch. upstream_branch_name,
153+ info. branch. local_branch_name. bright_cyan( ) ,
154+ hash. map( |commit_hash| format!( ", at commit {}" , commit_hash. bright_yellow( ) ) )
155+ . unwrap_or_default( )
156+ ) ;
157+
158+ // Attempt to cleanup after ourselves
159+ let _ = GIT ( & [ "remote" , "remove" , & info. remote . local_remote_alias ] ) ;
160+
161+ // If user uses --checkout flag, we're going to checkout the first fetched branch
162+ if i == 0 && has_checkout_flag {
163+ if let Err ( cant_checkout) = GIT ( & [ "checkout" , & info. branch . local_branch_name ] ) {
164+ fail ! (
165+ "Could not check out branch {}:\n {cant_checkout}" ,
166+ info. branch. local_branch_name
167+ ) ;
168+ } else {
169+ success ! (
170+ "Automatically checked out the first branch: {}" ,
171+ info. branch. local_branch_name
172+ ) ;
173+ }
174+ }
175+ }
176+ Err ( err) => {
177+ fail ! ( "{err}" ) ;
178+ continue ;
179+ }
180+ } ;
181+ }
182+
183+ Ok ( ( ) )
136184}
0 commit comments