@@ -12,7 +12,7 @@ use std::io::Write;
1212pub struct Config < ' a > {
1313 pub dry_run : bool ,
1414 pub force_author : bool ,
15- pub force : bool ,
15+ pub force_detach : bool ,
1616 pub base : Option < & ' a str > ,
1717 pub and_rebase : bool ,
1818 pub whole_file : bool ,
@@ -28,9 +28,13 @@ pub fn run(logger: &slog::Logger, config: &Config) -> Result<()> {
2828
2929fn run_with_repo ( logger : & slog:: Logger , config : & Config , repo : & git2:: Repository ) -> Result < ( ) > {
3030 let config = config:: unify ( & config, repo) ;
31- // have force flag enable all force* flags
32-
33- let stack = stack:: working_stack ( repo, config. base , config. force_author , config. force , logger) ?;
31+ let stack = stack:: working_stack (
32+ repo,
33+ config. base ,
34+ config. force_author ,
35+ config. force_detach ,
36+ logger,
37+ ) ?;
3438 if stack. is_empty ( ) {
3539 crit ! ( logger, "No commits available to fix up, exiting" ) ;
3640 return Ok ( ( ) ) ;
@@ -521,7 +525,7 @@ mod tests {
521525 fn foreign_author ( ) {
522526 let ctx = repo_utils:: prepare_and_stage ( ) ;
523527
524- repo_utils:: become_new_author ( & ctx) ;
528+ repo_utils:: become_new_author ( & ctx. repo ) ;
525529
526530 // run 'git-absorb'
527531 let drain = slog:: Discard ;
@@ -539,7 +543,7 @@ mod tests {
539543 fn foreign_author_with_force_author_flag ( ) {
540544 let ctx = repo_utils:: prepare_and_stage ( ) ;
541545
542- repo_utils:: become_new_author ( & ctx) ;
546+ repo_utils:: become_new_author ( & ctx. repo ) ;
543547
544548 // run 'git-absorb'
545549 let drain = slog:: Discard ;
@@ -558,48 +562,104 @@ mod tests {
558562 }
559563
560564 #[ test]
561- fn foreign_author_with_force_flag ( ) {
565+ fn foreign_author_with_force_author_config ( ) {
562566 let ctx = repo_utils:: prepare_and_stage ( ) ;
563567
564- repo_utils:: become_new_author ( & ctx) ;
568+ repo_utils:: become_new_author ( & ctx. repo ) ;
569+
570+ repo_utils:: set_config_flag ( & ctx. repo , "absorb.forceAuthor" ) ;
571+
572+ // run 'git-absorb'
573+ let drain = slog:: Discard ;
574+ let logger = slog:: Logger :: root ( drain, o ! ( ) ) ;
575+ run_with_repo ( & logger, & DEFAULT_CONFIG , & ctx. repo ) . unwrap ( ) ;
576+
577+ let mut revwalk = ctx. repo . revwalk ( ) . unwrap ( ) ;
578+ revwalk. push_head ( ) . unwrap ( ) ;
579+ assert_eq ! ( revwalk. count( ) , 3 ) ;
580+
581+ assert ! ( nothing_left_in_index( & ctx. repo) . unwrap( ) ) ;
582+ }
583+
584+ #[ test]
585+ fn detached_head ( ) {
586+ let ctx = repo_utils:: prepare_and_stage ( ) ;
587+ repo_utils:: detach_head ( & ctx. repo ) ;
588+
589+ // run 'git-absorb'
590+ let drain = slog:: Discard ;
591+ let logger = slog:: Logger :: root ( drain, o ! ( ) ) ;
592+ let result = run_with_repo ( & logger, & DEFAULT_CONFIG , & ctx. repo ) ;
593+ assert_eq ! (
594+ result. err( ) . unwrap( ) . to_string( ) ,
595+ "HEAD is not a branch, use --force-detach to override"
596+ ) ;
597+
598+ let mut revwalk = ctx. repo . revwalk ( ) . unwrap ( ) ;
599+ revwalk. push_head ( ) . unwrap ( ) ;
600+ assert_eq ! ( revwalk. count( ) , 1 ) ;
601+ let is_something_in_index = !nothing_left_in_index ( & ctx. repo ) . unwrap ( ) ;
602+ assert ! ( is_something_in_index) ;
603+ }
604+
605+ #[ test]
606+ fn detached_head_pointing_at_branch_with_force_detach_flag ( ) {
607+ let ctx = repo_utils:: prepare_and_stage ( ) ;
608+ repo_utils:: detach_head ( & ctx. repo ) ;
565609
566610 // run 'git-absorb'
567611 let drain = slog:: Discard ;
568612 let logger = slog:: Logger :: root ( drain, o ! ( ) ) ;
569613 let config = Config {
570- force : true ,
614+ force_detach : true ,
571615 ..DEFAULT_CONFIG
572616 } ;
573617 run_with_repo ( & logger, & config, & ctx. repo ) . unwrap ( ) ;
618+ let mut revwalk = ctx. repo . revwalk ( ) . unwrap ( ) ;
619+ revwalk. push_head ( ) . unwrap ( ) ;
620+
621+ assert_eq ! ( revwalk. count( ) , 1 ) ; // nothing was committed
622+ let is_something_in_index = !nothing_left_in_index ( & ctx. repo ) . unwrap ( ) ;
623+ assert ! ( is_something_in_index) ;
624+ }
574625
626+ #[ test]
627+ fn detached_head_with_force_detach_flag ( ) {
628+ let ctx = repo_utils:: prepare_and_stage ( ) ;
629+ repo_utils:: detach_head ( & ctx. repo ) ;
630+ repo_utils:: delete_branch ( & ctx. repo , "master" ) ;
631+
632+ // run 'git-absorb'
633+ let drain = slog:: Discard ;
634+ let logger = slog:: Logger :: root ( drain, o ! ( ) ) ;
635+ let config = Config {
636+ force_detach : true ,
637+ ..DEFAULT_CONFIG
638+ } ;
639+ run_with_repo ( & logger, & config, & ctx. repo ) . unwrap ( ) ;
575640 let mut revwalk = ctx. repo . revwalk ( ) . unwrap ( ) ;
576641 revwalk. push_head ( ) . unwrap ( ) ;
577- assert_eq ! ( revwalk. count( ) , 3 ) ;
578642
643+ assert_eq ! ( revwalk. count( ) , 3 ) ;
579644 assert ! ( nothing_left_in_index( & ctx. repo) . unwrap( ) ) ;
580645 }
581646
582647 #[ test]
583- fn foreign_author_with_force_author_config ( ) {
648+ fn detached_head_with_force_detach_config ( ) {
584649 let ctx = repo_utils:: prepare_and_stage ( ) ;
650+ repo_utils:: detach_head ( & ctx. repo ) ;
651+ repo_utils:: delete_branch ( & ctx. repo , "master" ) ;
585652
586- repo_utils:: become_new_author ( & ctx) ;
587-
588- ctx. repo
589- . config ( )
590- . unwrap ( )
591- . set_str ( "absorb.forceAuthor" , "true" )
592- . unwrap ( ) ;
653+ repo_utils:: set_config_flag ( & ctx. repo , "absorb.forceDetach" ) ;
593654
594655 // run 'git-absorb'
595656 let drain = slog:: Discard ;
596657 let logger = slog:: Logger :: root ( drain, o ! ( ) ) ;
597658 run_with_repo ( & logger, & DEFAULT_CONFIG , & ctx. repo ) . unwrap ( ) ;
598-
599659 let mut revwalk = ctx. repo . revwalk ( ) . unwrap ( ) ;
600660 revwalk. push_head ( ) . unwrap ( ) ;
601- assert_eq ! ( revwalk. count( ) , 3 ) ;
602661
662+ assert_eq ! ( revwalk. count( ) , 3 ) ;
603663 assert ! ( nothing_left_in_index( & ctx. repo) . unwrap( ) ) ;
604664 }
605665
@@ -725,7 +785,7 @@ mod tests {
725785 const DEFAULT_CONFIG : Config = Config {
726786 dry_run : false ,
727787 force_author : false ,
728- force : false ,
788+ force_detach : false ,
729789 base : None ,
730790 and_rebase : false ,
731791 whole_file : false ,
0 commit comments