diff --git a/Flow.Launcher.Core/Plugin/JsonRPCPlugin.cs b/Flow.Launcher.Core/Plugin/JsonRPCPlugin.cs index 88d595301be..b19bb6c79af 100644 --- a/Flow.Launcher.Core/Plugin/JsonRPCPlugin.cs +++ b/Flow.Launcher.Core/Plugin/JsonRPCPlugin.cs @@ -1,5 +1,4 @@ -using Flow.Launcher.Core.Resource; -using System; +using System; using System.Collections.Generic; using System.Diagnostics; using System.IO; @@ -7,10 +6,9 @@ using System.Text.Json; using System.Threading; using System.Threading.Tasks; -using Flow.Launcher.Infrastructure.Logger; +using Flow.Launcher.Core.Resource; using Flow.Launcher.Plugin; using Microsoft.IO; -using System.Windows; namespace Flow.Launcher.Core.Plugin { @@ -20,7 +18,9 @@ namespace Flow.Launcher.Core.Plugin /// internal abstract class JsonRPCPlugin : JsonRPCPluginBase { - public const string JsonRPC = "JsonRPC"; + public new const string JsonRPC = "JsonRPC"; + + private static readonly string ClassName = nameof(JsonRPCPlugin); protected abstract Task RequestAsync(JsonRPCRequestModel rpcRequest, CancellationToken token = default); protected abstract string Request(JsonRPCRequestModel rpcRequest, CancellationToken token = default); @@ -29,9 +29,6 @@ internal abstract class JsonRPCPlugin : JsonRPCPluginBase private int RequestId { get; set; } - private string SettingConfigurationPath => Path.Combine(Context.CurrentPluginMetadata.PluginDirectory, "SettingsTemplate.yaml"); - private string SettingPath => Path.Combine(Context.CurrentPluginMetadata.PluginSettingsDirectoryPath, "Settings.json"); - public override List LoadContextMenus(Result selectedResult) { var request = new JsonRPCRequestModel(RequestId++, @@ -57,13 +54,6 @@ public override List LoadContextMenus(Result selectedResult) } }; - private static readonly JsonSerializerOptions settingSerializeOption = new() - { - WriteIndented = true - }; - - private readonly Dictionary _settingControls = new(); - private async Task> DeserializedResultAsync(Stream output) { await using (output) @@ -122,7 +112,6 @@ protected override async Task ExecuteResultAsync(JsonRPCResult result) return !result.JsonRPCAction.DontHideAfterAction; } - /// /// Execute external program and return the output /// @@ -160,11 +149,11 @@ protected string Execute(ProcessStartInfo startInfo) var error = standardError.ReadToEnd(); if (!string.IsNullOrEmpty(error)) { - Log.Error($"|JsonRPCPlugin.Execute|{error}"); + Context.API.LogError(ClassName, error); return string.Empty; } - Log.Error("|JsonRPCPlugin.Execute|Empty standard output and standard error."); + Context.API.LogError(ClassName, "Empty standard output and standard error."); return string.Empty; } @@ -172,8 +161,8 @@ protected string Execute(ProcessStartInfo startInfo) } catch (Exception e) { - Log.Exception( - $"|JsonRPCPlugin.Execute|Exception for filename <{startInfo.FileName}> with argument <{startInfo.Arguments}>", + Context.API.LogException(ClassName, + $"Exception for filename <{startInfo.FileName}> with argument <{startInfo.Arguments}>", e); return string.Empty; } @@ -184,7 +173,7 @@ protected async Task ExecuteAsync(ProcessStartInfo startInfo, Cancellati using var process = Process.Start(startInfo); if (process == null) { - Log.Error("|JsonRPCPlugin.ExecuteAsync|Can't start new process"); + Context.API.LogError(ClassName, "Can't start new process"); return Stream.Null; } @@ -204,7 +193,7 @@ protected async Task ExecuteAsync(ProcessStartInfo startInfo, Cancellati } catch (Exception e) { - Log.Exception("|JsonRPCPlugin.ExecuteAsync|Exception when kill process", e); + Context.API.LogException(ClassName, "Exception when kill process", e); } }); @@ -225,7 +214,7 @@ protected async Task ExecuteAsync(ProcessStartInfo startInfo, Cancellati { case (0, 0): const string errorMessage = "Empty JSON-RPC Response."; - Log.Warn($"|{nameof(JsonRPCPlugin)}.{nameof(ExecuteAsync)}|{errorMessage}"); + Context.API.LogWarn(ClassName, errorMessage); break; case (_, not 0): throw new InvalidDataException(Encoding.UTF8.GetString(errorBuffer.ToArray())); // The process has exited with an error message diff --git a/Flow.Launcher.Core/Plugin/JsonRPCPluginBase.cs b/Flow.Launcher.Core/Plugin/JsonRPCPluginBase.cs index 779dcf887d8..df0438409f3 100644 --- a/Flow.Launcher.Core/Plugin/JsonRPCPluginBase.cs +++ b/Flow.Launcher.Core/Plugin/JsonRPCPluginBase.cs @@ -1,11 +1,11 @@ -using Flow.Launcher.Core.Resource; -using System; +using System; using System.Collections.Generic; using System.IO; using System.Linq; using System.Text.Json; using System.Threading; using System.Threading.Tasks; +using Flow.Launcher.Core.Resource; using Flow.Launcher.Plugin; using YamlDotNet.Serialization; using YamlDotNet.Serialization.NamingConventions; @@ -19,10 +19,9 @@ namespace Flow.Launcher.Core.Plugin /// public abstract class JsonRPCPluginBase : IAsyncPlugin, IContextMenu, ISettingProvider, ISavable { - protected PluginInitContext Context; public const string JsonRPC = "JsonRPC"; - private int RequestId { get; set; } + protected PluginInitContext Context; private string SettingConfigurationPath => Path.Combine(Context.CurrentPluginMetadata.PluginDirectory, "SettingsTemplate.yaml"); @@ -107,7 +106,6 @@ protected void ExecuteFlowLauncherAPI(string method, object[] parameters) public abstract Task> QueryAsync(Query query, CancellationToken token); - private async Task InitSettingAsync() { JsonRpcConfigurationModel configuration = null; @@ -119,7 +117,6 @@ private async Task InitSettingAsync() await File.ReadAllTextAsync(SettingConfigurationPath)); } - Settings ??= new JsonRPCPluginSettings { Configuration = configuration, SettingPath = SettingPath, API = Context.API @@ -130,7 +127,7 @@ private async Task InitSettingAsync() public virtual async Task InitAsync(PluginInitContext context) { - this.Context = context; + Context = context; await InitSettingAsync(); } diff --git a/Flow.Launcher.Core/Plugin/JsonRPCPluginV2.cs b/Flow.Launcher.Core/Plugin/JsonRPCPluginV2.cs index abe563c145a..148fd969e49 100644 --- a/Flow.Launcher.Core/Plugin/JsonRPCPluginV2.cs +++ b/Flow.Launcher.Core/Plugin/JsonRPCPluginV2.cs @@ -10,20 +10,20 @@ using StreamJsonRpc; using IAsyncDisposable = System.IAsyncDisposable; - namespace Flow.Launcher.Core.Plugin { internal abstract class JsonRPCPluginV2 : JsonRPCPluginBase, IAsyncDisposable, IAsyncReloadable, IResultUpdated { public const string JsonRpc = "JsonRPC"; + private static readonly string ClassName = nameof(JsonRPCPluginV2); + protected abstract IDuplexPipe ClientPipe { get; set; } protected StreamReader ErrorStream { get; set; } private JsonRpc RPC { get; set; } - protected override async Task ExecuteResultAsync(JsonRPCResult result) { var res = await RPC.InvokeAsync(result.JsonRPCAction.Method, @@ -55,7 +55,6 @@ public override async Task> QueryAsync(Query query, CancellationTok return results; } - public override async Task InitAsync(PluginInitContext context) { await base.InitAsync(context); @@ -88,7 +87,6 @@ protected enum MessageHandlerType protected abstract MessageHandlerType MessageHandler { get; } - private void SetupJsonRPC() { var formatter = new SystemTextJsonFormatter { JsonSerializerOptions = RequestSerializeOption }; @@ -118,8 +116,17 @@ public virtual async Task ReloadDataAsync() { await RPC.InvokeAsync("reload_data", Context); } - catch (RemoteMethodNotFoundException e) + catch (RemoteMethodNotFoundException) + { + // Ignored + } + catch (ConnectionLostException) { + // Ignored + } + catch (Exception e) + { + Context.API.LogException(ClassName, $"Failed to call reload_data for plugin {Context.CurrentPluginMetadata.Name}", e); } } @@ -129,8 +136,17 @@ public virtual async ValueTask DisposeAsync() { await RPC.InvokeAsync("close"); } - catch (RemoteMethodNotFoundException e) + catch (RemoteMethodNotFoundException) + { + // Ignored + } + catch (ConnectionLostException) + { + // Ignored + } + catch (Exception e) { + Context.API.LogException(ClassName, $"Failed to call close for plugin {Context.CurrentPluginMetadata.Name}", e); } finally {