@@ -3,19 +3,22 @@ use crate::conventional::commit::Commit;
33use crate :: git:: error:: TagError ;
44use crate :: git:: oid:: OidOf ;
55
6+ use crate :: conventional:: error:: BumpError as ConvBumpError ;
67use crate :: conventional:: version:: IncrementCommand ;
7- use crate :: git:: tag:: Tag ;
8+ use crate :: git:: repository:: Repository ;
9+ use crate :: git:: tag:: { Tag , TagLookUpOptions } ;
810use crate :: hook:: { Hook , HookVersion , Hooks } ;
911use crate :: settings:: { HookType , MonoRepoPackage , Settings } ;
1012use crate :: BumpError ;
1113use crate :: { CocoGitto , COMMITS_METADATA , SETTINGS } ;
1214use anyhow:: Result ;
13- use anyhow:: { anyhow , bail, ensure, Context } ;
15+ use anyhow:: { bail, ensure, Context } ;
1416use colored:: Colorize ;
1517use conventional_commit_parser:: commit:: CommitType ;
1618use globset:: Glob ;
1719use itertools:: Itertools ;
1820use log:: { error, info, warn} ;
21+ use semver:: { BuildMetadata , Prerelease } ;
1922use std:: default:: Default ;
2023use std:: fmt;
2124use std:: fmt:: Write ;
@@ -55,6 +58,83 @@ pub struct PackageBumpOptions<'a> {
5558pub disable_bump_commit : bool ,
5659}
5760
61+ struct BumpResult {
62+ current : Tag ,
63+ next : Tag ,
64+ had_commits : bool ,
65+ }
66+
67+ impl BumpResult {
68+ fn no_change ( & self ) ->bool {
69+ self . current . version ==self . next . version
70+ }
71+ }
72+
73+ impl < ' a > BumpOptions < ' a > {
74+ fn get_new_version (
75+ & self ,
76+ repository : & Repository ,
77+ package : Option < & str > ,
78+ allow_empty : bool ,
79+ increment : Option < IncrementCommand > ,
80+ ) ->Result < BumpResult > {
81+ let tag_opts = package. map ( TagLookUpOptions :: package) . unwrap_or_default ( ) ;
82+ let current =match repository. get_latest_tag ( tag_opts) {
83+ Ok ( tag) => tag,
84+ Err ( TagError :: NoTag ) =>Tag :: default ( ) ,
85+ Err ( other) =>bail ! ( other) ,
86+ } ;
87+
88+ let increment = increment. unwrap_or_else ( ||self . increment . clone ( ) ) ;
89+ let ( mut next, had_commits) =match current. bump ( increment, repository) {
90+ Ok ( tag) =>( tag, true ) ,
91+ Err ( ConvBumpError :: NoCommitFound ) if allow_empty =>( current. strip_metadata ( ) , false ) ,
92+ Err ( other) =>bail ! ( other) ,
93+ } ;
94+
95+ if let Some ( pre_release) =self . pre_release {
96+ next. version . pre =Prerelease :: new ( pre_release) ?;
97+ }
98+
99+ if let Some ( build) =self . build {
100+ next. version . build =BuildMetadata :: new ( build) ?;
101+ }
102+
103+ // ensure version doesn't decrease
104+ if next < current{
105+ bail ! (
106+ "{}:\n \t {} version MUST be greater than current one: {}\n " ,
107+ "SemVer Error" . red( ) ,
108+ "cause:" . red( ) ,
109+ format!( "{next} <= {current}" ) . red( ) ,
110+ ) ;
111+ }
112+
113+ Ok ( BumpResult {
114+ current,
115+ next,
116+ had_commits,
117+ } )
118+ }
119+ }
120+
121+ impl < ' a > PackageBumpOptions < ' a > {
122+ fn common ( & self ) ->BumpOptions < ' a > {
123+ BumpOptions {
124+ increment : self . increment . clone ( ) ,
125+ pre_release : self . pre_release ,
126+ build : self . build ,
127+ hooks_config : self . hooks_config ,
128+ annotated : self . annotated . clone ( ) ,
129+ dry_run : self . dry_run ,
130+ skip_ci : self . skip_ci ,
131+ skip_ci_override : self . skip_ci_override . clone ( ) ,
132+ skip_untracked : self . skip_untracked ,
133+ disable_bump_commit : self . disable_bump_commit ,
134+ }
135+ }
136+ }
137+
58138struct HookRunOptions < ' a > {
59139hook_type : HookType ,
60140current_tag : Option < & ' a HookVersion > ,
@@ -121,25 +201,6 @@ impl<'a> HookRunOptions<'a> {
121201}
122202}
123203
124- fn ensure_tag_is_greater_than_previous ( current : & Tag , next : & Tag ) ->Result < ( ) > {
125- if next < current{
126- let comparison =format ! ( "{current} <= {next}" ) . red ( ) ;
127- let cause_key ="cause:" . red ( ) ;
128- let cause =format ! ( "{cause_key} version MUST be greater than current one: {comparison}" ) ;
129- bail ! ( "{}:\n \t {}\n " , "SemVer Error" . red( ) , cause) ;
130- } ;
131-
132- Ok ( ( ) )
133- }
134-
135- fn tag_or_fallback_to_zero ( tag : Result < Tag , TagError > ) ->Result < Tag > {
136- match tag{
137- Ok ( ref tag) =>Ok ( tag. clone ( ) ) ,
138- Err ( TagError :: NoTag ) =>Ok ( Tag :: default ( ) ) ,
139- Err ( err) =>Err ( anyhow ! ( err) ) ,
140- }
141- }
142-
143204impl CocoGitto {
144205fn get_bump_revspec ( & mut self , current_tag : & Tag ) ->String {
145206if current_tag. is_zero ( ) {