Skip to content

Commit 3993a06

Browse files
authored
Merge pull request #545 from smallstep/mariano/fix-certificates-1917
Add support for setting the raw subject in the templates
2 parents 6eaaf7f + 936b845 commit 3993a06

File tree

6 files changed

+79
-0
lines changed

6 files changed

+79
-0
lines changed

x509util/certificate.go

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -17,6 +17,7 @@ import (
1717
type Certificate struct {
1818
Version int `json:"version"`
1919
Subject Subject `json:"subject"`
20+
RawSubject []byte `json:"rawSubject"`
2021
Issuer Issuer `json:"issuer"`
2122
SerialNumber SerialNumber `json:"serialNumber"`
2223
DNSNames MultiString `json:"dnsNames"`
@@ -128,6 +129,7 @@ func (c *Certificate) GetCertificate() *x509.Certificate {
128129
// Unparsed data
129130
cert.PublicKey = c.PublicKey
130131
cert.PublicKeyAlgorithm = c.PublicKeyAlgorithm
132+
cert.RawSubject = c.RawSubject
131133

132134
// Subject
133135
c.Subject.Set(cert)

x509util/certificate_request.go

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -45,6 +45,7 @@ type certificateRequest struct {
4545
type CertificateRequest struct {
4646
Version int `json:"version"`
4747
Subject Subject `json:"subject"`
48+
RawSubject []byte `json:"rawSubject"`
4849
DNSNames MultiString `json:"dnsNames"`
4950
EmailAddresses MultiString `json:"emailAddresses"`
5051
IPAddresses MultiIP `json:"ipAddresses"`
@@ -115,6 +116,7 @@ func NewCertificateRequestFromX509(cr *x509.CertificateRequest) *CertificateRequ
115116
return &CertificateRequest{
116117
Version: cr.Version,
117118
Subject: newSubject(cr.Subject),
119+
RawSubject: cr.RawSubject,
118120
DNSNames: cr.DNSNames,
119121
EmailAddresses: cr.EmailAddresses,
120122
IPAddresses: cr.IPAddresses,
@@ -134,6 +136,7 @@ func (c *CertificateRequest) GetCertificateRequest() (*x509.CertificateRequest,
134136
cert := c.GetCertificate().GetCertificate()
135137
asn1Data, err := x509.CreateCertificateRequest(rand.Reader, &x509.CertificateRequest{
136138
Subject: cert.Subject,
139+
RawSubject: cert.RawSubject,
137140
DNSNames: cert.DNSNames,
138141
IPAddresses: cert.IPAddresses,
139142
EmailAddresses: cert.EmailAddresses,

x509util/certificate_test.go

Lines changed: 50 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -22,6 +22,7 @@ import (
2222

2323
"github.com/stretchr/testify/assert"
2424
"github.com/stretchr/testify/require"
25+
"go.step.sm/crypto/pemutil"
2526
)
2627

2728
func createCertificateRequest(t *testing.T, commonName string, sans []string) (*x509.CertificateRequest, crypto.Signer) {
@@ -49,6 +50,21 @@ func createCertificateRequest(t *testing.T, commonName string, sans []string) (*
4950
return cr, priv
5051
}
5152

53+
func readCertificateRequest(t *testing.T, filename, keyFilename string) (*x509.CertificateRequest, crypto.Signer) {
54+
t.Helper()
55+
56+
cr, err := pemutil.ReadCertificateRequest(filename)
57+
require.NoError(t, err)
58+
59+
key, err := pemutil.Read(keyFilename)
60+
require.NoError(t, err)
61+
62+
signer, ok := key.(crypto.Signer)
63+
require.True(t, ok)
64+
65+
return cr, signer
66+
}
67+
5268
func createIssuerCertificate(t *testing.T, commonName string) (*x509.Certificate, crypto.Signer) {
5369
t.Helper()
5470
now := time.Now()
@@ -135,6 +151,8 @@ func TestNewCertificate(t *testing.T) {
135151
return ipNet
136152
}
137153

154+
rawSubjectCR, rawSubjectKey := readCertificateRequest(t, "testdata/rawSubject.csr", "testdata/rawSubject.key")
155+
138156
type args struct {
139157
cr *x509.CertificateRequest
140158
opts []Option
@@ -283,6 +301,38 @@ func TestNewCertificate(t *testing.T) {
283301
PublicKey: priv.Public(),
284302
PublicKeyAlgorithm: x509.Ed25519,
285303
}, false},
304+
{"okRawSubject", args{rawSubjectCR, []Option{WithTemplateFile("./testdata/rawSubject.tpl", TemplateData{
305+
SANsKey: []SubjectAlternativeName{
306+
{Type: "dns", Value: "foo.com"},
307+
},
308+
CertificateRequestKey: NewCertificateRequestFromX509(rawSubjectCR),
309+
})}}, &Certificate{
310+
Subject: Subject{},
311+
RawSubject: []byte{
312+
0x30, 0x68, 0x31, 0x0b, 0x30, 0x09, 0x06, 0x03,
313+
0x55, 0x04, 0x06, 0x13, 0x02, 0x55, 0x53, 0x31,
314+
0x13, 0x30, 0x11, 0x06, 0x03, 0x55, 0x04, 0x08,
315+
0x0c, 0x0a, 0x43, 0x61, 0x6c, 0x69, 0x66, 0x6f,
316+
0x72, 0x6e, 0x69, 0x61, 0x31, 0x16, 0x30, 0x14,
317+
0x06, 0x03, 0x55, 0x04, 0x07, 0x0c, 0x0d, 0x53,
318+
0x61, 0x6e, 0x20, 0x46, 0x72, 0x61, 0x6e, 0x63,
319+
0x69, 0x73, 0x63, 0x6f, 0x31, 0x1d, 0x30, 0x1b,
320+
0x06, 0x03, 0x55, 0x04, 0x0a, 0x0c, 0x14, 0x53,
321+
0x6d, 0x61, 0x6c, 0x6c, 0x73, 0x74, 0x65, 0x70,
322+
0x20, 0x4c, 0x61, 0x62, 0x73, 0x2c, 0x20, 0x49,
323+
0x6e, 0x63, 0x2e, 0x31, 0x0d, 0x30, 0x0b, 0x06,
324+
0x03, 0x55, 0x04, 0x03, 0x0c, 0x04, 0x54, 0x65,
325+
0x73, 0x74,
326+
},
327+
SANs: []SubjectAlternativeName{{Type: DNSType, Value: "foo.com"}},
328+
KeyUsage: KeyUsage(x509.KeyUsageDigitalSignature),
329+
ExtKeyUsage: ExtKeyUsage([]x509.ExtKeyUsage{
330+
x509.ExtKeyUsageServerAuth,
331+
x509.ExtKeyUsageClientAuth,
332+
}),
333+
PublicKey: rawSubjectKey.Public(),
334+
PublicKeyAlgorithm: x509.ECDSA,
335+
}, false},
286336
{"badSignature", args{crBadSignateure, nil}, nil, true},
287337
{"failTemplate", args{cr, []Option{WithTemplate(`{{ fail "fatal error }}`, CreateTemplateData("commonName", []string{"foo.com"}))}}, nil, true},
288338
{"missingTemplate", args{cr, []Option{WithTemplateFile("./testdata/missing.tpl", CreateTemplateData("commonName", []string{"foo.com"}))}}, nil, true},

x509util/testdata/rawSubject.csr

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,9 @@
1+
-----BEGIN CERTIFICATE REQUEST-----
2+
MIIBIjCBygIBADBoMQswCQYDVQQGEwJVUzETMBEGA1UECAwKQ2FsaWZvcm5pYTEW
3+
MBQGA1UEBwwNU2FuIEZyYW5jaXNjbzEdMBsGA1UECgwUU21hbGxzdGVwIExhYnMs
4+
IEluYy4xDTALBgNVBAMMBFRlc3QwWTATBgcqhkjOPQIBBggqhkjOPQMBBwNCAATG
5+
NLZtzv5dcl2Nz66XBV+tq5jKCH9WGPlsuBEq48NNUb1LzecjaVTZsEwe+ZpQbnzk
6+
wTdYXFI68HbovxWc9fDxoAAwCgYIKoZIzj0EAwIDRwAwRAIgODOqVqdeZzSwZOFB
7+
VZuSLoMVvCVoiFng8/2hXfJWJi4CIBNHEt9batonI4Z6Z0kij/qNTeTTWFd5yawX
8+
2DP2+6EP
9+
-----END CERTIFICATE REQUEST-----

x509util/testdata/rawSubject.key

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,5 @@
1+
-----BEGIN EC PRIVATE KEY-----
2+
MHcCAQEEIK9FBgwqr6Zjsbf2uPmvnDz341AhiJbPLTuq8+/BLbd/oAoGCCqGSM49
3+
AwEHoUQDQgAExjS2bc7+XXJdjc+ulwVfrauYygh/Vhj5bLgRKuPDTVG9S83nI2lU
4+
2bBMHvmaUG585ME3WFxSOvB26L8VnPXw8Q==
5+
-----END EC PRIVATE KEY-----

x509util/testdata/rawSubject.tpl

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,10 @@
1+
{
2+
"rawSubject": {{ toJson .Insecure.CR.RawSubject }},
3+
"sans": {{ toJson .SANs }},
4+
{{- if typeIs "*rsa.PublicKey" .Insecure.CR.PublicKey }}
5+
"keyUsage": ["keyEncipherment", "digitalSignature"],
6+
{{- else }}
7+
"keyUsage": ["digitalSignature"],
8+
{{- end }}
9+
"extKeyUsage": ["serverAuth", "clientAuth"]
10+
}

0 commit comments

Comments
 (0)