Skip to content

Commit cc5f3eb

Browse files
committed
refactor: do not run git add for untracked file while stashing local changes (#903)
1 parent d8168c3 commit cc5f3eb

File tree

6 files changed

+56
-108
lines changed

6 files changed

+56
-108
lines changed

src/Commands/QueryStashChanges.cs

Lines changed: 0 additions & 60 deletions
This file was deleted.

src/Commands/QueryStashes.cs

Lines changed: 17 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,5 @@
1-
using System.Collections.Generic;
1+
using System;
2+
using System.Collections.Generic;
23

34
namespace SourceGit.Commands
45
{
@@ -8,7 +9,7 @@ public QueryStashes(string repo)
89
{
910
WorkingDirectory = repo;
1011
Context = repo;
11-
Args = "stash list --pretty=format:%H%n%ct%n%gd%n%s";
12+
Args = "stash list --pretty=format:%H%n%P%n%ct%n%gd%n%s";
1213
}
1314

1415
public List<Models.Stash> Result()
@@ -26,21 +27,32 @@ protected override void OnReadline(string line)
2627
_stashes.Add(_current);
2728
break;
2829
case 1:
29-
_current.Time = ulong.Parse(line);
30+
ParseParent(line);
3031
break;
3132
case 2:
32-
_current.Name = line;
33+
_current.Time = ulong.Parse(line);
3334
break;
3435
case 3:
36+
_current.Name = line;
37+
break;
38+
case 4:
3539
_current.Message = line;
3640
break;
3741
}
3842

3943
_nextLineIdx++;
40-
if (_nextLineIdx > 3)
44+
if (_nextLineIdx > 4)
4145
_nextLineIdx = 0;
4246
}
4347

48+
private void ParseParent(string data)
49+
{
50+
if (data.Length < 8)
51+
return;
52+
53+
_current.Parents.AddRange(data.Split(separator: ' ', options: StringSplitOptions.RemoveEmptyEntries));
54+
}
55+
4456
private readonly List<Models.Stash> _stashes = new List<Models.Stash>();
4557
private Models.Stash _current = null;
4658
private int _nextLineIdx = 0;

src/Commands/Stash.cs

Lines changed: 12 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -11,9 +11,19 @@ public Stash(string repo)
1111
Context = repo;
1212
}
1313

14-
public bool Push(string message)
14+
public bool Push(string message, bool includeUntracked = true, bool keepIndex = false)
1515
{
16-
Args = $"stash push -m \"{message}\"";
16+
var builder = new StringBuilder();
17+
builder.Append("stash push ");
18+
if (includeUntracked)
19+
builder.Append("--include-untracked ");
20+
if (keepIndex)
21+
builder.Append("--keep-index ");
22+
builder.Append("-m \"");
23+
builder.Append(message);
24+
builder.Append("\"");
25+
26+
Args = builder.ToString();
1727
return Exec();
1828
}
1929

src/Models/Stash.cs

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,13 +1,16 @@
11
using System;
2+
using System.Collections.Generic;
23

34
namespace SourceGit.Models
45
{
56
public class Stash
67
{
78
public string Name { get; set; } = "";
89
public string SHA { get; set; } = "";
10+
public List<string> Parents { get; set; } = [];
911
public ulong Time { get; set; } = 0;
1012
public string Message { get; set; } = "";
13+
public bool HasUntracked => Parents.Count == 3;
1114

1215
public string TimeStr => DateTime.UnixEpoch.AddSeconds(Time).ToLocalTime().ToString(DateTimeFormat.Actived.DateTime);
1316
}

src/ViewModels/StashChanges.cs

Lines changed: 1 addition & 38 deletions
Original file line numberDiff line numberDiff line change
@@ -76,14 +76,11 @@ public override Task<bool> Sure()
7676
}
7777
else
7878
{
79-
if (IncludeUntracked)
80-
AddUntracked(_changes);
81-
succ = StashWithChanges(_changes);
79+
succ = new Commands.Stash(_repo.FullPath).Push(Message, IncludeUntracked, KeepIndex);
8280
}
8381
}
8482
else
8583
{
86-
AddUntracked(_changes);
8784
succ = StashWithChanges(_changes);
8885
}
8986

