Skip to content

Commit 8509567

Browse files
committed
fix(Avalonia): halt active tasks on view unload
1 parent f0c9114 commit 8509567

2 files changed

Lines changed: 36 additions & 10 deletions

File tree

SnapX.Avalonia/ViewModels/HomePageViewModel.cs

Lines changed: 34 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -201,21 +201,30 @@ public void UploadButton(object Sender)
201201
}
202202
UploadManager.UploadFile(ltt.task.FilePath);
203203
}
204-
205-
public async Task RefreshTasks()
204+
private CancellationTokenSource? _refreshCts;
205+
public async Task RefreshTasks(CancellationToken cancellationToken = default)
206206
{
207+
using var linkedCts = CancellationTokenSource.CreateLinkedTokenSource(
208+
cancellationToken,
209+
_refreshCts?.Token ?? CancellationToken.None);
210+
211+
var ct = linkedCts.Token;
212+
207213
var typeofVM = typeof(HomePageViewModel);
208214

209215
List<ListTaskTemplate> newDesiredTasks;
210216

211-
// Check cache first
212217
if (DateTime.Now - _lastCacheTime < _cacheDuration && _cachedTasks != null)
213218
{
214219
newDesiredTasks = _cachedTasks;
215220
}
216221
else
217222
{
218-
var historyItems = await TaskManager.History.GetHistoryItemsAsync(30_000).ConfigureAwait(false);
223+
var historyItems = await TaskManager.History.GetHistoryItemsAsync(30_000)
224+
.WaitAsync(ct)
225+
.ConfigureAwait(false);
226+
227+
ct.ThrowIfCancellationRequested();
219228

220229
var tasks = historyItems.Select(task => new ListTaskTemplate(typeofVM, task));
221230

@@ -227,21 +236,27 @@ public async Task RefreshTasks()
227236
_lastCacheTime = DateTime.Now;
228237
}
229238

239+
ct.ThrowIfCancellationRequested();
240+
230241
await Dispatcher.UIThread.InvokeAsync(() =>
231242
{
243+
ct.ThrowIfCancellationRequested();
244+
232245
if (newDesiredTasks.Count > 50_000)
233246
{
234247
recentTasks.ResetBehavior = ResetBehavior.Remove;
235248
recentTasks.Clear();
236249
recentTasks.AddRange(newDesiredTasks);
237250
return;
238251
}
239-
var currentTasksById = recentTasks.ToDictionary(template => template.task.Id);
240252

253+
var currentTasksById = recentTasks.ToDictionary(template => template.task.Id);
241254
var newDesiredTaskIds = newDesiredTasks.Select(template => template.task.Id).ToHashSet();
242255

243256
for (var i = recentTasks.Count - 1; i >= 0; i--)
244257
{
258+
ct.ThrowIfCancellationRequested();
259+
245260
if (!newDesiredTaskIds.Contains(recentTasks[i].task.Id))
246261
{
247262
recentTasks.RemoveAt(i);
@@ -250,12 +265,11 @@ await Dispatcher.UIThread.InvokeAsync(() =>
250265

251266
foreach (var newItem in newDesiredTasks)
252267
{
268+
ct.ThrowIfCancellationRequested();
269+
253270
if (currentTasksById.TryGetValue(newItem.task.Id, out var existingItem))
254271
{
255-
if (existingItem.Equals(newItem))
256-
{
257-
continue;
258-
}
272+
if (existingItem.Equals(newItem)) continue;
259273
var index = recentTasks.IndexOf(existingItem);
260274
if (index == -1) continue;
261275
recentTasks.RemoveAt(index);
@@ -268,4 +282,15 @@ await Dispatcher.UIThread.InvokeAsync(() =>
268282
}
269283
});
270284
}
285+
286+
public async Task HaltActiveTasks()
287+
{
288+
if (_refreshCts != null)
289+
{
290+
await _refreshCts.CancelAsync();
291+
_refreshCts.Dispose();
292+
_refreshCts = null;
293+
}
294+
await Task.CompletedTask;
295+
}
271296
}

SnapX.Avalonia/Views/HomePageView.axaml.cs

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -51,13 +51,14 @@ private void RemoveHistoryItem_OnClick(object? Sender, RoutedEventArgs E)
5151
ViewModel.RemoveHistoryItemCommand.Execute(menuFlyoutItem.DataContext);
5252
ViewModel.InvalidateCache();
5353
ViewModel.StopTimer();
54-
ViewModel.RefreshTasks();
54+
_ = ViewModel.RefreshTasks();
5555
ViewModel.StartTimer();
5656
}
5757

5858
private void Control_OnUnloaded(object? Sender, RoutedEventArgs E)
5959
{
6060
ViewModel.StopTimer();
61+
_ = ViewModel.HaltActiveTasks();
6162
}
6263

6364
private void Button_OnClick(object? Sender, RoutedEventArgs E)

0 commit comments

Comments
 (0)