Add github_organization_credential_authorization table - #552
Kanthi-Hegde wants to merge 2 commits into
Conversation
cbruno10
left a comment
There was a problem hiding this comment.
@Kanthi-Hegde Thanks for raising this PR! I've left a few minor suggestions.
Also, can you please share the results of the example queries (just for postgres is fine) in a PR comment so we can see the shape of real results? Thanks!
| KeyColumns: []*plugin.KeyColumn{ | ||
| {Name: "organization", Require: plugin.Required}, | ||
| }, | ||
| ShouldIgnoreError: isNotFoundError([]string{"404", "403"}), |
There was a problem hiding this comment.
Is there a reason we are ignoring 403 errors? I think ignoring these by default for the table is usually not desired behaviour, as the user wouldn't be aware of missing permissions.
| org := d.EqualsQuals["organization"].GetStringValue() | ||
|
|
||
| // Empty check | ||
| if org == "" { |
There was a problem hiding this comment.
Do we ever hit this if organization is a required qual for queries?
|
|
||
| The `github_organization_credential_authorization` table provides insights into the classic personal access tokens authorized against a GitHub organization. As a security or compliance engineer, use this table to inventory the classic PATs that can reach your organization's resources, review the scopes they have been granted, and identify tokens that are stale, never used, or approaching expiration. The same endpoint also returns authorized SSH keys, which can be distinguished using the `credential_type` column. | ||
|
|
||
| To query this table, the credential must be created under an organization owner. Classic personal access tokens require the `admin:org` scope (specifically `read:org`). |
There was a problem hiding this comment.
Having admin:org and read:org can't both be right, and GitHub's docs say admin:org for this endpoint.
Could you also mention it's classic PAT only (fine-grained tokens don't support it) and add the permissions block the other org tables have, e.g. github_organization_external_identity.md?
|
This PR is stale because it has been open 60 days with no activity. Remove stale label or comment or this will be closed in 30 days. |
cbruno10
left a comment
There was a problem hiding this comment.
@Kanthi-Hegde I've left a few suggestions, can you please have a look? Thanks!
| "github.com/turbot/steampipe-plugin-sdk/v5/grpc/proto" | ||
| "github.com/turbot/steampipe-plugin-sdk/v5/plugin" | ||
| "github.com/turbot/steampipe-plugin-sdk/v5/plugin/transform" |
There was a problem hiding this comment.
| "github.com/turbot/steampipe-plugin-sdk/v5/grpc/proto" | |
| "github.com/turbot/steampipe-plugin-sdk/v5/plugin" | |
| "github.com/turbot/steampipe-plugin-sdk/v5/plugin/transform" | |
| "github.com/turbot/steampipe-plugin-sdk/v6/grpc/proto" | |
| "github.com/turbot/steampipe-plugin-sdk/v6/plugin" | |
| "github.com/turbot/steampipe-plugin-sdk/v6/plugin/transform" |
main moved to SDK v6 in July, so can you please make this update so the plugin will build correctly after pulling in the latest from main?
|
|
||
| // Empty check | ||
| if org == "" { | ||
| return nil, fmt.Errorf("'organization' qual is required for the github_organization_credential_authorization table") | ||
| } |
There was a problem hiding this comment.
| // Empty check | |
| if org == "" { | |
| return nil, fmt.Errorf("'organization' qual is required for the github_organization_credential_authorization table") | |
| } |
See comment above please
| for { | ||
| creds, resp, err := client.Organizations.ListCredentialAuthorizations(ctx, org, opts) | ||
| if err != nil { | ||
| plugin.Logger(ctx).Error("github_organization_credential_authorization", "api_error", err) |
There was a problem hiding this comment.
| plugin.Logger(ctx).Error("github_organization_credential_authorization", "api_error", err) | |
| plugin.Logger(ctx).Error("github_organization_credential_authorization.tableGitHubOrganizationCredentialAuthorizationList", "api_error", err) |
Minor one, we usually use table.function for the log key
|
|
||
| **Important Notes** | ||
| - You must specify the `organization` column in the `where` or `join` clause to query the table. | ||
| - This table is only available for organizations on **GitHub Enterprise Cloud** that have **SAML single sign-on (SSO)** enabled. Organizations without SAML SSO return no rows. |
There was a problem hiding this comment.
This is only true because of the 403 in ShouldIgnoreError. Once that's out, this should say the query errors if the token isn't an org owner or SAML isn't enabled.
| "github_my_star": tableGitHubMyStar(), | ||
| "github_my_team": tableGitHubMyTeam(), | ||
| "github_organization": tableGitHubOrganization(), | ||
| "github_organization_credential_authorization": tableGitHubOrganizationCredentialAuthorization(), |
There was a problem hiding this comment.
This is where the merge conflict comes from. The new key is the longest in the map, so gofmt shifted every line and anything added on main since collides. Can you please take main's plugin.go, add just this one line, and then run gofmt.
Description
The plugin currently has no way to query classic personal access tokens (PATs) that members have authorized against an organization. This PR adds a new
github_organization_credential_authorizationtable to close that gap.It wraps GitHub's List SAML SSO authorizations for an organization REST API (
GET /orgs/{org}/credential-authorizations), which is the only API GitHub exposes for classic PATs at the org level. The same endpoint also returns authorized SSH keys, distinguishable via thecredential_typecolumn.What's included
github_organization_credential_authorizationplugin.goColumns
login,credential_id,token_last_eight,scopes,credential_type,credential_authorized_at,credential_accessed_at,authorized_credential_id,authorized_credential_note,authorized_credential_expires_at,authorized_credential_title,fingerprint.Notes
organizationqualifier is required.admin:org) and is only available for organizations on GitHub Enterprise Cloud with SAML SSO enabled; other orgs return no rows. A403/404is treated as an empty result, consistent with other org-scoped tables in this plugin.