github.com/annchain/OG@v0.0.9/tests/msg_marshal/msg.go (about) 1 // Copyright © 2019 Annchain Authors <EMAIL ADDRESS> 2 // 3 // Licensed under the Apache License, Version 2.0 (the "License"); 4 // you may not use this file except in compliance with the License. 5 // You may obtain a copy of the License at 6 // 7 // http://www.apache.org/licenses/LICENSE-2.0 8 // 9 // Unless required by applicable law or agreed to in writing, software 10 // distributed under the License is distributed on an "AS IS" BASIS, 11 // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 12 // See the License for the specific language governing permissions and 13 // limitations under the License. 14 package msg_marshal 15 16 import ( 17 "encoding/binary" 18 "fmt" 19 "github.com/tinylib/msgp/msgp" 20 ) 21 22 //go:generate msgp 23 24 type FooI interface { 25 String() string 26 // implemented by msgp 27 DecodeMsg(dc *msgp.Reader) (err error) 28 EncodeMsg(en *msgp.Writer) (err error) 29 MarshalMsg(b []byte) (o []byte, err error) 30 UnmarshalMsg(bts []byte) (o []byte, err error) 31 Msgsize() (s int) 32 GetType() uint16 33 GetName() string 34 } 35 36 //msgp:tuple Person 37 type Person struct { 38 Name string 39 Age int 40 Type uint16 41 } 42 43 //msgp:tuple Student 44 type Student struct { 45 Person 46 Score int 47 } 48 49 //msgp:tuple Teacher 50 type Teacher struct { 51 Person 52 Teach bool 53 } 54 55 func (p *Person) GetName() string { 56 return p.Name 57 } 58 59 func (p *Person) GetType() uint16 { 60 return p.Type 61 } 62 63 func (p Person) String() string { 64 return p.Name + " person" 65 } 66 67 func (s Student) String() string { 68 return s.Person.String() + " student" 69 } 70 71 func (s Teacher) String() string { 72 return s.Person.String() + " teacher" 73 } 74 75 func MashalFoo(f FooI, b []byte) ([]byte, error) { 76 if f == nil { 77 panic("nil foo") 78 } 79 tail := make([]byte, 2) 80 binary.BigEndian.PutUint16(tail, f.GetType()) 81 b = append(b, tail...) 82 o, err := f.MarshalMsg(b) 83 return o, err 84 } 85 86 func UnmarShalFoo(b []byte) (o []byte, f FooI, err error) { 87 if len(b) < 3 { 88 return b, nil, fmt.Errorf("size mismatch") 89 } 90 tp := binary.BigEndian.Uint16(b) 91 switch tp { 92 case 1: 93 var s Student 94 o, err := s.UnmarshalMsg(b[2:]) 95 if err != nil { 96 return o, nil, err 97 } 98 return o, &s, nil 99 case 2: 100 var s Teacher 101 o, err := s.UnmarshalMsg(b[2:]) 102 if err != nil { 103 return o, nil, err 104 } 105 return o, &s, nil 106 default: 107 return b, nil, fmt.Errorf("unkown type") 108 } 109 }