Files
Bassam (Sam) Khouri a78d98b92d Augment Option to support default as flag option (#830)
In some use cases, there is a need to have an option argument behave
like a flag.

This change introduced 4 new intialiazers to `Option` that accept a
`defaultAsFlag` value.

With the following usage:

```swift
struct Example: ParsableCommand {
    @Option(defaultAsFlag: "default", help: "Set output format.")
    var format: String?
    func run() {
        print("Format: \(format ?? "none")")
    }
}
```

The `defaultAsFlag` parameter creates a hybrid that supports both patterns:
  - **Flag behavior**: `--format` (sets format to "default")
  - **Option behavior**: `--format json` (sets format to "json")
  - **No usage**: format remains `nil`

As a user of the command line tool, the `--help` output clearly distinguishes
between the the hybrid and regular usages.

```
OPTIONS:
  --format [<format>]     Set output format. (default as flag: default)
````

Note the `(default as flag: ...)` text instead of regular `(default: ...)`,
and the optional value syntax `[<value>]` instead of required `<value>`.

Fixes: #829
2026-03-23 14:47:26 -05:00

55 lines
1.7 KiB
Swift

//===----------------------------------------------------------------------===//
//
// This source file is part of the Swift Argument Parser open source project
//
// Copyright (c) 2025 Apple Inc. and the Swift project authors
// Licensed under Apache License v2.0 with Runtime Library Exception
//
// See https://swift.org/LICENSE.txt for license information
//
//===----------------------------------------------------------------------===//
import ArgumentParser
@main
struct DefaultAsFlag: ParsableCommand {
static let configuration = CommandConfiguration(
abstract: "A utility demonstrating defaultAsFlag options.",
discussion: """
This command shows how defaultAsFlag options can work both as flags
and as options with values.
"""
)
@Option(defaultAsFlag: "default", help: "A string option with defaultAsFlag.")
var stringFlag: String?
@Option(defaultAsFlag: 42, help: "An integer option with defaultAsFlag.")
var numberFlag: Int?
@Option(defaultAsFlag: true, help: "A boolean option with defaultAsFlag.")
var boolFlag: Bool?
@Option(
defaultAsFlag: "transformed",
help: "A string option with transform and defaultAsFlag.",
transform: { $0.uppercased() }
)
var transformFlag: String?
@Option(name: .shortAndLong, help: "A regular option for comparison.")
var regular: String?
@Argument
var additionalArgs: [String] = []
func run() {
print("String flag: \(stringFlag?.description ?? "nil")")
print("Number flag: \(numberFlag?.description ?? "nil")")
print("Bool flag: \(boolFlag?.description ?? "nil")")
print("Transform flag: \(transformFlag?.description ?? "nil")")
print("Regular option: \(regular?.description ?? "nil")")
print("Additional args: \(additionalArgs)")
}
}