diff --git a/DevProxy/Commands/DevProxyCommand.cs b/DevProxy/Commands/DevProxyCommand.cs
index e3db039b..b41848f0 100644
--- a/DevProxy/Commands/DevProxyCommand.cs
+++ b/DevProxy/Commands/DevProxyCommand.cs
@@ -43,6 +43,8 @@ sealed class DevProxyCommand : RootCommand
private static bool _hasGlobalOptionsResolved;
private static bool _isStdioCommandResolved;
+ private static bool _isJwtCommandResolved;
+ private static bool _isRootCommandResolved;
private static bool _stdioLogFilePathResolved;
public static bool HasGlobalOptions
@@ -78,6 +80,47 @@ public static bool IsStdioCommand
}
}
+ public static bool IsJwtCommand
+ {
+ get
+ {
+ if (_isJwtCommandResolved)
+ {
+ return field;
+ }
+
+ var args = Environment.GetCommandLineArgs();
+ field = args.Length > 1 && string.Equals(args[1], "jwt", StringComparison.OrdinalIgnoreCase);
+ _isJwtCommandResolved = true;
+ return field;
+ }
+ }
+
+ ///
+ /// Determines if the root command (proxy itself) is being invoked.
+ /// Returns true when no subcommand is specified (only options or no args).
+ /// A subcommand is detected when the first non-program argument doesn't start with '-'.
+ ///
+ public static bool IsRootCommand
+ {
+ get
+ {
+ if (_isRootCommandResolved)
+ {
+ return field;
+ }
+
+ var args = Environment.GetCommandLineArgs();
+ // Skip the first argument which is the program name
+ // If there are no more arguments, it's the root command
+ // If the first argument starts with '-', it's an option (root command)
+ // Otherwise, it's a subcommand name
+ field = args.Length <= 1 || args[1].StartsWith('-');
+ _isRootCommandResolved = true;
+ return field;
+ }
+ }
+
public static string StdioLogFilePath
{
get
diff --git a/DevProxy/Extensions/ILoggingBuilderExtensions.cs b/DevProxy/Extensions/ILoggingBuilderExtensions.cs
index 00735f24..32c26fe4 100644
--- a/DevProxy/Extensions/ILoggingBuilderExtensions.cs
+++ b/DevProxy/Extensions/ILoggingBuilderExtensions.cs
@@ -39,15 +39,53 @@ public static ILoggingBuilder ConfigureDevProxyLogging(
return builder;
}
+ // For jwt command, suppress all logging to console to avoid interfering with token output
+ if (DevProxyCommand.IsJwtCommand)
+ {
+ _ = builder
+ .ClearProviders()
+ .SetMinimumLevel(LogLevel.None);
+ return builder;
+ }
+
+ // For root command (proxy itself), use rich logging
+ if (DevProxyCommand.IsRootCommand)
+ {
+ _ = builder
+ .AddFilter("Microsoft.Hosting.*", LogLevel.Error)
+ .AddFilter("Microsoft.AspNetCore.*", LogLevel.Error)
+ .AddFilter("Microsoft.Extensions.*", LogLevel.Error)
+ .AddFilter("System.*", LogLevel.Error)
+ // Only show plugin messages when no global options are set
+ .AddFilter("DevProxy.Plugins.*", level =>
+ level >= configuredLogLevel &&
+ !DevProxyCommand.HasGlobalOptions)
+ .AddConsole(options =>
+ {
+ options.FormatterName = ProxyConsoleFormatter.DefaultCategoryName;
+ options.LogToStandardErrorThreshold = LogLevel.Warning;
+ }
+ )
+ .AddConsoleFormatter(options =>
+ {
+ options.IncludeScopes = true;
+ options.ShowSkipMessages = configuration.GetValue("showSkipMessages", true);
+ options.ShowTimestamps = configuration.GetValue("showTimestamps", true);
+ }
+ )
+ .AddRequestLogger()
+ .SetMinimumLevel(configuredLogLevel);
+ return builder;
+ }
+
+ // For other subcommands (cert, config, outdated, msgraphdb), use rich logging
+ // but with plugin messages filtered out
_ = builder
.AddFilter("Microsoft.Hosting.*", LogLevel.Error)
.AddFilter("Microsoft.AspNetCore.*", LogLevel.Error)
.AddFilter("Microsoft.Extensions.*", LogLevel.Error)
.AddFilter("System.*", LogLevel.Error)
- // Only show plugin messages when no global options are set
- .AddFilter("DevProxy.Plugins.*", level =>
- level >= configuredLogLevel &&
- !DevProxyCommand.HasGlobalOptions)
+ .AddFilter("DevProxy.Plugins.*", LogLevel.None)
.AddConsole(options =>
{
options.FormatterName = ProxyConsoleFormatter.DefaultCategoryName;
@@ -61,7 +99,6 @@ public static ILoggingBuilder ConfigureDevProxyLogging(
options.ShowTimestamps = configuration.GetValue("showTimestamps", true);
}
)
- .AddRequestLogger()
.SetMinimumLevel(configuredLogLevel);
return builder;