githubapp

package
v0.0.0-...-66ff4a7 Latest Latest
Warning

This package is not in the latest version of its module.

Go to latest
Published: May 25, 2021 License: Apache-2.0 Imports: 14 Imported by: 0

Documentation

Overview

Package githubapp implements an http.Handler for GitHub events and provides utilities for building GitHub applications. Most users will create implementations of githubapp.EventHandler to handle different webhook event types and register them with the event dispatcher.

Many functions are instrumented with optional logging and metrics collection. The package also defines functions to create authenticated GitHub clients and manage application installations.

Index

Constants

View Source
const (
	LogKeyEventType       string = "github_event_type"
	LogKeyDeliveryID      string = "github_delivery_id"
	LogKeyRepositoryName  string = "github_repository_name"
	LogKeyRepositoryOwner string = "github_repository_owner"
	LogKeyPRNum           string = "github_pr_num"
	LogKeyInstallationID  string = "github_installation_id"
)
View Source
const (
	MetricsKeyRequests    = "github.requests"
	MetricsKeyRequests2xx = "github.requests.2xx"
	MetricsKeyRequests3xx = "github.requests.3xx"
	MetricsKeyRequests4xx = "github.requests.4xx"
	MetricsKeyRequests5xx = "github.requests.5xx"
)
View Source
const (
	DefaultCachingClientCapacity = 64
)
View Source
const (
	DefaultWebhookRoute string = "/api/github/hook"
)

Variables

This section is empty.

Functions

func DefaultErrorHandler

func DefaultErrorHandler(w http.ResponseWriter, r *http.Request, err error)

DefaultErrorHandler logs errors and responds with a 500 status code.

func GetInstallationIDFromEvent

func GetInstallationIDFromEvent(event InstallationSource) int64

GetInstallationIDFromEvent returns the installation ID from a GitHub webhook event payload.

func NewDefaultEventDispatcher

func NewDefaultEventDispatcher(c Config, handlers ...EventHandler) http.Handler

NewDefaultEventDispatcher is a convenience method to create an EventDispatcher from configuration using the default error handler.

func NewEventDispatcher

func NewEventDispatcher(handlers []EventHandler, secret string, onError ErrorHandler) http.Handler

NewEventDispatcher creates an http.Handler that dispatches GitHub webhook requests to the appropriate event handlers. It validates payload integrity using the given secret value.

If an error occurs during handling, the error handler is called with the error and should write an appropriate response. If the error handler is nil, a default handler is used.

func PreparePRContext

func PreparePRContext(ctx context.Context, installationID int64, repo *github.Repository, number int) (context.Context, zerolog.Logger)

PreparePRContext adds information about a pull request to the logger in a context and returns the modified context and logger.

func PrepareRepoContext

func PrepareRepoContext(ctx context.Context, installationID int64, repo *github.Repository) (context.Context, zerolog.Logger)

PrepareRepoContext adds information about a repository to the logger in a context and returns the modified context and logger.

Types

type ClientCreator

type ClientCreator interface {
	// NewAppClient returns a new github.Client that performs app authentication for
	// the GitHub app with a specific integration ID and private key. The returned
	// client makes all calls using the application's authorization token. The
	// client gets that token by creating and signing a JWT for the application and
	// requesting a token using it. The token is cached by the client and is
	// refreshed as needed if it expires.
	//
	// Used for performing app-level operations that are not associated with a
	// specific installation.
	//
	// See the following for more information:
	//  * https://developer.github.com/apps/building-github-apps/authenticating-with-github-apps/#authenticating-as-a-github-app
	//
	// Authenticating as a GitHub App lets you do a couple of things:
	//  * You can retrieve high-level management information about your GitHub App.
	//  * You can request access tokens for an installation of the app.
	//
	// Tips for determining the arguments for this function:
	//  * the integration ID is listed as "ID" in the "About" section of the app's page
	//  * the key bytes must be a PEM-encoded PKCS1 or PKCS8 private key for the application
	NewAppClient() (*github.Client, error)

	// NewAppV4Client returns an app-authenticated v4 API client, similar to NewAppClient.
	NewAppV4Client() (*githubv4.Client, error)

	// NewInstallationClient returns a new github.Client that performs app
	// authentication for the GitHub app with the a specific integration ID, private
	// key, and the given installation ID. The returned client makes all calls using
	// the application's authorization token. The client gets that token by creating
	// and signing a JWT for the application and requesting a token using it. The
	// token is cached by the client and is refreshed as needed if it expires.
	//
	// See the following for more information:
	//  * https://developer.github.com/apps/building-github-apps/authenticating-with-github-apps/#authenticating-as-an-installation
	//
	// Authenticating as an installation of a Github App lets you perform the following:
	//  * https://developer.github.com/v3/apps/available-endpoints/
	//
	// Tips for determining the arguments for this function:
	//  * the integration ID is listed as "ID" in the "About" section of the app's page
	//  * the installation ID is the ID that is shown in the URL of https://{githubURL}/settings/installations/{#}
	//      (navigate to the "installations" page without the # and go to the app's page to see the number)
	//  * the key bytes must be a PEM-encoded PKCS1 or PKCS8 private key for the application
	NewInstallationClient(installationID int64) (*github.Client, error)

	// NewInstallationV4Client returns an installation-authenticated v4 API client, similar to NewInstallationClient.
	NewInstallationV4Client(installationID int64) (*githubv4.Client, error)

	// NewTokenClient returns a *github.Client that uses the passed in OAuth token for authentication.
	NewTokenClient(token string) (*github.Client, error)

	// NewTokenV4Client returns a *githubv4.Client that uses the passed in OAuth token for authentication.
	NewTokenV4Client(token string) (*githubv4.Client, error)
}

