mirror of
https://github.com/BlossomiShymae/Needlework.Net.git
synced 2025-12-06 18:20:47 +01:00
Fix bug where event viewer may crash from a race condition, resolves #4
This commit is contained in:
@@ -18,6 +18,8 @@ namespace Needlework.Net.Desktop.ViewModels
|
|||||||
public partial class WebsocketViewModel : PageBase
|
public partial class WebsocketViewModel : PageBase
|
||||||
{
|
{
|
||||||
public ObservableCollection<string> EventLog { get; } = [];
|
public ObservableCollection<string> EventLog { get; } = [];
|
||||||
|
public SemaphoreSlim EventLogLock { get; } = new(1, 1);
|
||||||
|
|
||||||
[NotifyPropertyChangedFor(nameof(FilteredEventLog))]
|
[NotifyPropertyChangedFor(nameof(FilteredEventLog))]
|
||||||
[ObservableProperty] private string _search = string.Empty;
|
[ObservableProperty] private string _search = string.Empty;
|
||||||
[ObservableProperty] private bool _isAttach = true;
|
[ObservableProperty] private bool _isAttach = true;
|
||||||
@@ -94,12 +96,16 @@ namespace Needlework.Net.Desktop.ViewModels
|
|||||||
|
|
||||||
private void OnMessage(EventMessage message)
|
private void OnMessage(EventMessage message)
|
||||||
{
|
{
|
||||||
Avalonia.Threading.Dispatcher.UIThread.Invoke(() =>
|
Avalonia.Threading.Dispatcher.UIThread.Invoke(async () =>
|
||||||
{
|
{
|
||||||
if (!IsAttach) return;
|
if (!IsAttach) return;
|
||||||
|
|
||||||
var line = $"{DateTime.Now:HH:mm:ss.fff} {message.Data?.EventType.ToUpper()} {message.Data?.Uri}";
|
var line = $"{DateTime.Now:HH:mm:ss.fff} {message.Data?.EventType.ToUpper()} {message.Data?.Uri}";
|
||||||
Trace.WriteLine($"Message: {line}");
|
Trace.WriteLine($"Message: {line}");
|
||||||
|
|
||||||
|
await EventLogLock.WaitAsync();
|
||||||
|
try
|
||||||
|
{
|
||||||
if (EventLog.Count < 1000)
|
if (EventLog.Count < 1000)
|
||||||
{
|
{
|
||||||
EventLog.Add(line);
|
EventLog.Add(line);
|
||||||
@@ -114,6 +120,11 @@ namespace Needlework.Net.Desktop.ViewModels
|
|||||||
EventLog.Add(line);
|
EventLog.Add(line);
|
||||||
_events[line] = message;
|
_events[line] = message;
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
finally
|
||||||
|
{
|
||||||
|
EventLogLock.Release();
|
||||||
|
}
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -7,6 +7,7 @@ using CommunityToolkit.Mvvm.Messaging;
|
|||||||
using Needlework.Net.Desktop.Extensions;
|
using Needlework.Net.Desktop.Extensions;
|
||||||
using Needlework.Net.Desktop.Messages;
|
using Needlework.Net.Desktop.Messages;
|
||||||
using Needlework.Net.Desktop.ViewModels;
|
using Needlework.Net.Desktop.ViewModels;
|
||||||
|
using System;
|
||||||
using TextMateSharp.Grammars;
|
using TextMateSharp.Grammars;
|
||||||
|
|
||||||
namespace Needlework.Net.Desktop.Views;
|
namespace Needlework.Net.Desktop.Views;
|
||||||
@@ -14,6 +15,8 @@ namespace Needlework.Net.Desktop.Views;
|
|||||||
public partial class WebsocketView : UserControl, IRecipient<ResponseUpdatedMessage>
|
public partial class WebsocketView : UserControl, IRecipient<ResponseUpdatedMessage>
|
||||||
{
|
{
|
||||||
private TextEditor? _responseEditor;
|
private TextEditor? _responseEditor;
|
||||||
|
public WebsocketViewModel? _viewModel;
|
||||||
|
private ListBox? _viewer;
|
||||||
|
|
||||||
public WebsocketView()
|
public WebsocketView()
|
||||||
{
|
{
|
||||||
@@ -29,9 +32,9 @@ public partial class WebsocketView : UserControl, IRecipient<ResponseUpdatedMess
|
|||||||
{
|
{
|
||||||
base.OnApplyTemplate(e);
|
base.OnApplyTemplate(e);
|
||||||
|
|
||||||
var vm = (WebsocketViewModel)DataContext!;
|
_viewModel = (WebsocketViewModel)DataContext!;
|
||||||
var viewer = this.FindControl<ListBox>("EventViewer");
|
_viewer = this.FindControl<ListBox>("EventViewer");
|
||||||
vm.EventLog.CollectionChanged += (s, e) => { if (vm.IsTail) viewer!.ScrollIntoView(vm.EventLog.Count - 1); };
|
_viewModel.EventLog.CollectionChanged += EventLog_CollectionChanged; ;
|
||||||
|
|
||||||
_responseEditor = this.FindControl<TextEditor>("ResponseEditor");
|
_responseEditor = this.FindControl<TextEditor>("ResponseEditor");
|
||||||
_responseEditor?.ApplyJsonEditorSettings();
|
_responseEditor?.ApplyJsonEditorSettings();
|
||||||
@@ -41,6 +44,26 @@ public partial class WebsocketView : UserControl, IRecipient<ResponseUpdatedMess
|
|||||||
OnBaseThemeChanged(Application.Current!.ActualThemeVariant);
|
OnBaseThemeChanged(Application.Current!.ActualThemeVariant);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private void EventLog_CollectionChanged(object? sender, System.Collections.Specialized.NotifyCollectionChangedEventArgs e)
|
||||||
|
{
|
||||||
|
Avalonia.Threading.Dispatcher.UIThread.Post(async () =>
|
||||||
|
{
|
||||||
|
if (_viewModel!.IsTail)
|
||||||
|
{
|
||||||
|
await _viewModel.EventLogLock.WaitAsync();
|
||||||
|
try
|
||||||
|
{
|
||||||
|
_viewer!.ScrollIntoView(_viewModel.EventLog.Count - 1);
|
||||||
|
}
|
||||||
|
catch (InvalidOperationException) { }
|
||||||
|
finally
|
||||||
|
{
|
||||||
|
_viewModel.EventLogLock.Release();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
private void OnBaseThemeChanged(ThemeVariant currentTheme)
|
private void OnBaseThemeChanged(ThemeVariant currentTheme)
|
||||||
{
|
{
|
||||||
|
|
||||||
|
|||||||
Reference in New Issue
Block a user