curvetls
curvetls copied to clipboard
Implementing gRPC TransportCredentials interface
Howdy, thanks for providing an implementation of this protocol in Go. I'm interested in alternatives to TLS for transport security.
My issue is, I need to wrap a net.Listener
and not a net.Conn
, because I'd like to use
gRPC.
We should be able to implement the TransportCredentials
interface.
// TransportCredentials defines the common interface for all the live gRPC wire
// protocols and supported transport security protocols (e.g., TLS, SSL).
type TransportCredentials interface {
// ClientHandshake does the authentication handshake specified by the corresponding
// authentication protocol on rawConn for clients. It returns the authenticated
// connection and the corresponding auth information about the connection.
// Implementations must use the provided context to implement timely cancellation.
// gRPC will try to reconnect if the error returned is a temporary error
// (io.EOF, context.DeadlineExceeded or err.Temporary() == true).
// If the returned error is a wrapper error, implementations should make sure that
// the error implements Temporary() to have the correct retry behaviors.
//
// If the returned net.Conn is closed, it MUST close the net.Conn provided.
ClientHandshake(context.Context, string, net.Conn) (net.Conn, AuthInfo, error)
// ServerHandshake does the authentication handshake for servers. It returns
// the authenticated connection and the corresponding auth information about
// the connection.
//
// If the returned net.Conn is closed, it MUST close the net.Conn provided.
ServerHandshake(net.Conn) (net.Conn, AuthInfo, error)
// Info provides the ProtocolInfo of this TransportCredentials.
Info() ProtocolInfo
// Clone makes a copy of this TransportCredentials.
Clone() TransportCredentials
// OverrideServerName overrides the server name used to verify the hostname on the returned certificates from the server.
// gRPC internals also use it to override the virtual hosting name if it is set.
// It must be called before dialing. Currently, this is only used by grpclb.
OverrideServerName(string) error
}
Then we could start a curvetls-powered gRPC server with something like:
lis, _ := net.Listen("tcp", "...")
s := grpc.NewServer(curvetls.GRPCCredentials(pub, priv))
go func() { s.Serve(lis) }
I'm going to fork and give it a try. It seems like it should be straightforward. I'll comment here if I encounter any roadblocks.
Perhaps this implementation does not belong in core, but since I need access to some types that are currently private (to do the handshake in the way that gRPC makes us do it), I will depend on my own fork of curvetls. If there is a better way, I am willing to help. It might just be a matter of exporting things.
Closing PR #2 for now.