diff --git a/authority/options.go b/authority/options.go index 4fc5a20f..9d59137c 100644 --- a/authority/options.go +++ b/authority/options.go @@ -167,6 +167,15 @@ func WithKeyManager(k kms.KeyManager) Option { } } +// WithX509CAService allows the consumer to provide an externally implemented +// API implementation of apiv1.CertificateAuthorityService +func WithX509CAService(svc casapi.CertificateAuthorityService) Option { + return func(a *Authority) error { + a.x509CAService = svc + return nil + } +} + // WithX509Signer defines the signer used to sign X509 certificates. func WithX509Signer(crt *x509.Certificate, s crypto.Signer) Option { return WithX509SignerChain([]*x509.Certificate{crt}, s) diff --git a/ca/ca.go b/ca/ca.go index 7baf2419..f2b0ff12 100644 --- a/ca/ca.go +++ b/ca/ca.go @@ -24,6 +24,7 @@ import ( "github.com/smallstep/certificates/api" "github.com/smallstep/certificates/authority" "github.com/smallstep/certificates/authority/admin" + "github.com/smallstep/certificates/cas/apiv1" adminAPI "github.com/smallstep/certificates/authority/admin/api" "github.com/smallstep/certificates/authority/config" "github.com/smallstep/certificates/db" @@ -46,6 +47,7 @@ type options struct { sshHostPassword []byte sshUserPassword []byte database db.AuthDB + x509CAService apiv1.CertificateAuthorityService } func (o *options) apply(opts []Option) { @@ -65,6 +67,13 @@ func WithConfigFile(name string) Option { } } +// WithX509CAService provides the x509CAService to be used for signing x509 requests +func WithX509CAService(svc apiv1.CertificateAuthorityService) Option { + return func(o *options) { + o.x509CAService = svc + } +} + // WithPassword sets the given password as the configured password in the CA // options. func WithPassword(password []byte) Option { @@ -163,6 +172,10 @@ func (ca *CA) Init(cfg *config.Config) (*CA, error) { opts = append(opts, authority.WithQuietInit()) } + if ca.opts.x509CAService != nil { + opts = append(opts, authority.WithX509CAService(ca.opts.x509CAService)) + } + webhookTransport := http.DefaultTransport.(*http.Transport).Clone() opts = append(opts, authority.WithWebhookClient(&http.Client{Transport: webhookTransport})) diff --git a/cas/apiv1/services.go b/cas/apiv1/services.go index bca24d96..fdd35f16 100644 --- a/cas/apiv1/services.go +++ b/cas/apiv1/services.go @@ -53,6 +53,8 @@ const ( StepCAS = "stepcas" // VaultCAS is a CertificateAuthorityService using Hasicorp Vault PKI. VaultCAS = "vaultcas" + // ExternalCAS is a CertificateAuthorityService using an external injected CA implementation + ExternalCAS = "externalcas" ) // String returns a string from the type. It will always return the lower case diff --git a/cas/apiv1/services_test.go b/cas/apiv1/services_test.go index 9289de76..b4f1def7 100644 --- a/cas/apiv1/services_test.go +++ b/cas/apiv1/services_test.go @@ -13,6 +13,7 @@ func TestType_String(t *testing.T) { {"default", "", "softcas"}, {"SoftCAS", SoftCAS, "softcas"}, {"CloudCAS", CloudCAS, "cloudcas"}, + {"ExternalCAS", ExternalCAS, "externalcas"}, {"UnknownCAS", "UnknownCAS", "unknowncas"}, } for _, tt := range tests {