chore: remove dead devops tooling (travis, codeship, heroku, coveralls, arcanist, garden)#5053
Merged
Merged
Conversation
tuxpiper
force-pushed
the
chore/devops-cleanup
branch
from
July 13, 2026 17:13
3751a70 to
c642bfe
Compare
…s, arcanist, garden)
GitHub Actions (.github/workflows/test-and-ship.yml) is the only CI system in use,
alongside Docker + the Makefile for local dev. Everything removed here is config for
tooling that is no longer wired to anything.
Removed:
- Travis CI: .travis.yml, .env.travis (travis-ci.org shut down in 2021)
- Codeship: codeship-{services,steps}.yml, deployment.env.encrypted, and the
Codeship-only docker/{build,test,release,awscli}.Dockerfile + their .run.sh
scripts. CloudBees CodeShip is EOL and these still declared PHP 7.2/7.3 services.
docker/release.sh is NOT part of this -- it is still used by the release-tar action.
- Coveralls: .coveralls.yml + the php-coveralls dev dep (nothing has uploaded
coverage since 2016). Drops the orphaned symfony/stopwatch transitive dep too.
- Heroku one-click deploy: app.json, Procfile, apache_heroku.conf (Procfile invoked
bin/heroku-php-apache2, which does not exist)
- Phabricator Arcanist: .arcconfig, .arclint (paths referenced the pre-Laravel
Kohana tree)
- Garden.io: garden.yaml, garden_modules/
- librarian-puppet: .librarian/ (pointed at a puppet/modules/ tree that is gone)
Orphan files with no referrer anywhere in the repo: skeleton.php (a 2014 code
template), example.env (superseded by .env.example), package-lock.json (empty, and
there is no package.json), mapping.json, the root pre-commit script (superseded by
captainhook.json), phpspec.yml.coverage, apiary.apib (a stub; the real blueprints
live in docs/api/), and tests/CaptainHook/PHPCS.php (orphaned when the pre-commit
hook was dropped from captainhook.json in 2022).
Also:
- .gitignore / .dockerignore: drop rules for the removed tooling and the Kohana-era
tree. Kept the *.aes / deployment.env / docker.env / vault.txt rules on purpose --
old working copies may still hold those secrets, and these rules are what stops
them being committed or baked into an image. Added tmp/ (a Codeship-jet leftover
that was untracked *and* unignored).
- docs: drop the dead Travis/Coveralls/Heroku badges, and repoint the Gitter/IRC
links (Gitter is sunset) at GitHub issues and ushahidi.com/support. The 2019
hackathon archive and the Code of Conduct venue list are left as-is.
- resources/lang/README.md: it claimed translations are pulled from Transifex
automatically. There is no such CI job, and PRs do edit the English source strings
directly, so the stated policy was misleading.
Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
tuxpiper
force-pushed
the
chore/devops-cleanup
branch
from
July 15, 2026 14:17
c642bfe to
3ec822f
Compare
…ock (#5054) * fix: revive the inert Feature test suite, drop the dead behat Mink block Three defects found while auditing the devops config. All verified against a throwaway mariadb:10.11 stack mirroring the CI job. 1. The tests/Feature phpunit suite matched zero tests. phpunit.xml.dist selects ./tests/Feature with suffix="Test.php", but the two files there were named ExportJobAPI.php and WebhooksPostsUpdateAPI.php, so nothing ever ran. They had also rotted since the 2022 Lumen -> Laravel migration and could not simply be renamed: ExportJobAPI imported Laravel\Lumen\Testing\DatabaseTransactions (Lumen is no longer installed), WebhooksPostsUpdateAPI declared setUp()/tearDown() without the ': void' return types PHPUnit 9 requires, and both used the Lumen assertion API (seeStatusCode/seeJson/seeJsonStructure/expectsJobs), which does not exist on Laravel's TestCase. Ported both to Laravel 8 + PHPUnit 9 and renamed them so the suite collects them: - seeStatusCode/seeJson/seeJsonStructure -> assertStatus/assertJson/ assertJsonStructure on the returned TestResponse - expectsJobs(ExportPostsJob::class) -> Bus::fake() + Bus::assertDispatched() - ExportJobAPI referenced \Ushahidi\Modules\Auth\GenericUser, which does not exist; the real class is \Ushahidi\Authzn\GenericUser ExportJobAPITest now creates its own admin user in setUp() instead of assuming user id 2. Ushahidi\Authzn\Session::getUser() loads the acting user from the database, and id 2 is only an admin in the behat fixture (tests/datasets), which phpunit never loads -- and which rewrites the users table when behat does load it. Owning the user keeps the suite independent of run order. phpunit now reports 176 tests / 552 assertions, up from 172 / 534. 2. behat.yml.dist declared a Behat\MinkExtension block, but it was indented as a child of suites.default rather than at profile level, so behat silently ignored it. That was load-bearing: mink is not in composer.lock at all, so hoisting the block to where it "belongs" would break all 738 scenarios with an extension-not-found error. Removed the block rather than fix its indentation. The three contexts use no Mink. behat: 738 scenarios / 6339 steps still pass. 3. .editorconfig set indent_style = spaces. The spec only accepts 'tab' or 'space', so editors ignored the value and indent style was unenforced. Now 'space'. Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com> * fix: make the Vagrantfile find the Homestead.yml that ships with the repo The Vagrantfile only looked for Homestead.yaml or Homestead.json, but the repo ships Homestead.yml -- and .gitignore ignores the two names it did look for. So following the setup docs ("the Vagrant and Homestead.yml files that ship with Ushahidi", then `vagrant up`) aborted with "Homestead settings file not found". Broken since Homestead.yml was re-added in 2023. Add Homestead.yml to the lookup chain, after Homestead.yaml/.json so a developer's local override still wins. Preferred over renaming the tracked file, which would land it under a gitignored name. Also point the abort message at the project directory it actually searches, rather than confDir (the vendor Homestead install). Verified statically: Vagrantfile parses (ruby -c), Homestead.yml parses as YAML and its settings resolve, and the lookup chain now selects Homestead.yml where it previously aborted. NOT boot-tested: Homestead.yml pins provider: virtualbox, and VirtualBox on Apple Silicon cannot run the x86_64 Homestead box, so `vagrant up` needs an Intel Mac or a Linux host. Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com> --------- Co-authored-by: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
dukedanny
pushed a commit
that referenced
this pull request
Jul 17, 2026
…cks CI) (#5055) * fix: vendor symm/gisconverter, whose upstream repo was deleted The project could not be installed from a clean checkout. symm/gisconverter's GitHub repository no longer exists, and the dist URL recorded in composer.lock points straight at it, so `composer install` died with: Failed to download symm/gisconverter from dist: The "https://api.github.com/ repos/symm/gisconverter/zipball/21ab697b..." file could not be downloaded (404) This broke every from-scratch build, develop included -- the last green CI run was 2026-04-21, and nothing has built from a cold cache since. It surfaced now only because that was the last time anyone pushed a branch that had to resolve dependencies without a warm vendor/ directory. The library is not droppable: it does the WKT geometry decoding behind PointRepository, BoundingBox, PostPoint, the V5 geometry query handlers and the Twitter data source. Packagist still serves the metadata but marks the package abandoned, and the only dist URL it offers is the dead one. No maintained fork exists to repoint at. So vendor it. packages/gisconverter/src is byte-identical to the v1.0.5 release (upstream ref 21ab697b7692b891dac37c64d10c9d83d4433f80), wired up with a composer path repository. symlink: false so composer copies it into vendor/ exactly as before, which keeps the docker build and the release tarball unchanged. Nothing that imports Symm\Gisconverter\... had to change. The upstream composer.json is trimmed to what we need and pinned with an explicit version, which a path repository requires. Upstream's tests, example.php and its long-dead Travis config are not copied. The BSD-3-Clause licence and copyright notice are retained as that licence requires; it is compatible with our AGPL-3.0. src/ruleset.xml excludes packages/* from phpcs, alongside vendor/*, so the vendored source stays byte-identical to upstream rather than being reformatted. Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com> * fix: copy packages/ into the docker build before composer install The image build runs `composer install` (Dockerfile line ~23) before `COPY . .`, with only composer.json/composer.lock in the build context. symm/gisconverter is now a path-repository package, so composer needs its source at that layer and the build fails with: In PathDownloader.php line 51: Source path "packages/gisconverter" is not found for package symm/gisconverter Copy packages/ into the context before the install. This only affects the `ship` job (the Docker image build), which is push-only and skipped on PR checks -- which is why it was not caught by the test job or the pull_request run. Verified with a full `docker build .`: the image builds end to end and vendor/symm/gisconverter is present and autoloadable inside it. Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com> * chore: remove dead devops tooling (travis, codeship, heroku, coveralls, arcanist, garden) (#5053) * chore: remove dead devops tooling (travis, codeship, heroku, coveralls, arcanist, garden) GitHub Actions (.github/workflows/test-and-ship.yml) is the only CI system in use, alongside Docker + the Makefile for local dev. Everything removed here is config for tooling that is no longer wired to anything. Removed: - Travis CI: .travis.yml, .env.travis (travis-ci.org shut down in 2021) - Codeship: codeship-{services,steps}.yml, deployment.env.encrypted, and the Codeship-only docker/{build,test,release,awscli}.Dockerfile + their .run.sh scripts. CloudBees CodeShip is EOL and these still declared PHP 7.2/7.3 services. docker/release.sh is NOT part of this -- it is still used by the release-tar action. - Coveralls: .coveralls.yml + the php-coveralls dev dep (nothing has uploaded coverage since 2016). Drops the orphaned symfony/stopwatch transitive dep too. - Heroku one-click deploy: app.json, Procfile, apache_heroku.conf (Procfile invoked bin/heroku-php-apache2, which does not exist) - Phabricator Arcanist: .arcconfig, .arclint (paths referenced the pre-Laravel Kohana tree) - Garden.io: garden.yaml, garden_modules/ - librarian-puppet: .librarian/ (pointed at a puppet/modules/ tree that is gone) Orphan files with no referrer anywhere in the repo: skeleton.php (a 2014 code template), example.env (superseded by .env.example), package-lock.json (empty, and there is no package.json), mapping.json, the root pre-commit script (superseded by captainhook.json), phpspec.yml.coverage, apiary.apib (a stub; the real blueprints live in docs/api/), and tests/CaptainHook/PHPCS.php (orphaned when the pre-commit hook was dropped from captainhook.json in 2022). Also: - .gitignore / .dockerignore: drop rules for the removed tooling and the Kohana-era tree. Kept the *.aes / deployment.env / docker.env / vault.txt rules on purpose -- old working copies may still hold those secrets, and these rules are what stops them being committed or baked into an image. Added tmp/ (a Codeship-jet leftover that was untracked *and* unignored). - docs: drop the dead Travis/Coveralls/Heroku badges, and repoint the Gitter/IRC links (Gitter is sunset) at GitHub issues and ushahidi.com/support. The 2019 hackathon archive and the Code of Conduct venue list are left as-is. - resources/lang/README.md: it claimed translations are pulled from Transifex automatically. There is no such CI job, and PRs do edit the English source strings directly, so the stated policy was misleading. Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com> * fix: revive the inert Feature test suite, drop the dead behat Mink block (#5054) * fix: revive the inert Feature test suite, drop the dead behat Mink block Three defects found while auditing the devops config. All verified against a throwaway mariadb:10.11 stack mirroring the CI job. 1. The tests/Feature phpunit suite matched zero tests. phpunit.xml.dist selects ./tests/Feature with suffix="Test.php", but the two files there were named ExportJobAPI.php and WebhooksPostsUpdateAPI.php, so nothing ever ran. They had also rotted since the 2022 Lumen -> Laravel migration and could not simply be renamed: ExportJobAPI imported Laravel\Lumen\Testing\DatabaseTransactions (Lumen is no longer installed), WebhooksPostsUpdateAPI declared setUp()/tearDown() without the ': void' return types PHPUnit 9 requires, and both used the Lumen assertion API (seeStatusCode/seeJson/seeJsonStructure/expectsJobs), which does not exist on Laravel's TestCase. Ported both to Laravel 8 + PHPUnit 9 and renamed them so the suite collects them: - seeStatusCode/seeJson/seeJsonStructure -> assertStatus/assertJson/ assertJsonStructure on the returned TestResponse - expectsJobs(ExportPostsJob::class) -> Bus::fake() + Bus::assertDispatched() - ExportJobAPI referenced \Ushahidi\Modules\Auth\GenericUser, which does not exist; the real class is \Ushahidi\Authzn\GenericUser ExportJobAPITest now creates its own admin user in setUp() instead of assuming user id 2. Ushahidi\Authzn\Session::getUser() loads the acting user from the database, and id 2 is only an admin in the behat fixture (tests/datasets), which phpunit never loads -- and which rewrites the users table when behat does load it. Owning the user keeps the suite independent of run order. phpunit now reports 176 tests / 552 assertions, up from 172 / 534. 2. behat.yml.dist declared a Behat\MinkExtension block, but it was indented as a child of suites.default rather than at profile level, so behat silently ignored it. That was load-bearing: mink is not in composer.lock at all, so hoisting the block to where it "belongs" would break all 738 scenarios with an extension-not-found error. Removed the block rather than fix its indentation. The three contexts use no Mink. behat: 738 scenarios / 6339 steps still pass. 3. .editorconfig set indent_style = spaces. The spec only accepts 'tab' or 'space', so editors ignored the value and indent style was unenforced. Now 'space'. Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com> * fix: make the Vagrantfile find the Homestead.yml that ships with the repo The Vagrantfile only looked for Homestead.yaml or Homestead.json, but the repo ships Homestead.yml -- and .gitignore ignores the two names it did look for. So following the setup docs ("the Vagrant and Homestead.yml files that ship with Ushahidi", then `vagrant up`) aborted with "Homestead settings file not found". Broken since Homestead.yml was re-added in 2023. Add Homestead.yml to the lookup chain, after Homestead.yaml/.json so a developer's local override still wins. Preferred over renaming the tracked file, which would land it under a gitignored name. Also point the abort message at the project directory it actually searches, rather than confDir (the vendor Homestead install). Verified statically: Vagrantfile parses (ruby -c), Homestead.yml parses as YAML and its settings resolve, and the lookup chain now selects Homestead.yml where it previously aborted. NOT boot-tested: Homestead.yml pins provider: virtualbox, and VirtualBox on Apple Silicon cannot run the x86_64 Homestead box, so `vagrant up` needs an Intel Mac or a Linux host. Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com> --------- Co-authored-by: Claude Opus 4.8 (1M context) <noreply@anthropic.com> --------- Co-authored-by: Claude Opus 4.8 (1M context) <noreply@anthropic.com> --------- Co-authored-by: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Why
The repo carries ~10 years of CI/CD config for tools nobody uses any more. Today there is exactly one live CI system — GitHub Actions (
.github/workflows/test-and-ship.yml) — plus Docker + theMakefilefor local dev. Everything removed here is config wired to nothing.This PR is purely subtractive. The three real bugs found while surveying are in a separate stacked PR so this one stays easy to review.
What's removed
.travis.yml,.env.traviscodeship-{services,steps}.yml,deployment.env.encrypted,docker/{build,test,release,awscli}.Dockerfile+ their.run.sh.coveralls.yml,php-coverallsdev depapp.json,Procfile,apache_heroku.confProcfileinvokedbin/heroku-php-apache2, which doesn't exist.arcconfig,.arclintgarden.yaml,garden_modules/buildModemodern Garden removed.librarian/puppet/modules/tree that is gonePlus orphan files with no referrer anywhere:
skeleton.php(a 2014 code template),example.env(superseded by.env.example),package-lock.json(empty — and there is nopackage.json),mapping.json, the rootpre-commitscript (superseded bycaptainhook.json),phpspec.yml.coverage,apiary.apib(a stub; real blueprints live indocs/api/), andtests/CaptainHook/PHPCS.php.What is deliberately NOT removed
docker/release.sh— sits right next to the Codeship-onlyrelease.Dockerfile/release.run.shbut is live:.github/actions/release-tarcalls it.composer testruns both. Behat is the dominant suite (738 scenarios vs 172 unit tests).*.aes/deployment.env/docker.env/vault.txtignore rules — kept in.gitignore/.dockerignoreon purpose. Old working copies may still hold those secrets, and these rules are what stops them being committed or baked into an image.Also
.gitignore/.dockerignore: dropped rules for the removed tooling and the Kohana-era tree; addedtmp/(a Codeship-jetleftover that was untracked and unignored).docs/README.md, and repointed the Gitter/IRC links (Gitter is sunset) at GitHub issues + ushahidi.com/support. The 2019 hackathon archive and the Code of Conduct venue list are left alone.resources/lang/README.md: it claimed translations are pulled from Transifex automatically. There is no such CI job, and PRs do edit the English source strings directly — the stated policy was misleading.Verification
Run against a throwaway
mariadb:10.11stack mirroring the CI job:composer lint(3 phpcs rulesets)Also verified: every deleted filename has zero remaining references (
git grep), allDockerfileCOPY inputs still exist, and.github/actions/release-tarstill resolvesdocker/release.sh.🤖 Generated with Claude Code