vendor: upgrade grpc-gateway to v1.2.0

This commit is contained in:
Anthony Romano
2017-04-07 16:36:14 -07:00
parent c0560be98a
commit 2769cae6bd
7 changed files with 177 additions and 23 deletions

View File

@ -15,12 +15,17 @@ import (
"google.golang.org/grpc/metadata" "google.golang.org/grpc/metadata"
) )
// MetadataHeaderPrefix is prepended to HTTP headers in order to convert them to // MetadataHeaderPrefix is the http prefix that represents custom metadata
// gRPC metadata for incoming requests processed by grpc-gateway // parameters to or from a gRPC call.
const MetadataHeaderPrefix = "Grpc-Metadata-" const MetadataHeaderPrefix = "Grpc-Metadata-"
// MetadataPrefix is the prefix for grpc-gateway supplied custom metadata fields.
const MetadataPrefix = "grpcgateway-"
// MetadataTrailerPrefix is prepended to gRPC metadata as it is converted to // MetadataTrailerPrefix is prepended to gRPC metadata as it is converted to
// HTTP headers in a response handled by grpc-gateway // HTTP headers in a response handled by grpc-gateway
const MetadataTrailerPrefix = "Grpc-Trailer-" const MetadataTrailerPrefix = "Grpc-Trailer-"
const metadataGrpcTimeout = "Grpc-Timeout" const metadataGrpcTimeout = "Grpc-Timeout"
const xForwardedFor = "X-Forwarded-For" const xForwardedFor = "X-Forwarded-For"
@ -52,8 +57,12 @@ func AnnotateContext(ctx context.Context, req *http.Request) (context.Context, e
for key, vals := range req.Header { for key, vals := range req.Header {
for _, val := range vals { for _, val := range vals {
if key == "Authorization" { // For backwards-compatibility, pass through 'authorization' header with no prefix.
if strings.ToLower(key) == "authorization" {
pairs = append(pairs, "authorization", val) pairs = append(pairs, "authorization", val)
}
if isPermanentHTTPHeader(key) {
pairs = append(pairs, strings.ToLower(fmt.Sprintf("%s%s", MetadataPrefix, key)), val)
continue continue
} }
if strings.HasPrefix(key, MetadataHeaderPrefix) { if strings.HasPrefix(key, MetadataHeaderPrefix) {
@ -141,3 +150,38 @@ func timeoutUnitToDuration(u uint8) (d time.Duration, ok bool) {
} }
return return
} }
// isPermanentHTTPHeader checks whether hdr belongs to the list of
// permenant request headers maintained by IANA.
// http://www.iana.org/assignments/message-headers/message-headers.xml
func isPermanentHTTPHeader(hdr string) bool {
switch hdr {
case
"Accept",
"Accept-Charset",
"Accept-Language",
"Accept-Ranges",
"Authorization",
"Cache-Control",
"Content-Type",
"Cookie",
"Date",
"Expect",
"From",
"Host",
"If-Match",
"If-Modified-Since",
"If-None-Match",
"If-Schedule-Tag-Match",
"If-Unmodified-Since",
"Max-Forwards",
"Origin",
"Pragma",
"Referer",
"User-Agent",
"Via",
"Warning":
return true
}
return false
}

View File

@ -64,7 +64,7 @@ var (
type errorBody struct { type errorBody struct {
Error string `protobuf:"bytes,1,name=error" json:"error"` Error string `protobuf:"bytes,1,name=error" json:"error"`
Code int `protobuf:"bytes,2,name=code" json:"code"` Code int32 `protobuf:"varint,2,name=code" json:"code"`
} }
//Make this also conform to proto.Message for builtin JSONPb Marshaler //Make this also conform to proto.Message for builtin JSONPb Marshaler
@ -85,7 +85,7 @@ func DefaultHTTPError(ctx context.Context, marshaler Marshaler, w http.ResponseW
w.Header().Set("Content-Type", marshaler.ContentType()) w.Header().Set("Content-Type", marshaler.ContentType())
body := &errorBody{ body := &errorBody{
Error: grpc.ErrorDesc(err), Error: grpc.ErrorDesc(err),
Code: int(grpc.Code(err)), Code: int32(grpc.Code(err)),
} }
buf, merr := marshaler.Marshal(body) buf, merr := marshaler.Marshal(body)

View File

@ -42,6 +42,34 @@ func (m *StreamError) String() string { return proto.CompactTextStrin
func (*StreamError) ProtoMessage() {} func (*StreamError) ProtoMessage() {}
func (*StreamError) Descriptor() ([]byte, []int) { return fileDescriptor0, []int{0} } func (*StreamError) Descriptor() ([]byte, []int) { return fileDescriptor0, []int{0} }
func (m *StreamError) GetGrpcCode() int32 {
if m != nil {
return m.GrpcCode
}
return 0
}
func (m *StreamError) GetHttpCode() int32 {
if m != nil {
return m.HttpCode
}
return 0
}
func (m *StreamError) GetMessage() string {
if m != nil {
return m.Message
}
return ""
}
func (m *StreamError) GetHttpStatus() string {
if m != nil {
return m.HttpStatus
}
return ""
}
func init() { func init() {
proto.RegisterType((*StreamError)(nil), "grpc.gateway.runtime.StreamError") proto.RegisterType((*StreamError)(nil), "grpc.gateway.runtime.StreamError")
} }
@ -50,7 +78,7 @@ func init() { proto.RegisterFile("runtime/internal/stream_chunk.proto", fileDesc
var fileDescriptor0 = []byte{ var fileDescriptor0 = []byte{
// 181 bytes of a gzipped FileDescriptorProto // 181 bytes of a gzipped FileDescriptorProto
0x1f, 0x8b, 0x08, 0x00, 0x00, 0x09, 0x6e, 0x88, 0x02, 0xff, 0x34, 0x8e, 0xbf, 0xee, 0x82, 0x30, 0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0xff, 0x34, 0x8e, 0xbf, 0xee, 0x82, 0x30,
0x14, 0x85, 0xd3, 0xdf, 0x1f, 0x85, 0xcb, 0x46, 0x1c, 0x9a, 0x38, 0x48, 0x74, 0x61, 0x82, 0xc1, 0x14, 0x85, 0xd3, 0xdf, 0x1f, 0x85, 0xcb, 0x46, 0x1c, 0x9a, 0x38, 0x48, 0x74, 0x61, 0x82, 0xc1,
0x37, 0xd0, 0xf8, 0x02, 0xb0, 0xb9, 0x90, 0x0a, 0x37, 0x40, 0x94, 0x96, 0xdc, 0x5e, 0x62, 0x5c, 0x37, 0xd0, 0xf8, 0x02, 0xb0, 0xb9, 0x90, 0x0a, 0x37, 0x40, 0x94, 0x96, 0xdc, 0x5e, 0x62, 0x5c,
0x7d, 0x72, 0xd3, 0x22, 0xe3, 0xf9, 0xbe, 0x73, 0x92, 0x03, 0x07, 0x9a, 0x34, 0xf7, 0x03, 0xe6, 0x7d, 0x72, 0xd3, 0x22, 0xe3, 0xf9, 0xbe, 0x73, 0x92, 0x03, 0x07, 0x9a, 0x34, 0xf7, 0x03, 0xe6,

View File

@ -21,7 +21,7 @@ type op struct {
operand int operand int
} }
// Pattern is a template pattern of http request paths defined in third_party/googleapis/google/api/http.proto. // Pattern is a template pattern of http request paths defined in github.com/googleapis/googleapis/google/api/http.proto.
type Pattern struct { type Pattern struct {
// ops is a list of operations // ops is a list of operations
ops []op ops []op

View File

@ -4,7 +4,9 @@ import (
"fmt" "fmt"
"net/url" "net/url"
"reflect" "reflect"
"strconv"
"strings" "strings"
"time"
"github.com/golang/protobuf/proto" "github.com/golang/protobuf/proto"
"github.com/grpc-ecosystem/grpc-gateway/utilities" "github.com/grpc-ecosystem/grpc-gateway/utilities"
@ -38,13 +40,15 @@ func populateFieldValueFromPath(msg proto.Message, fieldPath []string, values []
if m.Kind() != reflect.Ptr { if m.Kind() != reflect.Ptr {
return fmt.Errorf("unexpected type %T: %v", msg, msg) return fmt.Errorf("unexpected type %T: %v", msg, msg)
} }
var props *proto.Properties
m = m.Elem() m = m.Elem()
for i, fieldName := range fieldPath { for i, fieldName := range fieldPath {
isLast := i == len(fieldPath)-1 isLast := i == len(fieldPath)-1
if !isLast && m.Kind() != reflect.Struct { if !isLast && m.Kind() != reflect.Struct {
return fmt.Errorf("non-aggregate type in the mid of path: %s", strings.Join(fieldPath, ".")) return fmt.Errorf("non-aggregate type in the mid of path: %s", strings.Join(fieldPath, "."))
} }
f := fieldByProtoName(m, fieldName) var f reflect.Value
f, props = fieldByProtoName(m, fieldName)
if !f.IsValid() { if !f.IsValid() {
grpclog.Printf("field not found in %T: %s", msg, strings.Join(fieldPath, ".")) grpclog.Printf("field not found in %T: %s", msg, strings.Join(fieldPath, "."))
return nil return nil
@ -52,17 +56,20 @@ func populateFieldValueFromPath(msg proto.Message, fieldPath []string, values []
switch f.Kind() { switch f.Kind() {
case reflect.Bool, reflect.Float32, reflect.Float64, reflect.Int32, reflect.Int64, reflect.String, reflect.Uint32, reflect.Uint64: case reflect.Bool, reflect.Float32, reflect.Float64, reflect.Int32, reflect.Int64, reflect.String, reflect.Uint32, reflect.Uint64:
if !isLast {
return fmt.Errorf("unexpected nested field %s in %s", fieldPath[i+1], strings.Join(fieldPath[:i+1], "."))
}
m = f m = f
case reflect.Slice: case reflect.Slice:
// TODO(yugui) Support []byte // TODO(yugui) Support []byte
if !isLast { if !isLast {
return fmt.Errorf("unexpected repeated field in %s", strings.Join(fieldPath, ".")) return fmt.Errorf("unexpected repeated field in %s", strings.Join(fieldPath, "."))
} }
return populateRepeatedField(f, values) return populateRepeatedField(f, values, props)
case reflect.Ptr: case reflect.Ptr:
if f.IsNil() { if f.IsNil() {
m = reflect.New(f.Type().Elem()) m = reflect.New(f.Type().Elem())
f.Set(m) f.Set(m.Convert(f.Type()))
} }
m = f.Elem() m = f.Elem()
continue continue
@ -80,39 +87,73 @@ func populateFieldValueFromPath(msg proto.Message, fieldPath []string, values []
default: default:
grpclog.Printf("too many field values: %s", strings.Join(fieldPath, ".")) grpclog.Printf("too many field values: %s", strings.Join(fieldPath, "."))
} }
return populateField(m, values[0]) return populateField(m, values[0], props)
} }
// fieldByProtoName looks up a field whose corresponding protobuf field name is "name". // fieldByProtoName looks up a field whose corresponding protobuf field name is "name".
// "m" must be a struct value. It returns zero reflect.Value if no such field found. // "m" must be a struct value. It returns zero reflect.Value if no such field found.
func fieldByProtoName(m reflect.Value, name string) reflect.Value { func fieldByProtoName(m reflect.Value, name string) (reflect.Value, *proto.Properties) {
props := proto.GetProperties(m.Type()) props := proto.GetProperties(m.Type())
for _, p := range props.Prop { for _, p := range props.Prop {
if p.OrigName == name { if p.OrigName == name {
return m.FieldByName(p.Name) return m.FieldByName(p.Name), p
} }
} }
return reflect.Value{} return reflect.Value{}, nil
} }
func populateRepeatedField(f reflect.Value, values []string) error { func populateRepeatedField(f reflect.Value, values []string, props *proto.Properties) error {
elemType := f.Type().Elem() elemType := f.Type().Elem()
// is the destination field a slice of an enumeration type?
if enumValMap := proto.EnumValueMap(props.Enum); enumValMap != nil {
return populateFieldEnumRepeated(f, values, enumValMap)
}
conv, ok := convFromType[elemType.Kind()] conv, ok := convFromType[elemType.Kind()]
if !ok { if !ok {
return fmt.Errorf("unsupported field type %s", elemType) return fmt.Errorf("unsupported field type %s", elemType)
} }
f.Set(reflect.MakeSlice(f.Type(), len(values), len(values))) f.Set(reflect.MakeSlice(f.Type(), len(values), len(values)).Convert(f.Type()))
for i, v := range values { for i, v := range values {
result := conv.Call([]reflect.Value{reflect.ValueOf(v)}) result := conv.Call([]reflect.Value{reflect.ValueOf(v)})
if err := result[1].Interface(); err != nil { if err := result[1].Interface(); err != nil {
return err.(error) return err.(error)
} }
f.Index(i).Set(result[0]) f.Index(i).Set(result[0].Convert(f.Index(i).Type()))
} }
return nil return nil
} }
func populateField(f reflect.Value, value string) error { func populateField(f reflect.Value, value string, props *proto.Properties) error {
// Handle well known type
type wkt interface {
XXX_WellKnownType() string
}
if wkt, ok := f.Addr().Interface().(wkt); ok {
switch wkt.XXX_WellKnownType() {
case "Timestamp":
if value == "null" {
f.Field(0).SetInt(0)
f.Field(1).SetInt(0)
return nil
}
t, err := time.Parse(time.RFC3339Nano, value)
if err != nil {
return fmt.Errorf("bad Timestamp: %v", err)
}
f.Field(0).SetInt(int64(t.Unix()))
f.Field(1).SetInt(int64(t.Nanosecond()))
return nil
}
}
// is the destination field an enumeration type?
if enumValMap := proto.EnumValueMap(props.Enum); enumValMap != nil {
return populateFieldEnum(f, value, enumValMap)
}
conv, ok := convFromType[f.Kind()] conv, ok := convFromType[f.Kind()]
if !ok { if !ok {
return fmt.Errorf("unsupported field type %T", f) return fmt.Errorf("unsupported field type %T", f)
@ -121,7 +162,48 @@ func populateField(f reflect.Value, value string) error {
if err := result[1].Interface(); err != nil { if err := result[1].Interface(); err != nil {
return err.(error) return err.(error)
} }
f.Set(result[0]) f.Set(result[0].Convert(f.Type()))
return nil
}
func convertEnum(value string, t reflect.Type, enumValMap map[string]int32) (reflect.Value, error) {
// see if it's an enumeration string
if enumVal, ok := enumValMap[value]; ok {
return reflect.ValueOf(enumVal).Convert(t), nil
}
// check for an integer that matches an enumeration value
eVal, err := strconv.Atoi(value)
if err != nil {
return reflect.Value{}, fmt.Errorf("%s is not a valid %s", value, t)
}
for _, v := range enumValMap {
if v == int32(eVal) {
return reflect.ValueOf(eVal).Convert(t), nil
}
}
return reflect.Value{}, fmt.Errorf("%s is not a valid %s", value, t)
}
func populateFieldEnum(f reflect.Value, value string, enumValMap map[string]int32) error {
cval, err := convertEnum(value, f.Type(), enumValMap)
if err != nil {
return err
}
f.Set(cval)
return nil
}
func populateFieldEnumRepeated(f reflect.Value, values []string, enumValMap map[string]int32) error {
elemType := f.Type().Elem()
f.Set(reflect.MakeSlice(f.Type(), len(values), len(values)).Convert(f.Type()))
for i, v := range values {
result, err := convertEnum(v, elemType, enumValMap)
if err != nil {
return err
}
f.Index(i).Set(result)
}
return nil return nil
} }

6
glide.lock generated
View File

@ -1,5 +1,5 @@
hash: d546c79ab7f1bcc7b048995624e4353713fe1b5fad5d69a50202e309fe9dd2fc hash: 96143db7f79ff5fad84bd66a435153981b793dc8df5e3ef7e55cd096959b6c73
updated: 2017-04-07T14:31:10.872688463-07:00 updated: 2017-04-07T16:28:46.088989482-07:00
imports: imports:
- name: github.com/beorn7/perks - name: github.com/beorn7/perks
version: 4c0e84591b9aa9e6dcfdf3e020114cd81f89d5f9 version: 4c0e84591b9aa9e6dcfdf3e020114cd81f89d5f9
@ -54,7 +54,7 @@ imports:
- name: github.com/grpc-ecosystem/go-grpc-prometheus - name: github.com/grpc-ecosystem/go-grpc-prometheus
version: 6b7015e65d366bf3f19b2b2a000a831940f0f7e0 version: 6b7015e65d366bf3f19b2b2a000a831940f0f7e0
- name: github.com/grpc-ecosystem/grpc-gateway - name: github.com/grpc-ecosystem/grpc-gateway
version: 84398b94e188ee336f307779b57b3aa91af7063c version: 18d159699f2e83fc5bb9ef2f79465ca3f3122676
subpackages: subpackages:
- runtime - runtime
- runtime/internal - runtime/internal

View File

@ -40,7 +40,7 @@ import:
- package: github.com/google/btree - package: github.com/google/btree
version: 925471ac9e2131377a91e1595defec898166fe49 version: 925471ac9e2131377a91e1595defec898166fe49
- package: github.com/grpc-ecosystem/grpc-gateway - package: github.com/grpc-ecosystem/grpc-gateway
version: 84398b94e188ee336f307779b57b3aa91af7063c version: v1.2.0
subpackages: subpackages:
- runtime - runtime
- runtime/internal - runtime/internal