Golang基于泛化调用与Nacos实现Dubbo代理的方法是什么
这篇“Golang基于泛化调用与Nacos实现Dubbo代理的方法是什么”文章的知识点大部分人都不太理解,所以小编给大家总结了以下内容,内容详细,步骤清晰,具有一定的借鉴价值,希望大家阅读完这篇文章能有所收获,下面我们一起来看看这篇“Golang基于泛化调用与Nacos实现Dubbo代理的方法是什么”文章吧。
准备
由于是通用的 dubbo 代理,因此肯定需要使用泛化调用。而我们使用的注册中心是 nacos,因此也需要使用 nacos-sdk 来获取 provider 的实例信息。
实现
项目结构
│
├── dubbo/
│ ├─ generic.go # 泛化调用 dubbo 接口
│ ├─ models.go # 数据模型
│ └─ nacos.go # 获取 nacos 元信息
├── web/
│ └─ server.go # 对外 http 接口
│
├── main.go # main 入口函数
└── go.mod # 模块描述文件
go.mod
module dubbo-proxygo 1.20require (dubbo.apache.org/dubbo-go/v3 v3.0.5github.com/apache/dubbo-go-hessian2 v1.12.0github.com/gin-gonic/gin v1.9.0github.com/nacos-group/nacos-sdk-go/v2 v2.1.2)
返回数据格式
dubbo/models.go
:
type DataResult struct {Env string `json:"env,omitempty"` // 当前调用环境Code string `json:"code,omitempty"` // 返回结果码Data any `json:"data,omitempty"` // 返回结果Message string `json:"message,omitempty"` // 返回消息}
获取 nacos 元信息
根据环境创建 nacos client
func buildClient(env string, serverCfgs []constant.ServerConfig) naming_client.INamingClient {client, _ := clients.NewNamingClient(vo.NacosClientParam{ClientConfig: constant.NewClientConfig(constant.WithNamespaceId(env),constant.WithNotLoadCacheAtStart(true),),ServerConfigs: serverCfgs,},)return client}
获取服务实例
func SelectInstance(env, servName string) (string, bool) {cli, ok := cliMap[env]if !ok {return "client not found from " + env, false}instances, e := cli.SelectInstances(vo.SelectInstancesParam{ServiceName: fmt.Sprintf("providers:%s:1.0.0:", servName),HealthyOnly: true,})if e != nil {return "instance not found, " + e.Error(), false}if len(instances) <= 0 {return "instance not found", false}return fmt.Sprintf("dubbo://%s:%d", instances[0].Ip, instances[0].Port), true}
完整代码
dubbo/nacos.go
:
package dubboimport ("fmt""github.com/nacos-group/nacos-sdk-go/v2/clients""github.com/nacos-group/nacos-sdk-go/v2/clients/naming_client""github.com/nacos-group/nacos-sdk-go/v2/common/constant""github.com/nacos-group/nacos-sdk-go/v2/vo")var cliMap = make(map[string]naming_client.INamingClient)func init() {serverCfgs := []constant.ServerConfig{*constant.NewServerConfig("127.0.0.1", 6801, constant.WithContextPath("/nacos")),}cliMap["local"] = buildClient("local", serverCfgs)cliMap["dev"] = buildClient("develop", serverCfgs)cliMap["test"] = buildClient("test", serverCfgs)}func buildClient(env string, serverCfgs []constant.ServerConfig) naming_client.INamingClient {client, _ := clients.NewNamingClient(vo.NacosClientParam{ClientConfig: constant.NewClientConfig(constant.WithNamespaceId(env),constant.WithNotLoadCacheAtStart(true),),ServerConfigs: serverCfgs,},)return client}func SelectInstance(env, servName string) (string, bool) {cli, ok := cliMap[env]if !ok {return "client not found from " + env, false}instances, e := cli.SelectInstances(vo.SelectInstancesParam{ServiceName: fmt.Sprintf("providers:%s:1.0.0:", servName),HealthyOnly: true,})if e != nil {return "instance not found, " + e.Error(), false}if len(instances) <= 0 {return "instance not found", false}return fmt.Sprintf("dubbo://%s:%d", instances[0].Ip, instances[0].Port), true}
泛化调用
dubbo root 配置
var dubboRoot = cfg.NewRootConfigBuilder().SetProtocols(map[string]*cfg.ProtocolConfig{dubbo.DUBBO: {Params: map[string]interface{}{"getty-session-param": map[string]interface{}{"max-msg-len": 1024000,},},},}).Build()
泛化调用
func GenericInvoke(iName, method, env string, req []byte) DataResult {instance, ok := SelectInstance(env, iName)if !ok {return DataResult{Code: "ERROR",Message: instance,}}cfg.Load(cfg.WithRootConfig(dubboRoot))refConf := cfg.ReferenceConfig{InterfaceName: iName,Cluster: "failover",Protocol: dubbo.DUBBO,Generic: "true",Version: "1.0.0",URL: instance,}refConf.Init(dubboRoot)refConf.GenericLoad("dubbo-proxy")var args = utils.Unmarshal(req, &map[string]hessian.Object{})raw, err := refConf.GetRPCService().(*generic.GenericService).Invoke(context.Background(), method, nil, []hessian.Object{args})if err != nil {panic(err)}rawResult := raw.(map[interface{}]interface{})result := DataResult{Code: rawResult["code"].(string),Message: rawResult["message"].(string),Data: utils.ConvertAs(rawResult["data"], map[string]interface{}{}),}return result}
注意25-30
行要根据业务自身的返回数据格式包装结果:
rawResult := raw.(map[interface{}]interface{})result := DataResult{Code: rawResult["code"].(string),Message: rawResult["message"].(string),Data: rawResult["data"],}
完整代码
dubbo/generic.go
:
package dubboimport ("context""dubbo-proxy/utils"cfg "dubbo.apache.org/dubbo-go/v3/config""dubbo.apache.org/dubbo-go/v3/config/generic"_ "dubbo.apache.org/dubbo-go/v3/imports""dubbo.apache.org/dubbo-go/v3/protocol/dubbo"hessian "github.com/apache/dubbo-go-hessian2")var dubboRoot = cfg.NewRootConfigBuilder().SetProtocols(map[string]*cfg.ProtocolConfig{dubbo.DUBBO: {Params: map[string]interface{}{"getty-session-param": map[string]interface{}{"max-msg-len": 1024000,},},},}).Build()func GenericInvoke(iName, method, env string, req []byte) DataResult {instance, ok := SelectInstance(env, iName)if !ok {return DataResult{Code: "ERROR",Message: instance,}}cfg.Load(cfg.WithRootConfig(dubboRoot))refConf := cfg.ReferenceConfig{InterfaceName: iName,Cluster: "failover",Protocol: dubbo.DUBBO,Generic: "true",Version: "1.0.0",URL: instance,}refConf.Init(dubboRoot)refConf.GenericLoad("dubbo-proxy")var args = utils.Unmarshal(req, &map[string]hessian.Object{})raw, err := refConf.GetRPCService().(*generic.GenericService).Invoke(context.Background(), method, nil, []hessian.Object{args})if err != nil {panic(err)}rawResult := raw.(map[interface{}]interface{})result := DataResult{Code: rawResult["code"].(string),Message: rawResult["message"].(string),Data: utils.ConvertAs(rawResult["data"], map[string]interface{}{}),}return result}
提供 http 服务
dubbo/generic.go
:
package webimport ("dubbo-proxy/dubbo""github.com/gin-gonic/gin""net/http")func Run() {router := gin.Default()router.POST("/:intf/:method", func(c *gin.Context) {intf := c.Param("intf")method := c.Param("method")env := c.Query("env")data, err := c.GetRawData()if err != nil { panic(err)}res := dubbo.GenericInvoke(intf, method, env, data)res.Env = envc.JSON(http.StatusOK, res)})panic(router.Run(":7788"))}
启动
main.go
:
package mainimport "dubbo-proxy/web"func main() {web.Run()}
效果
以上就是关于“Golang基于泛化调用与Nacos实现Dubbo代理的方法是什么”这篇文章的内容,相信大家都有了一定的了解,希望小编分享的内容对大家有帮助,若想了解更多相关的知识内容,请关注编程网行业资讯频道。
免责声明:
① 本站未注明“稿件来源”的信息均来自网络整理。其文字、图片和音视频稿件的所属权归原作者所有。本站收集整理出于非商业性的教育和科研之目的,并不意味着本站赞同其观点或证实其内容的真实性。仅作为临时的测试数据,供内部测试之用。本站并未授权任何人以任何方式主动获取本站任何信息。
② 本站未注明“稿件来源”的临时测试数据将在测试完成后最终做删除处理。有问题或投稿请发送至: 邮箱/279061341@qq.com QQ/279061341