Skip to content

ci/backward-compatibility-check - #634

Open
SNO7E-G wants to merge 4 commits into
google:mainfrom
SNO7E-G:ci/backward-compatibility-check
Open

ci/backward-compatibility-check#634
SNO7E-G wants to merge 4 commits into
google:mainfrom
SNO7E-G:ci/backward-compatibility-check

Conversation

@SNO7E-G

@SNO7E-G SNO7E-G commented Jul 27, 2026

Copy link
Copy Markdown
Contributor

1.5.0 shipped several BC breaks in a minor release without anyone noticing until after the tag (#628). This addsRoave/BackwardCompatibilityCheck as a CI job so that this class of mistake fails the build instead of reaching a release. As suggested in review, this is more robust than adding unit tests for specific bits of BC.

It runs as its own job and compares against the most recent release tag, so the checkout needs the full history rather than a shallow clone. It is added as a container action rather than a dev dependency, to keep it out of the project's own dependency resolution.

One ordering note: this is only useful once the restored API has been tagged. Until then, the most recent tag is 1.5.0, and the check would correctly flag the deliberate revert in the previous PR as a break.

Props to @acoulton

SNO7E-G added 2 commits July 28, 2026 02:10
1.5.0 introduced backward-incompatible changes in a minor release (google#628).
This restores src/ and tests/ to the 1.4.2 tag verbatim, so the library is
behaviourally identical to 1.4.2 for every consumer.

Verification: `git diff 1.4.2 -- src` is empty. There are no source changes
to review, and no version constant is touched here, since choosing and
tagging the release is the maintainers' call.

Restored by reverting rather than by re-implementing:
- untyped public signatures with phpdoc, no native param or return types
- no return type on the RequestMethod::submit() interface
- non-readonly Response and RequestParameters
- the Curl and Socket wrapper classes and their ?Curl / ?Socket
  dependency-injection constructors, so the documented pattern for testing
  a custom RequestMethod works again

1.4.2 predates the phpstan level max and php-cs-fixer setup this repo now
runs in CI, and reports 191 pre-existing errors, 62 of them in src/. Many
of those, such as offset access on mixed and resource parameters, cannot be
resolved with annotations alone. Changing code in a revert would defeat the
purpose of the revert, so they are recorded in phpstan-baseline.neon
instead. The follow-up hardening removes entries from it as it adds the
guards that fix them. php-cs-fixer needed no changes to the 1.4.2 sources.

phpunit 52 passing, phpstan clean against the baseline, php-cs-fixer clean.
1.5.0 shipped several BC breaks in a minor release without anyone noticing
until after the tag (google#628). This adds Roave/BackwardCompatibilityCheck as a
CI job so that class of mistake fails the build instead of reaching a
release.

The check runs as its own job and compares against the most recent release
tag, so the checkout needs the full history rather than a shallow clone. It
is added as a container action rather than a dev dependency, to keep it out
of the project's own dependency resolution.

One ordering note: this is only useful once the restored API has been
tagged, since until then the most recent tag is 1.5.0 and the check would
correctly flag the deliberate revert as a break.
Comment thread .github/workflows/php.yml Outdated
fetch-depth: 0

- name: Check for BC breaks since the last release
uses: docker://nyholm/roave-bc-check-ga

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

Unfortunately the nyholm/roave-bc-check-ga docker image isn't maintained by roave/backward-compatibility-check and is more than 3 years out of date (there's an open issue for this) - it contains a number of dependency versions with security vulnerabilities.

You could explore getting the docker image updated, alternatively in Behat we deal with this by just composer install roave-backward-compatibility-check in a temporary subdirectory, which ensures we're always using the latest versions. https://github.com/Behat/Behat/blob/b077d2c8ddc6c78506e4372150e0b6d9db3e0781/.github/workflows/build.yml#L154-L178

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

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

Good catch, thank you — I hadn't realised the Docker image was that stale. I've switched to the same approach Behat uses: composer-installing roave/backward-compatibility-check into its own directory at runtime, so it always picks up current releases and stays out of the project's dependency resolution. Pushed as a follow-up commit.

SNO7E-G added 2 commits August 4, 2026 19:07
Review on the PR pointed out that the nyholm/roave-bc-check-ga docker
image is not maintained by the Roave project, is several years out of
date, and carries dependency versions with known vulnerabilities.

Following the approach Behat uses: install
roave/backward-compatibility-check with composer into its own directory at
run time, so the check always runs with current releases while its
dependencies stay out of this library's own dependency resolution, then
invoke the binary directly with the github-actions output format.
The repository's workflow security check requires every action reference to
be pinned to a full commit hash rather than a mutable tag, and it flags all
five uses in this file, including the three that predate this branch. Each
is pinned to the commit behind the latest release within the major version
the workflow was already using, with the version kept as a comment:

- actions/checkout v4.4.0
- shivammathur/setup-php 2.37.2
- actions/cache v4.3.0

No behaviour change beyond moving to the newest release of each major.
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