-
Notifications
You must be signed in to change notification settings - Fork 0
/
Copy pathgenca.go
127 lines (108 loc) · 3.24 KB
/
genca.go
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
package cmd
import (
"fmt"
"os"
"time"
"github.com/spf13/cobra"
"github.com/chenzhiwei/certctl/pkg/cert"
)
var (
caSize int
caDays int
caSubject string
caSan string
caKeyUsage string
caExtKeyUsage string
caNoDefaults bool
caKeyfile string
caCertfile string
gencaLong string = `Generate Root CA certificate.
Examples:
# Generate Root CA certificate
certctl genca --subject "C=CN/ST=Beijing/L=Haidian/O=Any Corp/CN=Root CA" \
--key ca.key --cert ca.crt \
--days 36500 --size 2048
# Set Key Usages and Extended Key usages manaully
certctl genca --subject "C=CN/ST=Beijing/L=Haidian/O=Any Corp/CN=Root CA" \
--nodefault \
--key ca.key --cert ca.crt \
--san "root.com,*.root.com,localhost,127.0.0.1" \
--ku digitalSignature,keyCertSign --eku serverAuth \
--days 36500 --size 2048
The list of key usages are:
* digitalSignature
* contentCommitment
* keyEncipherment
* dataEncipherment
* keyAgreement
* keyCertSign
* cRLSign
* encipherOnly
* decipherOnly
The list of extended key usages are:
* any
* serverAuth
* clientAuth
* codeSigning
* emailProtection
* IPSECEndSystem
* IPSECTunnel
* IPSECUser
* timeStamping
* OCSPSigning
* netscapeServerGatedCrypto
* microsoftServerGatedCrypto
* microsoftCommercialCodeSigning
* microsoftKernelCodeSigning
`
gencaCmd = &cobra.Command{
Use: "genca",
Aliases: []string{"generate-ca", "create-ca"},
Short: "Generate Root CA certificate",
Long: gencaLong,
Args: cobra.MaximumNArgs(0),
RunE: func(cmd *cobra.Command, _ []string) error {
if err := runGenerateCA(); err != nil {
return err
}
return nil
},
}
)
func init() {
gencaCmd.Flags().StringVar(&caSubject, "subject", "", "the certificate subject")
gencaCmd.Flags().StringVar(&caSan, "san", "", "the certificate subject alternate names")
gencaCmd.Flags().StringVar(&caKeyUsage, "ku", "", "the certificate key usage")
gencaCmd.Flags().StringVar(&caExtKeyUsage, "eku", "", "the certificate extended key usage")
gencaCmd.Flags().IntVar(&caDays, "days", 365, "the certificate validation period")
gencaCmd.Flags().IntVar(&caSize, "size", 2048, "the certificate RSA private key size")
gencaCmd.Flags().BoolVar(&caNoDefaults, "nodefault", false, "do not set any default vaules")
gencaCmd.Flags().StringVar(&caKeyfile, "key", "certctl.key", "the output key file")
gencaCmd.Flags().StringVar(&caCertfile, "cert", "certctl.crt", "the output cert file")
gencaCmd.Flags().SortFlags = false
gencaCmd.MarkFlagRequired("subject")
}
func runGenerateCA() error {
duration := time.Hour * 24 * time.Duration(caDays)
if !caNoDefaults {
caKeyUsage = "cRLSign,keyCertSign,digitalSignature"
caExtKeyUsage = ""
}
certInfo, err := cert.NewCertInfo(duration, caSubject, caSan, caKeyUsage, caExtKeyUsage, true)
if err != nil {
return err
}
certBytes, keyBytes, err := cert.NewCertKey(certInfo, caSize)
if err != nil {
return err
}
if err := os.WriteFile(caKeyfile, keyBytes, 0600); err != nil {
return err
}
fmt.Printf("Writing new private key to '%s'\n", caKeyfile)
if err := os.WriteFile(caCertfile, certBytes, 0644); err != nil {
return err
}
fmt.Printf("Writing new certificate to '%s'\n", caCertfile)
return nil
}