Documentation ¶
Overview ¶
Package orion is a small lightweight framework written around grpc with the aim to shorten time to build microservices
Source code for Orion can be found at https://github.com/carousell/Orion
It is derived from 'Framework' a small microservices framework written and used inside https://carousell.com, It comes with a number of sensible defaults such as zipkin tracing, hystrix, live reload of configuration, etc.
Why Orion ¶
Orion uses protocol-buffers definitions (https://developers.google.com/protocol-buffers/docs/proto3) using gRPC and orion proto plugin as base for building services.
Using proto definitions as our service base allows us to define clean contracts that everyone can understand and enables auto generation of client code.
You define your services as a proto definition, for example
service SimpleService{ rpc Echo (EchoRequest) returns (EchoResponse){ } } message EchoRequest { string msg = 1; } message EchoResponse { string msg = 1; }
The above definition represents a service named 'SimpleService' which accepts 'EchoRequest' and returns 'EchoResponse' at 'Echo' endpoint.
After you have generated the code from protoc (using grpc and orion plugin), you need to implement the server interface generated by gRPC, orion uses this service definition and enables HTTP/gRPC calls to be made to the same service implementation.
How do i use it ¶
Lets go through the example defined at https://github.com/carousell/Orion/tree/master/example/simple , It covers the minimum required implementation for orion. It has the following structure
. ├── cmd │ ├── client │ │ └── client.go │ └── server │ └── server.go ├── service │ └── service.go └── simple_proto ├── generate.sh └── simple.proto
First we define the proto 'simple_proto/simple.proto' as
syntax = "proto3"; package simple_proto; service SimpleService{ rpc Echo (EchoRequest) returns (EchoResponse){ } } message EchoRequest { string msg = 1; } message EchoResponse { string msg = 1; }
The above definition represents a service named 'SimpleService' which accepts 'EchoRequest' and returns 'EchoResponse' at 'Echo' endpoint.
Now we can execute 'generate.sh' which contains
protoc -I . simple.proto --go_out=plugins=grpc:. --orion_out=.
Running this command generates the following file in the simple_proto directory:
. ├── generate.sh ├── simple.pb.go ├── simple.proto └── simple.proto.orion.pb.go
This contains:
All the protocol buffer code to populate, serialize, and retrieve our request and response message types (simple.pb.go) An interface type (or stub) for clients to call with the methods defined in the SimpleService (simple.pb.go) An interface type for servers to implement, also with the methods defined in the SimpleService (simple.pb.go) Registration function for Orion (simple.proto.orion.pb.go)
Whats Incuded ¶
Orion comes included with.
Hystrix (http://github.com/afex/hystrix-go) Zipkin (http://github.com/opentracing/opentracing-go) NewRelic (http://github.com/newrelic/go-agent) Prometheus (http://github.com/grpc-ecosystem/go-grpc-prometheus) Pprof (https://golang.org/pkg/net/http/pprof/)) Configuration (http://github.com/spf13/viper) Live Configuration Reload (http://github.com/carousell/Orion/utils/listenerutils) And much more...
Getting Started ¶
First follow the install guide at https://github.com/carousell/Orion/blob/master/README.md
Index ¶
- Constants
- Variables
- func AddConfigPath(path ...string)
- func RegisterDecoder(svr Server, serviceName, method string, decoder Decoder)
- func RegisterDefaultDecoder(svr Server, serviceName string, decoder Decoder)
- func RegisterDefaultEncoder(svr Server, serviceName string, encoder Encoder)
- func RegisterEncoder(svr Server, serviceName, method, httpMethod, path string, encoder Encoder)
- func RegisterEncoders(svr Server, serviceName, method string, httpMethod []string, path string, ...)
- func RegisterHandler(svr Server, serviceName, method string, path string, handler HTTPHandler)
- func RegisterMethodOption(svr Server, serviceName, method, option string)
- func RegisterMiddleware(svr Server, serviceName, method string, middleware ...string)
- func ResetConfigPath()
- type Config
- type Decoder
- type DefaultServerImpl
- func (d *DefaultServerImpl) AddDecoder(serviceName, method string, decoder handlers.Decoder)
- func (d *DefaultServerImpl) AddDefaultDecoder(serviceName string, decoder Decoder)
- func (d *DefaultServerImpl) AddDefaultEncoder(serviceName string, encoder Encoder)
- func (d *DefaultServerImpl) AddEncoder(serviceName, method string, httpMethod []string, path string, ...)
- func (d *DefaultServerImpl) AddHTTPHandler(serviceName string, method string, path string, handler handlers.HTTPHandler)
- func (d *DefaultServerImpl) AddInitializers(ins ...Initializer)
- func (d *DefaultServerImpl) AddMiddleware(serviceName string, method string, middlewares ...string)
- func (d *DefaultServerImpl) AddOption(serviceName, method, option string)
- func (d *DefaultServerImpl) GetConfig() map[string]interface{}
- func (d *DefaultServerImpl) GetOrionConfig() Config
- func (d *DefaultServerImpl) RegisterService(sd *grpc.ServiceDesc, sf interface{}) error
- func (d *DefaultServerImpl) Start()
- func (d *DefaultServerImpl) Stop(timeout time.Duration) error
- func (d *DefaultServerImpl) Wait() error
- type DefaultServerOption
- type Encoder
- type FactoryParams
- type HTTPHandler
- type HystrixConfig
- type Initializer
- type NewRelicConfig
- type Server
- type ServiceFactory
- type ServiceFactoryV2
- type ZipkinConfig
Constants ¶
const ( //ProtoGenVersion1_0 is the version of protoc-gen-orion plugin compatible with current code base ProtoGenVersion1_0 = true //BANNER is the orion banner text BANNER = `` /* 173-byte string literal not displayed */ )
Variables ¶
var ( //ErrNil when the passed argument is nil ErrNil = errors.New("nil argument passed") //ErrNotServiceFactory when passed argument is not a service factory ErrNotServiceFactory = errors.New("you need to pass either a ServiceFactory or ServiceFactoryV2") )
var ( //DefaultInitializers are the initializers applied by orion as default DefaultInitializers = []Initializer{ HystrixInitializer(), ZipkinInitializer(), NewRelicInitializer(), PrometheusInitializer(), PprofInitializer(), ErrorLoggingInitializer(), } )
Functions ¶
func AddConfigPath ¶
func AddConfigPath(path ...string)
AddConfigPath adds a config path from where orion tries to read config values
func RegisterDecoder ¶
RegisterDecoder allows for registering an HTTP request decoder to a method Note: this is normally called from protoc-gen-orion autogenerated files
func RegisterDefaultDecoder ¶
RegisterDefaultDecoder allows for registering an HTTP request decoder to arbitrary urls for the entire service Note: this is normally called from protoc-gen-orion autogenerated files
func RegisterDefaultEncoder ¶
RegisterDefaultEncoder allows for registering an HTTP request encoder to arbitrary urls for the entire service Note: this is normally called from protoc-gen-orion autogenerated files
func RegisterEncoder ¶
RegisterEncoder allows for registering an HTTP request encoder to arbitrary urls Note: this is normally called from protoc-gen-orion autogenerated files
func RegisterEncoders ¶
func RegisterEncoders(svr Server, serviceName, method string, httpMethod []string, path string, encoder Encoder)
RegisterEncoders allows for registering an HTTP request encoder to arbitrary urls Note: this is normally called from protoc-gen-orion autogenerated files
func RegisterHandler ¶
func RegisterHandler(svr Server, serviceName, method string, path string, handler HTTPHandler)
RegisterHandler allows registering an HTTP handler for a given path Note: this is normally called from protoc-gen-orion autogenerated files
func RegisterMethodOption ¶
RegisterMethodOption allows for registering an handler option to a particular method Note: this is normally called from protoc-gen-orion autogenerated files
func RegisterMiddleware ¶
RegisterMiddleware allows for registering middlewares to a particular method Note: this is normally called from protoc-gen-orion autogenerated files
Types ¶
type Config ¶
type Config struct { //OrionServerName is the name of this orion server that is tracked OrionServerName string // GRPCOnly tells orion not to build HTTP/1.1 server and only initializes gRPC server GRPCOnly bool //HTTPOnly tells orion not to build gRPC server and only initializes HTTP/1.1 server HTTPOnly bool // HTTPPort is the port to bind for HTTP requests HTTPPort string // GRPCPost id the port to bind for gRPC requests GRPCPort string //PprofPort is the port to use for pprof PProfport string // HotReload when set reloads the service when it receives SIGHUP HotReload bool //EnableProtoURL adds gRPC generated urls in HTTP handler EnableProtoURL bool //EnablePrometheus enables prometheus metric for services on path '/metrics' on pprof port EnablePrometheus bool //EnablePrometheusHistograms enables request histograms for services //ref: https://github.com/grpc-ecosystem/go-grpc-prometheus#histograms EnablePrometheusHistogram bool //HystrixConfig is the configuration options for hystrix HystrixConfig HystrixConfig //ZipkinConfig is the configuration options for zipkin ZipkinConfig ZipkinConfig //NewRelicConfig is the configuration options for new relic NewRelicConfig NewRelicConfig //RollbarToken is the token to be used in rollbar RollbarToken string //SentryDSN is the token used by sentry for error reporting SentryDSN string //Env is the environment this service is running in Env string // DefaultJSONPB sets jsonpb as the encoder/decoder for application/json request/response bodies DefaultJSONPB bool // DisableDefaultInterceptors disables the default interceptors for all handlers DisableDefaultInterceptors bool // Receive message Size is used to update the default limit of message that can be received MaxRecvMsgSize int }
Config is the configuration used by Orion core
func BuildDefaultConfig ¶
BuildDefaultConfig builds a default config object for Orion
type DefaultServerImpl ¶
type DefaultServerImpl struct {
// contains filtered or unexported fields
}
DefaultServerImpl provides a default implementation of orion.Server this can be embedded in custom orion.Server implementations
func (*DefaultServerImpl) AddDecoder ¶
func (d *DefaultServerImpl) AddDecoder(serviceName, method string, decoder handlers.Decoder)
AddDecoder is the implementation of handlers.Decodable
func (*DefaultServerImpl) AddDefaultDecoder ¶
func (d *DefaultServerImpl) AddDefaultDecoder(serviceName string, decoder Decoder)
AddDefaultDecoder is the implementation of handlers.Decodable
func (*DefaultServerImpl) AddDefaultEncoder ¶
func (d *DefaultServerImpl) AddDefaultEncoder(serviceName string, encoder Encoder)
AddDefaultEncoder is the implementation of handlers.Encodable
func (*DefaultServerImpl) AddEncoder ¶
func (d *DefaultServerImpl) AddEncoder(serviceName, method string, httpMethod []string, path string, encoder handlers.Encoder)
AddEncoder is the implementation of handlers.Encodable
func (*DefaultServerImpl) AddHTTPHandler ¶
func (d *DefaultServerImpl) AddHTTPHandler(serviceName string, method string, path string, handler handlers.HTTPHandler)
AddHTTPHandler is the implementation of handlers.HTTPInterceptor
func (*DefaultServerImpl) AddInitializers ¶
func (d *DefaultServerImpl) AddInitializers(ins ...Initializer)
AddInitializers adds the initializers to orion server
func (*DefaultServerImpl) AddMiddleware ¶
func (d *DefaultServerImpl) AddMiddleware(serviceName string, method string, middlewares ...string)
AddMiddleware adds middlewares for particular service/method
func (*DefaultServerImpl) AddOption ¶
func (d *DefaultServerImpl) AddOption(serviceName, method, option string)
AddOption adds a option for the particular service/method
func (*DefaultServerImpl) GetConfig ¶
func (d *DefaultServerImpl) GetConfig() map[string]interface{}
GetConfig returns current config as parsed from the file/defaults
func (*DefaultServerImpl) GetOrionConfig ¶
func (d *DefaultServerImpl) GetOrionConfig() Config
GetOrionConfig returns current orion config NOTE: this config can not be modifies
func (*DefaultServerImpl) RegisterService ¶
func (d *DefaultServerImpl) RegisterService(sd *grpc.ServiceDesc, sf interface{}) error
RegisterService registers a service from a generated proto file Note: this is only called from code generated by orion plugin
func (*DefaultServerImpl) Stop ¶
func (d *DefaultServerImpl) Stop(timeout time.Duration) error
Stop stops the server
func (*DefaultServerImpl) Wait ¶
func (d *DefaultServerImpl) Wait() error
Wait waits for all the serving servers to quit
type DefaultServerOption ¶
type DefaultServerOption interface {
// contains filtered or unexported methods
}
func WithGrpcUnknownHandler ¶
func WithGrpcUnknownHandler(grpcUnknownServiceHandler grpc.StreamHandler) DefaultServerOption
WithGrpcUnknownHandler returns a DefaultServerOption which sets UnknownServiceHandler option in grpc server
type FactoryParams ¶
type FactoryParams struct { // ServiceName contains the proto service name ServiceName string // Version is a counter that is incremented every time a new service object is requested // NOTE: version might rollover in long running services Version uint64 }
FactoryParams are the parameters used by the ServiceFactoryV2
type HystrixConfig ¶
type HystrixConfig struct { //Port is the port to start hystrix stream handler on Port string //CommandConfig is configuration for individual commands CommandConfig map[string]hystrix.CommandConfig //StatsdAddr is the address of the statsd hosts to send hystrix data to StatsdAddr string // DefaultTimeout is how long to wait for command to complete, in milliseconds DefaultTimeout int // DefaultMaxConcurrent is how many commands of the same type can run at the same time DefaultMaxConcurrent int // DefaultVolumeThreshold is the minimum number of requests needed before a circuit can be tripped due to health DefaultVolumeThreshold int // DefaultSleepWindow is how long, in milliseconds, to wait after a circuit opens before testing for recovery DefaultSleepWindow int // DefaultErrorPercentThreshold causes circuits to open once the rolling measure of errors exceeds this percent of requests DefaultErrorPercentThreshold int }
HystrixConfig is configuration used by hystrix
func BuildDefaultHystrixConfig ¶
func BuildDefaultHystrixConfig() HystrixConfig
BuildDefaultHystrixConfig builds a default config for hystrix
type Initializer ¶
Initializer is the interface needed to be implemented by custom initializers
func ErrorLoggingInitializer ¶
func ErrorLoggingInitializer() Initializer
ErrorLoggingInitializer returns a Initializer implementation for error notifier
func HystrixInitializer ¶
func HystrixInitializer() Initializer
HystrixInitializer returns a Initializer implementation for Hystrix
func NewRelicInitializer ¶
func NewRelicInitializer() Initializer
NewRelicInitializer returns a Initializer implementation for NewRelic
func PprofInitializer ¶
func PprofInitializer() Initializer
PprofInitializer returns a Initializer implementation for Pprof
func PrometheusInitializer ¶
func PrometheusInitializer() Initializer
PrometheusInitializer returns a Initializer implementation for Prometheus
func ZipkinInitializer ¶
func ZipkinInitializer() Initializer
ZipkinInitializer returns a Initializer implementation for Zipkin
type NewRelicConfig ¶
type NewRelicConfig struct { APIKey string ServiceName string //HttpTxNameType decides the transaction name logged in NR. Options are "fullmethod" (default), "method" , "route". HttpTxNameType string IncludeAttributes []string ExcludeAttributes []string }
NewRelicConfig is the configuration for newrelic
func BuildDefaultNewRelicConfig ¶
func BuildDefaultNewRelicConfig() NewRelicConfig
BuildDefaultNewRelicConfig builds a default config for newrelic
type Server ¶
type Server interface { //Start starts the orion server, this is non blocking call Start() //RegisterService registers the service to origin server RegisterService(sd *grpc.ServiceDesc, sf interface{}) error //Wait waits for the Server loop to exit Wait() error //Stop stops the Server Stop(timeout time.Duration) error //GetOrionConfig returns current orion config GetOrionConfig() Config //GetConfig returns current config as parsed from the file/defaults GetConfig() map[string]interface{} //AddInitializers adds the initializers to orion server AddInitializers(ins ...Initializer) }
Server is the interface that needs to be implemented by any orion server 'DefaultServerImpl' should be enough for most users.
func GetDefaultServer ¶
func GetDefaultServer(name string, opts ...DefaultServerOption) Server
GetDefaultServer returns a default server object that can be directly used to start orion server
func GetDefaultServerWithConfig ¶
GetDefaultServerWithConfig returns a default server object that uses provided configuration
type ServiceFactory ¶
type ServiceFactory interface { // NewService function receives the server object for which service has to be initialized NewService(Server) interface{} //DisposeService function disposes the service object DisposeService(svc interface{}) }
ServiceFactory is the interface that need to be implemented by client that provides with a new service object
type ServiceFactoryV2 ¶
type ServiceFactoryV2 interface { // NewService function receives the server object for which service has to be initialized NewService(svr Server, params FactoryParams) interface{} //DisposeService function disposes the service object DisposeService(svc interface{}, params FactoryParams) }
ServiceFactoryV2 is the interface that needs to be implemented by client that provides a new service object for multiple services this allows a single struct to implement multiple services
func ToServiceFactoryV2 ¶
func ToServiceFactoryV2(sf interface{}) (ServiceFactoryV2, error)
ToServiceFactoryV2 converts ServiceFactory to ServiceFactoryV2
type ZipkinConfig ¶
type ZipkinConfig struct { //Addr is the address of the zipkin collector Addr string }
ZipkinConfig is the configuration for the zipkin collector
func BuildDefaultZipkinConfig ¶
func BuildDefaultZipkinConfig() ZipkinConfig
BuildDefaultZipkinConfig builds a default config for zipkin