gRPC and HTTP 1 call on single port, with out using TLS in goLang

huangapple go评论85阅读模式
英文:

gRPC and HTTP 1 call on single port, with out using TLS in goLang

问题

我最近开始在一个项目中使用golang,其中我需要在服务器上使用gRPC进行推送通知,以连接到Android设备。我已经创建了一个简单的多路复用器mux := http.NewServeMux(),在我的服务器代码中运行良好:

serverWeb := http.Server{
    Addr:    constants.ServerIPWeb,
    Handler: mux,
}

serverWeb.ListenAndServe()

根据gRPC.io上的示例,我还创建了一个简单的独立的gRPC客户端/服务器项目,连接到我的Android设备,没有任何TLS配置,它也正常工作。

type server struct{}

func (s *server) DeviceData(ctx context.Context, req *pb.GetDeviceRequest) (*pb.SetDeviceResponse, error) {
    util.P("Device is: ", req) // 简单的 fmt.PrintF(a ... interface)
    return &pb.SetDeviceResponse{Message: "Success"}, nil
}

func main() {
    lis, err := net.Listen("tcp", ":8080")
    if err != nil {
        log.Fatalf("Failed to listen: %v", err)
    }
    s := grpc.NewServer()
    pb.RegisterDeviceInfoServer(s, &server{})
    reflection.Register(s)
    if err := s.Serve(lis); err != nil {
        log.Fatalf("Falied to server: %v", err)
    }
}

问题是我无法将我的当前gRPC服务器连接到上面的serverStruct。我尝试添加Handler: grpcHandlerFunc(grpcServer, mux),将我的服务器连接到以下代码,如这里所解释的(gRPC与开放API):

func grpcHandlerFunc(grpcServer *grpc.Server, otherHandler http.Handler) http.Handler {
    return http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
        // TODO(tamird): point to merged gRPC code rather than a PR.
        // This is a partial recreation of gRPC's internal checks https://github.com/grpc/grpc-go/pull/514/files#diff-95e9a25b738459a2d3030e1e6fa2a718R61
        util.P("ResponseFunction: GRPC: ", r.URL) // 简单的 fmt.PrintF(a ... interface)
        if r.ProtoMajor == 2 && strings.Contains(r.Header.Get("Content-Type"), "application/grpc") {
            grpcServer.ServeHTTP(w, r)
        } else {
            otherHandler.ServeHTTP(w, r)
        }
    })
}

上述代码将运行从mux连接到http的服务,但不会运行来自gRPC的服务,即不会连接到我的Android设备。

我相信这需要TLS连接,但我不想实现安全我的Web和Android端代码,因为这将要求我更改Android端和Web的所有代码,我想避免这样做。

因此,我正在寻找一种在不使用任何TLS配置的情况下将此grpcServer连接到我的当前serverStruct的方法。

此外,我还进行了更多的研究:
我还搜索到一个名为cmuxrepoConnection Mux),它可以完成同样的工作,但我不明白如何将其与我的当前serverStruct一起使用,因为我有一个完全功能的Web应用程序正在运行,我只需要在其中添加gRPC

英文:

I have recently started working in <b>golang</b> for a project, where I have to use gRPC for push notification on my server to connect to an Android device.
I have created a simple multiplexer mux := http.NewServeMux() which is working fine with my server code:

  serverWeb := http.Server{
	Addr:	constants.ServerIPWeb,
	//Handler: grpcHandlerFunc(grpcServer, mux),
	Handler: mux,
}

serverWeb.ListenAndServe()

As from the examples on <a href="https://grpc.io/">gRPC.io</a> I have also created a simple gRPC client/server as a standalone project connected to my android device, with out any TLS configuration and its working fine.

type server struct{}

func (s *server) DeviceData(ctx context.Context,req *pb.GetDeviceRequest) (*pb.SetDeviceResponse, error){
    util.P(&quot;Device is: &quot;,req) // simple fmt.PrintF(a ... interface)
    return  &amp;pb.SetDeviceResponse{Message:&quot;Success&quot;}, nil
}

func main(){
    lis, err := net.Listen(&quot;tcp&quot;, &quot;:8080&quot;)
    if err!=nil{
	log.Fatalf(&quot;Failed to listen: %v&quot;, err)
	}
	s := grpc.NewServer()
	pb.RegisterDeviceInfoServer(s,&amp;server{})
    reflection.Register(s)
    if err := s.Serve(lis); err != nil{
	    log.Fatalf(&quot;Falied to server: %v&quot;, err)
    }
}

