chore: harden installAtEnd integrity contracts - #445
Open
gnodet wants to merge 1 commit into
Open
Conversation
Security audit findings (integrity hardening, no adversary): - f005 (LOW): Group reactor projects by plugin presence instead of execution-id equality; log explicit partial-install inventory on mid-loop deferred-install failure - f006 (LOW): Synchronize the deferred-install mark-check-fire sequence; transition project state to INSTALLED for exactly-once semantics Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
5 tasks
| ArtifactInstallerRequest request = | ||
| (ArtifactInstallerRequest) pluginContext.get(ArtifactInstallerRequest.class.getName()); | ||
| try { | ||
| installProject(request); |
Member
There was a problem hiding this comment.
In 3.x branch we build request wich contains all artifacts from all projects, and finally repositorySystem.install is called only once, so we resolver take care about install all artifacts
Contributor
Author
There was a problem hiding this comment.
Correct — 3.x collects all artifacts into a single InstallRequest and calls repositorySystem.install() only once, so:
- f005 (usingPlugin): 3.x already matches by plugin presence (
hasExecutionchecks goals + phase ≠ none), not by execution-id — no fix needed - f005 (partial-install inventory): the single atomic install means there is no per-project loop that could fail mid-way — no partial state to log
- f006 (DEFERRED_INSTALL_LOCK): even if two threads race into the deferred block, the second call just re-installs the same request — idempotent, no risk of mixed state
No backport to 3.x planned for this PR.
gnodet
marked this pull request as ready for review
September 1, 2026 10:57
Contributor
Author
|
No backport to
|
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.
Summary
Hardens the
installAtEndintegrity contracts inInstallMojo, addressing two findings from a static security audit. No adversary steers these — they are reported because the plugin's own javadoc promises an all-or-nothing property the code does not enforce, and the deviation lands in the trusted-on-arrival shared local repository.Findings addressed
Changes
usingPlugin()now groups reactor projects by plugin presence (any execution not bound to phasenone) instead of exact execution-id equality. A module binding the goal under a custom id can no longer observe a singleton project set, trivially satisfyallProjectsMarked, and install mid-build.installAtEndjavadoc is updated to state the actual guarantee.synchronizedblock (static lock shared across reactor threads). Each project transitionsTO_BE_INSTALLED → INSTALLEDinside the loop, so a concurrent or repeated trigger skips completed work.Category
Integrity hardening — no adversary, no live exploit. The documented all-or-nothing contract is now enforced.
Test plan
usingPluginMatchesAnyExecutionId— custom execution id is recognizedusingPluginIgnoresExecutionsBoundToNone— phasenoneis excludedmidLoopFailureLogsPartialInstallInventory— explicit inventory logged on failuredeferredInstallRunsExactlyOncePerProject— secondexecute()call does not re-installmvn clean install -Bsucceeds🤖 Generated with Claude Code