Skip to content

build: rewrite CI to use matrices and cut down on workflow calls #256

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

Open
wants to merge 1 commit into
base: main
Choose a base branch
from

Conversation

matt-codecov
Copy link
Collaborator

@matt-codecov matt-codecov commented Jun 20, 2025

rewrites all our CI to:

  • deduplicate _build-app.yml and the image-building parts of _self-hosted.yml into a single workflow: _build-images.yml
  • deduplicate _push-env.yml and the image-pushing parts of _self-hosted.yml into a single workflow: _push-images.yml
  • make any push to staging deploy both worker and api regardless of what the commit actually touched
  • instead of having worker-ci.yml, api-ci.yml, and shared-ci.yml all call _build-images.yml (for instance), make _build-images.yml use a matrix to run on worker/api/shared

the main motivation is that we are pretty close to GHA's 20-workflow-call limit on PRs that need to run worker-ci.yml, api-ci.yml, and shared-ci.yml. in fact, when i tried to make staging pushes work better (#216), i hit the limit and the job wouldn't work. so, instead of calling like 6 workflows for worker, 6 for api, and 6 for shared for a total of 18, this PR makes us call 6 in total and have each workflow handle worker/api/shared internally.

to be honest, i think this is a worse setup than how it currently works. matrix shenanigans are complicated and very copypasty, it forces synchronization at the end of each "step" instead of allowing worker/api/shared to run start-to-finish in parallel, and it doesn't allow for any uniqueness for different projects. but, it takes us far below the workflow-call limit and it makes staging deploys work better.

the other option i tried was #234. it uses the gh cli to sidestep the workflow-call limit by using the REST API to do workflow dispatches instead. however, workflows started that way don't show up in the PR checks section, so you have to use the REST API to create your own checks. that's not great.

Legal Boilerplate

Look, I get it. The entity doing business as "Sentry" was incorporated in the State of Delaware in 2015 as Functional Software, Inc. In 2022 this entity acquired Codecov and as result Sentry is going to need some rights from me in order to utilize my contributions in this PR. So here's the deal: I retain all rights, title and interest in and to my contributions, and by keeping this boilerplate intact I confirm that Sentry can use, modify, copy, and redistribute my contributions, under Sentry's choice of terms.

Copy link

seer-by-sentry bot commented Jun 20, 2025

Sentry detected 2 potential issues in your recent changes

A potential issue exists where GitHub Actions workflows call non-existent Makefile targets, such as `worker.build.app`, because required Makefile include files are missing from the repository. This could lead to workflow termination.
  • Description: The build and push workflows depend on Makefile targets (e.g., worker.build.app, worker.load.app) that are not defined. The root Makefile includes docker/Makefile.docker and docker/Makefile.ci-tests, but these files are missing from the repository. Consequently, when a workflow attempts to execute a command like make worker.build.app, the make utility will fail with a "No rule to make target" error. For example, if docker/Makefile.docker were present, it might define _load.app, but the workflow calls worker.load.app, which is not resolved due to the missing included Makefiles. This will cause the GitHub Actions workflow to terminate unexpectedly.
  • Code location: .github/workflows/_build-images.yml:126
  • Suggested fix: Ensure all Makefiles included by the root Makefile (e.g., docker/Makefile.docker, docker/Makefile.ci-tests) are present in the repository and define the necessary targets (e.g., worker.build.app, api.load.app) that the workflows depend on.
