diff --git a/.github/dependabot.yaml b/.github/dependabot.yaml new file mode 100644 index 00000000..c344a506 --- /dev/null +++ b/.github/dependabot.yaml @@ -0,0 +1,44 @@ +version: 2 +updates: +- package-ecosystem: github-actions + commit-message: + prefix: chore + include: scope + directory: / + schedule: + interval: monthly + groups: + github-actions: + patterns: + - "*" + update-types: + - "minor" + - "patch" +- package-ecosystem: docker + commit-message: + prefix: chore + include: scope + directory: / + schedule: + interval: monthly + groups: + docker: + patterns: + - "*" + update-types: + - "minor" + - "patch" +- package-ecosystem: gomod + commit-message: + prefix: chore + include: scope + directory: / + schedule: + interval: monthly + groups: + gomod: + patterns: + - "*" + update-types: + - "minor" + - "patch" diff --git a/.github/dependency-review-config.yaml b/.github/dependency-review-config.yaml new file mode 100644 index 00000000..08389a1e --- /dev/null +++ b/.github/dependency-review-config.yaml @@ -0,0 +1,20 @@ +# https://github.com/cncf/foundation/blob/main/allowed-third-party-license-policy.md +allow-licenses: +- 'Apache-2.0' +- 'BSD-2-Clause' +- 'BSD-2-Clause-FreeBSD' +- 'BSD-3-Clause' +- 'ISC' +- 'MIT' +- 'PostgreSQL' +- 'Python-2.0' +- 'X11' +- 'Zlib' + +allow-dependencies-licenses: +# this action is GPL-3 but it is only used in CI +# https://github.com/actions/dependency-review-action/issues/530#issuecomment-1638291806 +- pkg:githubactions/vladopajic/go-test-coverage@bcd064e5ceef1ccec5441519eb054263b6a44787 +# this package is MPL-2.0 and has a CNCF exception +# https://github.com/cncf/foundation/blob/9b8c9173c2101c1b4aedad3caf2c0128715133f6/license-exceptions/cncf-exceptions-2022-04-12.json#L43C17-L43C47 +- pkg:golang/github.com/go-sql-driver/mysql diff --git a/.github/workflows/coverage.yaml b/.github/workflows/coverage.yaml new file mode 100644 index 00000000..2901dead --- /dev/null +++ b/.github/workflows/coverage.yaml @@ -0,0 +1,29 @@ +name: coverage +on: + push: + branches: + - main +permissions: {} +jobs: + coverage: + permissions: + contents: write + runs-on: ubuntu-latest + steps: + - uses: actions/checkout@692973e3d937129bcbf40652eb9f2f61becf3332 # v4.1.7 + - uses: actions/setup-go@0a12ed9d6a96ab950c8f026ed9f722fe0da7ef32 # v5.0.2 + with: + go-version: stable + - name: Calculate coverage + run: | + go test -v -covermode=atomic -coverprofile=cover.out.raw -coverpkg=./... ./... + # remove generated code from coverage calculation + grep -Ev 'internal/mock|_enumer.go' cover.out.raw > cover.out + - name: Generage coverage badge + uses: vladopajic/go-test-coverage@1079cd4e58dda229c04ffdb6324fc3756b8542ff # v2.10.1 + with: + profile: cover.out + local-prefix: github.com/${{ github.repository }} + git-token: ${{ secrets.GITHUB_TOKEN }} + # orphan branch for storing badges + git-branch: badges diff --git a/.github/workflows/dependency-review.yaml b/.github/workflows/dependency-review.yaml new file mode 100644 index 00000000..86d7a9ec --- /dev/null +++ b/.github/workflows/dependency-review.yaml @@ -0,0 +1,16 @@ +name: dependency review +on: + pull_request: + branches: + - main +permissions: {} +jobs: + dependency-review: + permissions: + contents: read + runs-on: ubuntu-latest + steps: + - uses: actions/checkout@692973e3d937129bcbf40652eb9f2f61becf3332 # v4.1.7 + - uses: actions/dependency-review-action@5a2ce3f5b92ee19cbb1541a4984c76d921601d7c # v4.3.4 + with: + config-file: .github/dependency-review-config.yaml diff --git a/.github/workflows/lint.yaml b/.github/workflows/lint.yaml new file mode 100644 index 00000000..e13c0afe --- /dev/null +++ b/.github/workflows/lint.yaml @@ -0,0 +1,28 @@ +name: lint +on: + pull_request: + branches: + - main +permissions: {} +jobs: + lint-go: + permissions: + contents: read + runs-on: ubuntu-latest + steps: + - uses: actions/checkout@692973e3d937129bcbf40652eb9f2f61becf3332 # v4.1.7 + - uses: actions/setup-go@0a12ed9d6a96ab950c8f026ed9f722fe0da7ef32 # v5.0.2 + with: + go-version: stable + - uses: golangci/golangci-lint-action@a4f60bb28d35aeee14e6880718e0c85ff1882e64 # v6.0.1 + with: + args: --timeout=180s --enable gocritic + lint-actions: + permissions: + contents: read + runs-on: ubuntu-latest + steps: + - uses: actions/checkout@692973e3d937129bcbf40652eb9f2f61becf3332 # v4.1.7 + - uses: docker://rhysd/actionlint:1.7.0@sha256:601d6faeefa07683a4a79f756f430a1850b34d575d734b1d1324692202bf312e # v1.7.0 + with: + args: -color -shellcheck= diff --git a/.github/workflows/ossf-analysis.yaml b/.github/workflows/ossf-analysis.yaml new file mode 100644 index 00000000..655b3f41 --- /dev/null +++ b/.github/workflows/ossf-analysis.yaml @@ -0,0 +1,31 @@ +name: OSSF scorecard +on: + push: + branches: + - main +permissions: {} +jobs: + ossf-scorecard-analysis: + runs-on: ubuntu-latest + permissions: + contents: read + # Needed if using Code scanning alerts + security-events: write + # Needed for GitHub OIDC token if publish_results is true + id-token: write + steps: + - uses: actions/checkout@692973e3d937129bcbf40652eb9f2f61becf3332 # v4.1.7 + - name: Run analysis + uses: ossf/scorecard-action@dc50aa9510b46c811795eb24b2f1ba02a914e534 # v2.3.3 + with: + results_file: results.sarif + results_format: sarif + # Publish the results for public repositories to enable scorecard badges. For more details, see + # https://github.com/ossf/scorecard-action#publishing-results. + # For private repositories, `publish_results` will automatically be set to `false`, regardless + # of the value entered here. + publish_results: true + - name: Upload SARIF results to code scanning + uses: github/codeql-action/upload-sarif@4fa2a7953630fd2f3fb380f21be14ede0169dd4f # v3.25.12 + with: + sarif_file: results.sarif diff --git a/.github/workflows/release.yaml b/.github/workflows/release.yaml index 21f08e8d..5cec1a15 100644 --- a/.github/workflows/release.yaml +++ b/.github/workflows/release.yaml @@ -3,18 +3,18 @@ name: Release CLI on: push: tags: - - 'v*.*.*' + - 'v*.*.*' jobs: release: runs-on: ubuntu-latest steps: - name: Checkout - uses: actions/checkout@v2 + uses: actions/checkout@v4 with: fetch-depth: "0" - name: Set up Go - uses: actions/setup-go@v2 + uses: actions/setup-go@v4 with: go-version: 1.21 - name: Build CLI @@ -29,9 +29,23 @@ jobs: # create the archived versions and remove anything not required for the release rm ./builds/README.md ./builds/release_template.md for BUILD in $(ls builds); do tar --transform="flags=r;s|${BUILD}|lagoon|" -czf builds/${BUILD}.tar.gz -C builds ${BUILD}; done + - name: Generate SBOM from Github API + uses: advanced-security/sbom-generator-action@375dee8e6144d9fd0ec1f5667b4f6fb4faacefed # v0.0.1 + id: sbom + env: + GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }} + - name: Move SBOM to avoid dirty git + run: mv "$GITHUB_SBOM_PATH" ./sbom.spdx.json + env: + GITHUB_SBOM_PATH: ${{ steps.sbom.outputs.fileName }} - name: Create GitHub Release uses: softprops/action-gh-release@v1 if: startsWith(github.ref, 'refs/tags/') with: files: | - builds/* \ No newline at end of file + builds/* + sbom.spdx.json + - name: Attest build provenance + uses: actions/attest-build-provenance@5e9cb68e95676991667494a6a4e59b8a2f13e1d0 # v1.3.3 + with: + subject-path: "builds/*" diff --git a/.gitignore b/.gitignore index 84f7e26b..7e275b7b 100644 --- a/.gitignore +++ b/.gitignore @@ -1,15 +1,4 @@ -# Binaries for programs and plugins -*.exe -*.exe~ -*.dll -*.so -*.dylib - -# Test binary, built with `go test -c` -*.test - -/vendor -/.idea -site/ - -/builds/lagoon-cli-* +/dist +/cover.out +/cover.out.raw +/sbom.spdx.json diff --git a/README.md b/README.md index 35eaa81f..67847158 100644 --- a/README.md +++ b/README.md @@ -1,5 +1,12 @@ ## Lagoon CLI +[![Go Reference](https://pkg.go.dev/badge/github.com/uselagoon/lagoon-cli.svg)](https://pkg.go.dev/github.com/uselagoon/lagoon-cli) +[![Release](https://github.com/uselagoon/lagoon-cli/actions/workflows/goreleaser.yaml/badge.svg)](https://github.com/uselagoon/lagoon-cli/actions/workflows/goreleaser.yaml) +[![coverage](https://raw.githubusercontent.com/uselagoon/lagoon-cli/badges/.badges/main/coverage.svg)](https://github.com/uselagoon/lagoon-cli/actions/workflows/coverage.yaml) +[![Go Report Card](https://goreportcard.com/badge/github.com/uselagoon/lagoon-cli)](https://goreportcard.com/report/github.com/uselagoon/lagoon-cli) +[![OpenSSF Scorecard](https://api.securityscorecards.dev/projects/github.com/uselagoon/lagoon-cli/badge)](https://securityscorecards.dev/viewer/?uri=github.com/uselagoon/lagoon-cli) +[![OpenSSF Best Practices](https://www.bestpractices.dev/projects/9386/badge)](https://www.bestpractices.dev/projects/9386) + This is a CLI for interacting with a [Lagoon](https://github.com/uselagoon/lagoon) instance. By default, it is configured diff --git a/pkg/app/app.go b/pkg/app/app.go index 5a21e15f..eef4f5c2 100644 --- a/pkg/app/app.go +++ b/pkg/app/app.go @@ -98,7 +98,7 @@ func findLocalProjectRoot(path string) (string, error) { return path, nil } } - return "", fmt.Errorf("no %s file was found in this directory or any parent", filepath.Join(".lagoon.yml")) + return "", fmt.Errorf("no .lagoon.yml file was found in this directory or any parent") } // FileExists checks a file's existence