Skip to content

Commit 369bf80

Browse files
committed
最终还是在 CommandLine 里把 Runner 放进去了。不过两者都支持
1 parent 73dbbcf commit 369bf80

4 files changed

Lines changed: 32 additions & 17 deletions

File tree

src/DotNetCampus.CommandLine.Analyzer/Generators/InterceptorGenerator.cs

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -151,7 +151,7 @@ private void GenerateCommandLineAddHandlerCode(TypeDeclarationSourceTextBuilder
151151
.AddTypeConstraints("where T : class, global::DotNetCampus.Cli.ICommandHandler")
152152
.AddRawStatement(GenerateComment(model))
153153
.AddRawStatements($"""
154-
return commandLine.ToRunner().AddHandler<T>(global::{model.CommandObjectType.ContainingNamespace}.{model.GetBuilderTypeName()}.CommandNameGroup, global::{model.CommandObjectType.ContainingNamespace}.{model.GetBuilderTypeName()}.CreateInstance);
154+
return commandLine.AsRunner().AddHandler<T>(global::{model.CommandObjectType.ContainingNamespace}.{model.GetBuilderTypeName()}.CommandNameGroup, global::{model.CommandObjectType.ContainingNamespace}.{model.GetBuilderTypeName()}.CreateInstance);
155155
"""));
156156
}
157157

@@ -166,7 +166,7 @@ private void GenerateCommandLineAddHandlerActionCode(TypeDeclarationSourceTextBu
166166
.AddTypeConstraints("where T : class")
167167
.AddRawStatement(GenerateComment(model))
168168
.AddRawStatements($"""
169-
return commandLine.ToRunner().AddHandler<T>(handler, global::{model.CommandObjectType.ContainingNamespace}.{model.GetBuilderTypeName()}.CommandNameGroup, global::{model.CommandObjectType.ContainingNamespace}.{model.GetBuilderTypeName()}.CreateInstance);
169+
return commandLine.AsRunner().AddHandler<T>(handler, global::{model.CommandObjectType.ContainingNamespace}.{model.GetBuilderTypeName()}.CommandNameGroup, global::{model.CommandObjectType.ContainingNamespace}.{model.GetBuilderTypeName()}.CreateInstance);
170170
"""));
171171
}
172172

src/DotNetCampus.CommandLine/CommandLine.cs

Lines changed: 27 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -9,8 +9,13 @@ namespace DotNetCampus.Cli;
99
/// <summary>
1010
/// 为应用程序提供统一的命令行参数解析功能。
1111
/// </summary>
12-
public class CommandLine
12+
public class CommandLine : ICommandRunnerBuilder
1313
{
14+
/// <summary>
15+
/// 存储与此命令行解析类型关联的命令行执行器。
16+
/// </summary>
17+
private CommandRunner? _runner;
18+
1419
/// <summary>
1520
/// 存储特殊处理过 URL 的命令行参数。
1621
/// </summary>
@@ -129,14 +134,34 @@ public string ToRawString()
129134
return string.Join(" ", RawArguments.Select(x => x.Contains(' ') ? $"\"{x}\"" : x));
130135
}
131136

137+
/// <summary>
138+
/// 将当前命令行对象视作一个命令行执行器,以支持根据命令自动选择命令处理器运行。<br/>
139+
/// 随后后,可通过 AddHandler 方法添加多个命令处理器。
140+
/// </summary>
141+
/// <returns>命令行执行器。</returns>
142+
/// <remarks>
143+
/// 与 <see cref="ToRunner"/> 方法不同,本方法每次都会返回同一个命令行执行器实例。<br/>
144+
/// 如果多次调用本方法,后续对命令行执行器的修改会影响之前获得的命令行执行器。
145+
/// </remarks>
146+
public ICommandRunnerBuilder AsRunner() => _runner ??= new CommandRunner(this);
147+
132148
/// <summary>
133149
/// 创建一个命令行执行器,以支持根据命令自动选择命令处理器运行。<br/>
134150
/// 创建后,可通过 AddHandler 方法添加多个命令处理器。
135151
/// </summary>
136152
/// <returns>命令行执行器。</returns>
137-
[Pure]
153+
/// <remarks>
154+
/// 与 <see cref="AsRunner"/> 方法不同,本方法每次都会返回一个新的命令行执行器实例。<br/>
155+
/// 如果多次调用本方法,后续对命令行执行器的修改不会影响之前获得的命令行执行器。
156+
/// </remarks>
138157
public ICommandRunnerBuilder ToRunner() => new CommandRunner(this);
139158

159+
/// <inheritdoc />
160+
CommandRunner ICoreCommandRunnerBuilder.AsRunner() => _runner ??= new CommandRunner(this);
161+
162+
/// <inheritdoc />
163+
CommandRunningResult ICommandRunnerBuilder.Run() => AsRunner().Run();
164+
140165
/// <summary>
141166
/// 当某个方法本应该被源生成器拦截时,却仍然被调用了,就调用此方法抛出异常。
142167
/// </summary>

src/DotNetCampus.CommandLine/CommandRunnerBuilderExtensions.cs

Lines changed: 1 addition & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -15,11 +15,6 @@ public static class CommandRunnerBuilderExtensions
1515
/// <param name="builder">命令行执行器构造的链式调用。</param>
1616
/// <typeparam name="T">命令处理器的类型。</typeparam>
1717
/// <returns>命令行执行器构造的链式调用。</returns>
18-
/// <remarks>
19-
/// 请注意,<see cref="CommandLine"/> 对象是不可变的,所以你需要使用这个方法的返回值,否则当你再次调用 AddHandler 时,之前添加的处理器将会丢失。<br/>
20-
/// 如果你需要分多次添加处理器,请先调用 <see cref="CommandLine.ToRunner"/> 方法获得 <see cref="ICommandRunnerBuilder"/> 对象;
21-
/// 在这个对象上多次调用 AddHandler 方法是安全的。
22-
/// </remarks>
2318
public static IAsyncCommandRunnerBuilder AddHandler<T>(this CommandLine builder)
2419
{
2520
throw CommandLine.MethodShouldBeInspected();
@@ -34,7 +29,7 @@ public static IAsyncCommandRunnerBuilder AddHandler<T>(this CommandLine builder)
3429
/// <returns>命令行执行器构造的链式调用。</returns>
3530
public static StatedCommandRunnerBuilder<TState> ForState<TState>(this CommandLine builder, TState state)
3631
{
37-
return new StatedCommandRunnerBuilder<TState>(builder.ToRunner().AsRunner(), state);
32+
return new StatedCommandRunnerBuilder<TState>(((ICommandRunnerBuilder)builder).AsRunner(), state);
3833
}
3934

4035
/// <inheritdoc cref="AddHandler{T}(CommandLine,Func{T, Task{int}})" />
@@ -62,11 +57,6 @@ public static IAsyncCommandRunnerBuilder AddHandler<T>(this CommandLine builder,
6257
/// <param name="handler">用于处理已解析的命令行参数的委托。</param>
6358
/// <typeparam name="T">命令处理器的类型。</typeparam>
6459
/// <returns>命令行执行器构造的链式调用。</returns>
65-
/// <remarks>
66-
/// 请注意,<see cref="CommandLine"/> 对象是不可变的,所以你需要使用这个方法的返回值,否则当你再次调用 AddHandler 时,之前添加的处理器将会丢失。<br/>
67-
/// 如果你需要分多次添加处理器,请先调用 <see cref="CommandLine.ToRunner"/> 方法获得 <see cref="ICommandRunnerBuilder"/> 对象;
68-
/// 在这个对象上多次调用 AddHandler 方法是安全的。
69-
/// </remarks>
7060
public static IAsyncCommandRunnerBuilder AddHandler<T>(this CommandLine builder, Func<T, Task<int>> handler)
7161
{
7262
throw CommandLine.MethodShouldBeInspected();

tests/DotNetCampus.CommandLine.Tests/AddHandlerTests.cs

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -230,8 +230,8 @@ public void ChainedCalls_ReturnCorrectBuilderTypes()
230230
var commandLine = CommandLine.Parse(args, Flexible);
231231

232232
// Act
233-
var syncBuilder = commandLine.AddHandler<SimpleOptions>(_ => { });
234-
var asyncBuilder = commandLine.AddHandler<SimpleOptions>(async _ => {
233+
var syncBuilder = commandLine.ToRunner().AddHandler<SimpleOptions>(_ => { });
234+
var asyncBuilder = commandLine.ToRunner().AddHandler<SimpleOptions>(async _ => {
235235
await Task.Delay(1);
236236
return 0;
237237
});

0 commit comments

Comments
 (0)