first steps

pull/599/head
max furman 3 years ago
parent 2f60f20b0b
commit af3cf7dae9

@ -31,7 +31,7 @@ import (
// Authority implements the Certificate Authority internal interface. // Authority implements the Certificate Authority internal interface.
type Authority struct { type Authority struct {
config *config.Config config *config.Config
mgmtDB *mgmt.DB mgmtDB mgmt.DB
keyManager kms.KeyManager keyManager kms.KeyManager
provisioners *provisioner.Collection provisioners *provisioner.Collection
db db.AuthDB db db.AuthDB
@ -146,20 +146,26 @@ func (a *Authority) init() error {
// Pull AuthConfig from DB. // Pull AuthConfig from DB.
if true { if true {
if len(a.config.AuthConfig.AuthorityID)_== 0 { // Check if AuthConfig already exists
mgmtDB, err := authMgmtNosql.New(a.db.(nosql.DB), mgmt.DefaultAuthorityID) a.mgmtDB, err = authMgmtNosql.New(a.db.(nosql.DB), mgmt.DefaultAuthorityID)
if err != nil { if err != nil {
return err return err
} }
mgmtAuthConfig, err := mgmt.CreateAuthority(context.Background, mgmtDB, WithDefaultAuthorityID) mgmtAuthConfig, err := a.mgmtDB.GetAuthConfig(context.Background(), mgmt.DefaultAuthorityID)
if err != nil { if err != nil {
return err if k, ok := err.(*mgmt.Error); ok && k.IsType(mgmt.ErrorNotFoundType) {
} mgmtAuthConfig, err = mgmt.CreateAuthority(context.Background(), a.mgmtDB, mgmt.WithDefaultAuthorityID)
a.config.AuthConfig, err := mgmtAuthConfig.ToCertificates() if err != nil {
if err != nil { return mgmt.WrapErrorISE(err, "error creating authConfig")
return err }
} else {
return mgmt.WrapErrorISE(err, "error getting authConfig from db")
} }
} }
a.config.AuthorityConfig, err = mgmtAuthConfig.ToCertificates()
if err != nil {
return err
}
} }
// Initialize key manager if it has not been set in the options. // Initialize key manager if it has not been set in the options.
@ -394,6 +400,11 @@ func (a *Authority) GetDatabase() db.AuthDB {
return a.db return a.db
} }
// GetMgmtDatabase returns the mgmt database, if one exists.
func (a *Authority) GetMgmtDatabase() mgmt.DB {
return a.mgmtDB
}
// Shutdown safely shuts down any clients, databases, etc. held by the Authority. // Shutdown safely shuts down any clients, databases, etc. held by the Authority.
func (a *Authority) Shutdown() error { func (a *Authority) Shutdown() error {
if err := a.keyManager.Close(); err != nil { if err := a.keyManager.Close(); err != nil {

@ -32,9 +32,14 @@ var (
MaxVersion: 1.2, MaxVersion: 1.2,
Renegotiation: false, Renegotiation: false,
} }
DefaultBackdate = time.Minute // DefaultBackdate length of time to backdate certificates to avoid
// clock skew validation issues.
DefaultBackdate = time.Minute
// DefaultDisableRenewal disables renewals per provisioner.
DefaultDisableRenewal = false DefaultDisableRenewal = false
DefaultEnableSSHCA = false // DefaultEnableSSHCA enable SSH CA features per provisioner or globally
// for all provisioners.
DefaultEnableSSHCA = false
// GlobalProvisionerClaims default claims for the Authority. Can be overriden // GlobalProvisionerClaims default claims for the Authority. Can be overriden
// by provisioner specific claims. // by provisioner specific claims.
GlobalProvisionerClaims = provisioner.Claims{ GlobalProvisionerClaims = provisioner.Claims{
@ -153,7 +158,7 @@ func LoadConfiguration(filename string) (*Config, error) {
return nil, errors.Wrapf(err, "error parsing %s", filename) return nil, errors.Wrapf(err, "error parsing %s", filename)
} }
c.init() c.Init()
return &c, nil return &c, nil
} }

@ -58,55 +58,59 @@ func (h *Handler) GetAdmins(w http.ResponseWriter, r *http.Request) {
// CreateAdmin creates a new admin. // CreateAdmin creates a new admin.
func (h *Handler) CreateAdmin(w http.ResponseWriter, r *http.Request) { func (h *Handler) CreateAdmin(w http.ResponseWriter, r *http.Request) {
ctx := r.Context() /*
ctx := r.Context()
var body CreateAdminRequest
if err := ReadJSON(r.Body, &body); err != nil { var body CreateAdminRequest
api.WriteError(w, err) if err := ReadJSON(r.Body, &body); err != nil {
return api.WriteError(w, err)
} return
if err := body.Validate(); err != nil { }
api.WriteError(w, err) if err := body.Validate(); err != nil {
} api.WriteError(w, err)
}
adm := &config.Admin{
Name: body.Name, adm := &config.Admin{
Provisioner: body.Provisioner, Name: body.Name,
IsSuperAdmin: body.IsSuperAdmin, Provisioner: body.Provisioner,
} IsSuperAdmin: body.IsSuperAdmin,
if err := h.db.CreateAdmin(ctx, adm); err != nil { }
api.WriteError(w, err) if err := h.db.CreateAdmin(ctx, adm); err != nil {
return api.WriteError(w, err)
} return
api.JSONStatus(w, adm, http.StatusCreated) }
api.JSONStatus(w, adm, http.StatusCreated)
*/
} }
// UpdateAdmin updates an existing admin. // UpdateAdmin updates an existing admin.
func (h *Handler) UpdateAdmin(w http.ResponseWriter, r *http.Request) { func (h *Handler) UpdateAdmin(w http.ResponseWriter, r *http.Request) {
ctx := r.Context() /*
id := chi.URLParam(r, "id") ctx := r.Context()
id := chi.URLParam(r, "id")
var body UpdateAdminRequest
if err := ReadJSON(r.Body, &body); err != nil { var body UpdateAdminRequest
api.WriteError(w, err) if err := ReadJSON(r.Body, &body); err != nil {
return api.WriteError(w, err)
} return
if err := body.Validate(); err != nil { }
api.WriteError(w, err) if err := body.Validate(); err != nil {
return api.WriteError(w, err)
} return
if adm, err := h.db.GetAdmin(ctx, id); err != nil { }
api.WriteError(w, err) if adm, err := h.db.GetAdmin(ctx, id); err != nil {
return api.WriteError(w, err)
} return
}
adm.Name = body.Name
adm.Provisioner = body.Provisioner adm.Name = body.Name
adm.IsSuperAdmin = body.IsSuperAdmin adm.Provisioner = body.Provisioner
adm.IsSuperAdmin = body.IsSuperAdmin
if err := h.db.UpdateAdmin(ctx, adm); err != nil {
api.WriteError(w, err) if err := h.db.UpdateAdmin(ctx, adm); err != nil {
return api.WriteError(w, err)
} return
api.JSON(w, adm) }
api.JSON(w, adm)
*/
} }

@ -5,16 +5,15 @@ import (
"github.com/go-chi/chi" "github.com/go-chi/chi"
"github.com/smallstep/certificates/api" "github.com/smallstep/certificates/api"
"github.com/smallstep/certificates/authority"
"github.com/smallstep/certificates/authority/config" "github.com/smallstep/certificates/authority/config"
"github.com/smallstep/certificates/authority/mgmt"
) )
// CreateAuthConfigRequest represents the body for a CreateAuthConfig request. // CreateAuthConfigRequest represents the body for a CreateAuthConfig request.
type CreateAuthConfigRequest struct { type CreateAuthConfigRequest struct {
ASN1DN *authority.ASN1DN `json:"asn1dn,omitempty"` ASN1DN *config.ASN1DN `json:"asn1dn,omitempty"`
Claims *config.Claims `json:"claims,omitempty"` Claims *mgmt.Claims `json:"claims,omitempty"`
DisableIssuedAtCheck bool `json:"disableIssuedAtCheck,omitempty"` Backdate string `json:"backdate,omitempty"`
Backdate string `json:"backdate,omitempty"`
} }
// Validate validates a CreateAuthConfig request body. // Validate validates a CreateAuthConfig request body.
@ -24,10 +23,9 @@ func (car *CreateAuthConfigRequest) Validate() error {
// UpdateAuthConfigRequest represents the body for a UpdateAuthConfig request. // UpdateAuthConfigRequest represents the body for a UpdateAuthConfig request.
type UpdateAuthConfigRequest struct { type UpdateAuthConfigRequest struct {
ASN1DN *authority.ASN1DN `json:"asn1dn"` ASN1DN *config.ASN1DN `json:"asn1dn"`
Claims *config.Claims `json:"claims"` Claims *mgmt.Claims `json:"claims"`
DisableIssuedAtCheck bool `json:"disableIssuedAtCheck,omitempty"` Backdate string `json:"backdate,omitempty"`
Backdate string `json:"backdate,omitempty"`
} }
// Validate validates a new-admin request body. // Validate validates a new-admin request body.
@ -53,7 +51,7 @@ func (h *Handler) CreateAuthConfig(w http.ResponseWriter, r *http.Request) {
ctx := r.Context() ctx := r.Context()
var body CreateAuthConfigRequest var body CreateAuthConfigRequest
if err := ReadJSON(r.Body, &body); err != nil { if err := api.ReadJSON(r.Body, &body); err != nil {
api.WriteError(w, err) api.WriteError(w, err)
return return
} }
@ -61,10 +59,9 @@ func (h *Handler) CreateAuthConfig(w http.ResponseWriter, r *http.Request) {
api.WriteError(w, err) api.WriteError(w, err)
} }
ac := config.AuthConfig{ ac := &mgmt.AuthConfig{
Status: config.StatusActive, Status: mgmt.StatusActive,
DisableIssuedAtCheck: body.DisableIssuedAtCheck, Backdate: "1m",
Backdate: "1m",
} }
if body.ASN1DN != nil { if body.ASN1DN != nil {
ac.ASN1DN = body.ASN1DN ac.ASN1DN = body.ASN1DN
@ -84,38 +81,40 @@ func (h *Handler) CreateAuthConfig(w http.ResponseWriter, r *http.Request) {
// UpdateAuthConfig updates an existing AuthConfig. // UpdateAuthConfig updates an existing AuthConfig.
func (h *Handler) UpdateAuthConfig(w http.ResponseWriter, r *http.Request) { func (h *Handler) UpdateAuthConfig(w http.ResponseWriter, r *http.Request) {
ctx := r.Context() /*
id := chi.URLParam(r, "id") ctx := r.Context()
id := chi.URLParam(r, "id")
var body UpdateAuthConfigRequest var body UpdateAuthConfigRequest
if err := ReadJSON(r.Body, &body); err != nil { if err := api.ReadJSON(r.Body, &body); err != nil {
api.WriteError(w, err) api.WriteError(w, err)
return return
} }
if err := body.Validate(); err != nil { if err := body.Validate(); err != nil {
api.WriteError(w, err) api.WriteError(w, err)
return return
} }
if ac, err := h.db.GetAuthConfig(ctx, id); err != nil { ac, err := h.db.GetAuthConfig(ctx, id)
api.WriteError(w, err) if err != nil {
return api.WriteError(w, err)
} return
}
ac.DisableIssuedAtCheck = body.DisableIssuedAtCheck ac.Status = body.Status
ac.Status = body.Status if body.ASN1DN != nil {
if body.ASN1DN != nil { ac.ASN1DN = body.ASN1DN
ac.ASN1DN = body.ASN1DN }
} if body.Claims != nil {
if body.Claims != nil { ac.Claims = body.Claims
ac.Claims = body.Claims }
} if body.Backdate != "" {
if body.Backdate != "" { ac.Backdate = body.Backdate
ac.Backdate = body.Backdate }
}
if err := h.db.UpdateAuthConfig(ctx, ac); err != nil { if err := h.db.UpdateAuthConfig(ctx, ac); err != nil {
api.WriteError(w, err) api.WriteError(w, err)
return return
} }
api.JSON(w, ac) api.JSON(w, ac)
*/
} }

@ -4,7 +4,7 @@ import (
"time" "time"
"github.com/smallstep/certificates/api" "github.com/smallstep/certificates/api"
"github.com/smallstep/certificates/authority/config" "github.com/smallstep/certificates/authority/mgmt"
) )
// Clock that returns time in UTC rounded to seconds. // Clock that returns time in UTC rounded to seconds.
@ -19,14 +19,12 @@ var clock Clock
// Handler is the ACME API request handler. // Handler is the ACME API request handler.
type Handler struct { type Handler struct {
db config.DB db mgmt.DB
} }
// NewHandler returns a new Authority Config Handler. // NewHandler returns a new Authority Config Handler.
func NewHandler(db config.DB) api.RouterHandler { func NewHandler(db mgmt.DB) api.RouterHandler {
return &Handler{ return &Handler{db}
db: ops.DB,
}
} }
// Route traffic and implement the Router interface. // Route traffic and implement the Router interface.

@ -5,17 +5,17 @@ import (
"github.com/go-chi/chi" "github.com/go-chi/chi"
"github.com/smallstep/certificates/api" "github.com/smallstep/certificates/api"
"github.com/smallstep/certificates/authority/config" "github.com/smallstep/certificates/authority/mgmt"
) )
// CreateProvisionerRequest represents the body for a CreateProvisioner request. // CreateProvisionerRequest represents the body for a CreateProvisioner request.
type CreateProvisionerRequest struct { type CreateProvisionerRequest struct {
Type string `json:"type"` Type string `json:"type"`
Name string `json:"name"` Name string `json:"name"`
Claims *config.Claims `json:"claims"` Claims *mgmt.Claims `json:"claims"`
Details interface{} `json:"details"` Details interface{} `json:"details"`
X509Template string `json:"x509Template"` X509Template string `json:"x509Template"`
SSHTemplate string `json:"sshTemplate"` SSHTemplate string `json:"sshTemplate"`
} }
// Validate validates a new-provisioner request body. // Validate validates a new-provisioner request body.
@ -25,10 +25,10 @@ func (car *CreateProvisionerRequest) Validate() error {
// UpdateProvisionerRequest represents the body for a UpdateProvisioner request. // UpdateProvisionerRequest represents the body for a UpdateProvisioner request.
type UpdateProvisionerRequest struct { type UpdateProvisionerRequest struct {
Claims *config.Claims `json:"claims"` Claims *mgmt.Claims `json:"claims"`
Details interface{} `json:"details"` Details interface{} `json:"details"`
X509Template string `json:"x509Template"` X509Template string `json:"x509Template"`
SSHTemplate string `json:"sshTemplate"` SSHTemplate string `json:"sshTemplate"`
} }
// Validate validates a new-provisioner request body. // Validate validates a new-provisioner request body.
@ -66,7 +66,7 @@ func (h *Handler) CreateProvisioner(w http.ResponseWriter, r *http.Request) {
ctx := r.Context() ctx := r.Context()
var body CreateProvisionerRequest var body CreateProvisionerRequest
if err := ReadJSON(r.Body, &body); err != nil { if err := api.ReadJSON(r.Body, &body); err != nil {
api.WriteError(w, err) api.WriteError(w, err)
return return
} }
@ -74,7 +74,7 @@ func (h *Handler) CreateProvisioner(w http.ResponseWriter, r *http.Request) {
api.WriteError(w, err) api.WriteError(w, err)
} }
prov := &config.Provisioner{ prov := &mgmt.Provisioner{
Type: body.Type, Type: body.Type,
Name: body.Name, Name: body.Name,
Claims: body.Claims, Claims: body.Claims,
@ -91,32 +91,34 @@ func (h *Handler) CreateProvisioner(w http.ResponseWriter, r *http.Request) {
// UpdateProvisioner updates an existing prov. // UpdateProvisioner updates an existing prov.
func (h *Handler) UpdateProvisioner(w http.ResponseWriter, r *http.Request) { func (h *Handler) UpdateProvisioner(w http.ResponseWriter, r *http.Request) {
ctx := r.Context() /*
id := chi.URLParam(r, "id") ctx := r.Context()
id := chi.URLParam(r, "id")
var body UpdateProvisionerRequest
if err := ReadJSON(r.Body, &body); err != nil { var body UpdateProvisionerRequest
api.WriteError(w, err) if err := ReadJSON(r.Body, &body); err != nil {
return api.WriteError(w, err)
} return
if err := body.Validate(); err != nil { }
api.WriteError(w, err) if err := body.Validate(); err != nil {
return api.WriteError(w, err)
} return
if prov, err := h.db.GetProvisioner(ctx, id); err != nil { }
api.WriteError(w, err) if prov, err := h.db.GetProvisioner(ctx, id); err != nil {
return api.WriteError(w, err)
} return
}
prov.Claims = body.Claims
prov.Details = body.Provisioner prov.Claims = body.Claims
prov.X509Template = body.X509Template prov.Details = body.Provisioner
prov.SSHTemplate = body.SSHTemplate prov.X509Template = body.X509Template
prov.Status = body.Status prov.SSHTemplate = body.SSHTemplate
prov.Status = body.Status
if err := h.db.UpdateProvisioner(ctx, prov); err != nil {
api.WriteError(w, err) if err := h.db.UpdateProvisioner(ctx, prov); err != nil {
return api.WriteError(w, err)
} return
api.JSON(w, prov) }
api.JSON(w, prov)
*/
} }

@ -19,28 +19,8 @@ type AuthConfig struct {
func NewDefaultAuthConfig() *AuthConfig { func NewDefaultAuthConfig() *AuthConfig {
return &AuthConfig{ return &AuthConfig{
Claims: &Claims{ Claims: NewDefaultClaims(),
X509: &X509Claims{ ASN1DN: &config.ASN1DN{},
Durations: &Durations{
Min: config.GlobalProvisionerClaims.MinTLSDur.String(),
Max: config.GlobalProvisionerClaims.MaxTLSDur.String(),
Default: config.GlobalProvisionerClaims.DefaultTLSDur.String(),
},
},
SSH: &SSHClaims{
UserDurations: &Durations{
Min: config.GlobalProvisionerClaims.MinUserSSHDur.String(),
Max: config.GlobalProvisionerClaims.MaxUserSSHDur.String(),
Default: config.GlobalProvisionerClaims.DefaultUserSSHDur.String(),
},
HostDurations: &Durations{
Min: config.GlobalProvisionerClaims.MinHostSSHDur.String(),
Max: config.GlobalProvisionerClaims.MaxHostSSHDur.String(),
Default: config.GlobalProvisionerClaims.DefaultHostSSHDur.String(),
},
},
DisableRenewal: config.DefaultDisableRenewal,
},
Backdate: config.DefaultBackdate.String(), Backdate: config.DefaultBackdate.String(),
Status: StatusActive, Status: StatusActive,
} }

@ -4,6 +4,7 @@ import (
"context" "context"
"github.com/pkg/errors" "github.com/pkg/errors"
"github.com/smallstep/certificates/authority/config"
) )
const ( const (
@ -50,6 +51,31 @@ type Durations struct {
Default string `json:"default"` Default string `json:"default"`
} }
func NewDefaultClaims() *Claims {
return &Claims{
X509: &X509Claims{
Durations: &Durations{
Min: config.GlobalProvisionerClaims.MinTLSDur.String(),
Max: config.GlobalProvisionerClaims.MaxTLSDur.String(),
Default: config.GlobalProvisionerClaims.DefaultTLSDur.String(),
},
},
SSH: &SSHClaims{
UserDurations: &Durations{
Min: config.GlobalProvisionerClaims.MinUserSSHDur.String(),
Max: config.GlobalProvisionerClaims.MaxUserSSHDur.String(),
Default: config.GlobalProvisionerClaims.DefaultUserSSHDur.String(),
},
HostDurations: &Durations{
Min: config.GlobalProvisionerClaims.MinHostSSHDur.String(),
Max: config.GlobalProvisionerClaims.MaxHostSSHDur.String(),
Default: config.GlobalProvisionerClaims.DefaultHostSSHDur.String(),
},
},
DisableRenewal: config.DefaultDisableRenewal,
}
}
type AuthorityOption func(*AuthConfig) error type AuthorityOption func(*AuthConfig) error
func WithDefaultAuthorityID(ac *AuthConfig) error { func WithDefaultAuthorityID(ac *AuthConfig) error {

@ -18,7 +18,7 @@ type DB interface {
UpdateProvisioner(ctx context.Context, prov *Provisioner) error UpdateProvisioner(ctx context.Context, prov *Provisioner) error
CreateAdmin(ctx context.Context, admin *Admin) error CreateAdmin(ctx context.Context, admin *Admin) error
GetAdmin(ctx context.Context, id string) error GetAdmin(ctx context.Context, id string) (*Admin, error)
GetAdmins(ctx context.Context) ([]*Admin, error) GetAdmins(ctx context.Context) ([]*Admin, error)
UpdateAdmin(ctx context.Context, admin *Admin) error UpdateAdmin(ctx context.Context, admin *Admin) error
@ -116,7 +116,7 @@ func (m *MockDB) GetAdmins(ctx context.Context) ([]*Admin, error) {
// UpdateAdmin mock // UpdateAdmin mock
func (m *MockDB) UpdateAdmin(ctx context.Context, adm *Admin) error { func (m *MockDB) UpdateAdmin(ctx context.Context, adm *Admin) error {
if m.UpdateAdmin != nil { if m.MockUpdateAdmin != nil {
return m.MockUpdateAdmin(ctx, adm) return m.MockUpdateAdmin(ctx, adm)
} }
return m.MockError return m.MockError
@ -142,7 +142,7 @@ func (m *MockDB) GetAuthConfig(ctx context.Context, id string) (*AuthConfig, err
// UpdateAuthConfig mock // UpdateAuthConfig mock
func (m *MockDB) UpdateAuthConfig(ctx context.Context, adm *AuthConfig) error { func (m *MockDB) UpdateAuthConfig(ctx context.Context, adm *AuthConfig) error {
if m.UpdateAuthConfig != nil { if m.MockUpdateAuthConfig != nil {
return m.MockUpdateAuthConfig(ctx, adm) return m.MockUpdateAuthConfig(ctx, adm)
} }
return m.MockError return m.MockError

@ -6,7 +6,6 @@ import (
"time" "time"
"github.com/pkg/errors" "github.com/pkg/errors"
"github.com/smallstep/certificates/acme"
"github.com/smallstep/certificates/authority/mgmt" "github.com/smallstep/certificates/authority/mgmt"
"github.com/smallstep/nosql" "github.com/smallstep/nosql"
) )
@ -109,7 +108,7 @@ func unmarshalAdmin(data []byte, id string) (*mgmt.Admin, error) {
// GetAdmins retrieves and unmarshals all active (not deleted) admins // GetAdmins retrieves and unmarshals all active (not deleted) admins
// from the database. // from the database.
// TODO should we be paginating? // TODO should we be paginating?
func (db *DB) GetAdmins(ctx context.Context, az *acme.Authorization) ([]*mgmt.Admin, error) { func (db *DB) GetAdmins(ctx context.Context) ([]*mgmt.Admin, error) {
dbEntries, err := db.db.List(authorityAdminsTable) dbEntries, err := db.db.List(authorityAdminsTable)
if err != nil { if err != nil {
return nil, errors.Wrap(err, "error loading admins") return nil, errors.Wrap(err, "error loading admins")

@ -12,13 +12,12 @@ import (
) )
type dbAuthConfig struct { type dbAuthConfig struct {
ID string `json:"id"` ID string `json:"id"`
ASN1DN *config.ASN1DN `json:"asn1dn"` ASN1DN *config.ASN1DN `json:"asn1dn"`
Claims *mgmt.Claims `json:"claims"` Claims *mgmt.Claims `json:"claims"`
DisableIssuedAtCheck bool `json:"disableIssuedAtCheck,omitempty"` Backdate string `json:"backdate,omitempty"`
Backdate string `json:"backdate,omitempty"` CreatedAt time.Time `json:"createdAt"`
CreatedAt time.Time `json:"createdAt"` DeletedAt time.Time `json:"deletedAt"`
DeletedAt time.Time `json:"deletedAt"`
} }
func (dbp *dbAuthConfig) clone() *dbAuthConfig { func (dbp *dbAuthConfig) clone() *dbAuthConfig {
@ -63,30 +62,30 @@ func (db *DB) GetAuthConfig(ctx context.Context, id string) (*mgmt.AuthConfig, e
} }
return &mgmt.AuthConfig{ return &mgmt.AuthConfig{
ID: dba.ID, ID: dba.ID,
Provisioners: provs, Provisioners: provs,
ASN1DN: dba.ASN1DN, ASN1DN: dba.ASN1DN,
Backdate: dba.Backdate, Backdate: dba.Backdate,
Claims: dba.Claims, Claims: dba.Claims,
DisableIssuedAtCheck: dba.DisableIssuedAtCheck,
}, nil }, nil
} }
// CreateAuthConfig stores a new provisioner to the database. // CreateAuthConfig stores a new provisioner to the database.
func (db *DB) CreateAuthConfig(ctx context.Context, ac *mgmt.AuthConfig) error { func (db *DB) CreateAuthConfig(ctx context.Context, ac *mgmt.AuthConfig) error {
var err error var err error
ac.ID, err = randID() if ac.ID == "" {
if err != nil { ac.ID, err = randID()
return errors.Wrap(err, "error generating random id for provisioner") if err != nil {
return errors.Wrap(err, "error generating random id for provisioner")
}
} }
dba := &dbAuthConfig{ dba := &dbAuthConfig{
ID: ac.ID, ID: ac.ID,
ASN1DN: ac.ASN1DN, ASN1DN: ac.ASN1DN,
Claims: ac.Claims, Claims: ac.Claims,
DisableIssuedAtCheck: ac.DisableIssuedAtCheck, Backdate: ac.Backdate,
Backdate: ac.Backdate, CreatedAt: clock.Now(),
CreatedAt: clock.Now(),
} }
return db.save(ctx, dba.ID, dba, nil, "authConfig", authorityConfigsTable) return db.save(ctx, dba.ID, dba, nil, "authConfig", authorityConfigsTable)
@ -106,7 +105,6 @@ func (db *DB) UpdateAuthConfig(ctx context.Context, ac *mgmt.AuthConfig) error {
nu.DeletedAt = clock.Now() nu.DeletedAt = clock.Now()
} }
nu.Claims = ac.Claims nu.Claims = ac.Claims
nu.DisableIssuedAtCheck = ac.DisableIssuedAtCheck
nu.Backdate = ac.Backdate nu.Backdate = ac.Backdate
return db.save(ctx, old.ID, nu, old, "authConfig", authorityProvisionersTable) return db.save(ctx, old.ID, nu, old, "authConfig", authorityProvisionersTable)

@ -87,6 +87,11 @@ type Error struct {
Status int `json:"-"` Status int `json:"-"`
} }
// IsType returns true if the error type matches the input type.
func (e *Error) IsType(pt ProblemType) bool {
return pt.String() == e.Type
}
// NewError creates a new Error type. // NewError creates a new Error type.
func NewError(pt ProblemType, msg string, args ...interface{}) *Error { func NewError(pt ProblemType, msg string, args ...interface{}) *Error {
return newError(pt, errors.Errorf(msg, args...)) return newError(pt, errors.Errorf(msg, args...))

@ -20,6 +20,16 @@ type ProvisionerCtx struct {
Password string Password string
} }
func NewProvisionerCtx(opts ...ProvisionerOption) *ProvisionerCtx {
pc := &ProvisionerCtx{
Claims: NewDefaultClaims(),
}
for _, o := range opts {
o(pc)
}
return pc
}
func WithJWK(jwk *jose.JSONWebKey, jwe *jose.JSONWebEncryption) func(*ProvisionerCtx) { func WithJWK(jwk *jose.JSONWebKey, jwe *jose.JSONWebEncryption) func(*ProvisionerCtx) {
return func(ctx *ProvisionerCtx) { return func(ctx *ProvisionerCtx) {
ctx.JWK = jwk ctx.JWK = jwk
@ -62,10 +72,7 @@ func (p *Provisioner) GetOptions() *provisioner.Options {
} }
func CreateProvisioner(ctx context.Context, db DB, typ, name string, opts ...ProvisionerOption) (*Provisioner, error) { func CreateProvisioner(ctx context.Context, db DB, typ, name string, opts ...ProvisionerOption) (*Provisioner, error) {
pc := new(ProvisionerCtx) pc := NewProvisionerCtx(opts...)
for _, o := range opts {
o(pc)
}
details, err := createJWKDetails(pc) details, err := createJWKDetails(pc)
if err != nil { if err != nil {

@ -18,6 +18,7 @@ import (
"github.com/smallstep/certificates/authority" "github.com/smallstep/certificates/authority"
"github.com/smallstep/certificates/authority/config" "github.com/smallstep/certificates/authority/config"
"github.com/smallstep/certificates/authority/mgmt" "github.com/smallstep/certificates/authority/mgmt"
mgmtAPI "github.com/smallstep/certificates/authority/mgmt/api"
"github.com/smallstep/certificates/db" "github.com/smallstep/certificates/db"
"github.com/smallstep/certificates/logging" "github.com/smallstep/certificates/logging"
"github.com/smallstep/certificates/monitoring" "github.com/smallstep/certificates/monitoring"
@ -143,6 +144,7 @@ func (ca *CA) Init(config *config.Config) (*CA, error) {
dns = fmt.Sprintf("%s:%s", dns, port) dns = fmt.Sprintf("%s:%s", dns, port)
} }
// ACME Router
prefix := "acme" prefix := "acme"
var acmeDB acme.DB var acmeDB acme.DB
if config.DB == nil { if config.DB == nil {
@ -169,6 +171,16 @@ func (ca *CA) Init(config *config.Config) (*CA, error) {
acmeHandler.Route(r) acmeHandler.Route(r)
}) })
// MGMT Router
mgmtDB := auth.GetMgmtDatabase()
if mgmtDB != nil {
mgmtHandler := mgmtAPI.NewHandler(mgmtDB)
mux.Route("/mgmt", func(r chi.Router) {
mgmtHandler.Route(r)
})
}
// helpful routine for logging all routes // // helpful routine for logging all routes //
/* /*
walkFunc := func(method string, route string, handler http.Handler, middlewares ...func(http.Handler) http.Handler) error { walkFunc := func(method string, route string, handler http.Handler, middlewares ...func(http.Handler) http.Handler) error {

@ -60,10 +60,10 @@ func (c *MgmtClient) retryOnError(r *http.Response) bool {
return false return false
} }
// GetAdmin performs the GET /config/admin/{id} request to the CA. // GetAdmin performs the GET /mgmt/admin/{id} request to the CA.
func (c *MgmtClient) GetAdmin(id string) (*mgmt.Admin, error) { func (c *MgmtClient) GetAdmin(id string) (*mgmt.Admin, error) {
var retried bool var retried bool
u := c.endpoint.ResolveReference(&url.URL{Path: path.Join("/config/admin", id)}) u := c.endpoint.ResolveReference(&url.URL{Path: path.Join("/mgmt/admin", id)})
retry: retry:
resp, err := c.client.Get(u.String()) resp, err := c.client.Get(u.String())
if err != nil { if err != nil {
@ -83,10 +83,10 @@ retry:
return adm, nil return adm, nil
} }
// GetAdmins performs the GET /config/admins request to the CA. // GetAdmins performs the GET /mgmt/admins request to the CA.
func (c *MgmtClient) GetAdmins() ([]*mgmt.Admin, error) { func (c *MgmtClient) GetAdmins() ([]*mgmt.Admin, error) {
var retried bool var retried bool
u := c.endpoint.ResolveReference(&url.URL{Path: "/config/admins"}) u := c.endpoint.ResolveReference(&url.URL{Path: "/mgmt/admins"})
retry: retry:
resp, err := c.client.Get(u.String()) resp, err := c.client.Get(u.String())
if err != nil { if err != nil {

Loading…
Cancel
Save