From 70b21d80f4307463e756facd937b90689e9be885 Mon Sep 17 00:00:00 2001 From: Joshua Gilman Date: Fri, 30 Aug 2024 12:36:21 -0400 Subject: [PATCH] chore: adds docker provider support --- blueprint.cue | 16 ++++++++++++ forge/actions/setup/action.yml | 48 +++++++++++++++++++++++++++------- forge/cli/cmd/cmds/secret.go | 37 ++++++++++++++++++++++++++ 3 files changed, 91 insertions(+), 10 deletions(-) diff --git a/blueprint.cue b/blueprint.cue index 57a0085..1621cfa 100644 --- a/blueprint.cue +++ b/blueprint.cue @@ -5,5 +5,21 @@ ci: { region: "eu-central-1" role: "arn:aws:iam::332405224602:role/ci" } + docker: { + credentials: { + provider: "aws" + path: "global/ci/docker" + maps: { + usernames: "username" + passwords: "password" + } + } + } + earthly: { + credentials: { + provider: "aws" + path: "global/ci/earthly" + } + } } } diff --git a/forge/actions/setup/action.yml b/forge/actions/setup/action.yml index 95a17cc..635553f 100644 --- a/forge/actions/setup/action.yml +++ b/forge/actions/setup/action.yml @@ -32,24 +32,52 @@ runs: run: | earthly --artifact ./forge/cli+build/forge /usr/local/bin/forge - - name: Get provider configuration - id: provider + # AWS Provider + - name: Get AWS provider configuration + id: aws shell: bash run: | BP=$(forge blueprint dump .) AWS=$(echo "$BP" | jq -r .ci.providers.aws) if [[ "$AWS" != "null" ]]; then - AWS_REGION=$(echo "$BP" | jq -r .ci.providers.aws.region) - AWS_ROLE=$(echo "$BP" | jq -r .ci.providers.aws.role) + REGION=$(echo "$BP" | jq -r .ci.providers.aws.region) + ROLE=$(echo "$BP" | jq -r .ci.providers.aws.role) fi - echo "aws_region=$AWS_REGION" >> $GITHUB_OUTPUT - echo "aws_role=$AWS_ROLE" >> $GITHUB_OUTPUT - + echo "region=$REGION" >> $GITHUB_OUTPUT + echo "role=$ROLE" >> $GITHUB_OUTPUT - name: Configure AWS uses: aws-actions/configure-aws-credentials@v4 - if: ${{ steps.provider.outputs.aws_region != '' && steps.provider.outputs.aws_role != '' }} + if: ${{ steps.aws.outputs.region != '' && steps.aws.outputs.role != '' }} + with: + aws-region: ${{ steps.aws.outputs.region }} + role-to-assume: ${{ steps.aws.outputs.role }} + + # Docker Provider + - name: Get Docker provider configuration + id: docker + shell: bash + run: | + BP=$(forge blueprint dump .) + + DOCKER=$(echo "$BP" | jq -r .ci.providers.docker.credentials) + if [[ "$DOCKER" != "null" ]]; then + SECRET=$(forge secret get -b . ci.providers.docker.credentials) + USERNAME=$(echo "$SECRET" | jq -r .username) + PASSWORD=$(echo "$SECRET" | jq -r .password) + + if [[ "$USERNAME" == "null" || "$PASSWORD" == "null"]]; then + echo "Error: the docker provider secret must map secret values to 'username' and 'password'" + exit 1 + fi + fi + + echo "username=$USERNAME" >> $GITHUB_OUTPUT + echo "password=$PASSWORD" >> $GITHUB_OUTPUT + - name: Login to Docker Hub + uses: docker/login-action@v3 + if: ${{ steps.docker.outputs.username != '' && steps.docker.outputs.password != '' }} with: - aws-region: ${{ steps.provider.outputs.aws_region }} - role-to-assume: ${{ steps.provider.outputs.aws_role }} \ No newline at end of file + username: ${{ steps.docker.outputs.username }} + password: ${{ steps.docker.outputs.password }} \ No newline at end of file diff --git a/forge/cli/cmd/cmds/secret.go b/forge/cli/cmd/cmds/secret.go index 868f1d0..fe403f8 100644 --- a/forge/cli/cmd/cmds/secret.go +++ b/forge/cli/cmd/cmds/secret.go @@ -38,6 +38,7 @@ type SecretCmd struct { func (c *Get) Run(logger *slog.Logger) error { var path, provider string + var maps map[string]string if c.Blueprint != "" { loader := loader.NewDefaultBlueprintLoader(c.Blueprint, logger) @@ -56,9 +57,16 @@ func (c *Get) Run(logger *slog.Logger) error { path = *secret.Path provider = *secret.Provider } + + if len(secret.Maps) > 0 { + maps = secret.Maps + } else { + maps = make(map[string]string) + } } else { path = c.Path provider = c.Provider + maps = make(map[string]string) } store := secrets.NewDefaultSecretStore() @@ -73,6 +81,35 @@ func (c *Get) Run(logger *slog.Logger) error { return fmt.Errorf("could not get secret: %w", err) } + if len(maps) > 0 { + mappedSecret := make(map[string]string) + m := make(map[string]string) + + if err := json.Unmarshal([]byte(s), &m); err != nil { + return err + } + + for k, v := range maps { + if _, ok := m[v]; !ok { + return fmt.Errorf("key %s not found in secret at %s", v, path) + } + + mappedSecret[k] = m[v] + } + + if c.Key != "" { + if _, ok := mappedSecret[c.Key]; !ok { + return fmt.Errorf("key %s not found in mapped secret at %s", c.Key, path) + } + + fmt.Println(mappedSecret[c.Key]) + return nil + } else { + printJson(mappedSecret, false) + return nil + } + } + if c.Key != "" { m := make(map[string]string)