@@ -97,40 +94,6 @@ public override Task<bool> Sure()
9794
});
9895
}
9996

100-
private void AddUntracked(List<Models.Change> changes)
101-
{
102-
var toBeAdded = new List<Models.Change>();
103-
foreach (var c in changes)
104-
{
105-
if (c.WorkTree == Models.ChangeState.Added || c.WorkTree == Models.ChangeState.Untracked)
106-
toBeAdded.Add(c);
107-
}
108-
109-
if (toBeAdded.Count == 0)
110-
return;
111-
112-
if (Native.OS.GitVersion >= Models.GitVersions.ADD_WITH_PATHSPECFILE)
113-
{
114-
var paths = new List<string>();
115-
foreach (var c in toBeAdded)
116-
paths.Add(c.Path);
117-
118-
var tmpFile = Path.GetTempFileName();
119-
File.WriteAllLines(tmpFile, paths);
120-
new Commands.Add(_repo.FullPath, tmpFile).Exec();
121-
File.Delete(tmpFile);
122-
}
123-
else
124-
{
125-
for (int i = 0; i < toBeAdded.Count; i += 10)
126-
{
127-
var count = Math.Min(10, toBeAdded.Count - i);
128-
var step = toBeAdded.GetRange(i, count);
129-
new Commands.Add(_repo.FullPath, step).Exec();
130-
}
131-
}
132-
}
133-
13497
private bool StashWithChanges(List<Models.Change> changes)
13598
{
13699
if (changes.Count == 0)

src/ViewModels/StashesPage.cs

Lines changed: 23 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -57,8 +57,25 @@ public Models.Stash SelectedStash
5757
{
5858
Task.Run(() =>
5959
{
60-
var changes = new Commands.QueryStashChanges(_repo.FullPath, value.SHA).Result();
61-
Dispatcher.UIThread.Invoke(() => Changes = changes);
60+
var changes = new Commands.CompareRevisions(_repo.FullPath, $"{value.SHA}^", value.SHA).Result();
61+
var untracked = new HashSet<string>();
62+
if (value.HasUntracked)
63+
{
64+
var untrackedChanges = new Commands.CompareRevisions(_repo.FullPath, "4b825dc642cb6eb9a060e54bf8d69288fbee4904", value.Parents[2]).Result();
65+
foreach (var c in untrackedChanges)
66+
{
67+
untracked.Add(c.Path);
68+
changes.Add(c);
69+
}
70+
}
71+
72+
changes.Sort((l, r) => Models.NumericSort.Compare(l.Path, r.Path));
73+
74+
Dispatcher.UIThread.Invoke(() =>
75+
{
76+
Changes = changes;
77+
_untrackedChanges = untracked;
78+
});
6279
});
6380
}
6481
}
@@ -84,8 +101,10 @@ public Models.Change SelectedChange
84101
{
85102
if (value == null)
86103
DiffContext = null;
104+
else if (_untrackedChanges.Contains(value.Path))
105+
DiffContext = new DiffContext(_repo.FullPath, new Models.DiffOption("4b825dc642cb6eb9a060e54bf8d69288fbee4904", _selectedStash.Parents[2], value), _diffContext);
87106
else
88-
DiffContext = new DiffContext(_repo.FullPath, new Models.DiffOption($"{_selectedStash.SHA}^", _selectedStash.SHA, value), _diffContext);
107+
DiffContext = new DiffContext(_repo.FullPath, new Models.DiffOption(_selectedStash.Parents[0], _selectedStash.SHA, value), _diffContext);
89108
}
90109
}
91110
}
@@ -254,6 +273,7 @@ private void RefreshVisible()
254273
private List<Models.Stash> _visibleStashes = new List<Models.Stash>();
255274
private string _searchFilter = string.Empty;
256275
private Models.Stash _selectedStash = null;
276+
private HashSet<string> _untrackedChanges = new HashSet<string>();
257277
private List<Models.Change> _changes = null;
258278
private Models.Change _selectedChange = null;
259279
private DiffContext _diffContext = null;

0 commit comments

Comments
 (0)