1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29 package required
30
31 import (
32 "github.com/gogo/protobuf/proto"
33 "github.com/gogo/protobuf/test"
34 "math/rand"
35 "reflect"
36 "strconv"
37 "testing"
38 "time"
39 )
40
41 func TestMarshalToErrorsWhenRequiredFieldIsNotPresent(t *testing.T) {
42 data := RequiredExample{}
43 buf, err := proto.Marshal(&data)
44 if err == nil {
45 t.Fatalf("err == nil; was %v instead", err)
46 }
47 if err.Error() != `proto: required field "theRequiredString" not set` {
48 t.Fatalf(`err.Error() != "proto: required field "theRequiredString" not set"; was "%s" instead`, err.Error())
49 }
50 if len(buf) != 0 {
51 t.Fatalf(`len(buf) != 0; was %d instead`, len(buf))
52 }
53 }
54
55 func TestMarshalToSucceedsWhenRequiredFieldIsPresent(t *testing.T) {
56 data := RequiredExample{
57 TheRequiredString: proto.String("present"),
58 }
59 buf, err := proto.Marshal(&data)
60 if err != nil {
61 t.Fatalf("err != nil; was %v instead", err)
62 }
63 if len(buf) == 0 {
64 t.Fatalf(`len(buf) == 0; expected nonzero`)
65 }
66 }
67
68 func TestUnmarshalErrorsWhenRequiredFieldIsNotPresent(t *testing.T) {
69 missingRequiredField := []byte{0x12, 0x8, 0x6f, 0x70, 0x74, 0x69, 0x6f, 0x6e, 0x61, 0x6c}
70 data := RequiredExample{}
71 err := proto.Unmarshal(missingRequiredField, &data)
72 if err == nil {
73 t.Fatalf("err == nil; was %v instead", err)
74 }
75 if err.Error() != `proto: required field "theRequiredString" not set` {
76 t.Fatalf(`err.Error() != "proto: required field "theRequiredString" not set"; was "%s" instead`, err.Error())
77 }
78 }
79
80 func TestUnmarshalSucceedsWhenRequiredIsNotPresent(t *testing.T) {
81 dataOut := RequiredExample{
82 TheRequiredString: proto.String("present"),
83 }
84 encodedMessage, err := proto.Marshal(&dataOut)
85 if err != nil {
86 t.Fatalf("Unexpected error when marshalling dataOut: %v", err)
87 }
88 dataIn := RequiredExample{}
89 err = proto.Unmarshal(encodedMessage, &dataIn)
90 if err != nil {
91 t.Fatalf("err != nil; was %v instead", err)
92 }
93 }
94
95 func TestUnmarshalPopulatedOptionalFieldsAsRequiredSucceeds(t *testing.T) {
96 r := rand.New(rand.NewSource(time.Now().UnixNano()))
97 dataOut := test.NewPopulatedNidOptNative(r, true)
98 encodedMessage, err := proto.Marshal(dataOut)
99 if err != nil {
100 t.Fatalf("Unexpected error when marshalling dataOut: %v", err)
101 }
102 dataIn := NidOptNative{}
103 err = proto.Unmarshal(encodedMessage, &dataIn)
104 if err != nil {
105 t.Fatalf("err != nil; was %v instead", err)
106 }
107 }
108
109 func TestUnmarshalPartiallyPopulatedOptionalFieldsFails(t *testing.T) {
110
111 dataOut := &test.NinOptNative{
112 Field1: proto.Float64(0),
113 Field2: proto.Float32(0),
114 Field3: proto.Int32(0),
115 Field4: proto.Int64(0),
116 Field5: proto.Uint32(0),
117 Field6: proto.Uint64(0),
118 Field7: proto.Int32(0),
119 Field8: proto.Int64(0),
120 Field9: proto.Uint32(0),
121 Field10: proto.Int32(0),
122 Field11: proto.Uint64(0),
123 Field12: proto.Int64(0),
124 Field13: proto.Bool(false),
125 Field14: proto.String("0"),
126 Field15: []byte("0"),
127 }
128 r := rand.New(rand.NewSource(time.Now().UnixNano()))
129 fieldName := "Field" + strconv.Itoa(r.Intn(15)+1)
130 field := reflect.ValueOf(dataOut).Elem().FieldByName(fieldName)
131 fieldType := field.Type()
132 field.Set(reflect.Zero(fieldType))
133 encodedMessage, err := proto.Marshal(dataOut)
134 if err != nil {
135 t.Fatalf("Unexpected error when marshalling dataOut: %v", err)
136 }
137 dataIn := NidOptNative{}
138 err = proto.Unmarshal(encodedMessage, &dataIn)
139 if err.Error() != `proto: required field "`+fieldName+`" not set` {
140 t.Fatalf(`err.Error() != "proto: required field "`+fieldName+`" not set"; was "%s" instead`, err.Error())
141 }
142 }
143
144 func TestMarshalFailsWithoutAllFieldsSet(t *testing.T) {
145 r := rand.New(rand.NewSource(time.Now().UnixNano()))
146 dataOut := NewPopulatedNinOptNative(r, true)
147 fieldName := "Field" + strconv.Itoa(r.Intn(15)+1)
148 field := reflect.ValueOf(dataOut).Elem().FieldByName(fieldName)
149 fieldType := field.Type()
150 field.Set(reflect.Zero(fieldType))
151 encodedMessage, err := proto.Marshal(dataOut)
152 if err.Error() != `proto: required field "`+fieldName+`" not set` {
153 t.Fatalf(`err.Error() != "proto: required field "`+fieldName+`" not set"; was "%s" instead`, err.Error())
154 }
155 if len(encodedMessage) > 0 {
156 t.Fatalf("Got some bytes from marshal, expected none.")
157 }
158 }
159
160 func TestMissingFieldsOnRepeatedNestedTypes(t *testing.T) {
161 r := rand.New(rand.NewSource(time.Now().UnixNano()))
162 dataOut := &NestedNinOptNative{
163 NestedNinOpts: []*NinOptNative{
164 NewPopulatedNinOptNative(r, true),
165 NewPopulatedNinOptNative(r, true),
166 NewPopulatedNinOptNative(r, true),
167 },
168 }
169 middle := dataOut.GetNestedNinOpts()[1]
170 fieldName := "Field" + strconv.Itoa(r.Intn(15)+1)
171 field := reflect.ValueOf(middle).Elem().FieldByName(fieldName)
172 fieldType := field.Type()
173 field.Set(reflect.Zero(fieldType))
174 encodedMessage, err := proto.Marshal(dataOut)
175 if err.Error() != `proto: required field "`+fieldName+`" not set` {
176 t.Fatalf(`err.Error() != "proto: required field "`+fieldName+`" not set"; was "%s" instead`, err.Error())
177 }
178 if len(encodedMessage) > 0 {
179 t.Fatalf("Got some bytes from marshal, expected none.")
180 }
181 }
182
View as plain text