Bump all dependencies except dev-tunnels
This commit is contained in:
parent
2b84a3d698
commit
96956da8de
501 changed files with 35317 additions and 31761 deletions
160
third-party/github.com/letsencrypt/boulder/unpause/unpause.go
vendored
Normal file
160
third-party/github.com/letsencrypt/boulder/unpause/unpause.go
vendored
Normal file
|
|
@ -0,0 +1,160 @@
|
|||
package unpause
|
||||
|
||||
import (
|
||||
"errors"
|
||||
"fmt"
|
||||
"strconv"
|
||||
"strings"
|
||||
"time"
|
||||
|
||||
"github.com/go-jose/go-jose/v4"
|
||||
"github.com/go-jose/go-jose/v4/jwt"
|
||||
"github.com/jmhodges/clock"
|
||||
|
||||
"github.com/letsencrypt/boulder/cmd"
|
||||
)
|
||||
|
||||
const (
|
||||
// API
|
||||
|
||||
// Changing this value will invalidate all existing JWTs.
|
||||
APIVersion = "v1"
|
||||
APIPrefix = "/sfe/" + APIVersion
|
||||
GetForm = APIPrefix + "/unpause"
|
||||
|
||||
// BatchSize is the maximum number of identifiers that the SA will unpause
|
||||
// in a single batch.
|
||||
BatchSize = 10000
|
||||
|
||||
// MaxBatches is the maximum number of batches that the SA will unpause in a
|
||||
// single request.
|
||||
MaxBatches = 5
|
||||
|
||||
// RequestLimit is the maximum number of identifiers that the SA will
|
||||
// unpause in a single request. This is used by the SFE to infer whether
|
||||
// there are more identifiers to unpause.
|
||||
RequestLimit = BatchSize * MaxBatches
|
||||
|
||||
// JWT
|
||||
defaultIssuer = "WFE"
|
||||
defaultAudience = "SFE Unpause"
|
||||
)
|
||||
|
||||
// JWTSigner is a type alias for jose.Signer. To create a JWTSigner instance,
|
||||
// use the NewJWTSigner function provided in this package.
|
||||
type JWTSigner = jose.Signer
|
||||
|
||||
// NewJWTSigner loads the HMAC key from the provided configuration and returns a
|
||||
// new JWT signer.
|
||||
func NewJWTSigner(hmacKey cmd.HMACKeyConfig) (JWTSigner, error) {
|
||||
key, err := hmacKey.Load()
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
return jose.NewSigner(jose.SigningKey{Algorithm: jose.HS256, Key: key}, nil)
|
||||
}
|
||||
|
||||
// JWTClaims represents the claims of a JWT token issued by the WFE for
|
||||
// redemption by the SFE. The following claims required for unpausing:
|
||||
// - Subject: the account ID of the Subscriber
|
||||
// - V: the API version this JWT was created for
|
||||
// - I: a set of ACME identifier values. Identifier types are omitted
|
||||
// since DNS and IP string representations do not overlap.
|
||||
type JWTClaims struct {
|
||||
jwt.Claims
|
||||
|
||||
// V is the API version this JWT was created for.
|
||||
V string `json:"version"`
|
||||
|
||||
// I is set of comma separated ACME identifiers.
|
||||
I string `json:"identifiers"`
|
||||
}
|
||||
|
||||
// GenerateJWT generates a serialized unpause JWT with the provided claims.
|
||||
func GenerateJWT(signer JWTSigner, regID int64, idents []string, lifetime time.Duration, clk clock.Clock) (string, error) {
|
||||
claims := JWTClaims{
|
||||
Claims: jwt.Claims{
|
||||
Issuer: defaultIssuer,
|
||||
Subject: fmt.Sprintf("%d", regID),
|
||||
Audience: jwt.Audience{defaultAudience},
|
||||
// IssuedAt is necessary for metrics.
|
||||
IssuedAt: jwt.NewNumericDate(clk.Now()),
|
||||
Expiry: jwt.NewNumericDate(clk.Now().Add(lifetime)),
|
||||
},
|
||||
V: APIVersion,
|
||||
I: strings.Join(idents, ","),
|
||||
}
|
||||
|
||||
serialized, err := jwt.Signed(signer).Claims(&claims).Serialize()
|
||||
if err != nil {
|
||||
return "", fmt.Errorf("serializing JWT: %s", err)
|
||||
}
|
||||
|
||||
return serialized, nil
|
||||
}
|
||||
|
||||
// ErrMalformedJWT is returned when the JWT is malformed.
|
||||
var ErrMalformedJWT = errors.New("malformed JWT")
|
||||
|
||||
// RedeemJWT deserializes an unpause JWT and returns the validated claims. The
|
||||
// key is used to validate the signature of the JWT. The version is the expected
|
||||
// API version of the JWT. This function validates that the JWT is:
|
||||
// - well-formed,
|
||||
// - valid for the current time (+/- 1 minute leeway),
|
||||
// - issued by the WFE,
|
||||
// - intended for the SFE,
|
||||
// - contains an Account ID as the 'Subject',
|
||||
// - subject can be parsed as a 64-bit integer,
|
||||
// - contains a set of paused identifiers as 'Identifiers', and
|
||||
// - contains the API the expected version as 'Version'.
|
||||
//
|
||||
// If the JWT is malformed or invalid in any way, ErrMalformedJWT is returned.
|
||||
func RedeemJWT(token string, key []byte, version string, clk clock.Clock) (JWTClaims, error) {
|
||||
parsedToken, err := jwt.ParseSigned(token, []jose.SignatureAlgorithm{jose.HS256})
|
||||
if err != nil {
|
||||
return JWTClaims{}, errors.Join(ErrMalformedJWT, err)
|
||||
}
|
||||
|
||||
claims := JWTClaims{}
|
||||
err = parsedToken.Claims(key, &claims)
|
||||
if err != nil {
|
||||
return JWTClaims{}, errors.Join(ErrMalformedJWT, err)
|
||||
}
|
||||
|
||||
err = claims.Validate(jwt.Expected{
|
||||
Issuer: defaultIssuer,
|
||||
AnyAudience: jwt.Audience{defaultAudience},
|
||||
|
||||
// By default, the go-jose library validates the NotBefore and Expiry
|
||||
// fields with a default leeway of 1 minute.
|
||||
Time: clk.Now(),
|
||||
})
|
||||
if err != nil {
|
||||
return JWTClaims{}, fmt.Errorf("validating JWT: %w", err)
|
||||
}
|
||||
|
||||
if len(claims.Subject) == 0 {
|
||||
return JWTClaims{}, errors.New("no account ID specified in the JWT")
|
||||
}
|
||||
account, err := strconv.ParseInt(claims.Subject, 10, 64)
|
||||
if err != nil {
|
||||
return JWTClaims{}, errors.New("invalid account ID specified in the JWT")
|
||||
}
|
||||
if account == 0 {
|
||||
return JWTClaims{}, errors.New("no account ID specified in the JWT")
|
||||
}
|
||||
|
||||
if claims.V == "" {
|
||||
return JWTClaims{}, errors.New("no API version specified in the JWT")
|
||||
}
|
||||
|
||||
if claims.V != version {
|
||||
return JWTClaims{}, fmt.Errorf("unexpected API version in the JWT: %s", claims.V)
|
||||
}
|
||||
|
||||
if claims.I == "" {
|
||||
return JWTClaims{}, errors.New("no identifiers specified in the JWT")
|
||||
}
|
||||
|
||||
return claims, nil
|
||||
}
|
||||
Loading…
Add table
Add a link
Reference in a new issue