Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Add parsed_params output #322

Merged
merged 12 commits into from
Nov 22, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
1 change: 1 addition & 0 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -309,6 +309,7 @@ As seen above, we have two steps. One for a noop deploy, and one for a regular d
| `actor` | The GitHub handle of the actor that invoked the IssueOps command |
| `environment` | The environment that has been selected for a deployment |
| `params` | The raw parameters that were passed into the deployment command (see param_separator) - Further [documentation](docs/parameters.md) |
| `parsed_params` | A stringified JSON object of the parsed parameters that were passed into the deployment command - Further [documentation](docs/parameters.md) |
| `noop` | The string "true" if the noop trigger was found, otherwise the string "false" - Use this to conditionally control whether your deployment runs as a noop or not |
| `sha` | The sha of the branch to be deployed |
| `default_branch_tree_sha` | The sha of the default branch tree (useful for subsequent workflow steps if they need to do commit comparisons) |
Expand Down
33 changes: 33 additions & 0 deletions __tests__/functions/environment-targets.test.js
Original file line number Diff line number Diff line change
Expand Up @@ -174,6 +174,39 @@ test('checks the comment body and finds an explicit environment target and an ex
)
})

test('checks the comment body and finds an explicit environment target and an explicit sha (sha1) for development with parsed params style params on a noop command', async () => {
expect(
await environmentTargets(
environment,
'.noop 82c238c277ca3df56fe9418a5913d9188eafe3bc development | --cpu=2 --memory=4G --env=development --port=8080 --name=my-app -q my-queue',
trigger,
noop_trigger,
stable_branch
)
).toStrictEqual({
environment: 'development',
environmentUrl: null,
environmentObj: {
target: 'development',
noop: true,
stable_branch_used: false,
params:
'--cpu=2 --memory=4G --env=development --port=8080 --name=my-app -q my-queue',
sha: '82c238c277ca3df56fe9418a5913d9188eafe3bc'
}
})
expect(debugMock).toHaveBeenCalledWith(
'found environment target for noop trigger: development'
)
expect(infoMock).toHaveBeenCalledWith(
`🧮 detected parameters in command: ${COLORS.highlight}--cpu=2 --memory=4G --env=development --port=8080 --name=my-app -q my-queue`
)
expect(setOutputMock).toHaveBeenCalledWith(
'params',
'--cpu=2 --memory=4G --env=development --port=8080 --name=my-app -q my-queue'
)
})

