• 
      

    Add GitHub App connectivity.

    Review Request #15144 — Created June 30, 2026 and updated

    Information

    Review Board
    release-9.x

    Reviewers

    This change adds a GitHub App as an alternative to Personal Access
    Tokens. This involves a bunch of moving parts:

    1. The actual GitHub App backend, which includes a redirect view that
      will trigger the GitHub App Manifest flow, and callback views for
      when the app has been created and when the app has been installed
      into a user or organization. This ends up creating a hidden
      HostingServiceAccount which holds the app registration keys, and
      then each time the app gets installed (for a user or organization)
      will create a new HostingServiceAccount for that entry.

    2. Modifications to the GitHub client to use the app for authentication.
      This involves minting short-lived RS256 JWT tokens for the actual API
      requests to GitHub.

    3. Customized UI parts for the connected services list. This involves:

    • Special templates and flows for the "Connect a service" wizard which
      lets users choose how they want to connect, and triggers for the new
      app creation flow.

    • An override for the entry template which adds an extra controls
      panel that either encourages users to create the app (if they have
      existing connections using PATs only), or provides a link into
      GitHub's settings UI (allowing changes to URLs or transferring the
      app registration to another owner).

    This also currently includes a stub webhook handler (since GitHub Apps
    have a single webhook endpoint for all authorized repositories), as well
    as some commented-out bits for future enhancement.

    • Connected a GitHub App and installed it into multiple organizations.
    • Tested all aspects of the wizard flow, including creation of the app
      and reassignment of any PAT-based repositories after app install.
    • Verified that API access works correctly when authenticating using the
      app tokens.
    • Ran unit tests.
    Summary ID
    Add GitHub App connectivity.
    This change adds a GitHub App as an alternative to Personal Access Tokens. This involves a bunch of moving parts: 1. The actual GitHub App backend, which includes a redirect view that will trigger the GitHub App Manifest flow, and callback views for when the app has been created and when the app has been installed into a user or organization. This ends up creating a hidden `HostingServiceAccount` which holds the app registration keys, and then each time the app gets installed (for a user or organization) will create a new `HostingServiceAccount` for that entry. 2. Modifications to the GitHub client to use the app for authentication. This involves minting short-lived RS256 JWT tokens for the actual API requests to GitHub. 3. Customized UI parts for the connected services list. This involves: - Special templates and flows for the "Connect a service" wizard which lets users choose how they want to connect, and triggers for the new app creation flow. - An override for the entry template which adds an extra controls panel that either encourages users to create the app (if they have existing connections using PATs only), or provides a link into GitHub's settings UI (allowing changes to URLs or transferring the app registration to another owner). This also currently includes a stub webhook handler (since GitHub Apps have a single webhook endpoint for all authorized repositories), as well as some commented-out bits for future enhancement. Testing Done: - Connected a GitHub App and installed it into multiple organizations. - Tested all aspects of the wizard flow, including creation of the app and reassignment of any PAT-based repositories after app install. - Verified that API access works correctly when authenticating using the app tokens. - Ran unit tests.
    qmxulzkloxrsnquyqwrxwlrrquzplqpr

    Description From Last Updated

    Can we make a pydantic model for the GitHub app data (the github_app data stored on the installation account)?

    maubin maubin

    Ok so thinking about local sites again (this is on my mind from neglecting to really consider local sites when …

    maubin maubin

    Do we nicely handle things if there's a lot of repositories here? Like having a vertical scrollbar if there's a …

    maubin maubin

    continuation line under-indented for visual indent Column: 34 Error code: E128

    reviewbot reviewbot

    'reviewboard.site.models.LocalSite' imported but unused Column: 5 Error code: F401

    reviewbot reviewbot

    Can we rename to AppManifestResponse.

    maubin maubin

    Can we rename to InstallationAccountResponse.

    maubin maubin

    Can you add a Version Added to this.

    maubin maubin

    In this change the App views were put into reviewboard.hostingsvcs.github.views and I don't see any other changes where you split …

    maubin maubin

    This needs a Version Added.

    maubin maubin

    Should we pass local_site=request.get('local_site') here?

    maubin maubin

    I think there will always be a request.local_site attribute because of our LocalSiteMiddleware.

    maubin maubin

    Same note about request.local_site always existing.

    maubin maubin

    line too long (87 > 79 characters) Column: 80 Error code: E501

    reviewbot reviewbot

    line too long (85 > 79 characters) Column: 80 Error code: E501

    reviewbot reviewbot

    Missing a docstring.

    maubin maubin

    Could this be Literal['user', 'organization', '']?

    maubin maubin

    Same comment as above.

    maubin maubin

    Seems like this could be Literal['all', 'selected'].

    maubin maubin

    Can you add a docstring for this.

    maubin maubin

    This can be removed, we do this below in the if condition.

    maubin maubin

    We do these isinstance checks on the app data a lot more than we do is_installation_account() or is_app_record_account(). Might be …

    maubin maubin

    This can be an elif or add back in the blank line before this.

    maubin maubin

    We can remove local_site here because we do a local_site = app_account.local_site in the view instead of using this value …

    maubin maubin

    Same comment as above.

    maubin maubin

    I'm getting a bit mixed up with the namings. We have "app-record accounts" and "installation accounts". A hosting service account …

    maubin maubin
    Checks run (1 failed, 1 succeeded)
    flake8 failed.
    JSHint passed.

    flake8

    david
    david
    david
    david
    david
    Review request changed
    Change Summary:

    Update for renamed and changed APIs

    Commits:
    Summary ID
    Add GitHub App connectivity.
    This change adds a GitHub App as an alternative to Personal Access Tokens. This involves a bunch of moving parts: 1. The actual GitHub App backend, which includes a redirect view that will trigger the GitHub App Manifest flow, and callback views for when the app has been created and when the app has been installed into a user or organization. This ends up creating a hidden `HostingServiceAccount` which holds the app registration keys, and then each time the app gets installed (for a user or organization) will create a new `HostingServiceAccount` for that entry. 2. Modifications to the GitHub client to use the app for authentication. This involves minting short-lived RS256 JWT tokens for the actual API requests to GitHub. 3. Customized UI parts for the connected services list. This involves: - Special templates and flows for the "Connect a service" wizard which lets users choose how they want to connect, and triggers for the new app creation flow. - An override for the entry template which adds an extra controls panel that either encourages users to create the app (if they have existing connections using PATs only), or provides a link into GitHub's settings UI (allowing changes to URLs or transferring the app registration to another owner). This also currently includes a stub webhook handler (since GitHub Apps have a single webhook endpoint for all authorized repositories), as well as some commented-out bits for future enhancement. Testing Done: - Connected a GitHub App and installed it into multiple organizations. - Tested all aspects of the wizard flow, including creation of the app and reassignment of any PAT-based repositories after app install. - Verified that API access works correctly when authenticating using the app tokens. - Ran unit tests.
    qmxulzkloxrsnquyqwrxwlrrquzplqpr
    Add GitHub App connectivity.
    This change adds a GitHub App as an alternative to Personal Access Tokens. This involves a bunch of moving parts: 1. The actual GitHub App backend, which includes a redirect view that will trigger the GitHub App Manifest flow, and callback views for when the app has been created and when the app has been installed into a user or organization. This ends up creating a hidden `HostingServiceAccount` which holds the app registration keys, and then each time the app gets installed (for a user or organization) will create a new `HostingServiceAccount` for that entry. 2. Modifications to the GitHub client to use the app for authentication. This involves minting short-lived RS256 JWT tokens for the actual API requests to GitHub. 3. Customized UI parts for the connected services list. This involves: - Special templates and flows for the "Connect a service" wizard which lets users choose how they want to connect, and triggers for the new app creation flow. - An override for the entry template which adds an extra controls panel that either encourages users to create the app (if they have existing connections using PATs only), or provides a link into GitHub's settings UI (allowing changes to URLs or transferring the app registration to another owner). This also currently includes a stub webhook handler (since GitHub Apps have a single webhook endpoint for all authorized repositories), as well as some commented-out bits for future enhancement. Testing Done: - Connected a GitHub App and installed it into multiple organizations. - Tested all aspects of the wizard flow, including creation of the app and reassignment of any PAT-based repositories after app install. - Verified that API access works correctly when authenticating using the app tokens. - Ran unit tests.
    qmxulzkloxrsnquyqwrxwlrrquzplqpr

    Checks run (1 failed, 1 succeeded)

    flake8 failed.
    JSHint passed.

    flake8

    david
    david
    david
    maubin
    1. 
        
    2. Show all issues

      Can we make a pydantic model for the GitHub app data (the github_app data stored on the installation account)?

      1. That's a great idea, but I'll need to do it in a separate change because I have a couple other github-related changes in my stack that will also need updating.

      2. Changed my mind, merging it into this (and other) changes.

    3. Show all issues

      Do we nicely handle things if there's a lot of repositories here? Like having a vertical scrollbar if there's a bunch of repositories listed.

      1. Yeah, the contents of this dialog are scrollable when necessary.

    4. reviewboard/hostingsvcs/github/api.py (Diff revision 9)
       
       
      Show all issues

      Can we rename to AppManifestResponse.

    5. reviewboard/hostingsvcs/github/api.py (Diff revision 9)
       
       
      Show all issues

      Can we rename to InstallationAccountResponse.

      1. This is actually nested data inside of the Installation (and in a later change, webhook payloads), so it's not a response directly. I can change Installation to InstallationResponse, though.

    6. reviewboard/hostingsvcs/github/client.py (Diff revision 9)
       
       
       
       
       
      Show all issues

      Can you add a Version Added to this.

    7. Show all issues

      In this change the App views were put into reviewboard.hostingsvcs.github.views and I don't see any other changes where you split them out into an app_views module.

    8. Show all issues

      This needs a Version Added.

    9. Show all issues

      Should we pass local_site=request.get('local_site') here?

    10. Show all issues

      I think there will always be a request.local_site attribute because of our LocalSiteMiddleware.

    11. reviewboard/hostingsvcs/github/views.py (Diff revision 9)
       
       
      Show all issues

      Same note about request.local_site always existing.

    12. 
        
    david
    Review request changed
    Commits:
    Summary ID
    Add GitHub App connectivity.
    This change adds a GitHub App as an alternative to Personal Access Tokens. This involves a bunch of moving parts: 1. The actual GitHub App backend, which includes a redirect view that will trigger the GitHub App Manifest flow, and callback views for when the app has been created and when the app has been installed into a user or organization. This ends up creating a hidden `HostingServiceAccount` which holds the app registration keys, and then each time the app gets installed (for a user or organization) will create a new `HostingServiceAccount` for that entry. 2. Modifications to the GitHub client to use the app for authentication. This involves minting short-lived RS256 JWT tokens for the actual API requests to GitHub. 3. Customized UI parts for the connected services list. This involves: - Special templates and flows for the "Connect a service" wizard which lets users choose how they want to connect, and triggers for the new app creation flow. - An override for the entry template which adds an extra controls panel that either encourages users to create the app (if they have existing connections using PATs only), or provides a link into GitHub's settings UI (allowing changes to URLs or transferring the app registration to another owner). This also currently includes a stub webhook handler (since GitHub Apps have a single webhook endpoint for all authorized repositories), as well as some commented-out bits for future enhancement. Testing Done: - Connected a GitHub App and installed it into multiple organizations. - Tested all aspects of the wizard flow, including creation of the app and reassignment of any PAT-based repositories after app install. - Verified that API access works correctly when authenticating using the app tokens. - Ran unit tests.
    qmxulzkloxrsnquyqwrxwlrrquzplqpr
    Add GitHub App connectivity.
    This change adds a GitHub App as an alternative to Personal Access Tokens. This involves a bunch of moving parts: 1. The actual GitHub App backend, which includes a redirect view that will trigger the GitHub App Manifest flow, and callback views for when the app has been created and when the app has been installed into a user or organization. This ends up creating a hidden `HostingServiceAccount` which holds the app registration keys, and then each time the app gets installed (for a user or organization) will create a new `HostingServiceAccount` for that entry. 2. Modifications to the GitHub client to use the app for authentication. This involves minting short-lived RS256 JWT tokens for the actual API requests to GitHub. 3. Customized UI parts for the connected services list. This involves: - Special templates and flows for the "Connect a service" wizard which lets users choose how they want to connect, and triggers for the new app creation flow. - An override for the entry template which adds an extra controls panel that either encourages users to create the app (if they have existing connections using PATs only), or provides a link into GitHub's settings UI (allowing changes to URLs or transferring the app registration to another owner). This also currently includes a stub webhook handler (since GitHub Apps have a single webhook endpoint for all authorized repositories), as well as some commented-out bits for future enhancement. Testing Done: - Connected a GitHub App and installed it into multiple organizations. - Tested all aspects of the wizard flow, including creation of the app and reassignment of any PAT-based repositories after app install. - Verified that API access works correctly when authenticating using the app tokens. - Ran unit tests.
    qmxulzkloxrsnquyqwrxwlrrquzplqpr

    Checks run (1 failed, 1 succeeded)

    flake8 failed.
    JSHint passed.

    flake8

    david
    david
    david
    maubin
    1. 
        
    2. Show all issues

      Ok so thinking about local sites again (this is on my mind from neglecting to really consider local sites when implementing document review and then having to go in and add it later), is the idea for GitHub app-record accounts to be local-site dependent? This seems to be the current design because we pass local_site for both the app-record accounts and installation accounts (e.g. in make_connect_ui_context() we do HostingServiceAccount.objects.filter(service_name=..., local_site=request.local_site).

      But I know you mentioned possibly having a "GitHub App for all of RBCommons" in a reply to one of my other reviews. And we have staff_member_required decorators on the views, which means only server admins (not local site team admins) will be able to access the views.

      So even though RBCommons will require its own development effort, I think we need to make some design decisions at this stage since we are currently passing around local sites in this code.

      1. Hmm, I'll have to think about that a bit. Will follow up on that in a later change.

    3. Show all issues

      Missing a docstring.

    4. Show all issues

      Could this be Literal['user', 'organization', '']?

    5. Show all issues

      Same comment as above.

    6. Show all issues

      Seems like this could be Literal['all', 'selected'].

    7. reviewboard/hostingsvcs/github/accounts.py (Diff revision 13)
       
       
       
      Show all issues

      Can you add a docstring for this.

    8. Show all issues

      This can be removed, we do this below in the if condition.

    9. reviewboard/hostingsvcs/github/service.py (Diff revision 13)
       
       
       
       
       
       
      Show all issues

      We do these isinstance checks on the app data a lot more than we do is_installation_account() or is_app_record_account(). Might be worth making some is_installation_data() is_app_record_data() functions?

    10. Show all issues

      We can remove local_site here because we do a local_site = app_account.local_site in the view instead of using this value that was passed in.

      1. We do that in GitHubAppInstallCallbackView, but this is referring to GitHubAppInstallView.

    11. Show all issues

      Same comment as above.

    12. reviewboard/hostingsvcs/tests/github/test_app.py (Diff revision 13)
       
       
       
       
       
       
       
       
       
       
       
       
       
       
       
       
       
       
       
       
       
       
       
       
       
       
       
       
       
       
       
       
       
       
       
       
       
       
       
       
       
      Show all issues

      I'm getting a bit mixed up with the namings. We have "app-record accounts" and "installation accounts". A hosting service account can be either of those.

      Can we rename _create_app_record() to _create_app_record_account() to clarify that. And then rename _create_app_account() to _create_app_installation_account() to specify that its an installation account. Because "app account" could really mean either a record account or installation account, you even name the record account variable app_account.

    13. 
        
    david
    david
    Review request changed
    Change Summary:

    Reduce some duplication across test cases.

    Commits:
    Summary ID
    Add GitHub App connectivity.
    This change adds a GitHub App as an alternative to Personal Access Tokens. This involves a bunch of moving parts: 1. The actual GitHub App backend, which includes a redirect view that will trigger the GitHub App Manifest flow, and callback views for when the app has been created and when the app has been installed into a user or organization. This ends up creating a hidden `HostingServiceAccount` which holds the app registration keys, and then each time the app gets installed (for a user or organization) will create a new `HostingServiceAccount` for that entry. 2. Modifications to the GitHub client to use the app for authentication. This involves minting short-lived RS256 JWT tokens for the actual API requests to GitHub. 3. Customized UI parts for the connected services list. This involves: - Special templates and flows for the "Connect a service" wizard which lets users choose how they want to connect, and triggers for the new app creation flow. - An override for the entry template which adds an extra controls panel that either encourages users to create the app (if they have existing connections using PATs only), or provides a link into GitHub's settings UI (allowing changes to URLs or transferring the app registration to another owner). This also currently includes a stub webhook handler (since GitHub Apps have a single webhook endpoint for all authorized repositories), as well as some commented-out bits for future enhancement. Testing Done: - Connected a GitHub App and installed it into multiple organizations. - Tested all aspects of the wizard flow, including creation of the app and reassignment of any PAT-based repositories after app install. - Verified that API access works correctly when authenticating using the app tokens. - Ran unit tests.
    qmxulzkloxrsnquyqwrxwlrrquzplqpr
    Add GitHub App connectivity.
    This change adds a GitHub App as an alternative to Personal Access Tokens. This involves a bunch of moving parts: 1. The actual GitHub App backend, which includes a redirect view that will trigger the GitHub App Manifest flow, and callback views for when the app has been created and when the app has been installed into a user or organization. This ends up creating a hidden `HostingServiceAccount` which holds the app registration keys, and then each time the app gets installed (for a user or organization) will create a new `HostingServiceAccount` for that entry. 2. Modifications to the GitHub client to use the app for authentication. This involves minting short-lived RS256 JWT tokens for the actual API requests to GitHub. 3. Customized UI parts for the connected services list. This involves: - Special templates and flows for the "Connect a service" wizard which lets users choose how they want to connect, and triggers for the new app creation flow. - An override for the entry template which adds an extra controls panel that either encourages users to create the app (if they have existing connections using PATs only), or provides a link into GitHub's settings UI (allowing changes to URLs or transferring the app registration to another owner). This also currently includes a stub webhook handler (since GitHub Apps have a single webhook endpoint for all authorized repositories), as well as some commented-out bits for future enhancement. Testing Done: - Connected a GitHub App and installed it into multiple organizations. - Tested all aspects of the wizard flow, including creation of the app and reassignment of any PAT-based repositories after app install. - Verified that API access works correctly when authenticating using the app tokens. - Ran unit tests.
    qmxulzkloxrsnquyqwrxwlrrquzplqpr

    Checks run (2 succeeded)

    flake8 passed.
    JSHint passed.
    maubin
    1. 
        
    2. reviewboard/hostingsvcs/github/service.py (Diff revisions 13 - 15)
       
       
      Show all issues

      This can be an elif or add back in the blank line before this.

    3.