【问题标题】:How can cake build arguments be documented?如何记录蛋糕构建参数?
【发布时间】:2017-07-31 10:34:38
【问题描述】:

在蛋糕构建脚本中,有一种非常简洁的方法可以使用任务上的 .Description() 扩展名来记录任务。当使用 -showdescription 参数调用构建脚本时会显示这些描述。

我的构建脚本中有几个自定义参数,我想以某种方式记录它们。目前,我添加了一个任务,该任务输出类似于manual page style 的描述文本,可用参数如下所示:

var nextLineDescription = "\n\t\t\t\t\t"; // for formatting 
Console.WriteLine("ARGUMENTS");
Console.WriteLine("");

Console.WriteLine("\t--someparameter=<number>\t\t" +
                "Description of the parameter" + nextLineDescription +
                "that can span multiple lines" + nextLineDescription +
                "and defaults to 5.\n");

这很好用,但工作量很大,特别是如果文本应该正确格式化以便在命令行中可读。

所以当我打电话给./build.ps1 -Target MyDocTask 我得到了一个不错的结果:

论据 --someparameter=number 参数说明 可以跨越多行 并且默认为 5 --nextParameter 下一个描述 ...

是否有另一种方法或最佳实践来为参数添加文档,以便它可以在类似于任务描述的命令行中显示?

编辑: 或者,我是否可以在我的构建脚本中找到所有可用参数来循环它们并生成这样的描述,而不是为每个参数手动编写它?

【问题讨论】:

  • 我写这篇评论是因为您特别询问了 Cake。然而,Nuke 提供了这个功能:nuke.build/command-line.html(我是维护者)。

标签: c# build documentation cakebuild


【解决方案1】:

目前没有用于“注册”参数以寻求帮助的内置功能,不过这将是一个很好的补充,所以请提出一个关于此的问题。

也就是说可以实现,因为 Cake 只是 .NET,您可以利用 NuGet 上可用的命令行解析器之一来实现这一点。一个这样的解析器是CommandLineParser

可以使用#addin 指令从 NuGet 引用程序集,对于 CommandLineParser,它如下所示

#addin "nuget:?package=CommandLineParser&version=2.1.1-beta&prerelease=true"

由于它不是“原生”Cake 插件,您需要使用完全限定的类型名称,或者像常规 C# 一样添加这样的 using 语句

using CommandLine;

CommandLineParser 使用类和属性上的属性来提供规则和帮助。在下面移植您的示例将如下所示

class Options
{
    [Option("someparameter",
        HelpText = "Description of the parameter, that can span multiple lines",
        Default = 5)]
    public int SomeParameter { get; set; }

    [Option("nextParameter", HelpText = "Next description")]
    public string NextParameter { get; set; }

    [Option("target", HelpText = "Target", Default = "Default")]
    public string Target { get; set; }
}

通常 CommandLineParser 会向控制台输出帮助,但如果您想在任务中显示它,您可以使用 TextWriter 捕获输出

var helpWriter = new StringWriter();
var parser = new Parser(config => config.HelpWriter = helpWriter);

然后解析参数,如果指定了“MyDocTask”,则将帮助呈现给helpWriter

Options options = parser
    .ParseArguments<Options>(
        StringComparer.OrdinalIgnoreCase.Equals(Argument("target", "Default"), "MyDocTask")
            ? new []{ "--help" }
            : System.Environment.GetCommandLineArgs()
    )
    .MapResult(
        o => o,
        errors=> new Options { Target = "MyDocTask"} // TODO capture errors here
);

和任务

Task("MyDocTask")
    .Does(() => {
        Information(helpWriter.ToString());
}
);

Task("Default")
    .Does(() => {
        Information("SomeParameter: {0}", options.SomeParameter);
        Information("NextParameter: {0}", options.NextParameter);
        Information("Target: {0}", options.Target);
}
);

然后执行

RunTarget(options.Target);

MyDocTask 将输出帮助

>> cake .\commandline.cake --Target="MyDocTask"

========================================
MyDocTask
========================================
Cake 0.20.0+Branch.main.Sha.417d1eb9097a6c71ab25736687162c0f58bbb74a
Copyright (c) .NET Foundation and Contributors

  --someparameter    (Default: 5) Description of the parameter, that can span multiple lines

  --nextParameter    Next description

  --target           (Default: Default) Target

  --help             Display this help screen.

  --version          Display version information.

Default 任务只会输出解析参数的值

>> cake .\commandline.cake

========================================
Default
========================================
SomeParameter: 5
NextParameter: [NULL]
Target: Default

Task                          Duration
--------------------------------------------------
Default                       00:00:00.0133265
--------------------------------------------------
Total:                        00:00:00.0133265

这将以一种相当简单的方式为您提供强类型和文档化的参数。

完整的 Cake 脚本如下:

#addin "nuget:?package=CommandLineParser&version=2.1.1-beta&prerelease=true"
using CommandLine;
class Options
{
    [Option("someparameter",
        HelpText = "Description of the parameter, that can span multiple lines",
        Default = 5)]
    public int SomeParameter { get; set; }

    [Option("nextParameter", HelpText = "Next description")]
    public string NextParameter { get; set; }

    [Option("target", HelpText = "Target", Default = "Default")]
    public string Target { get; set; }
}

var helpWriter = new StringWriter();
var parser = new Parser(config => config.HelpWriter = helpWriter);

    Options options = parser
        .ParseArguments<Options>(
            StringComparer.OrdinalIgnoreCase.Equals(Argument("target", "Default"), "MyDocTask")
                ? new []{ "--help" }
                : System.Environment.GetCommandLineArgs()
        )
        .MapResult(
            o => o,
            errors=> new Options { Target = "MyDocTask"} // could capture errors here
    );


    Task("MyDocTask")
        .Does(() => {
            Information(helpWriter.ToString());
    }
    );

    Task("Default")
        .Does(() => {
            Information("SomeParameter: {0}", options.SomeParameter);
            Information("NextParameter: {0}", options.NextParameter);
            Information("Target: {0}", options.Target);
    }
    );


RunTarget(options.Target);

【讨论】:

  • 感谢您的详细描述。这似乎是一个不错的选择。我只是在玩它,直接使用 cake 可执行文件时看起来不错。当使用 bootstrap powershell 文件时,它使用显式命名参数 -target -configuration -verbosity 调用 cake。请注意,仅使用一个- 调用它。这会导致 CommandLineParser 始终转到错误路径,因为它表示未找到参数 t、c 和 v。它需要带有双破折号的参数。正如建议的那样,我直接为蛋糕创建了一个问题:github.com/cake-build/cake/issues/1708
  • 实际上 cake 也支持双破折号,并且可能将来会成为标准,双破折号表示完整命令,单短划线即 -t 或 --target
  • 是的,我的自定义参数也使用双破折号。我只是想暗示一下,powershell 脚本使用单破折号 atm。 :)
  • 因此您可以将引导程序更改为 --target --configuration --verbosity 并且一切仍然有效。
猜你喜欢
  • 1970-01-01
  • 2018-02-14
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多