test('checks the comment body and finds an explicit environment target and an explicit sha (sha1) for development with params on a noop command and the sha is a sha256 hash (64 characters)', async () => {
expect(
await environmentTargets(
Expand Down
75 changes: 75 additions & 0 deletions __tests__/functions/params.test.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,75 @@
import * as core from '@actions/core'
import {parseParams} from '../../src/functions/params'

beforeEach(() => {
jest.clearAllMocks()
jest.spyOn(core, 'debug').mockImplementation(() => {})
})

test('it parses positional parameters', async () => {
expect(parseParams('foo')).toHaveProperty('_', ['foo'])
})

test('it parses arguments using the default settings of library', async () => {
const parsed = parseParams('--foo bar --env.foo=bar')
expect(parsed).toHaveProperty('foo', 'bar')
expect(parsed).toHaveProperty('env', {foo: 'bar'})
expect(parsed).toHaveProperty('_', [])
})

test('it works with empty string', async () => {
expect(parseParams('')).toHaveProperty('_', [])
})

test('it parses multiple positional parameters', async () => {
expect(parseParams('foo bar baz')).toHaveProperty('_', ['foo', 'bar', 'baz'])
})

test('it parses flags correctly', async () => {
const parsed = parseParams('--foo --bar')
expect(parsed).toHaveProperty('foo', true)
expect(parsed).toHaveProperty('bar', true)
expect(parsed).toHaveProperty('_', [])
})

test('it parses numeric values correctly', async () => {
const parsed = parseParams('--count 42')
expect(parsed).toHaveProperty('count', 42)
expect(parsed).toHaveProperty('_', [])
})

test('it parses plain values', async () => {
const parsed = parseParams('count 42')
expect(parsed).toHaveProperty('_', ['count', 42])
})

test('it parses string values with comma separation', async () => {
const parsed = parseParams('LOG_LEVEL=debug,CPU_CORES=4')
expect(parsed).toHaveProperty('_', ['LOG_LEVEL=debug,CPU_CORES=4'])
})

test('it parses boolean values correctly', async () => {
const parsed = parseParams('--enabled=true --disabled false')
expect(parsed).toHaveProperty('enabled', 'true')
expect(parsed).toHaveProperty('disabled', 'false')
expect(parsed).toHaveProperty('_', [])
})

test('it parses nested objects correctly', async () => {
const parsed = parseParams('--config.db.host=localhost --config.db.port=5432')
expect(parsed).toHaveProperty('config', {db: {host: 'localhost', port: 5432}})
expect(parsed).toHaveProperty('_', [])
})

test('it parses a real world example correctly', async () => {
const parsed = parseParams(
'--cpu=2 --memory=4G --env=development --port=8080 --name=my-app -q my-queue'
)
expect(parsed).toHaveProperty('cpu', 2)
expect(parsed).toHaveProperty('memory', '4G')
expect(parsed).toHaveProperty('env', 'development')
expect(parsed).toHaveProperty('port', 8080)
expect(parsed).toHaveProperty('name', 'my-app')
expect(parsed).toHaveProperty('q', 'my-queue')
expect(parsed).toHaveProperty('_', [])
})
32 changes: 32 additions & 0 deletions __tests__/main.test.js
Original file line number Diff line number Diff line change
Expand Up @@ -780,6 +780,38 @@ test('successfully runs the action on a deployment to an exact sha in developmen
expect(debugMock).toHaveBeenCalledWith('production_environment: false')
})

test('successfully runs the action on a deployment and parse the given parameters', async () => {
process.env.INPUT_ALLOW_SHA_DEPLOYMENTS = 'true'
jest.spyOn(prechecks, 'prechecks').mockImplementation(() => {
return {
ref: 'test-ref',
status: true,
message: '✔️ PR is approved and all CI checks passed - OK',
noopMode: false,
sha: '82c238c277ca3df56fe9418a5913d9188eafe3bc'
}
})

github.context.payload.comment.body =
'.deploy | --cpu=2 --memory=4G --env=development --port=8080 --name=my-app -q my-queue'
const expectedParams = {
_: [],
cpu: 2, // Parser automatically cast to number
memory: '4G',
env: 'development',
port: 8080, // Same here
name: 'my-app',
q: 'my-queue'
}

expect(await run()).toBe('success')
expect(setOutputMock).toHaveBeenCalledWith(
'params',
'--cpu=2 --memory=4G --env=development --port=8080 --name=my-app -q my-queue'
)
expect(setOutputMock).toHaveBeenCalledWith('parsed_params', expectedParams)
})

test('successfully runs the action after trimming the body', async () => {
jest.spyOn(prechecks, 'prechecks').mockImplementation(() => {
return {
Expand Down
4 changes: 4 additions & 0 deletions __tests__/schemas/action.schema.yml
Original file line number Diff line number Diff line change
Expand Up @@ -599,3 +599,7 @@ outputs:
description:
type: string
required: true
parsed_params:
description:
type: string
required: true
4 changes: 3 additions & 1 deletion action.yml
Original file line number Diff line number Diff line change
Expand Up @@ -192,6 +192,8 @@ outputs:
description: The environment that has been selected for a deployment
params:
description: The raw parameters that were passed into the deployment command (see param_separator)
parsed_params:
description: A stringified JSON object of the parsed parameters that were passed into the deployment command
noop:
description: 'The string "true" if the noop trigger was found, otherwise the string "false" - Use this to conditionally control whether your deployment runs as a noop or not'
sha:
Expand All @@ -216,7 +218,7 @@ outputs:
description: 'The console command presented in the GitHub UI to checkout a given fork locally'
fork_full_name:
description: 'The full name of the fork in "org/repo" format'
deployment_id:
deployment_id:
description: The ID of the deployment created by running this action
environment_url:
description: The environment URL detected and used for the deployment (sourced from the environment_urls input)
Expand Down
Loading