@@ -18,6 +18,8 @@ pub struct Context<W> {
18
18
pub ignore_bots : bool ,
19
19
/// Show personally identifiable information before the summary. Includes names and email addresses.
20
20
pub show_pii : bool ,
21
+ /// Collect additional information like tree changes and changed lines.
22
+ pub stats : bool ,
21
23
/// Omit unifying identities by name and email which can lead to the same author appear multiple times
22
24
/// due to using different names or email addresses.
23
25
pub omit_unify_identities : bool ,
@@ -38,6 +40,7 @@ pub fn estimate<W, P>(
38
40
Context {
39
41
show_pii,
40
42
ignore_bots,
43
+ stats : _,
41
44
omit_unify_identities,
42
45
mut out,
43
46
} : Context < W > ,
@@ -52,80 +55,77 @@ where
52
55
53
56
let ( all_commits, is_shallow) = {
54
57
let mut progress = progress. add_child ( "Traverse commit graph" ) ;
55
- let string_heap = & mut string_heap;
56
- std:: thread:: scope (
57
- move |scope| -> anyhow:: Result < ( Vec < actor:: SignatureRef < ' static > > , bool ) > {
58
- let start = Instant :: now ( ) ;
59
- progress. init ( None , progress:: count ( "commits" ) ) ;
60
- let ( tx, rx) = std:: sync:: mpsc:: channel :: < Vec < u8 > > ( ) ;
61
- let mailmap = repo. open_mailmap ( ) ;
58
+ std:: thread:: scope ( |scope| -> anyhow:: Result < ( Vec < actor:: SignatureRef < ' static > > , bool ) > {
59
+ let start = Instant :: now ( ) ;
60
+ progress. init ( None , progress:: count ( "commits" ) ) ;
61
+ let ( tx, rx) = std:: sync:: mpsc:: channel :: < Vec < u8 > > ( ) ;
62
+ let mailmap = repo. open_mailmap ( ) ;
62
63
63
- let handle = scope. spawn ( move || -> anyhow:: Result < Vec < actor:: SignatureRef < ' static > > > {
64
- let mut out = Vec :: new ( ) ;
65
- for commit_data in rx {
66
- if let Some ( author) = objs:: CommitRefIter :: from_bytes ( & commit_data)
67
- . author ( )
68
- . map ( |author| mailmap. resolve_cow ( author. trim ( ) ) )
69
- . ok ( )
70
- {
71
- let mut string_ref = |s : & [ u8 ] | -> & ' static BStr {
72
- match string_heap. get ( s) {
73
- Some ( n) => n. as_bstr ( ) ,
74
- None => {
75
- let sv: Vec < u8 > = s. to_owned ( ) . into ( ) ;
76
- string_heap. insert ( Box :: leak ( sv. into_boxed_slice ( ) ) ) ;
77
- ( * string_heap. get ( s) . expect ( "present" ) ) . as_ref ( )
78
- }
64
+ let handle = scope. spawn ( move || -> anyhow:: Result < Vec < actor:: SignatureRef < ' static > > > {
65
+ let mut out = Vec :: new ( ) ;
66
+ for commit_data in rx {
67
+ if let Some ( author) = objs:: CommitRefIter :: from_bytes ( & commit_data)
68
+ . author ( )
69
+ . map ( |author| mailmap. resolve_cow ( author. trim ( ) ) )
70
+ . ok ( )
71
+ {
72
+ let mut string_ref = |s : & [ u8 ] | -> & ' static BStr {
73
+ match string_heap. get ( s) {
74
+ Some ( n) => n. as_bstr ( ) ,
75
+ None => {
76
+ let sv: Vec < u8 > = s. to_owned ( ) . into ( ) ;
77
+ string_heap. insert ( Box :: leak ( sv. into_boxed_slice ( ) ) ) ;
78
+ ( * string_heap. get ( s) . expect ( "present" ) ) . as_ref ( )
79
79
}
80
- } ;
81
- let name = string_ref ( author. name . as_ref ( ) ) ;
82
- let email = string_ref ( & author. email . as_ref ( ) ) ;
80
+ }
81
+ } ;
82
+ let name = string_ref ( author. name . as_ref ( ) ) ;
83
+ let email = string_ref ( & author. email . as_ref ( ) ) ;
83
84
84
- out. push ( actor:: SignatureRef {
85
- name,
86
- email,
87
- time : author. time ,
88
- } ) ;
89
- }
85
+ out. push ( actor:: SignatureRef {
86
+ name,
87
+ email,
88
+ time : author. time ,
89
+ } ) ;
90
90
}
91
- out. shrink_to_fit ( ) ;
92
- out. sort_by ( |a, b| {
93
- a. email . cmp ( & b. email ) . then (
94
- a. time
95
- . seconds_since_unix_epoch
96
- . cmp ( & b. time . seconds_since_unix_epoch )
97
- . reverse ( ) ,
98
- )
99
- } ) ;
100
- Ok ( out)
91
+ }
92
+ out. shrink_to_fit ( ) ;
93
+ out. sort_by ( |a, b| {
94
+ a. email . cmp ( & b. email ) . then (
95
+ a. time
96
+ . seconds_since_unix_epoch
97
+ . cmp ( & b. time . seconds_since_unix_epoch )
98
+ . reverse ( ) ,
99
+ )
101
100
} ) ;
101
+ Ok ( out)
102
+ } ) ;
102
103
103
- let commit_iter = interrupt:: Iter :: new (
104
- commit_id. ancestors ( |oid, buf| {
105
- progress. inc ( ) ;
106
- repo. objects . find ( oid, buf) . map ( |o| {
107
- tx. send ( o. data . to_owned ( ) ) . ok ( ) ;
108
- objs:: CommitRefIter :: from_bytes ( o. data )
109
- } )
110
- } ) ,
111
- || anyhow ! ( "Cancelled by user" ) ,
112
- ) ;
113
- let mut is_shallow = false ;
114
- for c in commit_iter {
115
- match c? {
116
- Ok ( c) => c,
117
- Err ( git:: traverse:: commit:: ancestors:: Error :: FindExisting { .. } ) => {
118
- is_shallow = true ;
119
- break ;
120
- }
121
- Err ( err) => return Err ( err. into ( ) ) ,
122
- } ;
123
- }
124
- drop ( tx) ;
125
- progress. show_throughput ( start) ;
126
- Ok ( ( handle. join ( ) . expect ( "no panic" ) ?, is_shallow) )
127
- } ,
128
- ) ?
104
+ let commit_iter = interrupt:: Iter :: new (
105
+ commit_id. ancestors ( |oid, buf| {
106
+ progress. inc ( ) ;
107
+ repo. objects . find ( oid, buf) . map ( |o| {
108
+ tx. send ( o. data . to_owned ( ) ) . ok ( ) ;
109
+ objs:: CommitRefIter :: from_bytes ( o. data )
110
+ } )
111
+ } ) ,
112
+ || anyhow ! ( "Cancelled by user" ) ,
113
+ ) ;
114
+ let mut is_shallow = false ;
115
+ for c in commit_iter {
116
+ match c? {
117
+ Ok ( c) => c,
118
+ Err ( git:: traverse:: commit:: ancestors:: Error :: FindExisting { .. } ) => {
119
+ is_shallow = true ;
120
+ break ;
121
+ }
122
+ Err ( err) => return Err ( err. into ( ) ) ,
123
+ } ;
124
+ }
125
+ drop ( tx) ;
126
+ progress. show_throughput ( start) ;
127
+ Ok ( ( handle. join ( ) . expect ( "no panic" ) ?, is_shallow) )
128
+ } ) ?
129
129
} ;
130
130
131
131
if all_commits. is_empty ( ) {
0 commit comments