Skip to content

Commit

Permalink
Merge branch 'main' into feature/dev-2953-update-help-and-usageyaml-w…
Browse files Browse the repository at this point in the history
…ith-snapshots
  • Loading branch information
osterman authored Feb 12, 2025
2 parents 3f19100 + 2ccb7be commit 46e53e2
Show file tree
Hide file tree
Showing 4 changed files with 109 additions and 4 deletions.
39 changes: 35 additions & 4 deletions cmd/cmd_utils.go
Original file line number Diff line number Diff line change
Expand Up @@ -79,7 +79,8 @@ func processCustomCommands(
executeCustomCommand(atmosConfig, cmd, args, parentCommand, commandConfig)
},
}

// TODO: we need to update this post https://github.com/cloudposse/atmos/pull/959 gets merged
customCommand.PersistentFlags().Bool("", false, "Use double dashes to separate Atmos-specific options from native arguments and flags for the command.")
// Process and add flags to the command
for _, flag := range commandConfig.Flags {
if flag.Type == "bool" {
Expand Down Expand Up @@ -304,7 +305,7 @@ func executeCustomCommand(
commandConfig *schema.Command,
) {
var err error

args, trailingArgs := extractTrailingArgs(args, os.Args)
if commandConfig.Verbose {
atmosConfig.Logs.Level = u.LogLevelTrace
}
Expand Down Expand Up @@ -345,8 +346,9 @@ func executeCustomCommand(

// Prepare template data
data := map[string]any{
"Arguments": argumentsData,
"Flags": flagsData,
"Arguments": argumentsData,
"Flags": flagsData,
"TrailingArgs": trailingArgs,
}

// If the custom command defines 'component_config' section with 'component' and 'stack' attributes,
Expand Down Expand Up @@ -441,6 +443,35 @@ func executeCustomCommand(
}
}

// Extracts native arguments (everything after "--") signifying the end of Atmos-specific arguments.
// Because of the flag hint for double dash, args is already consumed by Cobra.
// So we need to perform manual parsing of os.Args to extract the "trailing args" after the "--" end of args marker.
func extractTrailingArgs(args []string, osArgs []string) ([]string, string) {
doubleDashIndex := lo.IndexOf(osArgs, "--")
mainArgs := args
trailingArgs := ""
if doubleDashIndex > 0 {
mainArgs = lo.Slice(osArgs, 0, doubleDashIndex)
trailingArgs = strings.Join(lo.Slice(osArgs, doubleDashIndex+1, len(osArgs)), " ")
result := []string{}
lookup := make(map[string]bool)

// Populate a lookup map for quick existence check
for _, val := range mainArgs {
lookup[val] = true
}

// Iterate over leftArr and collect matching elements in order
for _, val := range args {
if lookup[val] {
result = append(result, val)
}
}
mainArgs = result
}
return mainArgs, trailingArgs
}

// cloneCommand clones a custom command config into a new struct
func cloneCommand(orig *schema.Command) (*schema.Command, error) {
origJSON, err := json.Marshal(orig)
Expand Down
23 changes: 23 additions & 0 deletions tests/fixtures/scenarios/custom-command/atmos.yaml
Original file line number Diff line number Diff line change
@@ -0,0 +1,23 @@
base_path: "./"

stacks:
base_path: "stacks"
included_paths:
- "deploy/**/*"
logs:
file: "/dev/stderr"
level: Info

commands:
# # Use positional arguments with default values
- name: echo
description: "Displays a args before and after double dash."
arguments:
- name: name
description: >-
Enter your string as an argument
required: true
default: before double dash
steps:
- "echo Cobra Args: [{{ .Arguments.name }}]"
- "echo Trailing Args: [{{ .TrailingArgs }}]"
23 changes: 23 additions & 0 deletions tests/test-cases/custom-command.yaml
Original file line number Diff line number Diff line change
@@ -0,0 +1,23 @@
tests:
- name: double dash should work
enabled: true
description: "Validate atmos custom command greet runs with argument provided."
workdir: "fixtures/scenarios/custom-command"
command: "atmos"
args:
- "echo"
- "Name"
- "--"
- "-this"
- "--is"
- "trailing"
- "-"
- "arg"
expect:
diff: []
stdout:
- "Cobra Args: \\[Name\\]"
- "Trailing Args: \\[-this --is trailing - arg\\]"
stderr:
- "^$"
exit_code: 0
28 changes: 28 additions & 0 deletions website/docs/core-concepts/custom-commands/custom-commands.mdx
Original file line number Diff line number Diff line change
Expand Up @@ -70,6 +70,34 @@ or defaulting to "John Doe"
atmos greet
```

## Trailing Arguments

Atmos supports **trailing arguments** after `--` (a standalone double-dash). The `--` itself is a delimiter that signals the end of Atmos-specific options. Anything after `--` is passed directly to the underlying command without being interpreted by Atmos. The value of these trailing arguments is accessible in `{{ .TrailingArgs }}`.

For the example, adding the following to `atmos.yaml` will introduce a new `echo` command that accepts one `name` argument and also uses trailingArgs

```yaml
- name: ansible run
description: "Runs an Ansible playbook, allowing extra arguments after --."
arguments:
- name: playbook
description: "The Ansible playbook to run"
default: site.yml
required: true
steps:
- "ansible-playbook {{ .Arguments.playbook }} {{ .TrailingArgs }}"
```
Output:
```bash
$ atmos ansible run -- --limit web
Running: ansible-playbook site.yml --limit web

PLAY [web] *********************************************************************

```


## Passing Flags

Passing flags works much like passing positional arguments, except for that they are passed using long or short flags.
Expand Down

0 comments on commit 46e53e2

Please sign in to comment.