Skip to content

Conversation

@apuig
Copy link
Contributor

@apuig apuig commented Oct 24, 2025

See JENKINS-76235 for reproduction steps and screen-cast.

When saving an organization folder, the system automatically checks the connection for registered webhooks.
This check fails gracefully with an IOException, but it may also throw an IllegalArgumentException if the issue is related to the connection’s owner.

This PR catches all possible exceptions, making the afterSave process a best-effort operation.

Original exception, app is installed in test-corp, but Owner in 'Specify specific repositories' is owner-creds:

java.lang.IllegalArgumentException: Found multiple installations for GitHub app ID XXXX but none match credential owner "owner-creds". Configure the repository access strategy for the credential to use one of these owners: test-corp
	at PluginClassLoader for github-branch-source//org.jenkinsci.plugins.github_branch_source.GitHubAppCredentials.generateAppInstallationToken(GitHubAppCredentials.java:321)
	at PluginClassLoader for github-branch-source//org.jenkinsci.plugins.github_branch_source.GitHubAppCredentials.getToken(GitHubAppCredentials.java:393)
	at PluginClassLoader for github-branch-source//org.jenkinsci.plugins.github_branch_source.GitHubAppCredentials$CredentialsTokenProvider.getEncodedAuthorization(GitHubAppCredentials.java:265)
	at PluginClassLoader for github-api//org.kohsuke.github.GitHubClient.prepareConnectorRequest(GitHubClient.java:616)
	at PluginClassLoader for github-api//org.kohsuke.github.GitHubClient.sendRequest(GitHubClient.java:455)
	at PluginClassLoader for github-api//org.kohsuke.github.GitHubClient.fetch(GitHubClient.java:159)
	at PluginClassLoader for github-api//org.kohsuke.github.GitHubClient.checkApiUrlValidity(GitHubClient.java:390)
	at PluginClassLoader for github-api//org.kohsuke.github.GitHub.checkApiUrlValidity(GitHub.java:1310)
	at PluginClassLoader for github-branch-source//org.jenkinsci.plugins.github_branch_source.ApiRateLimitChecker.verifyConnection(ApiRateLimitChecker.java:192)
	at PluginClassLoader for github-branch-source//org.jenkinsci.plugins.github_branch_source.Connector$GitHubConnection.verifyConnection(Connector.java:738)
	at PluginClassLoader for github-branch-source//org.jenkinsci.plugins.github_branch_source.Connector.connect(Connector.java:435)
	at PluginClassLoader for github-branch-source//org.jenkinsci.plugins.github_branch_source.GitHubSCMNavigator.afterSave(GitHubSCMNavigator.java:1693)

🗣️ While working on the fix, I noticed another issue (JENKINS-76236), but I do not currently plan to address it myself.

Submitter checklist

  • Link to JIRA ticket in description, if appropriate.
  • Change is code complete and matches issue description
  • Automated tests have been added to exercise the changes
  • Reviewer's manual test instructions provided in PR description. See Reviewer's first task below.

Reviewer checklist

  • Run the changes and verify that the change matches the issue description
  • Reviewed the code
  • Verified that the appropriate tests have been written or valid explanation given

Documentation changes

  • Link to jenkins.io PR, or an explanation for why no doc changes are needed

Users/aliases to notify

@apuig apuig requested a review from a team as a code owner October 24, 2025 11:01
Copy link
Member

@jtnord jtnord left a comment

Choose a reason for hiding this comment

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

So a user can now save an invalid configuration and they have no feedback taht things will not work?

Shouldn't this throw a hudson.model.Descriptor.FormException or something else that can be suitably shown to the user? (was there any validation of the field before the save?)

@jtnord jtnord requested a review from a team October 24, 2025 11:05
Connector.release(hub);
}
} catch (IOException e) {
} catch (Exception e) {
Copy link
Member

Choose a reason for hiding this comment

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

the user setting up the job may not have access to the Jenkins logs (they may not be an admin) and as such how will they be able to tell that something was wrong with the config (as opposed to a transient issue with GH that should recover?)

Copy link
Contributor Author

Choose a reason for hiding this comment

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

After breaking the credentials, accessing the folder configuration triggers an error that reports the connection issue. The same Exception cached in afterSave is also shown.
Screenshot from 2025-10-23 17-35-51

To help prevent these situations, I suggest adding the ability to perform an early check while editing the credentials JENKINS-76236

Copy link
Contributor Author

Choose a reason for hiding this comment

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

to be clear: there is no need to change any folder attribute, but the connection check in afterSave prevents any update (e.g its not the user making a mistake in this form)

Copy link
Member

Choose a reason for hiding this comment

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

(e.g its not the user making a mistake in this form)

the user is choosing the credential (that is invalid) in this form though?

Copy link
Contributor Author

Choose a reason for hiding this comment

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

Indeed, it is also possible to create a new folder and select an invalid Credential. In such cases, the field’s validation method correctly reports the selection as invalid (and the stacktrace provides details), yet it is still possible to save the folder.

My statement was based on the steps described in the Jira: first, set up the app and folder correctly, and then modify the credential owner to trigger this issue (IMO where a new validation should be added).
Then, in this scenario, accessing the folder config also shows a failed connection, but with this change, it allows updating any other information.

Please note that afterSave was intentionally swallowing IOExceptions, which cover many error cases (not founds or connectivity issues). However, this IllegalArgumentException is specific to the owner logic and was not included in that catch block.

Copy link
Member

@jtnord jtnord Oct 24, 2025

Choose a reason for hiding this comment

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

However, this IllegalArgumentException is specific to the owner logic and was not included in that catch block.

But I think this is important - An IOException is by its nature likely to be transient when talking to remote servers, however IllegalStateException is not and it is (in this case IIUC) saying your page save is rubbish.
Throwing the exception is bad as it results in the angry Jenkins and I am not disagreeing with that part, however I am saying this IllegalStateException is a special case should be caught and then presented to the user in an understandable way say e.g. "The owner for the GitHub Application is invalid for this repository/organisation etc etc..".
Swallowing it and logging, is sweeping an issue with the configuration under the carpet, and is not good UX.

Copy link
Contributor Author

Choose a reason for hiding this comment

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

IIRC in this case the IllegalStateException could be transient (and easily fixed with the reported error), and its not related to jenkins confs. This is not coming from the folder configuration itself but rather from the credential (just to reiterate) when the app is not installed (or have been removed) in the selected credential owner.
It’s not a Jenkins internal state issue, but rather related to the installation status of the app on GitHub (which the error gives a hint on how to fix it).

We may want to prevent folder creation in these scenarios. However, for folders that were previously working but have since lost their connection, it seems reasonable to allow updates to fields like the description (for example, to indicate “don’t use this anymore”).

@jtnord jtnord requested a review from a team October 24, 2025 12:10
@jtnord jtnord merged commit c09e017 into jenkinsci:master Oct 24, 2025
17 checks passed
@jtnord jtnord added the bug label Oct 24, 2025
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants