github.com/cloudwego/kitex@v0.9.0/server/invoke.go (about) 1 /* 2 * Copyright 2021 CloudWeGo Authors 3 * 4 * Licensed under the Apache License, Version 2.0 (the "License"); 5 * you may not use this file except in compliance with the License. 6 * You may obtain a copy of the License at 7 * 8 * http://www.apache.org/licenses/LICENSE-2.0 9 * 10 * Unless required by applicable law or agreed to in writing, software 11 * distributed under the License is distributed on an "AS IS" BASIS, 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 * See the License for the specific language governing permissions and 14 * limitations under the License. 15 */ 16 17 package server 18 19 // Invoker is for calling handler function wrapped by Kitex suites without connection. 20 21 import ( 22 "errors" 23 24 internal_server "github.com/cloudwego/kitex/internal/server" 25 "github.com/cloudwego/kitex/pkg/remote" 26 "github.com/cloudwego/kitex/pkg/remote/bound" 27 "github.com/cloudwego/kitex/pkg/remote/trans/invoke" 28 "github.com/cloudwego/kitex/pkg/serviceinfo" 29 ) 30 31 // InvokeCaller is the abstraction for invoker call. 32 type InvokeCaller interface { 33 Call(invoke.Message) error 34 } 35 36 // Invoker is the abstraction for invoker. 37 type Invoker interface { 38 RegisterService(svcInfo *serviceinfo.ServiceInfo, handler interface{}, opts ...RegisterOption) error 39 Init() (err error) 40 InvokeCaller 41 } 42 43 type tInvoker struct { 44 invoke.Handler 45 *server 46 } 47 48 // NewInvoker creates new Invoker. 49 func NewInvoker(opts ...Option) Invoker { 50 s := &server{ 51 opt: internal_server.NewOptions(opts), 52 svcs: newServices(), 53 } 54 s.init() 55 return &tInvoker{ 56 server: s, 57 } 58 } 59 60 // Init does initialization job for invoker. 61 func (s *tInvoker) Init() (err error) { 62 if len(s.server.svcs.svcMap) == 0 { 63 return errors.New("run: no service. Use RegisterService to set one") 64 } 65 s.initBasicRemoteOption() 66 // for server trans info handler 67 if len(s.server.opt.MetaHandlers) > 0 { 68 transInfoHdlr := bound.NewTransMetaHandler(s.server.opt.MetaHandlers) 69 doAddBoundHandler(transInfoHdlr, s.server.opt.RemoteOpt) 70 } 71 s.Lock() 72 s.Handler, err = s.newInvokeHandler() 73 s.Unlock() 74 if err != nil { 75 return err 76 } 77 for i := range onServerStart { 78 go onServerStart[i]() 79 } 80 return nil 81 } 82 83 // Call implements the InvokeCaller interface. 84 func (s *tInvoker) Call(msg invoke.Message) error { 85 return s.Handler.Call(msg) 86 } 87 88 func (s *tInvoker) newInvokeHandler() (handler invoke.Handler, err error) { 89 opt := s.server.opt.RemoteOpt 90 tf := invoke.NewIvkTransHandlerFactory() 91 hdlr, err := tf.NewTransHandler(opt) 92 if err != nil { 93 return nil, err 94 } 95 hdlr.(remote.InvokeHandleFuncSetter).SetInvokeHandleFunc(s.eps) 96 pl := remote.NewTransPipeline(hdlr) 97 hdlr.SetPipeline(pl) 98 for _, ib := range opt.Inbounds { 99 pl.AddInboundHandler(ib) 100 } 101 for _, ob := range opt.Outbounds { 102 pl.AddOutboundHandler(ob) 103 } 104 return invoke.NewIvkHandler(opt, pl) 105 }