| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384 |
- package api
- import (
- "crypto/ecdsa"
- "crypto/elliptic"
- "crypto/rand"
- "crypto/x509"
- "crypto/x509/pkix"
- "encoding/pem"
- "math/big"
- "net"
- "os"
- "path/filepath"
- "time"
- )
- func EnsureSelfSignedCert(certFile, keyFile string) error {
- if _, err := os.Stat(certFile); err == nil {
- if _, err := os.Stat(keyFile); err == nil {
- return nil
- }
- }
- priv, err := ecdsa.GenerateKey(elliptic.P256(), rand.Reader)
- if err != nil {
- return err
- }
- serial, err := rand.Int(rand.Reader, new(big.Int).Lsh(big.NewInt(1), 128))
- if err != nil {
- return err
- }
- tmpl := &x509.Certificate{
- SerialNumber: serial,
- Subject: pkix.Name{
- Organization: []string{"AI-Status-Light"},
- CommonName: "localhost",
- },
- NotBefore: time.Now(),
- NotAfter: time.Now().Add(10 * 365 * 24 * time.Hour),
- KeyUsage: x509.KeyUsageKeyEncipherment | x509.KeyUsageDigitalSignature,
- ExtKeyUsage: []x509.ExtKeyUsage{x509.ExtKeyUsageServerAuth},
- BasicConstraintsValid: true,
- DNSNames: []string{"localhost"},
- IPAddresses: []net.IP{net.ParseIP("127.0.0.1")},
- }
- certDER, err := x509.CreateCertificate(rand.Reader, tmpl, tmpl, &priv.PublicKey, priv)
- if err != nil {
- return err
- }
- if err := os.MkdirAll(filepath.Dir(certFile), 0700); err != nil {
- return err
- }
- certOut, err := os.Create(certFile)
- if err != nil {
- return err
- }
- if err := pem.Encode(certOut, &pem.Block{Type: "CERTIFICATE", Bytes: certDER}); err != nil {
- certOut.Close()
- return err
- }
- certOut.Close()
- keyOut, err := os.Create(keyFile)
- if err != nil {
- return err
- }
- privBytes, err := x509.MarshalECPrivateKey(priv)
- if err != nil {
- keyOut.Close()
- return err
- }
- if err := pem.Encode(keyOut, &pem.Block{Type: "EC PRIVATE KEY", Bytes: privBytes}); err != nil {
- keyOut.Close()
- return err
- }
- keyOut.Close()
- return nil
- }
|