grpc+http服务器搭建


前言

grpc-gateway使用教程》中已有现成的 grpc+https 服务器搭建教程&源码,可直接学习搭建。基于爱搞事情的心态,就是不想用 TLS,应该怎么处理?详见本文


去除TLS & 解决遇到的问题

按照《grpc-gateway使用教程》描述,去掉项目中的TLS配置相关代码,设置 dialOpt 为 grpc.WithInsecure() 即可

dialOpt := []grpc.DialOption{grpc.WithInsecure()}

结果实际测试发起请求,却遇到了下面问题:
在这里插入图片描述


通过《Why am i getting connection connection closed before server preface received in go?》可以知道问题的解决方式,使用 h2c 改造 /pkg/util/grpc.go 代码如下:

package util

import (
	"golang.org/x/net/http2"
	"golang.org/x/net/http2/h2c"
	"google.golang.org/grpc"
	"net/http"
	"strings"
)

// GrpcHandlerFunc 函数是用于判断请求来源于Rpc客户端还是Restful api的请求,根据不同的请求注册不同的ServerHTTP服务,
// r.ProtoMajor=2代表着请求必须基于HTTP/2
func GrpcHandlerFunc(grpcServer *grpc.Server, otherHandler http.Handler) http.Handler {
	return h2c.NewHandler(http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
		if otherHandler == nil {
			grpcServer.ServeHTTP(w, r)
			return
		}
		if r.ProtoMajor == 2 && strings.Contains(r.Header.Get("Content-Type"), "application/grpc") {
			grpcServer.ServeHTTP(w, r)
		} else {
			otherHandler.ServeHTTP(w, r)
		}
	}), &http2.Server{})
}

好了,现在可以正常使用http访问了
在这里插入图片描述


解决CORS问题

HTTP服务器常遇跨域CORS问题,可在上文/pkg/util/grpc.gootherHandler.ServeHTTP(w, r)前加入下述代码解决

// CORS
if r.Method == "OPTIONS" && r.Header.Get("Access-Control-Request-Method") != "" {
	w.Header().Set("Access-Control-Allow-Origin", "*")
	headers := []string{"Content-Type", "Accept"}
	w.Header().Set("Access-Control-Allow-Headers", strings.Join(headers, ","))
	methods := []string{"GET", "HEAD", "POST", "PUT", "DELETE"}
	w.Header().Set("Access-Control-Allow-Methods", strings.Join(methods, ","))
	return
}
// 可根据需要,调整允许访问的orgin
w.Header().Set("Access-Control-Allow-Origin", "*")

可使用 cors.html 进行测试

在这里插入图片描述

具体请见:grpc-gateway-demo的wipe_tls分支代码


参考文章

评论 2
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值