blob: 11379f8ad355e2ea2a7cf1645bc31543508731ab [file] [log] [blame]
Shawn O. Pearcef522c9b2007-05-07 23:35:48 -04001# git-gui misc. commit reading/writing support
2# Copyright (C) 2006, 2007 Shawn Pearce
3
4proc load_last_commit {} {
Pat Thoytscfe616b2016-10-06 14:04:42 +01005 global HEAD PARENT MERGE_HEAD commit_type ui_comm commit_author
Shawn O. Pearcef522c9b2007-05-07 23:35:48 -04006 global repo_config
7
8 if {[llength $PARENT] == 0} {
Christian Stimming1ac17952007-07-21 14:21:34 +02009 error_popup [mc "There is nothing to amend.
Shawn O. Pearcef522c9b2007-05-07 23:35:48 -040010
11You are about to create the initial commit. There is no commit before this to amend.
Christian Stimming1ac17952007-07-21 14:21:34 +020012"]
Shawn O. Pearcef522c9b2007-05-07 23:35:48 -040013 return
14 }
15
16 repository_state curType curHEAD curMERGE_HEAD
17 if {$curType eq {merge}} {
Christian Stimming1ac17952007-07-21 14:21:34 +020018 error_popup [mc "Cannot amend while merging.
Shawn O. Pearcef522c9b2007-05-07 23:35:48 -040019
20You are currently in the middle of a merge that has not been fully completed. You cannot amend the prior commit unless you first abort the current merge activity.
Christian Stimming1ac17952007-07-21 14:21:34 +020021"]
Shawn O. Pearcef522c9b2007-05-07 23:35:48 -040022 return
23 }
24
25 set msg {}
26 set parents [list]
27 if {[catch {
Łukasz Stelmach331450f2017-12-05 15:23:26 +010028 set name ""
29 set email ""
Shawn O. Pearce0b812612007-07-09 01:17:09 -040030 set fd [git_read cat-file commit $curHEAD]
Shawn O. Pearcef522c9b2007-05-07 23:35:48 -040031 fconfigure $fd -encoding binary -translation lf
Alexander Gavrilov3ac31e42008-12-06 20:24:35 +030032 # By default commits are assumed to be in utf-8
33 set enc utf-8
Shawn O. Pearcef522c9b2007-05-07 23:35:48 -040034 while {[gets $fd line] > 0} {
35 if {[string match {parent *} $line]} {
36 lappend parents [string range $line 7 end]
37 } elseif {[string match {encoding *} $line]} {
38 set enc [string tolower [string range $line 9 end]]
Łukasz Stelmach331450f2017-12-05 15:23:26 +010039 } elseif {[regexp "author (.*)\\s<(.*)>\\s(\\d.*$)" $line all name email time]} { }
Shawn O. Pearcef522c9b2007-05-07 23:35:48 -040040 }
Shawn O. Pearcec4638f62007-07-19 01:13:29 -040041 set msg [read $fd]
Shawn O. Pearcef522c9b2007-05-07 23:35:48 -040042 close $fd
Shawn O. Pearcec4638f62007-07-19 01:13:29 -040043
44 set enc [tcl_encoding $enc]
45 if {$enc ne {}} {
46 set msg [encoding convertfrom $enc $msg]
Łukasz Stelmach331450f2017-12-05 15:23:26 +010047 set name [encoding convertfrom $enc $name]
48 set email [encoding convertfrom $enc $email]
Shawn O. Pearcec4638f62007-07-19 01:13:29 -040049 }
Łukasz Stelmach331450f2017-12-05 15:23:26 +010050 if {$name ne {} && $email ne {}} {
51 set commit_author [list name $name email $email date $time]
52 }
53
Shawn O. Pearcec4638f62007-07-19 01:13:29 -040054 set msg [string trim $msg]
Shawn O. Pearcef522c9b2007-05-07 23:35:48 -040055 } err]} {
Shawn O. Pearce31bb1d12007-09-14 01:50:09 -040056 error_popup [strcat [mc "Error loading commit data for amend:"] "\n\n$err"]
Shawn O. Pearcef522c9b2007-05-07 23:35:48 -040057 return
58 }
59
60 set HEAD $curHEAD
61 set PARENT $parents
62 set MERGE_HEAD [list]
63 switch -- [llength $parents] {
64 0 {set commit_type amend-initial}
65 1 {set commit_type amend}
66 default {set commit_type amend-merge}
67 }
68
69 $ui_comm delete 0.0 end
70 $ui_comm insert end $msg
71 $ui_comm edit reset
72 $ui_comm edit modified false
Shawn O. Pearce699d5602007-07-05 23:16:13 -040073 rescan ui_ready
Shawn O. Pearcef522c9b2007-05-07 23:35:48 -040074}
75
76set GIT_COMMITTER_IDENT {}
77
78proc committer_ident {} {
79 global GIT_COMMITTER_IDENT
80
81 if {$GIT_COMMITTER_IDENT eq {}} {
82 if {[catch {set me [git var GIT_COMMITTER_IDENT]} err]} {
Shawn O. Pearce31bb1d12007-09-14 01:50:09 -040083 error_popup [strcat [mc "Unable to obtain your identity:"] "\n\n$err"]
Shawn O. Pearcef522c9b2007-05-07 23:35:48 -040084 return {}
85 }
86 if {![regexp {^(.*) [0-9]+ [-+0-9]+$} \
87 $me me GIT_COMMITTER_IDENT]} {
Shawn O. Pearce31bb1d12007-09-14 01:50:09 -040088 error_popup [strcat [mc "Invalid GIT_COMMITTER_IDENT:"] "\n\n$me"]
Shawn O. Pearcef522c9b2007-05-07 23:35:48 -040089 return {}
90 }
91 }
92
93 return $GIT_COMMITTER_IDENT
94}
95
96proc do_signoff {} {
97 global ui_comm
98
99 set me [committer_ident]
100 if {$me eq {}} return
101
102 set sob "Signed-off-by: $me"
103 set last [$ui_comm get {end -1c linestart} {end -1c}]
104 if {$last ne $sob} {
105 $ui_comm edit separator
106 if {$last ne {}
107 && ![regexp {^[A-Z][A-Za-z]*-[A-Za-z-]+: *} $last]} {
108 $ui_comm insert end "\n"
109 }
110 $ui_comm insert end "\n$sob"
111 $ui_comm edit separator
112 $ui_comm see end
113 }
114}
115
116proc create_new_commit {} {
Pat Thoytscfe616b2016-10-06 14:04:42 +0100117 global commit_type ui_comm commit_author
Shawn O. Pearcef522c9b2007-05-07 23:35:48 -0400118
119 set commit_type normal
Pat Thoytscfe616b2016-10-06 14:04:42 +0100120 unset -nocomplain commit_author
Shawn O. Pearcef522c9b2007-05-07 23:35:48 -0400121 $ui_comm delete 0.0 end
122 $ui_comm edit reset
123 $ui_comm edit modified false
Shawn O. Pearce699d5602007-07-05 23:16:13 -0400124 rescan ui_ready
Shawn O. Pearcef522c9b2007-05-07 23:35:48 -0400125}
126
Alexander Gavrilov06569cd2009-01-24 00:18:13 +0300127proc setup_commit_encoding {msg_wt {quiet 0}} {
128 global repo_config
129
130 if {[catch {set enc $repo_config(i18n.commitencoding)}]} {
131 set enc utf-8
132 }
133 set use_enc [tcl_encoding $enc]
134 if {$use_enc ne {}} {
135 fconfigure $msg_wt -encoding $use_enc
136 } else {
137 if {!$quiet} {
138 error_popup [mc "warning: Tcl does not support encoding '%s'." $enc]
139 }
140 fconfigure $msg_wt -encoding utf-8
141 }
142}
143
Shawn O. Pearcef522c9b2007-05-07 23:35:48 -0400144proc commit_tree {} {
145 global HEAD commit_type file_states ui_comm repo_config
Shawn O. Pearce699d5602007-07-05 23:16:13 -0400146 global pch_error
Shawn O. Pearcef522c9b2007-05-07 23:35:48 -0400147
148 if {[committer_ident] eq {}} return
149 if {![lock_index update]} return
150
151 # -- Our in memory state should match the repository.
152 #
153 repository_state curType curHEAD curMERGE_HEAD
154 if {[string match amend* $commit_type]
155 && $curType eq {normal}
156 && $curHEAD eq $HEAD} {
157 } elseif {$commit_type ne $curType || $HEAD ne $curHEAD} {
Christian Stimming1ac17952007-07-21 14:21:34 +0200158 info_popup [mc "Last scanned state does not match repository state.
Shawn O. Pearcef522c9b2007-05-07 23:35:48 -0400159
160Another Git program has modified this repository since the last scan. A rescan must be performed before another commit can be created.
161
162The rescan will be automatically started now.
Christian Stimming1ac17952007-07-21 14:21:34 +0200163"]
Shawn O. Pearcef522c9b2007-05-07 23:35:48 -0400164 unlock_index
Shawn O. Pearce699d5602007-07-05 23:16:13 -0400165 rescan ui_ready
Shawn O. Pearcef522c9b2007-05-07 23:35:48 -0400166 return
167 }
168
169 # -- At least one file should differ in the index.
170 #
171 set files_ready 0
172 foreach path [array names file_states] {
Bert Wesarg4a065c82010-12-09 21:46:22 +0100173 set s $file_states($path)
174 switch -glob -- [lindex $s 0] {
Shawn O. Pearcef522c9b2007-05-07 23:35:48 -0400175 _? {continue}
176 A? -
177 D? -
Bert Wesarg7587f4d2010-12-09 21:46:23 +0100178 T? -
Shawn O. Pearcef522c9b2007-05-07 23:35:48 -0400179 M? {set files_ready 1}
Alexander Gavrilovff515d82008-08-31 01:00:49 +0400180 _U -
Shawn O. Pearcef522c9b2007-05-07 23:35:48 -0400181 U? {
Christian Stimming1ac17952007-07-21 14:21:34 +0200182 error_popup [mc "Unmerged files cannot be committed.
Shawn O. Pearcef522c9b2007-05-07 23:35:48 -0400183
Christian Stimming1ac17952007-07-21 14:21:34 +0200184File %s has merge conflicts. You must resolve them and stage the file before committing.
185" [short_path $path]]
Shawn O. Pearcef522c9b2007-05-07 23:35:48 -0400186 unlock_index
187 return
188 }
189 default {
Christian Stimming1ac17952007-07-21 14:21:34 +0200190 error_popup [mc "Unknown file state %s detected.
Shawn O. Pearcef522c9b2007-05-07 23:35:48 -0400191
Christian Stimming1ac17952007-07-21 14:21:34 +0200192File %s cannot be committed by this program.
193" [lindex $s 0] [short_path $path]]
Shawn O. Pearcef522c9b2007-05-07 23:35:48 -0400194 }
195 }
196 }
Alexander Gavrilov1e65c622008-09-12 22:43:49 +0400197 if {!$files_ready && ![string match *merge $curType] && ![is_enabled nocommit]} {
Christian Stimming1ac17952007-07-21 14:21:34 +0200198 info_popup [mc "No changes to commit.
Shawn O. Pearcef522c9b2007-05-07 23:35:48 -0400199
Christian Stimming360cc102007-07-28 22:17:10 +0200200You must stage at least 1 file before you can commit.
Christian Stimming1ac17952007-07-21 14:21:34 +0200201"]
Shawn O. Pearcef522c9b2007-05-07 23:35:48 -0400202 unlock_index
203 return
204 }
205
Alexander Gavrilov1e65c622008-09-12 22:43:49 +0400206 if {[is_enabled nocommitmsg]} { do_quit 0 }
207
Shawn O. Pearcef522c9b2007-05-07 23:35:48 -0400208 # -- A message is required.
209 #
Pratyush Yadavc0698df2021-03-04 13:53:27 +0530210 set msg [string trim [$ui_comm get 1.0 end]]
211 regsub -all -line {[ \t\r]+$} $msg {} msg
Shawn O. Pearcef522c9b2007-05-07 23:35:48 -0400212 if {$msg eq {}} {
Christian Stimming1ac17952007-07-21 14:21:34 +0200213 error_popup [mc "Please supply a commit message.
Shawn O. Pearcef522c9b2007-05-07 23:35:48 -0400214
215A good commit message has the following format:
216
Michele Ballabio208320d2007-11-22 16:20:08 +0100217- First line: Describe in one sentence what you did.
Shawn O. Pearcef522c9b2007-05-07 23:35:48 -0400218- Second line: Blank
219- Remaining lines: Describe why this change is good.
Christian Stimming1ac17952007-07-21 14:21:34 +0200220"]
Shawn O. Pearcef522c9b2007-05-07 23:35:48 -0400221 unlock_index
222 return
223 }
224
Shawn O. Pearcefb0ca472008-01-20 14:11:52 -0500225 # -- Build the message file.
226 #
227 set msg_p [gitdir GITGUI_EDITMSG]
228 set msg_wt [open $msg_p w]
229 fconfigure $msg_wt -translation lf
Alexander Gavrilov06569cd2009-01-24 00:18:13 +0300230 setup_commit_encoding $msg_wt
Shawn O. Pearcefb0ca472008-01-20 14:11:52 -0500231 puts $msg_wt $msg
232 close $msg_wt
233
Alexander Gavrilov1e65c622008-09-12 22:43:49 +0400234 if {[is_enabled nocommit]} { do_quit 0 }
235
Shawn O. Pearcef522c9b2007-05-07 23:35:48 -0400236 # -- Run the pre-commit hook.
237 #
Shawn O. Pearceed76cb72008-01-20 14:46:59 -0500238 set fd_ph [githook_read pre-commit]
239 if {$fd_ph eq {}} {
Shawn O. Pearcefb0ca472008-01-20 14:11:52 -0500240 commit_commitmsg $curHEAD $msg_p
Shawn O. Pearcef522c9b2007-05-07 23:35:48 -0400241 return
242 }
243
Christian Stimming5e6d7762008-02-02 10:20:17 +0100244 ui_status [mc "Calling pre-commit hook..."]
Shawn O. Pearcef522c9b2007-05-07 23:35:48 -0400245 set pch_error {}
Shawn O. Pearce6eb420e2007-07-17 01:50:10 -0400246 fconfigure $fd_ph -blocking 0 -translation binary -eofchar {}
Shawn O. Pearcef522c9b2007-05-07 23:35:48 -0400247 fileevent $fd_ph readable \
Shawn O. Pearcefb0ca472008-01-20 14:11:52 -0500248 [list commit_prehook_wait $fd_ph $curHEAD $msg_p]
Shawn O. Pearcef522c9b2007-05-07 23:35:48 -0400249}
250
Shawn O. Pearcefb0ca472008-01-20 14:11:52 -0500251proc commit_prehook_wait {fd_ph curHEAD msg_p} {
Shawn O. Pearce699d5602007-07-05 23:16:13 -0400252 global pch_error
Shawn O. Pearcef522c9b2007-05-07 23:35:48 -0400253
254 append pch_error [read $fd_ph]
255 fconfigure $fd_ph -blocking 1
256 if {[eof $fd_ph]} {
257 if {[catch {close $fd_ph}]} {
Shawn O. Pearcefb0ca472008-01-20 14:11:52 -0500258 catch {file delete $msg_p}
Christian Stimming5e6d7762008-02-02 10:20:17 +0100259 ui_status [mc "Commit declined by pre-commit hook."]
Shawn O. Pearcef522c9b2007-05-07 23:35:48 -0400260 hook_failed_popup pre-commit $pch_error
261 unlock_index
262 } else {
Shawn O. Pearcefb0ca472008-01-20 14:11:52 -0500263 commit_commitmsg $curHEAD $msg_p
Shawn O. Pearcef522c9b2007-05-07 23:35:48 -0400264 }
265 set pch_error {}
266 return
267 }
268 fconfigure $fd_ph -blocking 0
269}
270
Shawn O. Pearcefb0ca472008-01-20 14:11:52 -0500271proc commit_commitmsg {curHEAD msg_p} {
Heiko Voigte34789c2011-02-15 19:43:54 +0000272 global is_detached repo_config
Shawn O. Pearcefb0ca472008-01-20 14:11:52 -0500273 global pch_error
274
Bert Wesargd8d166b2011-10-22 21:39:40 +0200275 if {$is_detached
276 && ![file exists [gitdir rebase-merge head-name]]
277 && [is_config_true gui.warndetachedcommit]} {
Heiko Voigte34789c2011-02-15 19:43:54 +0000278 set msg [mc "You are about to commit on a detached head.\
279This is a potentially dangerous thing to do because if you switch\
Beat Bolli9ef75082012-08-18 13:24:00 -0700280to another branch you will lose your changes and it can be difficult\
Heiko Voigte34789c2011-02-15 19:43:54 +0000281to retrieve them later from the reflog. You should probably cancel this\
282commit and create a new branch to continue.\n\
283\n\
284Do you really want to proceed with your Commit?"]
285 if {[ask_popup $msg] ne yes} {
286 unlock_index
287 return
288 }
289 }
290
Shawn O. Pearcefb0ca472008-01-20 14:11:52 -0500291 # -- Run the commit-msg hook.
292 #
Shawn O. Pearceed76cb72008-01-20 14:46:59 -0500293 set fd_ph [githook_read commit-msg $msg_p]
294 if {$fd_ph eq {}} {
Shawn O. Pearcefb0ca472008-01-20 14:11:52 -0500295 commit_writetree $curHEAD $msg_p
296 return
297 }
298
Christian Stimming5e6d7762008-02-02 10:20:17 +0100299 ui_status [mc "Calling commit-msg hook..."]
Shawn O. Pearcefb0ca472008-01-20 14:11:52 -0500300 set pch_error {}
Shawn O. Pearcefb0ca472008-01-20 14:11:52 -0500301 fconfigure $fd_ph -blocking 0 -translation binary -eofchar {}
302 fileevent $fd_ph readable \
303 [list commit_commitmsg_wait $fd_ph $curHEAD $msg_p]
304}
305
306proc commit_commitmsg_wait {fd_ph curHEAD msg_p} {
307 global pch_error
308
309 append pch_error [read $fd_ph]
310 fconfigure $fd_ph -blocking 1
311 if {[eof $fd_ph]} {
312 if {[catch {close $fd_ph}]} {
313 catch {file delete $msg_p}
Christian Stimming5e6d7762008-02-02 10:20:17 +0100314 ui_status [mc "Commit declined by commit-msg hook."]
Shawn O. Pearcefb0ca472008-01-20 14:11:52 -0500315 hook_failed_popup commit-msg $pch_error
316 unlock_index
317 } else {
318 commit_writetree $curHEAD $msg_p
319 }
320 set pch_error {}
321 return
322 }
323 fconfigure $fd_ph -blocking 0
324}
325
326proc commit_writetree {curHEAD msg_p} {
Christian Stimming5e6d7762008-02-02 10:20:17 +0100327 ui_status [mc "Committing changes..."]
Shawn O. Pearce0b812612007-07-09 01:17:09 -0400328 set fd_wt [git_read write-tree]
Shawn O. Pearcef522c9b2007-05-07 23:35:48 -0400329 fileevent $fd_wt readable \
Shawn O. Pearcefb0ca472008-01-20 14:11:52 -0500330 [list commit_committree $fd_wt $curHEAD $msg_p]
Shawn O. Pearcef522c9b2007-05-07 23:35:48 -0400331}
332
Shawn O. Pearcefb0ca472008-01-20 14:11:52 -0500333proc commit_committree {fd_wt curHEAD msg_p} {
Pat Thoytscfe616b2016-10-06 14:04:42 +0100334 global HEAD PARENT MERGE_HEAD commit_type commit_author
Shawn O. Pearce699d5602007-07-05 23:16:13 -0400335 global current_branch
Bert Wesargba41b5b2019-09-13 08:02:30 +0200336 global ui_comm commit_type_is_amend
Shawn O. Pearcef522c9b2007-05-07 23:35:48 -0400337 global file_states selected_paths rescan_active
338 global repo_config
Pat Thoytscfe616b2016-10-06 14:04:42 +0100339 global env
Shawn O. Pearcef522c9b2007-05-07 23:35:48 -0400340
341 gets $fd_wt tree_id
Shawn O. Pearce8af52d72007-10-20 01:42:01 -0400342 if {[catch {close $fd_wt} err]} {
Shawn O. Pearcefb0ca472008-01-20 14:11:52 -0500343 catch {file delete $msg_p}
Shawn O. Pearce31bb1d12007-09-14 01:50:09 -0400344 error_popup [strcat [mc "write-tree failed:"] "\n\n$err"]
Christian Stimming5e6d7762008-02-02 10:20:17 +0100345 ui_status [mc "Commit failed."]
Shawn O. Pearcef522c9b2007-05-07 23:35:48 -0400346 unlock_index
347 return
348 }
349
350 # -- Verify this wasn't an empty change.
351 #
352 if {$commit_type eq {normal}} {
Shawn O. Pearceb2158832007-07-12 02:45:23 -0400353 set fd_ot [git_read cat-file commit $PARENT]
Shawn O. Pearce20f1a102007-07-12 02:31:28 -0400354 fconfigure $fd_ot -encoding binary -translation lf
355 set old_tree [gets $fd_ot]
356 close $fd_ot
357
358 if {[string equal -length 5 {tree } $old_tree]
359 && [string length $old_tree] == 45} {
360 set old_tree [string range $old_tree 5 end]
361 } else {
Michele Ballabioc8c48542007-09-13 15:19:05 +0200362 error [mc "Commit %s appears to be corrupt" $PARENT]
Shawn O. Pearce20f1a102007-07-12 02:31:28 -0400363 }
364
Shawn O. Pearcef522c9b2007-05-07 23:35:48 -0400365 if {$tree_id eq $old_tree} {
Shawn O. Pearcefb0ca472008-01-20 14:11:52 -0500366 catch {file delete $msg_p}
Christian Stimming1ac17952007-07-21 14:21:34 +0200367 info_popup [mc "No changes to commit.
Shawn O. Pearcef522c9b2007-05-07 23:35:48 -0400368
369No files were modified by this commit and it was not a merge commit.
370
371A rescan will be automatically started now.
Christian Stimming1ac17952007-07-21 14:21:34 +0200372"]
Shawn O. Pearcef522c9b2007-05-07 23:35:48 -0400373 unlock_index
Christian Stimming1ac17952007-07-21 14:21:34 +0200374 rescan {ui_status [mc "No changes to commit."]}
Shawn O. Pearcef522c9b2007-05-07 23:35:48 -0400375 return
376 }
377 }
378
Pat Thoytscfe616b2016-10-06 14:04:42 +0100379 if {[info exists commit_author]} {
380 set old_author [commit_author_ident $commit_author]
Orgad Shaneh7e71adc2016-04-11 09:57:39 +0300381 }
Shawn O. Pearcef522c9b2007-05-07 23:35:48 -0400382 # -- Create the commit.
383 #
384 set cmd [list commit-tree $tree_id]
Johannes Schindelin2afe6b72016-09-09 14:28:24 +0200385 if {[is_config_true commit.gpgsign]} {
386 lappend cmd -S
387 }
Shawn O. Pearcef522c9b2007-05-07 23:35:48 -0400388 foreach p [concat $PARENT $MERGE_HEAD] {
389 lappend cmd -p $p
390 }
391 lappend cmd <$msg_p
392 if {[catch {set cmt_id [eval git $cmd]} err]} {
Shawn O. Pearcefb0ca472008-01-20 14:11:52 -0500393 catch {file delete $msg_p}
Shawn O. Pearce31bb1d12007-09-14 01:50:09 -0400394 error_popup [strcat [mc "commit-tree failed:"] "\n\n$err"]
Christian Stimming5e6d7762008-02-02 10:20:17 +0100395 ui_status [mc "Commit failed."]
Shawn O. Pearcef522c9b2007-05-07 23:35:48 -0400396 unlock_index
Pat Thoytscfe616b2016-10-06 14:04:42 +0100397 unset -nocomplain commit_author
398 commit_author_reset $old_author
Shawn O. Pearcef522c9b2007-05-07 23:35:48 -0400399 return
400 }
Pat Thoytscfe616b2016-10-06 14:04:42 +0100401 if {[info exists commit_author]} {
402 unset -nocomplain commit_author
403 commit_author_reset $old_author
404 }
Shawn O. Pearcef522c9b2007-05-07 23:35:48 -0400405
406 # -- Update the HEAD ref.
407 #
408 set reflogm commit
409 if {$commit_type ne {normal}} {
410 append reflogm " ($commit_type)"
411 }
Shawn O. Pearcefb0ca472008-01-20 14:11:52 -0500412 set msg_fd [open $msg_p r]
Alexander Gavrilov06569cd2009-01-24 00:18:13 +0300413 setup_commit_encoding $msg_fd 1
Shawn O. Pearcefb0ca472008-01-20 14:11:52 -0500414 gets $msg_fd subject
415 close $msg_fd
Shawn O. Pearcef522c9b2007-05-07 23:35:48 -0400416 append reflogm {: } $subject
417 if {[catch {
418 git update-ref -m $reflogm HEAD $cmt_id $curHEAD
419 } err]} {
Shawn O. Pearcefb0ca472008-01-20 14:11:52 -0500420 catch {file delete $msg_p}
Shawn O. Pearce31bb1d12007-09-14 01:50:09 -0400421 error_popup [strcat [mc "update-ref failed:"] "\n\n$err"]
Christian Stimming5e6d7762008-02-02 10:20:17 +0100422 ui_status [mc "Commit failed."]
Shawn O. Pearcef522c9b2007-05-07 23:35:48 -0400423 unlock_index
424 return
425 }
426
427 # -- Cleanup after ourselves.
428 #
429 catch {file delete $msg_p}
430 catch {file delete [gitdir MERGE_HEAD]}
431 catch {file delete [gitdir MERGE_MSG]}
432 catch {file delete [gitdir SQUASH_MSG]}
433 catch {file delete [gitdir GITGUI_MSG]}
Beat Bolli5a5e4d22012-08-18 13:28:00 -0700434 catch {file delete [gitdir CHERRY_PICK_HEAD]}
Shawn O. Pearcef522c9b2007-05-07 23:35:48 -0400435
436 # -- Let rerere do its thing.
437 #
Shawn O. Pearced4c53072007-07-08 17:41:24 -0400438 if {[get_config rerere.enabled] eq {}} {
439 set rerere [file isdirectory [gitdir rr-cache]]
440 } else {
441 set rerere [is_config_true rerere.enabled]
442 }
443 if {$rerere} {
Shawn O. Pearcef522c9b2007-05-07 23:35:48 -0400444 catch {git rerere}
445 }
446
447 # -- Run the post-commit hook.
448 #
Shawn O. Pearceed76cb72008-01-20 14:46:59 -0500449 set fd_ph [githook_read post-commit]
450 if {$fd_ph ne {}} {
Jens Lehmannf0d4eec2009-03-30 20:35:57 +0200451 global pch_error
452 set pch_error {}
Shawn O. Pearceed76cb72008-01-20 14:46:59 -0500453 fconfigure $fd_ph -blocking 0 -translation binary -eofchar {}
454 fileevent $fd_ph readable \
455 [list commit_postcommit_wait $fd_ph $cmt_id]
Shawn O. Pearcef522c9b2007-05-07 23:35:48 -0400456 }
457
458 $ui_comm delete 0.0 end
Martin Schön627c87f2018-07-02 15:28:09 +0200459 load_message [get_config commit.template]
Shawn O. Pearcef522c9b2007-05-07 23:35:48 -0400460 $ui_comm edit reset
461 $ui_comm edit modified false
Shawn O. Pearce4578c5c2007-07-21 04:57:57 -0400462 if {$::GITGUI_BCK_exists} {
463 catch {file delete [gitdir GITGUI_BCK]}
Shawn O. Pearce9c5a3c72007-07-23 00:20:04 -0400464 set ::GITGUI_BCK_exists 0
Shawn O. Pearce4578c5c2007-07-21 04:57:57 -0400465 }
Shawn O. Pearcef522c9b2007-05-07 23:35:48 -0400466
Alexander Gavrilov1e65c622008-09-12 22:43:49 +0400467 if {[is_enabled singlecommit]} { do_quit 0 }
Shawn O. Pearcef522c9b2007-05-07 23:35:48 -0400468
Shawn O. Pearcef522c9b2007-05-07 23:35:48 -0400469 # -- Update in memory status
470 #
Shawn O. Pearcef522c9b2007-05-07 23:35:48 -0400471 set commit_type normal
Bert Wesargba41b5b2019-09-13 08:02:30 +0200472 set commit_type_is_amend 0
Shawn O. Pearcef522c9b2007-05-07 23:35:48 -0400473 set HEAD $cmt_id
474 set PARENT $cmt_id
475 set MERGE_HEAD [list]
476
477 foreach path [array names file_states] {
478 set s $file_states($path)
479 set m [lindex $s 0]
480 switch -glob -- $m {
481 _O -
482 _M -
483 _D {continue}
484 __ -
485 A_ -
486 M_ -
Gustaf Hendebye681cb72008-08-22 22:10:27 +0200487 T_ -
Shawn O. Pearcef522c9b2007-05-07 23:35:48 -0400488 D_ {
489 unset file_states($path)
490 catch {unset selected_paths($path)}
491 }
492 DO {
493 set file_states($path) [list _O [lindex $s 1] {} {}]
494 }
495 AM -
496 AD -
Bert Wesarg7587f4d2010-12-09 21:46:23 +0100497 AT -
498 TM -
499 TD -
Shawn O. Pearcef522c9b2007-05-07 23:35:48 -0400500 MM -
Bert Wesarg7587f4d2010-12-09 21:46:23 +0100501 MT -
Shawn O. Pearcef522c9b2007-05-07 23:35:48 -0400502 MD {
503 set file_states($path) [list \
504 _[string index $m 1] \
505 [lindex $s 1] \
506 [lindex $s 3] \
507 {}]
508 }
509 }
510 }
511
512 display_all_files
513 unlock_index
514 reshow_diff
Christian Stimming1ac17952007-07-21 14:21:34 +0200515 ui_status [mc "Created commit %s: %s" [string range $cmt_id 0 7] $subject]
Shawn O. Pearcef522c9b2007-05-07 23:35:48 -0400516}
Shawn O. Pearceed76cb72008-01-20 14:46:59 -0500517
518proc commit_postcommit_wait {fd_ph cmt_id} {
Jens Lehmannf0d4eec2009-03-30 20:35:57 +0200519 global pch_error
Shawn O. Pearceed76cb72008-01-20 14:46:59 -0500520
521 append pch_error [read $fd_ph]
522 fconfigure $fd_ph -blocking 1
523 if {[eof $fd_ph]} {
524 if {[catch {close $fd_ph}]} {
525 hook_failed_popup post-commit $pch_error 0
526 }
527 unset pch_error
528 return
529 }
530 fconfigure $fd_ph -blocking 0
531}
Pat Thoytscfe616b2016-10-06 14:04:42 +0100532
533proc commit_author_ident {details} {
534 global env
535 array set author $details
536 set old [array get env GIT_AUTHOR_*]
537 set env(GIT_AUTHOR_NAME) $author(name)
538 set env(GIT_AUTHOR_EMAIL) $author(email)
539 set env(GIT_AUTHOR_DATE) $author(date)
540 return $old
541}
542proc commit_author_reset {details} {
543 global env
544 unset env(GIT_AUTHOR_NAME) env(GIT_AUTHOR_EMAIL) env(GIT_AUTHOR_DATE)
545 if {$details ne {}} {
546 array set env $details
547 }
548}