1package main
2
3import (
4 "crypto/ecdsa"
5 "crypto/elliptic"
6 "crypto/rand"
7 "crypto/x509"
8 "crypto/x509/pkix"
9 "encoding/pem"
10 "log"
11 "net"
12 "os"
13 "time"
14)
15
16func main() {
17 key, err := ecdsa.GenerateKey(elliptic.P256(), rand.Reader)
18 if err != nil {
19 log.Fatal(err)
20 }
21
22 now := time.Now()
23 template := &x509.Certificate{
24 // No SerialNumber: since Go 1.24, CreateCertificate generates a random one
25 Subject: pkix.Name{CommonName: "localhost"},
26 NotBefore: now,
27 NotAfter: now.AddDate(0, 0, 365),
28 DNSNames: []string{"localhost"},
29 IPAddresses: []net.IP{net.ParseIP("127.0.0.1")},
30 KeyUsage: x509.KeyUsageDigitalSignature,
31 ExtKeyUsage: []x509.ExtKeyUsage{x509.ExtKeyUsageServerAuth},
32 BasicConstraintsValid: true, // writes basicConstraints; IsCA false = CA:FALSE
33 }
34 // Self-signed: the template is both the certificate and its issuer
35 der, err := x509.CreateCertificate(rand.Reader, template, template, &key.PublicKey, key)
36 if err != nil {
37 log.Fatal(err)
38 }
39
40 keyDER, err := x509.MarshalPKCS8PrivateKey(key)
41 if err != nil {
42 log.Fatal(err)
43 }
44 if err := os.WriteFile("key.pem", pem.EncodeToMemory(&pem.Block{Type: "PRIVATE KEY", Bytes: keyDER}), 0o600); err != nil {
45 log.Fatal(err)
46 }
47 if err := os.WriteFile("cert.pem", pem.EncodeToMemory(&pem.Block{Type: "CERTIFICATE", Bytes: der}), 0o644); err != nil {
48 log.Fatal(err)
49 }
50}
51