From 038cbc322141dfbdabe1db25957763ceed282843 Mon Sep 17 00:00:00 2001 From: Claude Date: Tue, 7 Jul 2026 08:13:16 +0000 Subject: [PATCH] fix: fail fast on missing Publishing secrets in Java publish workflow The publish workflow signed artifacts (maven-gpg-plugin, bound to the release profile's verify phase) on both dry runs and real publishes, but its credential guard validated only the Maven Central secrets and was skipped on dry runs. A missing GPG signing key therefore surfaced deep in Maven as an opaque "gpg: no default secret key: No secret key" error. Add an early "Require publishing secrets" step that validates the GPG signing secrets (MAVEN_GPG_PRIVATE_KEY, MAVEN_GPG_PASSPHRASE) on every run and the Maven Central credentials on real publishes only, failing with an explicit message naming the missing secret(s). Bump client version to 0.1.1. --- .github/workflows/java-publish.yml | 58 +++++++++++++-------- CHANGELOG.md | 8 +++ README.md | 6 +-- pom.xml | 2 +- src/main/java/com/apify/client/Version.java | 2 +- 5 files changed, 49 insertions(+), 27 deletions(-) diff --git a/.github/workflows/java-publish.yml b/.github/workflows/java-publish.yml index 4ad8af1..1f8c22e 100644 --- a/.github/workflows/java-publish.yml +++ b/.github/workflows/java-publish.yml @@ -40,6 +40,42 @@ jobs: exit 1 fi + # Fail fast before the expensive build if the "Publishing" environment is missing any secret + # this run needs, so a release can never die deep inside Maven with a cryptic error on a + # mis-provisioned environment. GPG signing is bound to the release profile's `verify` phase, so + # the signing secrets are required for BOTH the dry run (`verify`) and the real publish + # (`deploy`) — this step therefore always runs; without it a missing MAVEN_GPG_PRIVATE_KEY only + # surfaces as maven-gpg-plugin's opaque "No secret key". The Maven Central repository + # credentials are consumed only by `deploy`, so they are required only on a real (non-dry) run. + - name: Require publishing secrets + env: + DRY_RUN: ${{ github.event.inputs.dry_run }} + MAVEN_GPG_PRIVATE_KEY: ${{ secrets.MAVEN_GPG_PRIVATE_KEY }} + MAVEN_GPG_PASSPHRASE: ${{ secrets.MAVEN_GPG_PASSPHRASE }} + MAVEN_CENTRAL_REPOSITORY_USERNAME: ${{ secrets.MAVEN_CENTRAL_REPOSITORY_USERNAME }} + MAVEN_CENTRAL_REPOSITORY_PASSWORD: ${{ secrets.MAVEN_CENTRAL_REPOSITORY_PASSWORD }} + MAVEN_CENTRAL_REPOSITORY_USERNAME_PASSWORD_BASE64: ${{ secrets.MAVEN_CENTRAL_REPOSITORY_USERNAME_PASSWORD_BASE64 }} + run: | + missing="" + # This project signs with a passphrase-protected key (setup-java is wired with + # gpg-passphrase), so both the key and its passphrase are mandatory. + [ -z "${MAVEN_GPG_PRIVATE_KEY}" ] && missing="${missing} MAVEN_GPG_PRIVATE_KEY" + [ -z "${MAVEN_GPG_PASSPHRASE}" ] && missing="${missing} MAVEN_GPG_PASSPHRASE" + # Maven Central credentials are only consumed by the real `deploy`. USERNAME/PASSWORD feed + # setup-java's "central" server; the base64 form is the same credential pre-encoded as the + # Central Portal bearer token (username:password), mandated in the Publishing environment by + # the client's publishing policy, so it is validated here to catch a mis-provisioned + # environment before a release proceeds. + if [ "${DRY_RUN}" != "true" ]; then + [ -z "${MAVEN_CENTRAL_REPOSITORY_USERNAME}" ] && missing="${missing} MAVEN_CENTRAL_REPOSITORY_USERNAME" + [ -z "${MAVEN_CENTRAL_REPOSITORY_PASSWORD}" ] && missing="${missing} MAVEN_CENTRAL_REPOSITORY_PASSWORD" + [ -z "${MAVEN_CENTRAL_REPOSITORY_USERNAME_PASSWORD_BASE64}" ] && missing="${missing} MAVEN_CENTRAL_REPOSITORY_USERNAME_PASSWORD_BASE64" + fi + if [ -n "${missing}" ]; then + echo "::error::Missing Publishing environment secret(s):${missing}" + exit 1 + fi + - name: Set up JDK uses: actions/setup-java@v4 with: @@ -85,28 +121,6 @@ jobs: exit 1 fi - # Verify the "Publishing" environment holds the three Maven Central repository secrets that the - # project's publishing policy mandates, so a release cannot silently proceed with a - # mis-provisioned environment. The mvn deploy below authenticates the "central" server with the - # username/password pair; the base64 form is the same credential pre-encoded as the Central - # Portal bearer token (username:password), kept in the environment per policy for tooling that - # talks to the Central Portal API directly. - - name: Require Maven Central credentials - if: ${{ github.event.inputs.dry_run != 'true' }} - env: - MAVEN_CENTRAL_REPOSITORY_USERNAME: ${{ secrets.MAVEN_CENTRAL_REPOSITORY_USERNAME }} - MAVEN_CENTRAL_REPOSITORY_PASSWORD: ${{ secrets.MAVEN_CENTRAL_REPOSITORY_PASSWORD }} - MAVEN_CENTRAL_REPOSITORY_USERNAME_PASSWORD_BASE64: ${{ secrets.MAVEN_CENTRAL_REPOSITORY_USERNAME_PASSWORD_BASE64 }} - run: | - missing="" - [ -z "${MAVEN_CENTRAL_REPOSITORY_USERNAME}" ] && missing="${missing} MAVEN_CENTRAL_REPOSITORY_USERNAME" - [ -z "${MAVEN_CENTRAL_REPOSITORY_PASSWORD}" ] && missing="${missing} MAVEN_CENTRAL_REPOSITORY_PASSWORD" - [ -z "${MAVEN_CENTRAL_REPOSITORY_USERNAME_PASSWORD_BASE64}" ] && missing="${missing} MAVEN_CENTRAL_REPOSITORY_USERNAME_PASSWORD_BASE64" - if [ -n "${missing}" ]; then - echo "::error::Missing Publishing environment secret(s):${missing}" - exit 1 - fi - # Build, sign and publish to Maven Central via the Sonatype Central Publisher Portal. The # central-publishing-maven-plugin authenticates the "central" server with the username/password # provisioned by setup-java above; both come from the "Publishing" environment's secrets. diff --git a/CHANGELOG.md b/CHANGELOG.md index f06e082..a413d87 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -5,6 +5,14 @@ All notable changes to the Apify Java client are documented in this file. The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/), and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.html). +## [0.1.1] - 2026-07-07 + +### Fixed + +- `Publish Java client` workflow now fails fast with an explicit message when a required `Publishing` + environment secret is missing (GPG signing secrets on dry runs and real publishes, Maven Central + credentials on real publishes only). + ## [0.1.0] - 2026-07-03 Initial release of the official (experimental, AI-generated and AI-maintained) Java client for the diff --git a/README.md b/README.md index 68bce1e..d38f655 100644 --- a/README.md +++ b/README.md @@ -21,14 +21,14 @@ Maven: com.apify apify-client - 0.1.0 + 0.1.1 ``` Gradle: ```groovy -implementation 'com.apify:apify-client:0.1.0' +implementation 'com.apify:apify-client:0.1.1' ``` ## Quick start @@ -122,7 +122,7 @@ try { ## Versioning -- `Version.CLIENT_VERSION` — the semantic version of this client (`0.1.0`). +- `Version.CLIENT_VERSION` — the semantic version of this client (`0.1.1`). - `Version.API_SPEC_VERSION` — the Apify OpenAPI specification version this client was verified against (`v2-2026-07-02T131926Z`). diff --git a/pom.xml b/pom.xml index 1d08b2b..a1d1372 100644 --- a/pom.xml +++ b/pom.xml @@ -6,7 +6,7 @@ com.apify apify-client - 0.1.0 + 0.1.1 jar Apify Java Client diff --git a/src/main/java/com/apify/client/Version.java b/src/main/java/com/apify/client/Version.java index 6b3cebf..bf180aa 100644 --- a/src/main/java/com/apify/client/Version.java +++ b/src/main/java/com/apify/client/Version.java @@ -13,7 +13,7 @@ public final class Version { * The semantic version of this client library (see SemVer). * Changes to the public interface other than additive ones are considered breaking changes. */ - public static final String CLIENT_VERSION = "0.1.0"; + public static final String CLIENT_VERSION = "0.1.1"; /** * The version of the Apify OpenAPI specification this client was generated and verified against.