Skip to content

Commit

Permalink
Merge branch 'main' into dependabot/npm_and_yarn/undici-5.28.4
Browse files Browse the repository at this point in the history
  • Loading branch information
leslie-corbalt authored Nov 25, 2024
2 parents 38f6d97 + ac6255e commit d75fb04
Show file tree
Hide file tree
Showing 9 changed files with 257 additions and 34 deletions.
10 changes: 10 additions & 0 deletions .github/actions/report-dso-event/README.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,10 @@
# report-dso-event

This Action is a thin wrapper around the CLI program `report-event` that is [housed in the mac-fc-dso-metrics repo](https://github.com/Enterprise-CMCS/mac-fc-dso-metrics/tree/main/cmd/report-event). Please see the README of that program for documentation.

For documentation of the inputs and outputs of this Action, please see `action.yml`.

To report an event, the action requires valid AWS credentials stored in the environment when the action is run. These credentials must provide access to an IAM role that has an entry on the ACL used by the MACBIS DevSecOps Metrics API to determine the API permissions. For more information, please see the documentation for onboarding to the MACBIS DevSecOps Metrics API in Confluence [TODO]

For an example of usage, please see the workflow that tests the action: `.github/workflows/test-report-dso-event.yml`

21 changes: 21 additions & 0 deletions .github/actions/report-dso-event/action.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,21 @@
name: report-dso-event
description: 'Sends event data to the MACBIS DevSecOps Metrics API'
inputs:
args:
description: Arguments to pass to the report-event program. Please see Enterprise-CMCS/mac-fc-dso-metrics/cmd/report-event/README.md for documentation
version:
description: The version constraint for the report-event program in semantic version syntax. Defaults to the latest version (we recommend pinning to a specific version or range)
default: "*"
token:
description: The GitHub token used to list the (public) releases of report-event. A token is required to avoid the low non-authenticated rate limit. We recommend using the default GITHUB_TOKEN
default: ${{ github.token }}
outputs:
exit-code:
description: The exit code of the program
output:
description: The output of the program (stdout)
error-output:
description: The error output of the program (stderr)
runs:
using: node20
main: ../../../build/index.js
27 changes: 27 additions & 0 deletions .github/actions/run-command-with-metadata/action.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,27 @@
name: 'Run Command With Metadata'
description: 'Runs a bash command and outputs metadata about the execution'
inputs:
command:
description: 'The bash command to run'
required: true
outputs:
start-time:
value: ${{ steps.run-command.outputs.start-time }}
description: 'The start time of the command in ISO 8601 format'
end-time:
value: ${{ steps.run-command.outputs.end-time }}
description: 'The end time of the command in ISO 8601 format'
exit-code:
value: ${{ steps.run-command.outputs.exit-code }}
description: 'The exit code of the command'
runs:
using: 'composite'
steps:
- id: run-command
run: |
trap 'EXIT_CODE=$?; \
echo "end-time=$(date -Iseconds)" >> $GITHUB_OUTPUT; \
echo "exit-code=$EXIT_CODE" >> $GITHUB_OUTPUT' EXIT
echo "start-time=$(date -Iseconds)" >> $GITHUB_OUTPUT
${{ inputs.command }}
shell: bash
12 changes: 12 additions & 0 deletions .github/actions/warn-and-continue/action.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,12 @@
name: 'Warn and Continue'
description: 'Echos a warning message and continues on error'
inputs:
message:
description: 'The warning message to echo'
required: true
runs:
using: "composite"
steps:
- run: echo "::warning::${{ inputs.message }}"
shell: bash
continue-on-error: true
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
name: Test report-event action
name: Test report-dso-event action

on:
push:
Expand All @@ -16,13 +16,13 @@ jobs:

# TODO add a step to configure AWS creds if we decide to test reporting an event

- name: Test report-event action
- name: Test report-dso-event action
id: test-action
uses: ./
uses: ./.github/actions/report-dso-event
continue-on-error: true # TODO for now, we're expecting the program to exit 2 when usage is called
with:
args: -h # TODO we might decide to report a valid test event to test infrastructure when it is set up
version: "*" # use the latest version
version: "v0.1.0-dev"

- name: Assert against outputs
if: ${{ (steps.test-action.outputs.exit-code != 2) || (!contains(steps.test-action.outputs.output, 'report-event')) }}
Expand Down
40 changes: 33 additions & 7 deletions README.md
Original file line number Diff line number Diff line change
@@ -1,14 +1,40 @@
## report-dso-event
# Run Command And Report DevSecOps (DSO) Event GitHub Action

A GitHub Action that reports a DevSecOps event to the MACBIS DevSecOps Metrics API.
This GitHub Action allows you to run a command that triggers a DevSecOps (DSO) event, such as a deployment or test run, and send data about the event to the MACBIS DSO Metrics API.

### Usage
## Inputs

This Action is a thin wrapper around the CLI program `report-event` that is [housed in the mac-fc-dso-metrics repo](https://github.com/Enterprise-CMCS/mac-fc-dso-metrics/tree/main/cmd/report-event). Please see the README of that program for documentation.
| Input | Description | Required | Default |
| --- | --- | --- | --- |
| `command` | The command to run that triggers a DSO event (e.g. a deployment or test run) | Yes | N/A |
| `aws-account-id` | The AWS account ID containing the DSO Metrics cross-account role used for reporting the event | Yes | N/A |
| `event-type` | The event type. Must be one of "deploy" or "test" | Yes | N/A |
| `app` | The app corresponding to the event | Yes | N/A |
| `team` | The team corresponding to the event | Yes | N/A |
| `environment` | The environment corresponding to the event (can be "none") | Yes | N/A |
| `id` | The unique identifier of the event. See documentation (TODO) for choosing an ID | Yes | N/A |
| `oidc-role` | The OIDC role to assume that has permission to assume the DSO Metrics cross-account role. If not provided, AWS credentials with this permission must be set in the environment when this action is run | No | N/A |
| `oidc-role-session-name` | OIDC role session name | No | 'ReportDSOEvent' |
| `aws-region` | AWS region | No | 'us-east-1' |
| `report-event-version` | The version constraint for the Enterprise-CMCS/mac-fc-dso-metrics/cmd/report-event program in semantic version syntax. Defaults to the latest version (we recommend pinning to a specific version or range) | No | Latest version |

For documentation of the inputs and outputs of this Action, please see `action.yml`.
## Usage

Here's an example of how to use this action in your workflow:

```yaml
- name: Run Command And Report DSO Event
uses: Enterprise-CMCS/[email protected]
with:
command: go test ./...
event-type: test
app: my-app
team: my-team
environment: none
id: ${{ github.run_id }}-go-test
aws-account-id: 123456789012
oidc-role: arn:aws:iam::123456789012:role/example-role
```
To report an event, the action requires valid AWS credentials stored in the environment when the action is run. These credentials must provide access to an IAM role that has an entry on the ACL used by the MACBIS DevSecOps Metrics API to determine the API permissions. For more information, please see the documentation for onboarding to the MACBIS DevSecOps Metrics API in Confluence [TODO]
For an example of usage, please see the workflow that tests the action: `.github/workflows/test-action.yml`
158 changes: 139 additions & 19 deletions action.yml
Original file line number Diff line number Diff line change
@@ -1,21 +1,141 @@
name: report-event
description: 'Sends event data to the MACBIS DevSecOps Metrics API'
name: 'Run Command And Report DevSecOps (DSO) Event'
description: 'Runs a command and sends event data to the MACBIS DSO Metrics API'
inputs:
args:
description: Arguments to pass to the report-event program. Please see Enterprise-CMCS/mac-fc-dso-metrics/cmd/report-event/README.md for documentation
version:
description: The version constraint for the report-event program in semantic version syntax. Defaults to the latest version (we recommend pinning to a specific version or range)
default: "*"
token:
description: The GitHub token used to list the (public) releases of report-event. A token is required to avoid the low non-authenticated rate limit. We recommend using the default GITHUB_TOKEN
default: ${{ github.token }}
outputs:
exit-code:
description: The exit code of the program
output:
description: The output of the program (stdout)
error-output:
description: The error output of the program (stderr)
command:
description: 'The command to run that triggers a DSO event (e.g. a deployment or test run)'
required: true
aws-account-id:
description: 'The AWS account ID containing the DSO Metrics cross-account role used for reporting the event'
required: true
event-type:
description: 'The event type. Must be one of "deploy" or "test"'
required: true
report-event-version:
description: "The version constraint for the Enterprise-CMCS/mac-fc-dso-metrics/cmd/report-event program in semantic version syntax. Defaults to the latest version (we recommend pinning to a specific version or range)"
required: false
app:
description: 'The app corresponding to the event'
required: true
team:
description: 'The team corresponding to the event'
required: true
environment:
description: 'The environment corresponding to the event (use "none" if there is none)'
required: true
id:
description: 'The unique identifier of the event. See documentation (TODO) for choosing an ID'
required: true
aws-region:
description: '(Optional) AWS region'
required: false
default: us-east-1
oidc-role:
description: '(Optional) The OIDC role to assume that has permission to assume the DSO Metrics cross-account role. If not provided, AWS credentials with this permission must be set in the environment when this action is run'
required: false
oidc-role-session-name:
description: '(Optional) OIDC role session name'
required: false
default: 'ReportDSOEvent'

runs:
using: node20
main: build/index.js
using: 'composite'
steps:
- name: Run command
id: run-command
uses: Enterprise-CMCS/mac-fc-report-dso-event/.github/actions/[email protected]
with:
command: ${{ inputs.command }}

- name: Get OIDC credentials
id: get-oidc-creds
if: |
!cancelled() &&
steps.run-command.outputs.start-time != '' &&
inputs.oidc-role != ''
continue-on-error: true # allow the job to succeed when this and subsequent steps fail. that way we don't block the calling workflow by failing this action when the command succceeds but one of our steps fails
uses: aws-actions/configure-aws-credentials@v4
with:
role-to-assume: ${{ inputs.oidc-role}}
role-session-name: ${{ inputs.oidc-role-session-name }}
aws-region: ${{ inputs.aws-region }}

- name: Warn on failure
if: ${{ !cancelled() && steps.get-oidc-creds.outcome == 'failure' }}
uses: Enterprise-CMCS/mac-fc-report-dso-event/.github/actions/[email protected]
with:
message: 'Failed to get OIDC credentials when reporting DSO Metrics. Please investigate the failure.'

- name: Assume DSO metrics reporting role
id: assume-dso-role
if: |
!cancelled() &&
steps.run-command.outputs.start-time != '' &&
(inputs.oidc-role != '' && steps.get-oidc-creds.outcome == 'success')
continue-on-error: true
uses: aws-actions/configure-aws-credentials@v4
with:
role-to-assume: arn:aws:iam::${{ inputs.aws-account-id}}:role/delegatedadmin/developer/ct-cmcs-mac-fc-dso-metrics-report-events-role
role-session-name: ${{ inputs.oidc-role-session-name }}
aws-region: ${{ inputs.aws-region }}
role-chaining: true
role-skip-session-tagging: true

- name: Warn on failure
if: ${{ !cancelled() && steps.assume-dso-role.outcome == 'failure' }}
uses: Enterprise-CMCS/mac-fc-report-dso-event/.github/actions/[email protected]
with:
message: 'Failed to assume DSO metrics cross-account role when reporting DSO Metrics. Please investigate the failure.'

- name: Report test metrics
id: report-test-metrics
if: |
!cancelled() &&
steps.run-command.outputs.start-time != '' &&
steps.assume-dso-role.outcome == 'success' &&
inputs.event-type == 'test'
continue-on-error: true
uses: Enterprise-CMCS/mac-fc-report-dso-event/.github/actions/[email protected]
with:
# TODO add coverage
args: >
-app "${{ inputs.app }}"
-id "${{ inputs.id }}"
-team "${{ inputs.team }}"
-environment "${{ inputs.environment }}"
${{ inputs.event-type }}
-start "${{ steps.run-command.outputs.start-time }}"
-end "${{ steps.run-command.outputs.end-time }}"
-result "${{ steps.run-command.outputs.exit-code == '0' && 'pass' || 'fail' }}"
version: ${{ inputs.report-event-version }}

- name: Warn on failure
if: ${{ !cancelled() && steps.report-test-metrics.outcome == 'failure' }}
uses: Enterprise-CMCS/mac-fc-report-dso-event/.github/actions/[email protected]
with:
message: 'Failed to report test event metrics to the DSO Metrics API. Please investigate the failure.'

- name: Report deploy metrics
id: report-deploy-metrics
if: |
!cancelled() &&
steps.run-command.outputs.start-time != '' &&
steps.assume-dso-role.outcome == 'success' &&
inputs.event-type == 'deploy'
continue-on-error: true
uses: Enterprise-CMCS/mac-fc-report-dso-event/.github/actions/[email protected]
with:
args: >
-app "${{ inputs.app }}"
-id "${{ inputs.id }}"
-team "${{ inputs.team }}"
${{ inputs.event-type }}
-start "${{ steps.run-command.outputs.start-time }}"
-end "${{ steps.run-command.outputs.end-time }}"
-result "${{ steps.run-command.outputs.exit-code == '0' && 'success' || 'failure' }}"
version: ${{ inputs.report-event-version }}

- name: Warn on failure
if: ${{ !cancelled() && steps.report-deploy-metrics.outcome == 'failure' }}
uses: Enterprise-CMCS/mac-fc-report-dso-event/.github/actions/[email protected]
with:
message: 'Failed to report deploy event metrics to the DSO Metrics API. Please investigate the failure.'
7 changes: 5 additions & 2 deletions build/index.js
Original file line number Diff line number Diff line change
Expand Up @@ -32229,7 +32229,7 @@ function main() {
var _a;
return __awaiter(this, void 0, void 0, function* () {
const version = core.getInput("version");
const args = core.getInput("args").split(" ");
const args = core.getInput("args");
let releaseName;
try {
releaseName = yield downloadRelease(version);
Expand All @@ -32239,8 +32239,11 @@ function main() {
process.exit(1);
}
let returns;
const command = (0, os_1.type)() === windowsType
? `${releaseName} ${args}`
: `./${releaseName} ${args}`;
try {
returns = (0, child_process_1.spawnSync)(`./${releaseName}`, args);
returns = (0, child_process_1.spawnSync)(command, { shell: true });
}
catch (error) {
console.error(`Error spawning child process: ${error}`);
Expand Down
8 changes: 6 additions & 2 deletions src/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -92,7 +92,7 @@ async function downloadRelease(version: string): Promise<string> {

async function main() {
const version = core.getInput("version");
const args = core.getInput("args").split(" ");
const args = core.getInput("args");

let releaseName;
try {
Expand All @@ -103,8 +103,12 @@ async function main() {
}

let returns;
const command =
type() === windowsType
? `${releaseName} ${args}`
: `./${releaseName} ${args}`;
try {
returns = spawnSync(`./${releaseName}`, args);
returns = spawnSync(command, { shell: true });
} catch (error) {
console.error(`Error spawning child process: ${error}`);
process.exit(1);
Expand Down

0 comments on commit d75fb04

Please sign in to comment.