forked from hyperledger/fabric
-
Notifications
You must be signed in to change notification settings - Fork 0
/
client_grpc.go
138 lines (114 loc) · 3.7 KB
/
client_grpc.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
128
129
130
131
132
133
134
135
136
137
138
package ca
import (
"crypto/tls"
"crypto/x509"
"encoding/pem"
"io/ioutil"
"time"
pb "github.com/hyperledger/fabric/membersrvc/protos"
"github.com/spf13/viper"
"google.golang.org/grpc"
"google.golang.org/grpc/credentials"
)
/** Performs Certificate type validation **/
/*
* Checks for valid Cert format type
* Cert expiration
*
*/
func isValidCertFormatted(certLocation string) bool {
var isvalidCert = false
certificate, err := ioutil.ReadFile(certLocation)
if err != nil {
return false
}
block, _ := pem.Decode(certificate)
if block == nil {
certificates, err := x509.ParseCertificates(certificate)
if err != nil {
caLogger.Error("Not a valid Certificate")
} else {
validCert := validateCert(certificates[0])
if !validCert {
caLogger.Error("Certificate has expired")
}
return validCert
}
} else {
certificates, err := x509.ParseCertificates(block.Bytes)
if err != nil {
caLogger.Error("Not a valid Certificate")
} else {
validCert := validateCert(certificates[0])
if !validCert {
caLogger.Error("Certificate has expired")
}
return validCert
}
}
return isvalidCert
}
/** Given the cert , it checks for expiry
* Does not check for revocation
*/
func validateCert(cert *x509.Certificate) bool {
notBefore := cert.NotBefore
notAfter := cert.NotAfter
currentTime := time.Now()
diffFromExpiry := notAfter.Sub(currentTime)
diffFromStart := currentTime.Sub(notBefore)
return ((diffFromExpiry > 0) && (diffFromStart > 0))
}
// NewClientTLSFromFile creates Client TLS connection credentials
// @certFile : TLS Server Certificate in PEM format
// @serverNameOverride : Common Name (CN) of the TLS Server Certificate
// returns Secure Transport Credentials
//
func NewClientTLSFromFile(certFile, serverNameOverride string) (credentials.TransportCredentials, error) {
caLogger.Debug("upgrading to TLS1.2")
b, err := ioutil.ReadFile(certFile)
if err != nil {
caLogger.Errorf("Certificate could not be found in the [%s] path", certFile)
return nil, err
}
if !isValidCertFormatted(certFile) {
return nil, nil
}
cp := x509.NewCertPool()
ok := cp.AppendCertsFromPEM(b)
if !ok {
caLogger.Error("credentials: failed to append certificates: ")
return nil, nil
}
return credentials.NewTLS(&tls.Config{ServerName: serverNameOverride, RootCAs: cp, MinVersion: 0, MaxVersion: 0}), nil
}
//GetClientConn returns a connection to the server located on *address*.
func GetClientConn(address string, serverName string) (*grpc.ClientConn, error) {
caLogger.Debug("GetACAClient: using the given gRPC client connection to return a new ACA client")
var opts []grpc.DialOption
if viper.GetBool("security.tls_enabled") {
caLogger.Debug("TLS was enabled [security.tls_enabled == true]")
creds, err := NewClientTLSFromFile(viper.GetString("security.client.cert.file"), viper.GetString("security.serverhostoverride"))
if err != nil {
caLogger.Error("Could not establish TLS client connection in GetClientConn while getting creds:")
caLogger.Error(err)
return nil, err
}
opts = append(opts, grpc.WithTransportCredentials(creds))
} else {
caLogger.Debug("TLS was not enabled [security.tls_enabled == false]")
opts = append(opts, grpc.WithInsecure())
}
opts = append(opts, grpc.WithTimeout(time.Second*3))
return grpc.Dial(address, opts...)
}
//GetACAClient returns a client to Attribute Certificate Authority.
func GetACAClient() (*grpc.ClientConn, pb.ACAPClient, error) {
caLogger.Debug("GetACAClient: Trying to create a new ACA Client from the connection provided")
conn, err := GetClientConn(viper.GetString("aca.address"), viper.GetString("aca.server-name"))
if err != nil {
return nil, nil, err
}
client := pb.NewACAPClient(conn)
return conn, client, nil
}