The fromJSON() function, used in conditional logic, may receive an empty string if the upstream jq command fails, leading to a JSON parsing error and workflow crash.
  • Description: The jq command at app-ci.yml:75-78 generates a JSON string. If jq fails (e.g., due to malformed input from steps.filter.outputs.changes), the $matrix variable becomes an empty string. This empty string is then used as steps.strip.outputs.matrix. When this empty string is passed to fromJSON() in expressions like contains(fromJSON(needs.change-detection.outputs.changes), 'worker') (e.g., at app-ci.yml:147), fromJSON('') will cause a JSON parsing error. This error is not handled, leading to workflow failure. For example, if steps.filter.outputs.changes was {"invalid_json", jq would fail, $matrix would be '', and fromJSON('') would crash. This lack of error handling around JSON generation and parsing creates a single point of failure that could crash multiple workflows simultaneously.
  • Code location: .github/workflows/app-ci.yml:147
  • Suggested fix: Implement error handling for the jq command to ensure valid JSON output, or provide a default valid JSON array if jq fails. Add a check for empty string before calling fromJSON().

Did you find this useful? React with a 👍 or 👎

token: ${{ secrets[matrix.codecov_token_secret] }}
url: ${{ secrets[matrix.codecov_url_secret] }}
recurse_submodules: true
token: ${{ secrets[matrix.codecov-instance.token] }}

Check warning

Code scanning / CodeQL

Excessive Secrets Exposure Medium

All organization and repository secrets are passed to the workflow runner in
secrets[matrix.codecov-instance.token]
url: ${{ secrets[matrix.codecov_url_secret] }}
recurse_submodules: true
token: ${{ secrets[matrix.codecov-instance.token] }}
url: ${{ secrets[matrix.codecov-instance.url] }}

Check warning

Code scanning / CodeQL

Excessive Secrets Exposure Medium

All organization and repository secrets are passed to the workflow runner in
secrets[matrix.codecov-instance.url]

Copilot Autofix

AI 16 days ago

To fix the issue, we need to avoid dynamically accessing secrets using secrets[matrix.codecov-instance.url]. Instead, explicitly define the secrets required for each possible value of matrix.codecov-instance.url and pass only those secrets to the workflow. This can be achieved by using conditional logic or matrix configurations to map specific secrets to specific scenarios.

For example, if matrix.codecov-instance.url can have values like url1 and url2, we should define separate secrets for each (secrets.CODECOV_URL1 and secrets.CODECOV_URL2) and explicitly reference them in the workflow.

Suggested changeset 1
.github/workflows/_run-tests.yml

Autofix patch

Autofix patch
Run the following command in your local git repository to apply this patch
cat << 'EOF' | git apply
diff --git a/.github/workflows/_run-tests.yml b/.github/workflows/_run-tests.yml
--- a/.github/workflows/_run-tests.yml
+++ b/.github/workflows/_run-tests.yml
@@ -164,3 +164,3 @@
           token: ${{ secrets[matrix.codecov-instance.token] }}
-          url: ${{ secrets[matrix.codecov-instance.url] }}
+          url: ${{ matrix.codecov-instance.url == 'url1' && secrets.CODECOV_URL1 || matrix.codecov-instance.url == 'url2' && secrets.CODECOV_URL2 }}
 
@@ -177,3 +177,3 @@
           token: ${{ secrets[matrix.codecov-instance.token] }}
-          url: ${{ secrets[matrix.codecov-instance.url] }}
+          url: ${{ matrix.codecov-instance.url == 'url1' && secrets.CODECOV_URL1 || matrix.codecov-instance.url == 'url2' && secrets.CODECOV_URL2 }}
 
@@ -187,3 +187,3 @@
           token: ${{ secrets[matrix.codecov-instance.token] }}
-          url: ${{ secrets[matrix.codecov-instance.url] }}
+          url: ${{ matrix.codecov-instance.url == 'url1' && secrets.CODECOV_URL1 || matrix.codecov-instance.url == 'url2' && secrets.CODECOV_URL2 }}
           # The coverage action will have installed codecovcli with pip. The
@@ -201,3 +201,3 @@
           token: ${{ secrets[matrix.codecov-instance.token] }}
-          url: ${{ secrets[matrix.codecov-instance.url] }}
+          url: ${{ matrix.codecov-instance.url == 'url1' && secrets.CODECOV_URL1 || matrix.codecov-instance.url == 'url2' && secrets.CODECOV_URL2 }}
           # The coverage action will have installed codecovcli with pip. The
EOF
@@ -164,3 +164,3 @@
token: ${{ secrets[matrix.codecov-instance.token] }}
url: ${{ secrets[matrix.codecov-instance.url] }}
url: ${{ matrix.codecov-instance.url == 'url1' && secrets.CODECOV_URL1 || matrix.codecov-instance.url == 'url2' && secrets.CODECOV_URL2 }}

@@ -177,3 +177,3 @@
token: ${{ secrets[matrix.codecov-instance.token] }}
url: ${{ secrets[matrix.codecov-instance.url] }}
url: ${{ matrix.codecov-instance.url == 'url1' && secrets.CODECOV_URL1 || matrix.codecov-instance.url == 'url2' && secrets.CODECOV_URL2 }}

@@ -187,3 +187,3 @@
token: ${{ secrets[matrix.codecov-instance.token] }}
url: ${{ secrets[matrix.codecov-instance.url] }}
url: ${{ matrix.codecov-instance.url == 'url1' && secrets.CODECOV_URL1 || matrix.codecov-instance.url == 'url2' && secrets.CODECOV_URL2 }}
# The coverage action will have installed codecovcli with pip. The
@@ -201,3 +201,3 @@
token: ${{ secrets[matrix.codecov-instance.token] }}
url: ${{ secrets[matrix.codecov-instance.url] }}
url: ${{ matrix.codecov-instance.url == 'url1' && secrets.CODECOV_URL1 || matrix.codecov-instance.url == 'url2' && secrets.CODECOV_URL2 }}
# The coverage action will have installed codecovcli with pip. The
Copilot is powered by AI and may make mistakes. Always verify output.
token: ${{ secrets[matrix.codecov_token_secret] }}
url: ${{ secrets[matrix.codecov_url_secret] }}
recurse_submodules: true
token: ${{ secrets[matrix.codecov-instance.token] }}

Check warning

Code scanning / CodeQL

Excessive Secrets Exposure Medium

All organization and repository secrets are passed to the workflow runner in
secrets[matrix.codecov-instance.token]

Copilot Autofix

AI 16 days ago

To fix the problem, we need to replace the dynamic secret access (secrets[matrix.codecov-instance.token]) with explicit references to the required secrets. This involves defining specific secrets for each matrix configuration and referencing them directly. For example, if the matrix includes configurations for different environments or instances, secrets should be explicitly defined for each case (e.g., secrets.CODECOV_TOKEN_PROD, secrets.CODECOV_TOKEN_DEV, etc.).

The changes will involve:

  1. Defining explicit secrets for each matrix configuration in the workflow file.
  2. Replacing the dynamic secret access with direct references to these secrets.
Suggested changeset 1
.github/workflows/_run-tests.yml

Autofix patch

Autofix patch
Run the following command in your local git repository to apply this patch
cat << 'EOF' | git apply
diff --git a/.github/workflows/_run-tests.yml b/.github/workflows/_run-tests.yml
--- a/.github/workflows/_run-tests.yml
+++ b/.github/workflows/_run-tests.yml
@@ -163,4 +163,4 @@
           use_pypi: true
-          token: ${{ secrets[matrix.codecov-instance.token] }}
-          url: ${{ secrets[matrix.codecov-instance.url] }}
+          token: ${{ secrets.CODECOV_TOKEN }}
+          url: ${{ secrets.CODECOV_URL }}
 
@@ -176,4 +176,4 @@
           use_pypi: true
-          token: ${{ secrets[matrix.codecov-instance.token] }}
-          url: ${{ secrets[matrix.codecov-instance.url] }}
+          token: ${{ secrets.CODECOV_TOKEN }}
+          url: ${{ secrets.CODECOV_URL }}
 
@@ -186,4 +186,4 @@
           disable_search: true
-          token: ${{ secrets[matrix.codecov-instance.token] }}
-          url: ${{ secrets[matrix.codecov-instance.url] }}
+          token: ${{ secrets.CODECOV_TOKEN }}
+          url: ${{ secrets.CODECOV_URL }}
           # The coverage action will have installed codecovcli with pip. The
@@ -200,4 +200,4 @@
           disable_search: true
-          token: ${{ secrets[matrix.codecov-instance.token] }}
-          url: ${{ secrets[matrix.codecov-instance.url] }}
+          token: ${{ secrets.CODECOV_TOKEN }}
+          url: ${{ secrets.CODECOV_URL }}
           # The coverage action will have installed codecovcli with pip. The
EOF
@@ -163,4 +163,4 @@
use_pypi: true
token: ${{ secrets[matrix.codecov-instance.token] }}
url: ${{ secrets[matrix.codecov-instance.url] }}
token: ${{ secrets.CODECOV_TOKEN }}
url: ${{ secrets.CODECOV_URL }}

@@ -176,4 +176,4 @@
use_pypi: true
token: ${{ secrets[matrix.codecov-instance.token] }}
url: ${{ secrets[matrix.codecov-instance.url] }}
token: ${{ secrets.CODECOV_TOKEN }}
url: ${{ secrets.CODECOV_URL }}

@@ -186,4 +186,4 @@
disable_search: true
token: ${{ secrets[matrix.codecov-instance.token] }}
url: ${{ secrets[matrix.codecov-instance.url] }}
token: ${{ secrets.CODECOV_TOKEN }}
url: ${{ secrets.CODECOV_URL }}
# The coverage action will have installed codecovcli with pip. The
@@ -200,4 +200,4 @@
disable_search: true
token: ${{ secrets[matrix.codecov-instance.token] }}
url: ${{ secrets[matrix.codecov-instance.url] }}
token: ${{ secrets.CODECOV_TOKEN }}
url: ${{ secrets.CODECOV_URL }}
# The coverage action will have installed codecovcli with pip. The
Copilot is powered by AI and may make mistakes. Always verify output.
url: ${{ secrets[matrix.codecov_url_secret] }}
recurse_submodules: true
token: ${{ secrets[matrix.codecov-instance.token] }}
url: ${{ secrets[matrix.codecov-instance.url] }}

Check warning

Code scanning / CodeQL

Excessive Secrets Exposure Medium

All organization and repository secrets are passed to the workflow runner in
secrets[matrix.codecov-instance.url]

Copilot Autofix

AI 16 days ago

To fix the issue, we need to avoid dynamically accessing secrets using secrets[matrix.codecov-instance.url]. Instead, explicitly define the secrets required for each possible value of matrix.codecov-instance.url and pass only those secrets to the workflow. This can be achieved by using conditional logic or matrix configurations to map specific secrets to specific scenarios.

For example, if matrix.codecov-instance.url can have values like url1 and url2, we should explicitly define secrets.CODECOV_URL1 and secrets.CODECOV_URL2 and use them directly in the workflow. This ensures that only the necessary secrets are passed to the runner.

Suggested changeset 1
.github/workflows/_run-tests.yml

Autofix patch

Autofix patch
Run the following command in your local git repository to apply this patch
cat << 'EOF' | git apply
diff --git a/.github/workflows/_run-tests.yml b/.github/workflows/_run-tests.yml
--- a/.github/workflows/_run-tests.yml
+++ b/.github/workflows/_run-tests.yml
@@ -164,3 +164,3 @@
           token: ${{ secrets[matrix.codecov-instance.token] }}
-          url: ${{ secrets[matrix.codecov-instance.url] }}
+          url: ${{ matrix.codecov-instance.url == 'url1' && secrets.CODECOV_URL1 || matrix.codecov-instance.url == 'url2' && secrets.CODECOV_URL2 }}
 
@@ -177,3 +177,3 @@
           token: ${{ secrets[matrix.codecov-instance.token] }}
-          url: ${{ secrets[matrix.codecov-instance.url] }}
+          url: ${{ matrix.codecov-instance.url == 'url1' && secrets.CODECOV_URL1 || matrix.codecov-instance.url == 'url2' && secrets.CODECOV_URL2 }}
 
@@ -201,3 +201,3 @@
           token: ${{ secrets[matrix.codecov-instance.token] }}
-          url: ${{ secrets[matrix.codecov-instance.url] }}
+          url: ${{ matrix.codecov-instance.url == 'url1' && secrets.CODECOV_URL1 || matrix.codecov-instance.url == 'url2' && secrets.CODECOV_URL2 }}
           # The coverage action will have installed codecovcli with pip. The
EOF
@@ -164,3 +164,3 @@
token: ${{ secrets[matrix.codecov-instance.token] }}
url: ${{ secrets[matrix.codecov-instance.url] }}
url: ${{ matrix.codecov-instance.url == 'url1' && secrets.CODECOV_URL1 || matrix.codecov-instance.url == 'url2' && secrets.CODECOV_URL2 }}

@@ -177,3 +177,3 @@
token: ${{ secrets[matrix.codecov-instance.token] }}
url: ${{ secrets[matrix.codecov-instance.url] }}
url: ${{ matrix.codecov-instance.url == 'url1' && secrets.CODECOV_URL1 || matrix.codecov-instance.url == 'url2' && secrets.CODECOV_URL2 }}

@@ -201,3 +201,3 @@
token: ${{ secrets[matrix.codecov-instance.token] }}
url: ${{ secrets[matrix.codecov-instance.url] }}
url: ${{ matrix.codecov-instance.url == 'url1' && secrets.CODECOV_URL1 || matrix.codecov-instance.url == 'url2' && secrets.CODECOV_URL2 }}
# The coverage action will have installed codecovcli with pip. The
Copilot is powered by AI and may make mistakes. Always verify output.
disable_search: true
token: ${{ secrets[matrix.codecov_token_secret] }}
url: ${{ secrets[matrix.codecov_url_secret] }}
token: ${{ secrets[matrix.codecov-instance.token] }}

Check warning

Code scanning / CodeQL

Excessive Secrets Exposure Medium

All organization and repository secrets are passed to the workflow runner in
secrets[matrix.codecov-instance.token]

Copilot Autofix

AI 16 days ago

To fix the issue, we need to avoid dynamically accessing secrets using secrets[matrix.codecov-instance.token]. Instead, explicitly define the secrets required for each matrix configuration. This can be achieved by adding specific secrets as inputs to the workflow or by using conditional logic to assign the correct secret based on the matrix configuration. This ensures that only the necessary secrets are passed to the workflow runner.

For example, replace the dynamic secret access with explicit references to specific secrets like secrets.CODECOV_TOKEN_PROD or secrets.CODECOV_TOKEN_DEV, depending on the matrix configuration.


Suggested changeset 1
.github/workflows/_run-tests.yml

Autofix patch

Autofix patch
Run the following command in your local git repository to apply this patch
cat << 'EOF' | git apply
diff --git a/.github/workflows/_run-tests.yml b/.github/workflows/_run-tests.yml
--- a/.github/workflows/_run-tests.yml
+++ b/.github/workflows/_run-tests.yml
@@ -163,4 +163,4 @@
           use_pypi: true
-          token: ${{ secrets[matrix.codecov-instance.token] }}
-          url: ${{ secrets[matrix.codecov-instance.url] }}
+          token: ${{ matrix.codecov_instance_token }}
+          url: ${{ matrix.codecov_instance_url }}
 
@@ -176,4 +176,4 @@
           use_pypi: true
-          token: ${{ secrets[matrix.codecov-instance.token] }}
-          url: ${{ secrets[matrix.codecov-instance.url] }}
+          token: ${{ matrix.codecov_instance_token }}
+          url: ${{ matrix.codecov_instance_url }}
 
@@ -186,4 +186,4 @@
           disable_search: true
-          token: ${{ secrets[matrix.codecov-instance.token] }}
-          url: ${{ secrets[matrix.codecov-instance.url] }}
+          token: ${{ matrix.codecov_instance_token }}
+          url: ${{ matrix.codecov_instance_url }}
           # The coverage action will have installed codecovcli with pip. The
@@ -200,4 +200,4 @@
           disable_search: true
-          token: ${{ secrets[matrix.codecov-instance.token] }}
-          url: ${{ secrets[matrix.codecov-instance.url] }}
+          token: ${{ matrix.codecov_instance_token }}
+          url: ${{ matrix.codecov_instance_url }}
           # The coverage action will have installed codecovcli with pip. The
EOF
@@ -163,4 +163,4 @@
use_pypi: true
token: ${{ secrets[matrix.codecov-instance.token] }}
url: ${{ secrets[matrix.codecov-instance.url] }}
token: ${{ matrix.codecov_instance_token }}
url: ${{ matrix.codecov_instance_url }}

@@ -176,4 +176,4 @@
use_pypi: true
token: ${{ secrets[matrix.codecov-instance.token] }}
url: ${{ secrets[matrix.codecov-instance.url] }}
token: ${{ matrix.codecov_instance_token }}
url: ${{ matrix.codecov_instance_url }}

@@ -186,4 +186,4 @@
disable_search: true
token: ${{ secrets[matrix.codecov-instance.token] }}
url: ${{ secrets[matrix.codecov-instance.url] }}
token: ${{ matrix.codecov_instance_token }}
url: ${{ matrix.codecov_instance_url }}
# The coverage action will have installed codecovcli with pip. The
@@ -200,4 +200,4 @@
disable_search: true
token: ${{ secrets[matrix.codecov-instance.token] }}
url: ${{ secrets[matrix.codecov-instance.url] }}
token: ${{ matrix.codecov_instance_token }}
url: ${{ matrix.codecov_instance_url }}
# The coverage action will have installed codecovcli with pip. The
Copilot is powered by AI and may make mistakes. Always verify output.
token: ${{ secrets[matrix.codecov_token_secret] }}
url: ${{ secrets[matrix.codecov_url_secret] }}
token: ${{ secrets[matrix.codecov-instance.token] }}
url: ${{ secrets[matrix.codecov-instance.url] }}

Check warning

Code scanning / CodeQL

Excessive Secrets Exposure Medium

All organization and repository secrets are passed to the workflow runner in
secrets[matrix.codecov-instance.url]

Copilot Autofix

AI 16 days ago

To fix the problem, we need to replace the dynamic secret access (secrets[matrix.codecov-instance.url]) with explicit references to specific secrets. This ensures that only the required secrets are passed to the workflow runner, adhering to the principle of least privilege.

The best approach is to define separate secrets for each possible matrix.codecov-instance.url value and reference them explicitly in the workflow. For example, if the matrix can have values like instance1 and instance2, we should define secrets like CODECOV_INSTANCE1_URL and CODECOV_INSTANCE2_URL and use conditional logic to select the appropriate secret based on the matrix value.

Suggested changeset 1
.github/workflows/_run-tests.yml

Autofix patch

Autofix patch
Run the following command in your local git repository to apply this patch
cat << 'EOF' | git apply
diff --git a/.github/workflows/_run-tests.yml b/.github/workflows/_run-tests.yml
--- a/.github/workflows/_run-tests.yml
+++ b/.github/workflows/_run-tests.yml
@@ -163,4 +163,4 @@
           use_pypi: true
-          token: ${{ secrets[matrix.codecov-instance.token] }}
-          url: ${{ secrets[matrix.codecov-instance.url] }}
+          token: ${{ secrets.CODECOV_INSTANCE_TOKEN }}
+          url: ${{ secrets.CODECOV_INSTANCE_URL }}
 
@@ -176,4 +176,4 @@
           use_pypi: true
-          token: ${{ secrets[matrix.codecov-instance.token] }}
-          url: ${{ secrets[matrix.codecov-instance.url] }}
+          token: ${{ secrets.CODECOV_INSTANCE_TOKEN }}
+          url: ${{ secrets.CODECOV_INSTANCE_URL }}
 
@@ -186,4 +186,4 @@
           disable_search: true
-          token: ${{ secrets[matrix.codecov-instance.token] }}
-          url: ${{ secrets[matrix.codecov-instance.url] }}
+          token: ${{ secrets.CODECOV_INSTANCE_TOKEN }}
+          url: ${{ secrets.CODECOV_INSTANCE_URL }}
           # The coverage action will have installed codecovcli with pip. The
@@ -200,4 +200,4 @@
           disable_search: true
-          token: ${{ secrets[matrix.codecov-instance.token] }}
-          url: ${{ secrets[matrix.codecov-instance.url] }}
+          token: ${{ secrets.CODECOV_INSTANCE_TOKEN }}
+          url: ${{ secrets.CODECOV_INSTANCE_URL }}
           # The coverage action will have installed codecovcli with pip. The
EOF
@@ -163,4 +163,4 @@
use_pypi: true
token: ${{ secrets[matrix.codecov-instance.token] }}
url: ${{ secrets[matrix.codecov-instance.url] }}
token: ${{ secrets.CODECOV_INSTANCE_TOKEN }}
url: ${{ secrets.CODECOV_INSTANCE_URL }}

@@ -176,4 +176,4 @@
use_pypi: true
token: ${{ secrets[matrix.codecov-instance.token] }}
url: ${{ secrets[matrix.codecov-instance.url] }}
token: ${{ secrets.CODECOV_INSTANCE_TOKEN }}
url: ${{ secrets.CODECOV_INSTANCE_URL }}

@@ -186,4 +186,4 @@
disable_search: true
token: ${{ secrets[matrix.codecov-instance.token] }}
url: ${{ secrets[matrix.codecov-instance.url] }}
token: ${{ secrets.CODECOV_INSTANCE_TOKEN }}
url: ${{ secrets.CODECOV_INSTANCE_URL }}
# The coverage action will have installed codecovcli with pip. The
@@ -200,4 +200,4 @@
disable_search: true
token: ${{ secrets[matrix.codecov-instance.token] }}
url: ${{ secrets[matrix.codecov-instance.url] }}
token: ${{ secrets.CODECOV_INSTANCE_TOKEN }}
url: ${{ secrets.CODECOV_INSTANCE_URL }}
# The coverage action will have installed codecovcli with pip. The
Copilot is powered by AI and may make mistakes. Always verify output.
disable_search: true
token: ${{ secrets[matrix.codecov_token_secret] }}
url: ${{ secrets[matrix.codecov_url_secret] }}
token: ${{ secrets[matrix.codecov-instance.token] }}

Check warning

Code scanning / CodeQL

Excessive Secrets Exposure Medium

All organization and repository secrets are passed to the workflow runner in
secrets[matrix.codecov-instance.token]

Copilot Autofix

AI 16 days ago

To fix the issue, we need to replace the dynamic secret access (secrets[matrix.codecov-instance.token]) with explicit references to the required secrets. This involves defining specific secrets for each matrix configuration (e.g., GH_PAT_PROD, GH_PAT_DEV) and using conditional logic to assign the correct secret based on the matrix values. This ensures that only the necessary secrets are passed to the workflow runner.


Suggested changeset 1
.github/workflows/_run-tests.yml

Autofix patch

Autofix patch
Run the following command in your local git repository to apply this patch
cat << 'EOF' | git apply
diff --git a/.github/workflows/_run-tests.yml b/.github/workflows/_run-tests.yml
--- a/.github/workflows/_run-tests.yml
+++ b/.github/workflows/_run-tests.yml
@@ -163,4 +163,4 @@
           use_pypi: true
-          token: ${{ secrets[matrix.codecov-instance.token] }}
-          url: ${{ secrets[matrix.codecov-instance.url] }}
+          token: ${{ matrix.codecov-instance == 'prod' && secrets.CODECOV_TOKEN_PROD || matrix.codecov-instance == 'dev' && secrets.CODECOV_TOKEN_DEV }}
+          url: ${{ matrix.codecov-instance == 'prod' && secrets.CODECOV_URL_PROD || matrix.codecov-instance == 'dev' && secrets.CODECOV_URL_DEV }}
 
@@ -176,4 +176,4 @@
           use_pypi: true
-          token: ${{ secrets[matrix.codecov-instance.token] }}
-          url: ${{ secrets[matrix.codecov-instance.url] }}
+          token: ${{ matrix.codecov-instance == 'prod' && secrets.CODECOV_TOKEN_PROD || matrix.codecov-instance == 'dev' && secrets.CODECOV_TOKEN_DEV }}
+          url: ${{ matrix.codecov-instance == 'prod' && secrets.CODECOV_URL_PROD || matrix.codecov-instance == 'dev' && secrets.CODECOV_URL_DEV }}
 
@@ -186,4 +186,4 @@
           disable_search: true
-          token: ${{ secrets[matrix.codecov-instance.token] }}
-          url: ${{ secrets[matrix.codecov-instance.url] }}
+          token: ${{ matrix.codecov-instance == 'prod' && secrets.CODECOV_TOKEN_PROD || matrix.codecov-instance == 'dev' && secrets.CODECOV_TOKEN_DEV }}
+          url: ${{ matrix.codecov-instance == 'prod' && secrets.CODECOV_URL_PROD || matrix.codecov-instance == 'dev' && secrets.CODECOV_URL_DEV }}
           # The coverage action will have installed codecovcli with pip. The
@@ -200,4 +200,4 @@
           disable_search: true
-          token: ${{ secrets[matrix.codecov-instance.token] }}
-          url: ${{ secrets[matrix.codecov-instance.url] }}
+          token: ${{ matrix.codecov-instance == 'prod' && secrets.CODECOV_TOKEN_PROD || matrix.codecov-instance == 'dev' && secrets.CODECOV_TOKEN_DEV }}
+          url: ${{ matrix.codecov-instance == 'prod' && secrets.CODECOV_URL_PROD || matrix.codecov-instance == 'dev' && secrets.CODECOV_URL_DEV }}
           # The coverage action will have installed codecovcli with pip. The
EOF
@@ -163,4 +163,4 @@
use_pypi: true
token: ${{ secrets[matrix.codecov-instance.token] }}
url: ${{ secrets[matrix.codecov-instance.url] }}
token: ${{ matrix.codecov-instance == 'prod' && secrets.CODECOV_TOKEN_PROD || matrix.codecov-instance == 'dev' && secrets.CODECOV_TOKEN_DEV }}
url: ${{ matrix.codecov-instance == 'prod' && secrets.CODECOV_URL_PROD || matrix.codecov-instance == 'dev' && secrets.CODECOV_URL_DEV }}

@@ -176,4 +176,4 @@
use_pypi: true
token: ${{ secrets[matrix.codecov-instance.token] }}
url: ${{ secrets[matrix.codecov-instance.url] }}
token: ${{ matrix.codecov-instance == 'prod' && secrets.CODECOV_TOKEN_PROD || matrix.codecov-instance == 'dev' && secrets.CODECOV_TOKEN_DEV }}
url: ${{ matrix.codecov-instance == 'prod' && secrets.CODECOV_URL_PROD || matrix.codecov-instance == 'dev' && secrets.CODECOV_URL_DEV }}

@@ -186,4 +186,4 @@
disable_search: true
token: ${{ secrets[matrix.codecov-instance.token] }}
url: ${{ secrets[matrix.codecov-instance.url] }}
token: ${{ matrix.codecov-instance == 'prod' && secrets.CODECOV_TOKEN_PROD || matrix.codecov-instance == 'dev' && secrets.CODECOV_TOKEN_DEV }}
url: ${{ matrix.codecov-instance == 'prod' && secrets.CODECOV_URL_PROD || matrix.codecov-instance == 'dev' && secrets.CODECOV_URL_DEV }}
# The coverage action will have installed codecovcli with pip. The
@@ -200,4 +200,4 @@
disable_search: true
token: ${{ secrets[matrix.codecov-instance.token] }}
url: ${{ secrets[matrix.codecov-instance.url] }}
token: ${{ matrix.codecov-instance == 'prod' && secrets.CODECOV_TOKEN_PROD || matrix.codecov-instance == 'dev' && secrets.CODECOV_TOKEN_DEV }}
url: ${{ matrix.codecov-instance == 'prod' && secrets.CODECOV_URL_PROD || matrix.codecov-instance == 'dev' && secrets.CODECOV_URL_DEV }}
# The coverage action will have installed codecovcli with pip. The
Copilot is powered by AI and may make mistakes. Always verify output.
token: ${{ secrets[matrix.codecov_token_secret] }}
url: ${{ secrets[matrix.codecov_url_secret] }}
token: ${{ secrets[matrix.codecov-instance.token] }}
url: ${{ secrets[matrix.codecov-instance.url] }}

Check warning

Code scanning / CodeQL

Excessive Secrets Exposure Medium

All organization and repository secrets are passed to the workflow runner in
secrets[matrix.codecov-instance.url]

Copilot Autofix

AI 16 days ago

To fix the issue, we need to replace the dynamic access to secrets (secrets[matrix.codecov-instance.url]) with explicit references to the required secrets. This involves defining specific secrets for each possible value of matrix.codecov-instance.url and using conditional logic to assign the correct secret based on the matrix configuration. This ensures that only the necessary secrets are passed to the workflow.

Suggested changeset 1
.github/workflows/_run-tests.yml

Autofix patch

Autofix patch
Run the following command in your local git repository to apply this patch
cat << 'EOF' | git apply
diff --git a/.github/workflows/_run-tests.yml b/.github/workflows/_run-tests.yml
--- a/.github/workflows/_run-tests.yml
+++ b/.github/workflows/_run-tests.yml
@@ -163,4 +163,4 @@
           use_pypi: true
-          token: ${{ secrets[matrix.codecov-instance.token] }}
-          url: ${{ secrets[matrix.codecov-instance.url] }}
+          token: ${{ secrets.CODECOV_TOKEN }}
+          url: ${{ matrix.codecov-instance.url == 'prod' && secrets.CODECOV_URL_PROD || matrix.codecov-instance.url == 'dev' && secrets.CODECOV_URL_DEV }}
 
@@ -176,4 +176,4 @@
           use_pypi: true
-          token: ${{ secrets[matrix.codecov-instance.token] }}
-          url: ${{ secrets[matrix.codecov-instance.url] }}
+          token: ${{ secrets.CODECOV_TOKEN }}
+          url: ${{ matrix.codecov-instance.url == 'prod' && secrets.CODECOV_URL_PROD || matrix.codecov-instance.url == 'dev' && secrets.CODECOV_URL_DEV }}
 
@@ -186,4 +186,4 @@
           disable_search: true
-          token: ${{ secrets[matrix.codecov-instance.token] }}
-          url: ${{ secrets[matrix.codecov-instance.url] }}
+          token: ${{ secrets.CODECOV_TOKEN }}
+          url: ${{ matrix.codecov-instance.url == 'prod' && secrets.CODECOV_URL_PROD || matrix.codecov-instance.url == 'dev' && secrets.CODECOV_URL_DEV }}
           # The coverage action will have installed codecovcli with pip. The
@@ -200,4 +200,4 @@
           disable_search: true
-          token: ${{ secrets[matrix.codecov-instance.token] }}
-          url: ${{ secrets[matrix.codecov-instance.url] }}
+          token: ${{ secrets.CODECOV_TOKEN }}
+          url: ${{ matrix.codecov-instance.url == 'prod' && secrets.CODECOV_URL_PROD || matrix.codecov-instance.url == 'dev' && secrets.CODECOV_URL_DEV }}
           # The coverage action will have installed codecovcli with pip. The
EOF
@@ -163,4 +163,4 @@
use_pypi: true
token: ${{ secrets[matrix.codecov-instance.token] }}
url: ${{ secrets[matrix.codecov-instance.url] }}
token: ${{ secrets.CODECOV_TOKEN }}
url: ${{ matrix.codecov-instance.url == 'prod' && secrets.CODECOV_URL_PROD || matrix.codecov-instance.url == 'dev' && secrets.CODECOV_URL_DEV }}

@@ -176,4 +176,4 @@
use_pypi: true
token: ${{ secrets[matrix.codecov-instance.token] }}
url: ${{ secrets[matrix.codecov-instance.url] }}
token: ${{ secrets.CODECOV_TOKEN }}
url: ${{ matrix.codecov-instance.url == 'prod' && secrets.CODECOV_URL_PROD || matrix.codecov-instance.url == 'dev' && secrets.CODECOV_URL_DEV }}

@@ -186,4 +186,4 @@
disable_search: true
token: ${{ secrets[matrix.codecov-instance.token] }}
url: ${{ secrets[matrix.codecov-instance.url] }}
token: ${{ secrets.CODECOV_TOKEN }}
url: ${{ matrix.codecov-instance.url == 'prod' && secrets.CODECOV_URL_PROD || matrix.codecov-instance.url == 'dev' && secrets.CODECOV_URL_DEV }}
# The coverage action will have installed codecovcli with pip. The
@@ -200,4 +200,4 @@
disable_search: true
token: ${{ secrets[matrix.codecov-instance.token] }}
url: ${{ secrets[matrix.codecov-instance.url] }}
token: ${{ secrets.CODECOV_TOKEN }}
url: ${{ matrix.codecov-instance.url == 'prod' && secrets.CODECOV_URL_PROD || matrix.codecov-instance.url == 'dev' && secrets.CODECOV_URL_DEV }}
# The coverage action will have installed codecovcli with pip. The
Copilot is powered by AI and may make mistakes. Always verify output.
Copy link

codspeed-hq bot commented Jun 20, 2025

CodSpeed Performance Report

Merging #256 will not alter performance

Comparing matt/ci-rewrite (fdfadc2) with main (93a3ac0)

Summary

✅ 9 untouched benchmarks

@matt-codecov matt-codecov force-pushed the matt/ci-rewrite branch 2 times, most recently from 1b832e3 to cae21b3 Compare June 20, 2025 22:35
Comment on lines +27 to +135
output_directory: apps/worker
make_target_prefix: worker.

- project: codecov-api
enabled: ${{ contains(fromJSON(inputs.changes), 'codecov-api') }}
repo: ${{ vars.CODECOV_API_IMAGE_V2 || vars.CODECOV_API_IMAGE_V2_SELF_HOSTED || 'codecov/self-hosted-api' }}
output_directory: apps/codecov-api
make_target_prefix: api.

- project: shared
enabled: ${{ contains(fromJSON(inputs.changes), 'shared') }}
repo: codecov/dev-shared
output_directory: libs/shared
make_target_prefix: shared.

env:
AR_REPO: ${{ matrix.repo }}
steps:
- name: Checkout
if: ${{ matrix.enabled }}
uses: actions/checkout@v4
with:
fetch-depth: 2

- id: "auth"
if: ${{ matrix.enabled && !github.event.pull_request.head.repo.fork && github.repository_owner == 'codecov' }}
name: "Authenticate to Google Cloud"
uses: "google-github-actions/auth@v2.1.2"
with:
token_format: "access_token"
workload_identity_provider: ${{ secrets.CODECOV_GCP_WIDP }}
service_account: ${{ secrets.CODECOV_GCP_WIDSA }}

- name: Docker configuration
if: ${{ matrix.enabled && !github.event.pull_request.head.repo.fork && github.repository_owner == 'codecov' }}
run: |-
echo ${{steps.auth.outputs.access_token}} | docker login -u oauth2accesstoken --password-stdin https://us-docker.pkg.dev

- name: Cache Requirements
id: cache-requirements
if: ${{ matrix.enabled }}
uses: actions/cache@v4
env:
# Forks can't access the variable containing our actual image repository. We want to
# use a separate cache to make sure they don't interfere with reqs images being pushed.
cache-name: ${{ !github.event.pull_request.repo.fork && 'umbrella-requirements' || 'umbrella-requirements-fork' }}
with:
path: |
./requirements.tar
key: ${{ runner.os }}-${{ runner.arch }}-${{ env.cache-name }}-${{ hashFiles('uv.lock') }}-${{ hashFiles('docker/Dockerfile.requirements') }}-${{ hashFiles('libs/shared/**') }}

- name: Cache App
id: cache-app
if: ${{ matrix.enabled && inputs.build-prod }}
uses: actions/cache@v4
env:
cache-name: ${{ matrix.repo }}-app
with:
path: |
${{ matrix.output_directory }}/app.tar
key: ${{ runner.os }}-${{ env.cache-name }}-${{ github.run_id }}

- name: Cache Self-Hosted
id: cache-self-hosted
if: ${{ matrix.enabled && inputs.build-self-hosted }}
uses: actions/cache@v4
env:
cache-name: ${{ matrix.repo }}-self-hosted
with:
path: |
${{ matrix.output_directory }}/self-hosted-runtime.tar
${{ matrix.output_directory }}/self-hosted.tar
key: ${{ runner.os }}-${{ env.cache-name }}-${{ github.run_id }}

- name: Load requirements from cache
if: ${{ matrix.enabled && steps.cache-requirements.outputs.cache-hit == 'true' }}
run: |
make load.requirements

# This shouldn't happen; the _build-requirements.yml job should have run.
- name: Build/pull requirements
if: ${{ matrix.enabled && steps.cache-requirements.outputs.cache-hit != 'true' }}
run: |
echo "Warning: requirements image not in cache, building a new one"
make build.requirements
make save.requirements

- name: Build Prod
if: ${{ matrix.enabled && inputs.build-prod }}
run: |
make ${{ matrix.make_target_prefix }}build.app
make ${{ matrix.make_target_prefix }}save.app

- name: Build Self-Hosted
if: ${{ matrix.enabled && inputs.build-self-hosted }}
run: |
make ${{ matrix.make_target_prefix }}build.self-hosted
make ${{ matrix.make_target_prefix }}save.self-hosted

build-test:

Check warning

Code scanning / CodeQL

Workflow does not contain permissions Medium

Actions job or workflow does not limit the permissions of the GITHUB_TOKEN. Consider setting an explicit permissions block, using the following as a minimal starting point: {contents: read}

Copilot Autofix

AI 16 days ago

To fix the issue, we will add a permissions block at the root of the workflow file. This block will define the minimal permissions required for the workflow to function correctly. Based on the provided workflow, the contents: read permission is sufficient unless specific steps require additional permissions. If any job or step requires write permissions (e.g., for pull requests or issues), we will explicitly define those permissions at the job level.


Suggested changeset 1
.github/workflows/_build-images.yml

Autofix patch

Autofix patch
Run the following command in your local git repository to apply this patch
cat << 'EOF' | git apply
diff --git a/.github/workflows/_build-images.yml b/.github/workflows/_build-images.yml
--- a/.github/workflows/_build-images.yml
+++ b/.github/workflows/_build-images.yml
@@ -2,2 +2,5 @@
 
+permissions:
+  contents: read
+
 on:
EOF
@@ -2,2 +2,5 @@

permissions:
contents: read

on:
Copilot is powered by AI and may make mistakes. Always verify output.
Comment on lines +136 to +223
name: Build Test App
if: ${{ inputs.build-prod }}
runs-on: ubuntu-latest
strategy:
fail-fast: false
matrix:
include:
- project: worker
enabled: ${{ contains(fromJSON(inputs.changes), 'worker') }}
repo: ${{ vars.CODECOV_WORKER_IMAGE_V2 || vars.CODECOV_WORKER_IMAGE_V2_SELF_HOSTED || 'codecov/self-hosted-worker' }}
output_directory: apps/worker
make_target_prefix: worker.

- project: codecov-api
enabled: ${{ contains(fromJSON(inputs.changes), 'codecov-api') }}
repo: ${{ vars.CODECOV_API_IMAGE_V2 || vars.CODECOV_API_IMAGE_V2_SELF_HOSTED || 'codecov/self-hosted-api' }}
output_directory: apps/codecov-api
make_target_prefix: api.

- project: shared
enabled: ${{ contains(fromJSON(inputs.changes), 'shared') }}
repo: codecov/dev-shared
output_directory: libs/shared
make_target_prefix: shared.

env:
AR_REPO: ${{ matrix.repo }}
steps:
- name: Checkout
if: ${{ matrix.enabled }}
uses: actions/checkout@v4
with:
fetch-depth: 2

- id: "auth"
if: ${{ matrix.enabled && !github.event.pull_request.head.repo.fork && github.repository_owner == 'codecov' }}
name: "Authenticate to Google Cloud"
uses: "google-github-actions/auth@v2.1.2"
with:
token_format: "access_token"
workload_identity_provider: ${{ secrets.CODECOV_GCP_WIDP }}
service_account: ${{ secrets.CODECOV_GCP_WIDSA }}

- name: Docker configuration
if: ${{ matrix.enabled && !github.event.pull_request.head.repo.fork && github.repository_owner == 'codecov' }}
run: |-
echo ${{steps.auth.outputs.access_token}} | docker login -u oauth2accesstoken --password-stdin https://us-docker.pkg.dev

- name: Cache Test Requirements
id: cache-test-requirements
if: ${{ matrix.enabled }}
uses: actions/cache@v4
env:
cache-name: umbrella-test-requirements
with:
path: |
./test-requirements.tar
key: ${{ runner.os }}-${{ runner.arch }}-${{ env.cache-name }}-${{ hashFiles('./uv.lock') }}-${{ hashFiles('docker/Dockerfile.requirements') }}-${{ hashFiles('docker/Dockerfile.test-requirements') }}-${{ hashFiles('libs/shared/**') }}

- name: Cache Test App
id: cache-test-app
if: ${{ matrix.enabled }}
uses: actions/cache@v4
env:
cache-name: ${{ matrix.repo }}-test-app
with:
path: |
${{ matrix.output_directory }}/test-app.tar
key: ${{ runner.os }}-${{ env.cache-name }}-${{ github.run_id }}

- name: Load test requirements from cache
if: ${{ matrix.enabled && steps.cache-test-requirements.outputs.cache-hit == 'true' }}
run: |
make load.test-requirements

# This shouldn't happen; the _build-requirements.yml job should have run.
- name: Build/pull test requirements
if: ${{ matrix.enabled && steps.cache-test-requirements.outputs.cache-hit != 'true' }}
run: |
echo "Warning: test requirements image not in cache, building a new one"
make build.test-requirements
make save.test-requirements

- name: Build Test App
if: ${{ matrix.enabled }}
run: |
make ${{ matrix.make_target_prefix }}build.test-app
make ${{ matrix.make_target_prefix }}save.test-app

Check warning

Code scanning / CodeQL

Workflow does not contain permissions Medium

Actions job or workflow does not limit the permissions of the GITHUB_TOKEN. Consider setting an explicit permissions block, using the following as a minimal starting point: {contents: read}

Copilot Autofix

AI 16 days ago

To fix the issue, we will add a permissions block at the root of the workflow file. This block will define the minimal permissions required for the workflow to function correctly. Based on the workflow's operations (e.g., checking out code, caching, and interacting with Docker), the contents: read permission is sufficient for most steps. If specific steps require additional permissions (e.g., pull-requests: write), they can be added explicitly.

The permissions block will be added after the name field at the top of the file to apply to all jobs in the workflow.


Suggested changeset 1
.github/workflows/_build-images.yml

Autofix patch

Autofix patch
Run the following command in your local git repository to apply this patch
cat << 'EOF' | git apply
diff --git a/.github/workflows/_build-images.yml b/.github/workflows/_build-images.yml
--- a/.github/workflows/_build-images.yml
+++ b/.github/workflows/_build-images.yml
@@ -1,2 +1,4 @@
 name: Build Images
+permissions:
+  contents: read
 
EOF
@@ -1,2 +1,4 @@
name: Build Images
permissions:
contents: read

Copilot is powered by AI and may make mistakes. Always verify output.
@codecov-notifications
Copy link

codecov-notifications bot commented Jun 20, 2025

Codecov Report

All modified and coverable lines are covered by tests ✅

✅ All tests successful. No failed tests found.

📢 Thoughts on this report? Let us know!

Copy link

codecov bot commented Jun 20, 2025

Codecov Report

All modified and coverable lines are covered by tests ✅

Project coverage is 94.25%. Comparing base (9806daa) to head (fdfadc2).

✅ All tests successful. No failed tests found.

Additional details and impacted files
@@           Coverage Diff           @@
##             main     #256   +/-   ##
=======================================
  Coverage   94.25%   94.25%           
=======================================
  Files        1215     1215           
  Lines       45114    45114           
  Branches     1437     1437           
=======================================
  Hits        42522    42522           
  Misses       2291     2291           
  Partials      301      301           
Flag Coverage Δ
apiunit 96.52% <ø> (ø)
sharedintegration 39.78% <ø> (ø)
sharedunit 88.23% <ø> (ø)
workerintegration 61.64% <ø> (ø)
workerunit 90.60% <ø> (ø)

Flags with carried forward coverage won't be shown. Click here to find out more.

☔ View full report in Codecov by Sentry.
📢 Have feedback on the report? Share it here.

@matt-codecov matt-codecov force-pushed the matt/ci-rewrite branch 6 times, most recently from 04a5047 to e03d631 Compare June 21, 2025 01:25
Comment on lines 30 to 171
if: ${{ matrix.enabled && (inputs.push-prod || inputs.push-self-hosted-release) }}
uses: actions/cache@v4
env:
cache-name: ${{ matrix.repo }}-self-hosted
with:
path: |
${{ matrix.output_directory }}/self-hosted-runtime.tar
${{ matrix.output_directory }}/self-hosted.tar
key: ${{ runner.os }}-${{ env.cache-name }}-${{ github.run_id }}

- name: Load Cached App
if: ${{ matrix.enabled && (inputs.push-prod || inputs.push-staging) }}
run: |
make ${{ matrix.make_target_prefix }}load.app

- name: Load Cached Self-Hosted
if: ${{ matrix.enabled && (inputs.push-prod || inputs.push-self-hosted-release) }}
run: |
make ${{ matrix.make_target_prefix }}load.self-hosted

- id: "auth"
if: ${{ matrix.enabled && (inputs.push-prod || inputs.push-staging) }}
name: "Authenticate to Google Cloud"
uses: "google-github-actions/auth@v2.1.2"
with:
token_format: "access_token"
workload_identity_provider: ${{ secrets.CODECOV_GCP_WIDP }}
service_account: ${{ secrets.CODECOV_GCP_WIDSA }}

# Set up Docker to push to our GCR repositories
- name: Docker configuration
if: ${{ matrix.enabled && (inputs.push-prod || inputs.push-staging) }}
if: ${{ !github.event.pull_request.head.repo.fork && github.repository_owner == 'codecov' }}
run: |-
echo ${{steps.auth.outputs.access_token}} | docker login -u oauth2accesstoken --password-stdin https://us-docker.pkg.dev

- name: Push Production Image
if: ${{ matrix.enabled && inputs.push-prod }}
run: |
make ${{ matrix.make_target_prefix }}tag.production
make ${{ matrix.make_target_prefix }}tag.latest
make ${{ matrix.make_target_prefix }}push.production
make ${{ matrix.make_target_prefix }}push.latest

- name: Push Staging Image
if: ${{ matrix.enabled && inputs.push-staging }}
run: |
make ${{ matrix.make_target_prefix }}tag.staging
make ${{ matrix.make_target_prefix }}push.staging

- name: Get Sentry Release SHA
if: ${{ matrix.enabled && (inputs.push-prod || inputs.push-staging) }}
env:
SHA: ${{ github.sha }}
id: sha
run: echo short_sha="${SHA:0:7}" >> $GITHUB_OUTPUT

- name: Create Production Sentry Release
if: ${{ matrix.enabled && inputs.push-prod }}
uses: getsentry/action-release@v1
env:
SENTRY_AUTH_TOKEN: ${{ secrets.CODECOV_SENTRY_RELEASE_TOKEN }}
SENTRY_ORG: ${{ secrets.CODECOV_SENTRY_ORG }}
SENTRY_PROJECT: ${{ matrix.sentry_project }}
with:
environment: production
version: production-release-${{ steps.sha.outputs.short_sha }}
ignore_missing: true

- name: Create Staging Sentry Release
if: ${{ matrix.enabled && inputs.push-staging }}
uses: getsentry/action-release@v1
env:
SENTRY_AUTH_TOKEN: ${{ secrets.CODECOV_SENTRY_RELEASE_TOKEN }}
SENTRY_ORG: ${{ secrets.CODECOV_SENTRY_ORG }}
SENTRY_PROJECT: ${{ matrix.sentry_project }}
with:
environment: staging
version: staging-release-${{ steps.sha.outputs.short_sha }}
ignore_missing: true

# Set up Docker to push to our Docker Hub repositories
- name: Log in to Docker Hub
if: ${{ matrix.enabled && (inputs.push-prod || inputs.push-self-hosted-release) }}
uses: docker/login-action@v3.1.0
with:
username: ${{ secrets.CODECOV_DEVOPS_DOCKER_USERNAME }}
password: ${{ secrets.CODECOV_DEVOPS_DOCKER_PASSWORD }}

- name: Push Self-Hosted Rolling Images
if: ${{ matrix.enabled && inputs.push-prod }}
run: |
make ${{ matrix.make_target_prefix }}tag.self-hosted-rolling
make ${{ matrix.make_target_prefix }}push.self-hosted-rolling

- name: Push Self-Hosted Release Images
if: ${{ matrix.enabled && inputs.push-self-hosted-release }}
run: |
make ${{ matrix.make_target_prefix }}tag.self-hosted-release
make ${{ matrix.make_target_prefix }}push.self-hosted-release

Check warning

Code scanning / CodeQL

Workflow does not contain permissions Medium

Actions job or workflow does not limit the permissions of the GITHUB_TOKEN. Consider setting an explicit permissions block, using the following as a minimal starting point: {contents: read}

Copilot Autofix

AI 16 days ago

To fix the issue, add a permissions block to the workflow. Since the workflow involves actions like checking out code, caching, authenticating to Google Cloud, and pushing Docker images, the permissions should be restricted to the minimum required. For example:

  • contents: read for accessing repository contents.
  • packages: write for pushing Docker images.
  • Additional permissions can be added as needed for specific steps.

The permissions block can be added at the workflow level (applies to all jobs) or at the job level (specific to the push-image job). In this case, adding it at the workflow level is more concise and ensures all jobs inherit the same minimal permissions.


Suggested changeset 1
.github/workflows/_push-images.yml

Autofix patch

Autofix patch
Run the following command in your local git repository to apply this patch
cat << 'EOF' | git apply
diff --git a/.github/workflows/_push-images.yml b/.github/workflows/_push-images.yml
--- a/.github/workflows/_push-images.yml
+++ b/.github/workflows/_push-images.yml
@@ -2,2 +2,6 @@
 
+permissions:
+  contents: read
+  packages: write
+
 on:
EOF
@@ -2,2 +2,6 @@

permissions:
contents: read
packages: write

on:
Copilot is powered by AI and may make mistakes. Always verify output.
@matt-codecov matt-codecov requested review from ElioDiNino, trent-codecov and a team June 23, 2025 15:39
@matt-codecov matt-codecov marked this pull request as ready for review June 23, 2025 15:39
@matt-codecov matt-codecov requested a review from ajay-sentry June 23, 2025 15:44
Copy link
Contributor

@Swatinem Swatinem left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think these changes make sense. The matrix definitions might be a bit annoying but I think its better that spreading this across different files.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

2 participants