-
Notifications
You must be signed in to change notification settings - Fork 18
/
cert.go
84 lines (75 loc) · 2.09 KB
/
cert.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
// SPDX-License-Identifier: Apache-2.0
package firestore
import (
"context"
"crypto/sha256"
"crypto/x509"
"encoding/base64"
"encoding/pem"
"fmt"
"google.golang.org/grpc/codes"
"google.golang.org/grpc/status"
)
type certificate struct {
PemCertificate string `firestore:"pem"`
}
func (s *Store) SetCertificate(ctx context.Context, pemCertificate string) error {
certificateHash, err := getPEMCertificateHash(pemCertificate)
if err != nil {
return err
}
csRef := s.client.Doc(fmt.Sprintf("Certificate/%s", certificateHash))
_, err = csRef.Set(ctx, &certificate{
PemCertificate: pemCertificate,
})
if err != nil {
return err
}
return nil
}
func getPEMCertificateHash(pemCertificate string) (string, error) {
var cert *x509.Certificate
block, _ := pem.Decode([]byte(pemCertificate))
if block != nil {
if block.Type == "CERTIFICATE" {
var err error
cert, err = x509.ParseCertificate(block.Bytes)
if err != nil {
return "", err
}
} else {
return "", fmt.Errorf("pem block does not contain certificate, but %s", block.Type)
}
} else {
return "", fmt.Errorf("pem block not found")
}
hash := sha256.Sum256(cert.Raw)
b64Hash := base64.RawURLEncoding.EncodeToString(hash[:])
return b64Hash, nil
}
func (s *Store) LookupCertificate(ctx context.Context, certificateHash string) (string, error) {
csRef := s.client.Doc(fmt.Sprintf("Certificate/%s", certificateHash))
snap, err := csRef.Get(ctx)
if err != nil {
if status.Code(err) == codes.NotFound {
return "", nil
}
return "", fmt.Errorf("lookup certificate %s: %w", certificateHash, err)
}
var cert certificate
if err = snap.DataTo(&cert); err != nil {
return "", fmt.Errorf("lookup certificate %s: %w", certificateHash, err)
}
return cert.PemCertificate, nil
}
func (s *Store) DeleteCertificate(ctx context.Context, certificateHash string) error {
csRef := s.client.Doc(fmt.Sprintf("Certificate/%s", certificateHash))
_, err := csRef.Delete(ctx)
if err != nil {
if status.Code(err) == codes.NotFound {
return nil
}
return fmt.Errorf("delete certificate %s: %w", certificateHash, err)
}
return nil
}