Documentation
¶
Overview ¶
Package browser implements AuthHub relying-party browser sessions using the reviewed OIDC libraries and durable PostgreSQL generation fences. It supplies identity proofs, never local user linking or application permissions.
Index ¶
- Variables
- func ReadClientSecret(path, clientID string) (string, error)
- func ReadProtected(path string, limit int64) ([]byte, error)
- func Schema() string
- func ValidateConfig(c Config) error
- func ValidateIssuerEndpoint(issuer, endpoint string) error
- type Binding
- type Client
- func (c *Client) Begin(w http.ResponseWriter, r *http.Request)
- func (c *Client) Callback(w http.ResponseWriter, r *http.Request)
- func (c *Client) Check(ctx context.Context, b Binding) (Proof, error)
- func (c *Client) Handler(render func(http.ResponseWriter, *http.Request, View)) http.Handler
- func (c *Client) Logout(w http.ResponseWriter, r *http.Request)
- func (c *Client) RevokeBinding(ctx context.Context, b Binding) error
- func (c *Client) Valid(ctx context.Context, p Proof) error
- func (c *Client) Verify(r *http.Request) (Proof, error)
- type Config
- type Identity
- type Option
- func WithCallback(value string) Option
- func WithCentralLogoutURL(value string) Option
- func WithClientID(value string) Option
- func WithClientSecret(value string) Option
- func WithFreshness(value time.Duration) Option
- func WithIngress(value *ingress.Policy) Option
- func WithIssuer(value string) Option
- func WithIssuerCAFile(value string) Option
- func WithOrigin(value string) Option
- func WithProjectID(value string) Option
- func WithRevocationEndpoint(value string) Option
- func WithStorageKey(value []byte) Option
- func WithStore(value *PostgresStore) Option
- type Options
- type PostgresStore
- type Proof
- type View
Constants ¶
This section is empty.
Variables ¶
var ErrDenied = errFenced
ErrDenied means this proof/session cannot authorize the current request. Expired, terminal and superseded generations require a new admission.
var ErrRevocationUnconfirmed = errors.New("local logout committed; central revocation unconfirmed")
ErrRevocationUnconfirmed means local terminal state committed, but central revocation could not be confirmed. Never replay refresh or resurrect a binding.
ErrUnavailable means the boundary could not confirm validity. Fail closed; do not mint or extend a host session. A later request may retry validity, but must never independently replay an OAuth exchange or claimed refresh.
Functions ¶
func ReadClientSecret ¶
ReadClientSecret reads the exact restart-bound maintenance candidate format.
func ReadProtected ¶
ReadProtected loads an explicitly supplied Linux protected file with the reviewed ownership, mode, size and no-symlink checks. It never prints contents.
func Schema ¶
func Schema() string
Schema returns the reviewed RP schema. Existing table names are retained for compatibility; isolate each application's rows using its PostgreSQL schema.
func ValidateConfig ¶
ValidateConfig checks exact origins and identity pins without network access.
func ValidateIssuerEndpoint ¶
ValidateIssuerEndpoint checks an explicit provider endpoint without network access. Validate application identity/origin settings with ValidateConfig too. For an absent optional central logout link, omit this check and its option.
Types ¶
type Binding ¶
type Binding struct {
Reference string `json:"reference"`
Generation int64 `json:"generation"`
LoginGeneration int64 `json:"loginGeneration"`
Deadline time.Time `json:"deadline"`
Issuer string `json:"issuer"`
Subject string `json:"subject"`
ProjectID string `json:"projectId"`
ClientID string `json:"clientId"`
CentralSessionID string `json:"centralSessionId"`
AuthTime int64 `json:"authTime"`
AbsoluteUntil time.Time `json:"absoluteUntil"`
}
Binding is persisted inside a protected host-owned external session after successful admission. Never accept it from browser form/query/header input. The host must preserve the original Deadline unchanged; it is not a TTL. LoginGeneration identifies a local login admission, preserved across refresh. Zero markers from legacy rows/bindings require a fresh sign-in.
type Client ¶
type Client struct {
// contains filtered or unexported fields
}
Client is safe for concurrent HTTP use. The caller owns the database lifetime.
func New ¶
New retains the original AuthHub-profile API and provider-relative logout routes for existing callers. New integrations should use NewWithOptions. New performs bounded OIDC discovery using the configured issuer trust roots.
func NewWithOptions ¶
NewWithOptions validates explicit identity, origin and protected inputs before discovery. It uses a supplied or discovered revocation endpoint, never a guessed provider route. No central logout link is exposed unless configured. Configuration is frozen at construction; only the caller-owned database and an immutable ingress policy are shared. Protocol and session fences are the same as New; this constructor does not imply general OIDC-provider support.
func (*Client) Begin ¶
func (c *Client) Begin(w http.ResponseWriter, r *http.Request)
Begin handles the exact POST /login form using the library CSRF/browser state.
func (*Client) Callback ¶
func (c *Client) Callback(w http.ResponseWriter, r *http.Request)
Callback handles the exact GET /callback. Success installs durable state and redirects; admit the local user on a subsequent Verify, never from query data.
func (*Client) Check ¶
Check validates a previously admitted host-owned binding after restart without network access or refresh. An edited deadline beyond the durable proof cap is rejected. The host must also match the returned issuer/subject to its explicit local user link and recheck its own ACL; this method grants no local roles.
func (*Client) Handler ¶
Handler serves GET /, POST /login, GET /callback and POST /logout. render owns the landing UI, explicit local user resolution and local permissions. Form POSTs must carry View.CSRF. Other application routes can call Verify directly.
func (*Client) Logout ¶
func (c *Client) Logout(w http.ResponseWriter, r *http.Request)
Logout handles the exact POST /logout. Local terminal generation commits before bounded central revocation. Failed confirmation is not a success acknowledgement; the host must still fail closed at its Check/Valid boundary. A stale login returns 409 and preserves the newer cookie. Local termination with unconfirmed remote revoke/decryption returns 503 and clears the cookie. Anonymous/pending logout redirects to /?logout=local-only. The response's X-AuthHub-Logout-Scope is binding-revoked, local-only, or unconfirmed; it never promises issuer-wide logout. Refresh descendants retain the original intent.
func (*Client) RevokeBinding ¶
RevokeBinding is intentional user logout, not session-replacement cleanup. It ends the current generation and refresh descendants of this same login. A subsequent login has a different LoginGeneration and cannot be revoked by this old binding, even when all central identity claims are unchanged. Expired freshness does not cancel logout intent. AbsoluteUntil is a pin. Unknown local commit returns ErrUnavailable; no automatic retry or remote revoke follows it. ErrRevocationUnconfirmed confirms local termination only. Caller must enforce logout request authentication and CSRF protection.
func (*Client) Valid ¶
Valid checks an external session's original proof against current durable state. It never refreshes, extends deadlines or resurrects a terminal session. Refresh generation changes require a newly admitted proof. Central revocation is bounded by the original signed freshness deadline, at most five minutes.
type Config ¶
type Config struct {
Issuer, ClientID, ProjectID, Origin, Callback string
Freshness time.Duration
IssuerCAFile string
Ingress *ingress.Policy
}
Config pins the authority, application origin, client and project. Callback is exactly Origin + /callback. Zero Freshness means the reviewed five-minute cap. Ingress must be nil for direct TLS or an explicitly constructed trusted edge.
type Identity ¶
type Identity struct {
Issuer string `json:"issuer"`
ClientID string `json:"client_id"`
Subject string `json:"subject"`
ProjectID string `json:"project_id"`
SessionID string `json:"sid"`
AuthTime int64 `json:"auth_time"`
IssuedAt time.Time `json:"issued_at"`
FreshUntil time.Time `json:"fresh_until"`
AbsoluteUntil time.Time `json:"absolute_until"`
Profile map[string]string `json:"profile,omitempty"`
Project map[string]string `json:"project,omitempty"`
}
Identity contains independently verified OIDC identity claims.
type Option ¶
type Option func(*options)
Option configures a new client. Use the typed With functions; duplicate options, including repeated identical values, and nil options are rejected.
func WithCallback ¶
WithCallback supplies the registered callback, exactly origin plus /callback.
func WithCentralLogoutURL ¶
WithCentralLogoutURL sets an optional browser sign-out landing URL. It must remain on the issuer origin and conveys no guarantee of issuer-wide logout.
func WithClientID ¶
WithClientID supplies the explicitly registered client identifier.
func WithClientSecret ¶
WithClientSecret supplies a protected client secret. It is never logged.
func WithFreshness ¶
WithFreshness sets a cap no greater than five minutes. Zero retains that cap.
func WithIngress ¶
WithIngress selects an immutable verified edge policy. Nil means direct TLS.
func WithIssuer ¶
WithIssuer supplies the exact canonical HTTPS issuer origin.
func WithIssuerCAFile ¶
WithIssuerCAFile selects bounded public PEM trust roots read at construction.
func WithOrigin ¶
WithOrigin supplies the exact application HTTPS origin, distinct from issuer.
func WithProjectID ¶
WithProjectID supplies the nonzero canonical project UUID to pin in tokens.
func WithRevocationEndpoint ¶
WithRevocationEndpoint explicitly pins the revocation URL and takes precedence over discovery. Without this option, valid revocation discovery is required.
func WithStorageKey ¶
WithStorageKey snapshots exactly 32 raw key bytes when this option is created. Reusing the option gives each construction a separate copy.
func WithStore ¶
func WithStore(value *PostgresStore) Option
WithStore supplies a store constructed by NewPostgresStore. The caller still owns its database; constructing a client does not transfer pool ownership.
type Options ¶
type Options struct {
Store *PostgresStore
ClientSecret string
StorageKey []byte
}
Options supplies protected inputs. New does not log, generate or persist keys. Store is mandatory: there is no in-memory fallback. No customizable token transport or clock is exposed in the consumer API.
type PostgresStore ¶
type PostgresStore struct {
// contains filtered or unexported fields
}
PostgresStore owns no connection pool. The caller owns db and must apply Schema in an application-owned schema before construction. There are no authority/internal imports and no automatic migrations.
func NewPostgresStore ¶
NewPostgresStore fails closed on absent or partial durable schema.
type Proof ¶
type Proof struct {
// contains filtered or unexported fields
}
Proof is an immutable snapshot minted by Client.Verify or Handler. Copying a proof preserves its original deadline. Call Valid at each external session admission/validity boundary; do not turn Deadline into a rolling local TTL. The reference is opaque app-owned durable state, not the central OIDC sid.
func (Proof) Binding ¶
Binding returns the durable reference, exact generation and immutable deadline.
func (Proof) Deadline ¶
Deadline returns the fixed minimum of verified freshness and absolute lifetime.
func (Proof) Generation ¶
Generation returns the exact durable generation checked for this proof.
func (Proof) Identity ¶
Identity returns a copy of verified claims. Metadata is display-only, never ACL.
func (Proof) SessionReference ¶
SessionReference returns the nonsecret durable browser-session reference.
type View ¶
type View struct {
CSRF string
Proof *Proof
// CentralLogout is empty unless an explicit central sign-out URL was set.
// Renderers must omit the link when it is empty. Legacy New retains its route.
CentralLogout string
}
View is supplied to application-owned rendering after browser/session checks. A nil Proof conveys no authenticated identity, including outage recovery pages.