The <b>problem</b> is I could not connect my current gRPC server to my serverStruct above. I have tried to add Handler: grpcHandlerFunc(grpcServer, mux) that will connect my server to the following code, as explained here (<a href="https://grpc.io/blog/coreos"> gRPC with open API </a>)

func grpcHandlerFunc(grpcServer *grpc.Server, otherHandler http.Handler) http.Handler {
return http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
	// TODO(tamird): point to merged gRPC code rather than a PR.
	// This is a partial recreation of gRPC&#39;s internal checks https://github.com/grpc/grpc-go/pull/514/files#diff-95e9a25b738459a2d3030e1e6fa2a718R61
	util.P(&quot;ResponseFunction: GRPC: &quot;,r.URL) // simple fmt.PrintF(a ... interface)
	if r.ProtoMajor == 2 &amp;&amp; strings.Contains(r.Header.Get(&quot;Content-Type&quot;), &quot;application/grpc&quot;) {
		grpcServer.ServeHTTP(w, r)
	} else {
		otherHandler.ServeHTTP(w, r)
	}
})
}

The above code will run my Service running from my mux i.e connecting to http, but it won't run services from gRPC, i.e is connecting to my Android Device.

I believe it requires, TLS connection, but I don't want to get into the implementation of securing my web and Android side code, as that would require me to change all the code at my Android Side and Web, which I want to avoid.

So I am looking for a way to connect this grpcServer to my current serverStruct without using any TLS configuration.

<b>More Over myResearcH:</b>
I have also searched there is a repo called cmux (<a href="https://github.com/soheilhy/cmux">Connection Mux</a>) which will do the same job, but I don't understand how would I use it with my current serverStruct, as I have a fully functional web app running on this, and I just need to add gRPC with my current code.

答案1

得分: 1

gRPC服务可以通过使用Go协程而无需实现TLS来实现。<br /><br />
<b>创建一个函数,用于提供gRPC服务</b>

func RunGRPC()  {
    grpcServer := grpc.NewServer()
    pb.RegisterGlassInfoServer(grpcServer,&amp;GlassApkBean{})
    pb.RegisterDeviceInfoServer(grpcServer, &amp;DeviceInfoBean{}) // 用于多个服务
    lis, err := net.Listen(&quot;tcp&quot;, &quot;:50051&quot;)
    if err !=nil{
        log.Fatalf(&quot;错误: %v\n&quot; , err.Error())
    }
    grpcServer.Serve(lis)
}

<b>使用此函数接收客户端请求</b>

func main(){
    .
    . // 你的代码
    .
    go RunGRPC() // 在Go协程中运行gRPC服务器的代码
    serverWeb := http.Server{
        Addr:   &quot;localhost:8080&quot;,
        Handler: mux,
}

serverWeb.ListenAndServe()
}
英文:

gRPC Service can be achieved with out the implementation of TLS by using go routines.<br /><br />
<b>Create a Function, Serving your gRPC</b>

func RunGRPC()  {
    grpcServer := grpc.NewServer()
	pb.RegisterGlassInfoServer(grpcServer,&amp;GlassApkBean{})
    pb.RegisterDeviceInfoServer(grpcServer, &amp;DeviceInfoBean{}) // for multiple services
	lis, err := net.Listen(&quot;tcp&quot;, &quot;:50051&quot;)
    if err !=nil{
	    log.Fatalf(&quot;Error: %v\n&quot; , err.Error())
    }
	grpcServer.Serve(lis)
}

<b> use this function, to recive client request</b>

func main(){
    .
    . // Your Code
    .
    go RunGRPC() // code to run grpc server in go routine. 
    serverWeb := http.Server{
        Addr:   &quot;localhost:8080&quot;,
        Handler: mux,
}

serverWeb.ListenAndServe()
}

huangapple
  • 本文由 发表于 2017年9月6日 17:24:16
  • 转载请务必保留本文链接:https://go.coder-hub.com/46071453.html
匿名

发表评论

匿名网友

:?: :razz: :sad: :evil: :!: :smile: :oops: :grin: :eek: :shock: :???: :cool: :lol: :mad: :twisted: :roll: :wink: :idea: :arrow: :neutral: :cry: :mrgreen:

确定