Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Adding TLS to RPC #180

Closed
freman opened this issue Jun 25, 2017 · 17 comments
Closed

Adding TLS to RPC #180

freman opened this issue Jun 25, 2017 · 17 comments

Comments

@freman
Copy link

freman commented Jun 25, 2017

I'm feeling a little bit dumb, I don't suppose you have an example of adding TLS to a RPC service?

	security.Setup(log, security.Vault())
	tlsConfig := &tls.Config{
		GetCertificate: security.Vault().CertificateGetter(),
	}

	// initialise service
	service.Init(
		micro.Action(func(c *cli.Context) {
			if c.Bool("debug") {
				log.Level = logrus.DebugLevel
				log.Debug("Debug log level enabled")
			}
		}),
// transport.TLSConfig(tlsConfig),
	)

	countryHandler, err := handler.NewCountryHandler()
	if err != nil {
		log.Fatal(err)
	}

	country.RegisterCountriesHandler(service.Server(), countryHandler)

	if err := service.Run(); err != nil {
		log.Fatal(err)
	}

I tried adding transport options to the service.Init but it's clearly not that simple?

@freman
Copy link
Author

freman commented Jun 25, 2017

So I got it to compile and work with this

	// initialise service
	service.Init(
		micro.Action(func(c *cli.Context) {
			if c.Bool("debug") {
				log.Level = logrus.DebugLevel
				log.Debug("Debug log level enabled")
			}
		}),
		micro.Transport(transport.NewTransport(
			transport.TLSConfig(tlsConfig),
		)),
	)

But now the micro client strokes out with

{"id":"go.micro.client.transport","code":500,"detail":"malformed HTTP response \"\\x15\\x03\\x01\\x00\\x02\\x02\\x16\"","status":"Internal Server Error"}

@asim
Copy link
Member

asim commented Jun 25, 2017

Is the client actually using tls?

@freman
Copy link
Author

freman commented Jun 25, 2017

I'm pretty sure no, I'm just using the micro cli tool

I've tried

micro --enable_tls query srv.mapper Country.List

And

micro --enable_tls=true query srv.mapper Country.List

@asim
Copy link
Member

asim commented Jun 25, 2017

The micro cli does not currently support tls. The enable_tls flag is used to enable it for the http entrypoints; api, sidecar, web ui. You will need to setup tls yourself by switching out the default transport in go-micro/transport and compiling with that. The micro cli will make use of the default transport.

Example tls.go file

package main

import (
    "github.com/micro/go-micro/transport"
)

func init() {
    // initialise a tls config
    t := tls.Config{InsecureSkipVerify: true}
    transport.DefaultTransport = transport.NewTransport(transport.TLSConfig(t))
}

rebuild with that

go build -o micro main.go tls.go

@freman
Copy link
Author

freman commented Jun 25, 2017

Might be awesome to figure it out with meta data - the service registers as using tls then the client should use tls. Less chance of cross channels.

Thanks for that tho.

@asim
Copy link
Member

asim commented Jun 25, 2017

Yea might be something to add but requires some work to do it without it being a hack. Also has the potential to be exploited in reverse where untrustworthy services are registered with no tls in a secure environment causing data to leak. There's no reason why a client could not be written to check metadata and do this but not sure it will be the default behaviour.

@freman
Copy link
Author

freman commented Jun 25, 2017

Hmm yes, that's a concern, but perhaps that can be negated with a "requiretls" option - when you know you want tls, then require it.

I know that sounds backwards, but I'm thinking from a dev perspective where they'll probably have a mix of tls and non tls while developing but they'll deploy to tls (although, I'm currently working on that being not the case with dev vault instances that just work)

@asim
Copy link
Member

asim commented Jun 25, 2017

Likely to spend more time thinking about it before actually implementing anything. A secure by default config would be nice but it's not quite simple.

Please close the issue when satisfied that tls works.

@freman
Copy link
Author

freman commented Jun 25, 2017

That doesn't seem to be working, looks like it's still trying to http transport.

@asim
Copy link
Member

asim commented Jun 25, 2017

Try setting the transport in the client after setting it up.

import "github.com/micro/go-micro/client"

func init() {
    client.Init(client.Transport(t))
}

@freman
Copy link
Author

freman commented Jun 25, 2017

package main

import (
	"crypto/tls"

	"github.com/micro/go-micro/client"
	"github.com/micro/go-micro/transport"
)

func init() {
	// initialise a tls config
	t := &tls.Config{InsecureSkipVerify: false}
	tr := transport.NewTransport(transport.TLSConfig(t))
	client.DefaultClient.Init(client.Transport(tr))
}

This works, now to convert everyone over to tls so I don't even have to deal with the tls vs not tls :D

@asim
Copy link
Member

asim commented Jun 25, 2017

Decided to test it myself.

When creating a service I set:

service := micro.NewService(
    micro.Transport(transport.NewTransport(transport.Secure(true))),
)

For the micro client I set:

package main

import (
	"github.com/micro/go-micro/client"
	"github.com/micro/go-micro/transport"
)

func init() {
	client.DefaultClient.Init(
		client.Transport(
			transport.NewTransport(transport.Secure(true)),
		),
	)
}

This works.

@freman
Copy link
Author

freman commented Jun 25, 2017

Cheers

@freman freman closed this as completed Jun 25, 2017
@adebnath-rb
Copy link

adebnath-rb commented Apr 28, 2018

@asim : I tried what you mentioned, but the client and server still communicates even though they are set to true/false.

I also tried with certificates:
Server.go
`service.Init(

	micro.Action(func(c *cli.Context) {

		config.PackageFilePath = c.String("filepath")

	}),

	micro.Transport(transport.NewTransport(

		transport.TLSConfig(tlsConfig),

	)),

)

`

Client.go
`
service.Init(

	micro.Action(func(c *cli.Context) {

		Server1 = c.String("server")

	}),

	micro.Transport(transport.NewTransport(

		transport.TLSConfig(tlsConfig),

	)),

)

`

Here, even if the certificates are different on both sides, they still communicate.

This is strange as I am facing this issue only in case of go-micro.
I tried with normal grpc, and there it works perfectly.

@asim
Copy link
Member

asim commented Apr 28, 2018

Are you using go-micro with grpc? If so it ignores the transport and you need to set this in the client and server.

@asim
Copy link
Member

asim commented Apr 28, 2018

Please don't comment on closed issues. Feel free to join the slack to discuss resolving this. Alternatively for direct support please ask Riverbed to pay for this.

If you're using go-grpc please pay attention to the options https://godoc.org/github.com/micro/go-grpc#WithTLS

@hamidabdul1994
Copy link

{"id":"go.micro.client","code":500,"detail":"connection error: x509: certificate signed by unknown authority","status":"Internal Server Error"}

Getting error in my client to hit sample.com:443, Kindly please help me in creating client

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

4 participants