前面的rpc调用虽然简单,但是和普通的http的调用差异不大,这次我们解决下面的问题:
1. serviceName统一和名称冲突的问题
- server端和client端如何统一serviceName
- 多个server的包中serviceName同名的问题
新建handler/handler.go文件内容如下: 为什么要新建一个文件? - 解耦
package handlerconst HelloServiceName = "handler/HelloService"
1. 服务端
package mainimport ("net""net/rpc""start/rpc_ch01/handler")type HelloService struct {}func (s *HelloService) Hello(request string, reply *string) error {*reply = "hello "+ requestreturn nil}func main(){_ = rpc.RegisterName(handler.HelloServiceName, &HelloService{})listener, err := net.Listen("tcp", ":1234")if err != nil {panic("监听端口失败")}conn, err := listener.Accept()if err != nil {panic("建立链接失败")}rpc.ServeConn(conn)}
2. 客户端
package mainimport ("fmt""net/rpc""start/rpc_ch01/handler")func main() {client, err := rpc.Dial("tcp", "localhost:1234")if err != nil {panic("连接到服务器失败")}var reply stringerr = client.Call(handler.HelloServiceName+".Hello", "imooc", &reply)if err != nil {panic("服务调用失败")}fmt.Println(reply)}
2. 继续屏蔽HelloServiceName和Hello函数名称
1. handler源码
package handlertype HelloService struct{}func (s *HelloService) Hello(request string, reply *string) error {*reply = "hello " + requestreturn nil}
2. 服务端代理
package server_proxyimport "net/rpc"const HelloServiceName = "handler/HelloService"type HelloServiceInterface interface {Hello(request string, reply *string) error}func RegisterHelloService(srv HelloServiceInterface) error {return rpc.RegisterName(HelloServiceName, srv)}
3. 服务端
package mainimport ("net""net/rpc""start/rpc_ch01/handler""start/rpc_ch01/server_proxy")func main(){hellohandler := &handler.HelloService{}_ = server_proxy.RegisterHelloService(hellohandler)listener, err := net.Listen("tcp", ":1234")if err != nil {panic("监听端口失败")}conn, err := listener.Accept()if err != nil {panic("建立链接失败")}rpc.ServeConn(conn)}
4. 客户端代理
package client_proxyimport "net/rpc"const HelloServiceName = "handler/HelloService"type HelloServiceClient struct{*rpc.Client}func NewClient(address string) HelloServiceClient {conn, err := rpc.Dial("tcp", address)if err != nil {panic("连接服务器错误")}return HelloServiceClient{conn}}func (c *HelloServiceClient) Hello(request string, reply *string) error {err := c.Call(HelloServiceName+".Hello", request, reply)if err != nil {return err}return nil}
5. 客户端
package mainimport ("fmt""start/rpc_ch01/client_proxy")func main(){client := client_proxy.NewClient("localhost:1234")var reply stringerr := client.Hello("bobby",&reply)if err != nil {panic("调用失败")}fmt.Println(reply)}