func NewCachingClientCreator

func NewCachingClientCreator(delegate ClientCreator, capacity int) (ClientCreator, error)

NewCachingClientCreator returns a ClientCreator that creates a GitHub client for installations of the app specified by the provided arguments. It uses an LRU cache of the provided capacity to store clients created for installations and returns cached clients when a cache hit exists.

func NewClientCreator

func NewClientCreator(v3BaseURL, v4BaseURL string, integrationID int64, privKeyBytes []byte, opts ...ClientOption) ClientCreator

NewClientCreator returns a ClientCreator that creates a GitHub client for installations of the app specified by the provided arguments.

func NewDefaultCachingClientCreator

func NewDefaultCachingClientCreator(c Config, opts ...ClientOption) (ClientCreator, error)

NewDefaultCachingClientCreator returns a ClientCreator using values from the configuration or other defaults.

type ClientMiddleware

type ClientMiddleware func(http.RoundTripper) http.RoundTripper

ClientMiddleware modifes the transport of a GitHub client to add common functionality, like logging or metrics collection.

func ClientLogging

func ClientLogging(lvl zerolog.Level) ClientMiddleware

ClientLogging creates client middleware that logs request and response information at the given level. If the request fails without creating a response, it is logged with a status code of -1. The middleware uses a logger from the request context.

func ClientMetrics

func ClientMetrics(registry metrics.Registry) ClientMiddleware

ClientMetrics creates client middleware that records metrics about all requests. It also defines the metrics in the provided registry.

type ClientOption

type ClientOption func(c *clientCreator)

func WithClientMiddleware

func WithClientMiddleware(middleware ...ClientMiddleware) ClientOption

WithClientMiddleware adds middleware that is applied to all created clients.

func WithClientUserAgent

func WithClientUserAgent(agent string) ClientOption

WithClientUserAgent sets the base user agent for all created clients.

type Config

type Config struct {
	WebURL   string `yaml:"web_url" json:"webUrl"`
	V3APIURL string `yaml:"v3_api_url" json:"v3ApiUrl"`
	V4APIURL string `yaml:"v4_api_url" json:"v4ApiUrl"`

	App struct {
		IntegrationID int64  `yaml:"integration_id" json:"integrationId"`
		WebhookSecret string `yaml:"webhook_secret" json:"webhookSecret"`
		PrivateKey    string `yaml:"private_key" json:"privateKey"`
	} `yaml:"app" json:"app"`

	OAuth struct {
		ClientID     string `yaml:"client_id" json:"clientId"`
		ClientSecret string `yaml:"client_secret" json:"clientSecret"`
		RedirectURL  string `yaml:"redirect_url" json:"redirectURL"`
	} `yaml:"oauth" json:"oauth"`
}

type ErrorHandler

type ErrorHandler func(http.ResponseWriter, *http.Request, error)

type EventHandler

type EventHandler interface {
	// Handles returns a list of GitHub events that this handler handles
	// See https://developer.github.com/v3/activity/events/types/
	Handles() []string

	// Handle processes the GitHub event "eventType" with the given delivery ID
	// and payload. The EventDispatcher guarantees that the Handle method will
	// only be called for the events returned by Handles().
	//
	// If Handle returns an error, processing stops and the error is passed
	// directly to the configured error handler.
	Handle(ctx context.Context, eventType, deliveryID string, payload []byte) error
}

type Installation

type Installation struct {
	ID      int64
	Owner   string
	OwnerID int64
}

Installation is a minimal representation of a GitHub app installation.

type InstallationNotFound

type InstallationNotFound string

InstallationNotFound is returned when no installation exists for a specific owner or repository.

func (InstallationNotFound) Error

func (err InstallationNotFound) Error() string

type InstallationSource

type InstallationSource interface {
	GetInstallation() *github.Installation
}

InstallationSource is implemented by GitHub webhook event payload types.

type InstallationsService

type InstallationsService interface {
	// ListAll returns all installations for this app.
	ListAll(ctx context.Context) ([]Installation, error)

	// GetByOwner returns the installation for an owner (user or organization).
	// It returns an InstallationNotFound error if no installation exists for
	// the owner.
	GetByOwner(ctx context.Context, owner string) (Installation, error)
}

InstallationsService retrieves installation information for a given app. Implementations may chose how to retrieve, store, or cache these values.

This service is useful for background processes that do not respond directly to webhooks, since webhooks provide installation IDs in their payloads.

func NewInstallationsService

func NewInstallationsService(appClient *github.Client) InstallationsService

NewInstallationsService returns an InstallationsService that always queries GitHub. It should be created with a client that authenticates as the target application.

Jump to

Keyboard shortcuts

? : This menu
/ : Search site
f or F : Jump to
y or Y : Canonical URL