1 package ldmodel
2
3 import (
4 "encoding/json"
5 "testing"
6
7 "github.com/launchdarkly/go-jsonstream/v3/jreader"
8 "github.com/launchdarkly/go-jsonstream/v3/jwriter"
9 "github.com/launchdarkly/go-test-helpers/v3/jsonhelpers"
10
11 "github.com/stretchr/testify/assert"
12 "github.com/stretchr/testify/require"
13 )
14
15 type testMarshalFlagFn func(FeatureFlag) ([]byte, error)
16 type testUnmarshalFlagFn func([]byte) (FeatureFlag, error)
17
18 type testMarshalSegmentFn func(Segment) ([]byte, error)
19 type testUnmarshalSegmentFn func([]byte) (Segment, error)
20
21 func doMarshalFlagTest(t *testing.T, marshalFn testMarshalFlagFn) {
22 for _, p := range makeFlagSerializationTestParams() {
23 t.Run(p.name, func(t *testing.T) {
24 bytes, err := marshalFn(p.flag)
25 require.NoError(t, err)
26 expected := mergeDefaultProperties(json.RawMessage(p.jsonString), flagTopLevelDefaultProperties)
27 jsonhelpers.AssertEqual(t, expected, bytes)
28 })
29 }
30 }
31
32 func doMarshalSegmentTest(t *testing.T, marshalFn testMarshalSegmentFn) {
33 for _, p := range makeSegmentSerializationTestParams() {
34 t.Run(p.name, func(t *testing.T) {
35 bytes, err := marshalFn(p.segment)
36 require.NoError(t, err)
37 expected := mergeDefaultProperties(json.RawMessage(p.jsonString), segmentTopLevelDefaultProperties)
38 jsonhelpers.AssertEqual(t, expected, bytes)
39 })
40 }
41 }
42
43 func doUnmarshalFlagTest(t *testing.T, unmarshalFn testUnmarshalFlagFn) {
44 for _, p := range makeFlagSerializationTestParams() {
45 t.Run(p.name, func(t *testing.T) {
46 flag, err := unmarshalFn([]byte(p.jsonString))
47 require.NoError(t, err)
48
49 expectedFlag := p.flag
50 PreprocessFlag(&expectedFlag)
51 if !p.isCustomClientSideAvailability {
52 expectedFlag.ClientSideAvailability = ClientSideAvailability{UsingMobileKey: true}
53 }
54 assert.Equal(t, expectedFlag, flag)
55
56 for _, altJSON := range p.jsonAltInputs {
57 t.Run(altJSON, func(t *testing.T) {
58 flag, err := unmarshalFn([]byte(altJSON))
59 require.NoError(t, err)
60 assert.Equal(t, expectedFlag, flag)
61 })
62 }
63 })
64 }
65 }
66
67 func doUnmarshalSegmentTest(t *testing.T, unmarshalFn testUnmarshalSegmentFn) {
68 for _, p := range makeSegmentSerializationTestParams() {
69 t.Run(p.name, func(t *testing.T) {
70 segment, err := unmarshalFn([]byte(p.jsonString))
71 require.NoError(t, err)
72
73 expectedSegment := p.segment
74 PreprocessSegment(&expectedSegment)
75
76 assert.Equal(t, expectedSegment, segment)
77
78 for _, altJSON := range p.jsonAltInputs {
79 t.Run(altJSON, func(t *testing.T) {
80 segment, err := unmarshalFn([]byte(altJSON))
81 require.NoError(t, err)
82 assert.Equal(t, expectedSegment, segment)
83 })
84 }
85 })
86 }
87 }
88
89 func TestMarshalFlagWithJSONMarshal(t *testing.T) {
90 doMarshalFlagTest(t, func(flag FeatureFlag) ([]byte, error) {
91 return json.Marshal(flag)
92 })
93 }
94
95 func TestMarshalFlagWithDefaultSerialization(t *testing.T) {
96 doMarshalFlagTest(t, NewJSONDataModelSerialization().MarshalFeatureFlag)
97 }
98
99 func TestMarshalFlagWithJSONWriter(t *testing.T) {
100 doMarshalFlagTest(t, func(flag FeatureFlag) ([]byte, error) {
101 w := jwriter.NewWriter()
102 MarshalFeatureFlagToJSONWriter(flag, &w)
103 return w.Bytes(), w.Error()
104 })
105 }
106
107 func TestUnmarshalFlagWithJSONUnmarshal(t *testing.T) {
108 doUnmarshalFlagTest(t, func(data []byte) (FeatureFlag, error) {
109 var flag FeatureFlag
110 err := json.Unmarshal(data, &flag)
111 return flag, err
112 })
113 }
114
115 func TestUnmarshalFlagWithDefaultSerialization(t *testing.T) {
116 doUnmarshalFlagTest(t, NewJSONDataModelSerialization().UnmarshalFeatureFlag)
117 }
118
119 func TestUnmarshalFlagWithJSONReader(t *testing.T) {
120 doUnmarshalFlagTest(t, func(data []byte) (FeatureFlag, error) {
121 r := jreader.NewReader(data)
122 flag := UnmarshalFeatureFlagFromJSONReader(&r)
123 return flag, r.Error()
124 })
125 }
126
127 func TestMarshalSegmentWithJSONMarshal(t *testing.T) {
128 doMarshalSegmentTest(t, func(segment Segment) ([]byte, error) {
129 return json.Marshal(segment)
130 })
131 }
132
133 func TestMarshalSegmentWithDefaultSerialization(t *testing.T) {
134 doMarshalSegmentTest(t, NewJSONDataModelSerialization().MarshalSegment)
135 }
136
137 func TestMarshalSegmentWithJSONWriter(t *testing.T) {
138 doMarshalSegmentTest(t, func(segment Segment) ([]byte, error) {
139 w := jwriter.NewWriter()
140 MarshalSegmentToJSONWriter(segment, &w)
141 return w.Bytes(), w.Error()
142 })
143 }
144
145 func TestUnmarshalSegmentWithJSONUnmarshal(t *testing.T) {
146 doUnmarshalSegmentTest(t, func(data []byte) (Segment, error) {
147 var segment Segment
148 err := json.Unmarshal(data, &segment)
149 return segment, err
150 })
151 }
152
153 func TestUnmarshalSegmentWithDefaultSerialization(t *testing.T) {
154 doUnmarshalSegmentTest(t, NewJSONDataModelSerialization().UnmarshalSegment)
155 }
156
157 func TestUnmarshalSegmentWithJSONReader(t *testing.T) {
158 doUnmarshalSegmentTest(t, func(data []byte) (Segment, error) {
159 r := jreader.NewReader(data)
160 segment := UnmarshalSegmentFromJSONReader(&r)
161 return segment, r.Error()
162 })
163 }
164
165 func TestUnmarshalFlagErrors(t *testing.T) {
166 _, err := NewJSONDataModelSerialization().UnmarshalFeatureFlag([]byte(`{`))
167 assert.Error(t, err)
168
169 _, err = NewJSONDataModelSerialization().UnmarshalFeatureFlag([]byte(`{"key":[]}`))
170 assert.Error(t, err)
171 }
172
173 func TestUnmarshalSegmentErrors(t *testing.T) {
174 _, err := NewJSONDataModelSerialization().UnmarshalSegment([]byte(`{`))
175 assert.Error(t, err)
176
177 _, err = NewJSONDataModelSerialization().UnmarshalSegment([]byte(`{"key":[]}`))
178 assert.Error(t, err)
179 }
180
View as plain text