Skip to content

Commit 16403d0

Browse files
committed
git-gui: Refresh a file if it has an empty diff.
When the user has enabled the Trust File Modification Timestamp option then we may display a file as being modified yet that file may not have a difference. When the user clicks on that file we wind up displaying an empty diff viewer, which makes no sense to the user. So instead if we get an empty diff and the user has this option enabled and the file's current state is _M (no change in index but the working file appears modified) then run a quick update-index on just that file and remove it from the list of modified files. We also give the user a quick dialog stating we are removing it, and why. Usually I don't run into this situation when I have the Trust File Modification Timestamp option enabled, so its not that annoying to have a dialog pop open to remind me why there are no differences. Signed-off-by: Shawn O. Pearce <[email protected]>
1 parent 2c26e6f commit 16403d0

File tree

1 file changed

+72
-4
lines changed

1 file changed

+72
-4
lines changed

git-gui

Lines changed: 72 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -88,6 +88,25 @@ proc error_popup {msg} {
8888
-message $msg
8989
}
9090

91+
proc info_popup {msg} {
92+
global gitdir appname
93+
94+
set title $appname
95+
if {$gitdir != {}} {
96+
append title { (}
97+
append title [lindex \
98+
[file split [file normalize [file dirname $gitdir]]] \
99+
end]
100+
append title {)}
101+
}
102+
tk_messageBox \
103+
-parent . \
104+
-icon error \
105+
-type ok \
106+
-title $title \
107+
-message $msg
108+
}
109+
91110
######################################################################
92111
##
93112
## repository setup
@@ -204,7 +223,12 @@ proc update_status {{final Ready.}} {
204223
} else {
205224
set status_active 1
206225
set ui_status_value {Refreshing file status...}
207-
set fd_rf [open "| git update-index -q --unmerged --refresh" r]
226+
set cmd [list git update-index]
227+
lappend cmd -q
228+
lappend cmd --unmerged
229+
lappend cmd --ignore-missing
230+
lappend cmd --refresh
231+
set fd_rf [open "| $cmd" r]
208232
fconfigure $fd_rf -blocking 0 -translation binary
209233
fileevent $fd_rf readable \
210234
[list update_status_stage2 $fd_rf $final]
@@ -381,6 +405,42 @@ proc reshow_diff {} {
381405
}
382406
}
383407

408+
proc handle_empty_diff {} {
409+
global ui_fname_value file_states file_lists
410+
411+
set path $ui_fname_value
412+
set s $file_states($path)
413+
if {[lindex $s 0] != {_M}} return
414+
415+
info_popup "No differences detected.
416+
417+
[short_path $path] has no changes.
418+
419+
The modification date of this file was updated by another
420+
application and you currently have the Trust File Modification
421+
Timestamps feature enabled, so Git did not automatically detect
422+
that there are no content differences in this file.
423+
424+
This file will now be removed from the modified files list, to
425+
prevent possible confusion.
426+
"
427+
if {[catch {exec git update-index -- $path} err]} {
428+
error_popup "Failed to refresh index:\n\n$err"
429+
}
430+
431+
clear_diff
432+
set old_w [mapcol [lindex $file_states($path) 0] $path]
433+
set lno [lsearch -sorted $file_lists($old_w) $path]
434+
if {$lno >= 0} {
435+
set file_lists($old_w) \
436+
[lreplace $file_lists($old_w) $lno $lno]
437+
incr lno
438+
$old_w conf -state normal
439+
$old_w delete $lno.0 [expr $lno + 1].0
440+
$old_w conf -state disabled
441+
}
442+
}
443+
384444
proc show_diff {path {w {}} {lno {}}} {
385445
global file_states file_lists
386446
global PARENT diff_3way diff_active
@@ -451,6 +511,7 @@ proc show_diff {path {w {}} {lno {}}} {
451511

452512
proc read_diff {fd} {
453513
global ui_diff ui_status_value diff_3way diff_active
514+
global cfg_trust_mtime
454515

455516
while {[gets $fd line] >= 0} {
456517
if {[string match {diff --git *} $line]} continue
@@ -497,6 +558,10 @@ proc read_diff {fd} {
497558
set diff_active 0
498559
unlock_index
499560
set ui_status_value {Ready.}
561+
562+
if {$cfg_trust_mtime && [$ui_diff index end] == {2.0}} {
563+
handle_empty_diff
564+
}
500565
}
501566
}
502567

@@ -588,7 +653,7 @@ before committing.
588653
U? {
589654
error_popup "Unmerged files cannot be committed.
590655
591-
File [escape_path $path] has merge conflicts.
656+
File [short_path $path] has merge conflicts.
592657
You must resolve them and include the file before committing.
593658
"
594659
unlock_index
@@ -597,7 +662,7 @@ You must resolve them and include the file before committing.
597662
default {
598663
error_popup "Unknown file state [lindex $s 0] detected.
599664
600-
File [escape_path $path] cannot be committed by this program.
665+
File [short_path $path] cannot be committed by this program.
601666
"
602667
}
603668
}
@@ -888,6 +953,10 @@ proc escape_path {path} {
888953
return $path
889954
}
890955

956+
proc short_path {path} {
957+
return [escape_path [lindex [file split $path] end]]
958+
}
959+
891960
set next_icon_id 0
892961

893962
proc merge_state {path new_state} {
@@ -921,7 +990,6 @@ proc merge_state {path new_state} {
921990
}
922991

923992
proc display_file {path state} {
924-
global ui_index ui_other
925993
global file_states file_lists status_active
926994

927995
set old_m [merge_state $path $state]

0 commit comments

Comments
 (0)