github.com/annwntech/go-micro/v2@v2.9.5/codec/jsonpb/jsonpb.go (about) 1 // Package jsonpb provides a json codec 2 package jsonpb 3 4 import ( 5 "bytes" 6 "io" 7 "io/ioutil" 8 9 // nolint: staticcheck 10 oldjsonpb "github.com/golang/protobuf/jsonpb" 11 // nolint: staticcheck 12 "github.com/annwntech/go-micro/v2/codec" 13 bytesCodec "github.com/annwntech/go-micro/v2/codec/bytes" 14 oldproto "github.com/golang/protobuf/proto" 15 jsonpb "google.golang.org/protobuf/encoding/protojson" 16 "google.golang.org/protobuf/proto" 17 ) 18 19 var ( 20 JsonpbMarshaler = jsonpb.MarshalOptions{ 21 UseEnumNumbers: false, 22 EmitUnpopulated: false, 23 UseProtoNames: true, 24 AllowPartial: false, 25 } 26 27 JsonpbUnmarshaler = jsonpb.UnmarshalOptions{ 28 DiscardUnknown: false, 29 AllowPartial: false, 30 } 31 32 OldJsonpbMarshaler = oldjsonpb.Marshaler{ 33 OrigName: true, 34 EmitDefaults: false, 35 } 36 37 OldJsonpbUnmarshaler = oldjsonpb.Unmarshaler{ 38 AllowUnknownFields: false, 39 } 40 ) 41 42 type jsonpbCodec struct { 43 Conn io.ReadWriteCloser 44 } 45 46 func (c *jsonpbCodec) Marshal(v interface{}) ([]byte, error) { 47 switch m := v.(type) { 48 case nil: 49 return nil, nil 50 case *bytesCodec.Frame: 51 return m.Data, nil 52 case proto.Message: 53 return JsonpbMarshaler.Marshal(m) 54 case oldproto.Message: 55 buf, err := OldJsonpbMarshaler.MarshalToString(m) 56 return []byte(buf), err 57 } 58 return nil, codec.ErrInvalidMessage 59 } 60 61 func (c *jsonpbCodec) Unmarshal(d []byte, v interface{}) error { 62 if d == nil { 63 return nil 64 } 65 switch m := v.(type) { 66 case nil: 67 return nil 68 case *bytesCodec.Frame: 69 m.Data = d 70 return nil 71 case proto.Message: 72 return JsonpbUnmarshaler.Unmarshal(d, m) 73 case oldproto.Message: 74 return OldJsonpbUnmarshaler.Unmarshal(bytes.NewReader(d), m) 75 } 76 return codec.ErrInvalidMessage 77 } 78 func (c *jsonpbCodec) ReadHeader(m *codec.Message, t codec.MessageType) error { 79 return nil 80 } 81 82 func (c *jsonpbCodec) ReadBody(b interface{}) error { 83 switch m := b.(type) { 84 case nil: 85 return nil 86 case *bytesCodec.Frame: 87 buf, err := ioutil.ReadAll(c.Conn) 88 if err != nil { 89 return err 90 } 91 m.Data = buf 92 return nil 93 case oldproto.Message: 94 return OldJsonpbUnmarshaler.Unmarshal(c.Conn, m) 95 case proto.Message: 96 buf, err := ioutil.ReadAll(c.Conn) 97 if err != nil { 98 return err 99 } 100 return JsonpbUnmarshaler.Unmarshal(buf, m) 101 } 102 return codec.ErrInvalidMessage 103 } 104 105 func (c *jsonpbCodec) Write(m *codec.Message, b interface{}) error { 106 switch m := b.(type) { 107 case nil: 108 return nil 109 case *bytesCodec.Frame: 110 _, err := c.Conn.Write(m.Data) 111 return err 112 case oldproto.Message: 113 return OldJsonpbMarshaler.Marshal(c.Conn, m) 114 case proto.Message: 115 buf, err := JsonpbMarshaler.Marshal(m) 116 if err != nil { 117 return err 118 } 119 _, err = c.Conn.Write(buf) 120 return err 121 } 122 return codec.ErrInvalidMessage 123 } 124 125 func (c *jsonpbCodec) Close() error { 126 return c.Conn.Close() 127 } 128 129 func (c *jsonpbCodec) String() string { 130 return "jsonpb" 131 } 132 133 func NewCodec(c io.ReadWriteCloser) codec.Codec { 134 return &jsonpbCodec{ 135 Conn: c, 136 } 137 }