Welcome to mirror list, hosted at ThFree Co, Russian Federation.

gitlab.com/gitlab-org/gitlab-pages.git - Unnamed repository; edit this file 'description' to name the repository.
summaryrefslogtreecommitdiff
path: root/vendor
diff options
context:
space:
mode:
authorJacob Vosmaer <jacob@gitlab.com>2018-04-12 16:42:12 +0300
committerJacob Vosmaer <jacob@gitlab.com>2018-04-12 16:42:12 +0300
commit2195e6ca9544764cf0b64daafd11d591de1ae4ea (patch)
treebee50cc9d62936930584e81e74a2c20d007ae083 /vendor
parent1429da85cb13d6d2105b475dac600832d756affb (diff)
Add more gRPC dependencies
Diffstat (limited to 'vendor')
-rw-r--r--vendor/github.com/golang/protobuf/jsonpb/jsonpb.go1083
-rw-r--r--vendor/github.com/golang/protobuf/ptypes/struct/struct.pb.go380
-rw-r--r--vendor/github.com/golang/protobuf/ptypes/struct/struct.proto96
-rw-r--r--vendor/github.com/grpc-ecosystem/go-grpc-middleware/DOC.md166
-rw-r--r--vendor/github.com/grpc-ecosystem/go-grpc-middleware/Gopkg.lock123
-rw-r--r--vendor/github.com/grpc-ecosystem/go-grpc-middleware/Gopkg.toml35
-rw-r--r--vendor/github.com/grpc-ecosystem/go-grpc-middleware/LICENSE201
-rw-r--r--vendor/github.com/grpc-ecosystem/go-grpc-middleware/README.md86
-rw-r--r--vendor/github.com/grpc-ecosystem/go-grpc-middleware/auth/DOC.md148
-rw-r--r--vendor/github.com/grpc-ecosystem/go-grpc-middleware/auth/README.md148
-rw-r--r--vendor/github.com/grpc-ecosystem/go-grpc-middleware/auth/auth.go67
-rw-r--r--vendor/github.com/grpc-ecosystem/go-grpc-middleware/auth/doc.go20
-rw-r--r--vendor/github.com/grpc-ecosystem/go-grpc-middleware/auth/metadata.go38
-rw-r--r--vendor/github.com/grpc-ecosystem/go-grpc-middleware/chain.go183
-rw-r--r--vendor/github.com/grpc-ecosystem/go-grpc-middleware/doc.go69
-rw-r--r--vendor/github.com/grpc-ecosystem/go-grpc-middleware/logging/DOC.md91
-rw-r--r--vendor/github.com/grpc-ecosystem/go-grpc-middleware/logging/README.md91
-rw-r--r--vendor/github.com/grpc-ecosystem/go-grpc-middleware/logging/common.go35
-rw-r--r--vendor/github.com/grpc-ecosystem/go-grpc-middleware/logging/doc.go35
-rw-r--r--vendor/github.com/grpc-ecosystem/go-grpc-middleware/logging/logrus/DOC.md391
-rw-r--r--vendor/github.com/grpc-ecosystem/go-grpc-middleware/logging/logrus/README.md391
-rw-r--r--vendor/github.com/grpc-ecosystem/go-grpc-middleware/logging/logrus/client_interceptors.go65
-rw-r--r--vendor/github.com/grpc-ecosystem/go-grpc-middleware/logging/logrus/context.go19
-rw-r--r--vendor/github.com/grpc-ecosystem/go-grpc-middleware/logging/logrus/ctxlogrus/DOC.md93
-rw-r--r--vendor/github.com/grpc-ecosystem/go-grpc-middleware/logging/logrus/ctxlogrus/README.md58
-rw-r--r--vendor/github.com/grpc-ecosystem/go-grpc-middleware/logging/logrus/ctxlogrus/context.go65
-rw-r--r--vendor/github.com/grpc-ecosystem/go-grpc-middleware/logging/logrus/ctxlogrus/doc.go14
-rw-r--r--vendor/github.com/grpc-ecosystem/go-grpc-middleware/logging/logrus/ctxlogrus/noop.go16
-rw-r--r--vendor/github.com/grpc-ecosystem/go-grpc-middleware/logging/logrus/doc.go67
-rw-r--r--vendor/github.com/grpc-ecosystem/go-grpc-middleware/logging/logrus/grpclogger.go15
-rw-r--r--vendor/github.com/grpc-ecosystem/go-grpc-middleware/logging/logrus/options.go185
-rw-r--r--vendor/github.com/grpc-ecosystem/go-grpc-middleware/logging/logrus/payload_interceptors.go144
-rw-r--r--vendor/github.com/grpc-ecosystem/go-grpc-middleware/logging/logrus/server_interceptors.go129
-rw-r--r--vendor/github.com/grpc-ecosystem/go-grpc-middleware/makefile19
-rw-r--r--vendor/github.com/grpc-ecosystem/go-grpc-middleware/recovery/DOC.md107
-rw-r--r--vendor/github.com/grpc-ecosystem/go-grpc-middleware/recovery/README.md107
-rw-r--r--vendor/github.com/grpc-ecosystem/go-grpc-middleware/recovery/doc.go15
-rw-r--r--vendor/github.com/grpc-ecosystem/go-grpc-middleware/recovery/interceptors.go48
-rw-r--r--vendor/github.com/grpc-ecosystem/go-grpc-middleware/recovery/options.go32
-rw-r--r--vendor/github.com/grpc-ecosystem/go-grpc-middleware/tags/DOC.md188
-rw-r--r--vendor/github.com/grpc-ecosystem/go-grpc-middleware/tags/README.md188
-rw-r--r--vendor/github.com/grpc-ecosystem/go-grpc-middleware/tags/context.go78
-rw-r--r--vendor/github.com/grpc-ecosystem/go-grpc-middleware/tags/doc.go22
-rw-r--r--vendor/github.com/grpc-ecosystem/go-grpc-middleware/tags/fieldextractor.go85
-rw-r--r--vendor/github.com/grpc-ecosystem/go-grpc-middleware/tags/interceptors.go83
-rw-r--r--vendor/github.com/grpc-ecosystem/go-grpc-middleware/tags/logrus/context.go25
-rw-r--r--vendor/github.com/grpc-ecosystem/go-grpc-middleware/tags/options.go44
-rw-r--r--vendor/github.com/grpc-ecosystem/go-grpc-middleware/util/metautils/DOC.md114
-rw-r--r--vendor/github.com/grpc-ecosystem/go-grpc-middleware/util/metautils/README.md114
-rw-r--r--vendor/github.com/grpc-ecosystem/go-grpc-middleware/util/metautils/doc.go19
-rw-r--r--vendor/github.com/grpc-ecosystem/go-grpc-middleware/util/metautils/nicemd.go126
-rw-r--r--vendor/github.com/grpc-ecosystem/go-grpc-middleware/util/metautils/single_key.go22
-rw-r--r--vendor/github.com/grpc-ecosystem/go-grpc-middleware/wrappers.go29
-rw-r--r--vendor/github.com/grpc-ecosystem/go-grpc-prometheus/LICENSE201
-rw-r--r--vendor/github.com/grpc-ecosystem/go-grpc-prometheus/README.md247
-rw-r--r--vendor/github.com/grpc-ecosystem/go-grpc-prometheus/client.go39
-rw-r--r--vendor/github.com/grpc-ecosystem/go-grpc-prometheus/client_metrics.go166
-rw-r--r--vendor/github.com/grpc-ecosystem/go-grpc-prometheus/client_reporter.go46
-rw-r--r--vendor/github.com/grpc-ecosystem/go-grpc-prometheus/makefile16
-rw-r--r--vendor/github.com/grpc-ecosystem/go-grpc-prometheus/metric_options.go35
-rw-r--r--vendor/github.com/grpc-ecosystem/go-grpc-prometheus/server.go48
-rw-r--r--vendor/github.com/grpc-ecosystem/go-grpc-prometheus/server_metrics.go202
-rw-r--r--vendor/github.com/grpc-ecosystem/go-grpc-prometheus/server_reporter.go46
-rw-r--r--vendor/github.com/grpc-ecosystem/go-grpc-prometheus/util.go50
-rw-r--r--vendor/gitlab.com/gitlab-org/gitaly/LICENSE21
-rw-r--r--vendor/gitlab.com/gitlab-org/gitaly/NOTICE2496
-rw-r--r--vendor/gitlab.com/gitlab-org/gitaly/auth/rpccredentials.go25
-rw-r--r--vendor/gitlab.com/gitlab-org/gitaly/auth/token.go45
-rw-r--r--vendor/google.golang.org/grpc/health/grpc_health_v1/health.pb.go190
-rw-r--r--vendor/google.golang.org/grpc/health/grpc_health_v1/health.proto34
-rw-r--r--vendor/google.golang.org/grpc/health/health.go72
-rw-r--r--vendor/vendor.json94
72 files changed, 10285 insertions, 0 deletions
diff --git a/vendor/github.com/golang/protobuf/jsonpb/jsonpb.go b/vendor/github.com/golang/protobuf/jsonpb/jsonpb.go
new file mode 100644
index 00000000..110ae138
--- /dev/null
+++ b/vendor/github.com/golang/protobuf/jsonpb/jsonpb.go
@@ -0,0 +1,1083 @@
+// Go support for Protocol Buffers - Google's data interchange format
+//
+// Copyright 2015 The Go Authors. All rights reserved.
+// https://github.com/golang/protobuf
+//
+// Redistribution and use in source and binary forms, with or without
+// modification, are permitted provided that the following conditions are
+// met:
+//
+// * Redistributions of source code must retain the above copyright
+// notice, this list of conditions and the following disclaimer.
+// * Redistributions in binary form must reproduce the above
+// copyright notice, this list of conditions and the following disclaimer
+// in the documentation and/or other materials provided with the
+// distribution.
+// * Neither the name of Google Inc. nor the names of its
+// contributors may be used to endorse or promote products derived from
+// this software without specific prior written permission.
+//
+// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
+// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
+// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
+// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
+// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+
+/*
+Package jsonpb provides marshaling and unmarshaling between protocol buffers and JSON.
+It follows the specification at https://developers.google.com/protocol-buffers/docs/proto3#json.
+
+This package produces a different output than the standard "encoding/json" package,
+which does not operate correctly on protocol buffers.
+*/
+package jsonpb
+
+import (
+ "bytes"
+ "encoding/json"
+ "errors"
+ "fmt"
+ "io"
+ "math"
+ "reflect"
+ "sort"
+ "strconv"
+ "strings"
+ "time"
+
+ "github.com/golang/protobuf/proto"
+
+ stpb "github.com/golang/protobuf/ptypes/struct"
+)
+
+// Marshaler is a configurable object for converting between
+// protocol buffer objects and a JSON representation for them.
+type Marshaler struct {
+ // Whether to render enum values as integers, as opposed to string values.
+ EnumsAsInts bool
+
+ // Whether to render fields with zero values.
+ EmitDefaults bool
+
+ // A string to indent each level by. The presence of this field will
+ // also cause a space to appear between the field separator and
+ // value, and for newlines to be appear between fields and array
+ // elements.
+ Indent string
+
+ // Whether to use the original (.proto) name for fields.
+ OrigName bool
+
+ // A custom URL resolver to use when marshaling Any messages to JSON.
+ // If unset, the default resolution strategy is to extract the
+ // fully-qualified type name from the type URL and pass that to
+ // proto.MessageType(string).
+ AnyResolver AnyResolver
+}
+
+// AnyResolver takes a type URL, present in an Any message, and resolves it into
+// an instance of the associated message.
+type AnyResolver interface {
+ Resolve(typeUrl string) (proto.Message, error)
+}
+
+func defaultResolveAny(typeUrl string) (proto.Message, error) {
+ // Only the part of typeUrl after the last slash is relevant.
+ mname := typeUrl
+ if slash := strings.LastIndex(mname, "/"); slash >= 0 {
+ mname = mname[slash+1:]
+ }
+ mt := proto.MessageType(mname)
+ if mt == nil {
+ return nil, fmt.Errorf("unknown message type %q", mname)
+ }
+ return reflect.New(mt.Elem()).Interface().(proto.Message), nil
+}
+
+// JSONPBMarshaler is implemented by protobuf messages that customize the
+// way they are marshaled to JSON. Messages that implement this should
+// also implement JSONPBUnmarshaler so that the custom format can be
+// parsed.
+type JSONPBMarshaler interface {
+ MarshalJSONPB(*Marshaler) ([]byte, error)
+}
+
+// JSONPBUnmarshaler is implemented by protobuf messages that customize
+// the way they are unmarshaled from JSON. Messages that implement this
+// should also implement JSONPBMarshaler so that the custom format can be
+// produced.
+type JSONPBUnmarshaler interface {
+ UnmarshalJSONPB(*Unmarshaler, []byte) error
+}
+
+// Marshal marshals a protocol buffer into JSON.
+func (m *Marshaler) Marshal(out io.Writer, pb proto.Message) error {
+ writer := &errWriter{writer: out}
+ return m.marshalObject(writer, pb, "", "")
+}
+
+// MarshalToString converts a protocol buffer object to JSON string.
+func (m *Marshaler) MarshalToString(pb proto.Message) (string, error) {
+ var buf bytes.Buffer
+ if err := m.Marshal(&buf, pb); err != nil {
+ return "", err
+ }
+ return buf.String(), nil
+}
+
+type int32Slice []int32
+
+var nonFinite = map[string]float64{
+ `"NaN"`: math.NaN(),
+ `"Infinity"`: math.Inf(1),
+ `"-Infinity"`: math.Inf(-1),
+}
+
+// For sorting extensions ids to ensure stable output.
+func (s int32Slice) Len() int { return len(s) }
+func (s int32Slice) Less(i, j int) bool { return s[i] < s[j] }
+func (s int32Slice) Swap(i, j int) { s[i], s[j] = s[j], s[i] }
+
+type wkt interface {
+ XXX_WellKnownType() string
+}
+
+// marshalObject writes a struct to the Writer.
+func (m *Marshaler) marshalObject(out *errWriter, v proto.Message, indent, typeURL string) error {
+ if jsm, ok := v.(JSONPBMarshaler); ok {
+ b, err := jsm.MarshalJSONPB(m)
+ if err != nil {
+ return err
+ }
+ if typeURL != "" {
+ // we are marshaling this object to an Any type
+ var js map[string]*json.RawMessage
+ if err = json.Unmarshal(b, &js); err != nil {
+ return fmt.Errorf("type %T produced invalid JSON: %v", v, err)
+ }
+ turl, err := json.Marshal(typeURL)
+ if err != nil {
+ return fmt.Errorf("failed to marshal type URL %q to JSON: %v", typeURL, err)
+ }
+ js["@type"] = (*json.RawMessage)(&turl)
+ if b, err = json.Marshal(js); err != nil {
+ return err
+ }
+ }
+
+ out.write(string(b))
+ return out.err
+ }
+
+ s := reflect.ValueOf(v).Elem()
+
+ // Handle well-known types.
+ if wkt, ok := v.(wkt); ok {
+ switch wkt.XXX_WellKnownType() {
+ case "DoubleValue", "FloatValue", "Int64Value", "UInt64Value",
+ "Int32Value", "UInt32Value", "BoolValue", "StringValue", "BytesValue":
+ // "Wrappers use the same representation in JSON
+ // as the wrapped primitive type, ..."
+ sprop := proto.GetProperties(s.Type())
+ return m.marshalValue(out, sprop.Prop[0], s.Field(0), indent)
+ case "Any":
+ // Any is a bit more involved.
+ return m.marshalAny(out, v, indent)
+ case "Duration":
+ // "Generated output always contains 3, 6, or 9 fractional digits,
+ // depending on required precision."
+ s, ns := s.Field(0).Int(), s.Field(1).Int()
+ d := time.Duration(s)*time.Second + time.Duration(ns)*time.Nanosecond
+ x := fmt.Sprintf("%.9f", d.Seconds())
+ x = strings.TrimSuffix(x, "000")
+ x = strings.TrimSuffix(x, "000")
+ out.write(`"`)
+ out.write(x)
+ out.write(`s"`)
+ return out.err
+ case "Struct", "ListValue":
+ // Let marshalValue handle the `Struct.fields` map or the `ListValue.values` slice.
+ // TODO: pass the correct Properties if needed.
+ return m.marshalValue(out, &proto.Properties{}, s.Field(0), indent)
+ case "Timestamp":
+ // "RFC 3339, where generated output will always be Z-normalized
+ // and uses 3, 6 or 9 fractional digits."
+ s, ns := s.Field(0).Int(), s.Field(1).Int()
+ t := time.Unix(s, ns).UTC()
+ // time.RFC3339Nano isn't exactly right (we need to get 3/6/9 fractional digits).
+ x := t.Format("2006-01-02T15:04:05.000000000")
+ x = strings.TrimSuffix(x, "000")
+ x = strings.TrimSuffix(x, "000")
+ out.write(`"`)
+ out.write(x)
+ out.write(`Z"`)
+ return out.err
+ case "Value":
+ // Value has a single oneof.
+ kind := s.Field(0)
+ if kind.IsNil() {
+ // "absence of any variant indicates an error"
+ return errors.New("nil Value")
+ }
+ // oneof -> *T -> T -> T.F
+ x := kind.Elem().Elem().Field(0)
+ // TODO: pass the correct Properties if needed.
+ return m.marshalValue(out, &proto.Properties{}, x, indent)
+ }
+ }
+
+ out.write("{")
+ if m.Indent != "" {
+ out.write("\n")
+ }
+
+ firstField := true
+
+ if typeURL != "" {
+ if err := m.marshalTypeURL(out, indent, typeURL); err != nil {
+ return err
+ }
+ firstField = false
+ }
+
+ for i := 0; i < s.NumField(); i++ {
+ value := s.Field(i)
+ valueField := s.Type().Field(i)
+ if strings.HasPrefix(valueField.Name, "XXX_") {
+ continue
+ }
+
+ // IsNil will panic on most value kinds.
+ switch value.Kind() {
+ case reflect.Chan, reflect.Func, reflect.Interface:
+ if value.IsNil() {
+ continue
+ }
+ }
+
+ if !m.EmitDefaults {
+ switch value.Kind() {
+ case reflect.Bool:
+ if !value.Bool() {
+ continue
+ }
+ case reflect.Int32, reflect.Int64:
+ if value.Int() == 0 {
+ continue
+ }
+ case reflect.Uint32, reflect.Uint64:
+ if value.Uint() == 0 {
+ continue
+ }
+ case reflect.Float32, reflect.Float64:
+ if value.Float() == 0 {
+ continue
+ }
+ case reflect.String:
+ if value.Len() == 0 {
+ continue
+ }
+ case reflect.Map, reflect.Ptr, reflect.Slice:
+ if value.IsNil() {
+ continue
+ }
+ }
+ }
+
+ // Oneof fields need special handling.
+ if valueField.Tag.Get("protobuf_oneof") != "" {
+ // value is an interface containing &T{real_value}.
+ sv := value.Elem().Elem() // interface -> *T -> T
+ value = sv.Field(0)
+ valueField = sv.Type().Field(0)
+ }
+ prop := jsonProperties(valueField, m.OrigName)
+ if !firstField {
+ m.writeSep(out)
+ }
+ if err := m.marshalField(out, prop, value, indent); err != nil {
+ return err
+ }
+ firstField = false
+ }
+
+ // Handle proto2 extensions.
+ if ep, ok := v.(proto.Message); ok {
+ extensions := proto.RegisteredExtensions(v)
+ // Sort extensions for stable output.
+ ids := make([]int32, 0, len(extensions))
+ for id, desc := range extensions {
+ if !proto.HasExtension(ep, desc) {
+ continue
+ }
+ ids = append(ids, id)
+ }
+ sort.Sort(int32Slice(ids))
+ for _, id := range ids {
+ desc := extensions[id]
+ if desc == nil {
+ // unknown extension
+ continue
+ }
+ ext, extErr := proto.GetExtension(ep, desc)
+ if extErr != nil {
+ return extErr
+ }
+ value := reflect.ValueOf(ext)
+ var prop proto.Properties
+ prop.Parse(desc.Tag)
+ prop.JSONName = fmt.Sprintf("[%s]", desc.Name)
+ if !firstField {
+ m.writeSep(out)
+ }
+ if err := m.marshalField(out, &prop, value, indent); err != nil {
+ return err
+ }
+ firstField = false
+ }
+
+ }
+
+ if m.Indent != "" {
+ out.write("\n")
+ out.write(indent)
+ }
+ out.write("}")
+ return out.err
+}
+
+func (m *Marshaler) writeSep(out *errWriter) {
+ if m.Indent != "" {
+ out.write(",\n")
+ } else {
+ out.write(",")
+ }
+}
+
+func (m *Marshaler) marshalAny(out *errWriter, any proto.Message, indent string) error {
+ // "If the Any contains a value that has a special JSON mapping,
+ // it will be converted as follows: {"@type": xxx, "value": yyy}.
+ // Otherwise, the value will be converted into a JSON object,
+ // and the "@type" field will be inserted to indicate the actual data type."
+ v := reflect.ValueOf(any).Elem()
+ turl := v.Field(0).String()
+ val := v.Field(1).Bytes()
+
+ var msg proto.Message
+ var err error
+ if m.AnyResolver != nil {
+ msg, err = m.AnyResolver.Resolve(turl)
+ } else {
+ msg, err = defaultResolveAny(turl)
+ }
+ if err != nil {
+ return err
+ }
+
+ if err := proto.Unmarshal(val, msg); err != nil {
+ return err
+ }
+
+ if _, ok := msg.(wkt); ok {
+ out.write("{")
+ if m.Indent != "" {
+ out.write("\n")
+ }
+ if err := m.marshalTypeURL(out, indent, turl); err != nil {
+ return err
+ }
+ m.writeSep(out)
+ if m.Indent != "" {
+ out.write(indent)
+ out.write(m.Indent)
+ out.write(`"value": `)
+ } else {
+ out.write(`"value":`)
+ }
+ if err := m.marshalObject(out, msg, indent+m.Indent, ""); err != nil {
+ return err
+ }
+ if m.Indent != "" {
+ out.write("\n")
+ out.write(indent)
+ }
+ out.write("}")
+ return out.err
+ }
+
+ return m.marshalObject(out, msg, indent, turl)
+}
+
+func (m *Marshaler) marshalTypeURL(out *errWriter, indent, typeURL string) error {
+ if m.Indent != "" {
+ out.write(indent)
+ out.write(m.Indent)
+ }
+ out.write(`"@type":`)
+ if m.Indent != "" {
+ out.write(" ")
+ }
+ b, err := json.Marshal(typeURL)
+ if err != nil {
+ return err
+ }
+ out.write(string(b))
+ return out.err
+}
+
+// marshalField writes field description and value to the Writer.
+func (m *Marshaler) marshalField(out *errWriter, prop *proto.Properties, v reflect.Value, indent string) error {
+ if m.Indent != "" {
+ out.write(indent)
+ out.write(m.Indent)
+ }
+ out.write(`"`)
+ out.write(prop.JSONName)
+ out.write(`":`)
+ if m.Indent != "" {
+ out.write(" ")
+ }
+ if err := m.marshalValue(out, prop, v, indent); err != nil {
+ return err
+ }
+ return nil
+}
+
+// marshalValue writes the value to the Writer.
+func (m *Marshaler) marshalValue(out *errWriter, prop *proto.Properties, v reflect.Value, indent string) error {
+ var err error
+ v = reflect.Indirect(v)
+
+ // Handle nil pointer
+ if v.Kind() == reflect.Invalid {
+ out.write("null")
+ return out.err
+ }
+
+ // Handle repeated elements.
+ if v.Kind() == reflect.Slice && v.Type().Elem().Kind() != reflect.Uint8 {
+ out.write("[")
+ comma := ""
+ for i := 0; i < v.Len(); i++ {
+ sliceVal := v.Index(i)
+ out.write(comma)
+ if m.Indent != "" {
+ out.write("\n")
+ out.write(indent)
+ out.write(m.Indent)
+ out.write(m.Indent)
+ }
+ if err := m.marshalValue(out, prop, sliceVal, indent+m.Indent); err != nil {
+ return err
+ }
+ comma = ","
+ }
+ if m.Indent != "" {
+ out.write("\n")
+ out.write(indent)
+ out.write(m.Indent)
+ }
+ out.write("]")
+ return out.err
+ }
+
+ // Handle well-known types.
+ // Most are handled up in marshalObject (because 99% are messages).
+ if wkt, ok := v.Interface().(wkt); ok {
+ switch wkt.XXX_WellKnownType() {
+ case "NullValue":
+ out.write("null")
+ return out.err
+ }
+ }
+
+ // Handle enumerations.
+ if !m.EnumsAsInts && prop.Enum != "" {
+ // Unknown enum values will are stringified by the proto library as their
+ // value. Such values should _not_ be quoted or they will be interpreted
+ // as an enum string instead of their value.
+ enumStr := v.Interface().(fmt.Stringer).String()
+ var valStr string
+ if v.Kind() == reflect.Ptr {
+ valStr = strconv.Itoa(int(v.Elem().Int()))
+ } else {
+ valStr = strconv.Itoa(int(v.Int()))
+ }
+ isKnownEnum := enumStr != valStr
+ if isKnownEnum {
+ out.write(`"`)
+ }
+ out.write(enumStr)
+ if isKnownEnum {
+ out.write(`"`)
+ }
+ return out.err
+ }
+
+ // Handle nested messages.
+ if v.Kind() == reflect.Struct {
+ return m.marshalObject(out, v.Addr().Interface().(proto.Message), indent+m.Indent, "")
+ }
+
+ // Handle maps.
+ // Since Go randomizes map iteration, we sort keys for stable output.
+ if v.Kind() == reflect.Map {
+ out.write(`{`)
+ keys := v.MapKeys()
+ sort.Sort(mapKeys(keys))
+ for i, k := range keys {
+ if i > 0 {
+ out.write(`,`)
+ }
+ if m.Indent != "" {
+ out.write("\n")
+ out.write(indent)
+ out.write(m.Indent)
+ out.write(m.Indent)
+ }
+
+ b, err := json.Marshal(k.Interface())
+ if err != nil {
+ return err
+ }
+ s := string(b)
+
+ // If the JSON is not a string value, encode it again to make it one.
+ if !strings.HasPrefix(s, `"`) {
+ b, err := json.Marshal(s)
+ if err != nil {
+ return err
+ }
+ s = string(b)
+ }
+
+ out.write(s)
+ out.write(`:`)
+ if m.Indent != "" {
+ out.write(` `)
+ }
+
+ if err := m.marshalValue(out, prop, v.MapIndex(k), indent+m.Indent); err != nil {
+ return err
+ }
+ }
+ if m.Indent != "" {
+ out.write("\n")
+ out.write(indent)
+ out.write(m.Indent)
+ }
+ out.write(`}`)
+ return out.err
+ }
+
+ // Handle non-finite floats, e.g. NaN, Infinity and -Infinity.
+ if v.Kind() == reflect.Float32 || v.Kind() == reflect.Float64 {
+ f := v.Float()
+ var sval string
+ switch {
+ case math.IsInf(f, 1):
+ sval = `"Infinity"`
+ case math.IsInf(f, -1):
+ sval = `"-Infinity"`
+ case math.IsNaN(f):
+ sval = `"NaN"`
+ }
+ if sval != "" {
+ out.write(sval)
+ return out.err
+ }
+ }
+
+ // Default handling defers to the encoding/json library.
+ b, err := json.Marshal(v.Interface())
+ if err != nil {
+ return err
+ }
+ needToQuote := string(b[0]) != `"` && (v.Kind() == reflect.Int64 || v.Kind() == reflect.Uint64)
+ if needToQuote {
+ out.write(`"`)
+ }
+ out.write(string(b))
+ if needToQuote {
+ out.write(`"`)
+ }
+ return out.err
+}
+
+// Unmarshaler is a configurable object for converting from a JSON
+// representation to a protocol buffer object.
+type Unmarshaler struct {
+ // Whether to allow messages to contain unknown fields, as opposed to
+ // failing to unmarshal.
+ AllowUnknownFields bool
+
+ // A custom URL resolver to use when unmarshaling Any messages from JSON.
+ // If unset, the default resolution strategy is to extract the
+ // fully-qualified type name from the type URL and pass that to
+ // proto.MessageType(string).
+ AnyResolver AnyResolver
+}
+
+// UnmarshalNext unmarshals the next protocol buffer from a JSON object stream.
+// This function is lenient and will decode any options permutations of the
+// related Marshaler.
+func (u *Unmarshaler) UnmarshalNext(dec *json.Decoder, pb proto.Message) error {
+ inputValue := json.RawMessage{}
+ if err := dec.Decode(&inputValue); err != nil {
+ return err
+ }
+ return u.unmarshalValue(reflect.ValueOf(pb).Elem(), inputValue, nil)
+}
+
+// Unmarshal unmarshals a JSON object stream into a protocol
+// buffer. This function is lenient and will decode any options
+// permutations of the related Marshaler.
+func (u *Unmarshaler) Unmarshal(r io.Reader, pb proto.Message) error {
+ dec := json.NewDecoder(r)
+ return u.UnmarshalNext(dec, pb)
+}
+
+// UnmarshalNext unmarshals the next protocol buffer from a JSON object stream.
+// This function is lenient and will decode any options permutations of the
+// related Marshaler.
+func UnmarshalNext(dec *json.Decoder, pb proto.Message) error {
+ return new(Unmarshaler).UnmarshalNext(dec, pb)
+}
+
+// Unmarshal unmarshals a JSON object stream into a protocol
+// buffer. This function is lenient and will decode any options
+// permutations of the related Marshaler.
+func Unmarshal(r io.Reader, pb proto.Message) error {
+ return new(Unmarshaler).Unmarshal(r, pb)
+}
+
+// UnmarshalString will populate the fields of a protocol buffer based
+// on a JSON string. This function is lenient and will decode any options
+// permutations of the related Marshaler.
+func UnmarshalString(str string, pb proto.Message) error {
+ return new(Unmarshaler).Unmarshal(strings.NewReader(str), pb)
+}
+
+// unmarshalValue converts/copies a value into the target.
+// prop may be nil.
+func (u *Unmarshaler) unmarshalValue(target reflect.Value, inputValue json.RawMessage, prop *proto.Properties) error {
+ targetType := target.Type()
+
+ // Allocate memory for pointer fields.
+ if targetType.Kind() == reflect.Ptr {
+ // If input value is "null" and target is a pointer type, then the field should be treated as not set
+ // UNLESS the target is structpb.Value, in which case it should be set to structpb.NullValue.
+ _, isJSONPBUnmarshaler := target.Interface().(JSONPBUnmarshaler)
+ if string(inputValue) == "null" && targetType != reflect.TypeOf(&stpb.Value{}) && !isJSONPBUnmarshaler {
+ return nil
+ }
+ target.Set(reflect.New(targetType.Elem()))
+
+ return u.unmarshalValue(target.Elem(), inputValue, prop)
+ }
+
+ if jsu, ok := target.Addr().Interface().(JSONPBUnmarshaler); ok {
+ return jsu.UnmarshalJSONPB(u, []byte(inputValue))
+ }
+
+ // Handle well-known types that are not pointers.
+ if w, ok := target.Addr().Interface().(wkt); ok {
+ switch w.XXX_WellKnownType() {
+ case "DoubleValue", "FloatValue", "Int64Value", "UInt64Value",
+ "Int32Value", "UInt32Value", "BoolValue", "StringValue", "BytesValue":
+ return u.unmarshalValue(target.Field(0), inputValue, prop)
+ case "Any":
+ // Use json.RawMessage pointer type instead of value to support pre-1.8 version.
+ // 1.8 changed RawMessage.MarshalJSON from pointer type to value type, see
+ // https://github.com/golang/go/issues/14493
+ var jsonFields map[string]*json.RawMessage
+ if err := json.Unmarshal(inputValue, &jsonFields); err != nil {
+ return err
+ }
+
+ val, ok := jsonFields["@type"]
+ if !ok || val == nil {
+ return errors.New("Any JSON doesn't have '@type'")
+ }
+
+ var turl string
+ if err := json.Unmarshal([]byte(*val), &turl); err != nil {
+ return fmt.Errorf("can't unmarshal Any's '@type': %q", *val)
+ }
+ target.Field(0).SetString(turl)
+
+ var m proto.Message
+ var err error
+ if u.AnyResolver != nil {
+ m, err = u.AnyResolver.Resolve(turl)
+ } else {
+ m, err = defaultResolveAny(turl)
+ }
+ if err != nil {
+ return err
+ }
+
+ if _, ok := m.(wkt); ok {
+ val, ok := jsonFields["value"]
+ if !ok {
+ return errors.New("Any JSON doesn't have 'value'")
+ }
+
+ if err := u.unmarshalValue(reflect.ValueOf(m).Elem(), *val, nil); err != nil {
+ return fmt.Errorf("can't unmarshal Any nested proto %T: %v", m, err)
+ }
+ } else {
+ delete(jsonFields, "@type")
+ nestedProto, err := json.Marshal(jsonFields)
+ if err != nil {
+ return fmt.Errorf("can't generate JSON for Any's nested proto to be unmarshaled: %v", err)
+ }
+
+ if err = u.unmarshalValue(reflect.ValueOf(m).Elem(), nestedProto, nil); err != nil {
+ return fmt.Errorf("can't unmarshal Any nested proto %T: %v", m, err)
+ }
+ }
+
+ b, err := proto.Marshal(m)
+ if err != nil {
+ return fmt.Errorf("can't marshal proto %T into Any.Value: %v", m, err)
+ }
+ target.Field(1).SetBytes(b)
+
+ return nil
+ case "Duration":
+ unq, err := strconv.Unquote(string(inputValue))
+ if err != nil {
+ return err
+ }
+
+ d, err := time.ParseDuration(unq)
+ if err != nil {
+ return fmt.Errorf("bad Duration: %v", err)
+ }
+
+ ns := d.Nanoseconds()
+ s := ns / 1e9
+ ns %= 1e9
+ target.Field(0).SetInt(s)
+ target.Field(1).SetInt(ns)
+ return nil
+ case "Timestamp":
+ unq, err := strconv.Unquote(string(inputValue))
+ if err != nil {
+ return err
+ }
+
+ t, err := time.Parse(time.RFC3339Nano, unq)
+ if err != nil {
+ return fmt.Errorf("bad Timestamp: %v", err)
+ }
+
+ target.Field(0).SetInt(t.Unix())
+ target.Field(1).SetInt(int64(t.Nanosecond()))
+ return nil
+ case "Struct":
+ var m map[string]json.RawMessage
+ if err := json.Unmarshal(inputValue, &m); err != nil {
+ return fmt.Errorf("bad StructValue: %v", err)
+ }
+
+ target.Field(0).Set(reflect.ValueOf(map[string]*stpb.Value{}))
+ for k, jv := range m {
+ pv := &stpb.Value{}
+ if err := u.unmarshalValue(reflect.ValueOf(pv).Elem(), jv, prop); err != nil {
+ return fmt.Errorf("bad value in StructValue for key %q: %v", k, err)
+ }
+ target.Field(0).SetMapIndex(reflect.ValueOf(k), reflect.ValueOf(pv))
+ }
+ return nil
+ case "ListValue":
+ var s []json.RawMessage
+ if err := json.Unmarshal(inputValue, &s); err != nil {
+ return fmt.Errorf("bad ListValue: %v", err)
+ }
+
+ target.Field(0).Set(reflect.ValueOf(make([]*stpb.Value, len(s), len(s))))
+ for i, sv := range s {
+ if err := u.unmarshalValue(target.Field(0).Index(i), sv, prop); err != nil {
+ return err
+ }
+ }
+ return nil
+ case "Value":
+ ivStr := string(inputValue)
+ if ivStr == "null" {
+ target.Field(0).Set(reflect.ValueOf(&stpb.Value_NullValue{}))
+ } else if v, err := strconv.ParseFloat(ivStr, 0); err == nil {
+ target.Field(0).Set(reflect.ValueOf(&stpb.Value_NumberValue{v}))
+ } else if v, err := strconv.Unquote(ivStr); err == nil {
+ target.Field(0).Set(reflect.ValueOf(&stpb.Value_StringValue{v}))
+ } else if v, err := strconv.ParseBool(ivStr); err == nil {
+ target.Field(0).Set(reflect.ValueOf(&stpb.Value_BoolValue{v}))
+ } else if err := json.Unmarshal(inputValue, &[]json.RawMessage{}); err == nil {
+ lv := &stpb.ListValue{}
+ target.Field(0).Set(reflect.ValueOf(&stpb.Value_ListValue{lv}))
+ return u.unmarshalValue(reflect.ValueOf(lv).Elem(), inputValue, prop)
+ } else if err := json.Unmarshal(inputValue, &map[string]json.RawMessage{}); err == nil {
+ sv := &stpb.Struct{}
+ target.Field(0).Set(reflect.ValueOf(&stpb.Value_StructValue{sv}))
+ return u.unmarshalValue(reflect.ValueOf(sv).Elem(), inputValue, prop)
+ } else {
+ return fmt.Errorf("unrecognized type for Value %q", ivStr)
+ }
+ return nil
+ }
+ }
+
+ // Handle enums, which have an underlying type of int32,
+ // and may appear as strings.
+ // The case of an enum appearing as a number is handled
+ // at the bottom of this function.
+ if inputValue[0] == '"' && prop != nil && prop.Enum != "" {
+ vmap := proto.EnumValueMap(prop.Enum)
+ // Don't need to do unquoting; valid enum names
+ // are from a limited character set.
+ s := inputValue[1 : len(inputValue)-1]
+ n, ok := vmap[string(s)]
+ if !ok {
+ return fmt.Errorf("unknown value %q for enum %s", s, prop.Enum)
+ }
+ if target.Kind() == reflect.Ptr { // proto2
+ target.Set(reflect.New(targetType.Elem()))
+ target = target.Elem()
+ }
+ target.SetInt(int64(n))
+ return nil
+ }
+
+ // Handle nested messages.
+ if targetType.Kind() == reflect.Struct {
+ var jsonFields map[string]json.RawMessage
+ if err := json.Unmarshal(inputValue, &jsonFields); err != nil {
+ return err
+ }
+
+ consumeField := func(prop *proto.Properties) (json.RawMessage, bool) {
+ // Be liberal in what names we accept; both orig_name and camelName are okay.
+ fieldNames := acceptedJSONFieldNames(prop)
+
+ vOrig, okOrig := jsonFields[fieldNames.orig]
+ vCamel, okCamel := jsonFields[fieldNames.camel]
+ if !okOrig && !okCamel {
+ return nil, false
+ }
+ // If, for some reason, both are present in the data, favour the camelName.
+ var raw json.RawMessage
+ if okOrig {
+ raw = vOrig
+ delete(jsonFields, fieldNames.orig)
+ }
+ if okCamel {
+ raw = vCamel
+ delete(jsonFields, fieldNames.camel)
+ }
+ return raw, true
+ }
+
+ sprops := proto.GetProperties(targetType)
+ for i := 0; i < target.NumField(); i++ {
+ ft := target.Type().Field(i)
+ if strings.HasPrefix(ft.Name, "XXX_") {
+ continue
+ }
+
+ valueForField, ok := consumeField(sprops.Prop[i])
+ if !ok {
+ continue
+ }
+
+ if err := u.unmarshalValue(target.Field(i), valueForField, sprops.Prop[i]); err != nil {
+ return err
+ }
+ }
+ // Check for any oneof fields.
+ if len(jsonFields) > 0 {
+ for _, oop := range sprops.OneofTypes {
+ raw, ok := consumeField(oop.Prop)
+ if !ok {
+ continue
+ }
+ nv := reflect.New(oop.Type.Elem())
+ target.Field(oop.Field).Set(nv)
+ if err := u.unmarshalValue(nv.Elem().Field(0), raw, oop.Prop); err != nil {
+ return err
+ }
+ }
+ }
+ // Handle proto2 extensions.
+ if len(jsonFields) > 0 {
+ if ep, ok := target.Addr().Interface().(proto.Message); ok {
+ for _, ext := range proto.RegisteredExtensions(ep) {
+ name := fmt.Sprintf("[%s]", ext.Name)
+ raw, ok := jsonFields[name]
+ if !ok {
+ continue
+ }
+ delete(jsonFields, name)
+ nv := reflect.New(reflect.TypeOf(ext.ExtensionType).Elem())
+ if err := u.unmarshalValue(nv.Elem(), raw, nil); err != nil {
+ return err
+ }
+ if err := proto.SetExtension(ep, ext, nv.Interface()); err != nil {
+ return err
+ }
+ }
+ }
+ }
+ if !u.AllowUnknownFields && len(jsonFields) > 0 {
+ // Pick any field to be the scapegoat.
+ var f string
+ for fname := range jsonFields {
+ f = fname
+ break
+ }
+ return fmt.Errorf("unknown field %q in %v", f, targetType)
+ }
+ return nil
+ }
+
+ // Handle arrays (which aren't encoded bytes)
+ if targetType.Kind() == reflect.Slice && targetType.Elem().Kind() != reflect.Uint8 {
+ var slc []json.RawMessage
+ if err := json.Unmarshal(inputValue, &slc); err != nil {
+ return err
+ }
+ if slc != nil {
+ l := len(slc)
+ target.Set(reflect.MakeSlice(targetType, l, l))
+ for i := 0; i < l; i++ {
+ if err := u.unmarshalValue(target.Index(i), slc[i], prop); err != nil {
+ return err
+ }
+ }
+ }
+ return nil
+ }
+
+ // Handle maps (whose keys are always strings)
+ if targetType.Kind() == reflect.Map {
+ var mp map[string]json.RawMessage
+ if err := json.Unmarshal(inputValue, &mp); err != nil {
+ return err
+ }
+ if mp != nil {
+ target.Set(reflect.MakeMap(targetType))
+ var keyprop, valprop *proto.Properties
+ if prop != nil {
+ // These could still be nil if the protobuf metadata is broken somehow.
+ // TODO: This won't work because the fields are unexported.
+ // We should probably just reparse them.
+ //keyprop, valprop = prop.mkeyprop, prop.mvalprop
+ }
+ for ks, raw := range mp {
+ // Unmarshal map key. The core json library already decoded the key into a
+ // string, so we handle that specially. Other types were quoted post-serialization.
+ var k reflect.Value
+ if targetType.Key().Kind() == reflect.String {
+ k = reflect.ValueOf(ks)
+ } else {
+ k = reflect.New(targetType.Key()).Elem()
+ if err := u.unmarshalValue(k, json.RawMessage(ks), keyprop); err != nil {
+ return err
+ }
+ }
+
+ // Unmarshal map value.
+ v := reflect.New(targetType.Elem()).Elem()
+ if err := u.unmarshalValue(v, raw, valprop); err != nil {
+ return err
+ }
+ target.SetMapIndex(k, v)
+ }
+ }
+ return nil
+ }
+
+ // 64-bit integers can be encoded as strings. In this case we drop
+ // the quotes and proceed as normal.
+ isNum := targetType.Kind() == reflect.Int64 || targetType.Kind() == reflect.Uint64
+ if isNum && strings.HasPrefix(string(inputValue), `"`) {
+ inputValue = inputValue[1 : len(inputValue)-1]
+ }
+
+ // Non-finite numbers can be encoded as strings.
+ isFloat := targetType.Kind() == reflect.Float32 || targetType.Kind() == reflect.Float64
+ if isFloat {
+ if num, ok := nonFinite[string(inputValue)]; ok {
+ target.SetFloat(num)
+ return nil
+ }
+ }
+
+ // Use the encoding/json for parsing other value types.
+ return json.Unmarshal(inputValue, target.Addr().Interface())
+}
+
+// jsonProperties returns parsed proto.Properties for the field and corrects JSONName attribute.
+func jsonProperties(f reflect.StructField, origName bool) *proto.Properties {
+ var prop proto.Properties
+ prop.Init(f.Type, f.Name, f.Tag.Get("protobuf"), &f)
+ if origName || prop.JSONName == "" {
+ prop.JSONName = prop.OrigName
+ }
+ return &prop
+}
+
+type fieldNames struct {
+ orig, camel string
+}
+
+func acceptedJSONFieldNames(prop *proto.Properties) fieldNames {
+ opts := fieldNames{orig: prop.OrigName, camel: prop.OrigName}
+ if prop.JSONName != "" {
+ opts.camel = prop.JSONName
+ }
+ return opts
+}
+
+// Writer wrapper inspired by https://blog.golang.org/errors-are-values
+type errWriter struct {
+ writer io.Writer
+ err error
+}
+
+func (w *errWriter) write(str string) {
+ if w.err != nil {
+ return
+ }
+ _, w.err = w.writer.Write([]byte(str))
+}
+
+// Map fields may have key types of non-float scalars, strings and enums.
+// The easiest way to sort them in some deterministic order is to use fmt.
+// If this turns out to be inefficient we can always consider other options,
+// such as doing a Schwartzian transform.
+//
+// Numeric keys are sorted in numeric order per
+// https://developers.google.com/protocol-buffers/docs/proto#maps.
+type mapKeys []reflect.Value
+
+func (s mapKeys) Len() int { return len(s) }
+func (s mapKeys) Swap(i, j int) { s[i], s[j] = s[j], s[i] }
+func (s mapKeys) Less(i, j int) bool {
+ if k := s[i].Kind(); k == s[j].Kind() {
+ switch k {
+ case reflect.Int32, reflect.Int64:
+ return s[i].Int() < s[j].Int()
+ case reflect.Uint32, reflect.Uint64:
+ return s[i].Uint() < s[j].Uint()
+ }
+ }
+ return fmt.Sprint(s[i].Interface()) < fmt.Sprint(s[j].Interface())
+}
diff --git a/vendor/github.com/golang/protobuf/ptypes/struct/struct.pb.go b/vendor/github.com/golang/protobuf/ptypes/struct/struct.pb.go
new file mode 100644
index 00000000..4cfe6081
--- /dev/null
+++ b/vendor/github.com/golang/protobuf/ptypes/struct/struct.pb.go
@@ -0,0 +1,380 @@
+// Code generated by protoc-gen-go. DO NOT EDIT.
+// source: google/protobuf/struct.proto
+
+/*
+Package structpb is a generated protocol buffer package.
+
+It is generated from these files:
+ google/protobuf/struct.proto
+
+It has these top-level messages:
+ Struct
+ Value
+ ListValue
+*/
+package structpb
+
+import proto "github.com/golang/protobuf/proto"
+import fmt "fmt"
+import math "math"
+
+// Reference imports to suppress errors if they are not otherwise used.
+var _ = proto.Marshal
+var _ = fmt.Errorf
+var _ = math.Inf
+
+// This is a compile-time assertion to ensure that this generated file
+// is compatible with the proto package it is being compiled against.
+// A compilation error at this line likely means your copy of the
+// proto package needs to be updated.
+const _ = proto.ProtoPackageIsVersion2 // please upgrade the proto package
+
+// `NullValue` is a singleton enumeration to represent the null value for the
+// `Value` type union.
+//
+// The JSON representation for `NullValue` is JSON `null`.
+type NullValue int32
+
+const (
+ // Null value.
+ NullValue_NULL_VALUE NullValue = 0
+)
+
+var NullValue_name = map[int32]string{
+ 0: "NULL_VALUE",
+}
+var NullValue_value = map[string]int32{
+ "NULL_VALUE": 0,
+}
+
+func (x NullValue) String() string {
+ return proto.EnumName(NullValue_name, int32(x))
+}
+func (NullValue) EnumDescriptor() ([]byte, []int) { return fileDescriptor0, []int{0} }
+func (NullValue) XXX_WellKnownType() string { return "NullValue" }
+
+// `Struct` represents a structured data value, consisting of fields
+// which map to dynamically typed values. In some languages, `Struct`
+// might be supported by a native representation. For example, in
+// scripting languages like JS a struct is represented as an
+// object. The details of that representation are described together
+// with the proto support for the language.
+//
+// The JSON representation for `Struct` is JSON object.
+type Struct struct {
+ // Unordered map of dynamically typed values.
+ Fields map[string]*Value `protobuf:"bytes,1,rep,name=fields" json:"fields,omitempty" protobuf_key:"bytes,1,opt,name=key" protobuf_val:"bytes,2,opt,name=value"`
+}
+
+func (m *Struct) Reset() { *m = Struct{} }
+func (m *Struct) String() string { return proto.CompactTextString(m) }
+func (*Struct) ProtoMessage() {}
+func (*Struct) Descriptor() ([]byte, []int) { return fileDescriptor0, []int{0} }
+func (*Struct) XXX_WellKnownType() string { return "Struct" }
+
+func (m *Struct) GetFields() map[string]*Value {
+ if m != nil {
+ return m.Fields
+ }
+ return nil
+}
+
+// `Value` represents a dynamically typed value which can be either
+// null, a number, a string, a boolean, a recursive struct value, or a
+// list of values. A producer of value is expected to set one of that
+// variants, absence of any variant indicates an error.
+//
+// The JSON representation for `Value` is JSON value.
+type Value struct {
+ // The kind of value.
+ //
+ // Types that are valid to be assigned to Kind:
+ // *Value_NullValue
+ // *Value_NumberValue
+ // *Value_StringValue
+ // *Value_BoolValue
+ // *Value_StructValue
+ // *Value_ListValue
+ Kind isValue_Kind `protobuf_oneof:"kind"`
+}
+
+func (m *Value) Reset() { *m = Value{} }
+func (m *Value) String() string { return proto.CompactTextString(m) }
+func (*Value) ProtoMessage() {}
+func (*Value) Descriptor() ([]byte, []int) { return fileDescriptor0, []int{1} }
+func (*Value) XXX_WellKnownType() string { return "Value" }
+
+type isValue_Kind interface {
+ isValue_Kind()
+}
+
+type Value_NullValue struct {
+ NullValue NullValue `protobuf:"varint,1,opt,name=null_value,json=nullValue,enum=google.protobuf.NullValue,oneof"`
+}
+type Value_NumberValue struct {
+ NumberValue float64 `protobuf:"fixed64,2,opt,name=number_value,json=numberValue,oneof"`
+}
+type Value_StringValue struct {
+ StringValue string `protobuf:"bytes,3,opt,name=string_value,json=stringValue,oneof"`
+}
+type Value_BoolValue struct {
+ BoolValue bool `protobuf:"varint,4,opt,name=bool_value,json=boolValue,oneof"`
+}
+type Value_StructValue struct {
+ StructValue *Struct `protobuf:"bytes,5,opt,name=struct_value,json=structValue,oneof"`
+}
+type Value_ListValue struct {
+ ListValue *ListValue `protobuf:"bytes,6,opt,name=list_value,json=listValue,oneof"`
+}
+
+func (*Value_NullValue) isValue_Kind() {}
+func (*Value_NumberValue) isValue_Kind() {}
+func (*Value_StringValue) isValue_Kind() {}
+func (*Value_BoolValue) isValue_Kind() {}
+func (*Value_StructValue) isValue_Kind() {}
+func (*Value_ListValue) isValue_Kind() {}
+
+func (m *Value) GetKind() isValue_Kind {
+ if m != nil {
+ return m.Kind
+ }
+ return nil
+}
+
+func (m *Value) GetNullValue() NullValue {
+ if x, ok := m.GetKind().(*Value_NullValue); ok {
+ return x.NullValue
+ }
+ return NullValue_NULL_VALUE
+}
+
+func (m *Value) GetNumberValue() float64 {
+ if x, ok := m.GetKind().(*Value_NumberValue); ok {
+ return x.NumberValue
+ }
+ return 0
+}
+
+func (m *Value) GetStringValue() string {
+ if x, ok := m.GetKind().(*Value_StringValue); ok {
+ return x.StringValue
+ }
+ return ""
+}
+
+func (m *Value) GetBoolValue() bool {
+ if x, ok := m.GetKind().(*Value_BoolValue); ok {
+ return x.BoolValue
+ }
+ return false
+}
+
+func (m *Value) GetStructValue() *Struct {
+ if x, ok := m.GetKind().(*Value_StructValue); ok {
+ return x.StructValue
+ }
+ return nil
+}
+
+func (m *Value) GetListValue() *ListValue {
+ if x, ok := m.GetKind().(*Value_ListValue); ok {
+ return x.ListValue
+ }
+ return nil
+}
+
+// XXX_OneofFuncs is for the internal use of the proto package.
+func (*Value) XXX_OneofFuncs() (func(msg proto.Message, b *proto.Buffer) error, func(msg proto.Message, tag, wire int, b *proto.Buffer) (bool, error), func(msg proto.Message) (n int), []interface{}) {
+ return _Value_OneofMarshaler, _Value_OneofUnmarshaler, _Value_OneofSizer, []interface{}{
+ (*Value_NullValue)(nil),
+ (*Value_NumberValue)(nil),
+ (*Value_StringValue)(nil),
+ (*Value_BoolValue)(nil),
+ (*Value_StructValue)(nil),
+ (*Value_ListValue)(nil),
+ }
+}
+
+func _Value_OneofMarshaler(msg proto.Message, b *proto.Buffer) error {
+ m := msg.(*Value)
+ // kind
+ switch x := m.Kind.(type) {
+ case *Value_NullValue:
+ b.EncodeVarint(1<<3 | proto.WireVarint)
+ b.EncodeVarint(uint64(x.NullValue))
+ case *Value_NumberValue:
+ b.EncodeVarint(2<<3 | proto.WireFixed64)
+ b.EncodeFixed64(math.Float64bits(x.NumberValue))
+ case *Value_StringValue:
+ b.EncodeVarint(3<<3 | proto.WireBytes)
+ b.EncodeStringBytes(x.StringValue)
+ case *Value_BoolValue:
+ t := uint64(0)
+ if x.BoolValue {
+ t = 1
+ }
+ b.EncodeVarint(4<<3 | proto.WireVarint)
+ b.EncodeVarint(t)
+ case *Value_StructValue:
+ b.EncodeVarint(5<<3 | proto.WireBytes)
+ if err := b.EncodeMessage(x.StructValue); err != nil {
+ return err
+ }
+ case *Value_ListValue:
+ b.EncodeVarint(6<<3 | proto.WireBytes)
+ if err := b.EncodeMessage(x.ListValue); err != nil {
+ return err
+ }
+ case nil:
+ default:
+ return fmt.Errorf("Value.Kind has unexpected type %T", x)
+ }
+ return nil
+}
+
+func _Value_OneofUnmarshaler(msg proto.Message, tag, wire int, b *proto.Buffer) (bool, error) {
+ m := msg.(*Value)
+ switch tag {
+ case 1: // kind.null_value
+ if wire != proto.WireVarint {
+ return true, proto.ErrInternalBadWireType
+ }
+ x, err := b.DecodeVarint()
+ m.Kind = &Value_NullValue{NullValue(x)}
+ return true, err
+ case 2: // kind.number_value
+ if wire != proto.WireFixed64 {
+ return true, proto.ErrInternalBadWireType
+ }
+ x, err := b.DecodeFixed64()
+ m.Kind = &Value_NumberValue{math.Float64frombits(x)}
+ return true, err
+ case 3: // kind.string_value
+ if wire != proto.WireBytes {
+ return true, proto.ErrInternalBadWireType
+ }
+ x, err := b.DecodeStringBytes()
+ m.Kind = &Value_StringValue{x}
+ return true, err
+ case 4: // kind.bool_value
+ if wire != proto.WireVarint {
+ return true, proto.ErrInternalBadWireType
+ }
+ x, err := b.DecodeVarint()
+ m.Kind = &Value_BoolValue{x != 0}
+ return true, err
+ case 5: // kind.struct_value
+ if wire != proto.WireBytes {
+ return true, proto.ErrInternalBadWireType
+ }
+ msg := new(Struct)
+ err := b.DecodeMessage(msg)
+ m.Kind = &Value_StructValue{msg}
+ return true, err
+ case 6: // kind.list_value
+ if wire != proto.WireBytes {
+ return true, proto.ErrInternalBadWireType
+ }
+ msg := new(ListValue)
+ err := b.DecodeMessage(msg)
+ m.Kind = &Value_ListValue{msg}
+ return true, err
+ default:
+ return false, nil
+ }
+}
+
+func _Value_OneofSizer(msg proto.Message) (n int) {
+ m := msg.(*Value)
+ // kind
+ switch x := m.Kind.(type) {
+ case *Value_NullValue:
+ n += proto.SizeVarint(1<<3 | proto.WireVarint)
+ n += proto.SizeVarint(uint64(x.NullValue))
+ case *Value_NumberValue:
+ n += proto.SizeVarint(2<<3 | proto.WireFixed64)
+ n += 8
+ case *Value_StringValue:
+ n += proto.SizeVarint(3<<3 | proto.WireBytes)
+ n += proto.SizeVarint(uint64(len(x.StringValue)))
+ n += len(x.StringValue)
+ case *Value_BoolValue:
+ n += proto.SizeVarint(4<<3 | proto.WireVarint)
+ n += 1
+ case *Value_StructValue:
+ s := proto.Size(x.StructValue)
+ n += proto.SizeVarint(5<<3 | proto.WireBytes)
+ n += proto.SizeVarint(uint64(s))
+ n += s
+ case *Value_ListValue:
+ s := proto.Size(x.ListValue)
+ n += proto.SizeVarint(6<<3 | proto.WireBytes)
+ n += proto.SizeVarint(uint64(s))
+ n += s
+ case nil:
+ default:
+ panic(fmt.Sprintf("proto: unexpected type %T in oneof", x))
+ }
+ return n
+}
+
+// `ListValue` is a wrapper around a repeated field of values.
+//
+// The JSON representation for `ListValue` is JSON array.
+type ListValue struct {
+ // Repeated field of dynamically typed values.
+ Values []*Value `protobuf:"bytes,1,rep,name=values" json:"values,omitempty"`
+}
+
+func (m *ListValue) Reset() { *m = ListValue{} }
+func (m *ListValue) String() string { return proto.CompactTextString(m) }
+func (*ListValue) ProtoMessage() {}
+func (*ListValue) Descriptor() ([]byte, []int) { return fileDescriptor0, []int{2} }
+func (*ListValue) XXX_WellKnownType() string { return "ListValue" }
+
+func (m *ListValue) GetValues() []*Value {
+ if m != nil {
+ return m.Values
+ }
+ return nil
+}
+
+func init() {
+ proto.RegisterType((*Struct)(nil), "google.protobuf.Struct")
+ proto.RegisterType((*Value)(nil), "google.protobuf.Value")
+ proto.RegisterType((*ListValue)(nil), "google.protobuf.ListValue")
+ proto.RegisterEnum("google.protobuf.NullValue", NullValue_name, NullValue_value)
+}
+
+func init() { proto.RegisterFile("google/protobuf/struct.proto", fileDescriptor0) }
+
+var fileDescriptor0 = []byte{
+ // 417 bytes of a gzipped FileDescriptorProto
+ 0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0xff, 0x74, 0x92, 0x41, 0x8b, 0xd3, 0x40,
+ 0x14, 0xc7, 0x3b, 0xc9, 0x36, 0x98, 0x17, 0x59, 0x97, 0x11, 0xb4, 0xac, 0xa2, 0xa1, 0x7b, 0x09,
+ 0x22, 0x29, 0xd6, 0x8b, 0x18, 0x2f, 0x06, 0xd6, 0x5d, 0x30, 0x2c, 0x31, 0xba, 0x15, 0xbc, 0x94,
+ 0x26, 0x4d, 0x63, 0xe8, 0x74, 0x26, 0x24, 0x33, 0x4a, 0x8f, 0x7e, 0x0b, 0xcf, 0x1e, 0x3d, 0xfa,
+ 0xe9, 0x3c, 0xca, 0xcc, 0x24, 0xa9, 0xb4, 0xf4, 0x94, 0xbc, 0xf7, 0x7e, 0xef, 0x3f, 0xef, 0xff,
+ 0x66, 0xe0, 0x71, 0xc1, 0x58, 0x41, 0xf2, 0x49, 0x55, 0x33, 0xce, 0x52, 0xb1, 0x9a, 0x34, 0xbc,
+ 0x16, 0x19, 0xf7, 0x55, 0x8c, 0xef, 0xe9, 0xaa, 0xdf, 0x55, 0xc7, 0x3f, 0x11, 0x58, 0x1f, 0x15,
+ 0x81, 0x03, 0xb0, 0x56, 0x65, 0x4e, 0x96, 0xcd, 0x08, 0xb9, 0xa6, 0xe7, 0x4c, 0x2f, 0xfc, 0x3d,
+ 0xd8, 0xd7, 0xa0, 0xff, 0x4e, 0x51, 0x97, 0x94, 0xd7, 0xdb, 0xa4, 0x6d, 0x39, 0xff, 0x00, 0xce,
+ 0x7f, 0x69, 0x7c, 0x06, 0xe6, 0x3a, 0xdf, 0x8e, 0x90, 0x8b, 0x3c, 0x3b, 0x91, 0xbf, 0xf8, 0x39,
+ 0x0c, 0xbf, 0x2d, 0x88, 0xc8, 0x47, 0x86, 0x8b, 0x3c, 0x67, 0xfa, 0xe0, 0x40, 0x7c, 0x26, 0xab,
+ 0x89, 0x86, 0x5e, 0x1b, 0xaf, 0xd0, 0xf8, 0x8f, 0x01, 0x43, 0x95, 0xc4, 0x01, 0x00, 0x15, 0x84,
+ 0xcc, 0xb5, 0x80, 0x14, 0x3d, 0x9d, 0x9e, 0x1f, 0x08, 0xdc, 0x08, 0x42, 0x14, 0x7f, 0x3d, 0x48,
+ 0x6c, 0xda, 0x05, 0xf8, 0x02, 0xee, 0x52, 0xb1, 0x49, 0xf3, 0x7a, 0xbe, 0x3b, 0x1f, 0x5d, 0x0f,
+ 0x12, 0x47, 0x67, 0x7b, 0xa8, 0xe1, 0x75, 0x49, 0x8b, 0x16, 0x32, 0xe5, 0xe0, 0x12, 0xd2, 0x59,
+ 0x0d, 0x3d, 0x05, 0x48, 0x19, 0xeb, 0xc6, 0x38, 0x71, 0x91, 0x77, 0x47, 0x1e, 0x25, 0x73, 0x1a,
+ 0x78, 0xa3, 0x54, 0x44, 0xc6, 0x5b, 0x64, 0xa8, 0xac, 0x3e, 0x3c, 0xb2, 0xc7, 0x56, 0x5e, 0x64,
+ 0xbc, 0x77, 0x49, 0xca, 0xa6, 0xeb, 0xb5, 0x54, 0xef, 0xa1, 0xcb, 0xa8, 0x6c, 0x78, 0xef, 0x92,
+ 0x74, 0x41, 0x68, 0xc1, 0xc9, 0xba, 0xa4, 0xcb, 0x71, 0x00, 0x76, 0x4f, 0x60, 0x1f, 0x2c, 0x25,
+ 0xd6, 0xdd, 0xe8, 0xb1, 0xa5, 0xb7, 0xd4, 0xb3, 0x47, 0x60, 0xf7, 0x4b, 0xc4, 0xa7, 0x00, 0x37,
+ 0xb7, 0x51, 0x34, 0x9f, 0xbd, 0x8d, 0x6e, 0x2f, 0xcf, 0x06, 0xe1, 0x0f, 0x04, 0xf7, 0x33, 0xb6,
+ 0xd9, 0x97, 0x08, 0x1d, 0xed, 0x26, 0x96, 0x71, 0x8c, 0xbe, 0xbc, 0x28, 0x4a, 0xfe, 0x55, 0xa4,
+ 0x7e, 0xc6, 0x36, 0x93, 0x82, 0x91, 0x05, 0x2d, 0x76, 0x4f, 0xb1, 0xe2, 0xdb, 0x2a, 0x6f, 0xda,
+ 0x17, 0x19, 0xe8, 0x4f, 0x95, 0xfe, 0x45, 0xe8, 0x97, 0x61, 0x5e, 0xc5, 0xe1, 0x6f, 0xe3, 0xc9,
+ 0x95, 0x16, 0x8f, 0xbb, 0xf9, 0x3e, 0xe7, 0x84, 0xbc, 0xa7, 0xec, 0x3b, 0xfd, 0x24, 0x3b, 0x53,
+ 0x4b, 0x49, 0xbd, 0xfc, 0x17, 0x00, 0x00, 0xff, 0xff, 0xe8, 0x1b, 0x59, 0xf8, 0xe5, 0x02, 0x00,
+ 0x00,
+}
diff --git a/vendor/github.com/golang/protobuf/ptypes/struct/struct.proto b/vendor/github.com/golang/protobuf/ptypes/struct/struct.proto
new file mode 100644
index 00000000..7d7808e7
--- /dev/null
+++ b/vendor/github.com/golang/protobuf/ptypes/struct/struct.proto
@@ -0,0 +1,96 @@
+// Protocol Buffers - Google's data interchange format
+// Copyright 2008 Google Inc. All rights reserved.
+// https://developers.google.com/protocol-buffers/
+//
+// Redistribution and use in source and binary forms, with or without
+// modification, are permitted provided that the following conditions are
+// met:
+//
+// * Redistributions of source code must retain the above copyright
+// notice, this list of conditions and the following disclaimer.
+// * Redistributions in binary form must reproduce the above
+// copyright notice, this list of conditions and the following disclaimer
+// in the documentation and/or other materials provided with the
+// distribution.
+// * Neither the name of Google Inc. nor the names of its
+// contributors may be used to endorse or promote products derived from
+// this software without specific prior written permission.
+//
+// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
+// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
+// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
+// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
+// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+
+syntax = "proto3";
+
+package google.protobuf;
+
+option csharp_namespace = "Google.Protobuf.WellKnownTypes";
+option cc_enable_arenas = true;
+option go_package = "github.com/golang/protobuf/ptypes/struct;structpb";
+option java_package = "com.google.protobuf";
+option java_outer_classname = "StructProto";
+option java_multiple_files = true;
+option objc_class_prefix = "GPB";
+
+
+// `Struct` represents a structured data value, consisting of fields
+// which map to dynamically typed values. In some languages, `Struct`
+// might be supported by a native representation. For example, in
+// scripting languages like JS a struct is represented as an
+// object. The details of that representation are described together
+// with the proto support for the language.
+//
+// The JSON representation for `Struct` is JSON object.
+message Struct {
+ // Unordered map of dynamically typed values.
+ map<string, Value> fields = 1;
+}
+
+// `Value` represents a dynamically typed value which can be either
+// null, a number, a string, a boolean, a recursive struct value, or a
+// list of values. A producer of value is expected to set one of that
+// variants, absence of any variant indicates an error.
+//
+// The JSON representation for `Value` is JSON value.
+message Value {
+ // The kind of value.
+ oneof kind {
+ // Represents a null value.
+ NullValue null_value = 1;
+ // Represents a double value.
+ double number_value = 2;
+ // Represents a string value.
+ string string_value = 3;
+ // Represents a boolean value.
+ bool bool_value = 4;
+ // Represents a structured value.
+ Struct struct_value = 5;
+ // Represents a repeated `Value`.
+ ListValue list_value = 6;
+ }
+}
+
+// `NullValue` is a singleton enumeration to represent the null value for the
+// `Value` type union.
+//
+// The JSON representation for `NullValue` is JSON `null`.
+enum NullValue {
+ // Null value.
+ NULL_VALUE = 0;
+}
+
+// `ListValue` is a wrapper around a repeated field of values.
+//
+// The JSON representation for `ListValue` is JSON array.
+message ListValue {
+ // Repeated field of dynamically typed values.
+ repeated Value values = 1;
+}
diff --git a/vendor/github.com/grpc-ecosystem/go-grpc-middleware/DOC.md b/vendor/github.com/grpc-ecosystem/go-grpc-middleware/DOC.md
new file mode 100644
index 00000000..511d953a
--- /dev/null
+++ b/vendor/github.com/grpc-ecosystem/go-grpc-middleware/DOC.md
@@ -0,0 +1,166 @@
+# grpc_middleware
+`import "github.com/grpc-ecosystem/go-grpc-middleware"`
+
+* [Overview](#pkg-overview)
+* [Imported Packages](#pkg-imports)
+* [Index](#pkg-index)
+
+## <a name="pkg-overview">Overview</a>
+`grpc_middleware` is a collection of gRPC middleware packages: interceptors, helpers and tools.
+
+### Middleware
+gRPC is a fantastic RPC middleware, which sees a lot of adoption in the Golang world. However, the
+upstream gRPC codebase is relatively bare bones.
+
+This package, and most of its child packages provides commonly needed middleware for gRPC:
+client-side interceptors for retires, server-side interceptors for input validation and auth,
+functions for chaining said interceptors, metadata convenience methods and more.
+
+### Chaining
+By default, gRPC doesn't allow one to have more than one interceptor either on the client nor on
+the server side. `grpc_middleware` provides convenient chaining methods
+
+Simple way of turning a multiple interceptors into a single interceptor. Here's an example for
+server chaining:
+
+ myServer := grpc.NewServer(
+ grpc.StreamInterceptor(grpc_middleware.ChainStreamServer(loggingStream, monitoringStream, authStream)),
+ grpc.UnaryInterceptor(grpc_middleware.ChainUnaryServer(loggingUnary, monitoringUnary, authUnary),
+ )
+
+These interceptors will be executed from left to right: logging, monitoring and auth.
+
+Here's an example for client side chaining:
+
+ clientConn, err = grpc.Dial(
+ address,
+ grpc.WithUnaryInterceptor(grpc_middleware.ChainUnaryClient(monitoringClientUnary, retryUnary)),
+ grpc.WithStreamInterceptor(grpc_middleware.ChainStreamClient(monitoringClientStream, retryStream)),
+ )
+ client = pb_testproto.NewTestServiceClient(clientConn)
+ resp, err := client.PingEmpty(s.ctx, &myservice.Request{Msg: "hello"})
+
+These interceptors will be executed from left to right: monitoring and then retry logic.
+
+The retry interceptor will call every interceptor that follows it whenever when a retry happens.
+
+### Writing Your Own
+Implementing your own interceptor is pretty trivial: there are interfaces for that. But the interesting
+bit exposing common data to handlers (and other middleware), similarly to HTTP Middleware design.
+For example, you may want to pass the identity of the caller from the auth interceptor all the way
+to the handling function.
+
+For example, a client side interceptor example for auth looks like:
+
+ func FakeAuthUnaryInterceptor(ctx context.Context, req interface{}, info *grpc.UnaryServerInfo, handler grpc.UnaryHandler) (interface{}, error) {
+ newCtx := context.WithValue(ctx, "user_id", "john@example.com")
+ return handler(newCtx, req)
+ }
+
+Unfortunately, it's not as easy for streaming RPCs. These have the `context.Context` embedded within
+the `grpc.ServerStream` object. To pass values through context, a wrapper (`WrappedServerStream`) is
+needed. For example:
+
+ func FakeAuthStreamingInterceptor(srv interface{}, stream grpc.ServerStream, info *grpc.StreamServerInfo, handler grpc.StreamHandler) error {
+ newStream := grpc_middleware.WrapServerStream(stream)
+ newStream.WrappedContext = context.WithValue(ctx, "user_id", "john@example.com")
+ return handler(srv, stream)
+ }
+
+## <a name="pkg-imports">Imported Packages</a>
+
+- [golang.org/x/net/context](https://godoc.org/golang.org/x/net/context)
+- [google.golang.org/grpc](https://godoc.org/google.golang.org/grpc)
+
+## <a name="pkg-index">Index</a>
+* [func ChainStreamClient(interceptors ...grpc.StreamClientInterceptor) grpc.StreamClientInterceptor](#ChainStreamClient)
+* [func ChainStreamServer(interceptors ...grpc.StreamServerInterceptor) grpc.StreamServerInterceptor](#ChainStreamServer)
+* [func ChainUnaryClient(interceptors ...grpc.UnaryClientInterceptor) grpc.UnaryClientInterceptor](#ChainUnaryClient)
+* [func ChainUnaryServer(interceptors ...grpc.UnaryServerInterceptor) grpc.UnaryServerInterceptor](#ChainUnaryServer)
+* [func WithStreamServerChain(interceptors ...grpc.StreamServerInterceptor) grpc.ServerOption](#WithStreamServerChain)
+* [func WithUnaryServerChain(interceptors ...grpc.UnaryServerInterceptor) grpc.ServerOption](#WithUnaryServerChain)
+* [type WrappedServerStream](#WrappedServerStream)
+ * [func WrapServerStream(stream grpc.ServerStream) \*WrappedServerStream](#WrapServerStream)
+ * [func (w \*WrappedServerStream) Context() context.Context](#WrappedServerStream.Context)
+
+#### <a name="pkg-files">Package files</a>
+[chain.go](./chain.go) [doc.go](./doc.go) [wrappers.go](./wrappers.go)
+
+## <a name="ChainStreamClient">func</a> [ChainStreamClient](./chain.go#L136)
+``` go
+func ChainStreamClient(interceptors ...grpc.StreamClientInterceptor) grpc.StreamClientInterceptor
+```
+ChainStreamClient creates a single interceptor out of a chain of many interceptors.
+
+Execution is done in left-to-right order, including passing of context.
+For example ChainStreamClient(one, two, three) will execute one before two before three.
+
+## <a name="ChainStreamServer">func</a> [ChainStreamServer](./chain.go#L58)
+``` go
+func ChainStreamServer(interceptors ...grpc.StreamServerInterceptor) grpc.StreamServerInterceptor
+```
+ChainStreamServer creates a single interceptor out of a chain of many interceptors.
+
+Execution is done in left-to-right order, including passing of context.
+For example ChainUnaryServer(one, two, three) will execute one before two before three.
+If you want to pass context between interceptors, use WrapServerStream.
+
+## <a name="ChainUnaryClient">func</a> [ChainUnaryClient](./chain.go#L97)
+``` go
+func ChainUnaryClient(interceptors ...grpc.UnaryClientInterceptor) grpc.UnaryClientInterceptor
+```
+ChainUnaryClient creates a single interceptor out of a chain of many interceptors.
+
+Execution is done in left-to-right order, including passing of context.
+For example ChainUnaryClient(one, two, three) will execute one before two before three.
+
+## <a name="ChainUnaryServer">func</a> [ChainUnaryServer](./chain.go#L18)
+``` go
+func ChainUnaryServer(interceptors ...grpc.UnaryServerInterceptor) grpc.UnaryServerInterceptor
+```
+ChainUnaryServer creates a single interceptor out of a chain of many interceptors.
+
+Execution is done in left-to-right order, including passing of context.
+For example ChainUnaryServer(one, two, three) will execute one before two before three, and three
+will see context changes of one and two.
+
+## <a name="WithStreamServerChain">func</a> [WithStreamServerChain](./chain.go#L181)
+``` go
+func WithStreamServerChain(interceptors ...grpc.StreamServerInterceptor) grpc.ServerOption
+```
+WithStreamServerChain is a grpc.Server config option that accepts multiple stream interceptors.
+Basically syntactic sugar.
+
+## <a name="WithUnaryServerChain">func</a> [WithUnaryServerChain](./chain.go#L175)
+``` go
+func WithUnaryServerChain(interceptors ...grpc.UnaryServerInterceptor) grpc.ServerOption
+```
+Chain creates a single interceptor out of a chain of many interceptors.
+
+WithUnaryServerChain is a grpc.Server config option that accepts multiple unary interceptors.
+Basically syntactic sugar.
+
+## <a name="WrappedServerStream">type</a> [WrappedServerStream](./wrappers.go#L12-L16)
+``` go
+type WrappedServerStream struct {
+ grpc.ServerStream
+ // WrappedContext is the wrapper's own Context. You can assign it.
+ WrappedContext context.Context
+}
+```
+WrappedServerStream is a thin wrapper around grpc.ServerStream that allows modifying context.
+
+### <a name="WrapServerStream">func</a> [WrapServerStream](./wrappers.go#L24)
+``` go
+func WrapServerStream(stream grpc.ServerStream) *WrappedServerStream
+```
+WrapServerStream returns a ServerStream that has the ability to overwrite context.
+
+### <a name="WrappedServerStream.Context">func</a> (\*WrappedServerStream) [Context](./wrappers.go#L19)
+``` go
+func (w *WrappedServerStream) Context() context.Context
+```
+Context returns the wrapper's WrappedContext, overwriting the nested grpc.ServerStream.Context()
+
+- - -
+Generated by [godoc2ghmd](https://github.com/GandalfUK/godoc2ghmd) \ No newline at end of file
diff --git a/vendor/github.com/grpc-ecosystem/go-grpc-middleware/Gopkg.lock b/vendor/github.com/grpc-ecosystem/go-grpc-middleware/Gopkg.lock
new file mode 100644
index 00000000..ebdcb75a
--- /dev/null
+++ b/vendor/github.com/grpc-ecosystem/go-grpc-middleware/Gopkg.lock
@@ -0,0 +1,123 @@
+# This file is autogenerated, do not edit; changes may be undone by the next 'dep ensure'.
+
+
+[[projects]]
+ name = "cloud.google.com/go"
+ packages = ["compute/metadata"]
+ revision = "2d3a6656c17a60b0815b7e06ab0be04eacb6e613"
+ version = "v0.16.0"
+
+[[projects]]
+ name = "github.com/davecgh/go-spew"
+ packages = ["spew"]
+ revision = "346938d642f2ec3594ed81d874461961cd0faa76"
+ version = "v1.1.0"
+
+[[projects]]
+ name = "github.com/gogo/protobuf"
+ packages = ["gogoproto","proto","protoc-gen-gogo/descriptor"]
+ revision = "342cbe0a04158f6dcb03ca0079991a51a4248c02"
+ version = "v0.5"
+
+[[projects]]
+ branch = "master"
+ name = "github.com/golang/protobuf"
+ packages = ["jsonpb","proto","ptypes","ptypes/any","ptypes/duration","ptypes/struct","ptypes/timestamp"]
+ revision = "1e59b77b52bf8e4b449a57e6f79f21226d571845"
+
+[[projects]]
+ name = "github.com/opentracing/opentracing-go"
+ packages = [".","ext","log","mocktracer"]
+ revision = "1949ddbfd147afd4d964a9f00b24eb291e0e7c38"
+ version = "v1.0.2"
+
+[[projects]]
+ name = "github.com/pmezard/go-difflib"
+ packages = ["difflib"]
+ revision = "792786c7400a136282c1664665ae0a8db921c6c2"
+ version = "v1.0.0"
+
+[[projects]]
+ name = "github.com/sirupsen/logrus"
+ packages = ["."]
+ revision = "f006c2ac4710855cf0f916dd6b77acf6b048dc6e"
+ version = "v1.0.3"
+
+[[projects]]
+ name = "github.com/stretchr/testify"
+ packages = ["assert","require","suite"]
+ revision = "69483b4bd14f5845b5a1e55bca19e954e827f1d0"
+ version = "v1.1.4"
+
+[[projects]]
+ name = "go.uber.org/atomic"
+ packages = ["."]
+ revision = "8474b86a5a6f79c443ce4b2992817ff32cf208b8"
+ version = "v1.3.1"
+
+[[projects]]
+ name = "go.uber.org/multierr"
+ packages = ["."]
+ revision = "3c4937480c32f4c13a875a1829af76c98ca3d40a"
+ version = "v1.1.0"
+
+[[projects]]
+ name = "go.uber.org/zap"
+ packages = [".","buffer","internal/bufferpool","internal/color","internal/exit","zapcore"]
+ revision = "35aad584952c3e7020db7b839f6b102de6271f89"
+ version = "v1.7.1"
+
+[[projects]]
+ branch = "master"
+ name = "golang.org/x/crypto"
+ packages = ["ssh/terminal"]
+ revision = "94eea52f7b742c7cbe0b03b22f0c4c8631ece122"
+
+[[projects]]
+ branch = "master"
+ name = "golang.org/x/net"
+ packages = ["context","context/ctxhttp","http2","http2/hpack","idna","internal/timeseries","lex/httplex","trace"]
+ revision = "a8b9294777976932365dabb6640cf1468d95c70f"
+
+[[projects]]
+ branch = "master"
+ name = "golang.org/x/oauth2"
+ packages = [".","google","internal","jws","jwt"]
+ revision = "f95fa95eaa936d9d87489b15d1d18b97c1ba9c28"
+
+[[projects]]
+ branch = "master"
+ name = "golang.org/x/sys"
+ packages = ["unix","windows"]
+ revision = "13fcbd661c8ececa8807a29b48407d674b1d8ed8"
+
+[[projects]]
+ branch = "master"
+ name = "golang.org/x/text"
+ packages = ["collate","collate/build","internal/colltab","internal/gen","internal/tag","internal/triegen","internal/ucd","language","secure/bidirule","transform","unicode/bidi","unicode/cldr","unicode/norm","unicode/rangetable"]
+ revision = "75cc3cad82b5f47d3fb229ddda8c5167da14f294"
+
+[[projects]]
+ name = "google.golang.org/appengine"
+ packages = [".","internal","internal/app_identity","internal/base","internal/datastore","internal/log","internal/modules","internal/remote_api","internal/urlfetch","urlfetch"]
+ revision = "150dc57a1b433e64154302bdc40b6bb8aefa313a"
+ version = "v1.0.0"
+
+[[projects]]
+ branch = "master"
+ name = "google.golang.org/genproto"
+ packages = ["googleapis/rpc/status"]
+ revision = "7f0da29060c682909f650ad8ed4e515bd74fa12a"
+
+[[projects]]
+ name = "google.golang.org/grpc"
+ packages = [".","balancer","balancer/roundrobin","codes","connectivity","credentials","credentials/oauth","encoding","grpclb/grpc_lb_v1/messages","grpclog","internal","keepalive","metadata","naming","peer","resolver","resolver/dns","resolver/passthrough","stats","status","tap","transport"]
+ revision = "5a9f7b402fe85096d2e1d0383435ee1876e863d0"
+ version = "v1.8.0"
+
+[solve-meta]
+ analyzer-name = "dep"
+ analyzer-version = 1
+ inputs-digest = "b24c6670412eb0bc44ed1db77fecc52333f8725f3e3272bdc568f5683a63031f"
+ solver-name = "gps-cdcl"
+ solver-version = 1
diff --git a/vendor/github.com/grpc-ecosystem/go-grpc-middleware/Gopkg.toml b/vendor/github.com/grpc-ecosystem/go-grpc-middleware/Gopkg.toml
new file mode 100644
index 00000000..0a7d4c1c
--- /dev/null
+++ b/vendor/github.com/grpc-ecosystem/go-grpc-middleware/Gopkg.toml
@@ -0,0 +1,35 @@
+[[constraint]]
+ name = "github.com/gogo/protobuf"
+ version = "0.5.0"
+
+[[constraint]]
+ branch = "master"
+ name = "github.com/golang/protobuf"
+
+[[constraint]]
+ name = "github.com/opentracing/opentracing-go"
+ version = "1.0.2"
+
+[[constraint]]
+ name = "github.com/sirupsen/logrus"
+ version = "1.0.3"
+
+[[constraint]]
+ name = "github.com/stretchr/testify"
+ version = "1.1.4"
+
+[[constraint]]
+ name = "go.uber.org/zap"
+ version = "1.7.1"
+
+[[constraint]]
+ branch = "master"
+ name = "golang.org/x/net"
+
+[[constraint]]
+ branch = "master"
+ name = "golang.org/x/oauth2"
+
+[[constraint]]
+ name = "google.golang.org/grpc"
+ version = "1.8.0"
diff --git a/vendor/github.com/grpc-ecosystem/go-grpc-middleware/LICENSE b/vendor/github.com/grpc-ecosystem/go-grpc-middleware/LICENSE
new file mode 100644
index 00000000..b2b06503
--- /dev/null
+++ b/vendor/github.com/grpc-ecosystem/go-grpc-middleware/LICENSE
@@ -0,0 +1,201 @@
+ Apache License
+ Version 2.0, January 2004
+ http://www.apache.org/licenses/
+
+ TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION
+
+ 1. Definitions.
+
+ "License" shall mean the terms and conditions for use, reproduction,
+ and distribution as defined by Sections 1 through 9 of this document.
+
+ "Licensor" shall mean the copyright owner or entity authorized by
+ the copyright owner that is granting the License.
+
+ "Legal Entity" shall mean the union of the acting entity and all
+ other entities that control, are controlled by, or are under common
+ control with that entity. For the purposes of this definition,
+ "control" means (i) the power, direct or indirect, to cause the
+ direction or management of such entity, whether by contract or
+ otherwise, or (ii) ownership of fifty percent (50%) or more of the
+ outstanding shares, or (iii) beneficial ownership of such entity.
+
+ "You" (or "Your") shall mean an individual or Legal Entity
+ exercising permissions granted by this License.
+
+ "Source" form shall mean the preferred form for making modifications,
+ including but not limited to software source code, documentation
+ source, and configuration files.
+
+ "Object" form shall mean any form resulting from mechanical
+ transformation or translation of a Source form, including but
+ not limited to compiled object code, generated documentation,
+ and conversions to other media types.
+
+ "Work" shall mean the work of authorship, whether in Source or
+ Object form, made available under the License, as indicated by a
+ copyright notice that is included in or attached to the work
+ (an example is provided in the Appendix below).
+
+ "Derivative Works" shall mean any work, whether in Source or Object
+ form, that is based on (or derived from) the Work and for which the
+ editorial revisions, annotations, elaborations, or other modifications
+ represent, as a whole, an original work of authorship. For the purposes
+ of this License, Derivative Works shall not include works that remain
+ separable from, or merely link (or bind by name) to the interfaces of,
+ the Work and Derivative Works thereof.
+
+ "Contribution" shall mean any work of authorship, including
+ the original version of the Work and any modifications or additions
+ to that Work or Derivative Works thereof, that is intentionally
+ submitted to Licensor for inclusion in the Work by the copyright owner
+ or by an individual or Legal Entity authorized to submit on behalf of
+ the copyright owner. For the purposes of this definition, "submitted"
+ means any form of electronic, verbal, or written communication sent
+ to the Licensor or its representatives, including but not limited to
+ communication on electronic mailing lists, source code control systems,
+ and issue tracking systems that are managed by, or on behalf of, the
+ Licensor for the purpose of discussing and improving the Work, but
+ excluding communication that is conspicuously marked or otherwise
+ designated in writing by the copyright owner as "Not a Contribution."
+
+ "Contributor" shall mean Licensor and any individual or Legal Entity
+ on behalf of whom a Contribution has been received by Licensor and
+ subsequently incorporated within the Work.
+
+ 2. Grant of Copyright License. Subject to the terms and conditions of
+ this License, each Contributor hereby grants to You a perpetual,
+ worldwide, non-exclusive, no-charge, royalty-free, irrevocable
+ copyright license to reproduce, prepare Derivative Works of,
+ publicly display, publicly perform, sublicense, and distribute the
+ Work and such Derivative Works in Source or Object form.
+
+ 3. Grant of Patent License. Subject to the terms and conditions of
+ this License, each Contributor hereby grants to You a perpetual,
+ worldwide, non-exclusive, no-charge, royalty-free, irrevocable
+ (except as stated in this section) patent license to make, have made,
+ use, offer to sell, sell, import, and otherwise transfer the Work,
+ where such license applies only to those patent claims licensable
+ by such Contributor that are necessarily infringed by their
+ Contribution(s) alone or by combination of their Contribution(s)
+ with the Work to which such Contribution(s) was submitted. If You
+ institute patent litigation against any entity (including a
+ cross-claim or counterclaim in a lawsuit) alleging that the Work
+ or a Contribution incorporated within the Work constitutes direct
+ or contributory patent infringement, then any patent licenses
+ granted to You under this License for that Work shall terminate
+ as of the date such litigation is filed.
+
+ 4. Redistribution. You may reproduce and distribute copies of the
+ Work or Derivative Works thereof in any medium, with or without
+ modifications, and in Source or Object form, provided that You
+ meet the following conditions:
+
+ (a) You must give any other recipients of the Work or
+ Derivative Works a copy of this License; and
+
+ (b) You must cause any modified files to carry prominent notices
+ stating that You changed the files; and
+
+ (c) You must retain, in the Source form of any Derivative Works
+ that You distribute, all copyright, patent, trademark, and
+ attribution notices from the Source form of the Work,
+ excluding those notices that do not pertain to any part of
+ the Derivative Works; and
+
+ (d) If the Work includes a "NOTICE" text file as part of its
+ distribution, then any Derivative Works that You distribute must
+ include a readable copy of the attribution notices contained
+ within such NOTICE file, excluding those notices that do not
+ pertain to any part of the Derivative Works, in at least one
+ of the following places: within a NOTICE text file distributed
+ as part of the Derivative Works; within the Source form or
+ documentation, if provided along with the Derivative Works; or,
+ within a display generated by the Derivative Works, if and
+ wherever such third-party notices normally appear. The contents
+ of the NOTICE file are for informational purposes only and
+ do not modify the License. You may add Your own attribution
+ notices within Derivative Works that You distribute, alongside
+ or as an addendum to the NOTICE text from the Work, provided
+ that such additional attribution notices cannot be construed
+ as modifying the License.
+
+ You may add Your own copyright statement to Your modifications and
+ may provide additional or different license terms and conditions
+ for use, reproduction, or distribution of Your modifications, or
+ for any such Derivative Works as a whole, provided Your use,
+ reproduction, and distribution of the Work otherwise complies with
+ the conditions stated in this License.
+
+ 5. Submission of Contributions. Unless You explicitly state otherwise,
+ any Contribution intentionally submitted for inclusion in the Work
+ by You to the Licensor shall be under the terms and conditions of
+ this License, without any additional terms or conditions.
+ Notwithstanding the above, nothing herein shall supersede or modify
+ the terms of any separate license agreement you may have executed
+ with Licensor regarding such Contributions.
+
+ 6. Trademarks. This License does not grant permission to use the trade
+ names, trademarks, service marks, or product names of the Licensor,
+ except as required for reasonable and customary use in describing the
+ origin of the Work and reproducing the content of the NOTICE file.
+
+ 7. Disclaimer of Warranty. Unless required by applicable law or
+ agreed to in writing, Licensor provides the Work (and each
+ Contributor provides its Contributions) on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
+ implied, including, without limitation, any warranties or conditions
+ of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A
+ PARTICULAR PURPOSE. You are solely responsible for determining the
+ appropriateness of using or redistributing the Work and assume any
+ risks associated with Your exercise of permissions under this License.
+
+ 8. Limitation of Liability. In no event and under no legal theory,
+ whether in tort (including negligence), contract, or otherwise,
+ unless required by applicable law (such as deliberate and grossly
+ negligent acts) or agreed to in writing, shall any Contributor be
+ liable to You for damages, including any direct, indirect, special,
+ incidental, or consequential damages of any character arising as a
+ result of this License or out of the use or inability to use the
+ Work (including but not limited to damages for loss of goodwill,
+ work stoppage, computer failure or malfunction, or any and all
+ other commercial damages or losses), even if such Contributor
+ has been advised of the possibility of such damages.
+
+ 9. Accepting Warranty or Additional Liability. While redistributing
+ the Work or Derivative Works thereof, You may choose to offer,
+ and charge a fee for, acceptance of support, warranty, indemnity,
+ or other liability obligations and/or rights consistent with this
+ License. However, in accepting such obligations, You may act only
+ on Your own behalf and on Your sole responsibility, not on behalf
+ of any other Contributor, and only if You agree to indemnify,
+ defend, and hold each Contributor harmless for any liability
+ incurred by, or claims asserted against, such Contributor by reason
+ of your accepting any such warranty or additional liability.
+
+ END OF TERMS AND CONDITIONS
+
+ APPENDIX: How to apply the Apache License to your work.
+
+ To apply the Apache License to your work, attach the following
+ boilerplate notice, with the fields enclosed by brackets "[]"
+ replaced with your own identifying information. (Don't include
+ the brackets!) The text should be enclosed in the appropriate
+ comment syntax for the file format. We also recommend that a
+ file or class name and description of purpose be included on the
+ same "printed page" as the copyright notice for easier
+ identification within third-party archives.
+
+ Copyright [yyyy] [name of copyright owner]
+
+ Licensed under the Apache License, Version 2.0 (the "License");
+ you may not use this file except in compliance with the License.
+ You may obtain a copy of the License at
+
+ http://www.apache.org/licenses/LICENSE-2.0
+
+ Unless required by applicable law or agreed to in writing, software
+ distributed under the License is distributed on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ See the License for the specific language governing permissions and
+ limitations under the License. \ No newline at end of file
diff --git a/vendor/github.com/grpc-ecosystem/go-grpc-middleware/README.md b/vendor/github.com/grpc-ecosystem/go-grpc-middleware/README.md
new file mode 100644
index 00000000..4fe246f2
--- /dev/null
+++ b/vendor/github.com/grpc-ecosystem/go-grpc-middleware/README.md
@@ -0,0 +1,86 @@
+# Go gRPC Middleware
+
+[![Travis Build](https://travis-ci.org/grpc-ecosystem/go-grpc-middleware.svg?branch=master)](https://travis-ci.org/grpc-ecosystem/go-grpc-middleware)
+[![Go Report Card](https://goreportcard.com/badge/github.com/grpc-ecosystem/go-grpc-middleware)](https://goreportcard.com/report/github.com/grpc-ecosystem/go-grpc-middleware)
+[![GoDoc](http://img.shields.io/badge/GoDoc-Reference-blue.svg)](https://godoc.org/github.com/grpc-ecosystem/go-grpc-middleware)
+[![SourceGraph](https://sourcegraph.com/github.com/grpc-ecosystem/go-grpc-middleware/-/badge.svg)](https://sourcegraph.com/github.com/grpc-ecosystem/go-grpc-middleware/?badge)
+[![codecov](https://codecov.io/gh/grpc-ecosystem/go-grpc-middleware/branch/master/graph/badge.svg)](https://codecov.io/gh/grpc-ecosystem/go-grpc-middleware)
+[![Apache 2.0 License](https://img.shields.io/badge/License-Apache%202.0-blue.svg)](LICENSE)
+[![quality: production](https://img.shields.io/badge/quality-production-orange.svg)](#status)
+
+
+[gRPC Go](https://github.com/grpc/grpc-go) Middleware: interceptors, helpers, utilities.
+
+**Important** The repo recently moved to `github.com/grpc-ecosystem/go-grpc-middleware`, please update your import paths.
+
+## Middleware
+
+[gRPC Go](https://github.com/grpc/grpc-go) recently acquired support for
+Interceptors, i.e. [middleware](https://medium.com/@matryer/writing-middleware-in-golang-and-how-go-makes-it-so-much-fun-4375c1246e81#.gv7tdlghs)
+that is executed either on the gRPC Server before the request is passed onto the user's application logic, or on the gRPC client either around the user call. It is a perfect way to implement
+common patterns: auth, logging, message, validation, retries or monitoring.
+
+These are generic building blocks that make it easy to build multiple microservices easily.
+The purpose of this repository is to act as a go-to point for such reusable functionality. It contains
+some of them itself, but also will link to useful external repos.
+
+`grpc_middleware` itself provides support for chaining interceptors. See [Documentation](DOC.md), but here's an example:
+
+```go
+import "github.com/grpc-ecosystem/go-grpc-middleware"
+
+myServer := grpc.NewServer(
+ grpc.StreamInterceptor(grpc_middleware.ChainStreamServer(
+ grpc_ctxtags.StreamServerInterceptor(),
+ grpc_opentracing.StreamServerInterceptor(),
+ grpc_prometheus.StreamServerInterceptor,
+ grpc_zap.StreamServerInterceptor(zapLogger),
+ grpc_auth.StreamServerInterceptor(myAuthFunction),
+ grpc_recovery.StreamServerInterceptor(),
+ )),
+ grpc.UnaryInterceptor(grpc_middleware.ChainUnaryServer(
+ grpc_ctxtags.UnaryServerInterceptor(),
+ grpc_opentracing.UnaryServerInterceptor(),
+ grpc_prometheus.UnaryServerInterceptor,
+ grpc_zap.UnaryServerInterceptor(zapLogger),
+ grpc_auth.UnaryServerInterceptor(myAuthFunction),
+ grpc_recovery.UnaryServerInterceptor(),
+ )),
+)
+```
+
+## Interceptors
+
+*Please send a PR to add new interceptors or middleware to this list*
+
+#### Auth
+ * [`grpc_auth`](auth) - a customizable (via `AuthFunc`) piece of auth middleware
+
+#### Logging
+ * [`grpc_ctxtags`](tags/) - a library that adds a `Tag` map to context, with data populated from request body
+ * [`grpc_zap`](logging/zap/) - integration of [zap](https://github.com/uber-go/zap) logging library into gRPC handlers.
+ * [`grpc_logrus`](logging/logrus/) - integration of [logrus](https://github.com/sirupsen/logrus) logging library into gRPC handlers.
+
+
+#### Monitoring
+ * [`grpc_prometheus`âš¡](https://github.com/grpc-ecosystem/go-grpc-prometheus) - Prometheus client-side and server-side monitoring middleware
+ * [`otgrpc`âš¡](https://github.com/grpc-ecosystem/grpc-opentracing/tree/master/go/otgrpc) - [OpenTracing](http://opentracing.io/) client-side and server-side interceptors
+ * [`grpc_opentracing`](tracing/opentracing) - [OpenTracing](http://opentracing.io/) client-side and server-side interceptors with support for streaming and handler-returned tags
+
+#### Client
+ * [`grpc_retry`](retry/) - a generic gRPC response code retry mechanism, client-side middleware
+
+#### Server
+ * [`grpc_validator`](validator/) - codegen inbound message validation from `.proto` options
+ * [`grpc_recovery`](recovery/) - turn panics into gRPC errors
+
+
+## Status
+
+This code has been running in *production* since May 2016 as the basis of the gRPC micro services stack at [Improbable](https://improbable.io).
+
+Additional tooling will be added, and contributions are welcome.
+
+## License
+
+`go-grpc-middleware` is released under the Apache 2.0 license. See the [LICENSE](LICENSE) file for details.
diff --git a/vendor/github.com/grpc-ecosystem/go-grpc-middleware/auth/DOC.md b/vendor/github.com/grpc-ecosystem/go-grpc-middleware/auth/DOC.md
new file mode 100644
index 00000000..5834112b
--- /dev/null
+++ b/vendor/github.com/grpc-ecosystem/go-grpc-middleware/auth/DOC.md
@@ -0,0 +1,148 @@
+# grpc_auth
+`import "github.com/grpc-ecosystem/go-grpc-middleware/auth"`
+
+* [Overview](#pkg-overview)
+* [Imported Packages](#pkg-imports)
+* [Index](#pkg-index)
+* [Examples](#pkg-examples)
+
+## <a name="pkg-overview">Overview</a>
+`grpc_auth` a generic server-side auth middleware for gRPC.
+
+### Server Side Auth Middleware
+It allows for easy assertion of `:authorization` headers in gRPC calls, be it HTTP Basic auth, or
+OAuth2 Bearer tokens.
+
+The middleware takes a user-customizable `AuthFunc`, which can be customized to verify and extract
+auth information from the request. The extracted information can be put in the `context.Context` of
+handlers downstream for retrieval.
+
+It also allows for per-service implementation overrides of `AuthFunc`. See `ServiceAuthFuncOverride`.
+
+Please see examples for simple examples of use.
+
+#### Example:
+
+<details>
+<summary>Click to expand code.</summary>
+
+```go
+package grpc_auth_test
+
+import (
+ "github.com/grpc-ecosystem/go-grpc-middleware/auth"
+ "github.com/grpc-ecosystem/go-grpc-middleware/tags"
+ "golang.org/x/net/context"
+ "google.golang.org/grpc"
+ "google.golang.org/grpc/codes"
+)
+
+var (
+ cc *grpc.ClientConn
+)
+
+func parseToken(token string) (struct{}, error) {
+ return struct{}{}, nil
+}
+
+func userClaimFromToken(struct{}) string {
+ return "foobar"
+}
+
+// Simple example of server initialization code.
+func Example_serverConfig() {
+ exampleAuthFunc := func(ctx context.Context) (context.Context, error) {
+ token, err := grpc_auth.AuthFromMD(ctx, "bearer")
+ if err != nil {
+ return nil, err
+ }
+ tokenInfo, err := parseToken(token)
+ if err != nil {
+ return nil, grpc.Errorf(codes.Unauthenticated, "invalid auth token: %v", err)
+ }
+ grpc_ctxtags.Extract(ctx).Set("auth.sub", userClaimFromToken(tokenInfo))
+ newCtx := context.WithValue(ctx, "tokenInfo", tokenInfo)
+ return newCtx, nil
+ }
+
+ _ = grpc.NewServer(
+ grpc.StreamInterceptor(grpc_auth.StreamServerInterceptor(exampleAuthFunc)),
+ grpc.UnaryInterceptor(grpc_auth.UnaryServerInterceptor(exampleAuthFunc)),
+ )
+}
+```
+
+</details>
+
+## <a name="pkg-imports">Imported Packages</a>
+
+- [github.com/grpc-ecosystem/go-grpc-middleware](./..)
+- [github.com/grpc-ecosystem/go-grpc-middleware/util/metautils](./../util/metautils)
+- [golang.org/x/net/context](https://godoc.org/golang.org/x/net/context)
+- [google.golang.org/grpc](https://godoc.org/google.golang.org/grpc)
+- [google.golang.org/grpc/codes](https://godoc.org/google.golang.org/grpc/codes)
+
+## <a name="pkg-index">Index</a>
+* [func AuthFromMD(ctx context.Context, expectedScheme string) (string, error)](#AuthFromMD)
+* [func StreamServerInterceptor(authFunc AuthFunc) grpc.StreamServerInterceptor](#StreamServerInterceptor)
+* [func UnaryServerInterceptor(authFunc AuthFunc) grpc.UnaryServerInterceptor](#UnaryServerInterceptor)
+* [type AuthFunc](#AuthFunc)
+* [type ServiceAuthFuncOverride](#ServiceAuthFuncOverride)
+
+#### <a name="pkg-examples">Examples</a>
+* [Package (ServerConfig)](#example__serverConfig)
+
+#### <a name="pkg-files">Package files</a>
+[auth.go](./auth.go) [doc.go](./doc.go) [metadata.go](./metadata.go)
+
+## <a name="AuthFromMD">func</a> [AuthFromMD](./metadata.go#L24)
+``` go
+func AuthFromMD(ctx context.Context, expectedScheme string) (string, error)
+```
+AuthFromMD is a helper function for extracting the :authorization header from the gRPC metadata of the request.
+
+It expects the `:authorization` header to be of a certain scheme (e.g. `basic`, `bearer`), in a
+case-insensitive format (see rfc2617, sec 1.2). If no such authorization is found, or the token
+is of wrong scheme, an error with gRPC status `Unauthenticated` is returned.
+
+## <a name="StreamServerInterceptor">func</a> [StreamServerInterceptor](./auth.go#L51)
+``` go
+func StreamServerInterceptor(authFunc AuthFunc) grpc.StreamServerInterceptor
+```
+StreamServerInterceptor returns a new unary server interceptors that performs per-request auth.
+
+## <a name="UnaryServerInterceptor">func</a> [UnaryServerInterceptor](./auth.go#L34)
+``` go
+func UnaryServerInterceptor(authFunc AuthFunc) grpc.UnaryServerInterceptor
+```
+UnaryServerInterceptor returns a new unary server interceptors that performs per-request auth.
+
+## <a name="AuthFunc">type</a> [AuthFunc](./auth.go#L23)
+``` go
+type AuthFunc func(ctx context.Context) (context.Context, error)
+```
+AuthFunc is the pluggable function that performs authentication.
+
+The passed in `Context` will contain the gRPC metadata.MD object (for header-based authentication) and
+the peer.Peer information that can contain transport-based credentials (e.g. `credentials.AuthInfo`).
+
+The returned context will be propagated to handlers, allowing user changes to `Context`. However,
+please make sure that the `Context` returned is a child `Context` of the one passed in.
+
+If error is returned, its `grpc.Code()` will be returned to the user as well as the verbatim message.
+Please make sure you use `codes.Unauthenticated` (lacking auth) and `codes.PermissionDenied`
+(authed, but lacking perms) appropriately.
+
+## <a name="ServiceAuthFuncOverride">type</a> [ServiceAuthFuncOverride](./auth.go#L29-L31)
+``` go
+type ServiceAuthFuncOverride interface {
+ AuthFuncOverride(ctx context.Context, fullMethodName string) (context.Context, error)
+}
+```
+ServiceAuthFuncOverride allows a given gRPC service implementation to override the global `AuthFunc`.
+
+If a service implements the AuthFuncOverride method, it takes precedence over the `AuthFunc` method,
+and will be called instead of AuthFunc for all method invocations within that service.
+
+- - -
+Generated by [godoc2ghmd](https://github.com/GandalfUK/godoc2ghmd) \ No newline at end of file
diff --git a/vendor/github.com/grpc-ecosystem/go-grpc-middleware/auth/README.md b/vendor/github.com/grpc-ecosystem/go-grpc-middleware/auth/README.md
new file mode 100644
index 00000000..5834112b
--- /dev/null
+++ b/vendor/github.com/grpc-ecosystem/go-grpc-middleware/auth/README.md
@@ -0,0 +1,148 @@
+# grpc_auth
+`import "github.com/grpc-ecosystem/go-grpc-middleware/auth"`
+
+* [Overview](#pkg-overview)
+* [Imported Packages](#pkg-imports)
+* [Index](#pkg-index)
+* [Examples](#pkg-examples)
+
+## <a name="pkg-overview">Overview</a>
+`grpc_auth` a generic server-side auth middleware for gRPC.
+
+### Server Side Auth Middleware
+It allows for easy assertion of `:authorization` headers in gRPC calls, be it HTTP Basic auth, or
+OAuth2 Bearer tokens.
+
+The middleware takes a user-customizable `AuthFunc`, which can be customized to verify and extract
+auth information from the request. The extracted information can be put in the `context.Context` of
+handlers downstream for retrieval.
+
+It also allows for per-service implementation overrides of `AuthFunc`. See `ServiceAuthFuncOverride`.
+
+Please see examples for simple examples of use.
+
+#### Example:
+
+<details>
+<summary>Click to expand code.</summary>
+
+```go
+package grpc_auth_test
+
+import (
+ "github.com/grpc-ecosystem/go-grpc-middleware/auth"
+ "github.com/grpc-ecosystem/go-grpc-middleware/tags"
+ "golang.org/x/net/context"
+ "google.golang.org/grpc"
+ "google.golang.org/grpc/codes"
+)
+
+var (
+ cc *grpc.ClientConn
+)
+
+func parseToken(token string) (struct{}, error) {
+ return struct{}{}, nil
+}
+
+func userClaimFromToken(struct{}) string {
+ return "foobar"
+}
+
+// Simple example of server initialization code.
+func Example_serverConfig() {
+ exampleAuthFunc := func(ctx context.Context) (context.Context, error) {
+ token, err := grpc_auth.AuthFromMD(ctx, "bearer")
+ if err != nil {
+ return nil, err
+ }
+ tokenInfo, err := parseToken(token)
+ if err != nil {
+ return nil, grpc.Errorf(codes.Unauthenticated, "invalid auth token: %v", err)
+ }
+ grpc_ctxtags.Extract(ctx).Set("auth.sub", userClaimFromToken(tokenInfo))
+ newCtx := context.WithValue(ctx, "tokenInfo", tokenInfo)
+ return newCtx, nil
+ }
+
+ _ = grpc.NewServer(
+ grpc.StreamInterceptor(grpc_auth.StreamServerInterceptor(exampleAuthFunc)),
+ grpc.UnaryInterceptor(grpc_auth.UnaryServerInterceptor(exampleAuthFunc)),
+ )
+}
+```
+
+</details>
+
+## <a name="pkg-imports">Imported Packages</a>
+
+- [github.com/grpc-ecosystem/go-grpc-middleware](./..)
+- [github.com/grpc-ecosystem/go-grpc-middleware/util/metautils](./../util/metautils)
+- [golang.org/x/net/context](https://godoc.org/golang.org/x/net/context)
+- [google.golang.org/grpc](https://godoc.org/google.golang.org/grpc)
+- [google.golang.org/grpc/codes](https://godoc.org/google.golang.org/grpc/codes)
+
+## <a name="pkg-index">Index</a>
+* [func AuthFromMD(ctx context.Context, expectedScheme string) (string, error)](#AuthFromMD)
+* [func StreamServerInterceptor(authFunc AuthFunc) grpc.StreamServerInterceptor](#StreamServerInterceptor)
+* [func UnaryServerInterceptor(authFunc AuthFunc) grpc.UnaryServerInterceptor](#UnaryServerInterceptor)
+* [type AuthFunc](#AuthFunc)
+* [type ServiceAuthFuncOverride](#ServiceAuthFuncOverride)
+
+#### <a name="pkg-examples">Examples</a>
+* [Package (ServerConfig)](#example__serverConfig)
+
+#### <a name="pkg-files">Package files</a>
+[auth.go](./auth.go) [doc.go](./doc.go) [metadata.go](./metadata.go)
+
+## <a name="AuthFromMD">func</a> [AuthFromMD](./metadata.go#L24)
+``` go
+func AuthFromMD(ctx context.Context, expectedScheme string) (string, error)
+```
+AuthFromMD is a helper function for extracting the :authorization header from the gRPC metadata of the request.
+
+It expects the `:authorization` header to be of a certain scheme (e.g. `basic`, `bearer`), in a
+case-insensitive format (see rfc2617, sec 1.2). If no such authorization is found, or the token
+is of wrong scheme, an error with gRPC status `Unauthenticated` is returned.
+
+## <a name="StreamServerInterceptor">func</a> [StreamServerInterceptor](./auth.go#L51)
+``` go
+func StreamServerInterceptor(authFunc AuthFunc) grpc.StreamServerInterceptor
+```
+StreamServerInterceptor returns a new unary server interceptors that performs per-request auth.
+
+## <a name="UnaryServerInterceptor">func</a> [UnaryServerInterceptor](./auth.go#L34)
+``` go
+func UnaryServerInterceptor(authFunc AuthFunc) grpc.UnaryServerInterceptor
+```
+UnaryServerInterceptor returns a new unary server interceptors that performs per-request auth.
+
+## <a name="AuthFunc">type</a> [AuthFunc](./auth.go#L23)
+``` go
+type AuthFunc func(ctx context.Context) (context.Context, error)
+```
+AuthFunc is the pluggable function that performs authentication.
+
+The passed in `Context` will contain the gRPC metadata.MD object (for header-based authentication) and
+the peer.Peer information that can contain transport-based credentials (e.g. `credentials.AuthInfo`).
+
+The returned context will be propagated to handlers, allowing user changes to `Context`. However,
+please make sure that the `Context` returned is a child `Context` of the one passed in.
+
+If error is returned, its `grpc.Code()` will be returned to the user as well as the verbatim message.
+Please make sure you use `codes.Unauthenticated` (lacking auth) and `codes.PermissionDenied`
+(authed, but lacking perms) appropriately.
+
+## <a name="ServiceAuthFuncOverride">type</a> [ServiceAuthFuncOverride](./auth.go#L29-L31)
+``` go
+type ServiceAuthFuncOverride interface {
+ AuthFuncOverride(ctx context.Context, fullMethodName string) (context.Context, error)
+}
+```
+ServiceAuthFuncOverride allows a given gRPC service implementation to override the global `AuthFunc`.
+
+If a service implements the AuthFuncOverride method, it takes precedence over the `AuthFunc` method,
+and will be called instead of AuthFunc for all method invocations within that service.
+
+- - -
+Generated by [godoc2ghmd](https://github.com/GandalfUK/godoc2ghmd) \ No newline at end of file
diff --git a/vendor/github.com/grpc-ecosystem/go-grpc-middleware/auth/auth.go b/vendor/github.com/grpc-ecosystem/go-grpc-middleware/auth/auth.go
new file mode 100644
index 00000000..a35c95fa
--- /dev/null
+++ b/vendor/github.com/grpc-ecosystem/go-grpc-middleware/auth/auth.go
@@ -0,0 +1,67 @@
+// Copyright 2016 Michal Witkowski. All Rights Reserved.
+// See LICENSE for licensing terms.
+
+package grpc_auth
+
+import (
+ "github.com/grpc-ecosystem/go-grpc-middleware"
+ "golang.org/x/net/context"
+ "google.golang.org/grpc"
+)
+
+// AuthFunc is the pluggable function that performs authentication.
+//
+// The passed in `Context` will contain the gRPC metadata.MD object (for header-based authentication) and
+// the peer.Peer information that can contain transport-based credentials (e.g. `credentials.AuthInfo`).
+//
+// The returned context will be propagated to handlers, allowing user changes to `Context`. However,
+// please make sure that the `Context` returned is a child `Context` of the one passed in.
+//
+// If error is returned, its `grpc.Code()` will be returned to the user as well as the verbatim message.
+// Please make sure you use `codes.Unauthenticated` (lacking auth) and `codes.PermissionDenied`
+// (authed, but lacking perms) appropriately.
+type AuthFunc func(ctx context.Context) (context.Context, error)
+
+// ServiceAuthFuncOverride allows a given gRPC service implementation to override the global `AuthFunc`.
+//
+// If a service implements the AuthFuncOverride method, it takes precedence over the `AuthFunc` method,
+// and will be called instead of AuthFunc for all method invocations within that service.
+type ServiceAuthFuncOverride interface {
+ AuthFuncOverride(ctx context.Context, fullMethodName string) (context.Context, error)
+}
+
+// UnaryServerInterceptor returns a new unary server interceptors that performs per-request auth.
+func UnaryServerInterceptor(authFunc AuthFunc) grpc.UnaryServerInterceptor {
+ return func(ctx context.Context, req interface{}, info *grpc.UnaryServerInfo, handler grpc.UnaryHandler) (interface{}, error) {
+ var newCtx context.Context
+ var err error
+ if overrideSrv, ok := info.Server.(ServiceAuthFuncOverride); ok {
+ newCtx, err = overrideSrv.AuthFuncOverride(ctx, info.FullMethod)
+ } else {
+ newCtx, err = authFunc(ctx)
+ }
+ if err != nil {
+ return nil, err
+ }
+ return handler(newCtx, req)
+ }
+}
+
+// StreamServerInterceptor returns a new unary server interceptors that performs per-request auth.
+func StreamServerInterceptor(authFunc AuthFunc) grpc.StreamServerInterceptor {
+ return func(srv interface{}, stream grpc.ServerStream, info *grpc.StreamServerInfo, handler grpc.StreamHandler) error {
+ var newCtx context.Context
+ var err error
+ if overrideSrv, ok := srv.(ServiceAuthFuncOverride); ok {
+ newCtx, err = overrideSrv.AuthFuncOverride(stream.Context(), info.FullMethod)
+ } else {
+ newCtx, err = authFunc(stream.Context())
+ }
+ if err != nil {
+ return err
+ }
+ wrapped := grpc_middleware.WrapServerStream(stream)
+ wrapped.WrappedContext = newCtx
+ return handler(srv, wrapped)
+ }
+}
diff --git a/vendor/github.com/grpc-ecosystem/go-grpc-middleware/auth/doc.go b/vendor/github.com/grpc-ecosystem/go-grpc-middleware/auth/doc.go
new file mode 100644
index 00000000..0550f023
--- /dev/null
+++ b/vendor/github.com/grpc-ecosystem/go-grpc-middleware/auth/doc.go
@@ -0,0 +1,20 @@
+// Copyright 2016 Michal Witkowski. All Rights Reserved.
+// See LICENSE for licensing terms.
+
+/*
+`grpc_auth` a generic server-side auth middleware for gRPC.
+
+Server Side Auth Middleware
+
+It allows for easy assertion of `:authorization` headers in gRPC calls, be it HTTP Basic auth, or
+OAuth2 Bearer tokens.
+
+The middleware takes a user-customizable `AuthFunc`, which can be customized to verify and extract
+auth information from the request. The extracted information can be put in the `context.Context` of
+handlers downstream for retrieval.
+
+It also allows for per-service implementation overrides of `AuthFunc`. See `ServiceAuthFuncOverride`.
+
+Please see examples for simple examples of use.
+*/
+package grpc_auth
diff --git a/vendor/github.com/grpc-ecosystem/go-grpc-middleware/auth/metadata.go b/vendor/github.com/grpc-ecosystem/go-grpc-middleware/auth/metadata.go
new file mode 100644
index 00000000..50020653
--- /dev/null
+++ b/vendor/github.com/grpc-ecosystem/go-grpc-middleware/auth/metadata.go
@@ -0,0 +1,38 @@
+// Copyright 2016 Michal Witkowski. All Rights Reserved.
+// See LICENSE for licensing terms.
+
+package grpc_auth
+
+import (
+ "strings"
+
+ "github.com/grpc-ecosystem/go-grpc-middleware/util/metautils"
+ "golang.org/x/net/context"
+ "google.golang.org/grpc"
+ "google.golang.org/grpc/codes"
+)
+
+var (
+ headerAuthorize = "authorization"
+)
+
+// AuthFromMD is a helper function for extracting the :authorization header from the gRPC metadata of the request.
+//
+// It expects the `:authorization` header to be of a certain scheme (e.g. `basic`, `bearer`), in a
+// case-insensitive format (see rfc2617, sec 1.2). If no such authorization is found, or the token
+// is of wrong scheme, an error with gRPC status `Unauthenticated` is returned.
+func AuthFromMD(ctx context.Context, expectedScheme string) (string, error) {
+ val := metautils.ExtractIncoming(ctx).Get(headerAuthorize)
+ if val == "" {
+ return "", grpc.Errorf(codes.Unauthenticated, "Request unauthenticated with "+expectedScheme)
+
+ }
+ splits := strings.SplitN(val, " ", 2)
+ if len(splits) < 2 {
+ return "", grpc.Errorf(codes.Unauthenticated, "Bad authorization string")
+ }
+ if strings.ToLower(splits[0]) != strings.ToLower(expectedScheme) {
+ return "", grpc.Errorf(codes.Unauthenticated, "Request unauthenticated with "+expectedScheme)
+ }
+ return splits[1], nil
+}
diff --git a/vendor/github.com/grpc-ecosystem/go-grpc-middleware/chain.go b/vendor/github.com/grpc-ecosystem/go-grpc-middleware/chain.go
new file mode 100644
index 00000000..45a2f5f4
--- /dev/null
+++ b/vendor/github.com/grpc-ecosystem/go-grpc-middleware/chain.go
@@ -0,0 +1,183 @@
+// Copyright 2016 Michal Witkowski. All Rights Reserved.
+// See LICENSE for licensing terms.
+
+// gRPC Server Interceptor chaining middleware.
+
+package grpc_middleware
+
+import (
+ "golang.org/x/net/context"
+ "google.golang.org/grpc"
+)
+
+// ChainUnaryServer creates a single interceptor out of a chain of many interceptors.
+//
+// Execution is done in left-to-right order, including passing of context.
+// For example ChainUnaryServer(one, two, three) will execute one before two before three, and three
+// will see context changes of one and two.
+func ChainUnaryServer(interceptors ...grpc.UnaryServerInterceptor) grpc.UnaryServerInterceptor {
+ n := len(interceptors)
+
+ if n > 1 {
+ lastI := n - 1
+ return func(ctx context.Context, req interface{}, info *grpc.UnaryServerInfo, handler grpc.UnaryHandler) (interface{}, error) {
+ var (
+ chainHandler grpc.UnaryHandler
+ curI int
+ )
+
+ chainHandler = func(currentCtx context.Context, currentReq interface{}) (interface{}, error) {
+ if curI == lastI {
+ return handler(currentCtx, currentReq)
+ }
+ curI++
+ resp, err := interceptors[curI](currentCtx, currentReq, info, chainHandler)
+ curI--
+ return resp, err
+ }
+
+ return interceptors[0](ctx, req, info, chainHandler)
+ }
+ }
+
+ if n == 1 {
+ return interceptors[0]
+ }
+
+ // n == 0; Dummy interceptor maintained for backward compatibility to avoid returning nil.
+ return func(ctx context.Context, req interface{}, _ *grpc.UnaryServerInfo, handler grpc.UnaryHandler) (interface{}, error) {
+ return handler(ctx, req)
+ }
+}
+
+// ChainStreamServer creates a single interceptor out of a chain of many interceptors.
+//
+// Execution is done in left-to-right order, including passing of context.
+// For example ChainUnaryServer(one, two, three) will execute one before two before three.
+// If you want to pass context between interceptors, use WrapServerStream.
+func ChainStreamServer(interceptors ...grpc.StreamServerInterceptor) grpc.StreamServerInterceptor {
+ n := len(interceptors)
+
+ if n > 1 {
+ lastI := n - 1
+ return func(srv interface{}, stream grpc.ServerStream, info *grpc.StreamServerInfo, handler grpc.StreamHandler) error {
+ var (
+ chainHandler grpc.StreamHandler
+ curI int
+ )
+
+ chainHandler = func(currentSrv interface{}, currentStream grpc.ServerStream) error {
+ if curI == lastI {
+ return handler(currentSrv, currentStream)
+ }
+ curI++
+ err := interceptors[curI](currentSrv, currentStream, info, chainHandler)
+ curI--
+ return err
+ }
+
+ return interceptors[0](srv, stream, info, chainHandler)
+ }
+ }
+
+ if n == 1 {
+ return interceptors[0]
+ }
+
+ // n == 0; Dummy interceptor maintained for backward compatibility to avoid returning nil.
+ return func(srv interface{}, stream grpc.ServerStream, _ *grpc.StreamServerInfo, handler grpc.StreamHandler) error {
+ return handler(srv, stream)
+ }
+}
+
+// ChainUnaryClient creates a single interceptor out of a chain of many interceptors.
+//
+// Execution is done in left-to-right order, including passing of context.
+// For example ChainUnaryClient(one, two, three) will execute one before two before three.
+func ChainUnaryClient(interceptors ...grpc.UnaryClientInterceptor) grpc.UnaryClientInterceptor {
+ n := len(interceptors)
+
+ if n > 1 {
+ lastI := n - 1
+ return func(ctx context.Context, method string, req, reply interface{}, cc *grpc.ClientConn, invoker grpc.UnaryInvoker, opts ...grpc.CallOption) error {
+ var (
+ chainHandler grpc.UnaryInvoker
+ curI int
+ )
+
+ chainHandler = func(currentCtx context.Context, currentMethod string, currentReq, currentRepl interface{}, currentConn *grpc.ClientConn, currentOpts ...grpc.CallOption) error {
+ if curI == lastI {
+ return invoker(currentCtx, currentMethod, currentReq, currentRepl, currentConn, currentOpts...)
+ }
+ curI++
+ err := interceptors[curI](currentCtx, currentMethod, currentReq, currentRepl, currentConn, chainHandler, currentOpts...)
+ curI--
+ return err
+ }
+
+ return interceptors[0](ctx, method, req, reply, cc, chainHandler, opts...)
+ }
+ }
+
+ if n == 1 {
+ return interceptors[0]
+ }
+
+ // n == 0; Dummy interceptor maintained for backward compatibility to avoid returning nil.
+ return func(ctx context.Context, method string, req, reply interface{}, cc *grpc.ClientConn, invoker grpc.UnaryInvoker, opts ...grpc.CallOption) error {
+ return invoker(ctx, method, req, reply, cc, opts...)
+ }
+}
+
+// ChainStreamClient creates a single interceptor out of a chain of many interceptors.
+//
+// Execution is done in left-to-right order, including passing of context.
+// For example ChainStreamClient(one, two, three) will execute one before two before three.
+func ChainStreamClient(interceptors ...grpc.StreamClientInterceptor) grpc.StreamClientInterceptor {
+ n := len(interceptors)
+
+ if n > 1 {
+ lastI := n - 1
+ return func(ctx context.Context, desc *grpc.StreamDesc, cc *grpc.ClientConn, method string, streamer grpc.Streamer, opts ...grpc.CallOption) (grpc.ClientStream, error) {
+ var (
+ chainHandler grpc.Streamer
+ curI int
+ )
+
+ chainHandler = func(currentCtx context.Context, currentDesc *grpc.StreamDesc, currentConn *grpc.ClientConn, currentMethod string, currentOpts ...grpc.CallOption) (grpc.ClientStream, error) {
+ if curI == lastI {
+ return streamer(currentCtx, currentDesc, currentConn, currentMethod, currentOpts...)
+ }
+ curI++
+ stream, err := interceptors[curI](currentCtx, currentDesc, currentConn, currentMethod, chainHandler, currentOpts...)
+ curI--
+ return stream, err
+ }
+
+ return interceptors[0](ctx, desc, cc, method, chainHandler, opts...)
+ }
+ }
+
+ if n == 1 {
+ return interceptors[0]
+ }
+
+ // n == 0; Dummy interceptor maintained for backward compatibility to avoid returning nil.
+ return func(ctx context.Context, desc *grpc.StreamDesc, cc *grpc.ClientConn, method string, streamer grpc.Streamer, opts ...grpc.CallOption) (grpc.ClientStream, error) {
+ return streamer(ctx, desc, cc, method, opts...)
+ }
+}
+
+// Chain creates a single interceptor out of a chain of many interceptors.
+//
+// WithUnaryServerChain is a grpc.Server config option that accepts multiple unary interceptors.
+// Basically syntactic sugar.
+func WithUnaryServerChain(interceptors ...grpc.UnaryServerInterceptor) grpc.ServerOption {
+ return grpc.UnaryInterceptor(ChainUnaryServer(interceptors...))
+}
+
+// WithStreamServerChain is a grpc.Server config option that accepts multiple stream interceptors.
+// Basically syntactic sugar.
+func WithStreamServerChain(interceptors ...grpc.StreamServerInterceptor) grpc.ServerOption {
+ return grpc.StreamInterceptor(ChainStreamServer(interceptors...))
+}
diff --git a/vendor/github.com/grpc-ecosystem/go-grpc-middleware/doc.go b/vendor/github.com/grpc-ecosystem/go-grpc-middleware/doc.go
new file mode 100644
index 00000000..71689503
--- /dev/null
+++ b/vendor/github.com/grpc-ecosystem/go-grpc-middleware/doc.go
@@ -0,0 +1,69 @@
+// Copyright 2016 Michal Witkowski. All Rights Reserved.
+// See LICENSE for licensing terms.
+
+/*
+`grpc_middleware` is a collection of gRPC middleware packages: interceptors, helpers and tools.
+
+Middleware
+
+gRPC is a fantastic RPC middleware, which sees a lot of adoption in the Golang world. However, the
+upstream gRPC codebase is relatively bare bones.
+
+This package, and most of its child packages provides commonly needed middleware for gRPC:
+client-side interceptors for retires, server-side interceptors for input validation and auth,
+functions for chaining said interceptors, metadata convenience methods and more.
+
+Chaining
+
+By default, gRPC doesn't allow one to have more than one interceptor either on the client nor on
+the server side. `grpc_middleware` provides convenient chaining methods
+
+Simple way of turning a multiple interceptors into a single interceptor. Here's an example for
+server chaining:
+
+ myServer := grpc.NewServer(
+ grpc.StreamInterceptor(grpc_middleware.ChainStreamServer(loggingStream, monitoringStream, authStream)),
+ grpc.UnaryInterceptor(grpc_middleware.ChainUnaryServer(loggingUnary, monitoringUnary, authUnary),
+ )
+
+These interceptors will be executed from left to right: logging, monitoring and auth.
+
+Here's an example for client side chaining:
+
+ clientConn, err = grpc.Dial(
+ address,
+ grpc.WithUnaryInterceptor(grpc_middleware.ChainUnaryClient(monitoringClientUnary, retryUnary)),
+ grpc.WithStreamInterceptor(grpc_middleware.ChainStreamClient(monitoringClientStream, retryStream)),
+ )
+ client = pb_testproto.NewTestServiceClient(clientConn)
+ resp, err := client.PingEmpty(s.ctx, &myservice.Request{Msg: "hello"})
+
+These interceptors will be executed from left to right: monitoring and then retry logic.
+
+The retry interceptor will call every interceptor that follows it whenever when a retry happens.
+
+Writing Your Own
+
+Implementing your own interceptor is pretty trivial: there are interfaces for that. But the interesting
+bit exposing common data to handlers (and other middleware), similarly to HTTP Middleware design.
+For example, you may want to pass the identity of the caller from the auth interceptor all the way
+to the handling function.
+
+For example, a client side interceptor example for auth looks like:
+
+ func FakeAuthUnaryInterceptor(ctx context.Context, req interface{}, info *grpc.UnaryServerInfo, handler grpc.UnaryHandler) (interface{}, error) {
+ newCtx := context.WithValue(ctx, "user_id", "john@example.com")
+ return handler(newCtx, req)
+ }
+
+Unfortunately, it's not as easy for streaming RPCs. These have the `context.Context` embedded within
+the `grpc.ServerStream` object. To pass values through context, a wrapper (`WrappedServerStream`) is
+needed. For example:
+
+ func FakeAuthStreamingInterceptor(srv interface{}, stream grpc.ServerStream, info *grpc.StreamServerInfo, handler grpc.StreamHandler) error {
+ newStream := grpc_middleware.WrapServerStream(stream)
+ newStream.WrappedContext = context.WithValue(ctx, "user_id", "john@example.com")
+ return handler(srv, stream)
+ }
+*/
+package grpc_middleware
diff --git a/vendor/github.com/grpc-ecosystem/go-grpc-middleware/logging/DOC.md b/vendor/github.com/grpc-ecosystem/go-grpc-middleware/logging/DOC.md
new file mode 100644
index 00000000..9deb4722
--- /dev/null
+++ b/vendor/github.com/grpc-ecosystem/go-grpc-middleware/logging/DOC.md
@@ -0,0 +1,91 @@
+# grpc_logging
+`import "github.com/grpc-ecosystem/go-grpc-middleware/logging"`
+
+* [Overview](#pkg-overview)
+* [Imported Packages](#pkg-imports)
+* [Index](#pkg-index)
+
+## <a name="pkg-overview">Overview</a>
+grpc_logging is a "parent" package for gRPC logging middlewares.
+
+### General functionality of all middleware
+The gRPC logging middleware populates request-scoped data to `grpc_ctxtags.Tags` that relate to the current gRPC call
+(e.g. service and method names).
+
+Once the gRPC logging middleware has added the gRPC specific Tags to the ctx they will then be written with the logs
+that are made using the `ctx_logrus` or `ctx_zap` loggers.
+
+All logging middleware will emit a final log statement. It is based on the error returned by the handler function,
+the gRPC status code, an error (if any) and it will emit at a level controlled via `WithLevels`.
+
+### This parent package
+This particular package is intended for use by other middleware, logging or otherwise. It contains interfaces that other
+logging middlewares *could* share . This allows code to be shared between different implementations.
+
+### Field names
+All field names of loggers follow the OpenTracing semantics definitions, with `grpc.` prefix if needed:
+<a href="https://github.com/opentracing/specification/blob/master/semantic_conventions.md">https://github.com/opentracing/specification/blob/master/semantic_conventions.md</a>
+
+### Implementations
+There are two implementations at the moment: logrus and zap
+
+See relevant packages below.
+
+## <a name="pkg-imports">Imported Packages</a>
+
+- [golang.org/x/net/context](https://godoc.org/golang.org/x/net/context)
+- [google.golang.org/grpc](https://godoc.org/google.golang.org/grpc)
+- [google.golang.org/grpc/codes](https://godoc.org/google.golang.org/grpc/codes)
+
+## <a name="pkg-index">Index</a>
+* [func DefaultDeciderMethod(fullMethodName string, err error) bool](#DefaultDeciderMethod)
+* [func DefaultErrorToCode(err error) codes.Code](#DefaultErrorToCode)
+* [type ClientPayloadLoggingDecider](#ClientPayloadLoggingDecider)
+* [type Decider](#Decider)
+* [type ErrorToCode](#ErrorToCode)
+* [type ServerPayloadLoggingDecider](#ServerPayloadLoggingDecider)
+
+#### <a name="pkg-files">Package files</a>
+[common.go](./common.go) [doc.go](./doc.go)
+
+## <a name="DefaultDeciderMethod">func</a> [DefaultDeciderMethod](./common.go#L25)
+``` go
+func DefaultDeciderMethod(fullMethodName string, err error) bool
+```
+DefaultDeciderMethod is the default implementation of decider to see if you should log the call
+by default this if always true so all calls are logged
+
+## <a name="DefaultErrorToCode">func</a> [DefaultErrorToCode](./common.go#L16)
+``` go
+func DefaultErrorToCode(err error) codes.Code
+```
+
+## <a name="ClientPayloadLoggingDecider">type</a> [ClientPayloadLoggingDecider](./common.go#L35)
+``` go
+type ClientPayloadLoggingDecider func(ctx context.Context, fullMethodName string) bool
+```
+ClientPayloadLoggingDecider is a user-provided function for deciding whether to log the client-side
+request/response payloads
+
+## <a name="Decider">type</a> [Decider](./common.go#L21)
+``` go
+type Decider func(fullMethodName string, err error) bool
+```
+Decider function defines rules for suppressing any interceptor logs
+
+## <a name="ErrorToCode">type</a> [ErrorToCode](./common.go#L14)
+``` go
+type ErrorToCode func(err error) codes.Code
+```
+ErrorToCode function determines the error code of an error
+This makes using custom errors with grpc middleware easier
+
+## <a name="ServerPayloadLoggingDecider">type</a> [ServerPayloadLoggingDecider](./common.go#L31)
+``` go
+type ServerPayloadLoggingDecider func(ctx context.Context, fullMethodName string, servingObject interface{}) bool
+```
+ServerPayloadLoggingDecider is a user-provided function for deciding whether to log the server-side
+request/response payloads
+
+- - -
+Generated by [godoc2ghmd](https://github.com/GandalfUK/godoc2ghmd) \ No newline at end of file
diff --git a/vendor/github.com/grpc-ecosystem/go-grpc-middleware/logging/README.md b/vendor/github.com/grpc-ecosystem/go-grpc-middleware/logging/README.md
new file mode 100644
index 00000000..9deb4722
--- /dev/null
+++ b/vendor/github.com/grpc-ecosystem/go-grpc-middleware/logging/README.md
@@ -0,0 +1,91 @@
+# grpc_logging
+`import "github.com/grpc-ecosystem/go-grpc-middleware/logging"`
+
+* [Overview](#pkg-overview)
+* [Imported Packages](#pkg-imports)
+* [Index](#pkg-index)
+
+## <a name="pkg-overview">Overview</a>
+grpc_logging is a "parent" package for gRPC logging middlewares.
+
+### General functionality of all middleware
+The gRPC logging middleware populates request-scoped data to `grpc_ctxtags.Tags` that relate to the current gRPC call
+(e.g. service and method names).
+
+Once the gRPC logging middleware has added the gRPC specific Tags to the ctx they will then be written with the logs
+that are made using the `ctx_logrus` or `ctx_zap` loggers.
+
+All logging middleware will emit a final log statement. It is based on the error returned by the handler function,
+the gRPC status code, an error (if any) and it will emit at a level controlled via `WithLevels`.
+
+### This parent package
+This particular package is intended for use by other middleware, logging or otherwise. It contains interfaces that other
+logging middlewares *could* share . This allows code to be shared between different implementations.
+
+### Field names
+All field names of loggers follow the OpenTracing semantics definitions, with `grpc.` prefix if needed:
+<a href="https://github.com/opentracing/specification/blob/master/semantic_conventions.md">https://github.com/opentracing/specification/blob/master/semantic_conventions.md</a>
+
+### Implementations
+There are two implementations at the moment: logrus and zap
+
+See relevant packages below.
+
+## <a name="pkg-imports">Imported Packages</a>
+
+- [golang.org/x/net/context](https://godoc.org/golang.org/x/net/context)
+- [google.golang.org/grpc](https://godoc.org/google.golang.org/grpc)
+- [google.golang.org/grpc/codes](https://godoc.org/google.golang.org/grpc/codes)
+
+## <a name="pkg-index">Index</a>
+* [func DefaultDeciderMethod(fullMethodName string, err error) bool](#DefaultDeciderMethod)
+* [func DefaultErrorToCode(err error) codes.Code](#DefaultErrorToCode)
+* [type ClientPayloadLoggingDecider](#ClientPayloadLoggingDecider)
+* [type Decider](#Decider)
+* [type ErrorToCode](#ErrorToCode)
+* [type ServerPayloadLoggingDecider](#ServerPayloadLoggingDecider)
+
+#### <a name="pkg-files">Package files</a>
+[common.go](./common.go) [doc.go](./doc.go)
+
+## <a name="DefaultDeciderMethod">func</a> [DefaultDeciderMethod](./common.go#L25)
+``` go
+func DefaultDeciderMethod(fullMethodName string, err error) bool
+```
+DefaultDeciderMethod is the default implementation of decider to see if you should log the call
+by default this if always true so all calls are logged
+
+## <a name="DefaultErrorToCode">func</a> [DefaultErrorToCode](./common.go#L16)
+``` go
+func DefaultErrorToCode(err error) codes.Code
+```
+
+## <a name="ClientPayloadLoggingDecider">type</a> [ClientPayloadLoggingDecider](./common.go#L35)
+``` go
+type ClientPayloadLoggingDecider func(ctx context.Context, fullMethodName string) bool
+```
+ClientPayloadLoggingDecider is a user-provided function for deciding whether to log the client-side
+request/response payloads
+
+## <a name="Decider">type</a> [Decider](./common.go#L21)
+``` go
+type Decider func(fullMethodName string, err error) bool
+```
+Decider function defines rules for suppressing any interceptor logs
+
+## <a name="ErrorToCode">type</a> [ErrorToCode](./common.go#L14)
+``` go
+type ErrorToCode func(err error) codes.Code
+```
+ErrorToCode function determines the error code of an error
+This makes using custom errors with grpc middleware easier
+
+## <a name="ServerPayloadLoggingDecider">type</a> [ServerPayloadLoggingDecider](./common.go#L31)
+``` go
+type ServerPayloadLoggingDecider func(ctx context.Context, fullMethodName string, servingObject interface{}) bool
+```
+ServerPayloadLoggingDecider is a user-provided function for deciding whether to log the server-side
+request/response payloads
+
+- - -
+Generated by [godoc2ghmd](https://github.com/GandalfUK/godoc2ghmd) \ No newline at end of file
diff --git a/vendor/github.com/grpc-ecosystem/go-grpc-middleware/logging/common.go b/vendor/github.com/grpc-ecosystem/go-grpc-middleware/logging/common.go
new file mode 100644
index 00000000..f725d038
--- /dev/null
+++ b/vendor/github.com/grpc-ecosystem/go-grpc-middleware/logging/common.go
@@ -0,0 +1,35 @@
+// Copyright 2017 Michal Witkowski. All Rights Reserved.
+// See LICENSE for licensing terms.
+
+package grpc_logging
+
+import (
+ "golang.org/x/net/context"
+ "google.golang.org/grpc"
+ "google.golang.org/grpc/codes"
+)
+
+// ErrorToCode function determines the error code of an error
+// This makes using custom errors with grpc middleware easier
+type ErrorToCode func(err error) codes.Code
+
+func DefaultErrorToCode(err error) codes.Code {
+ return grpc.Code(err)
+}
+
+// Decider function defines rules for suppressing any interceptor logs
+type Decider func(fullMethodName string, err error) bool
+
+// DefaultDeciderMethod is the default implementation of decider to see if you should log the call
+// by default this if always true so all calls are logged
+func DefaultDeciderMethod(fullMethodName string, err error) bool {
+ return true
+}
+
+// ServerPayloadLoggingDecider is a user-provided function for deciding whether to log the server-side
+// request/response payloads
+type ServerPayloadLoggingDecider func(ctx context.Context, fullMethodName string, servingObject interface{}) bool
+
+// ClientPayloadLoggingDecider is a user-provided function for deciding whether to log the client-side
+// request/response payloads
+type ClientPayloadLoggingDecider func(ctx context.Context, fullMethodName string) bool
diff --git a/vendor/github.com/grpc-ecosystem/go-grpc-middleware/logging/doc.go b/vendor/github.com/grpc-ecosystem/go-grpc-middleware/logging/doc.go
new file mode 100644
index 00000000..ce8bb298
--- /dev/null
+++ b/vendor/github.com/grpc-ecosystem/go-grpc-middleware/logging/doc.go
@@ -0,0 +1,35 @@
+// Copyright 2017 Michal Witkowski. All Rights Reserved.
+// See LICENSE for licensing terms.
+
+//
+/*
+grpc_logging is a "parent" package for gRPC logging middlewares.
+
+General functionality of all middleware
+
+The gRPC logging middleware populates request-scoped data to `grpc_ctxtags.Tags` that relate to the current gRPC call
+(e.g. service and method names).
+
+Once the gRPC logging middleware has added the gRPC specific Tags to the ctx they will then be written with the logs
+that are made using the `ctx_logrus` or `ctx_zap` loggers.
+
+All logging middleware will emit a final log statement. It is based on the error returned by the handler function,
+the gRPC status code, an error (if any) and it will emit at a level controlled via `WithLevels`.
+
+This parent package
+
+This particular package is intended for use by other middleware, logging or otherwise. It contains interfaces that other
+logging middlewares *could* share . This allows code to be shared between different implementations.
+
+Field names
+
+All field names of loggers follow the OpenTracing semantics definitions, with `grpc.` prefix if needed:
+https://github.com/opentracing/specification/blob/master/semantic_conventions.md
+
+Implementations
+
+There are two implementations at the moment: logrus and zap
+
+See relevant packages below.
+*/
+package grpc_logging
diff --git a/vendor/github.com/grpc-ecosystem/go-grpc-middleware/logging/logrus/DOC.md b/vendor/github.com/grpc-ecosystem/go-grpc-middleware/logging/logrus/DOC.md
new file mode 100644
index 00000000..77ebb64c
--- /dev/null
+++ b/vendor/github.com/grpc-ecosystem/go-grpc-middleware/logging/logrus/DOC.md
@@ -0,0 +1,391 @@
+# grpc_logrus
+`import "github.com/grpc-ecosystem/go-grpc-middleware/logging/logrus"`
+
+* [Overview](#pkg-overview)
+* [Imported Packages](#pkg-imports)
+* [Index](#pkg-index)
+* [Examples](#pkg-examples)
+
+## <a name="pkg-overview">Overview</a>
+`grpc_logrus` is a gRPC logging middleware backed by Logrus loggers
+
+It accepts a user-configured `logrus.Entry` that will be used for logging completed gRPC calls. The same
+`logrus.Entry` will be used for logging completed gRPC calls, and be populated into the `context.Context` passed into gRPC handler code.
+
+On calling `StreamServerInterceptor` or `UnaryServerInterceptor` this logging middleware will add gRPC call information
+to the ctx so that it will be present on subsequent use of the `ctxlogrus` logger.
+
+This package also implements request and response *payload* logging, both for server-side and client-side. These will be
+logged as structured `jsonpb` fields for every message received/sent (both unary and streaming). For that please use
+`Payload*Interceptor` functions for that. Please note that the user-provided function that determines whetether to log
+the full request/response payload needs to be written with care, this can significantly slow down gRPC.
+
+If a deadline is present on the gRPC request the grpc.request.deadline tag is populated when the request begins. grpc.request.deadline
+is a string representing the time (RFC3339) when the current call will expire.
+
+Logrus can also be made as a backend for gRPC library internals. For that use `ReplaceGrpcLogger`.
+
+*Server Interceptor*
+Below is a JSON formatted example of a log that would be logged by the server interceptor:
+
+ {
+ "level": "info", // string logrus log levels
+ "msg": "finished unary call", // string log message
+ "grpc.code": "OK", // string grpc status code
+ "grpc.method": "Ping", // string method name
+ "grpc.service": "mwitkow.testproto.TestService", // string full name of the called service
+ "grpc.start_time": "2006-01-02T15:04:05Z07:00", // string RFC3339 representation of the start time
+ "grpc.request.deadline": "2006-01-02T15:04:05Z07:00", // string RFC3339 deadline of the current request if supplied
+ "grpc.request.value": "something", // string value on the request
+ "grpc.time_ms": 1.234, // float32 run time of the call in ms
+ "peer.address": {
+ "IP": "127.0.0.1", // string IP address of calling party
+ "Port": 60216, // int port call is coming in on
+ "Zone": "" // string peer zone for caller
+ },
+ "span.kind": "server", // string client | server
+ "system": "grpc" // string
+
+ "custom_field": "custom_value", // string user defined field
+ "custom_tags.int": 1337, // int user defined tag on the ctx
+ "custom_tags.string": "something", // string user defined tag on the ctx
+ }
+
+*Payload Interceptor*
+Below is a JSON formatted example of a log that would be logged by the payload interceptor:
+
+ {
+ "level": "info", // string logrus log levels
+ "msg": "client request payload logged as grpc.request.content", // string log message
+
+ "grpc.request.content": { // object content of RPC request
+ "value": "something", // string defined by caller
+ "sleepTimeMs": 9999 // int defined by caller
+ },
+ "grpc.method": "Ping", // string method being called
+ "grpc.service": "mwitkow.testproto.TestService", // string service being called
+ "span.kind": "client", // string client | server
+ "system": "grpc" // string
+ }
+
+Note - due to implementation ZAP differs from Logrus in the "grpc.request.content" object by having an inner "msg" object.
+
+Please see examples and tests for examples of use.
+
+#### Example:
+
+<details>
+<summary>Click to expand code.</summary>
+
+```go
+// Logrus entry is used, allowing pre-definition of certain fields by the user.
+logrusEntry := logrus.NewEntry(logrusLogger)
+// Shared options for the logger, with a custom gRPC code to log level function.
+opts := []grpc_logrus.Option{
+ grpc_logrus.WithLevels(customFunc),
+}
+// Make sure that log statements internal to gRPC library are logged using the logrus Logger as well.
+grpc_logrus.ReplaceGrpcLogger(logrusEntry)
+// Create a server, make sure we put the grpc_ctxtags context before everything else.
+_ = grpc.NewServer(
+ grpc_middleware.WithUnaryServerChain(
+ grpc_ctxtags.UnaryServerInterceptor(grpc_ctxtags.WithFieldExtractor(grpc_ctxtags.CodeGenRequestFieldExtractor)),
+ grpc_logrus.UnaryServerInterceptor(logrusEntry, opts...),
+ ),
+ grpc_middleware.WithStreamServerChain(
+ grpc_ctxtags.StreamServerInterceptor(grpc_ctxtags.WithFieldExtractor(grpc_ctxtags.CodeGenRequestFieldExtractor)),
+ grpc_logrus.StreamServerInterceptor(logrusEntry, opts...),
+ ),
+)
+```
+
+</details>
+
+#### Example:
+
+<details>
+<summary>Click to expand code.</summary>
+
+```go
+// Logrus entry is used, allowing pre-definition of certain fields by the user.
+logrusEntry := logrus.NewEntry(logrusLogger)
+// Shared options for the logger, with a custom duration to log field function.
+opts := []grpc_logrus.Option{
+ grpc_logrus.WithDurationField(func(duration time.Duration) (key string, value interface{}) {
+ return "grpc.time_ns", duration.Nanoseconds()
+ }),
+}
+_ = grpc.NewServer(
+ grpc_middleware.WithUnaryServerChain(
+ grpc_ctxtags.UnaryServerInterceptor(),
+ grpc_logrus.UnaryServerInterceptor(logrusEntry, opts...),
+ ),
+ grpc_middleware.WithStreamServerChain(
+ grpc_ctxtags.StreamServerInterceptor(),
+ grpc_logrus.StreamServerInterceptor(logrusEntry, opts...),
+ ),
+)
+```
+
+</details>
+
+## <a name="pkg-imports">Imported Packages</a>
+
+- [github.com/golang/protobuf/jsonpb](https://godoc.org/github.com/golang/protobuf/jsonpb)
+- [github.com/golang/protobuf/proto](https://godoc.org/github.com/golang/protobuf/proto)
+- [github.com/grpc-ecosystem/go-grpc-middleware](./../..)
+- [github.com/grpc-ecosystem/go-grpc-middleware/logging](./..)
+- [github.com/grpc-ecosystem/go-grpc-middleware/logging/logrus/ctxlogrus](./ctxlogrus)
+- [github.com/grpc-ecosystem/go-grpc-middleware/tags/logrus](./../../tags/logrus)
+- [github.com/sirupsen/logrus](https://godoc.org/github.com/sirupsen/logrus)
+- [golang.org/x/net/context](https://godoc.org/golang.org/x/net/context)
+- [google.golang.org/grpc](https://godoc.org/google.golang.org/grpc)
+- [google.golang.org/grpc/codes](https://godoc.org/google.golang.org/grpc/codes)
+- [google.golang.org/grpc/grpclog](https://godoc.org/google.golang.org/grpc/grpclog)
+
+## <a name="pkg-index">Index</a>
+* [Variables](#pkg-variables)
+* [func AddFields(ctx context.Context, fields logrus.Fields)](#AddFields)
+* [func DefaultClientCodeToLevel(code codes.Code) logrus.Level](#DefaultClientCodeToLevel)
+* [func DefaultCodeToLevel(code codes.Code) logrus.Level](#DefaultCodeToLevel)
+* [func DurationToDurationField(duration time.Duration) (key string, value interface{})](#DurationToDurationField)
+* [func DurationToTimeMillisField(duration time.Duration) (key string, value interface{})](#DurationToTimeMillisField)
+* [func Extract(ctx context.Context) \*logrus.Entry](#Extract)
+* [func PayloadStreamClientInterceptor(entry \*logrus.Entry, decider grpc\_logging.ClientPayloadLoggingDecider) grpc.StreamClientInterceptor](#PayloadStreamClientInterceptor)
+* [func PayloadStreamServerInterceptor(entry \*logrus.Entry, decider grpc\_logging.ServerPayloadLoggingDecider) grpc.StreamServerInterceptor](#PayloadStreamServerInterceptor)
+* [func PayloadUnaryClientInterceptor(entry \*logrus.Entry, decider grpc\_logging.ClientPayloadLoggingDecider) grpc.UnaryClientInterceptor](#PayloadUnaryClientInterceptor)
+* [func PayloadUnaryServerInterceptor(entry \*logrus.Entry, decider grpc\_logging.ServerPayloadLoggingDecider) grpc.UnaryServerInterceptor](#PayloadUnaryServerInterceptor)
+* [func ReplaceGrpcLogger(logger \*logrus.Entry)](#ReplaceGrpcLogger)
+* [func StreamClientInterceptor(entry \*logrus.Entry, opts ...Option) grpc.StreamClientInterceptor](#StreamClientInterceptor)
+* [func StreamServerInterceptor(entry \*logrus.Entry, opts ...Option) grpc.StreamServerInterceptor](#StreamServerInterceptor)
+* [func UnaryClientInterceptor(entry \*logrus.Entry, opts ...Option) grpc.UnaryClientInterceptor](#UnaryClientInterceptor)
+* [func UnaryServerInterceptor(entry \*logrus.Entry, opts ...Option) grpc.UnaryServerInterceptor](#UnaryServerInterceptor)
+* [type CodeToLevel](#CodeToLevel)
+* [type DurationToField](#DurationToField)
+* [type Option](#Option)
+ * [func WithCodes(f grpc\_logging.ErrorToCode) Option](#WithCodes)
+ * [func WithDecider(f grpc\_logging.Decider) Option](#WithDecider)
+ * [func WithDurationField(f DurationToField) Option](#WithDurationField)
+ * [func WithLevels(f CodeToLevel) Option](#WithLevels)
+
+#### <a name="pkg-examples">Examples</a>
+* [Extract (Unary)](#example_Extract_unary)
+* [WithDecider](#example_WithDecider)
+* [Package (Initialization)](#example__initialization)
+* [Package (InitializationWithDurationFieldOverride)](#example__initializationWithDurationFieldOverride)
+
+#### <a name="pkg-files">Package files</a>
+[client_interceptors.go](./client_interceptors.go) [context.go](./context.go) [doc.go](./doc.go) [grpclogger.go](./grpclogger.go) [options.go](./options.go) [payload_interceptors.go](./payload_interceptors.go) [server_interceptors.go](./server_interceptors.go)
+
+## <a name="pkg-variables">Variables</a>
+``` go
+var (
+ // SystemField is used in every log statement made through grpc_logrus. Can be overwritten before any initialization code.
+ SystemField = "system"
+
+ // KindField describes the log gield used to incicate whether this is a server or a client log statment.
+ KindField = "span.kind"
+)
+```
+``` go
+var DefaultDurationToField = DurationToTimeMillisField
+```
+DefaultDurationToField is the default implementation of converting request duration to a log field (key and value).
+
+``` go
+var (
+ // JsonPBMarshaller is the marshaller used for serializing protobuf messages.
+ JsonPbMarshaller = &jsonpb.Marshaler{}
+)
+```
+
+## <a name="AddFields">func</a> [AddFields](./context.go#L11)
+``` go
+func AddFields(ctx context.Context, fields logrus.Fields)
+```
+AddFields adds logrus fields to the logger.
+Deprecated: should use the ctxlogrus.Extract instead
+
+## <a name="DefaultClientCodeToLevel">func</a> [DefaultClientCodeToLevel](./options.go#L129)
+``` go
+func DefaultClientCodeToLevel(code codes.Code) logrus.Level
+```
+DefaultClientCodeToLevel is the default implementation of gRPC return codes to log levels for client side.
+
+## <a name="DefaultCodeToLevel">func</a> [DefaultCodeToLevel](./options.go#L87)
+``` go
+func DefaultCodeToLevel(code codes.Code) logrus.Level
+```
+DefaultCodeToLevel is the default implementation of gRPC return codes to log levels for server side.
+
+## <a name="DurationToDurationField">func</a> [DurationToDurationField](./options.go#L179)
+``` go
+func DurationToDurationField(duration time.Duration) (key string, value interface{})
+```
+DurationToDurationField uses the duration value to log the request duration.
+
+## <a name="DurationToTimeMillisField">func</a> [DurationToTimeMillisField](./options.go#L174)
+``` go
+func DurationToTimeMillisField(duration time.Duration) (key string, value interface{})
+```
+DurationToTimeMillisField converts the duration to milliseconds and uses the key `grpc.time_ms`.
+
+## <a name="Extract">func</a> [Extract](./context.go#L17)
+``` go
+func Extract(ctx context.Context) *logrus.Entry
+```
+Extract takes the call-scoped logrus.Entry from grpc_logrus middleware.
+Deprecated: should use the ctxlogrus.Extract instead
+
+#### Example:
+
+<details>
+<summary>Click to expand code.</summary>
+
+```go
+_ = func(ctx context.Context, ping *pb_testproto.PingRequest) (*pb_testproto.PingResponse, error) {
+ // Add fields the ctxtags of the request which will be added to all extracted loggers.
+ grpc_ctxtags.Extract(ctx).Set("custom_tags.string", "something").Set("custom_tags.int", 1337)
+ // Extract a single request-scoped logrus.Logger and log messages.
+ l := ctx_logrus.Extract(ctx)
+ l.Info("some ping")
+ l.Info("another ping")
+ return &pb_testproto.PingResponse{Value: ping.Value}, nil
+}
+```
+
+</details>
+
+## <a name="PayloadStreamClientInterceptor">func</a> [PayloadStreamClientInterceptor](./payload_interceptors.go#L74)
+``` go
+func PayloadStreamClientInterceptor(entry *logrus.Entry, decider grpc_logging.ClientPayloadLoggingDecider) grpc.StreamClientInterceptor
+```
+PayloadStreamServerInterceptor returns a new streaming client interceptor that logs the paylods of requests and responses.
+
+## <a name="PayloadStreamServerInterceptor">func</a> [PayloadStreamServerInterceptor](./payload_interceptors.go#L45)
+``` go
+func PayloadStreamServerInterceptor(entry *logrus.Entry, decider grpc_logging.ServerPayloadLoggingDecider) grpc.StreamServerInterceptor
+```
+PayloadUnaryServerInterceptor returns a new server server interceptors that logs the payloads of requests.
+
+This *only* works when placed *after* the `grpc_logrus.StreamServerInterceptor`. However, the logging can be done to a
+separate instance of the logger.
+
+## <a name="PayloadUnaryClientInterceptor">func</a> [PayloadUnaryClientInterceptor](./payload_interceptors.go#L58)
+``` go
+func PayloadUnaryClientInterceptor(entry *logrus.Entry, decider grpc_logging.ClientPayloadLoggingDecider) grpc.UnaryClientInterceptor
+```
+PayloadUnaryClientInterceptor returns a new unary client interceptor that logs the paylods of requests and responses.
+
+## <a name="PayloadUnaryServerInterceptor">func</a> [PayloadUnaryServerInterceptor](./payload_interceptors.go#L25)
+``` go
+func PayloadUnaryServerInterceptor(entry *logrus.Entry, decider grpc_logging.ServerPayloadLoggingDecider) grpc.UnaryServerInterceptor
+```
+PayloadUnaryServerInterceptor returns a new unary server interceptors that logs the payloads of requests.
+
+This *only* works when placed *after* the `grpc_logrus.UnaryServerInterceptor`. However, the logging can be done to a
+separate instance of the logger.
+
+## <a name="ReplaceGrpcLogger">func</a> [ReplaceGrpcLogger](./grpclogger.go#L13)
+``` go
+func ReplaceGrpcLogger(logger *logrus.Entry)
+```
+ReplaceGrpcLogger sets the given logrus.Logger as a gRPC-level logger.
+This should be called *before* any other initialization, preferably from init() functions.
+
+## <a name="StreamClientInterceptor">func</a> [StreamClientInterceptor](./client_interceptors.go#L28)
+``` go
+func StreamClientInterceptor(entry *logrus.Entry, opts ...Option) grpc.StreamClientInterceptor
+```
+StreamServerInterceptor returns a new streaming client interceptor that optionally logs the execution of external gRPC calls.
+
+## <a name="StreamServerInterceptor">func</a> [StreamServerInterceptor](./server_interceptors.go#L58)
+``` go
+func StreamServerInterceptor(entry *logrus.Entry, opts ...Option) grpc.StreamServerInterceptor
+```
+StreamServerInterceptor returns a new streaming server interceptor that adds logrus.Entry to the context.
+
+## <a name="UnaryClientInterceptor">func</a> [UnaryClientInterceptor](./client_interceptors.go#L16)
+``` go
+func UnaryClientInterceptor(entry *logrus.Entry, opts ...Option) grpc.UnaryClientInterceptor
+```
+UnaryClientInterceptor returns a new unary client interceptor that optionally logs the execution of external gRPC calls.
+
+## <a name="UnaryServerInterceptor">func</a> [UnaryServerInterceptor](./server_interceptors.go#L26)
+``` go
+func UnaryServerInterceptor(entry *logrus.Entry, opts ...Option) grpc.UnaryServerInterceptor
+```
+PayloadUnaryServerInterceptor returns a new unary server interceptors that adds logrus.Entry to the context.
+
+## <a name="CodeToLevel">type</a> [CodeToLevel](./options.go#L53)
+``` go
+type CodeToLevel func(code codes.Code) logrus.Level
+```
+CodeToLevel function defines the mapping between gRPC return codes and interceptor log level.
+
+## <a name="DurationToField">type</a> [DurationToField](./options.go#L56)
+``` go
+type DurationToField func(duration time.Duration) (key string, value interface{})
+```
+DurationToField function defines how to produce duration fields for logging
+
+## <a name="Option">type</a> [Option](./options.go#L50)
+``` go
+type Option func(*options)
+```
+
+### <a name="WithCodes">func</a> [WithCodes](./options.go#L73)
+``` go
+func WithCodes(f grpc_logging.ErrorToCode) Option
+```
+WithCodes customizes the function for mapping errors to error codes.
+
+### <a name="WithDecider">func</a> [WithDecider](./options.go#L59)
+``` go
+func WithDecider(f grpc_logging.Decider) Option
+```
+WithDecider customizes the function for deciding if the gRPC interceptor logs should log.
+
+#### Example:
+
+<details>
+<summary>Click to expand code.</summary>
+
+```go
+opts := []grpc_logrus.Option{
+ grpc_logrus.WithDecider(func(methodFullName string, err error) bool {
+ // will not log gRPC calls if it was a call to healthcheck and no error was raised
+ if err == nil && methodFullName == "blah.foo.healthcheck" {
+ return false
+ }
+
+ // by default you will log all calls
+ return true
+ }),
+}
+
+_ = []grpc.ServerOption{
+ grpc_middleware.WithStreamServerChain(
+ grpc_ctxtags.StreamServerInterceptor(),
+ grpc_logrus.StreamServerInterceptor(logrus.NewEntry(logrus.New()), opts...)),
+ grpc_middleware.WithUnaryServerChain(
+ grpc_ctxtags.UnaryServerInterceptor(),
+ grpc_logrus.UnaryServerInterceptor(logrus.NewEntry(logrus.New()), opts...)),
+}
+```
+
+</details>
+### <a name="WithDurationField">func</a> [WithDurationField](./options.go#L80)
+``` go
+func WithDurationField(f DurationToField) Option
+```
+WithDurationField customizes the function for mapping request durations to log fields.
+
+### <a name="WithLevels">func</a> [WithLevels](./options.go#L66)
+``` go
+func WithLevels(f CodeToLevel) Option
+```
+WithLevels customizes the function for mapping gRPC return codes and interceptor log level statements.
+
+- - -
+Generated by [godoc2ghmd](https://github.com/GandalfUK/godoc2ghmd) \ No newline at end of file
diff --git a/vendor/github.com/grpc-ecosystem/go-grpc-middleware/logging/logrus/README.md b/vendor/github.com/grpc-ecosystem/go-grpc-middleware/logging/logrus/README.md
new file mode 100644
index 00000000..77ebb64c
--- /dev/null
+++ b/vendor/github.com/grpc-ecosystem/go-grpc-middleware/logging/logrus/README.md
@@ -0,0 +1,391 @@
+# grpc_logrus
+`import "github.com/grpc-ecosystem/go-grpc-middleware/logging/logrus"`
+
+* [Overview](#pkg-overview)
+* [Imported Packages](#pkg-imports)
+* [Index](#pkg-index)
+* [Examples](#pkg-examples)
+
+## <a name="pkg-overview">Overview</a>
+`grpc_logrus` is a gRPC logging middleware backed by Logrus loggers
+
+It accepts a user-configured `logrus.Entry` that will be used for logging completed gRPC calls. The same
+`logrus.Entry` will be used for logging completed gRPC calls, and be populated into the `context.Context` passed into gRPC handler code.
+
+On calling `StreamServerInterceptor` or `UnaryServerInterceptor` this logging middleware will add gRPC call information
+to the ctx so that it will be present on subsequent use of the `ctxlogrus` logger.
+
+This package also implements request and response *payload* logging, both for server-side and client-side. These will be
+logged as structured `jsonpb` fields for every message received/sent (both unary and streaming). For that please use
+`Payload*Interceptor` functions for that. Please note that the user-provided function that determines whetether to log
+the full request/response payload needs to be written with care, this can significantly slow down gRPC.
+
+If a deadline is present on the gRPC request the grpc.request.deadline tag is populated when the request begins. grpc.request.deadline
+is a string representing the time (RFC3339) when the current call will expire.
+
+Logrus can also be made as a backend for gRPC library internals. For that use `ReplaceGrpcLogger`.
+
+*Server Interceptor*
+Below is a JSON formatted example of a log that would be logged by the server interceptor:
+
+ {
+ "level": "info", // string logrus log levels
+ "msg": "finished unary call", // string log message
+ "grpc.code": "OK", // string grpc status code
+ "grpc.method": "Ping", // string method name
+ "grpc.service": "mwitkow.testproto.TestService", // string full name of the called service
+ "grpc.start_time": "2006-01-02T15:04:05Z07:00", // string RFC3339 representation of the start time
+ "grpc.request.deadline": "2006-01-02T15:04:05Z07:00", // string RFC3339 deadline of the current request if supplied
+ "grpc.request.value": "something", // string value on the request
+ "grpc.time_ms": 1.234, // float32 run time of the call in ms
+ "peer.address": {
+ "IP": "127.0.0.1", // string IP address of calling party
+ "Port": 60216, // int port call is coming in on
+ "Zone": "" // string peer zone for caller
+ },
+ "span.kind": "server", // string client | server
+ "system": "grpc" // string
+
+ "custom_field": "custom_value", // string user defined field
+ "custom_tags.int": 1337, // int user defined tag on the ctx
+ "custom_tags.string": "something", // string user defined tag on the ctx
+ }
+
+*Payload Interceptor*
+Below is a JSON formatted example of a log that would be logged by the payload interceptor:
+
+ {
+ "level": "info", // string logrus log levels
+ "msg": "client request payload logged as grpc.request.content", // string log message
+
+ "grpc.request.content": { // object content of RPC request
+ "value": "something", // string defined by caller
+ "sleepTimeMs": 9999 // int defined by caller
+ },
+ "grpc.method": "Ping", // string method being called
+ "grpc.service": "mwitkow.testproto.TestService", // string service being called
+ "span.kind": "client", // string client | server
+ "system": "grpc" // string
+ }
+
+Note - due to implementation ZAP differs from Logrus in the "grpc.request.content" object by having an inner "msg" object.
+
+Please see examples and tests for examples of use.
+
+#### Example:
+
+<details>
+<summary>Click to expand code.</summary>
+
+```go
+// Logrus entry is used, allowing pre-definition of certain fields by the user.
+logrusEntry := logrus.NewEntry(logrusLogger)
+// Shared options for the logger, with a custom gRPC code to log level function.
+opts := []grpc_logrus.Option{
+ grpc_logrus.WithLevels(customFunc),
+}
+// Make sure that log statements internal to gRPC library are logged using the logrus Logger as well.
+grpc_logrus.ReplaceGrpcLogger(logrusEntry)
+// Create a server, make sure we put the grpc_ctxtags context before everything else.
+_ = grpc.NewServer(
+ grpc_middleware.WithUnaryServerChain(
+ grpc_ctxtags.UnaryServerInterceptor(grpc_ctxtags.WithFieldExtractor(grpc_ctxtags.CodeGenRequestFieldExtractor)),
+ grpc_logrus.UnaryServerInterceptor(logrusEntry, opts...),
+ ),
+ grpc_middleware.WithStreamServerChain(
+ grpc_ctxtags.StreamServerInterceptor(grpc_ctxtags.WithFieldExtractor(grpc_ctxtags.CodeGenRequestFieldExtractor)),
+ grpc_logrus.StreamServerInterceptor(logrusEntry, opts...),
+ ),
+)
+```
+
+</details>
+
+#### Example:
+
+<details>
+<summary>Click to expand code.</summary>
+
+```go
+// Logrus entry is used, allowing pre-definition of certain fields by the user.
+logrusEntry := logrus.NewEntry(logrusLogger)
+// Shared options for the logger, with a custom duration to log field function.
+opts := []grpc_logrus.Option{
+ grpc_logrus.WithDurationField(func(duration time.Duration) (key string, value interface{}) {
+ return "grpc.time_ns", duration.Nanoseconds()
+ }),
+}
+_ = grpc.NewServer(
+ grpc_middleware.WithUnaryServerChain(
+ grpc_ctxtags.UnaryServerInterceptor(),
+ grpc_logrus.UnaryServerInterceptor(logrusEntry, opts...),
+ ),
+ grpc_middleware.WithStreamServerChain(
+ grpc_ctxtags.StreamServerInterceptor(),
+ grpc_logrus.StreamServerInterceptor(logrusEntry, opts...),
+ ),
+)
+```
+
+</details>
+
+## <a name="pkg-imports">Imported Packages</a>
+
+- [github.com/golang/protobuf/jsonpb](https://godoc.org/github.com/golang/protobuf/jsonpb)
+- [github.com/golang/protobuf/proto](https://godoc.org/github.com/golang/protobuf/proto)
+- [github.com/grpc-ecosystem/go-grpc-middleware](./../..)
+- [github.com/grpc-ecosystem/go-grpc-middleware/logging](./..)
+- [github.com/grpc-ecosystem/go-grpc-middleware/logging/logrus/ctxlogrus](./ctxlogrus)
+- [github.com/grpc-ecosystem/go-grpc-middleware/tags/logrus](./../../tags/logrus)
+- [github.com/sirupsen/logrus](https://godoc.org/github.com/sirupsen/logrus)
+- [golang.org/x/net/context](https://godoc.org/golang.org/x/net/context)
+- [google.golang.org/grpc](https://godoc.org/google.golang.org/grpc)
+- [google.golang.org/grpc/codes](https://godoc.org/google.golang.org/grpc/codes)
+- [google.golang.org/grpc/grpclog](https://godoc.org/google.golang.org/grpc/grpclog)
+
+## <a name="pkg-index">Index</a>
+* [Variables](#pkg-variables)
+* [func AddFields(ctx context.Context, fields logrus.Fields)](#AddFields)
+* [func DefaultClientCodeToLevel(code codes.Code) logrus.Level](#DefaultClientCodeToLevel)
+* [func DefaultCodeToLevel(code codes.Code) logrus.Level](#DefaultCodeToLevel)
+* [func DurationToDurationField(duration time.Duration) (key string, value interface{})](#DurationToDurationField)
+* [func DurationToTimeMillisField(duration time.Duration) (key string, value interface{})](#DurationToTimeMillisField)
+* [func Extract(ctx context.Context) \*logrus.Entry](#Extract)
+* [func PayloadStreamClientInterceptor(entry \*logrus.Entry, decider grpc\_logging.ClientPayloadLoggingDecider) grpc.StreamClientInterceptor](#PayloadStreamClientInterceptor)
+* [func PayloadStreamServerInterceptor(entry \*logrus.Entry, decider grpc\_logging.ServerPayloadLoggingDecider) grpc.StreamServerInterceptor](#PayloadStreamServerInterceptor)
+* [func PayloadUnaryClientInterceptor(entry \*logrus.Entry, decider grpc\_logging.ClientPayloadLoggingDecider) grpc.UnaryClientInterceptor](#PayloadUnaryClientInterceptor)
+* [func PayloadUnaryServerInterceptor(entry \*logrus.Entry, decider grpc\_logging.ServerPayloadLoggingDecider) grpc.UnaryServerInterceptor](#PayloadUnaryServerInterceptor)
+* [func ReplaceGrpcLogger(logger \*logrus.Entry)](#ReplaceGrpcLogger)
+* [func StreamClientInterceptor(entry \*logrus.Entry, opts ...Option) grpc.StreamClientInterceptor](#StreamClientInterceptor)
+* [func StreamServerInterceptor(entry \*logrus.Entry, opts ...Option) grpc.StreamServerInterceptor](#StreamServerInterceptor)
+* [func UnaryClientInterceptor(entry \*logrus.Entry, opts ...Option) grpc.UnaryClientInterceptor](#UnaryClientInterceptor)
+* [func UnaryServerInterceptor(entry \*logrus.Entry, opts ...Option) grpc.UnaryServerInterceptor](#UnaryServerInterceptor)
+* [type CodeToLevel](#CodeToLevel)
+* [type DurationToField](#DurationToField)
+* [type Option](#Option)
+ * [func WithCodes(f grpc\_logging.ErrorToCode) Option](#WithCodes)
+ * [func WithDecider(f grpc\_logging.Decider) Option](#WithDecider)
+ * [func WithDurationField(f DurationToField) Option](#WithDurationField)
+ * [func WithLevels(f CodeToLevel) Option](#WithLevels)
+
+#### <a name="pkg-examples">Examples</a>
+* [Extract (Unary)](#example_Extract_unary)
+* [WithDecider](#example_WithDecider)
+* [Package (Initialization)](#example__initialization)
+* [Package (InitializationWithDurationFieldOverride)](#example__initializationWithDurationFieldOverride)
+
+#### <a name="pkg-files">Package files</a>
+[client_interceptors.go](./client_interceptors.go) [context.go](./context.go) [doc.go](./doc.go) [grpclogger.go](./grpclogger.go) [options.go](./options.go) [payload_interceptors.go](./payload_interceptors.go) [server_interceptors.go](./server_interceptors.go)
+
+## <a name="pkg-variables">Variables</a>
+``` go
+var (
+ // SystemField is used in every log statement made through grpc_logrus. Can be overwritten before any initialization code.
+ SystemField = "system"
+
+ // KindField describes the log gield used to incicate whether this is a server or a client log statment.
+ KindField = "span.kind"
+)
+```
+``` go
+var DefaultDurationToField = DurationToTimeMillisField
+```
+DefaultDurationToField is the default implementation of converting request duration to a log field (key and value).
+
+``` go
+var (
+ // JsonPBMarshaller is the marshaller used for serializing protobuf messages.
+ JsonPbMarshaller = &jsonpb.Marshaler{}
+)
+```
+
+## <a name="AddFields">func</a> [AddFields](./context.go#L11)
+``` go
+func AddFields(ctx context.Context, fields logrus.Fields)
+```
+AddFields adds logrus fields to the logger.
+Deprecated: should use the ctxlogrus.Extract instead
+
+## <a name="DefaultClientCodeToLevel">func</a> [DefaultClientCodeToLevel](./options.go#L129)
+``` go
+func DefaultClientCodeToLevel(code codes.Code) logrus.Level
+```
+DefaultClientCodeToLevel is the default implementation of gRPC return codes to log levels for client side.
+
+## <a name="DefaultCodeToLevel">func</a> [DefaultCodeToLevel](./options.go#L87)
+``` go
+func DefaultCodeToLevel(code codes.Code) logrus.Level
+```
+DefaultCodeToLevel is the default implementation of gRPC return codes to log levels for server side.
+
+## <a name="DurationToDurationField">func</a> [DurationToDurationField](./options.go#L179)
+``` go
+func DurationToDurationField(duration time.Duration) (key string, value interface{})
+```
+DurationToDurationField uses the duration value to log the request duration.
+
+## <a name="DurationToTimeMillisField">func</a> [DurationToTimeMillisField](./options.go#L174)
+``` go
+func DurationToTimeMillisField(duration time.Duration) (key string, value interface{})
+```
+DurationToTimeMillisField converts the duration to milliseconds and uses the key `grpc.time_ms`.
+
+## <a name="Extract">func</a> [Extract](./context.go#L17)
+``` go
+func Extract(ctx context.Context) *logrus.Entry
+```
+Extract takes the call-scoped logrus.Entry from grpc_logrus middleware.
+Deprecated: should use the ctxlogrus.Extract instead
+
+#### Example:
+
+<details>
+<summary>Click to expand code.</summary>
+
+```go
+_ = func(ctx context.Context, ping *pb_testproto.PingRequest) (*pb_testproto.PingResponse, error) {
+ // Add fields the ctxtags of the request which will be added to all extracted loggers.
+ grpc_ctxtags.Extract(ctx).Set("custom_tags.string", "something").Set("custom_tags.int", 1337)
+ // Extract a single request-scoped logrus.Logger and log messages.
+ l := ctx_logrus.Extract(ctx)
+ l.Info("some ping")
+ l.Info("another ping")
+ return &pb_testproto.PingResponse{Value: ping.Value}, nil
+}
+```
+
+</details>
+
+## <a name="PayloadStreamClientInterceptor">func</a> [PayloadStreamClientInterceptor](./payload_interceptors.go#L74)
+``` go
+func PayloadStreamClientInterceptor(entry *logrus.Entry, decider grpc_logging.ClientPayloadLoggingDecider) grpc.StreamClientInterceptor
+```
+PayloadStreamServerInterceptor returns a new streaming client interceptor that logs the paylods of requests and responses.
+
+## <a name="PayloadStreamServerInterceptor">func</a> [PayloadStreamServerInterceptor](./payload_interceptors.go#L45)
+``` go
+func PayloadStreamServerInterceptor(entry *logrus.Entry, decider grpc_logging.ServerPayloadLoggingDecider) grpc.StreamServerInterceptor
+```
+PayloadUnaryServerInterceptor returns a new server server interceptors that logs the payloads of requests.
+
+This *only* works when placed *after* the `grpc_logrus.StreamServerInterceptor`. However, the logging can be done to a
+separate instance of the logger.
+
+## <a name="PayloadUnaryClientInterceptor">func</a> [PayloadUnaryClientInterceptor](./payload_interceptors.go#L58)
+``` go
+func PayloadUnaryClientInterceptor(entry *logrus.Entry, decider grpc_logging.ClientPayloadLoggingDecider) grpc.UnaryClientInterceptor
+```
+PayloadUnaryClientInterceptor returns a new unary client interceptor that logs the paylods of requests and responses.
+
+## <a name="PayloadUnaryServerInterceptor">func</a> [PayloadUnaryServerInterceptor](./payload_interceptors.go#L25)
+``` go
+func PayloadUnaryServerInterceptor(entry *logrus.Entry, decider grpc_logging.ServerPayloadLoggingDecider) grpc.UnaryServerInterceptor
+```
+PayloadUnaryServerInterceptor returns a new unary server interceptors that logs the payloads of requests.
+
+This *only* works when placed *after* the `grpc_logrus.UnaryServerInterceptor`. However, the logging can be done to a
+separate instance of the logger.
+
+## <a name="ReplaceGrpcLogger">func</a> [ReplaceGrpcLogger](./grpclogger.go#L13)
+``` go
+func ReplaceGrpcLogger(logger *logrus.Entry)
+```
+ReplaceGrpcLogger sets the given logrus.Logger as a gRPC-level logger.
+This should be called *before* any other initialization, preferably from init() functions.
+
+## <a name="StreamClientInterceptor">func</a> [StreamClientInterceptor](./client_interceptors.go#L28)
+``` go
+func StreamClientInterceptor(entry *logrus.Entry, opts ...Option) grpc.StreamClientInterceptor
+```
+StreamServerInterceptor returns a new streaming client interceptor that optionally logs the execution of external gRPC calls.
+
+## <a name="StreamServerInterceptor">func</a> [StreamServerInterceptor](./server_interceptors.go#L58)
+``` go
+func StreamServerInterceptor(entry *logrus.Entry, opts ...Option) grpc.StreamServerInterceptor
+```
+StreamServerInterceptor returns a new streaming server interceptor that adds logrus.Entry to the context.
+
+## <a name="UnaryClientInterceptor">func</a> [UnaryClientInterceptor](./client_interceptors.go#L16)
+``` go
+func UnaryClientInterceptor(entry *logrus.Entry, opts ...Option) grpc.UnaryClientInterceptor
+```
+UnaryClientInterceptor returns a new unary client interceptor that optionally logs the execution of external gRPC calls.
+
+## <a name="UnaryServerInterceptor">func</a> [UnaryServerInterceptor](./server_interceptors.go#L26)
+``` go
+func UnaryServerInterceptor(entry *logrus.Entry, opts ...Option) grpc.UnaryServerInterceptor
+```
+PayloadUnaryServerInterceptor returns a new unary server interceptors that adds logrus.Entry to the context.
+
+## <a name="CodeToLevel">type</a> [CodeToLevel](./options.go#L53)
+``` go
+type CodeToLevel func(code codes.Code) logrus.Level
+```
+CodeToLevel function defines the mapping between gRPC return codes and interceptor log level.
+
+## <a name="DurationToField">type</a> [DurationToField](./options.go#L56)
+``` go
+type DurationToField func(duration time.Duration) (key string, value interface{})
+```
+DurationToField function defines how to produce duration fields for logging
+
+## <a name="Option">type</a> [Option](./options.go#L50)
+``` go
+type Option func(*options)
+```
+
+### <a name="WithCodes">func</a> [WithCodes](./options.go#L73)
+``` go
+func WithCodes(f grpc_logging.ErrorToCode) Option
+```
+WithCodes customizes the function for mapping errors to error codes.
+
+### <a name="WithDecider">func</a> [WithDecider](./options.go#L59)
+``` go
+func WithDecider(f grpc_logging.Decider) Option
+```
+WithDecider customizes the function for deciding if the gRPC interceptor logs should log.
+
+#### Example:
+
+<details>
+<summary>Click to expand code.</summary>
+
+```go
+opts := []grpc_logrus.Option{
+ grpc_logrus.WithDecider(func(methodFullName string, err error) bool {
+ // will not log gRPC calls if it was a call to healthcheck and no error was raised
+ if err == nil && methodFullName == "blah.foo.healthcheck" {
+ return false
+ }
+
+ // by default you will log all calls
+ return true
+ }),
+}
+
+_ = []grpc.ServerOption{
+ grpc_middleware.WithStreamServerChain(
+ grpc_ctxtags.StreamServerInterceptor(),
+ grpc_logrus.StreamServerInterceptor(logrus.NewEntry(logrus.New()), opts...)),
+ grpc_middleware.WithUnaryServerChain(
+ grpc_ctxtags.UnaryServerInterceptor(),
+ grpc_logrus.UnaryServerInterceptor(logrus.NewEntry(logrus.New()), opts...)),
+}
+```
+
+</details>
+### <a name="WithDurationField">func</a> [WithDurationField](./options.go#L80)
+``` go
+func WithDurationField(f DurationToField) Option
+```
+WithDurationField customizes the function for mapping request durations to log fields.
+
+### <a name="WithLevels">func</a> [WithLevels](./options.go#L66)
+``` go
+func WithLevels(f CodeToLevel) Option
+```
+WithLevels customizes the function for mapping gRPC return codes and interceptor log level statements.
+
+- - -
+Generated by [godoc2ghmd](https://github.com/GandalfUK/godoc2ghmd) \ No newline at end of file
diff --git a/vendor/github.com/grpc-ecosystem/go-grpc-middleware/logging/logrus/client_interceptors.go b/vendor/github.com/grpc-ecosystem/go-grpc-middleware/logging/logrus/client_interceptors.go
new file mode 100644
index 00000000..f7655ff6
--- /dev/null
+++ b/vendor/github.com/grpc-ecosystem/go-grpc-middleware/logging/logrus/client_interceptors.go
@@ -0,0 +1,65 @@
+// Copyright 2017 Michal Witkowski. All Rights Reserved.
+// See LICENSE for licensing terms.
+
+package grpc_logrus
+
+import (
+ "path"
+ "time"
+
+ "github.com/sirupsen/logrus"
+ "golang.org/x/net/context"
+ "google.golang.org/grpc"
+)
+
+// UnaryClientInterceptor returns a new unary client interceptor that optionally logs the execution of external gRPC calls.
+func UnaryClientInterceptor(entry *logrus.Entry, opts ...Option) grpc.UnaryClientInterceptor {
+ o := evaluateClientOpt(opts)
+ return func(ctx context.Context, method string, req, reply interface{}, cc *grpc.ClientConn, invoker grpc.UnaryInvoker, opts ...grpc.CallOption) error {
+ fields := newClientLoggerFields(ctx, method)
+ startTime := time.Now()
+ err := invoker(ctx, method, req, reply, cc, opts...)
+ logFinalClientLine(o, entry.WithFields(fields), startTime, err, "finished client unary call")
+ return err
+ }
+}
+
+// StreamServerInterceptor returns a new streaming client interceptor that optionally logs the execution of external gRPC calls.
+func StreamClientInterceptor(entry *logrus.Entry, opts ...Option) grpc.StreamClientInterceptor {
+ o := evaluateClientOpt(opts)
+ return func(ctx context.Context, desc *grpc.StreamDesc, cc *grpc.ClientConn, method string, streamer grpc.Streamer, opts ...grpc.CallOption) (grpc.ClientStream, error) {
+ fields := newClientLoggerFields(ctx, method)
+ startTime := time.Now()
+ clientStream, err := streamer(ctx, desc, cc, method, opts...)
+ logFinalClientLine(o, entry.WithFields(fields), startTime, err, "finished client streaming call")
+ return clientStream, err
+ }
+}
+
+func logFinalClientLine(o *options, entry *logrus.Entry, startTime time.Time, err error, msg string) {
+ code := o.codeFunc(err)
+ level := o.levelFunc(code)
+ durField, durVal := o.durationFunc(time.Now().Sub(startTime))
+ fields := logrus.Fields{
+ "grpc.code": code.String(),
+ durField: durVal,
+ }
+ if err != nil {
+ fields[logrus.ErrorKey] = err
+ }
+ levelLogf(
+ entry.WithFields(fields),
+ level,
+ msg)
+}
+
+func newClientLoggerFields(ctx context.Context, fullMethodString string) logrus.Fields {
+ service := path.Dir(fullMethodString)[1:]
+ method := path.Base(fullMethodString)
+ return logrus.Fields{
+ SystemField: "grpc",
+ KindField: "client",
+ "grpc.service": service,
+ "grpc.method": method,
+ }
+}
diff --git a/vendor/github.com/grpc-ecosystem/go-grpc-middleware/logging/logrus/context.go b/vendor/github.com/grpc-ecosystem/go-grpc-middleware/logging/logrus/context.go
new file mode 100644
index 00000000..a39bb772
--- /dev/null
+++ b/vendor/github.com/grpc-ecosystem/go-grpc-middleware/logging/logrus/context.go
@@ -0,0 +1,19 @@
+package grpc_logrus
+
+import (
+ "github.com/grpc-ecosystem/go-grpc-middleware/logging/logrus/ctxlogrus"
+ "github.com/sirupsen/logrus"
+ "golang.org/x/net/context"
+)
+
+// AddFields adds logrus fields to the logger.
+// Deprecated: should use the ctxlogrus.Extract instead
+func AddFields(ctx context.Context, fields logrus.Fields) {
+ ctxlogrus.AddFields(ctx, fields)
+}
+
+// Extract takes the call-scoped logrus.Entry from grpc_logrus middleware.
+// Deprecated: should use the ctxlogrus.Extract instead
+func Extract(ctx context.Context) *logrus.Entry {
+ return ctxlogrus.Extract(ctx)
+}
diff --git a/vendor/github.com/grpc-ecosystem/go-grpc-middleware/logging/logrus/ctxlogrus/DOC.md b/vendor/github.com/grpc-ecosystem/go-grpc-middleware/logging/logrus/ctxlogrus/DOC.md
new file mode 100644
index 00000000..90918029
--- /dev/null
+++ b/vendor/github.com/grpc-ecosystem/go-grpc-middleware/logging/logrus/ctxlogrus/DOC.md
@@ -0,0 +1,93 @@
+# ctxlogrus
+`import "github.com/grpc-ecosystem/go-grpc-middleware/logging/logrus/ctxlogrus"`
+
+* [Overview](#pkg-overview)
+* [Imported Packages](#pkg-imports)
+* [Index](#pkg-index)
+* [Examples](#pkg-examples)
+
+## <a name="pkg-overview">Overview</a>
+`ctxlogrus` is a ctxlogger that is backed by logrus
+
+It accepts a user-configured `logrus.Logger` that will be used for logging. The same `logrus.Logger` will
+be populated into the `context.Context` passed into gRPC handler code.
+
+You can use `ctx_logrus.Extract` to log into a request-scoped `logrus.Logger` instance in your handler code.
+
+As `ctx_logrus.Extract` will iterate all tags on from `grpc_ctxtags` it is therefore expensive so it is advised that you
+extract once at the start of the function from the context and reuse it for the remainder of the function (see examples).
+
+Please see examples and tests for examples of use.
+
+## <a name="pkg-imports">Imported Packages</a>
+
+- [github.com/grpc-ecosystem/go-grpc-middleware/tags](./../../../tags)
+- [github.com/sirupsen/logrus](https://godoc.org/github.com/sirupsen/logrus)
+- [golang.org/x/net/context](https://godoc.org/golang.org/x/net/context)
+
+## <a name="pkg-index">Index</a>
+* [func AddFields(ctx context.Context, fields logrus.Fields)](#AddFields)
+* [func Extract(ctx context.Context) \*logrus.Entry](#Extract)
+* [func ToContext(ctx context.Context, entry \*logrus.Entry) context.Context](#ToContext)
+
+#### <a name="pkg-examples">Examples</a>
+* [Extract (Unary)](#example_Extract_unary)
+
+#### <a name="pkg-files">Package files</a>
+[context.go](./context.go) [doc.go](./doc.go) [noop.go](./noop.go)
+
+## <a name="AddFields">func</a> [AddFields](./context.go#L21)
+``` go
+func AddFields(ctx context.Context, fields logrus.Fields)
+```
+AddFields adds logrus fields to the logger.
+
+## <a name="Extract">func</a> [Extract](./context.go#L35)
+``` go
+func Extract(ctx context.Context) *logrus.Entry
+```
+Extract takes the call-scoped logrus.Entry from ctx_logrus middleware.
+
+If the ctx_logrus middleware wasn't used, a no-op `logrus.Entry` is returned. This makes it safe to
+use regardless.
+
+#### Example:
+
+<details>
+<summary>Click to expand code.</summary>
+
+```go
+package ctxlogrus_test
+
+import (
+ "github.com/grpc-ecosystem/go-grpc-middleware/logging/logrus/ctxlogrus"
+ "github.com/grpc-ecosystem/go-grpc-middleware/tags"
+ "github.com/sirupsen/logrus"
+ "golang.org/x/net/context"
+)
+
+var logrusLogger *logrus.Logger
+
+// Simple unary handler that adds custom fields to the requests's context. These will be used for all log statements.
+func ExampleExtract_unary() {
+ ctx := context.Background()
+ // setting tags will be added to the logger as log fields
+ grpc_ctxtags.Extract(ctx).Set("custom_tags.string", "something").Set("custom_tags.int", 1337)
+ // Extract a single request-scoped logrus.Logger and log messages.
+ l := ctxlogrus.Extract(ctx)
+ l.Info("some ping")
+ l.Info("another ping")
+}
+```
+
+</details>
+
+## <a name="ToContext">func</a> [ToContext](./context.go#L59)
+``` go
+func ToContext(ctx context.Context, entry *logrus.Entry) context.Context
+```
+ToContext adds the logrus.Entry to the context for extraction later.
+Returning the new context that has been created.
+
+- - -
+Generated by [godoc2ghmd](https://github.com/GandalfUK/godoc2ghmd) \ No newline at end of file
diff --git a/vendor/github.com/grpc-ecosystem/go-grpc-middleware/logging/logrus/ctxlogrus/README.md b/vendor/github.com/grpc-ecosystem/go-grpc-middleware/logging/logrus/ctxlogrus/README.md
new file mode 100644
index 00000000..fc1d0a92
--- /dev/null
+++ b/vendor/github.com/grpc-ecosystem/go-grpc-middleware/logging/logrus/ctxlogrus/README.md
@@ -0,0 +1,58 @@
+# ctx_logrus
+`import "github.com/grpc-ecosystem/go-grpc-middleware/tags/logrus"`
+
+* [Overview](#pkg-overview)
+* [Imported Packages](#pkg-imports)
+* [Index](#pkg-index)
+
+## <a name="pkg-overview">Overview</a>
+`ctx_logrus` is a ctxlogger that is backed by logrus
+
+It accepts a user-configured `logrus.Logger` that will be used for logging. The same `logrus.Logger` will
+be populated into the `context.Context` passed into gRPC handler code.
+
+You can use `ctx_logrus.Extract` to log into a request-scoped `logrus.Logger` instance in your handler code.
+
+As `ctx_logrus.Extract` will iterate all tags on from `grpc_ctxtags` it is therefore expensive so it is advised that you
+extract once at the start of the function from the context and reuse it for the remainder of the function (see examples).
+
+Please see examples and tests for examples of use.
+
+## <a name="pkg-imports">Imported Packages</a>
+
+- [github.com/grpc-ecosystem/go-grpc-middleware/tags](./..)
+- [github.com/sirupsen/logrus](https://godoc.org/github.com/sirupsen/logrus)
+- [golang.org/x/net/context](https://godoc.org/golang.org/x/net/context)
+
+## <a name="pkg-index">Index</a>
+* [func AddFields(ctx context.Context, fields logrus.Fields)](#AddFields)
+* [func Extract(ctx context.Context) \*logrus.Entry](#Extract)
+* [func ToContext(ctx context.Context, entry \*logrus.Entry) context.Context](#ToContext)
+
+#### <a name="pkg-files">Package files</a>
+[context.go](./context.go) [doc.go](./doc.go) [noop.go](./noop.go)
+
+## <a name="AddFields">func</a> [AddFields](./context.go#L21)
+``` go
+func AddFields(ctx context.Context, fields logrus.Fields)
+```
+AddFields adds logrus fields to the logger.
+
+## <a name="Extract">func</a> [Extract](./context.go#L35)
+``` go
+func Extract(ctx context.Context) *logrus.Entry
+```
+Extract takes the call-scoped logrus.Entry from ctx_logrus middleware.
+
+If the ctx_logrus middleware wasn't used, a no-op `logrus.Entry` is returned. This makes it safe to
+use regardless.
+
+## <a name="ToContext">func</a> [ToContext](./context.go#L59)
+``` go
+func ToContext(ctx context.Context, entry *logrus.Entry) context.Context
+```
+ToContext adds the logrus.Entry to the context for extraction later.
+Returning the new context that has been created.
+
+- - -
+Generated by [godoc2ghmd](https://github.com/GandalfUK/godoc2ghmd) \ No newline at end of file
diff --git a/vendor/github.com/grpc-ecosystem/go-grpc-middleware/logging/logrus/ctxlogrus/context.go b/vendor/github.com/grpc-ecosystem/go-grpc-middleware/logging/logrus/ctxlogrus/context.go
new file mode 100644
index 00000000..ff3e3353
--- /dev/null
+++ b/vendor/github.com/grpc-ecosystem/go-grpc-middleware/logging/logrus/ctxlogrus/context.go
@@ -0,0 +1,65 @@
+package ctxlogrus
+
+import (
+ "github.com/grpc-ecosystem/go-grpc-middleware/tags"
+ "github.com/sirupsen/logrus"
+ "golang.org/x/net/context"
+)
+
+type ctxLoggerMarker struct{}
+
+type ctxLogger struct {
+ logger *logrus.Entry
+ fields logrus.Fields
+}
+
+var (
+ ctxLoggerKey = &ctxLoggerMarker{}
+)
+
+// AddFields adds logrus fields to the logger.
+func AddFields(ctx context.Context, fields logrus.Fields) {
+ l, ok := ctx.Value(ctxLoggerKey).(*ctxLogger)
+ if !ok || l == nil {
+ return
+ }
+ for k, v := range fields {
+ l.fields[k] = v
+ }
+}
+
+// Extract takes the call-scoped logrus.Entry from ctx_logrus middleware.
+//
+// If the ctx_logrus middleware wasn't used, a no-op `logrus.Entry` is returned. This makes it safe to
+// use regardless.
+func Extract(ctx context.Context) *logrus.Entry {
+ l, ok := ctx.Value(ctxLoggerKey).(*ctxLogger)
+ if !ok || l == nil {
+ return logrus.NewEntry(nullLogger)
+ }
+
+ fields := logrus.Fields{}
+
+ // Add grpc_ctxtags tags metadata until now.
+ tags := grpc_ctxtags.Extract(ctx)
+ for k, v := range tags.Values() {
+ fields[k] = v
+ }
+
+ // Add logrus fields added until now.
+ for k, v := range l.fields {
+ fields[k] = v
+ }
+
+ return l.logger.WithFields(fields)
+}
+
+// ToContext adds the logrus.Entry to the context for extraction later.
+// Returning the new context that has been created.
+func ToContext(ctx context.Context, entry *logrus.Entry) context.Context {
+ l := &ctxLogger{
+ logger: entry,
+ fields: logrus.Fields{},
+ }
+ return context.WithValue(ctx, ctxLoggerKey, l)
+}
diff --git a/vendor/github.com/grpc-ecosystem/go-grpc-middleware/logging/logrus/ctxlogrus/doc.go b/vendor/github.com/grpc-ecosystem/go-grpc-middleware/logging/logrus/ctxlogrus/doc.go
new file mode 100644
index 00000000..95803fb6
--- /dev/null
+++ b/vendor/github.com/grpc-ecosystem/go-grpc-middleware/logging/logrus/ctxlogrus/doc.go
@@ -0,0 +1,14 @@
+/*
+`ctxlogrus` is a ctxlogger that is backed by logrus
+
+It accepts a user-configured `logrus.Logger` that will be used for logging. The same `logrus.Logger` will
+be populated into the `context.Context` passed into gRPC handler code.
+
+You can use `ctx_logrus.Extract` to log into a request-scoped `logrus.Logger` instance in your handler code.
+
+As `ctx_logrus.Extract` will iterate all tags on from `grpc_ctxtags` it is therefore expensive so it is advised that you
+extract once at the start of the function from the context and reuse it for the remainder of the function (see examples).
+
+Please see examples and tests for examples of use.
+*/
+package ctxlogrus
diff --git a/vendor/github.com/grpc-ecosystem/go-grpc-middleware/logging/logrus/ctxlogrus/noop.go b/vendor/github.com/grpc-ecosystem/go-grpc-middleware/logging/logrus/ctxlogrus/noop.go
new file mode 100644
index 00000000..7fcc0f64
--- /dev/null
+++ b/vendor/github.com/grpc-ecosystem/go-grpc-middleware/logging/logrus/ctxlogrus/noop.go
@@ -0,0 +1,16 @@
+package ctxlogrus
+
+import (
+ "io/ioutil"
+
+ "github.com/sirupsen/logrus"
+)
+
+var (
+ nullLogger = &logrus.Logger{
+ Out: ioutil.Discard,
+ Formatter: new(logrus.TextFormatter),
+ Hooks: make(logrus.LevelHooks),
+ Level: logrus.PanicLevel,
+ }
+)
diff --git a/vendor/github.com/grpc-ecosystem/go-grpc-middleware/logging/logrus/doc.go b/vendor/github.com/grpc-ecosystem/go-grpc-middleware/logging/logrus/doc.go
new file mode 100644
index 00000000..df8785f5
--- /dev/null
+++ b/vendor/github.com/grpc-ecosystem/go-grpc-middleware/logging/logrus/doc.go
@@ -0,0 +1,67 @@
+/*
+`grpc_logrus` is a gRPC logging middleware backed by Logrus loggers
+
+It accepts a user-configured `logrus.Entry` that will be used for logging completed gRPC calls. The same
+`logrus.Entry` will be used for logging completed gRPC calls, and be populated into the `context.Context` passed into gRPC handler code.
+
+On calling `StreamServerInterceptor` or `UnaryServerInterceptor` this logging middleware will add gRPC call information
+to the ctx so that it will be present on subsequent use of the `ctxlogrus` logger.
+
+This package also implements request and response *payload* logging, both for server-side and client-side. These will be
+logged as structured `jsonpb` fields for every message received/sent (both unary and streaming). For that please use
+`Payload*Interceptor` functions for that. Please note that the user-provided function that determines whetether to log
+the full request/response payload needs to be written with care, this can significantly slow down gRPC.
+
+If a deadline is present on the gRPC request the grpc.request.deadline tag is populated when the request begins. grpc.request.deadline
+is a string representing the time (RFC3339) when the current call will expire.
+
+Logrus can also be made as a backend for gRPC library internals. For that use `ReplaceGrpcLogger`.
+
+*Server Interceptor*
+Below is a JSON formatted example of a log that would be logged by the server interceptor:
+
+ {
+ "level": "info", // string logrus log levels
+ "msg": "finished unary call", // string log message
+ "grpc.code": "OK", // string grpc status code
+ "grpc.method": "Ping", // string method name
+ "grpc.service": "mwitkow.testproto.TestService", // string full name of the called service
+ "grpc.start_time": "2006-01-02T15:04:05Z07:00", // string RFC3339 representation of the start time
+ "grpc.request.deadline": "2006-01-02T15:04:05Z07:00", // string RFC3339 deadline of the current request if supplied
+ "grpc.request.value": "something", // string value on the request
+ "grpc.time_ms": 1.234, // float32 run time of the call in ms
+ "peer.address": {
+ "IP": "127.0.0.1", // string IP address of calling party
+ "Port": 60216, // int port call is coming in on
+ "Zone": "" // string peer zone for caller
+ },
+ "span.kind": "server", // string client | server
+ "system": "grpc" // string
+
+ "custom_field": "custom_value", // string user defined field
+ "custom_tags.int": 1337, // int user defined tag on the ctx
+ "custom_tags.string": "something", // string user defined tag on the ctx
+ }
+
+*Payload Interceptor*
+Below is a JSON formatted example of a log that would be logged by the payload interceptor:
+
+ {
+ "level": "info", // string logrus log levels
+ "msg": "client request payload logged as grpc.request.content", // string log message
+
+ "grpc.request.content": { // object content of RPC request
+ "value": "something", // string defined by caller
+ "sleepTimeMs": 9999 // int defined by caller
+ },
+ "grpc.method": "Ping", // string method being called
+ "grpc.service": "mwitkow.testproto.TestService", // string service being called
+ "span.kind": "client", // string client | server
+ "system": "grpc" // string
+ }
+
+Note - due to implementation ZAP differs from Logrus in the "grpc.request.content" object by having an inner "msg" object.
+
+Please see examples and tests for examples of use.
+*/
+package grpc_logrus
diff --git a/vendor/github.com/grpc-ecosystem/go-grpc-middleware/logging/logrus/grpclogger.go b/vendor/github.com/grpc-ecosystem/go-grpc-middleware/logging/logrus/grpclogger.go
new file mode 100644
index 00000000..c0f6c5ab
--- /dev/null
+++ b/vendor/github.com/grpc-ecosystem/go-grpc-middleware/logging/logrus/grpclogger.go
@@ -0,0 +1,15 @@
+// Copyright 2017 Michal Witkowski. All Rights Reserved.
+// See LICENSE for licensing terms.
+
+package grpc_logrus
+
+import (
+ "github.com/sirupsen/logrus"
+ "google.golang.org/grpc/grpclog"
+)
+
+// ReplaceGrpcLogger sets the given logrus.Logger as a gRPC-level logger.
+// This should be called *before* any other initialization, preferably from init() functions.
+func ReplaceGrpcLogger(logger *logrus.Entry) {
+ grpclog.SetLogger(logger.WithField("system", SystemField))
+}
diff --git a/vendor/github.com/grpc-ecosystem/go-grpc-middleware/logging/logrus/options.go b/vendor/github.com/grpc-ecosystem/go-grpc-middleware/logging/logrus/options.go
new file mode 100644
index 00000000..b2b35189
--- /dev/null
+++ b/vendor/github.com/grpc-ecosystem/go-grpc-middleware/logging/logrus/options.go
@@ -0,0 +1,185 @@
+// Copyright 2017 Michal Witkowski. All Rights Reserved.
+// See LICENSE for licensing terms.
+
+package grpc_logrus
+
+import (
+ "time"
+
+ "github.com/grpc-ecosystem/go-grpc-middleware/logging"
+ "github.com/sirupsen/logrus"
+ "google.golang.org/grpc/codes"
+)
+
+var (
+ defaultOptions = &options{
+ levelFunc: nil,
+ shouldLog: grpc_logging.DefaultDeciderMethod,
+ codeFunc: grpc_logging.DefaultErrorToCode,
+ durationFunc: DefaultDurationToField,
+ }
+)
+
+type options struct {
+ levelFunc CodeToLevel
+ shouldLog grpc_logging.Decider
+ codeFunc grpc_logging.ErrorToCode
+ durationFunc DurationToField
+}
+
+func evaluateServerOpt(opts []Option) *options {
+ optCopy := &options{}
+ *optCopy = *defaultOptions
+ optCopy.levelFunc = DefaultCodeToLevel
+ for _, o := range opts {
+ o(optCopy)
+ }
+ return optCopy
+}
+
+func evaluateClientOpt(opts []Option) *options {
+ optCopy := &options{}
+ *optCopy = *defaultOptions
+ optCopy.levelFunc = DefaultClientCodeToLevel
+ for _, o := range opts {
+ o(optCopy)
+ }
+ return optCopy
+}
+
+type Option func(*options)
+
+// CodeToLevel function defines the mapping between gRPC return codes and interceptor log level.
+type CodeToLevel func(code codes.Code) logrus.Level
+
+// DurationToField function defines how to produce duration fields for logging
+type DurationToField func(duration time.Duration) (key string, value interface{})
+
+// WithDecider customizes the function for deciding if the gRPC interceptor logs should log.
+func WithDecider(f grpc_logging.Decider) Option {
+ return func(o *options) {
+ o.shouldLog = f
+ }
+}
+
+// WithLevels customizes the function for mapping gRPC return codes and interceptor log level statements.
+func WithLevels(f CodeToLevel) Option {
+ return func(o *options) {
+ o.levelFunc = f
+ }
+}
+
+// WithCodes customizes the function for mapping errors to error codes.
+func WithCodes(f grpc_logging.ErrorToCode) Option {
+ return func(o *options) {
+ o.codeFunc = f
+ }
+}
+
+// WithDurationField customizes the function for mapping request durations to log fields.
+func WithDurationField(f DurationToField) Option {
+ return func(o *options) {
+ o.durationFunc = f
+ }
+}
+
+// DefaultCodeToLevel is the default implementation of gRPC return codes to log levels for server side.
+func DefaultCodeToLevel(code codes.Code) logrus.Level {
+ switch code {
+ case codes.OK:
+ return logrus.InfoLevel
+ case codes.Canceled:
+ return logrus.InfoLevel
+ case codes.Unknown:
+ return logrus.ErrorLevel
+ case codes.InvalidArgument:
+ return logrus.InfoLevel
+ case codes.DeadlineExceeded:
+ return logrus.WarnLevel
+ case codes.NotFound:
+ return logrus.InfoLevel
+ case codes.AlreadyExists:
+ return logrus.InfoLevel
+ case codes.PermissionDenied:
+ return logrus.WarnLevel
+ case codes.Unauthenticated:
+ return logrus.InfoLevel // unauthenticated requests can happen
+ case codes.ResourceExhausted:
+ return logrus.WarnLevel
+ case codes.FailedPrecondition:
+ return logrus.WarnLevel
+ case codes.Aborted:
+ return logrus.WarnLevel
+ case codes.OutOfRange:
+ return logrus.WarnLevel
+ case codes.Unimplemented:
+ return logrus.ErrorLevel
+ case codes.Internal:
+ return logrus.ErrorLevel
+ case codes.Unavailable:
+ return logrus.WarnLevel
+ case codes.DataLoss:
+ return logrus.ErrorLevel
+ default:
+ return logrus.ErrorLevel
+ }
+}
+
+// DefaultClientCodeToLevel is the default implementation of gRPC return codes to log levels for client side.
+func DefaultClientCodeToLevel(code codes.Code) logrus.Level {
+ switch code {
+ case codes.OK:
+ return logrus.DebugLevel
+ case codes.Canceled:
+ return logrus.DebugLevel
+ case codes.Unknown:
+ return logrus.InfoLevel
+ case codes.InvalidArgument:
+ return logrus.DebugLevel
+ case codes.DeadlineExceeded:
+ return logrus.InfoLevel
+ case codes.NotFound:
+ return logrus.DebugLevel
+ case codes.AlreadyExists:
+ return logrus.DebugLevel
+ case codes.PermissionDenied:
+ return logrus.InfoLevel
+ case codes.Unauthenticated:
+ return logrus.InfoLevel // unauthenticated requests can happen
+ case codes.ResourceExhausted:
+ return logrus.DebugLevel
+ case codes.FailedPrecondition:
+ return logrus.DebugLevel
+ case codes.Aborted:
+ return logrus.DebugLevel
+ case codes.OutOfRange:
+ return logrus.DebugLevel
+ case codes.Unimplemented:
+ return logrus.WarnLevel
+ case codes.Internal:
+ return logrus.WarnLevel
+ case codes.Unavailable:
+ return logrus.WarnLevel
+ case codes.DataLoss:
+ return logrus.WarnLevel
+ default:
+ return logrus.InfoLevel
+ }
+}
+
+// DefaultDurationToField is the default implementation of converting request duration to a log field (key and value).
+var DefaultDurationToField = DurationToTimeMillisField
+
+// DurationToTimeMillisField converts the duration to milliseconds and uses the key `grpc.time_ms`.
+func DurationToTimeMillisField(duration time.Duration) (key string, value interface{}) {
+ return "grpc.time_ms", durationToMilliseconds(duration)
+}
+
+// DurationToDurationField uses the duration value to log the request duration.
+func DurationToDurationField(duration time.Duration) (key string, value interface{}) {
+ return "grpc.duration", duration
+}
+
+func durationToMilliseconds(duration time.Duration) float32 {
+ return float32(duration.Nanoseconds()/1000) / 1000
+}
diff --git a/vendor/github.com/grpc-ecosystem/go-grpc-middleware/logging/logrus/payload_interceptors.go b/vendor/github.com/grpc-ecosystem/go-grpc-middleware/logging/logrus/payload_interceptors.go
new file mode 100644
index 00000000..6ac4d04a
--- /dev/null
+++ b/vendor/github.com/grpc-ecosystem/go-grpc-middleware/logging/logrus/payload_interceptors.go
@@ -0,0 +1,144 @@
+package grpc_logrus
+
+import (
+ "bytes"
+ "fmt"
+
+ "github.com/golang/protobuf/jsonpb"
+ "github.com/golang/protobuf/proto"
+ "github.com/grpc-ecosystem/go-grpc-middleware/logging"
+ "github.com/grpc-ecosystem/go-grpc-middleware/tags/logrus"
+ "github.com/sirupsen/logrus"
+ "golang.org/x/net/context"
+ "google.golang.org/grpc"
+)
+
+var (
+ // JsonPBMarshaller is the marshaller used for serializing protobuf messages.
+ JsonPbMarshaller = &jsonpb.Marshaler{}
+)
+
+// PayloadUnaryServerInterceptor returns a new unary server interceptors that logs the payloads of requests.
+//
+// This *only* works when placed *after* the `grpc_logrus.UnaryServerInterceptor`. However, the logging can be done to a
+// separate instance of the logger.
+func PayloadUnaryServerInterceptor(entry *logrus.Entry, decider grpc_logging.ServerPayloadLoggingDecider) grpc.UnaryServerInterceptor {
+ return func(ctx context.Context, req interface{}, info *grpc.UnaryServerInfo, handler grpc.UnaryHandler) (interface{}, error) {
+ if !decider(ctx, info.FullMethod, info.Server) {
+ return handler(ctx, req)
+ }
+ // Use the provided logrus.Entry for logging but use the fields from context.
+ logEntry := entry.WithFields(ctx_logrus.Extract(ctx).Data)
+ logProtoMessageAsJson(logEntry, req, "grpc.request.content", "server request payload logged as grpc.request.content field")
+ resp, err := handler(ctx, req)
+ if err == nil {
+ logProtoMessageAsJson(logEntry, resp, "grpc.response.content", "server response payload logged as grpc.request.content field")
+ }
+ return resp, err
+ }
+}
+
+// PayloadUnaryServerInterceptor returns a new server server interceptors that logs the payloads of requests.
+//
+// This *only* works when placed *after* the `grpc_logrus.StreamServerInterceptor`. However, the logging can be done to a
+// separate instance of the logger.
+func PayloadStreamServerInterceptor(entry *logrus.Entry, decider grpc_logging.ServerPayloadLoggingDecider) grpc.StreamServerInterceptor {
+ return func(srv interface{}, stream grpc.ServerStream, info *grpc.StreamServerInfo, handler grpc.StreamHandler) error {
+ if !decider(stream.Context(), info.FullMethod, srv) {
+ return handler(srv, stream)
+ }
+ // Use the provided logrus.Entry for logging but use the fields from context.
+ logEntry := entry.WithFields(Extract(stream.Context()).Data)
+ newStream := &loggingServerStream{ServerStream: stream, entry: logEntry}
+ return handler(srv, newStream)
+ }
+}
+
+// PayloadUnaryClientInterceptor returns a new unary client interceptor that logs the paylods of requests and responses.
+func PayloadUnaryClientInterceptor(entry *logrus.Entry, decider grpc_logging.ClientPayloadLoggingDecider) grpc.UnaryClientInterceptor {
+ return func(ctx context.Context, method string, req, reply interface{}, cc *grpc.ClientConn, invoker grpc.UnaryInvoker, opts ...grpc.CallOption) error {
+ if !decider(ctx, method) {
+ return invoker(ctx, method, req, reply, cc, opts...)
+ }
+ logEntry := entry.WithFields(newClientLoggerFields(ctx, method))
+ logProtoMessageAsJson(logEntry, req, "grpc.request.content", "client request payload logged as grpc.request.content")
+ err := invoker(ctx, method, req, reply, cc, opts...)
+ if err == nil {
+ logProtoMessageAsJson(logEntry, reply, "grpc.response.content", "client response payload logged as grpc.response.content")
+ }
+ return err
+ }
+}
+
+// PayloadStreamServerInterceptor returns a new streaming client interceptor that logs the paylods of requests and responses.
+func PayloadStreamClientInterceptor(entry *logrus.Entry, decider grpc_logging.ClientPayloadLoggingDecider) grpc.StreamClientInterceptor {
+ return func(ctx context.Context, desc *grpc.StreamDesc, cc *grpc.ClientConn, method string, streamer grpc.Streamer, opts ...grpc.CallOption) (grpc.ClientStream, error) {
+ if !decider(ctx, method) {
+ return streamer(ctx, desc, cc, method, opts...)
+ }
+ logEntry := entry.WithFields(newClientLoggerFields(ctx, method))
+ clientStream, err := streamer(ctx, desc, cc, method, opts...)
+ newStream := &loggingClientStream{ClientStream: clientStream, entry: logEntry}
+ return newStream, err
+ }
+}
+
+type loggingClientStream struct {
+ grpc.ClientStream
+ entry *logrus.Entry
+}
+
+func (l *loggingClientStream) SendMsg(m interface{}) error {
+ err := l.ClientStream.SendMsg(m)
+ if err == nil {
+ logProtoMessageAsJson(l.entry, m, "grpc.request.content", "server request payload logged as grpc.request.content field")
+ }
+ return err
+}
+
+func (l *loggingClientStream) RecvMsg(m interface{}) error {
+ err := l.ClientStream.RecvMsg(m)
+ if err == nil {
+ logProtoMessageAsJson(l.entry, m, "grpc.response.content", "server response payload logged as grpc.response.content field")
+ }
+ return err
+}
+
+type loggingServerStream struct {
+ grpc.ServerStream
+ entry *logrus.Entry
+}
+
+func (l *loggingServerStream) SendMsg(m interface{}) error {
+ err := l.ServerStream.SendMsg(m)
+ if err == nil {
+ logProtoMessageAsJson(l.entry, m, "grpc.response.content", "server response payload logged as grpc.response.content field")
+ }
+ return err
+}
+
+func (l *loggingServerStream) RecvMsg(m interface{}) error {
+ err := l.ServerStream.RecvMsg(m)
+ if err == nil {
+ logProtoMessageAsJson(l.entry, m, "grpc.request.content", "server request payload logged as grpc.request.content field")
+ }
+ return err
+}
+
+func logProtoMessageAsJson(entry *logrus.Entry, pbMsg interface{}, key string, msg string) {
+ if p, ok := pbMsg.(proto.Message); ok {
+ entry.WithField(key, &jsonpbMarshalleble{p}).Info(msg)
+ }
+}
+
+type jsonpbMarshalleble struct {
+ proto.Message
+}
+
+func (j *jsonpbMarshalleble) MarshalJSON() ([]byte, error) {
+ b := &bytes.Buffer{}
+ if err := JsonPbMarshaller.Marshal(b, j.Message); err != nil {
+ return nil, fmt.Errorf("jsonpb serializer failed: %v", err)
+ }
+ return b.Bytes(), nil
+}
diff --git a/vendor/github.com/grpc-ecosystem/go-grpc-middleware/logging/logrus/server_interceptors.go b/vendor/github.com/grpc-ecosystem/go-grpc-middleware/logging/logrus/server_interceptors.go
new file mode 100644
index 00000000..0711d881
--- /dev/null
+++ b/vendor/github.com/grpc-ecosystem/go-grpc-middleware/logging/logrus/server_interceptors.go
@@ -0,0 +1,129 @@
+// Copyright (c) Improbable Worlds Ltd, All Rights Reserved
+
+package grpc_logrus
+
+import (
+ "path"
+ "time"
+
+ "github.com/grpc-ecosystem/go-grpc-middleware"
+ "github.com/grpc-ecosystem/go-grpc-middleware/logging/logrus/ctxlogrus"
+ "github.com/grpc-ecosystem/go-grpc-middleware/tags/logrus"
+ "github.com/sirupsen/logrus"
+ "golang.org/x/net/context"
+ "google.golang.org/grpc"
+)
+
+var (
+ // SystemField is used in every log statement made through grpc_logrus. Can be overwritten before any initialization code.
+ SystemField = "system"
+
+ // KindField describes the log gield used to incicate whether this is a server or a client log statment.
+ KindField = "span.kind"
+)
+
+// PayloadUnaryServerInterceptor returns a new unary server interceptors that adds logrus.Entry to the context.
+func UnaryServerInterceptor(entry *logrus.Entry, opts ...Option) grpc.UnaryServerInterceptor {
+ o := evaluateServerOpt(opts)
+ return func(ctx context.Context, req interface{}, info *grpc.UnaryServerInfo, handler grpc.UnaryHandler) (interface{}, error) {
+ startTime := time.Now()
+ newCtx := newLoggerForCall(ctx, entry, info.FullMethod, startTime)
+
+ resp, err := handler(newCtx, req)
+
+ if !o.shouldLog(info.FullMethod, err) {
+ return resp, err
+ }
+ code := o.codeFunc(err)
+ level := o.levelFunc(code)
+ durField, durVal := o.durationFunc(time.Since(startTime))
+ fields := logrus.Fields{
+ "grpc.code": code.String(),
+ durField: durVal,
+ }
+ if err != nil {
+ fields[logrus.ErrorKey] = err
+ }
+
+ levelLogf(
+ ctx_logrus.Extract(newCtx).WithFields(fields), // re-extract logger from newCtx, as it may have extra fields that changed in the holder.
+ level,
+ "finished unary call with code "+code.String())
+
+ return resp, err
+ }
+}
+
+// StreamServerInterceptor returns a new streaming server interceptor that adds logrus.Entry to the context.
+func StreamServerInterceptor(entry *logrus.Entry, opts ...Option) grpc.StreamServerInterceptor {
+ o := evaluateServerOpt(opts)
+ return func(srv interface{}, stream grpc.ServerStream, info *grpc.StreamServerInfo, handler grpc.StreamHandler) error {
+ startTime := time.Now()
+ newCtx := newLoggerForCall(stream.Context(), entry, info.FullMethod, startTime)
+ wrapped := grpc_middleware.WrapServerStream(stream)
+ wrapped.WrappedContext = newCtx
+
+ err := handler(srv, wrapped)
+
+ if !o.shouldLog(info.FullMethod, err) {
+ return err
+ }
+ code := o.codeFunc(err)
+ level := o.levelFunc(code)
+ durField, durVal := o.durationFunc(time.Since(startTime))
+ fields := logrus.Fields{
+ "grpc.code": code.String(),
+ durField: durVal,
+ }
+ if err != nil {
+ fields[logrus.ErrorKey] = err
+ }
+
+ levelLogf(
+ ctx_logrus.Extract(newCtx).WithFields(fields), // re-extract logger from newCtx, as it may have extra fields that changed in the holder.
+ level,
+ "finished streaming call with code "+code.String())
+
+ return err
+ }
+}
+
+func levelLogf(entry *logrus.Entry, level logrus.Level, format string, args ...interface{}) {
+ switch level {
+ case logrus.DebugLevel:
+ entry.Debugf(format, args...)
+ case logrus.InfoLevel:
+ entry.Infof(format, args...)
+ case logrus.WarnLevel:
+ entry.Warningf(format, args...)
+ case logrus.ErrorLevel:
+ entry.Errorf(format, args...)
+ case logrus.FatalLevel:
+ entry.Fatalf(format, args...)
+ case logrus.PanicLevel:
+ entry.Panicf(format, args...)
+ }
+}
+
+func newLoggerForCall(ctx context.Context, entry *logrus.Entry, fullMethodString string, start time.Time) context.Context {
+ service := path.Dir(fullMethodString)[1:]
+ method := path.Base(fullMethodString)
+ callLog := entry.WithFields(
+ logrus.Fields{
+ SystemField: "grpc",
+ KindField: "server",
+ "grpc.service": service,
+ "grpc.method": method,
+ "grpc.start_time": start.Format(time.RFC3339),
+ })
+
+ if d, ok := ctx.Deadline(); ok {
+ callLog = callLog.WithFields(
+ logrus.Fields{
+ "grpc.request.deadline": d.Format(time.RFC3339),
+ })
+ }
+
+ callLog = callLog.WithFields(ctx_logrus.Extract(ctx).Data)
+ return ctxlogrus.ToContext(ctx, callLog)
+}
diff --git a/vendor/github.com/grpc-ecosystem/go-grpc-middleware/makefile b/vendor/github.com/grpc-ecosystem/go-grpc-middleware/makefile
new file mode 100644
index 00000000..4ad54c37
--- /dev/null
+++ b/vendor/github.com/grpc-ecosystem/go-grpc-middleware/makefile
@@ -0,0 +1,19 @@
+SHELL="/bin/bash"
+
+GOFILES_NOVENDOR = $(shell go list ./... | grep -v /vendor/)
+
+all: vet fmt docs test
+
+docs:
+ ./scripts/fixup.sh
+
+fmt:
+ go fmt $(GOFILES_NOVENDOR)
+
+vet:
+ go vet $(GOFILES_NOVENDOR)
+
+test: vet
+ ./scripts/test_all.sh
+
+.PHONY: all docs validate test
diff --git a/vendor/github.com/grpc-ecosystem/go-grpc-middleware/recovery/DOC.md b/vendor/github.com/grpc-ecosystem/go-grpc-middleware/recovery/DOC.md
new file mode 100644
index 00000000..d4ef78af
--- /dev/null
+++ b/vendor/github.com/grpc-ecosystem/go-grpc-middleware/recovery/DOC.md
@@ -0,0 +1,107 @@
+# grpc_recovery
+`import "github.com/grpc-ecosystem/go-grpc-middleware/recovery"`
+
+* [Overview](#pkg-overview)
+* [Imported Packages](#pkg-imports)
+* [Index](#pkg-index)
+* [Examples](#pkg-examples)
+
+## <a name="pkg-overview">Overview</a>
+`grpc_recovery` are intereceptors that recover from gRPC handler panics.
+
+### Server Side Recovery Middleware
+By default a panic will be converted into a gRPC error with `code.Internal`.
+
+Handling can be customised by providing an alternate recovery function.
+
+Please see examples for simple examples of use.
+
+#### Example:
+
+<details>
+<summary>Click to expand code.</summary>
+
+```go
+package grpc_recovery_test
+
+import (
+ "github.com/grpc-ecosystem/go-grpc-middleware"
+ "github.com/grpc-ecosystem/go-grpc-middleware/recovery"
+ "google.golang.org/grpc"
+)
+
+var (
+ customFunc grpc_recovery.RecoveryHandlerFunc
+)
+
+// Initialization shows an initialization sequence with a custom recovery handler func.
+func Example_initialization() {
+ // Shared options for the logger, with a custom gRPC code to log level function.
+ opts := []grpc_recovery.Option{
+ grpc_recovery.WithRecoveryHandler(customFunc),
+ }
+ // Create a server. Recovery handlers should typically be last in the chain so that other middleware
+ // (e.g. logging) can operate on the recovered state instead of being directly affected by any panic
+ _ = grpc.NewServer(
+ grpc_middleware.WithUnaryServerChain(
+ grpc_recovery.UnaryServerInterceptor(opts...),
+ ),
+ grpc_middleware.WithStreamServerChain(
+ grpc_recovery.StreamServerInterceptor(opts...),
+ ),
+ )
+}
+```
+
+</details>
+
+## <a name="pkg-imports">Imported Packages</a>
+
+- [golang.org/x/net/context](https://godoc.org/golang.org/x/net/context)
+- [google.golang.org/grpc](https://godoc.org/google.golang.org/grpc)
+- [google.golang.org/grpc/codes](https://godoc.org/google.golang.org/grpc/codes)
+
+## <a name="pkg-index">Index</a>
+* [func StreamServerInterceptor(opts ...Option) grpc.StreamServerInterceptor](#StreamServerInterceptor)
+* [func UnaryServerInterceptor(opts ...Option) grpc.UnaryServerInterceptor](#UnaryServerInterceptor)
+* [type Option](#Option)
+ * [func WithRecoveryHandler(f RecoveryHandlerFunc) Option](#WithRecoveryHandler)
+* [type RecoveryHandlerFunc](#RecoveryHandlerFunc)
+
+#### <a name="pkg-examples">Examples</a>
+* [Package (Initialization)](#example__initialization)
+
+#### <a name="pkg-files">Package files</a>
+[doc.go](./doc.go) [interceptors.go](./interceptors.go) [options.go](./options.go)
+
+## <a name="StreamServerInterceptor">func</a> [StreamServerInterceptor](./interceptors.go#L30)
+``` go
+func StreamServerInterceptor(opts ...Option) grpc.StreamServerInterceptor
+```
+StreamServerInterceptor returns a new streaming server interceptor for panic recovery.
+
+## <a name="UnaryServerInterceptor">func</a> [UnaryServerInterceptor](./interceptors.go#L16)
+``` go
+func UnaryServerInterceptor(opts ...Option) grpc.UnaryServerInterceptor
+```
+UnaryServerInterceptor returns a new unary server interceptor for panic recovery.
+
+## <a name="Option">type</a> [Option](./options.go#L25)
+``` go
+type Option func(*options)
+```
+
+### <a name="WithRecoveryHandler">func</a> [WithRecoveryHandler](./options.go#L28)
+``` go
+func WithRecoveryHandler(f RecoveryHandlerFunc) Option
+```
+WithRecoveryHandler customizes the function for recovering from a panic.
+
+## <a name="RecoveryHandlerFunc">type</a> [RecoveryHandlerFunc](./interceptors.go#L13)
+``` go
+type RecoveryHandlerFunc func(p interface{}) (err error)
+```
+RecoveryHandlerFunc is a function that recovers from the panic `p` by returning an `error`.
+
+- - -
+Generated by [godoc2ghmd](https://github.com/GandalfUK/godoc2ghmd) \ No newline at end of file
diff --git a/vendor/github.com/grpc-ecosystem/go-grpc-middleware/recovery/README.md b/vendor/github.com/grpc-ecosystem/go-grpc-middleware/recovery/README.md
new file mode 100644
index 00000000..d4ef78af
--- /dev/null
+++ b/vendor/github.com/grpc-ecosystem/go-grpc-middleware/recovery/README.md
@@ -0,0 +1,107 @@
+# grpc_recovery
+`import "github.com/grpc-ecosystem/go-grpc-middleware/recovery"`
+
+* [Overview](#pkg-overview)
+* [Imported Packages](#pkg-imports)
+* [Index](#pkg-index)
+* [Examples](#pkg-examples)
+
+## <a name="pkg-overview">Overview</a>
+`grpc_recovery` are intereceptors that recover from gRPC handler panics.
+
+### Server Side Recovery Middleware
+By default a panic will be converted into a gRPC error with `code.Internal`.
+
+Handling can be customised by providing an alternate recovery function.
+
+Please see examples for simple examples of use.
+
+#### Example:
+
+<details>
+<summary>Click to expand code.</summary>
+
+```go
+package grpc_recovery_test
+
+import (
+ "github.com/grpc-ecosystem/go-grpc-middleware"
+ "github.com/grpc-ecosystem/go-grpc-middleware/recovery"
+ "google.golang.org/grpc"
+)
+
+var (
+ customFunc grpc_recovery.RecoveryHandlerFunc
+)
+
+// Initialization shows an initialization sequence with a custom recovery handler func.
+func Example_initialization() {
+ // Shared options for the logger, with a custom gRPC code to log level function.
+ opts := []grpc_recovery.Option{
+ grpc_recovery.WithRecoveryHandler(customFunc),
+ }
+ // Create a server. Recovery handlers should typically be last in the chain so that other middleware
+ // (e.g. logging) can operate on the recovered state instead of being directly affected by any panic
+ _ = grpc.NewServer(
+ grpc_middleware.WithUnaryServerChain(
+ grpc_recovery.UnaryServerInterceptor(opts...),
+ ),
+ grpc_middleware.WithStreamServerChain(
+ grpc_recovery.StreamServerInterceptor(opts...),
+ ),
+ )
+}
+```
+
+</details>
+
+## <a name="pkg-imports">Imported Packages</a>
+
+- [golang.org/x/net/context](https://godoc.org/golang.org/x/net/context)
+- [google.golang.org/grpc](https://godoc.org/google.golang.org/grpc)
+- [google.golang.org/grpc/codes](https://godoc.org/google.golang.org/grpc/codes)
+
+## <a name="pkg-index">Index</a>
+* [func StreamServerInterceptor(opts ...Option) grpc.StreamServerInterceptor](#StreamServerInterceptor)
+* [func UnaryServerInterceptor(opts ...Option) grpc.UnaryServerInterceptor](#UnaryServerInterceptor)
+* [type Option](#Option)
+ * [func WithRecoveryHandler(f RecoveryHandlerFunc) Option](#WithRecoveryHandler)
+* [type RecoveryHandlerFunc](#RecoveryHandlerFunc)
+
+#### <a name="pkg-examples">Examples</a>
+* [Package (Initialization)](#example__initialization)
+
+#### <a name="pkg-files">Package files</a>
+[doc.go](./doc.go) [interceptors.go](./interceptors.go) [options.go](./options.go)
+
+## <a name="StreamServerInterceptor">func</a> [StreamServerInterceptor](./interceptors.go#L30)
+``` go
+func StreamServerInterceptor(opts ...Option) grpc.StreamServerInterceptor
+```
+StreamServerInterceptor returns a new streaming server interceptor for panic recovery.
+
+## <a name="UnaryServerInterceptor">func</a> [UnaryServerInterceptor](./interceptors.go#L16)
+``` go
+func UnaryServerInterceptor(opts ...Option) grpc.UnaryServerInterceptor
+```
+UnaryServerInterceptor returns a new unary server interceptor for panic recovery.
+
+## <a name="Option">type</a> [Option](./options.go#L25)
+``` go
+type Option func(*options)
+```
+
+### <a name="WithRecoveryHandler">func</a> [WithRecoveryHandler](./options.go#L28)
+``` go
+func WithRecoveryHandler(f RecoveryHandlerFunc) Option
+```
+WithRecoveryHandler customizes the function for recovering from a panic.
+
+## <a name="RecoveryHandlerFunc">type</a> [RecoveryHandlerFunc](./interceptors.go#L13)
+``` go
+type RecoveryHandlerFunc func(p interface{}) (err error)
+```
+RecoveryHandlerFunc is a function that recovers from the panic `p` by returning an `error`.
+
+- - -
+Generated by [godoc2ghmd](https://github.com/GandalfUK/godoc2ghmd) \ No newline at end of file
diff --git a/vendor/github.com/grpc-ecosystem/go-grpc-middleware/recovery/doc.go b/vendor/github.com/grpc-ecosystem/go-grpc-middleware/recovery/doc.go
new file mode 100644
index 00000000..da40190c
--- /dev/null
+++ b/vendor/github.com/grpc-ecosystem/go-grpc-middleware/recovery/doc.go
@@ -0,0 +1,15 @@
+// Copyright 2017 David Ackroyd. All Rights Reserved.
+// See LICENSE for licensing terms.
+
+/*
+`grpc_recovery` are intereceptors that recover from gRPC handler panics.
+
+Server Side Recovery Middleware
+
+By default a panic will be converted into a gRPC error with `code.Internal`.
+
+Handling can be customised by providing an alternate recovery function.
+
+Please see examples for simple examples of use.
+*/
+package grpc_recovery
diff --git a/vendor/github.com/grpc-ecosystem/go-grpc-middleware/recovery/interceptors.go b/vendor/github.com/grpc-ecosystem/go-grpc-middleware/recovery/interceptors.go
new file mode 100644
index 00000000..c0fb5ac8
--- /dev/null
+++ b/vendor/github.com/grpc-ecosystem/go-grpc-middleware/recovery/interceptors.go
@@ -0,0 +1,48 @@
+// Copyright 2017 David Ackroyd. All Rights Reserved.
+// See LICENSE for licensing terms.
+
+package grpc_recovery
+
+import (
+ "golang.org/x/net/context"
+ "google.golang.org/grpc"
+ "google.golang.org/grpc/codes"
+)
+
+// RecoveryHandlerFunc is a function that recovers from the panic `p` by returning an `error`.
+type RecoveryHandlerFunc func(p interface{}) (err error)
+
+// UnaryServerInterceptor returns a new unary server interceptor for panic recovery.
+func UnaryServerInterceptor(opts ...Option) grpc.UnaryServerInterceptor {
+ o := evaluateOptions(opts)
+ return func(ctx context.Context, req interface{}, info *grpc.UnaryServerInfo, handler grpc.UnaryHandler) (_ interface{}, err error) {
+ defer func() {
+ if r := recover(); r != nil {
+ err = recoverFrom(r, o.recoveryHandlerFunc)
+ }
+ }()
+
+ return handler(ctx, req)
+ }
+}
+
+// StreamServerInterceptor returns a new streaming server interceptor for panic recovery.
+func StreamServerInterceptor(opts ...Option) grpc.StreamServerInterceptor {
+ o := evaluateOptions(opts)
+ return func(srv interface{}, stream grpc.ServerStream, info *grpc.StreamServerInfo, handler grpc.StreamHandler) (err error) {
+ defer func() {
+ if r := recover(); r != nil {
+ err = recoverFrom(r, o.recoveryHandlerFunc)
+ }
+ }()
+
+ return handler(srv, stream)
+ }
+}
+
+func recoverFrom(p interface{}, r RecoveryHandlerFunc) error {
+ if r == nil {
+ return grpc.Errorf(codes.Internal, "%s", p)
+ }
+ return r(p)
+}
diff --git a/vendor/github.com/grpc-ecosystem/go-grpc-middleware/recovery/options.go b/vendor/github.com/grpc-ecosystem/go-grpc-middleware/recovery/options.go
new file mode 100644
index 00000000..e482d7a5
--- /dev/null
+++ b/vendor/github.com/grpc-ecosystem/go-grpc-middleware/recovery/options.go
@@ -0,0 +1,32 @@
+// Copyright 2017 David Ackroyd. All Rights Reserved.
+// See LICENSE for licensing terms.
+
+package grpc_recovery
+
+var (
+ defaultOptions = &options{
+ recoveryHandlerFunc: nil,
+ }
+)
+
+type options struct {
+ recoveryHandlerFunc RecoveryHandlerFunc
+}
+
+func evaluateOptions(opts []Option) *options {
+ optCopy := &options{}
+ *optCopy = *defaultOptions
+ for _, o := range opts {
+ o(optCopy)
+ }
+ return optCopy
+}
+
+type Option func(*options)
+
+// WithRecoveryHandler customizes the function for recovering from a panic.
+func WithRecoveryHandler(f RecoveryHandlerFunc) Option {
+ return func(o *options) {
+ o.recoveryHandlerFunc = f
+ }
+}
diff --git a/vendor/github.com/grpc-ecosystem/go-grpc-middleware/tags/DOC.md b/vendor/github.com/grpc-ecosystem/go-grpc-middleware/tags/DOC.md
new file mode 100644
index 00000000..b954b1f9
--- /dev/null
+++ b/vendor/github.com/grpc-ecosystem/go-grpc-middleware/tags/DOC.md
@@ -0,0 +1,188 @@
+# grpc_ctxtags
+`import "github.com/grpc-ecosystem/go-grpc-middleware/tags"`
+
+* [Overview](#pkg-overview)
+* [Imported Packages](#pkg-imports)
+* [Index](#pkg-index)
+* [Examples](#pkg-examples)
+
+## <a name="pkg-overview">Overview</a>
+`grpc_ctxtags` adds a Tag object to the context that can be used by other middleware to add context about a request.
+
+### Request Context Tags
+Tags describe information about the request, and can be set and used by other middleware, or handlers. Tags are used
+for logging and tracing of requests. Tags are populated both upwards, *and* downwards in the interceptor-handler stack.
+
+You can automatically extract tags (in `grpc.request.<field_name>`) from request payloads.
+
+For unary and server-streaming methods, pass in the `WithFieldExtractor` option. For client-streams and bidirectional-streams, you can
+use `WithFieldExtractorForInitialReq` which will extract the tags from the first message passed from client to server.
+Note the tags will not be modified for subsequent requests, so this option only makes sense when the initial message
+establishes the meta-data for the stream.
+
+If a user doesn't use the interceptors that initialize the `Tags` object, all operations following from an `Extract(ctx)`
+will be no-ops. This is to ensure that code doesn't panic if the interceptors weren't used.
+
+Tags fields are typed, and shallow and should follow the OpenTracing semantics convention:
+<a href="https://github.com/opentracing/specification/blob/master/semantic_conventions.md">https://github.com/opentracing/specification/blob/master/semantic_conventions.md</a>
+
+#### Example:
+
+<details>
+<summary>Click to expand code.</summary>
+
+```go
+opts := []grpc_ctxtags.Option{
+ grpc_ctxtags.WithFieldExtractorForInitialReq(grpc_ctxtags.TagBasedRequestFieldExtractor("log_fields")),
+}
+_ = grpc.NewServer(
+ grpc.StreamInterceptor(grpc_ctxtags.StreamServerInterceptor(opts...)),
+ grpc.UnaryInterceptor(grpc_ctxtags.UnaryServerInterceptor(opts...)),
+)
+```
+
+</details>
+
+#### Example:
+
+<details>
+<summary>Click to expand code.</summary>
+
+```go
+opts := []grpc_ctxtags.Option{
+ grpc_ctxtags.WithFieldExtractor(grpc_ctxtags.TagBasedRequestFieldExtractor("log_fields")),
+}
+_ = grpc.NewServer(
+ grpc.StreamInterceptor(grpc_ctxtags.StreamServerInterceptor(opts...)),
+ grpc.UnaryInterceptor(grpc_ctxtags.UnaryServerInterceptor(opts...)),
+)
+```
+
+</details>
+
+## <a name="pkg-imports">Imported Packages</a>
+
+- [github.com/grpc-ecosystem/go-grpc-middleware](./..)
+- [golang.org/x/net/context](https://godoc.org/golang.org/x/net/context)
+- [google.golang.org/grpc](https://godoc.org/google.golang.org/grpc)
+- [google.golang.org/grpc/peer](https://godoc.org/google.golang.org/grpc/peer)
+
+## <a name="pkg-index">Index</a>
+* [func CodeGenRequestFieldExtractor(fullMethod string, req interface{}) map[string]interface{}](#CodeGenRequestFieldExtractor)
+* [func StreamServerInterceptor(opts ...Option) grpc.StreamServerInterceptor](#StreamServerInterceptor)
+* [func UnaryServerInterceptor(opts ...Option) grpc.UnaryServerInterceptor](#UnaryServerInterceptor)
+* [type Option](#Option)
+ * [func WithFieldExtractor(f RequestFieldExtractorFunc) Option](#WithFieldExtractor)
+ * [func WithFieldExtractorForInitialReq(f RequestFieldExtractorFunc) Option](#WithFieldExtractorForInitialReq)
+* [type RequestFieldExtractorFunc](#RequestFieldExtractorFunc)
+ * [func TagBasedRequestFieldExtractor(tagName string) RequestFieldExtractorFunc](#TagBasedRequestFieldExtractor)
+* [type Tags](#Tags)
+ * [func Extract(ctx context.Context) \*Tags](#Extract)
+ * [func (t \*Tags) Has(key string) bool](#Tags.Has)
+ * [func (t \*Tags) Set(key string, value interface{}) \*Tags](#Tags.Set)
+ * [func (t \*Tags) Values() map[string]interface{}](#Tags.Values)
+
+#### <a name="pkg-examples">Examples</a>
+* [Package (InitialisationWithOptions)](#example__initialisationWithOptions)
+* [Package (Initialization)](#example__initialization)
+
+#### <a name="pkg-files">Package files</a>
+[context.go](./context.go) [doc.go](./doc.go) [fieldextractor.go](./fieldextractor.go) [interceptors.go](./interceptors.go) [options.go](./options.go)
+
+## <a name="CodeGenRequestFieldExtractor">func</a> [CodeGenRequestFieldExtractor](./fieldextractor.go#L23)
+``` go
+func CodeGenRequestFieldExtractor(fullMethod string, req interface{}) map[string]interface{}
+```
+CodeGenRequestFieldExtractor is a function that relies on code-generated functions that export log fields from requests.
+These are usually coming from a protoc-plugin that generates additional information based on custom field options.
+
+## <a name="StreamServerInterceptor">func</a> [StreamServerInterceptor](./interceptors.go#L26)
+``` go
+func StreamServerInterceptor(opts ...Option) grpc.StreamServerInterceptor
+```
+StreamServerInterceptor returns a new streaming server interceptor that sets the values for request tags.
+
+## <a name="UnaryServerInterceptor">func</a> [UnaryServerInterceptor](./interceptors.go#L14)
+``` go
+func UnaryServerInterceptor(opts ...Option) grpc.UnaryServerInterceptor
+```
+UnaryServerInterceptor returns a new unary server interceptors that sets the values for request tags.
+
+## <a name="Option">type</a> [Option](./options.go#L26)
+``` go
+type Option func(*options)
+```
+
+### <a name="WithFieldExtractor">func</a> [WithFieldExtractor](./options.go#L30)
+``` go
+func WithFieldExtractor(f RequestFieldExtractorFunc) Option
+```
+WithFieldExtractor customizes the function for extracting log fields from protobuf messages, for
+unary and server-streamed methods only.
+
+### <a name="WithFieldExtractorForInitialReq">func</a> [WithFieldExtractorForInitialReq](./options.go#L39)
+``` go
+func WithFieldExtractorForInitialReq(f RequestFieldExtractorFunc) Option
+```
+WithFieldExtractorForInitialReq customizes the function for extracting log fields from protobuf messages,
+for all unary and streaming methods. For client-streams and bidirectional-streams, the tags will be
+extracted from the first message from the client.
+
+## <a name="RequestFieldExtractorFunc">type</a> [RequestFieldExtractorFunc](./fieldextractor.go#L13)
+``` go
+type RequestFieldExtractorFunc func(fullMethod string, req interface{}) map[string]interface{}
+```
+RequestFieldExtractorFunc is a user-provided function that extracts field information from a gRPC request.
+It is called from tags middleware on arrival of unary request or a server-stream request.
+Keys and values will be added to the context tags of the request. If there are no fields, you should return a nil.
+
+### <a name="TagBasedRequestFieldExtractor">func</a> [TagBasedRequestFieldExtractor](./fieldextractor.go#L43)
+``` go
+func TagBasedRequestFieldExtractor(tagName string) RequestFieldExtractorFunc
+```
+TagBasedRequestFieldExtractor is a function that relies on Go struct tags to export log fields from requests.
+These are usualy coming from a protoc-plugin, such as Gogo protobuf.
+
+ message Metadata {
+ repeated string tags = 1 [ (gogoproto.moretags) = "log_field:\"meta_tags\"" ];
+ }
+
+The tagName is configurable using the tagName variable. Here it would be "log_field".
+
+## <a name="Tags">type</a> [Tags](./context.go#L17-L19)
+``` go
+type Tags struct {
+ // contains filtered or unexported fields
+}
+```
+Tags is the struct used for storing request tags between Context calls.
+This object is *not* thread safe, and should be handled only in the context of the request.
+
+### <a name="Extract">func</a> [Extract](./context.go#L41)
+``` go
+func Extract(ctx context.Context) *Tags
+```
+Extracts returns a pre-existing Tags object in the Context.
+If the context wasn't set in a tag interceptor, a no-op Tag storage is returned that will *not* be propagated in context.
+
+### <a name="Tags.Has">func</a> (\*Tags) [Has](./context.go#L28)
+``` go
+func (t *Tags) Has(key string) bool
+```
+Has checks if the given key exists.
+
+### <a name="Tags.Set">func</a> (\*Tags) [Set](./context.go#L22)
+``` go
+func (t *Tags) Set(key string, value interface{}) *Tags
+```
+Set sets the given key in the metadata tags.
+
+### <a name="Tags.Values">func</a> (\*Tags) [Values](./context.go#L35)
+``` go
+func (t *Tags) Values() map[string]interface{}
+```
+Values returns a map of key to values.
+Do not modify the underlying map, please use Set instead.
+
+- - -
+Generated by [godoc2ghmd](https://github.com/GandalfUK/godoc2ghmd) \ No newline at end of file
diff --git a/vendor/github.com/grpc-ecosystem/go-grpc-middleware/tags/README.md b/vendor/github.com/grpc-ecosystem/go-grpc-middleware/tags/README.md
new file mode 100644
index 00000000..b954b1f9
--- /dev/null
+++ b/vendor/github.com/grpc-ecosystem/go-grpc-middleware/tags/README.md
@@ -0,0 +1,188 @@
+# grpc_ctxtags
+`import "github.com/grpc-ecosystem/go-grpc-middleware/tags"`
+
+* [Overview](#pkg-overview)
+* [Imported Packages](#pkg-imports)
+* [Index](#pkg-index)
+* [Examples](#pkg-examples)
+
+## <a name="pkg-overview">Overview</a>
+`grpc_ctxtags` adds a Tag object to the context that can be used by other middleware to add context about a request.
+
+### Request Context Tags
+Tags describe information about the request, and can be set and used by other middleware, or handlers. Tags are used
+for logging and tracing of requests. Tags are populated both upwards, *and* downwards in the interceptor-handler stack.
+
+You can automatically extract tags (in `grpc.request.<field_name>`) from request payloads.
+
+For unary and server-streaming methods, pass in the `WithFieldExtractor` option. For client-streams and bidirectional-streams, you can
+use `WithFieldExtractorForInitialReq` which will extract the tags from the first message passed from client to server.
+Note the tags will not be modified for subsequent requests, so this option only makes sense when the initial message
+establishes the meta-data for the stream.
+
+If a user doesn't use the interceptors that initialize the `Tags` object, all operations following from an `Extract(ctx)`
+will be no-ops. This is to ensure that code doesn't panic if the interceptors weren't used.
+
+Tags fields are typed, and shallow and should follow the OpenTracing semantics convention:
+<a href="https://github.com/opentracing/specification/blob/master/semantic_conventions.md">https://github.com/opentracing/specification/blob/master/semantic_conventions.md</a>
+
+#### Example:
+
+<details>
+<summary>Click to expand code.</summary>
+
+```go
+opts := []grpc_ctxtags.Option{
+ grpc_ctxtags.WithFieldExtractorForInitialReq(grpc_ctxtags.TagBasedRequestFieldExtractor("log_fields")),
+}
+_ = grpc.NewServer(
+ grpc.StreamInterceptor(grpc_ctxtags.StreamServerInterceptor(opts...)),
+ grpc.UnaryInterceptor(grpc_ctxtags.UnaryServerInterceptor(opts...)),
+)
+```
+
+</details>
+
+#### Example:
+
+<details>
+<summary>Click to expand code.</summary>
+
+```go
+opts := []grpc_ctxtags.Option{
+ grpc_ctxtags.WithFieldExtractor(grpc_ctxtags.TagBasedRequestFieldExtractor("log_fields")),
+}
+_ = grpc.NewServer(
+ grpc.StreamInterceptor(grpc_ctxtags.StreamServerInterceptor(opts...)),
+ grpc.UnaryInterceptor(grpc_ctxtags.UnaryServerInterceptor(opts...)),
+)
+```
+
+</details>
+
+## <a name="pkg-imports">Imported Packages</a>
+
+- [github.com/grpc-ecosystem/go-grpc-middleware](./..)
+- [golang.org/x/net/context](https://godoc.org/golang.org/x/net/context)
+- [google.golang.org/grpc](https://godoc.org/google.golang.org/grpc)
+- [google.golang.org/grpc/peer](https://godoc.org/google.golang.org/grpc/peer)
+
+## <a name="pkg-index">Index</a>
+* [func CodeGenRequestFieldExtractor(fullMethod string, req interface{}) map[string]interface{}](#CodeGenRequestFieldExtractor)
+* [func StreamServerInterceptor(opts ...Option) grpc.StreamServerInterceptor](#StreamServerInterceptor)
+* [func UnaryServerInterceptor(opts ...Option) grpc.UnaryServerInterceptor](#UnaryServerInterceptor)
+* [type Option](#Option)
+ * [func WithFieldExtractor(f RequestFieldExtractorFunc) Option](#WithFieldExtractor)
+ * [func WithFieldExtractorForInitialReq(f RequestFieldExtractorFunc) Option](#WithFieldExtractorForInitialReq)
+* [type RequestFieldExtractorFunc](#RequestFieldExtractorFunc)
+ * [func TagBasedRequestFieldExtractor(tagName string) RequestFieldExtractorFunc](#TagBasedRequestFieldExtractor)
+* [type Tags](#Tags)
+ * [func Extract(ctx context.Context) \*Tags](#Extract)
+ * [func (t \*Tags) Has(key string) bool](#Tags.Has)
+ * [func (t \*Tags) Set(key string, value interface{}) \*Tags](#Tags.Set)
+ * [func (t \*Tags) Values() map[string]interface{}](#Tags.Values)
+
+#### <a name="pkg-examples">Examples</a>
+* [Package (InitialisationWithOptions)](#example__initialisationWithOptions)
+* [Package (Initialization)](#example__initialization)
+
+#### <a name="pkg-files">Package files</a>
+[context.go](./context.go) [doc.go](./doc.go) [fieldextractor.go](./fieldextractor.go) [interceptors.go](./interceptors.go) [options.go](./options.go)
+
+## <a name="CodeGenRequestFieldExtractor">func</a> [CodeGenRequestFieldExtractor](./fieldextractor.go#L23)
+``` go
+func CodeGenRequestFieldExtractor(fullMethod string, req interface{}) map[string]interface{}
+```
+CodeGenRequestFieldExtractor is a function that relies on code-generated functions that export log fields from requests.
+These are usually coming from a protoc-plugin that generates additional information based on custom field options.
+
+## <a name="StreamServerInterceptor">func</a> [StreamServerInterceptor](./interceptors.go#L26)
+``` go
+func StreamServerInterceptor(opts ...Option) grpc.StreamServerInterceptor
+```
+StreamServerInterceptor returns a new streaming server interceptor that sets the values for request tags.
+
+## <a name="UnaryServerInterceptor">func</a> [UnaryServerInterceptor](./interceptors.go#L14)
+``` go
+func UnaryServerInterceptor(opts ...Option) grpc.UnaryServerInterceptor
+```
+UnaryServerInterceptor returns a new unary server interceptors that sets the values for request tags.
+
+## <a name="Option">type</a> [Option](./options.go#L26)
+``` go
+type Option func(*options)
+```
+
+### <a name="WithFieldExtractor">func</a> [WithFieldExtractor](./options.go#L30)
+``` go
+func WithFieldExtractor(f RequestFieldExtractorFunc) Option
+```
+WithFieldExtractor customizes the function for extracting log fields from protobuf messages, for
+unary and server-streamed methods only.
+
+### <a name="WithFieldExtractorForInitialReq">func</a> [WithFieldExtractorForInitialReq](./options.go#L39)
+``` go
+func WithFieldExtractorForInitialReq(f RequestFieldExtractorFunc) Option
+```
+WithFieldExtractorForInitialReq customizes the function for extracting log fields from protobuf messages,
+for all unary and streaming methods. For client-streams and bidirectional-streams, the tags will be
+extracted from the first message from the client.
+
+## <a name="RequestFieldExtractorFunc">type</a> [RequestFieldExtractorFunc](./fieldextractor.go#L13)
+``` go
+type RequestFieldExtractorFunc func(fullMethod string, req interface{}) map[string]interface{}
+```
+RequestFieldExtractorFunc is a user-provided function that extracts field information from a gRPC request.
+It is called from tags middleware on arrival of unary request or a server-stream request.
+Keys and values will be added to the context tags of the request. If there are no fields, you should return a nil.
+
+### <a name="TagBasedRequestFieldExtractor">func</a> [TagBasedRequestFieldExtractor](./fieldextractor.go#L43)
+``` go
+func TagBasedRequestFieldExtractor(tagName string) RequestFieldExtractorFunc
+```
+TagBasedRequestFieldExtractor is a function that relies on Go struct tags to export log fields from requests.
+These are usualy coming from a protoc-plugin, such as Gogo protobuf.
+
+ message Metadata {
+ repeated string tags = 1 [ (gogoproto.moretags) = "log_field:\"meta_tags\"" ];
+ }
+
+The tagName is configurable using the tagName variable. Here it would be "log_field".
+
+## <a name="Tags">type</a> [Tags](./context.go#L17-L19)
+``` go
+type Tags struct {
+ // contains filtered or unexported fields
+}
+```
+Tags is the struct used for storing request tags between Context calls.
+This object is *not* thread safe, and should be handled only in the context of the request.
+
+### <a name="Extract">func</a> [Extract](./context.go#L41)
+``` go
+func Extract(ctx context.Context) *Tags
+```
+Extracts returns a pre-existing Tags object in the Context.
+If the context wasn't set in a tag interceptor, a no-op Tag storage is returned that will *not* be propagated in context.
+
+### <a name="Tags.Has">func</a> (\*Tags) [Has](./context.go#L28)
+``` go
+func (t *Tags) Has(key string) bool
+```
+Has checks if the given key exists.
+
+### <a name="Tags.Set">func</a> (\*Tags) [Set](./context.go#L22)
+``` go
+func (t *Tags) Set(key string, value interface{}) *Tags
+```
+Set sets the given key in the metadata tags.
+
+### <a name="Tags.Values">func</a> (\*Tags) [Values](./context.go#L35)
+``` go
+func (t *Tags) Values() map[string]interface{}
+```
+Values returns a map of key to values.
+Do not modify the underlying map, please use Set instead.
+
+- - -
+Generated by [godoc2ghmd](https://github.com/GandalfUK/godoc2ghmd) \ No newline at end of file
diff --git a/vendor/github.com/grpc-ecosystem/go-grpc-middleware/tags/context.go b/vendor/github.com/grpc-ecosystem/go-grpc-middleware/tags/context.go
new file mode 100644
index 00000000..583025ce
--- /dev/null
+++ b/vendor/github.com/grpc-ecosystem/go-grpc-middleware/tags/context.go
@@ -0,0 +1,78 @@
+package grpc_ctxtags
+
+import (
+ "context"
+)
+
+type ctxMarker struct{}
+
+var (
+ // ctxMarkerKey is the Context value marker used by *all* logging middleware.
+ // The logging middleware object must interf
+ ctxMarkerKey = &ctxMarker{}
+ // NoopTags is a trivial, minimum overhead implementation of Tags for which all operations are no-ops.
+ NoopTags = &noopTags{}
+)
+
+// Tags is the interface used for storing request tags between Context calls.
+// The default implementation is *not* thread safe, and should be handled only in the context of the request.
+type Tags interface {
+ // Set sets the given key in the metadata tags.
+ Set(key string, value interface{}) Tags
+ // Has checks if the given key exists.
+ Has(key string) bool
+ // Values returns a map of key to values.
+ // Do not modify the underlying map, please use Set instead.
+ Values() map[string]interface{}
+}
+
+type mapTags struct {
+ values map[string]interface{}
+}
+
+func (t *mapTags) Set(key string, value interface{}) Tags {
+ t.values[key] = value
+ return t
+}
+
+func (t *mapTags) Has(key string) bool {
+ _, ok := t.values[key]
+ return ok
+}
+
+func (t *mapTags) Values() map[string]interface{} {
+ return t.values
+}
+
+type noopTags struct{}
+
+func (t *noopTags) Set(key string, value interface{}) Tags {
+ return t
+}
+
+func (t *noopTags) Has(key string) bool {
+ return false
+}
+
+func (t *noopTags) Values() map[string]interface{} {
+ return nil
+}
+
+// Extracts returns a pre-existing Tags object in the Context.
+// If the context wasn't set in a tag interceptor, a no-op Tag storage is returned that will *not* be propagated in context.
+func Extract(ctx context.Context) Tags {
+ t, ok := ctx.Value(ctxMarkerKey).(Tags)
+ if !ok {
+ return NoopTags
+ }
+
+ return t
+}
+
+func setInContext(ctx context.Context, tags Tags) context.Context {
+ return context.WithValue(ctx, ctxMarkerKey, tags)
+}
+
+func newTags() Tags {
+ return &mapTags{values: make(map[string]interface{})}
+}
diff --git a/vendor/github.com/grpc-ecosystem/go-grpc-middleware/tags/doc.go b/vendor/github.com/grpc-ecosystem/go-grpc-middleware/tags/doc.go
new file mode 100644
index 00000000..960638d0
--- /dev/null
+++ b/vendor/github.com/grpc-ecosystem/go-grpc-middleware/tags/doc.go
@@ -0,0 +1,22 @@
+/*
+`grpc_ctxtags` adds a Tag object to the context that can be used by other middleware to add context about a request.
+
+Request Context Tags
+
+Tags describe information about the request, and can be set and used by other middleware, or handlers. Tags are used
+for logging and tracing of requests. Tags are populated both upwards, *and* downwards in the interceptor-handler stack.
+
+You can automatically extract tags (in `grpc.request.<field_name>`) from request payloads.
+
+For unary and server-streaming methods, pass in the `WithFieldExtractor` option. For client-streams and bidirectional-streams, you can
+use `WithFieldExtractorForInitialReq` which will extract the tags from the first message passed from client to server.
+Note the tags will not be modified for subsequent requests, so this option only makes sense when the initial message
+establishes the meta-data for the stream.
+
+If a user doesn't use the interceptors that initialize the `Tags` object, all operations following from an `Extract(ctx)`
+will be no-ops. This is to ensure that code doesn't panic if the interceptors weren't used.
+
+Tags fields are typed, and shallow and should follow the OpenTracing semantics convention:
+https://github.com/opentracing/specification/blob/master/semantic_conventions.md
+*/
+package grpc_ctxtags
diff --git a/vendor/github.com/grpc-ecosystem/go-grpc-middleware/tags/fieldextractor.go b/vendor/github.com/grpc-ecosystem/go-grpc-middleware/tags/fieldextractor.go
new file mode 100644
index 00000000..d87ee438
--- /dev/null
+++ b/vendor/github.com/grpc-ecosystem/go-grpc-middleware/tags/fieldextractor.go
@@ -0,0 +1,85 @@
+// Copyright 2017 Michal Witkowski. All Rights Reserved.
+// See LICENSE for licensing terms.
+
+package grpc_ctxtags
+
+import (
+ "reflect"
+)
+
+// RequestFieldExtractorFunc is a user-provided function that extracts field information from a gRPC request.
+// It is called from tags middleware on arrival of unary request or a server-stream request.
+// Keys and values will be added to the context tags of the request. If there are no fields, you should return a nil.
+type RequestFieldExtractorFunc func(fullMethod string, req interface{}) map[string]interface{}
+
+type requestFieldsExtractor interface {
+ // ExtractRequestFields is a method declared on a Protobuf message that extracts fields from the interface.
+ // The values from the extracted fields should be set in the appendToMap, in order to avoid allocations.
+ ExtractRequestFields(appendToMap map[string]interface{})
+}
+
+// CodeGenRequestFieldExtractor is a function that relies on code-generated functions that export log fields from requests.
+// These are usually coming from a protoc-plugin that generates additional information based on custom field options.
+func CodeGenRequestFieldExtractor(fullMethod string, req interface{}) map[string]interface{} {
+ if ext, ok := req.(requestFieldsExtractor); ok {
+ retMap := make(map[string]interface{})
+ ext.ExtractRequestFields(retMap)
+ if len(retMap) == 0 {
+ return nil
+ }
+ return retMap
+ }
+ return nil
+}
+
+// TagBasedRequestFieldExtractor is a function that relies on Go struct tags to export log fields from requests.
+// These are usualy coming from a protoc-plugin, such as Gogo protobuf.
+//
+// message Metadata {
+// repeated string tags = 1 [ (gogoproto.moretags) = "log_field:\"meta_tags\"" ];
+// }
+//
+// The tagName is configurable using the tagName variable. Here it would be "log_field".
+func TagBasedRequestFieldExtractor(tagName string) RequestFieldExtractorFunc {
+ return func(fullMethod string, req interface{}) map[string]interface{} {
+ retMap := make(map[string]interface{})
+ reflectMessageTags(req, retMap, tagName)
+ if len(retMap) == 0 {
+ return nil
+ }
+ return retMap
+ }
+}
+
+func reflectMessageTags(msg interface{}, existingMap map[string]interface{}, tagName string) {
+ v := reflect.ValueOf(msg)
+ // Only deal with pointers to structs.
+ if v.Kind() != reflect.Ptr || v.Elem().Kind() != reflect.Struct {
+ return
+ }
+ // Deref the pointer get to the struct.
+ v = v.Elem()
+ t := v.Type()
+ for i := 0; i < v.NumField(); i++ {
+ field := v.Field(i)
+ kind := field.Kind()
+ // Only recurse down direct pointers, which should only be to nested structs.
+ if kind == reflect.Ptr {
+ reflectMessageTags(field.Interface(), existingMap, tagName)
+ }
+ // In case of arrays/splices (repeated fields) go down to the concrete type.
+ if kind == reflect.Array || kind == reflect.Slice {
+ if field.Len() == 0 {
+ continue
+ }
+ kind = field.Index(0).Kind()
+ }
+ // Only be interested in
+ if (kind >= reflect.Bool && kind <= reflect.Float64) || kind == reflect.String {
+ if tag := t.Field(i).Tag.Get(tagName); tag != "" {
+ existingMap[tag] = field.Interface()
+ }
+ }
+ }
+ return
+}
diff --git a/vendor/github.com/grpc-ecosystem/go-grpc-middleware/tags/interceptors.go b/vendor/github.com/grpc-ecosystem/go-grpc-middleware/tags/interceptors.go
new file mode 100644
index 00000000..038afd26
--- /dev/null
+++ b/vendor/github.com/grpc-ecosystem/go-grpc-middleware/tags/interceptors.go
@@ -0,0 +1,83 @@
+// Copyright 2017 Michal Witkowski. All Rights Reserved.
+// See LICENSE for licensing terms.
+
+package grpc_ctxtags
+
+import (
+ "github.com/grpc-ecosystem/go-grpc-middleware"
+ "golang.org/x/net/context"
+ "google.golang.org/grpc"
+ "google.golang.org/grpc/peer"
+)
+
+// UnaryServerInterceptor returns a new unary server interceptors that sets the values for request tags.
+func UnaryServerInterceptor(opts ...Option) grpc.UnaryServerInterceptor {
+ o := evaluateOptions(opts)
+ return func(ctx context.Context, req interface{}, info *grpc.UnaryServerInfo, handler grpc.UnaryHandler) (interface{}, error) {
+ newCtx := newTagsForCtx(ctx)
+ if o.requestFieldsFunc != nil {
+ setRequestFieldTags(newCtx, o.requestFieldsFunc, info.FullMethod, req)
+ }
+ return handler(newCtx, req)
+ }
+}
+
+// StreamServerInterceptor returns a new streaming server interceptor that sets the values for request tags.
+func StreamServerInterceptor(opts ...Option) grpc.StreamServerInterceptor {
+ o := evaluateOptions(opts)
+ return func(srv interface{}, stream grpc.ServerStream, info *grpc.StreamServerInfo, handler grpc.StreamHandler) error {
+ newCtx := newTagsForCtx(stream.Context())
+ if o.requestFieldsFunc == nil {
+ // Short-circuit, don't do the expensive bit of allocating a wrappedStream.
+ wrappedStream := grpc_middleware.WrapServerStream(stream)
+ wrappedStream.WrappedContext = newCtx
+ return handler(srv, wrappedStream)
+ }
+ wrapped := &wrappedStream{stream, info, o, newCtx, true}
+ err := handler(srv, wrapped)
+ return err
+ }
+}
+
+// wrappedStream is a thin wrapper around grpc.ServerStream that allows modifying context and extracts log fields from the initial message.
+type wrappedStream struct {
+ grpc.ServerStream
+ info *grpc.StreamServerInfo
+ opts *options
+ // WrappedContext is the wrapper's own Context. You can assign it.
+ WrappedContext context.Context
+ initial bool
+}
+
+// Context returns the wrapper's WrappedContext, overwriting the nested grpc.ServerStream.Context()
+func (w *wrappedStream) Context() context.Context {
+ return w.WrappedContext
+}
+
+func (w *wrappedStream) RecvMsg(m interface{}) error {
+ err := w.ServerStream.RecvMsg(m)
+ // We only do log fields extraction on the single-request of a server-side stream.
+ if !w.info.IsClientStream || w.opts.requestFieldsFromInitial && w.initial {
+ w.initial = false
+
+ setRequestFieldTags(w.Context(), w.opts.requestFieldsFunc, w.info.FullMethod, m)
+ }
+ return err
+}
+
+func newTagsForCtx(ctx context.Context) context.Context {
+ t := newTags()
+ if peer, ok := peer.FromContext(ctx); ok {
+ t.Set("peer.address", peer.Addr.String())
+ }
+ return setInContext(ctx, t)
+}
+
+func setRequestFieldTags(ctx context.Context, f RequestFieldExtractorFunc, fullMethodName string, req interface{}) {
+ if valMap := f(fullMethodName, req); valMap != nil {
+ t := Extract(ctx)
+ for k, v := range valMap {
+ t.Set("grpc.request."+k, v)
+ }
+ }
+}
diff --git a/vendor/github.com/grpc-ecosystem/go-grpc-middleware/tags/logrus/context.go b/vendor/github.com/grpc-ecosystem/go-grpc-middleware/tags/logrus/context.go
new file mode 100644
index 00000000..2596be89
--- /dev/null
+++ b/vendor/github.com/grpc-ecosystem/go-grpc-middleware/tags/logrus/context.go
@@ -0,0 +1,25 @@
+package ctx_logrus
+
+import (
+ "github.com/grpc-ecosystem/go-grpc-middleware/logging/logrus/ctxlogrus"
+ "github.com/sirupsen/logrus"
+ "golang.org/x/net/context"
+)
+
+// AddFields adds logrus fields to the logger.
+// Deprecated: should use the ctxlogrus.Extract instead
+func AddFields(ctx context.Context, fields logrus.Fields) {
+ ctxlogrus.AddFields(ctx, fields)
+}
+
+// Extract takes the call-scoped logrus.Entry from grpc_logrus middleware.
+// Deprecated: should use the ctxlogrus.Extract instead
+func Extract(ctx context.Context) *logrus.Entry {
+ return ctxlogrus.Extract(ctx)
+}
+
+// ToContext adds the logrus.Entry to the context for extraction later.
+// Depricated: should use ctxlogrus.ToContext instead
+func ToContext(ctx context.Context, entry *logrus.Entry) context.Context {
+ return ctxlogrus.ToContext(ctx, entry)
+}
diff --git a/vendor/github.com/grpc-ecosystem/go-grpc-middleware/tags/options.go b/vendor/github.com/grpc-ecosystem/go-grpc-middleware/tags/options.go
new file mode 100644
index 00000000..952775f8
--- /dev/null
+++ b/vendor/github.com/grpc-ecosystem/go-grpc-middleware/tags/options.go
@@ -0,0 +1,44 @@
+// Copyright 2017 Michal Witkowski. All Rights Reserved.
+// See LICENSE for licensing terms.
+
+package grpc_ctxtags
+
+var (
+ defaultOptions = &options{
+ requestFieldsFunc: nil,
+ }
+)
+
+type options struct {
+ requestFieldsFunc RequestFieldExtractorFunc
+ requestFieldsFromInitial bool
+}
+
+func evaluateOptions(opts []Option) *options {
+ optCopy := &options{}
+ *optCopy = *defaultOptions
+ for _, o := range opts {
+ o(optCopy)
+ }
+ return optCopy
+}
+
+type Option func(*options)
+
+// WithFieldExtractor customizes the function for extracting log fields from protobuf messages, for
+// unary and server-streamed methods only.
+func WithFieldExtractor(f RequestFieldExtractorFunc) Option {
+ return func(o *options) {
+ o.requestFieldsFunc = f
+ }
+}
+
+// WithFieldExtractorForInitialReq customizes the function for extracting log fields from protobuf messages,
+// for all unary and streaming methods. For client-streams and bidirectional-streams, the tags will be
+// extracted from the first message from the client.
+func WithFieldExtractorForInitialReq(f RequestFieldExtractorFunc) Option {
+ return func(o *options) {
+ o.requestFieldsFunc = f
+ o.requestFieldsFromInitial = true
+ }
+}
diff --git a/vendor/github.com/grpc-ecosystem/go-grpc-middleware/util/metautils/DOC.md b/vendor/github.com/grpc-ecosystem/go-grpc-middleware/util/metautils/DOC.md
new file mode 100644
index 00000000..a02cde31
--- /dev/null
+++ b/vendor/github.com/grpc-ecosystem/go-grpc-middleware/util/metautils/DOC.md
@@ -0,0 +1,114 @@
+# metautils
+`import "github.com/grpc-ecosystem/go-grpc-middleware/util/metautils"`
+
+* [Overview](#pkg-overview)
+* [Imported Packages](#pkg-imports)
+* [Index](#pkg-index)
+
+## <a name="pkg-overview">Overview</a>
+
+## <a name="pkg-imports">Imported Packages</a>
+
+- [golang.org/x/net/context](https://godoc.org/golang.org/x/net/context)
+- [google.golang.org/grpc/metadata](https://godoc.org/google.golang.org/grpc/metadata)
+
+## <a name="pkg-index">Index</a>
+* [type NiceMD](#NiceMD)
+ * [func ExtractIncoming(ctx context.Context) NiceMD](#ExtractIncoming)
+ * [func ExtractOutgoing(ctx context.Context) NiceMD](#ExtractOutgoing)
+ * [func (m NiceMD) Add(key string, value string) NiceMD](#NiceMD.Add)
+ * [func (m NiceMD) Clone(copiedKeys ...string) NiceMD](#NiceMD.Clone)
+ * [func (m NiceMD) Del(key string) NiceMD](#NiceMD.Del)
+ * [func (m NiceMD) Get(key string) string](#NiceMD.Get)
+ * [func (m NiceMD) Set(key string, value string) NiceMD](#NiceMD.Set)
+ * [func (m NiceMD) ToIncoming(ctx context.Context) context.Context](#NiceMD.ToIncoming)
+ * [func (m NiceMD) ToOutgoing(ctx context.Context) context.Context](#NiceMD.ToOutgoing)
+
+#### <a name="pkg-files">Package files</a>
+[doc.go](./doc.go) [nicemd.go](./nicemd.go) [single_key.go](./single_key.go)
+
+## <a name="NiceMD">type</a> [NiceMD](./nicemd.go#L14)
+``` go
+type NiceMD metadata.MD
+```
+NiceMD is a convenience wrapper definiting extra functions on the metadata.
+
+### <a name="ExtractIncoming">func</a> [ExtractIncoming](./nicemd.go#L20)
+``` go
+func ExtractIncoming(ctx context.Context) NiceMD
+```
+ExtractIncoming extracts an inbound metadata from the server-side context.
+
+This function always returns a NiceMD wrapper of the metadata.MD, in case the context doesn't have metadata it returns
+a new empty NiceMD.
+
+### <a name="ExtractOutgoing">func</a> [ExtractOutgoing](./nicemd.go#L32)
+``` go
+func ExtractOutgoing(ctx context.Context) NiceMD
+```
+ExtractOutgoing extracts an outbound metadata from the client-side context.
+
+This function always returns a NiceMD wrapper of the metadata.MD, in case the context doesn't have metadata it returns
+a new empty NiceMD.
+
+### <a name="NiceMD.Add">func</a> (NiceMD) [Add](./nicemd.go#L122)
+``` go
+func (m NiceMD) Add(key string, value string) NiceMD
+```
+Add retrieves a single value from the metadata.
+
+It works analogously to http.Header.Add, as it appends to any existing values associated with key.
+
+The function is binary-key safe.
+
+### <a name="NiceMD.Clone">func</a> (NiceMD) [Clone](./nicemd.go#L44)
+``` go
+func (m NiceMD) Clone(copiedKeys ...string) NiceMD
+```
+Clone performs a *deep* copy of the metadata.MD.
+
+You can specify the lower-case copiedKeys to only copy certain whitelisted keys. If no keys are explicitly whitelisted
+all keys get copied.
+
+### <a name="NiceMD.Del">func</a> (NiceMD) [Del](./nicemd.go#L100)
+``` go
+func (m NiceMD) Del(key string) NiceMD
+```
+
+### <a name="NiceMD.Get">func</a> (NiceMD) [Get](./nicemd.go#L85)
+``` go
+func (m NiceMD) Get(key string) string
+```
+Get retrieves a single value from the metadata.
+
+It works analogously to http.Header.Get, returning the first value if there are many set. If the value is not set,
+an empty string is returned.
+
+The function is binary-key safe.
+
+### <a name="NiceMD.Set">func</a> (NiceMD) [Set](./nicemd.go#L111)
+``` go
+func (m NiceMD) Set(key string, value string) NiceMD
+```
+Set sets the given value in a metadata.
+
+It works analogously to http.Header.Set, overwriting all previous metadata values.
+
+The function is binary-key safe.
+
+### <a name="NiceMD.ToIncoming">func</a> (NiceMD) [ToIncoming](./nicemd.go#L75)
+``` go
+func (m NiceMD) ToIncoming(ctx context.Context) context.Context
+```
+ToIncoming sets the given NiceMD as a server-side context for dispatching.
+
+This is mostly useful in ServerInterceptors..
+
+### <a name="NiceMD.ToOutgoing">func</a> (NiceMD) [ToOutgoing](./nicemd.go#L68)
+``` go
+func (m NiceMD) ToOutgoing(ctx context.Context) context.Context
+```
+ToOutgoing sets the given NiceMD as a client-side context for dispatching.
+
+- - -
+Generated by [godoc2ghmd](https://github.com/GandalfUK/godoc2ghmd) \ No newline at end of file
diff --git a/vendor/github.com/grpc-ecosystem/go-grpc-middleware/util/metautils/README.md b/vendor/github.com/grpc-ecosystem/go-grpc-middleware/util/metautils/README.md
new file mode 100644
index 00000000..a02cde31
--- /dev/null
+++ b/vendor/github.com/grpc-ecosystem/go-grpc-middleware/util/metautils/README.md
@@ -0,0 +1,114 @@
+# metautils
+`import "github.com/grpc-ecosystem/go-grpc-middleware/util/metautils"`
+
+* [Overview](#pkg-overview)
+* [Imported Packages](#pkg-imports)
+* [Index](#pkg-index)
+
+## <a name="pkg-overview">Overview</a>
+
+## <a name="pkg-imports">Imported Packages</a>
+
+- [golang.org/x/net/context](https://godoc.org/golang.org/x/net/context)
+- [google.golang.org/grpc/metadata](https://godoc.org/google.golang.org/grpc/metadata)
+
+## <a name="pkg-index">Index</a>
+* [type NiceMD](#NiceMD)
+ * [func ExtractIncoming(ctx context.Context) NiceMD](#ExtractIncoming)
+ * [func ExtractOutgoing(ctx context.Context) NiceMD](#ExtractOutgoing)
+ * [func (m NiceMD) Add(key string, value string) NiceMD](#NiceMD.Add)
+ * [func (m NiceMD) Clone(copiedKeys ...string) NiceMD](#NiceMD.Clone)
+ * [func (m NiceMD) Del(key string) NiceMD](#NiceMD.Del)
+ * [func (m NiceMD) Get(key string) string](#NiceMD.Get)
+ * [func (m NiceMD) Set(key string, value string) NiceMD](#NiceMD.Set)
+ * [func (m NiceMD) ToIncoming(ctx context.Context) context.Context](#NiceMD.ToIncoming)
+ * [func (m NiceMD) ToOutgoing(ctx context.Context) context.Context](#NiceMD.ToOutgoing)
+
+#### <a name="pkg-files">Package files</a>
+[doc.go](./doc.go) [nicemd.go](./nicemd.go) [single_key.go](./single_key.go)
+
+## <a name="NiceMD">type</a> [NiceMD](./nicemd.go#L14)
+``` go
+type NiceMD metadata.MD
+```
+NiceMD is a convenience wrapper definiting extra functions on the metadata.
+
+### <a name="ExtractIncoming">func</a> [ExtractIncoming](./nicemd.go#L20)
+``` go
+func ExtractIncoming(ctx context.Context) NiceMD
+```
+ExtractIncoming extracts an inbound metadata from the server-side context.
+
+This function always returns a NiceMD wrapper of the metadata.MD, in case the context doesn't have metadata it returns
+a new empty NiceMD.
+
+### <a name="ExtractOutgoing">func</a> [ExtractOutgoing](./nicemd.go#L32)
+``` go
+func ExtractOutgoing(ctx context.Context) NiceMD
+```
+ExtractOutgoing extracts an outbound metadata from the client-side context.
+
+This function always returns a NiceMD wrapper of the metadata.MD, in case the context doesn't have metadata it returns
+a new empty NiceMD.
+
+### <a name="NiceMD.Add">func</a> (NiceMD) [Add](./nicemd.go#L122)
+``` go
+func (m NiceMD) Add(key string, value string) NiceMD
+```
+Add retrieves a single value from the metadata.
+
+It works analogously to http.Header.Add, as it appends to any existing values associated with key.
+
+The function is binary-key safe.
+
+### <a name="NiceMD.Clone">func</a> (NiceMD) [Clone](./nicemd.go#L44)
+``` go
+func (m NiceMD) Clone(copiedKeys ...string) NiceMD
+```
+Clone performs a *deep* copy of the metadata.MD.
+
+You can specify the lower-case copiedKeys to only copy certain whitelisted keys. If no keys are explicitly whitelisted
+all keys get copied.
+
+### <a name="NiceMD.Del">func</a> (NiceMD) [Del](./nicemd.go#L100)
+``` go
+func (m NiceMD) Del(key string) NiceMD
+```
+
+### <a name="NiceMD.Get">func</a> (NiceMD) [Get](./nicemd.go#L85)
+``` go
+func (m NiceMD) Get(key string) string
+```
+Get retrieves a single value from the metadata.
+
+It works analogously to http.Header.Get, returning the first value if there are many set. If the value is not set,
+an empty string is returned.
+
+The function is binary-key safe.
+
+### <a name="NiceMD.Set">func</a> (NiceMD) [Set](./nicemd.go#L111)
+``` go
+func (m NiceMD) Set(key string, value string) NiceMD
+```
+Set sets the given value in a metadata.
+
+It works analogously to http.Header.Set, overwriting all previous metadata values.
+
+The function is binary-key safe.
+
+### <a name="NiceMD.ToIncoming">func</a> (NiceMD) [ToIncoming](./nicemd.go#L75)
+``` go
+func (m NiceMD) ToIncoming(ctx context.Context) context.Context
+```
+ToIncoming sets the given NiceMD as a server-side context for dispatching.
+
+This is mostly useful in ServerInterceptors..
+
+### <a name="NiceMD.ToOutgoing">func</a> (NiceMD) [ToOutgoing](./nicemd.go#L68)
+``` go
+func (m NiceMD) ToOutgoing(ctx context.Context) context.Context
+```
+ToOutgoing sets the given NiceMD as a client-side context for dispatching.
+
+- - -
+Generated by [godoc2ghmd](https://github.com/GandalfUK/godoc2ghmd) \ No newline at end of file
diff --git a/vendor/github.com/grpc-ecosystem/go-grpc-middleware/util/metautils/doc.go b/vendor/github.com/grpc-ecosystem/go-grpc-middleware/util/metautils/doc.go
new file mode 100644
index 00000000..1ed9bb49
--- /dev/null
+++ b/vendor/github.com/grpc-ecosystem/go-grpc-middleware/util/metautils/doc.go
@@ -0,0 +1,19 @@
+// Copyright 2016 Michal Witkowski. All Rights Reserved.
+// See LICENSE for licensing terms.
+
+/*
+Package `metautils` provides convenience functions for dealing with gRPC metadata.MD objects inside
+Context handlers.
+
+While the upstream grpc-go package contains decent functionality (see https://github.com/grpc/grpc-go/blob/master/Documentation/grpc-metadata.md)
+they are hard to use.
+
+The majority of functions center around the NiceMD, which is a convenience wrapper around metadata.MD. For example
+the following code allows you to easily extract incoming metadata (server handler) and put it into a new client context
+metadata.
+
+ nmd := metautils.ExtractIncoming(serverCtx).Clone(":authorization", ":custom")
+ clientCtx := nmd.Set("x-client-header", "2").Set("x-another", "3").ToOutgoing(ctx)
+*/
+
+package metautils
diff --git a/vendor/github.com/grpc-ecosystem/go-grpc-middleware/util/metautils/nicemd.go b/vendor/github.com/grpc-ecosystem/go-grpc-middleware/util/metautils/nicemd.go
new file mode 100644
index 00000000..a277bee3
--- /dev/null
+++ b/vendor/github.com/grpc-ecosystem/go-grpc-middleware/util/metautils/nicemd.go
@@ -0,0 +1,126 @@
+// Copyright 2016 Michal Witkowski. All Rights Reserved.
+// See LICENSE for licensing terms.
+
+package metautils
+
+import (
+ "strings"
+
+ "golang.org/x/net/context"
+ "google.golang.org/grpc/metadata"
+)
+
+// NiceMD is a convenience wrapper definiting extra functions on the metadata.
+type NiceMD metadata.MD
+
+// ExtractIncoming extracts an inbound metadata from the server-side context.
+//
+// This function always returns a NiceMD wrapper of the metadata.MD, in case the context doesn't have metadata it returns
+// a new empty NiceMD.
+func ExtractIncoming(ctx context.Context) NiceMD {
+ md, ok := metadata.FromIncomingContext(ctx)
+ if !ok {
+ return NiceMD(metadata.Pairs())
+ }
+ return NiceMD(md)
+}
+
+// ExtractOutgoing extracts an outbound metadata from the client-side context.
+//
+// This function always returns a NiceMD wrapper of the metadata.MD, in case the context doesn't have metadata it returns
+// a new empty NiceMD.
+func ExtractOutgoing(ctx context.Context) NiceMD {
+ md, ok := metadata.FromOutgoingContext(ctx)
+ if !ok {
+ return NiceMD(metadata.Pairs())
+ }
+ return NiceMD(md)
+}
+
+// Clone performs a *deep* copy of the metadata.MD.
+//
+// You can specify the lower-case copiedKeys to only copy certain whitelisted keys. If no keys are explicitly whitelisted
+// all keys get copied.
+func (m NiceMD) Clone(copiedKeys ...string) NiceMD {
+ newMd := NiceMD(metadata.Pairs())
+ for k, vv := range m {
+ found := false
+ if len(copiedKeys) == 0 {
+ found = true
+ } else {
+ for _, allowedKey := range copiedKeys {
+ if strings.ToLower(allowedKey) == strings.ToLower(k) {
+ found = true
+ break
+ }
+ }
+ }
+ if !found {
+ continue
+ }
+ newMd[k] = make([]string, len(vv))
+ copy(newMd[k], vv)
+ }
+ return NiceMD(newMd)
+}
+
+// ToOutgoing sets the given NiceMD as a client-side context for dispatching.
+func (m NiceMD) ToOutgoing(ctx context.Context) context.Context {
+ return metadata.NewOutgoingContext(ctx, metadata.MD(m))
+}
+
+// ToIncoming sets the given NiceMD as a server-side context for dispatching.
+//
+// This is mostly useful in ServerInterceptors..
+func (m NiceMD) ToIncoming(ctx context.Context) context.Context {
+ return metadata.NewIncomingContext(ctx, metadata.MD(m))
+}
+
+// Get retrieves a single value from the metadata.
+//
+// It works analogously to http.Header.Get, returning the first value if there are many set. If the value is not set,
+// an empty string is returned.
+//
+// The function is binary-key safe.
+func (m NiceMD) Get(key string) string {
+ k, _ := encodeKeyValue(key, "")
+ vv, ok := m[k]
+ if !ok {
+ return ""
+ }
+ return vv[0]
+}
+
+// Del retrieves a single value from the metadata.
+//
+// It works analogously to http.Header.Del, deleting all values if they exist.
+//
+// The function is binary-key safe.
+
+func (m NiceMD) Del(key string) NiceMD {
+ k, _ := encodeKeyValue(key, "")
+ delete(m, k)
+ return m
+}
+
+// Set sets the given value in a metadata.
+//
+// It works analogously to http.Header.Set, overwriting all previous metadata values.
+//
+// The function is binary-key safe.
+func (m NiceMD) Set(key string, value string) NiceMD {
+ k, v := encodeKeyValue(key, value)
+ m[k] = []string{v}
+ return m
+}
+
+// Add retrieves a single value from the metadata.
+//
+// It works analogously to http.Header.Add, as it appends to any existing values associated with key.
+//
+// The function is binary-key safe.
+func (m NiceMD) Add(key string, value string) NiceMD {
+ k, v := encodeKeyValue(key, value)
+ m[k] = append(m[k], v)
+ return m
+}
diff --git a/vendor/github.com/grpc-ecosystem/go-grpc-middleware/util/metautils/single_key.go b/vendor/github.com/grpc-ecosystem/go-grpc-middleware/util/metautils/single_key.go
new file mode 100644
index 00000000..8a538716
--- /dev/null
+++ b/vendor/github.com/grpc-ecosystem/go-grpc-middleware/util/metautils/single_key.go
@@ -0,0 +1,22 @@
+// Copyright 2016 Michal Witkowski. All Rights Reserved.
+// See LICENSE for licensing terms.
+
+package metautils
+
+import (
+ "encoding/base64"
+ "strings"
+)
+
+const (
+ binHdrSuffix = "-bin"
+)
+
+func encodeKeyValue(k, v string) (string, string) {
+ k = strings.ToLower(k)
+ if strings.HasSuffix(k, binHdrSuffix) {
+ val := base64.StdEncoding.EncodeToString([]byte(v))
+ v = string(val)
+ }
+ return k, v
+}
diff --git a/vendor/github.com/grpc-ecosystem/go-grpc-middleware/wrappers.go b/vendor/github.com/grpc-ecosystem/go-grpc-middleware/wrappers.go
new file mode 100644
index 00000000..597b8624
--- /dev/null
+++ b/vendor/github.com/grpc-ecosystem/go-grpc-middleware/wrappers.go
@@ -0,0 +1,29 @@
+// Copyright 2016 Michal Witkowski. All Rights Reserved.
+// See LICENSE for licensing terms.
+
+package grpc_middleware
+
+import (
+ "golang.org/x/net/context"
+ "google.golang.org/grpc"
+)
+
+// WrappedServerStream is a thin wrapper around grpc.ServerStream that allows modifying context.
+type WrappedServerStream struct {
+ grpc.ServerStream
+ // WrappedContext is the wrapper's own Context. You can assign it.
+ WrappedContext context.Context
+}
+
+// Context returns the wrapper's WrappedContext, overwriting the nested grpc.ServerStream.Context()
+func (w *WrappedServerStream) Context() context.Context {
+ return w.WrappedContext
+}
+
+// WrapServerStream returns a ServerStream that has the ability to overwrite context.
+func WrapServerStream(stream grpc.ServerStream) *WrappedServerStream {
+ if existing, ok := stream.(*WrappedServerStream); ok {
+ return existing
+ }
+ return &WrappedServerStream{ServerStream: stream, WrappedContext: stream.Context()}
+}
diff --git a/vendor/github.com/grpc-ecosystem/go-grpc-prometheus/LICENSE b/vendor/github.com/grpc-ecosystem/go-grpc-prometheus/LICENSE
new file mode 100644
index 00000000..b2b06503
--- /dev/null
+++ b/vendor/github.com/grpc-ecosystem/go-grpc-prometheus/LICENSE
@@ -0,0 +1,201 @@
+ Apache License
+ Version 2.0, January 2004
+ http://www.apache.org/licenses/
+
+ TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION
+
+ 1. Definitions.
+
+ "License" shall mean the terms and conditions for use, reproduction,
+ and distribution as defined by Sections 1 through 9 of this document.
+
+ "Licensor" shall mean the copyright owner or entity authorized by
+ the copyright owner that is granting the License.
+
+ "Legal Entity" shall mean the union of the acting entity and all
+ other entities that control, are controlled by, or are under common
+ control with that entity. For the purposes of this definition,
+ "control" means (i) the power, direct or indirect, to cause the
+ direction or management of such entity, whether by contract or
+ otherwise, or (ii) ownership of fifty percent (50%) or more of the
+ outstanding shares, or (iii) beneficial ownership of such entity.
+
+ "You" (or "Your") shall mean an individual or Legal Entity
+ exercising permissions granted by this License.
+
+ "Source" form shall mean the preferred form for making modifications,
+ including but not limited to software source code, documentation
+ source, and configuration files.
+
+ "Object" form shall mean any form resulting from mechanical
+ transformation or translation of a Source form, including but
+ not limited to compiled object code, generated documentation,
+ and conversions to other media types.
+
+ "Work" shall mean the work of authorship, whether in Source or
+ Object form, made available under the License, as indicated by a
+ copyright notice that is included in or attached to the work
+ (an example is provided in the Appendix below).
+
+ "Derivative Works" shall mean any work, whether in Source or Object
+ form, that is based on (or derived from) the Work and for which the
+ editorial revisions, annotations, elaborations, or other modifications
+ represent, as a whole, an original work of authorship. For the purposes
+ of this License, Derivative Works shall not include works that remain
+ separable from, or merely link (or bind by name) to the interfaces of,
+ the Work and Derivative Works thereof.
+
+ "Contribution" shall mean any work of authorship, including
+ the original version of the Work and any modifications or additions
+ to that Work or Derivative Works thereof, that is intentionally
+ submitted to Licensor for inclusion in the Work by the copyright owner
+ or by an individual or Legal Entity authorized to submit on behalf of
+ the copyright owner. For the purposes of this definition, "submitted"
+ means any form of electronic, verbal, or written communication sent
+ to the Licensor or its representatives, including but not limited to
+ communication on electronic mailing lists, source code control systems,
+ and issue tracking systems that are managed by, or on behalf of, the
+ Licensor for the purpose of discussing and improving the Work, but
+ excluding communication that is conspicuously marked or otherwise
+ designated in writing by the copyright owner as "Not a Contribution."
+
+ "Contributor" shall mean Licensor and any individual or Legal Entity
+ on behalf of whom a Contribution has been received by Licensor and
+ subsequently incorporated within the Work.
+
+ 2. Grant of Copyright License. Subject to the terms and conditions of
+ this License, each Contributor hereby grants to You a perpetual,
+ worldwide, non-exclusive, no-charge, royalty-free, irrevocable
+ copyright license to reproduce, prepare Derivative Works of,
+ publicly display, publicly perform, sublicense, and distribute the
+ Work and such Derivative Works in Source or Object form.
+
+ 3. Grant of Patent License. Subject to the terms and conditions of
+ this License, each Contributor hereby grants to You a perpetual,
+ worldwide, non-exclusive, no-charge, royalty-free, irrevocable
+ (except as stated in this section) patent license to make, have made,
+ use, offer to sell, sell, import, and otherwise transfer the Work,
+ where such license applies only to those patent claims licensable
+ by such Contributor that are necessarily infringed by their
+ Contribution(s) alone or by combination of their Contribution(s)
+ with the Work to which such Contribution(s) was submitted. If You
+ institute patent litigation against any entity (including a
+ cross-claim or counterclaim in a lawsuit) alleging that the Work
+ or a Contribution incorporated within the Work constitutes direct
+ or contributory patent infringement, then any patent licenses
+ granted to You under this License for that Work shall terminate
+ as of the date such litigation is filed.
+
+ 4. Redistribution. You may reproduce and distribute copies of the
+ Work or Derivative Works thereof in any medium, with or without
+ modifications, and in Source or Object form, provided that You
+ meet the following conditions:
+
+ (a) You must give any other recipients of the Work or
+ Derivative Works a copy of this License; and
+
+ (b) You must cause any modified files to carry prominent notices
+ stating that You changed the files; and
+
+ (c) You must retain, in the Source form of any Derivative Works
+ that You distribute, all copyright, patent, trademark, and
+ attribution notices from the Source form of the Work,
+ excluding those notices that do not pertain to any part of
+ the Derivative Works; and
+
+ (d) If the Work includes a "NOTICE" text file as part of its
+ distribution, then any Derivative Works that You distribute must
+ include a readable copy of the attribution notices contained
+ within such NOTICE file, excluding those notices that do not
+ pertain to any part of the Derivative Works, in at least one
+ of the following places: within a NOTICE text file distributed
+ as part of the Derivative Works; within the Source form or
+ documentation, if provided along with the Derivative Works; or,
+ within a display generated by the Derivative Works, if and
+ wherever such third-party notices normally appear. The contents
+ of the NOTICE file are for informational purposes only and
+ do not modify the License. You may add Your own attribution
+ notices within Derivative Works that You distribute, alongside
+ or as an addendum to the NOTICE text from the Work, provided
+ that such additional attribution notices cannot be construed
+ as modifying the License.
+
+ You may add Your own copyright statement to Your modifications and
+ may provide additional or different license terms and conditions
+ for use, reproduction, or distribution of Your modifications, or
+ for any such Derivative Works as a whole, provided Your use,
+ reproduction, and distribution of the Work otherwise complies with
+ the conditions stated in this License.
+
+ 5. Submission of Contributions. Unless You explicitly state otherwise,
+ any Contribution intentionally submitted for inclusion in the Work
+ by You to the Licensor shall be under the terms and conditions of
+ this License, without any additional terms or conditions.
+ Notwithstanding the above, nothing herein shall supersede or modify
+ the terms of any separate license agreement you may have executed
+ with Licensor regarding such Contributions.
+
+ 6. Trademarks. This License does not grant permission to use the trade
+ names, trademarks, service marks, or product names of the Licensor,
+ except as required for reasonable and customary use in describing the
+ origin of the Work and reproducing the content of the NOTICE file.
+
+ 7. Disclaimer of Warranty. Unless required by applicable law or
+ agreed to in writing, Licensor provides the Work (and each
+ Contributor provides its Contributions) on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
+ implied, including, without limitation, any warranties or conditions
+ of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A
+ PARTICULAR PURPOSE. You are solely responsible for determining the
+ appropriateness of using or redistributing the Work and assume any
+ risks associated with Your exercise of permissions under this License.
+
+ 8. Limitation of Liability. In no event and under no legal theory,
+ whether in tort (including negligence), contract, or otherwise,
+ unless required by applicable law (such as deliberate and grossly
+ negligent acts) or agreed to in writing, shall any Contributor be
+ liable to You for damages, including any direct, indirect, special,
+ incidental, or consequential damages of any character arising as a
+ result of this License or out of the use or inability to use the
+ Work (including but not limited to damages for loss of goodwill,
+ work stoppage, computer failure or malfunction, or any and all
+ other commercial damages or losses), even if such Contributor
+ has been advised of the possibility of such damages.
+
+ 9. Accepting Warranty or Additional Liability. While redistributing
+ the Work or Derivative Works thereof, You may choose to offer,
+ and charge a fee for, acceptance of support, warranty, indemnity,
+ or other liability obligations and/or rights consistent with this
+ License. However, in accepting such obligations, You may act only
+ on Your own behalf and on Your sole responsibility, not on behalf
+ of any other Contributor, and only if You agree to indemnify,
+ defend, and hold each Contributor harmless for any liability
+ incurred by, or claims asserted against, such Contributor by reason
+ of your accepting any such warranty or additional liability.
+
+ END OF TERMS AND CONDITIONS
+
+ APPENDIX: How to apply the Apache License to your work.
+
+ To apply the Apache License to your work, attach the following
+ boilerplate notice, with the fields enclosed by brackets "[]"
+ replaced with your own identifying information. (Don't include
+ the brackets!) The text should be enclosed in the appropriate
+ comment syntax for the file format. We also recommend that a
+ file or class name and description of purpose be included on the
+ same "printed page" as the copyright notice for easier
+ identification within third-party archives.
+
+ Copyright [yyyy] [name of copyright owner]
+
+ Licensed under the Apache License, Version 2.0 (the "License");
+ you may not use this file except in compliance with the License.
+ You may obtain a copy of the License at
+
+ http://www.apache.org/licenses/LICENSE-2.0
+
+ Unless required by applicable law or agreed to in writing, software
+ distributed under the License is distributed on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ See the License for the specific language governing permissions and
+ limitations under the License. \ No newline at end of file
diff --git a/vendor/github.com/grpc-ecosystem/go-grpc-prometheus/README.md b/vendor/github.com/grpc-ecosystem/go-grpc-prometheus/README.md
new file mode 100644
index 00000000..0eaa0846
--- /dev/null
+++ b/vendor/github.com/grpc-ecosystem/go-grpc-prometheus/README.md
@@ -0,0 +1,247 @@
+# Go gRPC Interceptors for Prometheus monitoring
+
+[![Travis Build](https://travis-ci.org/grpc-ecosystem/go-grpc-prometheus.svg)](https://travis-ci.org/grpc-ecosystem/go-grpc-prometheus)
+[![Go Report Card](https://goreportcard.com/badge/github.com/grpc-ecosystem/go-grpc-prometheus)](http://goreportcard.com/report/grpc-ecosystem/go-grpc-prometheus)
+[![GoDoc](http://img.shields.io/badge/GoDoc-Reference-blue.svg)](https://godoc.org/github.com/grpc-ecosystem/go-grpc-prometheus)
+[![SourceGraph](https://sourcegraph.com/github.com/grpc-ecosystem/go-grpc-prometheus/-/badge.svg)](https://sourcegraph.com/github.com/grpc-ecosystem/go-grpc-prometheus/?badge)
+[![codecov](https://codecov.io/gh/grpc-ecosystem/go-grpc-prometheus/branch/master/graph/badge.svg)](https://codecov.io/gh/grpc-ecosystem/go-grpc-prometheus)
+[![Apache 2.0 License](https://img.shields.io/badge/License-Apache%202.0-blue.svg)](LICENSE)
+
+[Prometheus](https://prometheus.io/) monitoring for your [gRPC Go](https://github.com/grpc/grpc-go) servers and clients.
+
+A sister implementation for [gRPC Java](https://github.com/grpc/grpc-java) (same metrics, same semantics) is in [grpc-ecosystem/java-grpc-prometheus](https://github.com/grpc-ecosystem/java-grpc-prometheus).
+
+## Interceptors
+
+[gRPC Go](https://github.com/grpc/grpc-go) recently acquired support for Interceptors, i.e. middleware that is executed
+by a gRPC Server before the request is passed onto the user's application logic. It is a perfect way to implement
+common patterns: auth, logging and... monitoring.
+
+To use Interceptors in chains, please see [`go-grpc-middleware`](https://github.com/mwitkow/go-grpc-middleware).
+
+## Usage
+
+There are two types of interceptors: client-side and server-side. This package provides monitoring Interceptors for both.
+
+### Server-side
+
+```go
+import "github.com/grpc-ecosystem/go-grpc-prometheus"
+...
+ // Initialize your gRPC server's interceptor.
+ myServer := grpc.NewServer(
+ grpc.StreamInterceptor(grpc_prometheus.StreamServerInterceptor),
+ grpc.UnaryInterceptor(grpc_prometheus.UnaryServerInterceptor),
+ )
+ // Register your gRPC service implementations.
+ myservice.RegisterMyServiceServer(s.server, &myServiceImpl{})
+ // After all your registrations, make sure all of the Prometheus metrics are initialized.
+ grpc_prometheus.Register(myServer)
+ // Register Prometheus metrics handler.
+ http.Handle("/metrics", promhttp.Handler())
+...
+```
+
+### Client-side
+
+```go
+import "github.com/grpc-ecosystem/go-grpc-prometheus"
+...
+ clientConn, err = grpc.Dial(
+ address,
+ grpc.WithUnaryInterceptor(grpc_prometheus.UnaryClientInterceptor),
+ grpc.WithStreamInterceptor(grpc_prometheus.StreamClientInterceptor)
+ )
+ client = pb_testproto.NewTestServiceClient(clientConn)
+ resp, err := client.PingEmpty(s.ctx, &myservice.Request{Msg: "hello"})
+...
+```
+
+# Metrics
+
+## Labels
+
+All server-side metrics start with `grpc_server` as Prometheus subsystem name. All client-side metrics start with `grpc_client`. Both of them have mirror-concepts. Similarly all methods
+contain the same rich labels:
+
+ * `grpc_service` - the [gRPC service](http://www.grpc.io/docs/#defining-a-service) name, which is the combination of protobuf `package` and
+ the `grpc_service` section name. E.g. for `package = mwitkow.testproto` and
+ `service TestService` the label will be `grpc_service="mwitkow.testproto.TestService"`
+ * `grpc_method` - the name of the method called on the gRPC service. E.g.
+ `grpc_method="Ping"`
+ * `grpc_type` - the gRPC [type of request](http://www.grpc.io/docs/guides/concepts.html#rpc-life-cycle).
+ Differentiating between the two is important especially for latency measurements.
+
+ - `unary` is single request, single response RPC
+ - `client_stream` is a multi-request, single response RPC
+ - `server_stream` is a single request, multi-response RPC
+ - `bidi_stream` is a multi-request, multi-response RPC
+
+
+Additionally for completed RPCs, the following labels are used:
+
+ * `grpc_code` - the human-readable [gRPC status code](https://github.com/grpc/grpc-go/blob/master/codes/codes.go).
+ The list of all statuses is to long, but here are some common ones:
+
+ - `OK` - means the RPC was successful
+ - `IllegalArgument` - RPC contained bad values
+ - `Internal` - server-side error not disclosed to the clients
+
+## Counters
+
+The counters and their up to date documentation is in [server_reporter.go](server_reporter.go) and [client_reporter.go](client_reporter.go)
+the respective Prometheus handler (usually `/metrics`).
+
+For the purpose of this documentation we will only discuss `grpc_server` metrics. The `grpc_client` ones contain mirror concepts.
+
+For simplicity, let's assume we're tracking a single server-side RPC call of [`mwitkow.testproto.TestService`](examples/testproto/test.proto),
+calling the method `PingList`. The call succeeds and returns 20 messages in the stream.
+
+First, immediately after the server receives the call it will increment the
+`grpc_server_started_total` and start the handling time clock (if histograms are enabled).
+
+```jsoniq
+grpc_server_started_total{grpc_method="PingList",grpc_service="mwitkow.testproto.TestService",grpc_type="server_stream"} 1
+```
+
+Then the user logic gets invoked. It receives one message from the client containing the request
+(it's a `server_stream`):
+
+```jsoniq
+grpc_server_msg_received_total{grpc_method="PingList",grpc_service="mwitkow.testproto.TestService",grpc_type="server_stream"} 1
+```
+
+The user logic may return an error, or send multiple messages back to the client. In this case, on
+each of the 20 messages sent back, a counter will be incremented:
+
+```jsoniq
+grpc_server_msg_sent_total{grpc_method="PingList",grpc_service="mwitkow.testproto.TestService",grpc_type="server_stream"} 20
+```
+
+After the call completes, it's status (`OK` or other [gRPC status code](https://github.com/grpc/grpc-go/blob/master/codes/codes.go))
+and the relevant call labels increment the `grpc_server_handled_total` counter.
+
+```jsoniq
+grpc_server_handled_total{grpc_code="OK",grpc_method="PingList",grpc_service="mwitkow.testproto.TestService",grpc_type="server_stream"} 1
+```
+
+## Histograms
+
+[Prometheus histograms](https://prometheus.io/docs/concepts/metric_types/#histogram) are a great way
+to measure latency distributions of your RPCs. However, since it is bad practice to have metrics
+of [high cardinality](https://prometheus.io/docs/practices/instrumentation/#do-not-overuse-labels)
+the latency monitoring metrics are disabled by default. To enable them please call the following
+in your server initialization code:
+
+```jsoniq
+grpc_prometheus.EnableHandlingTimeHistogram()
+```
+
+After the call completes, its handling time will be recorded in a [Prometheus histogram](https://prometheus.io/docs/concepts/metric_types/#histogram)
+variable `grpc_server_handling_seconds`. The histogram variable contains three sub-metrics:
+
+ * `grpc_server_handling_seconds_count` - the count of all completed RPCs by status and method
+ * `grpc_server_handling_seconds_sum` - cumulative time of RPCs by status and method, useful for
+ calculating average handling times
+ * `grpc_server_handling_seconds_bucket` - contains the counts of RPCs by status and method in respective
+ handling-time buckets. These buckets can be used by Prometheus to estimate SLAs (see [here](https://prometheus.io/docs/practices/histograms/))
+
+The counter values will look as follows:
+
+```jsoniq
+grpc_server_handling_seconds_bucket{grpc_code="OK",grpc_method="PingList",grpc_service="mwitkow.testproto.TestService",grpc_type="server_stream",le="0.005"} 1
+grpc_server_handling_seconds_bucket{grpc_code="OK",grpc_method="PingList",grpc_service="mwitkow.testproto.TestService",grpc_type="server_stream",le="0.01"} 1
+grpc_server_handling_seconds_bucket{grpc_code="OK",grpc_method="PingList",grpc_service="mwitkow.testproto.TestService",grpc_type="server_stream",le="0.025"} 1
+grpc_server_handling_seconds_bucket{grpc_code="OK",grpc_method="PingList",grpc_service="mwitkow.testproto.TestService",grpc_type="server_stream",le="0.05"} 1
+grpc_server_handling_seconds_bucket{grpc_code="OK",grpc_method="PingList",grpc_service="mwitkow.testproto.TestService",grpc_type="server_stream",le="0.1"} 1
+grpc_server_handling_seconds_bucket{grpc_code="OK",grpc_method="PingList",grpc_service="mwitkow.testproto.TestService",grpc_type="server_stream",le="0.25"} 1
+grpc_server_handling_seconds_bucket{grpc_code="OK",grpc_method="PingList",grpc_service="mwitkow.testproto.TestService",grpc_type="server_stream",le="0.5"} 1
+grpc_server_handling_seconds_bucket{grpc_code="OK",grpc_method="PingList",grpc_service="mwitkow.testproto.TestService",grpc_type="server_stream",le="1"} 1
+grpc_server_handling_seconds_bucket{grpc_code="OK",grpc_method="PingList",grpc_service="mwitkow.testproto.TestService",grpc_type="server_stream",le="2.5"} 1
+grpc_server_handling_seconds_bucket{grpc_code="OK",grpc_method="PingList",grpc_service="mwitkow.testproto.TestService",grpc_type="server_stream",le="5"} 1
+grpc_server_handling_seconds_bucket{grpc_code="OK",grpc_method="PingList",grpc_service="mwitkow.testproto.TestService",grpc_type="server_stream",le="10"} 1
+grpc_server_handling_seconds_bucket{grpc_code="OK",grpc_method="PingList",grpc_service="mwitkow.testproto.TestService",grpc_type="server_stream",le="+Inf"} 1
+grpc_server_handling_seconds_sum{grpc_code="OK",grpc_method="PingList",grpc_service="mwitkow.testproto.TestService",grpc_type="server_stream"} 0.0003866430000000001
+grpc_server_handling_seconds_count{grpc_code="OK",grpc_method="PingList",grpc_service="mwitkow.testproto.TestService",grpc_type="server_stream"} 1
+```
+
+
+## Useful query examples
+
+Prometheus philosophy is to provide raw metrics to the monitoring system, and
+let the aggregations be handled there. The verbosity of above metrics make it possible to have that
+flexibility. Here's a couple of useful monitoring queries:
+
+
+### request inbound rate
+```jsoniq
+sum(rate(grpc_server_started_total{job="foo"}[1m])) by (grpc_service)
+```
+For `job="foo"` (common label to differentiate between Prometheus monitoring targets), calculate the
+rate of requests per second (1 minute window) for each gRPC `grpc_service` that the job has. Please note
+how the `grpc_method` is being omitted here: all methods of a given gRPC service will be summed together.
+
+### unary request error rate
+```jsoniq
+sum(rate(grpc_server_handled_total{job="foo",grpc_type="unary",grpc_code!="OK"}[1m])) by (grpc_service)
+```
+For `job="foo"`, calculate the per-`grpc_service` rate of `unary` (1:1) RPCs that failed, i.e. the
+ones that didn't finish with `OK` code.
+
+### unary request error percentage
+```jsoniq
+sum(rate(grpc_server_handled_total{job="foo",grpc_type="unary",grpc_code!="OK"}[1m])) by (grpc_service)
+ /
+sum(rate(grpc_server_started_total{job="foo",grpc_type="unary"}[1m])) by (grpc_service)
+ * 100.0
+```
+For `job="foo"`, calculate the percentage of failed requests by service. It's easy to notice that
+this is a combination of the two above examples. This is an example of a query you would like to
+[alert on](https://prometheus.io/docs/alerting/rules/) in your system for SLA violations, e.g.
+"no more than 1% requests should fail".
+
+### average response stream size
+```jsoniq
+sum(rate(grpc_server_msg_sent_total{job="foo",grpc_type="server_stream"}[10m])) by (grpc_service)
+ /
+sum(rate(grpc_server_started_total{job="foo",grpc_type="server_stream"}[10m])) by (grpc_service)
+```
+For `job="foo"` what is the `grpc_service`-wide `10m` average of messages returned for all `
+server_stream` RPCs. This allows you to track the stream sizes returned by your system, e.g. allows
+you to track when clients started to send "wide" queries that ret
+Note the divisor is the number of started RPCs, in order to account for in-flight requests.
+
+### 99%-tile latency of unary requests
+```jsoniq
+histogram_quantile(0.99,
+ sum(rate(grpc_server_handling_seconds_bucket{job="foo",grpc_type="unary"}[5m])) by (grpc_service,le)
+)
+```
+For `job="foo"`, returns an 99%-tile [quantile estimation](https://prometheus.io/docs/practices/histograms/#quantiles)
+of the handling time of RPCs per service. Please note the `5m` rate, this means that the quantile
+estimation will take samples in a rolling `5m` window. When combined with other quantiles
+(e.g. 50%, 90%), this query gives you tremendous insight into the responsiveness of your system
+(e.g. impact of caching).
+
+### percentage of slow unary queries (>250ms)
+```jsoniq
+100.0 - (
+sum(rate(grpc_server_handling_seconds_bucket{job="foo",grpc_type="unary",le="0.25"}[5m])) by (grpc_service)
+ /
+sum(rate(grpc_server_handling_seconds_count{job="foo",grpc_type="unary"}[5m])) by (grpc_service)
+) * 100.0
+```
+For `job="foo"` calculate the by-`grpc_service` fraction of slow requests that took longer than `0.25`
+seconds. This query is relatively complex, since the Prometheus aggregations use `le` (less or equal)
+buckets, meaning that counting "fast" requests fractions is easier. However, simple maths helps.
+This is an example of a query you would like to alert on in your system for SLA violations,
+e.g. "less than 1% of requests are slower than 250ms".
+
+
+## Status
+
+This code has been used since August 2015 as the basis for monitoring of *production* gRPC micro services at [Improbable](https://improbable.io).
+
+## License
+
+`go-grpc-prometheus` is released under the Apache 2.0 license. See the [LICENSE](LICENSE) file for details.
diff --git a/vendor/github.com/grpc-ecosystem/go-grpc-prometheus/client.go b/vendor/github.com/grpc-ecosystem/go-grpc-prometheus/client.go
new file mode 100644
index 00000000..751a4c72
--- /dev/null
+++ b/vendor/github.com/grpc-ecosystem/go-grpc-prometheus/client.go
@@ -0,0 +1,39 @@
+// Copyright 2016 Michal Witkowski. All Rights Reserved.
+// See LICENSE for licensing terms.
+
+// gRPC Prometheus monitoring interceptors for client-side gRPC.
+
+package grpc_prometheus
+
+import (
+ prom "github.com/prometheus/client_golang/prometheus"
+)
+
+var (
+ // DefaultClientMetrics is the default instance of ClientMetrics. It is
+ // intended to be used in conjunction the default Prometheus metrics
+ // registry.
+ DefaultClientMetrics = NewClientMetrics()
+
+ // UnaryClientInterceptor is a gRPC client-side interceptor that provides Prometheus monitoring for Unary RPCs.
+ UnaryClientInterceptor = DefaultClientMetrics.UnaryClientInterceptor()
+
+ // StreamClientInterceptor is a gRPC client-side interceptor that provides Prometheus monitoring for Streaming RPCs.
+ StreamClientInterceptor = DefaultClientMetrics.StreamClientInterceptor()
+)
+
+func init() {
+ prom.MustRegister(DefaultClientMetrics.clientStartedCounter)
+ prom.MustRegister(DefaultClientMetrics.clientHandledCounter)
+ prom.MustRegister(DefaultClientMetrics.clientStreamMsgReceived)
+ prom.MustRegister(DefaultClientMetrics.clientStreamMsgSent)
+}
+
+// EnableClientHandlingTimeHistogram turns on recording of handling time of
+// RPCs. Histogram metrics can be very expensive for Prometheus to retain and
+// query. This function acts on the DefaultClientMetrics variable and the
+// default Prometheus metrics registry.
+func EnableClientHandlingTimeHistogram(opts ...HistogramOption) {
+ DefaultClientMetrics.EnableClientHandlingTimeHistogram(opts...)
+ prom.Register(DefaultClientMetrics.clientHandledHistogram)
+}
diff --git a/vendor/github.com/grpc-ecosystem/go-grpc-prometheus/client_metrics.go b/vendor/github.com/grpc-ecosystem/go-grpc-prometheus/client_metrics.go
new file mode 100644
index 00000000..ba1a703f
--- /dev/null
+++ b/vendor/github.com/grpc-ecosystem/go-grpc-prometheus/client_metrics.go
@@ -0,0 +1,166 @@
+package grpc_prometheus
+
+import (
+ "io"
+
+ prom "github.com/prometheus/client_golang/prometheus"
+ "golang.org/x/net/context"
+ "google.golang.org/grpc"
+ "google.golang.org/grpc/codes"
+)
+
+// ClientMetrics represents a collection of metrics to be registered on a
+// Prometheus metrics registry for a gRPC client.
+type ClientMetrics struct {
+ clientStartedCounter *prom.CounterVec
+ clientHandledCounter *prom.CounterVec
+ clientStreamMsgReceived *prom.CounterVec
+ clientStreamMsgSent *prom.CounterVec
+ clientHandledHistogramEnabled bool
+ clientHandledHistogramOpts prom.HistogramOpts
+ clientHandledHistogram *prom.HistogramVec
+}
+
+// NewClientMetrics returns a ClientMetrics object. Use a new instance of
+// ClientMetrics when not using the default Prometheus metrics registry, for
+// example when wanting to control which metrics are added to a registry as
+// opposed to automatically adding metrics via init functions.
+func NewClientMetrics(counterOpts ...CounterOption) *ClientMetrics {
+ opts := counterOptions(counterOpts)
+ return &ClientMetrics{
+ clientStartedCounter: prom.NewCounterVec(
+ opts.apply(prom.CounterOpts{
+ Name: "grpc_client_started_total",
+ Help: "Total number of RPCs started on the client.",
+ }), []string{"grpc_type", "grpc_service", "grpc_method"}),
+
+ clientHandledCounter: prom.NewCounterVec(
+ opts.apply(prom.CounterOpts{
+ Name: "grpc_client_handled_total",
+ Help: "Total number of RPCs completed by the client, regardless of success or failure.",
+ }), []string{"grpc_type", "grpc_service", "grpc_method", "grpc_code"}),
+
+ clientStreamMsgReceived: prom.NewCounterVec(
+ opts.apply(prom.CounterOpts{
+ Name: "grpc_client_msg_received_total",
+ Help: "Total number of RPC stream messages received by the client.",
+ }), []string{"grpc_type", "grpc_service", "grpc_method"}),
+
+ clientStreamMsgSent: prom.NewCounterVec(
+ opts.apply(prom.CounterOpts{
+ Name: "grpc_client_msg_sent_total",
+ Help: "Total number of gRPC stream messages sent by the client.",
+ }), []string{"grpc_type", "grpc_service", "grpc_method"}),
+
+ clientHandledHistogramEnabled: false,
+ clientHandledHistogramOpts: prom.HistogramOpts{
+ Name: "grpc_client_handling_seconds",
+ Help: "Histogram of response latency (seconds) of the gRPC until it is finished by the application.",
+ Buckets: prom.DefBuckets,
+ },
+ clientHandledHistogram: nil,
+ }
+}
+
+// Describe sends the super-set of all possible descriptors of metrics
+// collected by this Collector to the provided channel and returns once
+// the last descriptor has been sent.
+func (m *ClientMetrics) Describe(ch chan<- *prom.Desc) {
+ m.clientStartedCounter.Describe(ch)
+ m.clientHandledCounter.Describe(ch)
+ m.clientStreamMsgReceived.Describe(ch)
+ m.clientStreamMsgSent.Describe(ch)
+ if m.clientHandledHistogramEnabled {
+ m.clientHandledHistogram.Describe(ch)
+ }
+}
+
+// Collect is called by the Prometheus registry when collecting
+// metrics. The implementation sends each collected metric via the
+// provided channel and returns once the last metric has been sent.
+func (m *ClientMetrics) Collect(ch chan<- prom.Metric) {
+ m.clientStartedCounter.Collect(ch)
+ m.clientHandledCounter.Collect(ch)
+ m.clientStreamMsgReceived.Collect(ch)
+ m.clientStreamMsgSent.Collect(ch)
+ if m.clientHandledHistogramEnabled {
+ m.clientHandledHistogram.Collect(ch)
+ }
+}
+
+// EnableClientHandlingTimeHistogram turns on recording of handling time of RPCs.
+// Histogram metrics can be very expensive for Prometheus to retain and query.
+func (m *ClientMetrics) EnableClientHandlingTimeHistogram(opts ...HistogramOption) {
+ for _, o := range opts {
+ o(&m.clientHandledHistogramOpts)
+ }
+ if !m.clientHandledHistogramEnabled {
+ m.clientHandledHistogram = prom.NewHistogramVec(
+ m.clientHandledHistogramOpts,
+ []string{"grpc_type", "grpc_service", "grpc_method"},
+ )
+ }
+ m.clientHandledHistogramEnabled = true
+}
+
+// UnaryClientInterceptor is a gRPC client-side interceptor that provides Prometheus monitoring for Unary RPCs.
+func (m *ClientMetrics) UnaryClientInterceptor() func(ctx context.Context, method string, req, reply interface{}, cc *grpc.ClientConn, invoker grpc.UnaryInvoker, opts ...grpc.CallOption) error {
+ return func(ctx context.Context, method string, req, reply interface{}, cc *grpc.ClientConn, invoker grpc.UnaryInvoker, opts ...grpc.CallOption) error {
+ monitor := newClientReporter(m, Unary, method)
+ monitor.SentMessage()
+ err := invoker(ctx, method, req, reply, cc, opts...)
+ if err != nil {
+ monitor.ReceivedMessage()
+ }
+ monitor.Handled(grpc.Code(err))
+ return err
+ }
+}
+
+// StreamServerInterceptor is a gRPC client-side interceptor that provides Prometheus monitoring for Streaming RPCs.
+func (m *ClientMetrics) StreamClientInterceptor() func(ctx context.Context, desc *grpc.StreamDesc, cc *grpc.ClientConn, method string, streamer grpc.Streamer, opts ...grpc.CallOption) (grpc.ClientStream, error) {
+ return func(ctx context.Context, desc *grpc.StreamDesc, cc *grpc.ClientConn, method string, streamer grpc.Streamer, opts ...grpc.CallOption) (grpc.ClientStream, error) {
+ monitor := newClientReporter(m, clientStreamType(desc), method)
+ clientStream, err := streamer(ctx, desc, cc, method, opts...)
+ if err != nil {
+ monitor.Handled(grpc.Code(err))
+ return nil, err
+ }
+ return &monitoredClientStream{clientStream, monitor}, nil
+ }
+}
+
+func clientStreamType(desc *grpc.StreamDesc) grpcType {
+ if desc.ClientStreams && !desc.ServerStreams {
+ return ClientStream
+ } else if !desc.ClientStreams && desc.ServerStreams {
+ return ServerStream
+ }
+ return BidiStream
+}
+
+// monitoredClientStream wraps grpc.ClientStream allowing each Sent/Recv of message to increment counters.
+type monitoredClientStream struct {
+ grpc.ClientStream
+ monitor *clientReporter
+}
+
+func (s *monitoredClientStream) SendMsg(m interface{}) error {
+ err := s.ClientStream.SendMsg(m)
+ if err == nil {
+ s.monitor.SentMessage()
+ }
+ return err
+}
+
+func (s *monitoredClientStream) RecvMsg(m interface{}) error {
+ err := s.ClientStream.RecvMsg(m)
+ if err == nil {
+ s.monitor.ReceivedMessage()
+ } else if err == io.EOF {
+ s.monitor.Handled(codes.OK)
+ } else {
+ s.monitor.Handled(grpc.Code(err))
+ }
+ return err
+}
diff --git a/vendor/github.com/grpc-ecosystem/go-grpc-prometheus/client_reporter.go b/vendor/github.com/grpc-ecosystem/go-grpc-prometheus/client_reporter.go
new file mode 100644
index 00000000..cbf15322
--- /dev/null
+++ b/vendor/github.com/grpc-ecosystem/go-grpc-prometheus/client_reporter.go
@@ -0,0 +1,46 @@
+// Copyright 2016 Michal Witkowski. All Rights Reserved.
+// See LICENSE for licensing terms.
+
+package grpc_prometheus
+
+import (
+ "time"
+
+ "google.golang.org/grpc/codes"
+)
+
+type clientReporter struct {
+ metrics *ClientMetrics
+ rpcType grpcType
+ serviceName string
+ methodName string
+ startTime time.Time
+}
+
+func newClientReporter(m *ClientMetrics, rpcType grpcType, fullMethod string) *clientReporter {
+ r := &clientReporter{
+ metrics: m,
+ rpcType: rpcType,
+ }
+ if r.metrics.clientHandledHistogramEnabled {
+ r.startTime = time.Now()
+ }
+ r.serviceName, r.methodName = splitMethodName(fullMethod)
+ r.metrics.clientStartedCounter.WithLabelValues(string(r.rpcType), r.serviceName, r.methodName).Inc()
+ return r
+}
+
+func (r *clientReporter) ReceivedMessage() {
+ r.metrics.clientStreamMsgReceived.WithLabelValues(string(r.rpcType), r.serviceName, r.methodName).Inc()
+}
+
+func (r *clientReporter) SentMessage() {
+ r.metrics.clientStreamMsgSent.WithLabelValues(string(r.rpcType), r.serviceName, r.methodName).Inc()
+}
+
+func (r *clientReporter) Handled(code codes.Code) {
+ r.metrics.clientHandledCounter.WithLabelValues(string(r.rpcType), r.serviceName, r.methodName, code.String()).Inc()
+ if r.metrics.clientHandledHistogramEnabled {
+ r.metrics.clientHandledHistogram.WithLabelValues(string(r.rpcType), r.serviceName, r.methodName).Observe(time.Since(r.startTime).Seconds())
+ }
+}
diff --git a/vendor/github.com/grpc-ecosystem/go-grpc-prometheus/makefile b/vendor/github.com/grpc-ecosystem/go-grpc-prometheus/makefile
new file mode 100644
index 00000000..74c08422
--- /dev/null
+++ b/vendor/github.com/grpc-ecosystem/go-grpc-prometheus/makefile
@@ -0,0 +1,16 @@
+SHELL="/bin/bash"
+
+GOFILES_NOVENDOR = $(shell go list ./... | grep -v /vendor/)
+
+all: vet fmt test
+
+fmt:
+ go fmt $(GOFILES_NOVENDOR)
+
+vet:
+ go vet $(GOFILES_NOVENDOR)
+
+test: vet
+ ./scripts/test_all.sh
+
+.PHONY: all vet test
diff --git a/vendor/github.com/grpc-ecosystem/go-grpc-prometheus/metric_options.go b/vendor/github.com/grpc-ecosystem/go-grpc-prometheus/metric_options.go
new file mode 100644
index 00000000..ad8a51c5
--- /dev/null
+++ b/vendor/github.com/grpc-ecosystem/go-grpc-prometheus/metric_options.go
@@ -0,0 +1,35 @@
+package grpc_prometheus
+
+import (
+ prom "github.com/prometheus/client_golang/prometheus"
+)
+
+type CounterOption func(opts *prom.CounterOpts)
+
+type counterOptions []CounterOption
+
+func (co counterOptions) apply(o prom.CounterOpts) prom.CounterOpts {
+ for _, f := range co {
+ f(&o)
+ }
+ return o
+}
+
+func WithConstLabels(labels prom.Labels) CounterOption {
+ return func(o *prom.CounterOpts) {
+ o.ConstLabels = labels
+ }
+}
+
+type HistogramOption func(*prom.HistogramOpts)
+
+// WithHistogramBuckets allows you to specify custom bucket ranges for histograms if EnableHandlingTimeHistogram is on.
+func WithHistogramBuckets(buckets []float64) HistogramOption {
+ return func(o *prom.HistogramOpts) { o.Buckets = buckets }
+}
+
+func WithHistogramConstLabels(labels prom.Labels) HistogramOption {
+ return func(o *prom.HistogramOpts) {
+ o.ConstLabels = labels
+ }
+}
diff --git a/vendor/github.com/grpc-ecosystem/go-grpc-prometheus/server.go b/vendor/github.com/grpc-ecosystem/go-grpc-prometheus/server.go
new file mode 100644
index 00000000..322f9904
--- /dev/null
+++ b/vendor/github.com/grpc-ecosystem/go-grpc-prometheus/server.go
@@ -0,0 +1,48 @@
+// Copyright 2016 Michal Witkowski. All Rights Reserved.
+// See LICENSE for licensing terms.
+
+// gRPC Prometheus monitoring interceptors for server-side gRPC.
+
+package grpc_prometheus
+
+import (
+ prom "github.com/prometheus/client_golang/prometheus"
+ "google.golang.org/grpc"
+)
+
+var (
+ // DefaultServerMetrics is the default instance of ServerMetrics. It is
+ // intended to be used in conjunction the default Prometheus metrics
+ // registry.
+ DefaultServerMetrics = NewServerMetrics()
+
+ // UnaryServerInterceptor is a gRPC server-side interceptor that provides Prometheus monitoring for Unary RPCs.
+ UnaryServerInterceptor = DefaultServerMetrics.UnaryServerInterceptor()
+
+ // StreamServerInterceptor is a gRPC server-side interceptor that provides Prometheus monitoring for Streaming RPCs.
+ StreamServerInterceptor = DefaultServerMetrics.StreamServerInterceptor()
+)
+
+func init() {
+ prom.MustRegister(DefaultServerMetrics.serverStartedCounter)
+ prom.MustRegister(DefaultServerMetrics.serverHandledCounter)
+ prom.MustRegister(DefaultServerMetrics.serverStreamMsgReceived)
+ prom.MustRegister(DefaultServerMetrics.serverStreamMsgSent)
+}
+
+// Register takes a gRPC server and pre-initializes all counters to 0. This
+// allows for easier monitoring in Prometheus (no missing metrics), and should
+// be called *after* all services have been registered with the server. This
+// function acts on the DefaultServerMetrics variable.
+func Register(server *grpc.Server) {
+ DefaultServerMetrics.InitializeMetrics(server)
+}
+
+// EnableHandlingTimeHistogram turns on recording of handling time
+// of RPCs. Histogram metrics can be very expensive for Prometheus
+// to retain and query. This function acts on the DefaultServerMetrics
+// variable and the default Prometheus metrics registry.
+func EnableHandlingTimeHistogram(opts ...HistogramOption) {
+ DefaultServerMetrics.EnableHandlingTimeHistogram(opts...)
+ prom.Register(DefaultServerMetrics.serverHandledHistogram)
+}
diff --git a/vendor/github.com/grpc-ecosystem/go-grpc-prometheus/server_metrics.go b/vendor/github.com/grpc-ecosystem/go-grpc-prometheus/server_metrics.go
new file mode 100644
index 00000000..afa01428
--- /dev/null
+++ b/vendor/github.com/grpc-ecosystem/go-grpc-prometheus/server_metrics.go
@@ -0,0 +1,202 @@
+package grpc_prometheus
+
+import (
+ prom "github.com/prometheus/client_golang/prometheus"
+ "golang.org/x/net/context"
+ "google.golang.org/grpc"
+)
+
+// ServerMetrics represents a collection of metrics to be registered on a
+// Prometheus metrics registry for a gRPC server.
+type ServerMetrics struct {
+ serverStartedCounter *prom.CounterVec
+ serverHandledCounter *prom.CounterVec
+ serverStreamMsgReceived *prom.CounterVec
+ serverStreamMsgSent *prom.CounterVec
+ serverHandledHistogramEnabled bool
+ serverHandledHistogramOpts prom.HistogramOpts
+ serverHandledHistogram *prom.HistogramVec
+}
+
+// NewServerMetrics returns a ServerMetrics object. Use a new instance of
+// ServerMetrics when not using the default Prometheus metrics registry, for
+// example when wanting to control which metrics are added to a registry as
+// opposed to automatically adding metrics via init functions.
+func NewServerMetrics(counterOpts ...CounterOption) *ServerMetrics {
+ opts := counterOptions(counterOpts)
+ return &ServerMetrics{
+ serverStartedCounter: prom.NewCounterVec(
+ opts.apply(prom.CounterOpts{
+ Name: "grpc_server_started_total",
+ Help: "Total number of RPCs started on the server.",
+ }), []string{"grpc_type", "grpc_service", "grpc_method"}),
+ serverHandledCounter: prom.NewCounterVec(
+ opts.apply(prom.CounterOpts{
+ Name: "grpc_server_handled_total",
+ Help: "Total number of RPCs completed on the server, regardless of success or failure.",
+ }), []string{"grpc_type", "grpc_service", "grpc_method", "grpc_code"}),
+ serverStreamMsgReceived: prom.NewCounterVec(
+ opts.apply(prom.CounterOpts{
+ Name: "grpc_server_msg_received_total",
+ Help: "Total number of RPC stream messages received on the server.",
+ }), []string{"grpc_type", "grpc_service", "grpc_method"}),
+ serverStreamMsgSent: prom.NewCounterVec(
+ opts.apply(prom.CounterOpts{
+ Name: "grpc_server_msg_sent_total",
+ Help: "Total number of gRPC stream messages sent by the server.",
+ }), []string{"grpc_type", "grpc_service", "grpc_method"}),
+ serverHandledHistogramEnabled: false,
+ serverHandledHistogramOpts: prom.HistogramOpts{
+ Name: "grpc_server_handling_seconds",
+ Help: "Histogram of response latency (seconds) of gRPC that had been application-level handled by the server.",
+ Buckets: prom.DefBuckets,
+ },
+ serverHandledHistogram: nil,
+ }
+}
+
+// EnableHandlingTimeHistogram enables histograms being registered when
+// registering the ServerMetrics on a Prometheus registry. Histograms can be
+// expensive on Prometheus servers. It takes options to configure histogram
+// options such as the defined buckets.
+func (m *ServerMetrics) EnableHandlingTimeHistogram(opts ...HistogramOption) {
+ for _, o := range opts {
+ o(&m.serverHandledHistogramOpts)
+ }
+ if !m.serverHandledHistogramEnabled {
+ m.serverHandledHistogram = prom.NewHistogramVec(
+ m.serverHandledHistogramOpts,
+ []string{"grpc_type", "grpc_service", "grpc_method"},
+ )
+ }
+ m.serverHandledHistogramEnabled = true
+}
+
+// Describe sends the super-set of all possible descriptors of metrics
+// collected by this Collector to the provided channel and returns once
+// the last descriptor has been sent.
+func (m *ServerMetrics) Describe(ch chan<- *prom.Desc) {
+ m.serverStartedCounter.Describe(ch)
+ m.serverHandledCounter.Describe(ch)
+ m.serverStreamMsgReceived.Describe(ch)
+ m.serverStreamMsgSent.Describe(ch)
+ if m.serverHandledHistogramEnabled {
+ m.serverHandledHistogram.Describe(ch)
+ }
+}
+
+// Collect is called by the Prometheus registry when collecting
+// metrics. The implementation sends each collected metric via the
+// provided channel and returns once the last metric has been sent.
+func (m *ServerMetrics) Collect(ch chan<- prom.Metric) {
+ m.serverStartedCounter.Collect(ch)
+ m.serverHandledCounter.Collect(ch)
+ m.serverStreamMsgReceived.Collect(ch)
+ m.serverStreamMsgSent.Collect(ch)
+ if m.serverHandledHistogramEnabled {
+ m.serverHandledHistogram.Collect(ch)
+ }
+}
+
+// UnaryServerInterceptor is a gRPC server-side interceptor that provides Prometheus monitoring for Unary RPCs.
+func (m *ServerMetrics) UnaryServerInterceptor() func(ctx context.Context, req interface{}, info *grpc.UnaryServerInfo, handler grpc.UnaryHandler) (interface{}, error) {
+ return func(ctx context.Context, req interface{}, info *grpc.UnaryServerInfo, handler grpc.UnaryHandler) (interface{}, error) {
+ monitor := newServerReporter(m, Unary, info.FullMethod)
+ monitor.ReceivedMessage()
+ resp, err := handler(ctx, req)
+ monitor.Handled(grpc.Code(err))
+ if err == nil {
+ monitor.SentMessage()
+ }
+ return resp, err
+ }
+}
+
+// StreamServerInterceptor is a gRPC server-side interceptor that provides Prometheus monitoring for Streaming RPCs.
+func (m *ServerMetrics) StreamServerInterceptor() func(srv interface{}, ss grpc.ServerStream, info *grpc.StreamServerInfo, handler grpc.StreamHandler) error {
+ return func(srv interface{}, ss grpc.ServerStream, info *grpc.StreamServerInfo, handler grpc.StreamHandler) error {
+ monitor := newServerReporter(m, streamRpcType(info), info.FullMethod)
+ err := handler(srv, &monitoredServerStream{ss, monitor})
+ monitor.Handled(grpc.Code(err))
+ return err
+ }
+}
+
+// InitializeMetrics initializes all metrics, with their appropriate null
+// value, for all gRPC methods registered on a gRPC server. This is useful, to
+// ensure that all metrics exist when collecting and querying.
+func (m *ServerMetrics) InitializeMetrics(server *grpc.Server) {
+ serviceInfo := server.GetServiceInfo()
+ for serviceName, info := range serviceInfo {
+ for _, mInfo := range info.Methods {
+ preRegisterMethod(m, serviceName, &mInfo)
+ }
+ }
+}
+
+// Register registers all server metrics in a given metrics registry. Depending
+// on histogram options and whether they are enabled, histogram metrics are
+// also registered.
+//
+// Deprecated: ServerMetrics implements Prometheus Collector interface. You can
+// register an instance of ServerMetrics directly by using
+// prometheus.Register(m).
+func (m *ServerMetrics) Register(r prom.Registerer) error {
+ return r.Register(m)
+}
+
+// MustRegister tries to register all server metrics and panics on an error.
+//
+// Deprecated: ServerMetrics implements Prometheus Collector interface. You can
+// register an instance of ServerMetrics directly by using
+// prometheus.MustRegister(m).
+func (m *ServerMetrics) MustRegister(r prom.Registerer) {
+ r.MustRegister(m)
+}
+
+func streamRpcType(info *grpc.StreamServerInfo) grpcType {
+ if info.IsClientStream && !info.IsServerStream {
+ return ClientStream
+ } else if !info.IsClientStream && info.IsServerStream {
+ return ServerStream
+ }
+ return BidiStream
+}
+
+// monitoredStream wraps grpc.ServerStream allowing each Sent/Recv of message to increment counters.
+type monitoredServerStream struct {
+ grpc.ServerStream
+ monitor *serverReporter
+}
+
+func (s *monitoredServerStream) SendMsg(m interface{}) error {
+ err := s.ServerStream.SendMsg(m)
+ if err == nil {
+ s.monitor.SentMessage()
+ }
+ return err
+}
+
+func (s *monitoredServerStream) RecvMsg(m interface{}) error {
+ err := s.ServerStream.RecvMsg(m)
+ if err == nil {
+ s.monitor.ReceivedMessage()
+ }
+ return err
+}
+
+// preRegisterMethod is invoked on Register of a Server, allowing all gRPC services labels to be pre-populated.
+func preRegisterMethod(metrics *ServerMetrics, serviceName string, mInfo *grpc.MethodInfo) {
+ methodName := mInfo.Name
+ methodType := string(typeFromMethodInfo(mInfo))
+ // These are just references (no increments), as just referencing will create the labels but not set values.
+ metrics.serverStartedCounter.GetMetricWithLabelValues(methodType, serviceName, methodName)
+ metrics.serverStreamMsgReceived.GetMetricWithLabelValues(methodType, serviceName, methodName)
+ metrics.serverStreamMsgSent.GetMetricWithLabelValues(methodType, serviceName, methodName)
+ if metrics.serverHandledHistogramEnabled {
+ metrics.serverHandledHistogram.GetMetricWithLabelValues(methodType, serviceName, methodName)
+ }
+ for _, code := range allCodes {
+ metrics.serverHandledCounter.GetMetricWithLabelValues(methodType, serviceName, methodName, code.String())
+ }
+}
diff --git a/vendor/github.com/grpc-ecosystem/go-grpc-prometheus/server_reporter.go b/vendor/github.com/grpc-ecosystem/go-grpc-prometheus/server_reporter.go
new file mode 100644
index 00000000..aa9db540
--- /dev/null
+++ b/vendor/github.com/grpc-ecosystem/go-grpc-prometheus/server_reporter.go
@@ -0,0 +1,46 @@
+// Copyright 2016 Michal Witkowski. All Rights Reserved.
+// See LICENSE for licensing terms.
+
+package grpc_prometheus
+
+import (
+ "time"
+
+ "google.golang.org/grpc/codes"
+)
+
+type serverReporter struct {
+ metrics *ServerMetrics
+ rpcType grpcType
+ serviceName string
+ methodName string
+ startTime time.Time
+}
+
+func newServerReporter(m *ServerMetrics, rpcType grpcType, fullMethod string) *serverReporter {
+ r := &serverReporter{
+ metrics: m,
+ rpcType: rpcType,
+ }
+ if r.metrics.serverHandledHistogramEnabled {
+ r.startTime = time.Now()
+ }
+ r.serviceName, r.methodName = splitMethodName(fullMethod)
+ r.metrics.serverStartedCounter.WithLabelValues(string(r.rpcType), r.serviceName, r.methodName).Inc()
+ return r
+}
+
+func (r *serverReporter) ReceivedMessage() {
+ r.metrics.serverStreamMsgReceived.WithLabelValues(string(r.rpcType), r.serviceName, r.methodName).Inc()
+}
+
+func (r *serverReporter) SentMessage() {
+ r.metrics.serverStreamMsgSent.WithLabelValues(string(r.rpcType), r.serviceName, r.methodName).Inc()
+}
+
+func (r *serverReporter) Handled(code codes.Code) {
+ r.metrics.serverHandledCounter.WithLabelValues(string(r.rpcType), r.serviceName, r.methodName, code.String()).Inc()
+ if r.metrics.serverHandledHistogramEnabled {
+ r.metrics.serverHandledHistogram.WithLabelValues(string(r.rpcType), r.serviceName, r.methodName).Observe(time.Since(r.startTime).Seconds())
+ }
+}
diff --git a/vendor/github.com/grpc-ecosystem/go-grpc-prometheus/util.go b/vendor/github.com/grpc-ecosystem/go-grpc-prometheus/util.go
new file mode 100644
index 00000000..d581c792
--- /dev/null
+++ b/vendor/github.com/grpc-ecosystem/go-grpc-prometheus/util.go
@@ -0,0 +1,50 @@
+// Copyright 2016 Michal Witkowski. All Rights Reserved.
+// See LICENSE for licensing terms.
+
+package grpc_prometheus
+
+import (
+ "strings"
+
+ "google.golang.org/grpc"
+ "google.golang.org/grpc/codes"
+)
+
+type grpcType string
+
+const (
+ Unary grpcType = "unary"
+ ClientStream grpcType = "client_stream"
+ ServerStream grpcType = "server_stream"
+ BidiStream grpcType = "bidi_stream"
+)
+
+var (
+ allCodes = []codes.Code{
+ codes.OK, codes.Canceled, codes.Unknown, codes.InvalidArgument, codes.DeadlineExceeded, codes.NotFound,
+ codes.AlreadyExists, codes.PermissionDenied, codes.Unauthenticated, codes.ResourceExhausted,
+ codes.FailedPrecondition, codes.Aborted, codes.OutOfRange, codes.Unimplemented, codes.Internal,
+ codes.Unavailable, codes.DataLoss,
+ }
+)
+
+func splitMethodName(fullMethodName string) (string, string) {
+ fullMethodName = strings.TrimPrefix(fullMethodName, "/") // remove leading slash
+ if i := strings.Index(fullMethodName, "/"); i >= 0 {
+ return fullMethodName[:i], fullMethodName[i+1:]
+ }
+ return "unknown", "unknown"
+}
+
+func typeFromMethodInfo(mInfo *grpc.MethodInfo) grpcType {
+ if mInfo.IsClientStream == false && mInfo.IsServerStream == false {
+ return Unary
+ }
+ if mInfo.IsClientStream == true && mInfo.IsServerStream == false {
+ return ClientStream
+ }
+ if mInfo.IsClientStream == false && mInfo.IsServerStream == true {
+ return ServerStream
+ }
+ return BidiStream
+}
diff --git a/vendor/gitlab.com/gitlab-org/gitaly/LICENSE b/vendor/gitlab.com/gitlab-org/gitaly/LICENSE
new file mode 100644
index 00000000..c7344c56
--- /dev/null
+++ b/vendor/gitlab.com/gitlab-org/gitaly/LICENSE
@@ -0,0 +1,21 @@
+The MIT License (MIT)
+
+Copyright (c) 2016-2017 GitLab B.V.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
+OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
+THE SOFTWARE.
diff --git a/vendor/gitlab.com/gitlab-org/gitaly/NOTICE b/vendor/gitlab.com/gitlab-org/gitaly/NOTICE
new file mode 100644
index 00000000..dbb1e63e
--- /dev/null
+++ b/vendor/gitlab.com/gitlab-org/gitaly/NOTICE
@@ -0,0 +1,2496 @@
+The following components are included in Gitaly:
+
+LICENSE - go
+Copyright (c) 2009 The Go Authors. All rights reserved.
+
+Redistribution and use in source and binary forms, with or without
+modification, are permitted provided that the following conditions are
+met:
+
+ * Redistributions of source code must retain the above copyright
+notice, this list of conditions and the following disclaimer.
+ * Redistributions in binary form must reproduce the above
+copyright notice, this list of conditions and the following disclaimer
+in the documentation and/or other materials provided with the
+distribution.
+ * Neither the name of Google Inc. nor the names of its
+contributors may be used to endorse or promote products derived from
+this software without specific prior written permission.
+
+THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
+A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
+OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
+SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
+LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+PATENTS - go
+Additional IP Rights Grant (Patents)
+
+"This implementation" means the copyrightable works distributed by
+Google as part of the Go project.
+
+Google hereby grants to You a perpetual, worldwide, non-exclusive,
+no-charge, royalty-free, irrevocable (except as stated in this section)
+patent license to make, have made, use, offer to sell, sell, import,
+transfer and otherwise run, modify and propagate the contents of this
+implementation of Go, where such license applies only to those patent
+claims, both currently owned or controlled by Google and acquired in
+the future, licensable by Google that are necessarily infringed by this
+implementation of Go. This grant does not include claims that would be
+infringed only as a consequence of further modification of this
+implementation. If you or your agent or exclusive licensee institute or
+order or agree to the institution of patent litigation against any
+entity (including a cross-claim or counterclaim in a lawsuit) alleging
+that this implementation of Go or any code incorporated within this
+implementation of Go constitutes direct or contributory patent
+infringement, or inducement of patent infringement, then any patent
+rights granted to you under this License for this implementation of Go
+shall terminate as of the date such litigation is filed.
+
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+LICENSE - gitlab.com/gitlab-org/gitaly
+The MIT License (MIT)
+
+Copyright (c) 2016-2017 GitLab B.V.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
+OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
+THE SOFTWARE.
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+LICENSE - gitlab.com/gitlab-org/gitaly/internal/middleware/panichandler
+Copyright (c) 2016 Masahiro Sano
+
+MIT License
+
+Permission is hereby granted, free of charge, to any person obtaining
+a copy of this software and associated documentation files (the
+"Software"), to deal in the Software without restriction, including
+without limitation the rights to use, copy, modify, merge, publish,
+distribute, sublicense, and/or sell copies of the Software, and to
+permit persons to whom the Software is furnished to do so, subject to
+the following conditions:
+
+The above copyright notice and this permission notice shall be
+included in all copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
+EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
+MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
+NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
+LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
+OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
+WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+COPYING - gitlab.com/gitlab-org/gitaly/vendor/github.com/BurntSushi/toml
+The MIT License (MIT)
+
+Copyright (c) 2013 TOML authors
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
+OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
+THE SOFTWARE.
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+LICENSE - gitlab.com/gitlab-org/gitaly/vendor/github.com/beorn7/perks
+Copyright (C) 2013 Blake Mizerany
+
+Permission is hereby granted, free of charge, to any person obtaining
+a copy of this software and associated documentation files (the
+"Software"), to deal in the Software without restriction, including
+without limitation the rights to use, copy, modify, merge, publish,
+distribute, sublicense, and/or sell copies of the Software, and to
+permit persons to whom the Software is furnished to do so, subject to
+the following conditions:
+
+The above copyright notice and this permission notice shall be
+included in all copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
+EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
+MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
+NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
+LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
+OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
+WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+LICENSE - gitlab.com/gitlab-org/gitaly/vendor/github.com/certifi/gocertifi
+This Source Code Form is subject to the terms of the Mozilla Public License,
+v. 2.0. If a copy of the MPL was not distributed with this file, You can obtain
+one at http://mozilla.org/MPL/2.0/.
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+LICENSE - gitlab.com/gitlab-org/gitaly/vendor/github.com/davecgh/go-spew
+ISC License
+
+Copyright (c) 2012-2016 Dave Collins <dave@davec.name>
+
+Permission to use, copy, modify, and distribute this software for any
+purpose with or without fee is hereby granted, provided that the above
+copyright notice and this permission notice appear in all copies.
+
+THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
+WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
+MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
+ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
+WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
+ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
+OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+LICENSE - gitlab.com/gitlab-org/gitaly/vendor/github.com/getsentry/raven-go
+Copyright (c) 2013 Apollic Software, LLC. All rights reserved.
+Copyright (c) 2015 Functional Software, Inc. All rights reserved.
+
+Redistribution and use in source and binary forms, with or without
+modification, are permitted provided that the following conditions are
+met:
+
+ * Redistributions of source code must retain the above copyright
+notice, this list of conditions and the following disclaimer.
+ * Redistributions in binary form must reproduce the above
+copyright notice, this list of conditions and the following disclaimer
+in the documentation and/or other materials provided with the
+distribution.
+ * Neither the name of Apollic Software, LLC nor the names of its
+contributors may be used to endorse or promote products derived from
+this software without specific prior written permission.
+
+THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
+A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
+OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
+SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
+LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+LICENSE - gitlab.com/gitlab-org/gitaly/vendor/github.com/golang/protobuf
+Go support for Protocol Buffers - Google's data interchange format
+
+Copyright 2010 The Go Authors. All rights reserved.
+https://github.com/golang/protobuf
+
+Redistribution and use in source and binary forms, with or without
+modification, are permitted provided that the following conditions are
+met:
+
+ * Redistributions of source code must retain the above copyright
+notice, this list of conditions and the following disclaimer.
+ * Redistributions in binary form must reproduce the above
+copyright notice, this list of conditions and the following disclaimer
+in the documentation and/or other materials provided with the
+distribution.
+ * Neither the name of Google Inc. nor the names of its
+contributors may be used to endorse or promote products derived from
+this software without specific prior written permission.
+
+THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
+A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
+OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
+SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
+LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+LICENSE - gitlab.com/gitlab-org/gitaly/vendor/github.com/grpc-ecosystem/go-grpc-middleware
+ Apache License
+ Version 2.0, January 2004
+ http://www.apache.org/licenses/
+
+ TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION
+
+ 1. Definitions.
+
+ "License" shall mean the terms and conditions for use, reproduction,
+ and distribution as defined by Sections 1 through 9 of this document.
+
+ "Licensor" shall mean the copyright owner or entity authorized by
+ the copyright owner that is granting the License.
+
+ "Legal Entity" shall mean the union of the acting entity and all
+ other entities that control, are controlled by, or are under common
+ control with that entity. For the purposes of this definition,
+ "control" means (i) the power, direct or indirect, to cause the
+ direction or management of such entity, whether by contract or
+ otherwise, or (ii) ownership of fifty percent (50%) or more of the
+ outstanding shares, or (iii) beneficial ownership of such entity.
+
+ "You" (or "Your") shall mean an individual or Legal Entity
+ exercising permissions granted by this License.
+
+ "Source" form shall mean the preferred form for making modifications,
+ including but not limited to software source code, documentation
+ source, and configuration files.
+
+ "Object" form shall mean any form resulting from mechanical
+ transformation or translation of a Source form, including but
+ not limited to compiled object code, generated documentation,
+ and conversions to other media types.
+
+ "Work" shall mean the work of authorship, whether in Source or
+ Object form, made available under the License, as indicated by a
+ copyright notice that is included in or attached to the work
+ (an example is provided in the Appendix below).
+
+ "Derivative Works" shall mean any work, whether in Source or Object
+ form, that is based on (or derived from) the Work and for which the
+ editorial revisions, annotations, elaborations, or other modifications
+ represent, as a whole, an original work of authorship. For the purposes
+ of this License, Derivative Works shall not include works that remain
+ separable from, or merely link (or bind by name) to the interfaces of,
+ the Work and Derivative Works thereof.
+
+ "Contribution" shall mean any work of authorship, including
+ the original version of the Work and any modifications or additions
+ to that Work or Derivative Works thereof, that is intentionally
+ submitted to Licensor for inclusion in the Work by the copyright owner
+ or by an individual or Legal Entity authorized to submit on behalf of
+ the copyright owner. For the purposes of this definition, "submitted"
+ means any form of electronic, verbal, or written communication sent
+ to the Licensor or its representatives, including but not limited to
+ communication on electronic mailing lists, source code control systems,
+ and issue tracking systems that are managed by, or on behalf of, the
+ Licensor for the purpose of discussing and improving the Work, but
+ excluding communication that is conspicuously marked or otherwise
+ designated in writing by the copyright owner as "Not a Contribution."
+
+ "Contributor" shall mean Licensor and any individual or Legal Entity
+ on behalf of whom a Contribution has been received by Licensor and
+ subsequently incorporated within the Work.
+
+ 2. Grant of Copyright License. Subject to the terms and conditions of
+ this License, each Contributor hereby grants to You a perpetual,
+ worldwide, non-exclusive, no-charge, royalty-free, irrevocable
+ copyright license to reproduce, prepare Derivative Works of,
+ publicly display, publicly perform, sublicense, and distribute the
+ Work and such Derivative Works in Source or Object form.
+
+ 3. Grant of Patent License. Subject to the terms and conditions of
+ this License, each Contributor hereby grants to You a perpetual,
+ worldwide, non-exclusive, no-charge, royalty-free, irrevocable
+ (except as stated in this section) patent license to make, have made,
+ use, offer to sell, sell, import, and otherwise transfer the Work,
+ where such license applies only to those patent claims licensable
+ by such Contributor that are necessarily infringed by their
+ Contribution(s) alone or by combination of their Contribution(s)
+ with the Work to which such Contribution(s) was submitted. If You
+ institute patent litigation against any entity (including a
+ cross-claim or counterclaim in a lawsuit) alleging that the Work
+ or a Contribution incorporated within the Work constitutes direct
+ or contributory patent infringement, then any patent licenses
+ granted to You under this License for that Work shall terminate
+ as of the date such litigation is filed.
+
+ 4. Redistribution. You may reproduce and distribute copies of the
+ Work or Derivative Works thereof in any medium, with or without
+ modifications, and in Source or Object form, provided that You
+ meet the following conditions:
+
+ (a) You must give any other recipients of the Work or
+ Derivative Works a copy of this License; and
+
+ (b) You must cause any modified files to carry prominent notices
+ stating that You changed the files; and
+
+ (c) You must retain, in the Source form of any Derivative Works
+ that You distribute, all copyright, patent, trademark, and
+ attribution notices from the Source form of the Work,
+ excluding those notices that do not pertain to any part of
+ the Derivative Works; and
+
+ (d) If the Work includes a "NOTICE" text file as part of its
+ distribution, then any Derivative Works that You distribute must
+ include a readable copy of the attribution notices contained
+ within such NOTICE file, excluding those notices that do not
+ pertain to any part of the Derivative Works, in at least one
+ of the following places: within a NOTICE text file distributed
+ as part of the Derivative Works; within the Source form or
+ documentation, if provided along with the Derivative Works; or,
+ within a display generated by the Derivative Works, if and
+ wherever such third-party notices normally appear. The contents
+ of the NOTICE file are for informational purposes only and
+ do not modify the License. You may add Your own attribution
+ notices within Derivative Works that You distribute, alongside
+ or as an addendum to the NOTICE text from the Work, provided
+ that such additional attribution notices cannot be construed
+ as modifying the License.
+
+ You may add Your own copyright statement to Your modifications and
+ may provide additional or different license terms and conditions
+ for use, reproduction, or distribution of Your modifications, or
+ for any such Derivative Works as a whole, provided Your use,
+ reproduction, and distribution of the Work otherwise complies with
+ the conditions stated in this License.
+
+ 5. Submission of Contributions. Unless You explicitly state otherwise,
+ any Contribution intentionally submitted for inclusion in the Work
+ by You to the Licensor shall be under the terms and conditions of
+ this License, without any additional terms or conditions.
+ Notwithstanding the above, nothing herein shall supersede or modify
+ the terms of any separate license agreement you may have executed
+ with Licensor regarding such Contributions.
+
+ 6. Trademarks. This License does not grant permission to use the trade
+ names, trademarks, service marks, or product names of the Licensor,
+ except as required for reasonable and customary use in describing the
+ origin of the Work and reproducing the content of the NOTICE file.
+
+ 7. Disclaimer of Warranty. Unless required by applicable law or
+ agreed to in writing, Licensor provides the Work (and each
+ Contributor provides its Contributions) on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
+ implied, including, without limitation, any warranties or conditions
+ of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A
+ PARTICULAR PURPOSE. You are solely responsible for determining the
+ appropriateness of using or redistributing the Work and assume any
+ risks associated with Your exercise of permissions under this License.
+
+ 8. Limitation of Liability. In no event and under no legal theory,
+ whether in tort (including negligence), contract, or otherwise,
+ unless required by applicable law (such as deliberate and grossly
+ negligent acts) or agreed to in writing, shall any Contributor be
+ liable to You for damages, including any direct, indirect, special,
+ incidental, or consequential damages of any character arising as a
+ result of this License or out of the use or inability to use the
+ Work (including but not limited to damages for loss of goodwill,
+ work stoppage, computer failure or malfunction, or any and all
+ other commercial damages or losses), even if such Contributor
+ has been advised of the possibility of such damages.
+
+ 9. Accepting Warranty or Additional Liability. While redistributing
+ the Work or Derivative Works thereof, You may choose to offer,
+ and charge a fee for, acceptance of support, warranty, indemnity,
+ or other liability obligations and/or rights consistent with this
+ License. However, in accepting such obligations, You may act only
+ on Your own behalf and on Your sole responsibility, not on behalf
+ of any other Contributor, and only if You agree to indemnify,
+ defend, and hold each Contributor harmless for any liability
+ incurred by, or claims asserted against, such Contributor by reason
+ of your accepting any such warranty or additional liability.
+
+ END OF TERMS AND CONDITIONS
+
+ APPENDIX: How to apply the Apache License to your work.
+
+ To apply the Apache License to your work, attach the following
+ boilerplate notice, with the fields enclosed by brackets "[]"
+ replaced with your own identifying information. (Don't include
+ the brackets!) The text should be enclosed in the appropriate
+ comment syntax for the file format. We also recommend that a
+ file or class name and description of purpose be included on the
+ same "printed page" as the copyright notice for easier
+ identification within third-party archives.
+
+ Copyright [yyyy] [name of copyright owner]
+
+ Licensed under the Apache License, Version 2.0 (the "License");
+ you may not use this file except in compliance with the License.
+ You may obtain a copy of the License at
+
+ http://www.apache.org/licenses/LICENSE-2.0
+
+ Unless required by applicable law or agreed to in writing, software
+ distributed under the License is distributed on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ See the License for the specific language governing permissions and
+ limitations under the License.~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+LICENSE - gitlab.com/gitlab-org/gitaly/vendor/github.com/grpc-ecosystem/go-grpc-prometheus
+ Apache License
+ Version 2.0, January 2004
+ http://www.apache.org/licenses/
+
+ TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION
+
+ 1. Definitions.
+
+ "License" shall mean the terms and conditions for use, reproduction,
+ and distribution as defined by Sections 1 through 9 of this document.
+
+ "Licensor" shall mean the copyright owner or entity authorized by
+ the copyright owner that is granting the License.
+
+ "Legal Entity" shall mean the union of the acting entity and all
+ other entities that control, are controlled by, or are under common
+ control with that entity. For the purposes of this definition,
+ "control" means (i) the power, direct or indirect, to cause the
+ direction or management of such entity, whether by contract or
+ otherwise, or (ii) ownership of fifty percent (50%) or more of the
+ outstanding shares, or (iii) beneficial ownership of such entity.
+
+ "You" (or "Your") shall mean an individual or Legal Entity
+ exercising permissions granted by this License.
+
+ "Source" form shall mean the preferred form for making modifications,
+ including but not limited to software source code, documentation
+ source, and configuration files.
+
+ "Object" form shall mean any form resulting from mechanical
+ transformation or translation of a Source form, including but
+ not limited to compiled object code, generated documentation,
+ and conversions to other media types.
+
+ "Work" shall mean the work of authorship, whether in Source or
+ Object form, made available under the License, as indicated by a
+ copyright notice that is included in or attached to the work
+ (an example is provided in the Appendix below).
+
+ "Derivative Works" shall mean any work, whether in Source or Object
+ form, that is based on (or derived from) the Work and for which the
+ editorial revisions, annotations, elaborations, or other modifications
+ represent, as a whole, an original work of authorship. For the purposes
+ of this License, Derivative Works shall not include works that remain
+ separable from, or merely link (or bind by name) to the interfaces of,
+ the Work and Derivative Works thereof.
+
+ "Contribution" shall mean any work of authorship, including
+ the original version of the Work and any modifications or additions
+ to that Work or Derivative Works thereof, that is intentionally
+ submitted to Licensor for inclusion in the Work by the copyright owner
+ or by an individual or Legal Entity authorized to submit on behalf of
+ the copyright owner. For the purposes of this definition, "submitted"
+ means any form of electronic, verbal, or written communication sent
+ to the Licensor or its representatives, including but not limited to
+ communication on electronic mailing lists, source code control systems,
+ and issue tracking systems that are managed by, or on behalf of, the
+ Licensor for the purpose of discussing and improving the Work, but
+ excluding communication that is conspicuously marked or otherwise
+ designated in writing by the copyright owner as "Not a Contribution."
+
+ "Contributor" shall mean Licensor and any individual or Legal Entity
+ on behalf of whom a Contribution has been received by Licensor and
+ subsequently incorporated within the Work.
+
+ 2. Grant of Copyright License. Subject to the terms and conditions of
+ this License, each Contributor hereby grants to You a perpetual,
+ worldwide, non-exclusive, no-charge, royalty-free, irrevocable
+ copyright license to reproduce, prepare Derivative Works of,
+ publicly display, publicly perform, sublicense, and distribute the
+ Work and such Derivative Works in Source or Object form.
+
+ 3. Grant of Patent License. Subject to the terms and conditions of
+ this License, each Contributor hereby grants to You a perpetual,
+ worldwide, non-exclusive, no-charge, royalty-free, irrevocable
+ (except as stated in this section) patent license to make, have made,
+ use, offer to sell, sell, import, and otherwise transfer the Work,
+ where such license applies only to those patent claims licensable
+ by such Contributor that are necessarily infringed by their
+ Contribution(s) alone or by combination of their Contribution(s)
+ with the Work to which such Contribution(s) was submitted. If You
+ institute patent litigation against any entity (including a
+ cross-claim or counterclaim in a lawsuit) alleging that the Work
+ or a Contribution incorporated within the Work constitutes direct
+ or contributory patent infringement, then any patent licenses
+ granted to You under this License for that Work shall terminate
+ as of the date such litigation is filed.
+
+ 4. Redistribution. You may reproduce and distribute copies of the
+ Work or Derivative Works thereof in any medium, with or without
+ modifications, and in Source or Object form, provided that You
+ meet the following conditions:
+
+ (a) You must give any other recipients of the Work or
+ Derivative Works a copy of this License; and
+
+ (b) You must cause any modified files to carry prominent notices
+ stating that You changed the files; and
+
+ (c) You must retain, in the Source form of any Derivative Works
+ that You distribute, all copyright, patent, trademark, and
+ attribution notices from the Source form of the Work,
+ excluding those notices that do not pertain to any part of
+ the Derivative Works; and
+
+ (d) If the Work includes a "NOTICE" text file as part of its
+ distribution, then any Derivative Works that You distribute must
+ include a readable copy of the attribution notices contained
+ within such NOTICE file, excluding those notices that do not
+ pertain to any part of the Derivative Works, in at least one
+ of the following places: within a NOTICE text file distributed
+ as part of the Derivative Works; within the Source form or
+ documentation, if provided along with the Derivative Works; or,
+ within a display generated by the Derivative Works, if and
+ wherever such third-party notices normally appear. The contents
+ of the NOTICE file are for informational purposes only and
+ do not modify the License. You may add Your own attribution
+ notices within Derivative Works that You distribute, alongside
+ or as an addendum to the NOTICE text from the Work, provided
+ that such additional attribution notices cannot be construed
+ as modifying the License.
+
+ You may add Your own copyright statement to Your modifications and
+ may provide additional or different license terms and conditions
+ for use, reproduction, or distribution of Your modifications, or
+ for any such Derivative Works as a whole, provided Your use,
+ reproduction, and distribution of the Work otherwise complies with
+ the conditions stated in this License.
+
+ 5. Submission of Contributions. Unless You explicitly state otherwise,
+ any Contribution intentionally submitted for inclusion in the Work
+ by You to the Licensor shall be under the terms and conditions of
+ this License, without any additional terms or conditions.
+ Notwithstanding the above, nothing herein shall supersede or modify
+ the terms of any separate license agreement you may have executed
+ with Licensor regarding such Contributions.
+
+ 6. Trademarks. This License does not grant permission to use the trade
+ names, trademarks, service marks, or product names of the Licensor,
+ except as required for reasonable and customary use in describing the
+ origin of the Work and reproducing the content of the NOTICE file.
+
+ 7. Disclaimer of Warranty. Unless required by applicable law or
+ agreed to in writing, Licensor provides the Work (and each
+ Contributor provides its Contributions) on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
+ implied, including, without limitation, any warranties or conditions
+ of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A
+ PARTICULAR PURPOSE. You are solely responsible for determining the
+ appropriateness of using or redistributing the Work and assume any
+ risks associated with Your exercise of permissions under this License.
+
+ 8. Limitation of Liability. In no event and under no legal theory,
+ whether in tort (including negligence), contract, or otherwise,
+ unless required by applicable law (such as deliberate and grossly
+ negligent acts) or agreed to in writing, shall any Contributor be
+ liable to You for damages, including any direct, indirect, special,
+ incidental, or consequential damages of any character arising as a
+ result of this License or out of the use or inability to use the
+ Work (including but not limited to damages for loss of goodwill,
+ work stoppage, computer failure or malfunction, or any and all
+ other commercial damages or losses), even if such Contributor
+ has been advised of the possibility of such damages.
+
+ 9. Accepting Warranty or Additional Liability. While redistributing
+ the Work or Derivative Works thereof, You may choose to offer,
+ and charge a fee for, acceptance of support, warranty, indemnity,
+ or other liability obligations and/or rights consistent with this
+ License. However, in accepting such obligations, You may act only
+ on Your own behalf and on Your sole responsibility, not on behalf
+ of any other Contributor, and only if You agree to indemnify,
+ defend, and hold each Contributor harmless for any liability
+ incurred by, or claims asserted against, such Contributor by reason
+ of your accepting any such warranty or additional liability.
+
+ END OF TERMS AND CONDITIONS
+
+ APPENDIX: How to apply the Apache License to your work.
+
+ To apply the Apache License to your work, attach the following
+ boilerplate notice, with the fields enclosed by brackets "[]"
+ replaced with your own identifying information. (Don't include
+ the brackets!) The text should be enclosed in the appropriate
+ comment syntax for the file format. We also recommend that a
+ file or class name and description of purpose be included on the
+ same "printed page" as the copyright notice for easier
+ identification within third-party archives.
+
+ Copyright [yyyy] [name of copyright owner]
+
+ Licensed under the Apache License, Version 2.0 (the "License");
+ you may not use this file except in compliance with the License.
+ You may obtain a copy of the License at
+
+ http://www.apache.org/licenses/LICENSE-2.0
+
+ Unless required by applicable law or agreed to in writing, software
+ distributed under the License is distributed on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ See the License for the specific language governing permissions and
+ limitations under the License.~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+LICENSE - gitlab.com/gitlab-org/gitaly/vendor/github.com/kelseyhightower/envconfig
+Copyright (c) 2013 Kelsey Hightower
+
+Permission is hereby granted, free of charge, to any person obtaining a copy of
+this software and associated documentation files (the "Software"), to deal in
+the Software without restriction, including without limitation the rights to
+use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies
+of the Software, and to permit persons to whom the Software is furnished to do
+so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in all
+copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
+OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
+SOFTWARE.
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+LICENSE - gitlab.com/gitlab-org/gitaly/vendor/github.com/matttproud/golang_protobuf_extensions
+ Apache License
+ Version 2.0, January 2004
+ http://www.apache.org/licenses/
+
+ TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION
+
+ 1. Definitions.
+
+ "License" shall mean the terms and conditions for use, reproduction,
+ and distribution as defined by Sections 1 through 9 of this document.
+
+ "Licensor" shall mean the copyright owner or entity authorized by
+ the copyright owner that is granting the License.
+
+ "Legal Entity" shall mean the union of the acting entity and all
+ other entities that control, are controlled by, or are under common
+ control with that entity. For the purposes of this definition,
+ "control" means (i) the power, direct or indirect, to cause the
+ direction or management of such entity, whether by contract or
+ otherwise, or (ii) ownership of fifty percent (50%) or more of the
+ outstanding shares, or (iii) beneficial ownership of such entity.
+
+ "You" (or "Your") shall mean an individual or Legal Entity
+ exercising permissions granted by this License.
+
+ "Source" form shall mean the preferred form for making modifications,
+ including but not limited to software source code, documentation
+ source, and configuration files.
+
+ "Object" form shall mean any form resulting from mechanical
+ transformation or translation of a Source form, including but
+ not limited to compiled object code, generated documentation,
+ and conversions to other media types.
+
+ "Work" shall mean the work of authorship, whether in Source or
+ Object form, made available under the License, as indicated by a
+ copyright notice that is included in or attached to the work
+ (an example is provided in the Appendix below).
+
+ "Derivative Works" shall mean any work, whether in Source or Object
+ form, that is based on (or derived from) the Work and for which the
+ editorial revisions, annotations, elaborations, or other modifications
+ represent, as a whole, an original work of authorship. For the purposes
+ of this License, Derivative Works shall not include works that remain
+ separable from, or merely link (or bind by name) to the interfaces of,
+ the Work and Derivative Works thereof.
+
+ "Contribution" shall mean any work of authorship, including
+ the original version of the Work and any modifications or additions
+ to that Work or Derivative Works thereof, that is intentionally
+ submitted to Licensor for inclusion in the Work by the copyright owner
+ or by an individual or Legal Entity authorized to submit on behalf of
+ the copyright owner. For the purposes of this definition, "submitted"
+ means any form of electronic, verbal, or written communication sent
+ to the Licensor or its representatives, including but not limited to
+ communication on electronic mailing lists, source code control systems,
+ and issue tracking systems that are managed by, or on behalf of, the
+ Licensor for the purpose of discussing and improving the Work, but
+ excluding communication that is conspicuously marked or otherwise
+ designated in writing by the copyright owner as "Not a Contribution."
+
+ "Contributor" shall mean Licensor and any individual or Legal Entity
+ on behalf of whom a Contribution has been received by Licensor and
+ subsequently incorporated within the Work.
+
+ 2. Grant of Copyright License. Subject to the terms and conditions of
+ this License, each Contributor hereby grants to You a perpetual,
+ worldwide, non-exclusive, no-charge, royalty-free, irrevocable
+ copyright license to reproduce, prepare Derivative Works of,
+ publicly display, publicly perform, sublicense, and distribute the
+ Work and such Derivative Works in Source or Object form.
+
+ 3. Grant of Patent License. Subject to the terms and conditions of
+ this License, each Contributor hereby grants to You a perpetual,
+ worldwide, non-exclusive, no-charge, royalty-free, irrevocable
+ (except as stated in this section) patent license to make, have made,
+ use, offer to sell, sell, import, and otherwise transfer the Work,
+ where such license applies only to those patent claims licensable
+ by such Contributor that are necessarily infringed by their
+ Contribution(s) alone or by combination of their Contribution(s)
+ with the Work to which such Contribution(s) was submitted. If You
+ institute patent litigation against any entity (including a
+ cross-claim or counterclaim in a lawsuit) alleging that the Work
+ or a Contribution incorporated within the Work constitutes direct
+ or contributory patent infringement, then any patent licenses
+ granted to You under this License for that Work shall terminate
+ as of the date such litigation is filed.
+
+ 4. Redistribution. You may reproduce and distribute copies of the
+ Work or Derivative Works thereof in any medium, with or without
+ modifications, and in Source or Object form, provided that You
+ meet the following conditions:
+
+ (a) You must give any other recipients of the Work or
+ Derivative Works a copy of this License; and
+
+ (b) You must cause any modified files to carry prominent notices
+ stating that You changed the files; and
+
+ (c) You must retain, in the Source form of any Derivative Works
+ that You distribute, all copyright, patent, trademark, and
+ attribution notices from the Source form of the Work,
+ excluding those notices that do not pertain to any part of
+ the Derivative Works; and
+
+ (d) If the Work includes a "NOTICE" text file as part of its
+ distribution, then any Derivative Works that You distribute must
+ include a readable copy of the attribution notices contained
+ within such NOTICE file, excluding those notices that do not
+ pertain to any part of the Derivative Works, in at least one
+ of the following places: within a NOTICE text file distributed
+ as part of the Derivative Works; within the Source form or
+ documentation, if provided along with the Derivative Works; or,
+ within a display generated by the Derivative Works, if and
+ wherever such third-party notices normally appear. The contents
+ of the NOTICE file are for informational purposes only and
+ do not modify the License. You may add Your own attribution
+ notices within Derivative Works that You distribute, alongside
+ or as an addendum to the NOTICE text from the Work, provided
+ that such additional attribution notices cannot be construed
+ as modifying the License.
+
+ You may add Your own copyright statement to Your modifications and
+ may provide additional or different license terms and conditions
+ for use, reproduction, or distribution of Your modifications, or
+ for any such Derivative Works as a whole, provided Your use,
+ reproduction, and distribution of the Work otherwise complies with
+ the conditions stated in this License.
+
+ 5. Submission of Contributions. Unless You explicitly state otherwise,
+ any Contribution intentionally submitted for inclusion in the Work
+ by You to the Licensor shall be under the terms and conditions of
+ this License, without any additional terms or conditions.
+ Notwithstanding the above, nothing herein shall supersede or modify
+ the terms of any separate license agreement you may have executed
+ with Licensor regarding such Contributions.
+
+ 6. Trademarks. This License does not grant permission to use the trade
+ names, trademarks, service marks, or product names of the Licensor,
+ except as required for reasonable and customary use in describing the
+ origin of the Work and reproducing the content of the NOTICE file.
+
+ 7. Disclaimer of Warranty. Unless required by applicable law or
+ agreed to in writing, Licensor provides the Work (and each
+ Contributor provides its Contributions) on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
+ implied, including, without limitation, any warranties or conditions
+ of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A
+ PARTICULAR PURPOSE. You are solely responsible for determining the
+ appropriateness of using or redistributing the Work and assume any
+ risks associated with Your exercise of permissions under this License.
+
+ 8. Limitation of Liability. In no event and under no legal theory,
+ whether in tort (including negligence), contract, or otherwise,
+ unless required by applicable law (such as deliberate and grossly
+ negligent acts) or agreed to in writing, shall any Contributor be
+ liable to You for damages, including any direct, indirect, special,
+ incidental, or consequential damages of any character arising as a
+ result of this License or out of the use or inability to use the
+ Work (including but not limited to damages for loss of goodwill,
+ work stoppage, computer failure or malfunction, or any and all
+ other commercial damages or losses), even if such Contributor
+ has been advised of the possibility of such damages.
+
+ 9. Accepting Warranty or Additional Liability. While redistributing
+ the Work or Derivative Works thereof, You may choose to offer,
+ and charge a fee for, acceptance of support, warranty, indemnity,
+ or other liability obligations and/or rights consistent with this
+ License. However, in accepting such obligations, You may act only
+ on Your own behalf and on Your sole responsibility, not on behalf
+ of any other Contributor, and only if You agree to indemnify,
+ defend, and hold each Contributor harmless for any liability
+ incurred by, or claims asserted against, such Contributor by reason
+ of your accepting any such warranty or additional liability.
+
+ END OF TERMS AND CONDITIONS
+
+ APPENDIX: How to apply the Apache License to your work.
+
+ To apply the Apache License to your work, attach the following
+ boilerplate notice, with the fields enclosed by brackets "{}"
+ replaced with your own identifying information. (Don't include
+ the brackets!) The text should be enclosed in the appropriate
+ comment syntax for the file format. We also recommend that a
+ file or class name and description of purpose be included on the
+ same "printed page" as the copyright notice for easier
+ identification within third-party archives.
+
+ Copyright {yyyy} {name of copyright owner}
+
+ Licensed under the Apache License, Version 2.0 (the "License");
+ you may not use this file except in compliance with the License.
+ You may obtain a copy of the License at
+
+ http://www.apache.org/licenses/LICENSE-2.0
+
+ Unless required by applicable law or agreed to in writing, software
+ distributed under the License is distributed on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ See the License for the specific language governing permissions and
+ limitations under the License.
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+NOTICE - gitlab.com/gitlab-org/gitaly/vendor/github.com/matttproud/golang_protobuf_extensions
+Copyright 2012 Matt T. Proud (matt.proud@gmail.com)
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+LICENSE - gitlab.com/gitlab-org/gitaly/vendor/github.com/pmezard/go-difflib
+Copyright (c) 2013, Patrick Mezard
+All rights reserved.
+
+Redistribution and use in source and binary forms, with or without
+modification, are permitted provided that the following conditions are
+met:
+
+ Redistributions of source code must retain the above copyright
+notice, this list of conditions and the following disclaimer.
+ Redistributions in binary form must reproduce the above copyright
+notice, this list of conditions and the following disclaimer in the
+documentation and/or other materials provided with the distribution.
+ The names of its contributors may not be used to endorse or promote
+products derived from this software without specific prior written
+permission.
+
+THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS
+IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
+TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A
+PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
+HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
+SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED
+TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
+PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
+LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
+NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
+SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+LICENSE - gitlab.com/gitlab-org/gitaly/vendor/github.com/prometheus/client_golang
+ Apache License
+ Version 2.0, January 2004
+ http://www.apache.org/licenses/
+
+ TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION
+
+ 1. Definitions.
+
+ "License" shall mean the terms and conditions for use, reproduction,
+ and distribution as defined by Sections 1 through 9 of this document.
+
+ "Licensor" shall mean the copyright owner or entity authorized by
+ the copyright owner that is granting the License.
+
+ "Legal Entity" shall mean the union of the acting entity and all
+ other entities that control, are controlled by, or are under common
+ control with that entity. For the purposes of this definition,
+ "control" means (i) the power, direct or indirect, to cause the
+ direction or management of such entity, whether by contract or
+ otherwise, or (ii) ownership of fifty percent (50%) or more of the
+ outstanding shares, or (iii) beneficial ownership of such entity.
+
+ "You" (or "Your") shall mean an individual or Legal Entity
+ exercising permissions granted by this License.
+
+ "Source" form shall mean the preferred form for making modifications,
+ including but not limited to software source code, documentation
+ source, and configuration files.
+
+ "Object" form shall mean any form resulting from mechanical
+ transformation or translation of a Source form, including but
+ not limited to compiled object code, generated documentation,
+ and conversions to other media types.
+
+ "Work" shall mean the work of authorship, whether in Source or
+ Object form, made available under the License, as indicated by a
+ copyright notice that is included in or attached to the work
+ (an example is provided in the Appendix below).
+
+ "Derivative Works" shall mean any work, whether in Source or Object
+ form, that is based on (or derived from) the Work and for which the
+ editorial revisions, annotations, elaborations, or other modifications
+ represent, as a whole, an original work of authorship. For the purposes
+ of this License, Derivative Works shall not include works that remain
+ separable from, or merely link (or bind by name) to the interfaces of,
+ the Work and Derivative Works thereof.
+
+ "Contribution" shall mean any work of authorship, including
+ the original version of the Work and any modifications or additions
+ to that Work or Derivative Works thereof, that is intentionally
+ submitted to Licensor for inclusion in the Work by the copyright owner
+ or by an individual or Legal Entity authorized to submit on behalf of
+ the copyright owner. For the purposes of this definition, "submitted"
+ means any form of electronic, verbal, or written communication sent
+ to the Licensor or its representatives, including but not limited to
+ communication on electronic mailing lists, source code control systems,
+ and issue tracking systems that are managed by, or on behalf of, the
+ Licensor for the purpose of discussing and improving the Work, but
+ excluding communication that is conspicuously marked or otherwise
+ designated in writing by the copyright owner as "Not a Contribution."
+
+ "Contributor" shall mean Licensor and any individual or Legal Entity
+ on behalf of whom a Contribution has been received by Licensor and
+ subsequently incorporated within the Work.
+
+ 2. Grant of Copyright License. Subject to the terms and conditions of
+ this License, each Contributor hereby grants to You a perpetual,
+ worldwide, non-exclusive, no-charge, royalty-free, irrevocable
+ copyright license to reproduce, prepare Derivative Works of,
+ publicly display, publicly perform, sublicense, and distribute the
+ Work and such Derivative Works in Source or Object form.
+
+ 3. Grant of Patent License. Subject to the terms and conditions of
+ this License, each Contributor hereby grants to You a perpetual,
+ worldwide, non-exclusive, no-charge, royalty-free, irrevocable
+ (except as stated in this section) patent license to make, have made,
+ use, offer to sell, sell, import, and otherwise transfer the Work,
+ where such license applies only to those patent claims licensable
+ by such Contributor that are necessarily infringed by their
+ Contribution(s) alone or by combination of their Contribution(s)
+ with the Work to which such Contribution(s) was submitted. If You
+ institute patent litigation against any entity (including a
+ cross-claim or counterclaim in a lawsuit) alleging that the Work
+ or a Contribution incorporated within the Work constitutes direct
+ or contributory patent infringement, then any patent licenses
+ granted to You under this License for that Work shall terminate
+ as of the date such litigation is filed.
+
+ 4. Redistribution. You may reproduce and distribute copies of the
+ Work or Derivative Works thereof in any medium, with or without
+ modifications, and in Source or Object form, provided that You
+ meet the following conditions:
+
+ (a) You must give any other recipients of the Work or
+ Derivative Works a copy of this License; and
+
+ (b) You must cause any modified files to carry prominent notices
+ stating that You changed the files; and
+
+ (c) You must retain, in the Source form of any Derivative Works
+ that You distribute, all copyright, patent, trademark, and
+ attribution notices from the Source form of the Work,
+ excluding those notices that do not pertain to any part of
+ the Derivative Works; and
+
+ (d) If the Work includes a "NOTICE" text file as part of its
+ distribution, then any Derivative Works that You distribute must
+ include a readable copy of the attribution notices contained
+ within such NOTICE file, excluding those notices that do not
+ pertain to any part of the Derivative Works, in at least one
+ of the following places: within a NOTICE text file distributed
+ as part of the Derivative Works; within the Source form or
+ documentation, if provided along with the Derivative Works; or,
+ within a display generated by the Derivative Works, if and
+ wherever such third-party notices normally appear. The contents
+ of the NOTICE file are for informational purposes only and
+ do not modify the License. You may add Your own attribution
+ notices within Derivative Works that You distribute, alongside
+ or as an addendum to the NOTICE text from the Work, provided
+ that such additional attribution notices cannot be construed
+ as modifying the License.
+
+ You may add Your own copyright statement to Your modifications and
+ may provide additional or different license terms and conditions
+ for use, reproduction, or distribution of Your modifications, or
+ for any such Derivative Works as a whole, provided Your use,
+ reproduction, and distribution of the Work otherwise complies with
+ the conditions stated in this License.
+
+ 5. Submission of Contributions. Unless You explicitly state otherwise,
+ any Contribution intentionally submitted for inclusion in the Work
+ by You to the Licensor shall be under the terms and conditions of
+ this License, without any additional terms or conditions.
+ Notwithstanding the above, nothing herein shall supersede or modify
+ the terms of any separate license agreement you may have executed
+ with Licensor regarding such Contributions.
+
+ 6. Trademarks. This License does not grant permission to use the trade
+ names, trademarks, service marks, or product names of the Licensor,
+ except as required for reasonable and customary use in describing the
+ origin of the Work and reproducing the content of the NOTICE file.
+
+ 7. Disclaimer of Warranty. Unless required by applicable law or
+ agreed to in writing, Licensor provides the Work (and each
+ Contributor provides its Contributions) on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
+ implied, including, without limitation, any warranties or conditions
+ of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A
+ PARTICULAR PURPOSE. You are solely responsible for determining the
+ appropriateness of using or redistributing the Work and assume any
+ risks associated with Your exercise of permissions under this License.
+
+ 8. Limitation of Liability. In no event and under no legal theory,
+ whether in tort (including negligence), contract, or otherwise,
+ unless required by applicable law (such as deliberate and grossly
+ negligent acts) or agreed to in writing, shall any Contributor be
+ liable to You for damages, including any direct, indirect, special,
+ incidental, or consequential damages of any character arising as a
+ result of this License or out of the use or inability to use the
+ Work (including but not limited to damages for loss of goodwill,
+ work stoppage, computer failure or malfunction, or any and all
+ other commercial damages or losses), even if such Contributor
+ has been advised of the possibility of such damages.
+
+ 9. Accepting Warranty or Additional Liability. While redistributing
+ the Work or Derivative Works thereof, You may choose to offer,
+ and charge a fee for, acceptance of support, warranty, indemnity,
+ or other liability obligations and/or rights consistent with this
+ License. However, in accepting such obligations, You may act only
+ on Your own behalf and on Your sole responsibility, not on behalf
+ of any other Contributor, and only if You agree to indemnify,
+ defend, and hold each Contributor harmless for any liability
+ incurred by, or claims asserted against, such Contributor by reason
+ of your accepting any such warranty or additional liability.
+
+ END OF TERMS AND CONDITIONS
+
+ APPENDIX: How to apply the Apache License to your work.
+
+ To apply the Apache License to your work, attach the following
+ boilerplate notice, with the fields enclosed by brackets "[]"
+ replaced with your own identifying information. (Don't include
+ the brackets!) The text should be enclosed in the appropriate
+ comment syntax for the file format. We also recommend that a
+ file or class name and description of purpose be included on the
+ same "printed page" as the copyright notice for easier
+ identification within third-party archives.
+
+ Copyright [yyyy] [name of copyright owner]
+
+ Licensed under the Apache License, Version 2.0 (the "License");
+ you may not use this file except in compliance with the License.
+ You may obtain a copy of the License at
+
+ http://www.apache.org/licenses/LICENSE-2.0
+
+ Unless required by applicable law or agreed to in writing, software
+ distributed under the License is distributed on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ See the License for the specific language governing permissions and
+ limitations under the License.
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+NOTICE - gitlab.com/gitlab-org/gitaly/vendor/github.com/prometheus/client_golang
+Prometheus instrumentation library for Go applications
+Copyright 2012-2015 The Prometheus Authors
+
+This product includes software developed at
+SoundCloud Ltd. (http://soundcloud.com/).
+
+
+The following components are included in this product:
+
+perks - a fork of https://github.com/bmizerany/perks
+https://github.com/beorn7/perks
+Copyright 2013-2015 Blake Mizerany, Björn Rabenstein
+See https://github.com/beorn7/perks/blob/master/README.md for license details.
+
+Go support for Protocol Buffers - Google's data interchange format
+http://github.com/golang/protobuf/
+Copyright 2010 The Go Authors
+See source code for license details.
+
+Support for streaming Protocol Buffer messages for the Go language (golang).
+https://github.com/matttproud/golang_protobuf_extensions
+Copyright 2013 Matt T. Proud
+Licensed under the Apache License, Version 2.0
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+LICENSE - gitlab.com/gitlab-org/gitaly/vendor/github.com/prometheus/client_model
+ Apache License
+ Version 2.0, January 2004
+ http://www.apache.org/licenses/
+
+ TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION
+
+ 1. Definitions.
+
+ "License" shall mean the terms and conditions for use, reproduction,
+ and distribution as defined by Sections 1 through 9 of this document.
+
+ "Licensor" shall mean the copyright owner or entity authorized by
+ the copyright owner that is granting the License.
+
+ "Legal Entity" shall mean the union of the acting entity and all
+ other entities that control, are controlled by, or are under common
+ control with that entity. For the purposes of this definition,
+ "control" means (i) the power, direct or indirect, to cause the
+ direction or management of such entity, whether by contract or
+ otherwise, or (ii) ownership of fifty percent (50%) or more of the
+ outstanding shares, or (iii) beneficial ownership of such entity.
+
+ "You" (or "Your") shall mean an individual or Legal Entity
+ exercising permissions granted by this License.
+
+ "Source" form shall mean the preferred form for making modifications,
+ including but not limited to software source code, documentation
+ source, and configuration files.
+
+ "Object" form shall mean any form resulting from mechanical
+ transformation or translation of a Source form, including but
+ not limited to compiled object code, generated documentation,
+ and conversions to other media types.
+
+ "Work" shall mean the work of authorship, whether in Source or
+ Object form, made available under the License, as indicated by a
+ copyright notice that is included in or attached to the work
+ (an example is provided in the Appendix below).
+
+ "Derivative Works" shall mean any work, whether in Source or Object
+ form, that is based on (or derived from) the Work and for which the
+ editorial revisions, annotations, elaborations, or other modifications
+ represent, as a whole, an original work of authorship. For the purposes
+ of this License, Derivative Works shall not include works that remain
+ separable from, or merely link (or bind by name) to the interfaces of,
+ the Work and Derivative Works thereof.
+
+ "Contribution" shall mean any work of authorship, including
+ the original version of the Work and any modifications or additions
+ to that Work or Derivative Works thereof, that is intentionally
+ submitted to Licensor for inclusion in the Work by the copyright owner
+ or by an individual or Legal Entity authorized to submit on behalf of
+ the copyright owner. For the purposes of this definition, "submitted"
+ means any form of electronic, verbal, or written communication sent
+ to the Licensor or its representatives, including but not limited to
+ communication on electronic mailing lists, source code control systems,
+ and issue tracking systems that are managed by, or on behalf of, the
+ Licensor for the purpose of discussing and improving the Work, but
+ excluding communication that is conspicuously marked or otherwise
+ designated in writing by the copyright owner as "Not a Contribution."
+
+ "Contributor" shall mean Licensor and any individual or Legal Entity
+ on behalf of whom a Contribution has been received by Licensor and
+ subsequently incorporated within the Work.
+
+ 2. Grant of Copyright License. Subject to the terms and conditions of
+ this License, each Contributor hereby grants to You a perpetual,
+ worldwide, non-exclusive, no-charge, royalty-free, irrevocable
+ copyright license to reproduce, prepare Derivative Works of,
+ publicly display, publicly perform, sublicense, and distribute the
+ Work and such Derivative Works in Source or Object form.
+
+ 3. Grant of Patent License. Subject to the terms and conditions of
+ this License, each Contributor hereby grants to You a perpetual,
+ worldwide, non-exclusive, no-charge, royalty-free, irrevocable
+ (except as stated in this section) patent license to make, have made,
+ use, offer to sell, sell, import, and otherwise transfer the Work,
+ where such license applies only to those patent claims licensable
+ by such Contributor that are necessarily infringed by their
+ Contribution(s) alone or by combination of their Contribution(s)
+ with the Work to which such Contribution(s) was submitted. If You
+ institute patent litigation against any entity (including a
+ cross-claim or counterclaim in a lawsuit) alleging that the Work
+ or a Contribution incorporated within the Work constitutes direct
+ or contributory patent infringement, then any patent licenses
+ granted to You under this License for that Work shall terminate
+ as of the date such litigation is filed.
+
+ 4. Redistribution. You may reproduce and distribute copies of the
+ Work or Derivative Works thereof in any medium, with or without
+ modifications, and in Source or Object form, provided that You
+ meet the following conditions:
+
+ (a) You must give any other recipients of the Work or
+ Derivative Works a copy of this License; and
+
+ (b) You must cause any modified files to carry prominent notices
+ stating that You changed the files; and
+
+ (c) You must retain, in the Source form of any Derivative Works
+ that You distribute, all copyright, patent, trademark, and
+ attribution notices from the Source form of the Work,
+ excluding those notices that do not pertain to any part of
+ the Derivative Works; and
+
+ (d) If the Work includes a "NOTICE" text file as part of its
+ distribution, then any Derivative Works that You distribute must
+ include a readable copy of the attribution notices contained
+ within such NOTICE file, excluding those notices that do not
+ pertain to any part of the Derivative Works, in at least one
+ of the following places: within a NOTICE text file distributed
+ as part of the Derivative Works; within the Source form or
+ documentation, if provided along with the Derivative Works; or,
+ within a display generated by the Derivative Works, if and
+ wherever such third-party notices normally appear. The contents
+ of the NOTICE file are for informational purposes only and
+ do not modify the License. You may add Your own attribution
+ notices within Derivative Works that You distribute, alongside
+ or as an addendum to the NOTICE text from the Work, provided
+ that such additional attribution notices cannot be construed
+ as modifying the License.
+
+ You may add Your own copyright statement to Your modifications and
+ may provide additional or different license terms and conditions
+ for use, reproduction, or distribution of Your modifications, or
+ for any such Derivative Works as a whole, provided Your use,
+ reproduction, and distribution of the Work otherwise complies with
+ the conditions stated in this License.
+
+ 5. Submission of Contributions. Unless You explicitly state otherwise,
+ any Contribution intentionally submitted for inclusion in the Work
+ by You to the Licensor shall be under the terms and conditions of
+ this License, without any additional terms or conditions.
+ Notwithstanding the above, nothing herein shall supersede or modify
+ the terms of any separate license agreement you may have executed
+ with Licensor regarding such Contributions.
+
+ 6. Trademarks. This License does not grant permission to use the trade
+ names, trademarks, service marks, or product names of the Licensor,
+ except as required for reasonable and customary use in describing the
+ origin of the Work and reproducing the content of the NOTICE file.
+
+ 7. Disclaimer of Warranty. Unless required by applicable law or
+ agreed to in writing, Licensor provides the Work (and each
+ Contributor provides its Contributions) on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
+ implied, including, without limitation, any warranties or conditions
+ of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A
+ PARTICULAR PURPOSE. You are solely responsible for determining the
+ appropriateness of using or redistributing the Work and assume any
+ risks associated with Your exercise of permissions under this License.
+
+ 8. Limitation of Liability. In no event and under no legal theory,
+ whether in tort (including negligence), contract, or otherwise,
+ unless required by applicable law (such as deliberate and grossly
+ negligent acts) or agreed to in writing, shall any Contributor be
+ liable to You for damages, including any direct, indirect, special,
+ incidental, or consequential damages of any character arising as a
+ result of this License or out of the use or inability to use the
+ Work (including but not limited to damages for loss of goodwill,
+ work stoppage, computer failure or malfunction, or any and all
+ other commercial damages or losses), even if such Contributor
+ has been advised of the possibility of such damages.
+
+ 9. Accepting Warranty or Additional Liability. While redistributing
+ the Work or Derivative Works thereof, You may choose to offer,
+ and charge a fee for, acceptance of support, warranty, indemnity,
+ or other liability obligations and/or rights consistent with this
+ License. However, in accepting such obligations, You may act only
+ on Your own behalf and on Your sole responsibility, not on behalf
+ of any other Contributor, and only if You agree to indemnify,
+ defend, and hold each Contributor harmless for any liability
+ incurred by, or claims asserted against, such Contributor by reason
+ of your accepting any such warranty or additional liability.
+
+ END OF TERMS AND CONDITIONS
+
+ APPENDIX: How to apply the Apache License to your work.
+
+ To apply the Apache License to your work, attach the following
+ boilerplate notice, with the fields enclosed by brackets "[]"
+ replaced with your own identifying information. (Don't include
+ the brackets!) The text should be enclosed in the appropriate
+ comment syntax for the file format. We also recommend that a
+ file or class name and description of purpose be included on the
+ same "printed page" as the copyright notice for easier
+ identification within third-party archives.
+
+ Copyright [yyyy] [name of copyright owner]
+
+ Licensed under the Apache License, Version 2.0 (the "License");
+ you may not use this file except in compliance with the License.
+ You may obtain a copy of the License at
+
+ http://www.apache.org/licenses/LICENSE-2.0
+
+ Unless required by applicable law or agreed to in writing, software
+ distributed under the License is distributed on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ See the License for the specific language governing permissions and
+ limitations under the License.
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+NOTICE - gitlab.com/gitlab-org/gitaly/vendor/github.com/prometheus/client_model
+Data model artifacts for Prometheus.
+Copyright 2012-2015 The Prometheus Authors
+
+This product includes software developed at
+SoundCloud Ltd. (http://soundcloud.com/).
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+LICENSE - gitlab.com/gitlab-org/gitaly/vendor/github.com/prometheus/common
+ Apache License
+ Version 2.0, January 2004
+ http://www.apache.org/licenses/
+
+ TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION
+
+ 1. Definitions.
+
+ "License" shall mean the terms and conditions for use, reproduction,
+ and distribution as defined by Sections 1 through 9 of this document.
+
+ "Licensor" shall mean the copyright owner or entity authorized by
+ the copyright owner that is granting the License.
+
+ "Legal Entity" shall mean the union of the acting entity and all
+ other entities that control, are controlled by, or are under common
+ control with that entity. For the purposes of this definition,
+ "control" means (i) the power, direct or indirect, to cause the
+ direction or management of such entity, whether by contract or
+ otherwise, or (ii) ownership of fifty percent (50%) or more of the
+ outstanding shares, or (iii) beneficial ownership of such entity.
+
+ "You" (or "Your") shall mean an individual or Legal Entity
+ exercising permissions granted by this License.
+
+ "Source" form shall mean the preferred form for making modifications,
+ including but not limited to software source code, documentation
+ source, and configuration files.
+
+ "Object" form shall mean any form resulting from mechanical
+ transformation or translation of a Source form, including but
+ not limited to compiled object code, generated documentation,
+ and conversions to other media types.
+
+ "Work" shall mean the work of authorship, whether in Source or
+ Object form, made available under the License, as indicated by a
+ copyright notice that is included in or attached to the work
+ (an example is provided in the Appendix below).
+
+ "Derivative Works" shall mean any work, whether in Source or Object
+ form, that is based on (or derived from) the Work and for which the
+ editorial revisions, annotations, elaborations, or other modifications
+ represent, as a whole, an original work of authorship. For the purposes
+ of this License, Derivative Works shall not include works that remain
+ separable from, or merely link (or bind by name) to the interfaces of,
+ the Work and Derivative Works thereof.
+
+ "Contribution" shall mean any work of authorship, including
+ the original version of the Work and any modifications or additions
+ to that Work or Derivative Works thereof, that is intentionally
+ submitted to Licensor for inclusion in the Work by the copyright owner
+ or by an individual or Legal Entity authorized to submit on behalf of
+ the copyright owner. For the purposes of this definition, "submitted"
+ means any form of electronic, verbal, or written communication sent
+ to the Licensor or its representatives, including but not limited to
+ communication on electronic mailing lists, source code control systems,
+ and issue tracking systems that are managed by, or on behalf of, the
+ Licensor for the purpose of discussing and improving the Work, but
+ excluding communication that is conspicuously marked or otherwise
+ designated in writing by the copyright owner as "Not a Contribution."
+
+ "Contributor" shall mean Licensor and any individual or Legal Entity
+ on behalf of whom a Contribution has been received by Licensor and
+ subsequently incorporated within the Work.
+
+ 2. Grant of Copyright License. Subject to the terms and conditions of
+ this License, each Contributor hereby grants to You a perpetual,
+ worldwide, non-exclusive, no-charge, royalty-free, irrevocable
+ copyright license to reproduce, prepare Derivative Works of,
+ publicly display, publicly perform, sublicense, and distribute the
+ Work and such Derivative Works in Source or Object form.
+
+ 3. Grant of Patent License. Subject to the terms and conditions of
+ this License, each Contributor hereby grants to You a perpetual,
+ worldwide, non-exclusive, no-charge, royalty-free, irrevocable
+ (except as stated in this section) patent license to make, have made,
+ use, offer to sell, sell, import, and otherwise transfer the Work,
+ where such license applies only to those patent claims licensable
+ by such Contributor that are necessarily infringed by their
+ Contribution(s) alone or by combination of their Contribution(s)
+ with the Work to which such Contribution(s) was submitted. If You
+ institute patent litigation against any entity (including a
+ cross-claim or counterclaim in a lawsuit) alleging that the Work
+ or a Contribution incorporated within the Work constitutes direct
+ or contributory patent infringement, then any patent licenses
+ granted to You under this License for that Work shall terminate
+ as of the date such litigation is filed.
+
+ 4. Redistribution. You may reproduce and distribute copies of the
+ Work or Derivative Works thereof in any medium, with or without
+ modifications, and in Source or Object form, provided that You
+ meet the following conditions:
+
+ (a) You must give any other recipients of the Work or
+ Derivative Works a copy of this License; and
+
+ (b) You must cause any modified files to carry prominent notices
+ stating that You changed the files; and
+
+ (c) You must retain, in the Source form of any Derivative Works
+ that You distribute, all copyright, patent, trademark, and
+ attribution notices from the Source form of the Work,
+ excluding those notices that do not pertain to any part of
+ the Derivative Works; and
+
+ (d) If the Work includes a "NOTICE" text file as part of its
+ distribution, then any Derivative Works that You distribute must
+ include a readable copy of the attribution notices contained
+ within such NOTICE file, excluding those notices that do not
+ pertain to any part of the Derivative Works, in at least one
+ of the following places: within a NOTICE text file distributed
+ as part of the Derivative Works; within the Source form or
+ documentation, if provided along with the Derivative Works; or,
+ within a display generated by the Derivative Works, if and
+ wherever such third-party notices normally appear. The contents
+ of the NOTICE file are for informational purposes only and
+ do not modify the License. You may add Your own attribution
+ notices within Derivative Works that You distribute, alongside
+ or as an addendum to the NOTICE text from the Work, provided
+ that such additional attribution notices cannot be construed
+ as modifying the License.
+
+ You may add Your own copyright statement to Your modifications and
+ may provide additional or different license terms and conditions
+ for use, reproduction, or distribution of Your modifications, or
+ for any such Derivative Works as a whole, provided Your use,
+ reproduction, and distribution of the Work otherwise complies with
+ the conditions stated in this License.
+
+ 5. Submission of Contributions. Unless You explicitly state otherwise,
+ any Contribution intentionally submitted for inclusion in the Work
+ by You to the Licensor shall be under the terms and conditions of
+ this License, without any additional terms or conditions.
+ Notwithstanding the above, nothing herein shall supersede or modify
+ the terms of any separate license agreement you may have executed
+ with Licensor regarding such Contributions.
+
+ 6. Trademarks. This License does not grant permission to use the trade
+ names, trademarks, service marks, or product names of the Licensor,
+ except as required for reasonable and customary use in describing the
+ origin of the Work and reproducing the content of the NOTICE file.
+
+ 7. Disclaimer of Warranty. Unless required by applicable law or
+ agreed to in writing, Licensor provides the Work (and each
+ Contributor provides its Contributions) on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
+ implied, including, without limitation, any warranties or conditions
+ of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A
+ PARTICULAR PURPOSE. You are solely responsible for determining the
+ appropriateness of using or redistributing the Work and assume any
+ risks associated with Your exercise of permissions under this License.
+
+ 8. Limitation of Liability. In no event and under no legal theory,
+ whether in tort (including negligence), contract, or otherwise,
+ unless required by applicable law (such as deliberate and grossly
+ negligent acts) or agreed to in writing, shall any Contributor be
+ liable to You for damages, including any direct, indirect, special,
+ incidental, or consequential damages of any character arising as a
+ result of this License or out of the use or inability to use the
+ Work (including but not limited to damages for loss of goodwill,
+ work stoppage, computer failure or malfunction, or any and all
+ other commercial damages or losses), even if such Contributor
+ has been advised of the possibility of such damages.
+
+ 9. Accepting Warranty or Additional Liability. While redistributing
+ the Work or Derivative Works thereof, You may choose to offer,
+ and charge a fee for, acceptance of support, warranty, indemnity,
+ or other liability obligations and/or rights consistent with this
+ License. However, in accepting such obligations, You may act only
+ on Your own behalf and on Your sole responsibility, not on behalf
+ of any other Contributor, and only if You agree to indemnify,
+ defend, and hold each Contributor harmless for any liability
+ incurred by, or claims asserted against, such Contributor by reason
+ of your accepting any such warranty or additional liability.
+
+ END OF TERMS AND CONDITIONS
+
+ APPENDIX: How to apply the Apache License to your work.
+
+ To apply the Apache License to your work, attach the following
+ boilerplate notice, with the fields enclosed by brackets "[]"
+ replaced with your own identifying information. (Don't include
+ the brackets!) The text should be enclosed in the appropriate
+ comment syntax for the file format. We also recommend that a
+ file or class name and description of purpose be included on the
+ same "printed page" as the copyright notice for easier
+ identification within third-party archives.
+
+ Copyright [yyyy] [name of copyright owner]
+
+ Licensed under the Apache License, Version 2.0 (the "License");
+ you may not use this file except in compliance with the License.
+ You may obtain a copy of the License at
+
+ http://www.apache.org/licenses/LICENSE-2.0
+
+ Unless required by applicable law or agreed to in writing, software
+ distributed under the License is distributed on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ See the License for the specific language governing permissions and
+ limitations under the License.
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+NOTICE - gitlab.com/gitlab-org/gitaly/vendor/github.com/prometheus/common
+Common libraries shared by Prometheus Go components.
+Copyright 2015 The Prometheus Authors
+
+This product includes software developed at
+SoundCloud Ltd. (http://soundcloud.com/).
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+LICENSE - gitlab.com/gitlab-org/gitaly/vendor/github.com/prometheus/procfs
+ Apache License
+ Version 2.0, January 2004
+ http://www.apache.org/licenses/
+
+ TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION
+
+ 1. Definitions.
+
+ "License" shall mean the terms and conditions for use, reproduction,
+ and distribution as defined by Sections 1 through 9 of this document.
+
+ "Licensor" shall mean the copyright owner or entity authorized by
+ the copyright owner that is granting the License.
+
+ "Legal Entity" shall mean the union of the acting entity and all
+ other entities that control, are controlled by, or are under common
+ control with that entity. For the purposes of this definition,
+ "control" means (i) the power, direct or indirect, to cause the
+ direction or management of such entity, whether by contract or
+ otherwise, or (ii) ownership of fifty percent (50%) or more of the
+ outstanding shares, or (iii) beneficial ownership of such entity.
+
+ "You" (or "Your") shall mean an individual or Legal Entity
+ exercising permissions granted by this License.
+
+ "Source" form shall mean the preferred form for making modifications,
+ including but not limited to software source code, documentation
+ source, and configuration files.
+
+ "Object" form shall mean any form resulting from mechanical
+ transformation or translation of a Source form, including but
+ not limited to compiled object code, generated documentation,
+ and conversions to other media types.
+
+ "Work" shall mean the work of authorship, whether in Source or
+ Object form, made available under the License, as indicated by a
+ copyright notice that is included in or attached to the work
+ (an example is provided in the Appendix below).
+
+ "Derivative Works" shall mean any work, whether in Source or Object
+ form, that is based on (or derived from) the Work and for which the
+ editorial revisions, annotations, elaborations, or other modifications
+ represent, as a whole, an original work of authorship. For the purposes
+ of this License, Derivative Works shall not include works that remain
+ separable from, or merely link (or bind by name) to the interfaces of,
+ the Work and Derivative Works thereof.
+
+ "Contribution" shall mean any work of authorship, including
+ the original version of the Work and any modifications or additions
+ to that Work or Derivative Works thereof, that is intentionally
+ submitted to Licensor for inclusion in the Work by the copyright owner
+ or by an individual or Legal Entity authorized to submit on behalf of
+ the copyright owner. For the purposes of this definition, "submitted"
+ means any form of electronic, verbal, or written communication sent
+ to the Licensor or its representatives, including but not limited to
+ communication on electronic mailing lists, source code control systems,
+ and issue tracking systems that are managed by, or on behalf of, the
+ Licensor for the purpose of discussing and improving the Work, but
+ excluding communication that is conspicuously marked or otherwise
+ designated in writing by the copyright owner as "Not a Contribution."
+
+ "Contributor" shall mean Licensor and any individual or Legal Entity
+ on behalf of whom a Contribution has been received by Licensor and
+ subsequently incorporated within the Work.
+
+ 2. Grant of Copyright License. Subject to the terms and conditions of
+ this License, each Contributor hereby grants to You a perpetual,
+ worldwide, non-exclusive, no-charge, royalty-free, irrevocable
+ copyright license to reproduce, prepare Derivative Works of,
+ publicly display, publicly perform, sublicense, and distribute the
+ Work and such Derivative Works in Source or Object form.
+
+ 3. Grant of Patent License. Subject to the terms and conditions of
+ this License, each Contributor hereby grants to You a perpetual,
+ worldwide, non-exclusive, no-charge, royalty-free, irrevocable
+ (except as stated in this section) patent license to make, have made,
+ use, offer to sell, sell, import, and otherwise transfer the Work,
+ where such license applies only to those patent claims licensable
+ by such Contributor that are necessarily infringed by their
+ Contribution(s) alone or by combination of their Contribution(s)
+ with the Work to which such Contribution(s) was submitted. If You
+ institute patent litigation against any entity (including a
+ cross-claim or counterclaim in a lawsuit) alleging that the Work
+ or a Contribution incorporated within the Work constitutes direct
+ or contributory patent infringement, then any patent licenses
+ granted to You under this License for that Work shall terminate
+ as of the date such litigation is filed.
+
+ 4. Redistribution. You may reproduce and distribute copies of the
+ Work or Derivative Works thereof in any medium, with or without
+ modifications, and in Source or Object form, provided that You
+ meet the following conditions:
+
+ (a) You must give any other recipients of the Work or
+ Derivative Works a copy of this License; and
+
+ (b) You must cause any modified files to carry prominent notices
+ stating that You changed the files; and
+
+ (c) You must retain, in the Source form of any Derivative Works
+ that You distribute, all copyright, patent, trademark, and
+ attribution notices from the Source form of the Work,
+ excluding those notices that do not pertain to any part of
+ the Derivative Works; and
+
+ (d) If the Work includes a "NOTICE" text file as part of its
+ distribution, then any Derivative Works that You distribute must
+ include a readable copy of the attribution notices contained
+ within such NOTICE file, excluding those notices that do not
+ pertain to any part of the Derivative Works, in at least one
+ of the following places: within a NOTICE text file distributed
+ as part of the Derivative Works; within the Source form or
+ documentation, if provided along with the Derivative Works; or,
+ within a display generated by the Derivative Works, if and
+ wherever such third-party notices normally appear. The contents
+ of the NOTICE file are for informational purposes only and
+ do not modify the License. You may add Your own attribution
+ notices within Derivative Works that You distribute, alongside
+ or as an addendum to the NOTICE text from the Work, provided
+ that such additional attribution notices cannot be construed
+ as modifying the License.
+
+ You may add Your own copyright statement to Your modifications and
+ may provide additional or different license terms and conditions
+ for use, reproduction, or distribution of Your modifications, or
+ for any such Derivative Works as a whole, provided Your use,
+ reproduction, and distribution of the Work otherwise complies with
+ the conditions stated in this License.
+
+ 5. Submission of Contributions. Unless You explicitly state otherwise,
+ any Contribution intentionally submitted for inclusion in the Work
+ by You to the Licensor shall be under the terms and conditions of
+ this License, without any additional terms or conditions.
+ Notwithstanding the above, nothing herein shall supersede or modify
+ the terms of any separate license agreement you may have executed
+ with Licensor regarding such Contributions.
+
+ 6. Trademarks. This License does not grant permission to use the trade
+ names, trademarks, service marks, or product names of the Licensor,
+ except as required for reasonable and customary use in describing the
+ origin of the Work and reproducing the content of the NOTICE file.
+
+ 7. Disclaimer of Warranty. Unless required by applicable law or
+ agreed to in writing, Licensor provides the Work (and each
+ Contributor provides its Contributions) on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
+ implied, including, without limitation, any warranties or conditions
+ of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A
+ PARTICULAR PURPOSE. You are solely responsible for determining the
+ appropriateness of using or redistributing the Work and assume any
+ risks associated with Your exercise of permissions under this License.
+
+ 8. Limitation of Liability. In no event and under no legal theory,
+ whether in tort (including negligence), contract, or otherwise,
+ unless required by applicable law (such as deliberate and grossly
+ negligent acts) or agreed to in writing, shall any Contributor be
+ liable to You for damages, including any direct, indirect, special,
+ incidental, or consequential damages of any character arising as a
+ result of this License or out of the use or inability to use the
+ Work (including but not limited to damages for loss of goodwill,
+ work stoppage, computer failure or malfunction, or any and all
+ other commercial damages or losses), even if such Contributor
+ has been advised of the possibility of such damages.
+
+ 9. Accepting Warranty or Additional Liability. While redistributing
+ the Work or Derivative Works thereof, You may choose to offer,
+ and charge a fee for, acceptance of support, warranty, indemnity,
+ or other liability obligations and/or rights consistent with this
+ License. However, in accepting such obligations, You may act only
+ on Your own behalf and on Your sole responsibility, not on behalf
+ of any other Contributor, and only if You agree to indemnify,
+ defend, and hold each Contributor harmless for any liability
+ incurred by, or claims asserted against, such Contributor by reason
+ of your accepting any such warranty or additional liability.
+
+ END OF TERMS AND CONDITIONS
+
+ APPENDIX: How to apply the Apache License to your work.
+
+ To apply the Apache License to your work, attach the following
+ boilerplate notice, with the fields enclosed by brackets "[]"
+ replaced with your own identifying information. (Don't include
+ the brackets!) The text should be enclosed in the appropriate
+ comment syntax for the file format. We also recommend that a
+ file or class name and description of purpose be included on the
+ same "printed page" as the copyright notice for easier
+ identification within third-party archives.
+
+ Copyright [yyyy] [name of copyright owner]
+
+ Licensed under the Apache License, Version 2.0 (the "License");
+ you may not use this file except in compliance with the License.
+ You may obtain a copy of the License at
+
+ http://www.apache.org/licenses/LICENSE-2.0
+
+ Unless required by applicable law or agreed to in writing, software
+ distributed under the License is distributed on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ See the License for the specific language governing permissions and
+ limitations under the License.
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+NOTICE - gitlab.com/gitlab-org/gitaly/vendor/github.com/prometheus/procfs
+procfs provides functions to retrieve system, kernel and process
+metrics from the pseudo-filesystem proc.
+
+Copyright 2014-2015 The Prometheus Authors
+
+This product includes software developed at
+SoundCloud Ltd. (http://soundcloud.com/).
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+LICENSE - gitlab.com/gitlab-org/gitaly/vendor/github.com/sirupsen/logrus
+The MIT License (MIT)
+
+Copyright (c) 2014 Simon Eskildsen
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
+OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
+THE SOFTWARE.
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+LICENSE - gitlab.com/gitlab-org/gitaly/vendor/github.com/stretchr/testify
+Copyright (c) 2012 - 2013 Mat Ryer and Tyler Bunnell
+
+Please consider promoting this project if you find it useful.
+
+Permission is hereby granted, free of charge, to any person
+obtaining a copy of this software and associated documentation
+files (the "Software"), to deal in the Software without restriction,
+including without limitation the rights to use, copy, modify, merge,
+publish, distribute, sublicense, and/or sell copies of the Software,
+and to permit persons to whom the Software is furnished to do so,
+subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included
+in all copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
+EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES
+OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
+IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM,
+DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT
+OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE
+OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+LICENSE - gitlab.com/gitlab-org/gitaly/vendor/gitlab.com/gitlab-org/gitaly-proto
+The MIT License (MIT)
+
+Copyright (c) 2016-2017 GitLab B.V.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
+OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
+THE SOFTWARE.
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+LICENSE - gitlab.com/gitlab-org/gitaly/vendor/golang.org/x/crypto
+Copyright (c) 2009 The Go Authors. All rights reserved.
+
+Redistribution and use in source and binary forms, with or without
+modification, are permitted provided that the following conditions are
+met:
+
+ * Redistributions of source code must retain the above copyright
+notice, this list of conditions and the following disclaimer.
+ * Redistributions in binary form must reproduce the above
+copyright notice, this list of conditions and the following disclaimer
+in the documentation and/or other materials provided with the
+distribution.
+ * Neither the name of Google Inc. nor the names of its
+contributors may be used to endorse or promote products derived from
+this software without specific prior written permission.
+
+THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
+A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
+OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
+SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
+LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+PATENTS - gitlab.com/gitlab-org/gitaly/vendor/golang.org/x/crypto
+Additional IP Rights Grant (Patents)
+
+"This implementation" means the copyrightable works distributed by
+Google as part of the Go project.
+
+Google hereby grants to You a perpetual, worldwide, non-exclusive,
+no-charge, royalty-free, irrevocable (except as stated in this section)
+patent license to make, have made, use, offer to sell, sell, import,
+transfer and otherwise run, modify and propagate the contents of this
+implementation of Go, where such license applies only to those patent
+claims, both currently owned or controlled by Google and acquired in
+the future, licensable by Google that are necessarily infringed by this
+implementation of Go. This grant does not include claims that would be
+infringed only as a consequence of further modification of this
+implementation. If you or your agent or exclusive licensee institute or
+order or agree to the institution of patent litigation against any
+entity (including a cross-claim or counterclaim in a lawsuit) alleging
+that this implementation of Go or any code incorporated within this
+implementation of Go constitutes direct or contributory patent
+infringement, or inducement of patent infringement, then any patent
+rights granted to you under this License for this implementation of Go
+shall terminate as of the date such litigation is filed.
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+LICENSE - gitlab.com/gitlab-org/gitaly/vendor/golang.org/x/net
+Copyright (c) 2009 The Go Authors. All rights reserved.
+
+Redistribution and use in source and binary forms, with or without
+modification, are permitted provided that the following conditions are
+met:
+
+ * Redistributions of source code must retain the above copyright
+notice, this list of conditions and the following disclaimer.
+ * Redistributions in binary form must reproduce the above
+copyright notice, this list of conditions and the following disclaimer
+in the documentation and/or other materials provided with the
+distribution.
+ * Neither the name of Google Inc. nor the names of its
+contributors may be used to endorse or promote products derived from
+this software without specific prior written permission.
+
+THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
+A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
+OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
+SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
+LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+PATENTS - gitlab.com/gitlab-org/gitaly/vendor/golang.org/x/net
+Additional IP Rights Grant (Patents)
+
+"This implementation" means the copyrightable works distributed by
+Google as part of the Go project.
+
+Google hereby grants to You a perpetual, worldwide, non-exclusive,
+no-charge, royalty-free, irrevocable (except as stated in this section)
+patent license to make, have made, use, offer to sell, sell, import,
+transfer and otherwise run, modify and propagate the contents of this
+implementation of Go, where such license applies only to those patent
+claims, both currently owned or controlled by Google and acquired in
+the future, licensable by Google that are necessarily infringed by this
+implementation of Go. This grant does not include claims that would be
+infringed only as a consequence of further modification of this
+implementation. If you or your agent or exclusive licensee institute or
+order or agree to the institution of patent litigation against any
+entity (including a cross-claim or counterclaim in a lawsuit) alleging
+that this implementation of Go or any code incorporated within this
+implementation of Go constitutes direct or contributory patent
+infringement, or inducement of patent infringement, then any patent
+rights granted to you under this License for this implementation of Go
+shall terminate as of the date such litigation is filed.
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+LICENSE - gitlab.com/gitlab-org/gitaly/vendor/golang.org/x/sync
+Copyright (c) 2009 The Go Authors. All rights reserved.
+
+Redistribution and use in source and binary forms, with or without
+modification, are permitted provided that the following conditions are
+met:
+
+ * Redistributions of source code must retain the above copyright
+notice, this list of conditions and the following disclaimer.
+ * Redistributions in binary form must reproduce the above
+copyright notice, this list of conditions and the following disclaimer
+in the documentation and/or other materials provided with the
+distribution.
+ * Neither the name of Google Inc. nor the names of its
+contributors may be used to endorse or promote products derived from
+this software without specific prior written permission.
+
+THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
+A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
+OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
+SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
+LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+PATENTS - gitlab.com/gitlab-org/gitaly/vendor/golang.org/x/sync
+Additional IP Rights Grant (Patents)
+
+"This implementation" means the copyrightable works distributed by
+Google as part of the Go project.
+
+Google hereby grants to You a perpetual, worldwide, non-exclusive,
+no-charge, royalty-free, irrevocable (except as stated in this section)
+patent license to make, have made, use, offer to sell, sell, import,
+transfer and otherwise run, modify and propagate the contents of this
+implementation of Go, where such license applies only to those patent
+claims, both currently owned or controlled by Google and acquired in
+the future, licensable by Google that are necessarily infringed by this
+implementation of Go. This grant does not include claims that would be
+infringed only as a consequence of further modification of this
+implementation. If you or your agent or exclusive licensee institute or
+order or agree to the institution of patent litigation against any
+entity (including a cross-claim or counterclaim in a lawsuit) alleging
+that this implementation of Go or any code incorporated within this
+implementation of Go constitutes direct or contributory patent
+infringement, or inducement of patent infringement, then any patent
+rights granted to you under this License for this implementation of Go
+shall terminate as of the date such litigation is filed.
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+LICENSE - gitlab.com/gitlab-org/gitaly/vendor/golang.org/x/sys
+Copyright (c) 2009 The Go Authors. All rights reserved.
+
+Redistribution and use in source and binary forms, with or without
+modification, are permitted provided that the following conditions are
+met:
+
+ * Redistributions of source code must retain the above copyright
+notice, this list of conditions and the following disclaimer.
+ * Redistributions in binary form must reproduce the above
+copyright notice, this list of conditions and the following disclaimer
+in the documentation and/or other materials provided with the
+distribution.
+ * Neither the name of Google Inc. nor the names of its
+contributors may be used to endorse or promote products derived from
+this software without specific prior written permission.
+
+THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
+A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
+OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
+SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
+LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+PATENTS - gitlab.com/gitlab-org/gitaly/vendor/golang.org/x/sys
+Additional IP Rights Grant (Patents)
+
+"This implementation" means the copyrightable works distributed by
+Google as part of the Go project.
+
+Google hereby grants to You a perpetual, worldwide, non-exclusive,
+no-charge, royalty-free, irrevocable (except as stated in this section)
+patent license to make, have made, use, offer to sell, sell, import,
+transfer and otherwise run, modify and propagate the contents of this
+implementation of Go, where such license applies only to those patent
+claims, both currently owned or controlled by Google and acquired in
+the future, licensable by Google that are necessarily infringed by this
+implementation of Go. This grant does not include claims that would be
+infringed only as a consequence of further modification of this
+implementation. If you or your agent or exclusive licensee institute or
+order or agree to the institution of patent litigation against any
+entity (including a cross-claim or counterclaim in a lawsuit) alleging
+that this implementation of Go or any code incorporated within this
+implementation of Go constitutes direct or contributory patent
+infringement, or inducement of patent infringement, then any patent
+rights granted to you under this License for this implementation of Go
+shall terminate as of the date such litigation is filed.
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+LICENSE - gitlab.com/gitlab-org/gitaly/vendor/golang.org/x/text
+Copyright (c) 2009 The Go Authors. All rights reserved.
+
+Redistribution and use in source and binary forms, with or without
+modification, are permitted provided that the following conditions are
+met:
+
+ * Redistributions of source code must retain the above copyright
+notice, this list of conditions and the following disclaimer.
+ * Redistributions in binary form must reproduce the above
+copyright notice, this list of conditions and the following disclaimer
+in the documentation and/or other materials provided with the
+distribution.
+ * Neither the name of Google Inc. nor the names of its
+contributors may be used to endorse or promote products derived from
+this software without specific prior written permission.
+
+THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
+A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
+OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
+SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
+LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+PATENTS - gitlab.com/gitlab-org/gitaly/vendor/golang.org/x/text
+Additional IP Rights Grant (Patents)
+
+"This implementation" means the copyrightable works distributed by
+Google as part of the Go project.
+
+Google hereby grants to You a perpetual, worldwide, non-exclusive,
+no-charge, royalty-free, irrevocable (except as stated in this section)
+patent license to make, have made, use, offer to sell, sell, import,
+transfer and otherwise run, modify and propagate the contents of this
+implementation of Go, where such license applies only to those patent
+claims, both currently owned or controlled by Google and acquired in
+the future, licensable by Google that are necessarily infringed by this
+implementation of Go. This grant does not include claims that would be
+infringed only as a consequence of further modification of this
+implementation. If you or your agent or exclusive licensee institute or
+order or agree to the institution of patent litigation against any
+entity (including a cross-claim or counterclaim in a lawsuit) alleging
+that this implementation of Go or any code incorporated within this
+implementation of Go constitutes direct or contributory patent
+infringement, or inducement of patent infringement, then any patent
+rights granted to you under this License for this implementation of Go
+shall terminate as of the date such litigation is filed.
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+LICENSE - gitlab.com/gitlab-org/gitaly/vendor/google.golang.org/genproto
+
+ Apache License
+ Version 2.0, January 2004
+ http://www.apache.org/licenses/
+
+ TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION
+
+ 1. Definitions.
+
+ "License" shall mean the terms and conditions for use, reproduction,
+ and distribution as defined by Sections 1 through 9 of this document.
+
+ "Licensor" shall mean the copyright owner or entity authorized by
+ the copyright owner that is granting the License.
+
+ "Legal Entity" shall mean the union of the acting entity and all
+ other entities that control, are controlled by, or are under common
+ control with that entity. For the purposes of this definition,
+ "control" means (i) the power, direct or indirect, to cause the
+ direction or management of such entity, whether by contract or
+ otherwise, or (ii) ownership of fifty percent (50%) or more of the
+ outstanding shares, or (iii) beneficial ownership of such entity.
+
+ "You" (or "Your") shall mean an individual or Legal Entity
+ exercising permissions granted by this License.
+
+ "Source" form shall mean the preferred form for making modifications,
+ including but not limited to software source code, documentation
+ source, and configuration files.
+
+ "Object" form shall mean any form resulting from mechanical
+ transformation or translation of a Source form, including but
+ not limited to compiled object code, generated documentation,
+ and conversions to other media types.
+
+ "Work" shall mean the work of authorship, whether in Source or
+ Object form, made available under the License, as indicated by a
+ copyright notice that is included in or attached to the work
+ (an example is provided in the Appendix below).
+
+ "Derivative Works" shall mean any work, whether in Source or Object
+ form, that is based on (or derived from) the Work and for which the
+ editorial revisions, annotations, elaborations, or other modifications
+ represent, as a whole, an original work of authorship. For the purposes
+ of this License, Derivative Works shall not include works that remain
+ separable from, or merely link (or bind by name) to the interfaces of,
+ the Work and Derivative Works thereof.
+
+ "Contribution" shall mean any work of authorship, including
+ the original version of the Work and any modifications or additions
+ to that Work or Derivative Works thereof, that is intentionally
+ submitted to Licensor for inclusion in the Work by the copyright owner
+ or by an individual or Legal Entity authorized to submit on behalf of
+ the copyright owner. For the purposes of this definition, "submitted"
+ means any form of electronic, verbal, or written communication sent
+ to the Licensor or its representatives, including but not limited to
+ communication on electronic mailing lists, source code control systems,
+ and issue tracking systems that are managed by, or on behalf of, the
+ Licensor for the purpose of discussing and improving the Work, but
+ excluding communication that is conspicuously marked or otherwise
+ designated in writing by the copyright owner as "Not a Contribution."
+
+ "Contributor" shall mean Licensor and any individual or Legal Entity
+ on behalf of whom a Contribution has been received by Licensor and
+ subsequently incorporated within the Work.
+
+ 2. Grant of Copyright License. Subject to the terms and conditions of
+ this License, each Contributor hereby grants to You a perpetual,
+ worldwide, non-exclusive, no-charge, royalty-free, irrevocable
+ copyright license to reproduce, prepare Derivative Works of,
+ publicly display, publicly perform, sublicense, and distribute the
+ Work and such Derivative Works in Source or Object form.
+
+ 3. Grant of Patent License. Subject to the terms and conditions of
+ this License, each Contributor hereby grants to You a perpetual,
+ worldwide, non-exclusive, no-charge, royalty-free, irrevocable
+ (except as stated in this section) patent license to make, have made,
+ use, offer to sell, sell, import, and otherwise transfer the Work,
+ where such license applies only to those patent claims licensable
+ by such Contributor that are necessarily infringed by their
+ Contribution(s) alone or by combination of their Contribution(s)
+ with the Work to which such Contribution(s) was submitted. If You
+ institute patent litigation against any entity (including a
+ cross-claim or counterclaim in a lawsuit) alleging that the Work
+ or a Contribution incorporated within the Work constitutes direct
+ or contributory patent infringement, then any patent licenses
+ granted to You under this License for that Work shall terminate
+ as of the date such litigation is filed.
+
+ 4. Redistribution. You may reproduce and distribute copies of the
+ Work or Derivative Works thereof in any medium, with or without
+ modifications, and in Source or Object form, provided that You
+ meet the following conditions:
+
+ (a) You must give any other recipients of the Work or
+ Derivative Works a copy of this License; and
+
+ (b) You must cause any modified files to carry prominent notices
+ stating that You changed the files; and
+
+ (c) You must retain, in the Source form of any Derivative Works
+ that You distribute, all copyright, patent, trademark, and
+ attribution notices from the Source form of the Work,
+ excluding those notices that do not pertain to any part of
+ the Derivative Works; and
+
+ (d) If the Work includes a "NOTICE" text file as part of its
+ distribution, then any Derivative Works that You distribute must
+ include a readable copy of the attribution notices contained
+ within such NOTICE file, excluding those notices that do not
+ pertain to any part of the Derivative Works, in at least one
+ of the following places: within a NOTICE text file distributed
+ as part of the Derivative Works; within the Source form or
+ documentation, if provided along with the Derivative Works; or,
+ within a display generated by the Derivative Works, if and
+ wherever such third-party notices normally appear. The contents
+ of the NOTICE file are for informational purposes only and
+ do not modify the License. You may add Your own attribution
+ notices within Derivative Works that You distribute, alongside
+ or as an addendum to the NOTICE text from the Work, provided
+ that such additional attribution notices cannot be construed
+ as modifying the License.
+
+ You may add Your own copyright statement to Your modifications and
+ may provide additional or different license terms and conditions
+ for use, reproduction, or distribution of Your modifications, or
+ for any such Derivative Works as a whole, provided Your use,
+ reproduction, and distribution of the Work otherwise complies with
+ the conditions stated in this License.
+
+ 5. Submission of Contributions. Unless You explicitly state otherwise,
+ any Contribution intentionally submitted for inclusion in the Work
+ by You to the Licensor shall be under the terms and conditions of
+ this License, without any additional terms or conditions.
+ Notwithstanding the above, nothing herein shall supersede or modify
+ the terms of any separate license agreement you may have executed
+ with Licensor regarding such Contributions.
+
+ 6. Trademarks. This License does not grant permission to use the trade
+ names, trademarks, service marks, or product names of the Licensor,
+ except as required for reasonable and customary use in describing the
+ origin of the Work and reproducing the content of the NOTICE file.
+
+ 7. Disclaimer of Warranty. Unless required by applicable law or
+ agreed to in writing, Licensor provides the Work (and each
+ Contributor provides its Contributions) on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
+ implied, including, without limitation, any warranties or conditions
+ of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A
+ PARTICULAR PURPOSE. You are solely responsible for determining the
+ appropriateness of using or redistributing the Work and assume any
+ risks associated with Your exercise of permissions under this License.
+
+ 8. Limitation of Liability. In no event and under no legal theory,
+ whether in tort (including negligence), contract, or otherwise,
+ unless required by applicable law (such as deliberate and grossly
+ negligent acts) or agreed to in writing, shall any Contributor be
+ liable to You for damages, including any direct, indirect, special,
+ incidental, or consequential damages of any character arising as a
+ result of this License or out of the use or inability to use the
+ Work (including but not limited to damages for loss of goodwill,
+ work stoppage, computer failure or malfunction, or any and all
+ other commercial damages or losses), even if such Contributor
+ has been advised of the possibility of such damages.
+
+ 9. Accepting Warranty or Additional Liability. While redistributing
+ the Work or Derivative Works thereof, You may choose to offer,
+ and charge a fee for, acceptance of support, warranty, indemnity,
+ or other liability obligations and/or rights consistent with this
+ License. However, in accepting such obligations, You may act only
+ on Your own behalf and on Your sole responsibility, not on behalf
+ of any other Contributor, and only if You agree to indemnify,
+ defend, and hold each Contributor harmless for any liability
+ incurred by, or claims asserted against, such Contributor by reason
+ of your accepting any such warranty or additional liability.
+
+ END OF TERMS AND CONDITIONS
+
+ APPENDIX: How to apply the Apache License to your work.
+
+ To apply the Apache License to your work, attach the following
+ boilerplate notice, with the fields enclosed by brackets "[]"
+ replaced with your own identifying information. (Don't include
+ the brackets!) The text should be enclosed in the appropriate
+ comment syntax for the file format. We also recommend that a
+ file or class name and description of purpose be included on the
+ same "printed page" as the copyright notice for easier
+ identification within third-party archives.
+
+ Copyright [yyyy] [name of copyright owner]
+
+ Licensed under the Apache License, Version 2.0 (the "License");
+ you may not use this file except in compliance with the License.
+ You may obtain a copy of the License at
+
+ http://www.apache.org/licenses/LICENSE-2.0
+
+ Unless required by applicable law or agreed to in writing, software
+ distributed under the License is distributed on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ See the License for the specific language governing permissions and
+ limitations under the License.
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+LICENSE - gitlab.com/gitlab-org/gitaly/vendor/google.golang.org/grpc
+
+ Apache License
+ Version 2.0, January 2004
+ http://www.apache.org/licenses/
+
+ TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION
+
+ 1. Definitions.
+
+ "License" shall mean the terms and conditions for use, reproduction,
+ and distribution as defined by Sections 1 through 9 of this document.
+
+ "Licensor" shall mean the copyright owner or entity authorized by
+ the copyright owner that is granting the License.
+
+ "Legal Entity" shall mean the union of the acting entity and all
+ other entities that control, are controlled by, or are under common
+ control with that entity. For the purposes of this definition,
+ "control" means (i) the power, direct or indirect, to cause the
+ direction or management of such entity, whether by contract or
+ otherwise, or (ii) ownership of fifty percent (50%) or more of the
+ outstanding shares, or (iii) beneficial ownership of such entity.
+
+ "You" (or "Your") shall mean an individual or Legal Entity
+ exercising permissions granted by this License.
+
+ "Source" form shall mean the preferred form for making modifications,
+ including but not limited to software source code, documentation
+ source, and configuration files.
+
+ "Object" form shall mean any form resulting from mechanical
+ transformation or translation of a Source form, including but
+ not limited to compiled object code, generated documentation,
+ and conversions to other media types.
+
+ "Work" shall mean the work of authorship, whether in Source or
+ Object form, made available under the License, as indicated by a
+ copyright notice that is included in or attached to the work
+ (an example is provided in the Appendix below).
+
+ "Derivative Works" shall mean any work, whether in Source or Object
+ form, that is based on (or derived from) the Work and for which the
+ editorial revisions, annotations, elaborations, or other modifications
+ represent, as a whole, an original work of authorship. For the purposes
+ of this License, Derivative Works shall not include works that remain
+ separable from, or merely link (or bind by name) to the interfaces of,
+ the Work and Derivative Works thereof.
+
+ "Contribution" shall mean any work of authorship, including
+ the original version of the Work and any modifications or additions
+ to that Work or Derivative Works thereof, that is intentionally
+ submitted to Licensor for inclusion in the Work by the copyright owner
+ or by an individual or Legal Entity authorized to submit on behalf of
+ the copyright owner. For the purposes of this definition, "submitted"
+ means any form of electronic, verbal, or written communication sent
+ to the Licensor or its representatives, including but not limited to
+ communication on electronic mailing lists, source code control systems,
+ and issue tracking systems that are managed by, or on behalf of, the
+ Licensor for the purpose of discussing and improving the Work, but
+ excluding communication that is conspicuously marked or otherwise
+ designated in writing by the copyright owner as "Not a Contribution."
+
+ "Contributor" shall mean Licensor and any individual or Legal Entity
+ on behalf of whom a Contribution has been received by Licensor and
+ subsequently incorporated within the Work.
+
+ 2. Grant of Copyright License. Subject to the terms and conditions of
+ this License, each Contributor hereby grants to You a perpetual,
+ worldwide, non-exclusive, no-charge, royalty-free, irrevocable
+ copyright license to reproduce, prepare Derivative Works of,
+ publicly display, publicly perform, sublicense, and distribute the
+ Work and such Derivative Works in Source or Object form.
+
+ 3. Grant of Patent License. Subject to the terms and conditions of
+ this License, each Contributor hereby grants to You a perpetual,
+ worldwide, non-exclusive, no-charge, royalty-free, irrevocable
+ (except as stated in this section) patent license to make, have made,
+ use, offer to sell, sell, import, and otherwise transfer the Work,
+ where such license applies only to those patent claims licensable
+ by such Contributor that are necessarily infringed by their
+ Contribution(s) alone or by combination of their Contribution(s)
+ with the Work to which such Contribution(s) was submitted. If You
+ institute patent litigation against any entity (including a
+ cross-claim or counterclaim in a lawsuit) alleging that the Work
+ or a Contribution incorporated within the Work constitutes direct
+ or contributory patent infringement, then any patent licenses
+ granted to You under this License for that Work shall terminate
+ as of the date such litigation is filed.
+
+ 4. Redistribution. You may reproduce and distribute copies of the
+ Work or Derivative Works thereof in any medium, with or without
+ modifications, and in Source or Object form, provided that You
+ meet the following conditions:
+
+ (a) You must give any other recipients of the Work or
+ Derivative Works a copy of this License; and
+
+ (b) You must cause any modified files to carry prominent notices
+ stating that You changed the files; and
+
+ (c) You must retain, in the Source form of any Derivative Works
+ that You distribute, all copyright, patent, trademark, and
+ attribution notices from the Source form of the Work,
+ excluding those notices that do not pertain to any part of
+ the Derivative Works; and
+
+ (d) If the Work includes a "NOTICE" text file as part of its
+ distribution, then any Derivative Works that You distribute must
+ include a readable copy of the attribution notices contained
+ within such NOTICE file, excluding those notices that do not
+ pertain to any part of the Derivative Works, in at least one
+ of the following places: within a NOTICE text file distributed
+ as part of the Derivative Works; within the Source form or
+ documentation, if provided along with the Derivative Works; or,
+ within a display generated by the Derivative Works, if and
+ wherever such third-party notices normally appear. The contents
+ of the NOTICE file are for informational purposes only and
+ do not modify the License. You may add Your own attribution
+ notices within Derivative Works that You distribute, alongside
+ or as an addendum to the NOTICE text from the Work, provided
+ that such additional attribution notices cannot be construed
+ as modifying the License.
+
+ You may add Your own copyright statement to Your modifications and
+ may provide additional or different license terms and conditions
+ for use, reproduction, or distribution of Your modifications, or
+ for any such Derivative Works as a whole, provided Your use,
+ reproduction, and distribution of the Work otherwise complies with
+ the conditions stated in this License.
+
+ 5. Submission of Contributions. Unless You explicitly state otherwise,
+ any Contribution intentionally submitted for inclusion in the Work
+ by You to the Licensor shall be under the terms and conditions of
+ this License, without any additional terms or conditions.
+ Notwithstanding the above, nothing herein shall supersede or modify
+ the terms of any separate license agreement you may have executed
+ with Licensor regarding such Contributions.
+
+ 6. Trademarks. This License does not grant permission to use the trade
+ names, trademarks, service marks, or product names of the Licensor,
+ except as required for reasonable and customary use in describing the
+ origin of the Work and reproducing the content of the NOTICE file.
+
+ 7. Disclaimer of Warranty. Unless required by applicable law or
+ agreed to in writing, Licensor provides the Work (and each
+ Contributor provides its Contributions) on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
+ implied, including, without limitation, any warranties or conditions
+ of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A
+ PARTICULAR PURPOSE. You are solely responsible for determining the
+ appropriateness of using or redistributing the Work and assume any
+ risks associated with Your exercise of permissions under this License.
+
+ 8. Limitation of Liability. In no event and under no legal theory,
+ whether in tort (including negligence), contract, or otherwise,
+ unless required by applicable law (such as deliberate and grossly
+ negligent acts) or agreed to in writing, shall any Contributor be
+ liable to You for damages, including any direct, indirect, special,
+ incidental, or consequential damages of any character arising as a
+ result of this License or out of the use or inability to use the
+ Work (including but not limited to damages for loss of goodwill,
+ work stoppage, computer failure or malfunction, or any and all
+ other commercial damages or losses), even if such Contributor
+ has been advised of the possibility of such damages.
+
+ 9. Accepting Warranty or Additional Liability. While redistributing
+ the Work or Derivative Works thereof, You may choose to offer,
+ and charge a fee for, acceptance of support, warranty, indemnity,
+ or other liability obligations and/or rights consistent with this
+ License. However, in accepting such obligations, You may act only
+ on Your own behalf and on Your sole responsibility, not on behalf
+ of any other Contributor, and only if You agree to indemnify,
+ defend, and hold each Contributor harmless for any liability
+ incurred by, or claims asserted against, such Contributor by reason
+ of your accepting any such warranty or additional liability.
+
+ END OF TERMS AND CONDITIONS
+
+ APPENDIX: How to apply the Apache License to your work.
+
+ To apply the Apache License to your work, attach the following
+ boilerplate notice, with the fields enclosed by brackets "[]"
+ replaced with your own identifying information. (Don't include
+ the brackets!) The text should be enclosed in the appropriate
+ comment syntax for the file format. We also recommend that a
+ file or class name and description of purpose be included on the
+ same "printed page" as the copyright notice for easier
+ identification within third-party archives.
+
+ Copyright [yyyy] [name of copyright owner]
+
+ Licensed under the Apache License, Version 2.0 (the "License");
+ you may not use this file except in compliance with the License.
+ You may obtain a copy of the License at
+
+ http://www.apache.org/licenses/LICENSE-2.0
+
+ Unless required by applicable law or agreed to in writing, software
+ distributed under the License is distributed on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ See the License for the specific language governing permissions and
+ limitations under the License.
+
diff --git a/vendor/gitlab.com/gitlab-org/gitaly/auth/rpccredentials.go b/vendor/gitlab.com/gitlab-org/gitaly/auth/rpccredentials.go
new file mode 100644
index 00000000..cbe94c25
--- /dev/null
+++ b/vendor/gitlab.com/gitlab-org/gitaly/auth/rpccredentials.go
@@ -0,0 +1,25 @@
+package gitalyauth
+
+import (
+ "encoding/base64"
+
+ "golang.org/x/net/context"
+ "google.golang.org/grpc/credentials"
+)
+
+// RPCCredentials can be used with grpc.WithPerRPCCredentials to create a
+// grpc.DialOption that inserts the supplied token for authentication
+// with a Gitaly server.
+func RPCCredentials(token string) credentials.PerRPCCredentials {
+ return &rpcCredentials{token: base64.StdEncoding.EncodeToString([]byte(token))}
+}
+
+type rpcCredentials struct {
+ token string
+}
+
+func (*rpcCredentials) RequireTransportSecurity() bool { return false }
+
+func (rc *rpcCredentials) GetRequestMetadata(context.Context, ...string) (map[string]string, error) {
+ return map[string]string{"authorization": "Bearer " + rc.token}, nil
+}
diff --git a/vendor/gitlab.com/gitlab-org/gitaly/auth/token.go b/vendor/gitlab.com/gitlab-org/gitaly/auth/token.go
new file mode 100644
index 00000000..fc13c5be
--- /dev/null
+++ b/vendor/gitlab.com/gitlab-org/gitaly/auth/token.go
@@ -0,0 +1,45 @@
+package gitalyauth
+
+import (
+ "crypto/subtle"
+ "encoding/base64"
+
+ "github.com/grpc-ecosystem/go-grpc-middleware/auth"
+ "golang.org/x/net/context"
+ "google.golang.org/grpc/codes"
+ "google.golang.org/grpc/status"
+)
+
+var (
+ errUnauthenticated = status.Errorf(codes.Unauthenticated, "authentication required")
+ errDenied = status.Errorf(codes.PermissionDenied, "permission denied")
+)
+
+// CheckToken checks the 'authentication' header of incoming gRPC
+// metadata in ctx. It returns nil if and only if the token matches
+// secret.
+func CheckToken(ctx context.Context, secret string) error {
+ if len(secret) == 0 {
+ panic("CheckToken: secret may not be empty")
+ }
+
+ encodedToken, err := grpc_auth.AuthFromMD(ctx, "bearer")
+ if err != nil {
+ return errUnauthenticated
+ }
+
+ token, err := base64.StdEncoding.DecodeString(encodedToken)
+ if err != nil {
+ return errUnauthenticated
+ }
+
+ if !tokensEqual(token, []byte(secret)) {
+ return errDenied
+ }
+
+ return nil
+}
+
+func tokensEqual(tok1, tok2 []byte) bool {
+ return subtle.ConstantTimeCompare(tok1, tok2) == 1
+}
diff --git a/vendor/google.golang.org/grpc/health/grpc_health_v1/health.pb.go b/vendor/google.golang.org/grpc/health/grpc_health_v1/health.pb.go
new file mode 100644
index 00000000..fdcbb9e0
--- /dev/null
+++ b/vendor/google.golang.org/grpc/health/grpc_health_v1/health.pb.go
@@ -0,0 +1,190 @@
+// Code generated by protoc-gen-go. DO NOT EDIT.
+// source: grpc_health_v1/health.proto
+
+/*
+Package grpc_health_v1 is a generated protocol buffer package.
+
+It is generated from these files:
+ grpc_health_v1/health.proto
+
+It has these top-level messages:
+ HealthCheckRequest
+ HealthCheckResponse
+*/
+package grpc_health_v1
+
+import proto "github.com/golang/protobuf/proto"
+import fmt "fmt"
+import math "math"
+
+import (
+ context "golang.org/x/net/context"
+ grpc "google.golang.org/grpc"
+)
+
+// Reference imports to suppress errors if they are not otherwise used.
+var _ = proto.Marshal
+var _ = fmt.Errorf
+var _ = math.Inf
+
+// This is a compile-time assertion to ensure that this generated file
+// is compatible with the proto package it is being compiled against.
+// A compilation error at this line likely means your copy of the
+// proto package needs to be updated.
+const _ = proto.ProtoPackageIsVersion2 // please upgrade the proto package
+
+type HealthCheckResponse_ServingStatus int32
+
+const (
+ HealthCheckResponse_UNKNOWN HealthCheckResponse_ServingStatus = 0
+ HealthCheckResponse_SERVING HealthCheckResponse_ServingStatus = 1
+ HealthCheckResponse_NOT_SERVING HealthCheckResponse_ServingStatus = 2
+)
+
+var HealthCheckResponse_ServingStatus_name = map[int32]string{
+ 0: "UNKNOWN",
+ 1: "SERVING",
+ 2: "NOT_SERVING",
+}
+var HealthCheckResponse_ServingStatus_value = map[string]int32{
+ "UNKNOWN": 0,
+ "SERVING": 1,
+ "NOT_SERVING": 2,
+}
+
+func (x HealthCheckResponse_ServingStatus) String() string {
+ return proto.EnumName(HealthCheckResponse_ServingStatus_name, int32(x))
+}
+func (HealthCheckResponse_ServingStatus) EnumDescriptor() ([]byte, []int) {
+ return fileDescriptor0, []int{1, 0}
+}
+
+type HealthCheckRequest struct {
+ Service string `protobuf:"bytes,1,opt,name=service" json:"service,omitempty"`
+}
+
+func (m *HealthCheckRequest) Reset() { *m = HealthCheckRequest{} }
+func (m *HealthCheckRequest) String() string { return proto.CompactTextString(m) }
+func (*HealthCheckRequest) ProtoMessage() {}
+func (*HealthCheckRequest) Descriptor() ([]byte, []int) { return fileDescriptor0, []int{0} }
+
+func (m *HealthCheckRequest) GetService() string {
+ if m != nil {
+ return m.Service
+ }
+ return ""
+}
+
+type HealthCheckResponse struct {
+ Status HealthCheckResponse_ServingStatus `protobuf:"varint,1,opt,name=status,enum=grpc.health.v1.HealthCheckResponse_ServingStatus" json:"status,omitempty"`
+}
+
+func (m *HealthCheckResponse) Reset() { *m = HealthCheckResponse{} }
+func (m *HealthCheckResponse) String() string { return proto.CompactTextString(m) }
+func (*HealthCheckResponse) ProtoMessage() {}
+func (*HealthCheckResponse) Descriptor() ([]byte, []int) { return fileDescriptor0, []int{1} }
+
+func (m *HealthCheckResponse) GetStatus() HealthCheckResponse_ServingStatus {
+ if m != nil {
+ return m.Status
+ }
+ return HealthCheckResponse_UNKNOWN
+}
+
+func init() {
+ proto.RegisterType((*HealthCheckRequest)(nil), "grpc.health.v1.HealthCheckRequest")
+ proto.RegisterType((*HealthCheckResponse)(nil), "grpc.health.v1.HealthCheckResponse")
+ proto.RegisterEnum("grpc.health.v1.HealthCheckResponse_ServingStatus", HealthCheckResponse_ServingStatus_name, HealthCheckResponse_ServingStatus_value)
+}
+
+// Reference imports to suppress errors if they are not otherwise used.
+var _ context.Context
+var _ grpc.ClientConn
+
+// This is a compile-time assertion to ensure that this generated file
+// is compatible with the grpc package it is being compiled against.
+const _ = grpc.SupportPackageIsVersion4
+
+// Client API for Health service
+
+type HealthClient interface {
+ Check(ctx context.Context, in *HealthCheckRequest, opts ...grpc.CallOption) (*HealthCheckResponse, error)
+}
+
+type healthClient struct {
+ cc *grpc.ClientConn
+}
+
+func NewHealthClient(cc *grpc.ClientConn) HealthClient {
+ return &healthClient{cc}
+}
+
+func (c *healthClient) Check(ctx context.Context, in *HealthCheckRequest, opts ...grpc.CallOption) (*HealthCheckResponse, error) {
+ out := new(HealthCheckResponse)
+ err := grpc.Invoke(ctx, "/grpc.health.v1.Health/Check", in, out, c.cc, opts...)
+ if err != nil {
+ return nil, err
+ }
+ return out, nil
+}
+
+// Server API for Health service
+
+type HealthServer interface {
+ Check(context.Context, *HealthCheckRequest) (*HealthCheckResponse, error)
+}
+
+func RegisterHealthServer(s *grpc.Server, srv HealthServer) {
+ s.RegisterService(&_Health_serviceDesc, srv)
+}
+
+func _Health_Check_Handler(srv interface{}, ctx context.Context, dec func(interface{}) error, interceptor grpc.UnaryServerInterceptor) (interface{}, error) {
+ in := new(HealthCheckRequest)
+ if err := dec(in); err != nil {
+ return nil, err
+ }
+ if interceptor == nil {
+ return srv.(HealthServer).Check(ctx, in)
+ }
+ info := &grpc.UnaryServerInfo{
+ Server: srv,
+ FullMethod: "/grpc.health.v1.Health/Check",
+ }
+ handler := func(ctx context.Context, req interface{}) (interface{}, error) {
+ return srv.(HealthServer).Check(ctx, req.(*HealthCheckRequest))
+ }
+ return interceptor(ctx, in, info, handler)
+}
+
+var _Health_serviceDesc = grpc.ServiceDesc{
+ ServiceName: "grpc.health.v1.Health",
+ HandlerType: (*HealthServer)(nil),
+ Methods: []grpc.MethodDesc{
+ {
+ MethodName: "Check",
+ Handler: _Health_Check_Handler,
+ },
+ },
+ Streams: []grpc.StreamDesc{},
+ Metadata: "grpc_health_v1/health.proto",
+}
+
+func init() { proto.RegisterFile("grpc_health_v1/health.proto", fileDescriptor0) }
+
+var fileDescriptor0 = []byte{
+ // 213 bytes of a gzipped FileDescriptorProto
+ 0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0xff, 0xe2, 0x92, 0x4e, 0x2f, 0x2a, 0x48,
+ 0x8e, 0xcf, 0x48, 0x4d, 0xcc, 0x29, 0xc9, 0x88, 0x2f, 0x33, 0xd4, 0x87, 0xb0, 0xf4, 0x0a, 0x8a,
+ 0xf2, 0x4b, 0xf2, 0x85, 0xf8, 0x40, 0x92, 0x7a, 0x50, 0xa1, 0x32, 0x43, 0x25, 0x3d, 0x2e, 0x21,
+ 0x0f, 0x30, 0xc7, 0x39, 0x23, 0x35, 0x39, 0x3b, 0x28, 0xb5, 0xb0, 0x34, 0xb5, 0xb8, 0x44, 0x48,
+ 0x82, 0x8b, 0xbd, 0x38, 0xb5, 0xa8, 0x2c, 0x33, 0x39, 0x55, 0x82, 0x51, 0x81, 0x51, 0x83, 0x33,
+ 0x08, 0xc6, 0x55, 0x9a, 0xc3, 0xc8, 0x25, 0x8c, 0xa2, 0xa1, 0xb8, 0x20, 0x3f, 0xaf, 0x38, 0x55,
+ 0xc8, 0x93, 0x8b, 0xad, 0xb8, 0x24, 0xb1, 0xa4, 0xb4, 0x18, 0xac, 0x81, 0xcf, 0xc8, 0x50, 0x0f,
+ 0xd5, 0x22, 0x3d, 0x2c, 0x9a, 0xf4, 0x82, 0x41, 0x86, 0xe6, 0xa5, 0x07, 0x83, 0x35, 0x06, 0x41,
+ 0x0d, 0x50, 0xb2, 0xe2, 0xe2, 0x45, 0x91, 0x10, 0xe2, 0xe6, 0x62, 0x0f, 0xf5, 0xf3, 0xf6, 0xf3,
+ 0x0f, 0xf7, 0x13, 0x60, 0x00, 0x71, 0x82, 0x5d, 0x83, 0xc2, 0x3c, 0xfd, 0xdc, 0x05, 0x18, 0x85,
+ 0xf8, 0xb9, 0xb8, 0xfd, 0xfc, 0x43, 0xe2, 0x61, 0x02, 0x4c, 0x46, 0x51, 0x5c, 0x6c, 0x10, 0x8b,
+ 0x84, 0x02, 0xb8, 0x58, 0xc1, 0x96, 0x09, 0x29, 0xe1, 0x75, 0x09, 0xd8, 0xbf, 0x52, 0xca, 0x44,
+ 0xb8, 0x36, 0x89, 0x0d, 0x1c, 0x82, 0xc6, 0x80, 0x00, 0x00, 0x00, 0xff, 0xff, 0x53, 0x2b, 0x65,
+ 0x20, 0x60, 0x01, 0x00, 0x00,
+}
diff --git a/vendor/google.golang.org/grpc/health/grpc_health_v1/health.proto b/vendor/google.golang.org/grpc/health/grpc_health_v1/health.proto
new file mode 100644
index 00000000..6072fdc3
--- /dev/null
+++ b/vendor/google.golang.org/grpc/health/grpc_health_v1/health.proto
@@ -0,0 +1,34 @@
+// Copyright 2017 gRPC authors.
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+syntax = "proto3";
+
+package grpc.health.v1;
+
+message HealthCheckRequest {
+ string service = 1;
+}
+
+message HealthCheckResponse {
+ enum ServingStatus {
+ UNKNOWN = 0;
+ SERVING = 1;
+ NOT_SERVING = 2;
+ }
+ ServingStatus status = 1;
+}
+
+service Health{
+ rpc Check(HealthCheckRequest) returns (HealthCheckResponse);
+}
diff --git a/vendor/google.golang.org/grpc/health/health.go b/vendor/google.golang.org/grpc/health/health.go
new file mode 100644
index 00000000..30a78667
--- /dev/null
+++ b/vendor/google.golang.org/grpc/health/health.go
@@ -0,0 +1,72 @@
+/*
+ *
+ * Copyright 2017 gRPC authors.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ *
+ */
+
+//go:generate protoc --go_out=plugins=grpc:. grpc_health_v1/health.proto
+
+// Package health provides some utility functions to health-check a server. The implementation
+// is based on protobuf. Users need to write their own implementations if other IDLs are used.
+package health
+
+import (
+ "sync"
+
+ "golang.org/x/net/context"
+ "google.golang.org/grpc/codes"
+ healthpb "google.golang.org/grpc/health/grpc_health_v1"
+ "google.golang.org/grpc/status"
+)
+
+// Server implements `service Health`.
+type Server struct {
+ mu sync.Mutex
+ // statusMap stores the serving status of the services this Server monitors.
+ statusMap map[string]healthpb.HealthCheckResponse_ServingStatus
+}
+
+// NewServer returns a new Server.
+func NewServer() *Server {
+ return &Server{
+ statusMap: make(map[string]healthpb.HealthCheckResponse_ServingStatus),
+ }
+}
+
+// Check implements `service Health`.
+func (s *Server) Check(ctx context.Context, in *healthpb.HealthCheckRequest) (*healthpb.HealthCheckResponse, error) {
+ s.mu.Lock()
+ defer s.mu.Unlock()
+ if in.Service == "" {
+ // check the server overall health status.
+ return &healthpb.HealthCheckResponse{
+ Status: healthpb.HealthCheckResponse_SERVING,
+ }, nil
+ }
+ if status, ok := s.statusMap[in.Service]; ok {
+ return &healthpb.HealthCheckResponse{
+ Status: status,
+ }, nil
+ }
+ return nil, status.Error(codes.NotFound, "unknown service")
+}
+
+// SetServingStatus is called when need to reset the serving status of a service
+// or insert a new service entry into the statusMap.
+func (s *Server) SetServingStatus(service string, status healthpb.HealthCheckResponse_ServingStatus) {
+ s.mu.Lock()
+ s.statusMap[service] = status
+ s.mu.Unlock()
+}
diff --git a/vendor/vendor.json b/vendor/vendor.json
index 54ea1697..ab76c48c 100644
--- a/vendor/vendor.json
+++ b/vendor/vendor.json
@@ -8,6 +8,12 @@
"revision": "4c0e84591b9aa9e6dcfdf3e020114cd81f89d5f9"
},
{
+ "checksumSHA1": "eG45Hg4ZnB4b1KuqsMknc5eAx4A=",
+ "path": "github.com/golang/protobuf/jsonpb",
+ "revision": "e09c5db296004fbe3f74490e84dcd62c3c5ddb1b",
+ "revisionTime": "2018-03-28T16:31:53Z"
+ },
+ {
"checksumSHA1": "XnbEHQRzINRKXKmu9GcaqGkK4Lg=",
"path": "github.com/golang/protobuf/proto",
"revision": "f592bd283e9ef86337a432eb50e592278c3d534d"
@@ -37,12 +43,78 @@
"revisionTime": "2018-03-28T16:31:53Z"
},
{
+ "checksumSHA1": "Ylq6kq3KWBy6mu68oyEwenhNMdg=",
+ "path": "github.com/golang/protobuf/ptypes/struct",
+ "revision": "e09c5db296004fbe3f74490e84dcd62c3c5ddb1b",
+ "revisionTime": "2018-03-28T16:31:53Z"
+ },
+ {
"checksumSHA1": "O2ItP5rmfrgxPufhjJXbFlXuyL8=",
"path": "github.com/golang/protobuf/ptypes/timestamp",
"revision": "e09c5db296004fbe3f74490e84dcd62c3c5ddb1b",
"revisionTime": "2018-03-28T16:31:53Z"
},
{
+ "checksumSHA1": "xtOnCs1i5rmga0KIQ9BZUHGRfL8=",
+ "path": "github.com/grpc-ecosystem/go-grpc-middleware",
+ "revision": "b9ed6aed6cf9de7330c7c8e81d3d8e49086539e8",
+ "revisionTime": "2018-04-09T12:24:56Z"
+ },
+ {
+ "checksumSHA1": "tvOR7YKj51rBR+j5C/ZyZj6rvYc=",
+ "path": "github.com/grpc-ecosystem/go-grpc-middleware/auth",
+ "revision": "b9ed6aed6cf9de7330c7c8e81d3d8e49086539e8",
+ "revisionTime": "2018-04-09T12:24:56Z"
+ },
+ {
+ "checksumSHA1": "YdjXbik3OwU+YwQL7OAzwqAAUjo=",
+ "path": "github.com/grpc-ecosystem/go-grpc-middleware/logging",
+ "revision": "b9ed6aed6cf9de7330c7c8e81d3d8e49086539e8",
+ "revisionTime": "2018-04-09T12:24:56Z"
+ },
+ {
+ "checksumSHA1": "6j+jI0V+xVmiRFOQh2pFfU8pGDI=",
+ "path": "github.com/grpc-ecosystem/go-grpc-middleware/logging/logrus",
+ "revision": "b9ed6aed6cf9de7330c7c8e81d3d8e49086539e8",
+ "revisionTime": "2018-04-09T12:24:56Z"
+ },
+ {
+ "checksumSHA1": "lyjaDmKU/dk/K4ciP5OUJEzmjfA=",
+ "path": "github.com/grpc-ecosystem/go-grpc-middleware/logging/logrus/ctxlogrus",
+ "revision": "b9ed6aed6cf9de7330c7c8e81d3d8e49086539e8",
+ "revisionTime": "2018-04-09T12:24:56Z"
+ },
+ {
+ "checksumSHA1": "mlh8jfZweEtX64NHqAyXHKm94kA=",
+ "path": "github.com/grpc-ecosystem/go-grpc-middleware/recovery",
+ "revision": "b9ed6aed6cf9de7330c7c8e81d3d8e49086539e8",
+ "revisionTime": "2018-04-09T12:24:56Z"
+ },
+ {
+ "checksumSHA1": "zJOUc3xTSI2qurPpvlaKWFMs67Q=",
+ "path": "github.com/grpc-ecosystem/go-grpc-middleware/tags",
+ "revision": "b9ed6aed6cf9de7330c7c8e81d3d8e49086539e8",
+ "revisionTime": "2018-04-09T12:24:56Z"
+ },
+ {
+ "checksumSHA1": "g5zvkcjKi3oc+BXuqJfMfG2tP+c=",
+ "path": "github.com/grpc-ecosystem/go-grpc-middleware/tags/logrus",
+ "revision": "b9ed6aed6cf9de7330c7c8e81d3d8e49086539e8",
+ "revisionTime": "2018-04-09T12:24:56Z"
+ },
+ {
+ "checksumSHA1": "L5z1C445GhhQmDKSisTFv754LdU=",
+ "path": "github.com/grpc-ecosystem/go-grpc-middleware/util/metautils",
+ "revision": "b9ed6aed6cf9de7330c7c8e81d3d8e49086539e8",
+ "revisionTime": "2018-04-09T12:24:56Z"
+ },
+ {
+ "checksumSHA1": "8NqQ+6tkBgT7m/SpvdzakK1c+1Y=",
+ "path": "github.com/grpc-ecosystem/go-grpc-prometheus",
+ "revision": "7a96c742b925b66f0206c15956f6eb7a14e23555",
+ "revisionTime": "2018-04-04T16:45:04Z"
+ },
+ {
"checksumSHA1": "LJA9zeZ+AZS9LHDacPd9OemVRDk=",
"path": "github.com/kardianos/osext",
"revision": "efacde03154693404c65e7aa7d461ac9014acd0c"
@@ -142,6 +214,12 @@
"revision": "1297dc01ed0a819ff634c89707081a4df43baf6b"
},
{
+ "checksumSHA1": "4Ensmb2/WSpaXsGOlRKwdC45P54=",
+ "path": "gitlab.com/gitlab-org/gitaly/auth",
+ "revision": "4accefd4aae0ceda0ff8a2cfeb505f2dfcb7a0e7",
+ "revisionTime": "2018-04-12T13:09:56Z"
+ },
+ {
"checksumSHA1": "QdEuED/Ha1K6DUBVG/HLboBxFt8=",
"path": "gitlab.com/gitlab-org/gitlab-pages-proto/go",
"revision": "66dafd4b2ddf25df75993329e08792b070217903",
@@ -328,6 +406,22 @@
"versionExact": "v1.11.2"
},
{
+ "checksumSHA1": "DyM0uqLtknaI4THSc3spn9XlL+g=",
+ "path": "google.golang.org/grpc/health",
+ "revision": "d89cded64628466c4ab532d1f0ba5c220459ebe8",
+ "revisionTime": "2018-04-04T21:41:50Z",
+ "version": "v1.11.2",
+ "versionExact": "v1.11.2"
+ },
+ {
+ "checksumSHA1": "6vY7tYjV84pnr3sDctzx53Bs8b0=",
+ "path": "google.golang.org/grpc/health/grpc_health_v1",
+ "revision": "d89cded64628466c4ab532d1f0ba5c220459ebe8",
+ "revisionTime": "2018-04-04T21:41:50Z",
+ "version": "v1.11.2",
+ "versionExact": "v1.11.2"
+ },
+ {
"checksumSHA1": "Qvf3zdmRCSsiM/VoBv0qB/naHtU=",
"path": "google.golang.org/grpc/internal",
"revision": "d89cded64628466c4ab532d1f0ba5c220459ebe8",