共用方式為


如何自定義System.CommandLine中的剖析和驗證

根據預設, System.CommandLine 提供一組內建剖析器,可剖析許多常見類型:

  • bool
  • bytesbyte
  • shortushort
  • intuint
  • longulong
  • floatdouble
  • decimal
  • DateTimeDateTimeOffset
  • DateOnlyTimeOnly
  • Guid
  • FileSystemInfoFileInfoDirectoryInfo
  • 列舉
  • 列出的類型的陣列和清單

不支援其他類型,但您可以為其建立自定義剖析器。 您也可以驗證剖析的值,這在您想要確保輸入符合特定準則時很有用。

驗證者

每個選項、自變數和命令都可以有一或多個驗證程式。 驗證程式是用來確保剖析的值符合特定準則。 例如,您可以驗證數位為正數,或是字串不是空的。 您也可以建立複雜的驗證程式,以檢查多個條件。

中的每個 System.CommandLine 符號類型都有一個 Validators 屬性,其中包含驗證程序清單。 驗證程式會在剖析輸入之後執行,而且如果驗證失敗,則可以報告錯誤。

若要提供自訂驗證程式碼,請在您的選項或自變數上呼叫 System.CommandLine.Option.Validators.Add ,如下列範例所示:

Option<int> delayOption = new("--delay");
delayOption.Validators.Add(result =>
{
    if (result.GetValue(delayOption) < 1)
    {
        result.AddError("Must be greater than 0");
    }
});

System.CommandLine 提供一組內建驗證程式,可用來驗證一般類型:

  • AcceptExistingOnly - 將指定的選項或自變數設定為只接受對應至現有檔案或目錄的值。
  • AcceptLegalFileNamesOnly - 將指定的選項或自變數設定為只接受代表合法檔名的值。
  • AcceptOnlyFromAmong - 將指定的選項或自變數設定為只接受來自指定值集的值。

自定義剖析器

若要剖析沒有預設剖析器的類型,例如複雜類型,您需要自定義剖析器。 自定義剖析器也可以用來以不同於內建剖析器的方式來剖析支持的類型。

假設您有一個Person 類型。

public class Person
{
    public string? FirstName { get; set; }
    public string? LastName { get; set; }
}

您可以在命令操作中讀取值並建立Person的實例:

rootCommand.SetAction(parseResult =>
{
    Person person = new()
    {
        FirstName = parseResult.GetValue(firstNameOption),
        LastName = parseResult.GetValue(lastNameOption)
    };
    DoRootCommand(parseResult.GetValue(fileOption), person);
});

使用自訂剖析器,您可以取得自訂類型,方式與取得基本值的方式相同:

Option<Person?> personOption = new("--person")
{
    Description = "An option whose argument is parsed as a Person",
    CustomParser = result =>
    {
        if (result.Tokens.Count != 2)
        {
            result.AddError("--person requires two arguments");
            return null;
        }
        return new Person
        {
            FirstName = result.Tokens.First().Value,
            LastName = result.Tokens.Last().Value
        };
    }
};

如果您要剖析及驗證輸入,請使用 CustomParser 委派,如下列範例所示:

Option<int> delayOption = new("--delay")
{
    Description = "An option whose argument is parsed as an int.",
    CustomParser = result =>
    {
        if (!result.Tokens.Any())
        {
            return 42;
        }

        if (int.TryParse(result.Tokens.Single().Value, out var delay))
        {
            if (delay < 1)
            {
                result.AddError("Must be greater than 0");
            }
            return delay;
        }
        else
        {
            result.AddError("Not an int.");
            return 0; // Ignored.
        }
    }
};

以下是一些您可以使用 CustomParser,而不是驗證程式,來執行的動作範例:

  • 剖析其他類型的輸入字串(例如,將 “1,2,3” 剖析為 int[])。
  • 動態參數個數。 例如,如果您有兩個自變數定義為字串陣列,而且您必須在命令行輸入中處理一連串字串,則 System.CommandLine.Parsing.ArgumentResult.OnlyTake 方法可讓您動態分割自變數之間的輸入字串。

另請參閱