1
0
mirror of https://github.com/gusaul/grpcox.git synced 2025-01-26 06:14:40 +00:00
grpcox/vendor/github.com/jhump/protoreflect/grpcreflect/server.go
2019-03-25 10:47:41 +07:00

62 lines
2.1 KiB
Go

package grpcreflect
import (
"fmt"
"google.golang.org/grpc"
"github.com/jhump/protoreflect/desc"
)
// LoadServiceDescriptors loads the service descriptors for all services exposed by the
// given GRPC server.
func LoadServiceDescriptors(s *grpc.Server) (map[string]*desc.ServiceDescriptor, error) {
descs := map[string]*desc.ServiceDescriptor{}
for name, info := range s.GetServiceInfo() {
file, ok := info.Metadata.(string)
if !ok {
return nil, fmt.Errorf("service %q has unexpected metadata: expecting a string; got %v", name, info.Metadata)
}
fd, err := desc.LoadFileDescriptor(file)
if err != nil {
return nil, err
}
d := fd.FindSymbol(name)
if d == nil {
return nil, fmt.Errorf("file descriptor for %q has no element named %q", file, name)
}
sd, ok := d.(*desc.ServiceDescriptor)
if !ok {
return nil, fmt.Errorf("file descriptor for %q has incorrect element named %q: expecting a service descriptor; got %v", file, name, d)
}
descs[name] = sd
}
return descs, nil
}
// LoadServiceDescriptor loads a rich descriptor for a given service description
// generated by protoc-gen-go. Generated code contains an unexported symbol with
// a name like "_<Service>_serviceDesc" which is the service's description. It
// is used internally to register a service implementation with a GRPC server.
// But it can also be used by this package to retrieve the rich descriptor for
// the service.
func LoadServiceDescriptor(svc *grpc.ServiceDesc) (*desc.ServiceDescriptor, error) {
file, ok := svc.Metadata.(string)
if !ok {
return nil, fmt.Errorf("service %q has unexpected metadata: expecting a string; got %v", svc.ServiceName, svc.Metadata)
}
fd, err := desc.LoadFileDescriptor(file)
if err != nil {
return nil, err
}
d := fd.FindSymbol(svc.ServiceName)
if d == nil {
return nil, fmt.Errorf("file descriptor for %q has no element named %q", file, svc.ServiceName)
}
sd, ok := d.(*desc.ServiceDescriptor)
if !ok {
return nil, fmt.Errorf("file descriptor for %q has incorrect element named %q: expecting a service descriptor; got %v", file, svc.ServiceName, d)
}
return sd, nil
}