1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17 package org.apache.juneau.rest.annotation;
18
19 import static org.junit.jupiter.api.Assertions.*;
20
21 import java.util.*;
22
23 import org.apache.juneau.*;
24 import org.apache.juneau.annotation.*;
25 import org.apache.juneau.collections.*;
26 import org.apache.juneau.http.annotation.*;
27 import org.apache.juneau.json.*;
28 import org.apache.juneau.rest.*;
29 import org.apache.juneau.rest.httppart.*;
30 import org.apache.juneau.rest.mock.*;
31 import org.apache.juneau.testutils.pojos.*;
32 import org.apache.juneau.urlencoding.*;
33 import org.junit.jupiter.api.*;
34
35 class FormData_Test extends TestBase {
36
37
38
39
40
41 @Rest(parsers=UrlEncodingParser.class)
42 public static class A {
43 @RestPost
44 public String a(RestRequest req, @FormData("p1") @Schema(allowEmptyValue=true) String p1, @FormData("p2") @Schema(allowEmptyValue=true) int p2) throws Exception {
45 var f = req.getFormParams();
46 return "p1=["+p1+","+f.get("p1").orElse(null)+","+f.get("p1").asString().orElse(null)+"],p2=["+p2+","+f.get("p2").orElse(null)+","+f.get("p2").as(int.class).orElse(null)+"]";
47 }
48 }
49
50 @Test void a01_basic() throws Exception {
51 var a = MockRestClient.build(A.class);
52 a.post("/a", "p1=p1&p2=2").contentType("application/x-www-form-urlencoded").run().assertContent("p1=[p1,p1,p1],p2=[2,2,2]");
53 a.post("/a", "p1&p2").contentType("application/x-www-form-urlencoded").run().assertContent("p1=[null,null,null],p2=[0,null,0]");
54 a.post("/a", "p1=&p2=").contentType("application/x-www-form-urlencoded").run().assertContent("p1=[,,],p2=[0,,0]");
55 a.post("/a", "").contentType("application/x-www-form-urlencoded").run().assertContent("p1=[null,null,null],p2=[0,null,0]");
56 a.post("/a", "p1").contentType("application/x-www-form-urlencoded").run().assertContent("p1=[null,null,null],p2=[0,null,0]");
57 a.post("/a", "p1=").contentType("application/x-www-form-urlencoded").run().assertContent("p1=[,,],p2=[0,null,0]");
58 a.post("/a", "p2").contentType("application/x-www-form-urlencoded").run().assertContent("p1=[null,null,null],p2=[0,null,0]");
59 a.post("/a", "p2=").contentType("application/x-www-form-urlencoded").run().assertContent("p1=[null,null,null],p2=[0,,0]");
60 a.post("/a", "p1=foo&p2").contentType("application/x-www-form-urlencoded").run().assertContent("p1=[foo,foo,foo],p2=[0,null,0]");
61 a.post("/a", "p1&p2=1").contentType("application/x-www-form-urlencoded").run().assertContent("p1=[null,null,null],p2=[1,1,1]");
62 String x = "a%2Fb%25c%3Dd+e";
63 a.post("/a", "p1="+x+"&p2=1").contentType("application/x-www-form-urlencoded").run().assertContent("p1=[a/b%c=d e,a/b%c=d e,a/b%c=d e],p2=[1,1,1]");
64 }
65
66
67
68
69
70 @Rest
71 public static class B {
72 @RestPost
73 public String a(RestRequest req, @FormData("p1") String p1) throws Exception {
74 var f = req.getFormParams();
75 return "p1=["+p1+","+f.get("p1").orElse(null)+","+f.get("p1").orElse(null)+"]";
76 }
77 @RestPost
78 public String b(RestRequest req, @FormData("p1") @Schema(format="uon") String p1) throws Exception {
79 var f = req.getFormParams();
80 return "p1=["+p1+","+f.get("p1").orElse(null)+","+f.get("p1").orElse(null)+"]";
81 }
82 }
83
84 @Test void b01_uonParameters() throws Exception {
85 var b = MockRestClient.build(B.class);
86
87 b.post("/a", "p1=p1").contentType("application/x-www-form-urlencoded").run().assertContent("p1=[p1,p1,p1]");
88 b.post("/a", "p1='p1'").contentType("application/x-www-form-urlencoded").run().assertContent("p1=['p1','p1','p1']");
89
90 b.post("/b", "p1=p1").contentType("application/x-www-form-urlencoded").run().assertContent("p1=[p1,p1,p1]");
91 b.post("/b", "p1='p1'").contentType("application/x-www-form-urlencoded").run().assertContent("p1=[p1,'p1','p1']");
92 }
93
94
95
96
97
98 @Rest
99 public static class C {
100 @RestPost(defaultRequestFormData={"f1:1","f2=2"," f3 : 3 "})
101 public JsonMap a(RequestFormParams formData) {
102 return JsonMap.create()
103 .append("f1", formData.get("f1").asString())
104 .append("f2", formData.get("f2").asString())
105 .append("f3", formData.get("f3").asString());
106 }
107 @RestPost
108 public JsonMap b(@FormData("f1") String f1, @FormData("f2") String f2, @FormData("f3") String f3) {
109 return JsonMap.create()
110 .append("f1", f1)
111 .append("f2", f2)
112 .append("f3", f3);
113 }
114 @RestPost
115 public JsonMap c(@FormData("f1") @Schema(_default="1") String f1, @FormData("f2") @Schema(_default="2") String f2, @FormData("f3") @Schema(_default="3") String f3) {
116 return JsonMap.create()
117 .append("f1", f1)
118 .append("f2", f2)
119 .append("f3", f3);
120 }
121 @RestPost(defaultRequestFormData={"f1:1","f2=2"," f3 : 3 "})
122 public JsonMap d(@FormData("f1") @Schema(_default="4") String f1, @FormData("f2") @Schema(_default="5") String f2, @FormData("f3") @Schema(_default="6") String f3) {
123 return JsonMap.create()
124 .append("f1", f1)
125 .append("f2", f2)
126 .append("f3", f3);
127 }
128 }
129
130 @Test void c01_defaultFormData() throws Exception {
131 var c = MockRestClient.build(C.class);
132
133 c.post("/a").contentType("application/x-www-form-urlencoded").run().assertContent("{f1:'1',f2:'2',f3:'3'}");
134 c.post("/a").contentType("application/x-www-form-urlencoded").formData("f1",4).formData("f2",5).formData("f3",6).run().assertContent("{f1:'4',f2:'5',f3:'6'}");
135
136 c.post("/b").contentType("application/x-www-form-urlencoded").run().assertContent("{f1:null,f2:null,f3:null}");
137 c.post("/b").contentType("application/x-www-form-urlencoded").formData("f1",4).formData("f2",5).formData("f3",6).run().assertContent("{f1:'4',f2:'5',f3:'6'}");
138
139 c.post("/c").contentType("application/x-www-form-urlencoded").run().assertContent("{f1:'1',f2:'2',f3:'3'}");
140 c.post("/c").contentType("application/x-www-form-urlencoded").formData("f1",4).formData("f2",5).formData("f3",6).run().assertContent("{f1:'4',f2:'5',f3:'6'}");
141
142 c.post("/d").contentType("application/x-www-form-urlencoded").run().assertContent("{f1:'1',f2:'2',f3:'3'}");
143 c.post("/d").contentType("application/x-www-form-urlencoded").formData("f1",7).formData("f2",8).formData("f3",9).run().assertContent("{f1:'7',f2:'8',f3:'9'}");
144 }
145
146
147
148
149
150 @Rest(serializers=Json5Serializer.class)
151 public static class D {
152 @RestPost
153 public Object a(@FormData("f1") Optional<Integer> f1) {
154 assertNotNull(f1);
155 return f1;
156 }
157 @RestPost
158 public Object b(@FormData("f1") Optional<ABean> f1) {
159 assertNotNull(f1);
160 return f1;
161 }
162 @RestPost
163 public Object c(@FormData("f1") Optional<List<ABean>> f1) {
164 assertNotNull(f1);
165 return f1;
166 }
167 @RestPost
168 public Object d(@FormData("f1") List<Optional<ABean>> f1) {
169 return f1;
170 }
171 }
172
173 @Test void d01_optionalParams() throws Exception {
174 var d = MockRestClient.create(D.class).accept("application/json").contentType("application/x-www-form-urlencoded").build();
175
176 d.post("/a", "f1=123")
177 .run()
178 .assertStatus(200)
179 .assertContent("123");
180 d.post("/a", "null")
181 .run()
182 .assertStatus(200)
183 .assertContent("null");
184
185 d.post("/b", "f1=a=1,b=foo")
186 .run()
187 .assertStatus(200)
188 .assertContent("{a:1,b:'foo'}");
189 d.post("/b", "null")
190 .run()
191 .assertStatus(200)
192 .assertContent("null");
193
194 d.post("/c", "f1=@((a=1,b=foo))")
195 .run()
196 .assertStatus(200)
197 .assertContent("[{a:1,b:'foo'}]");
198 d.post("/c", "null")
199 .run()
200 .assertStatus(200)
201 .assertContent("null");
202
203 d.post("/d", "f1=@((a=1,b=foo))")
204 .run()
205 .assertStatus(200)
206 .assertContent("[{a:1,b:'foo'}]");
207 d.post("/d", "null")
208 .run()
209 .assertStatus(200)
210 .assertContent("null");
211 }
212
213
214
215
216
217 @Rest(serializers=Json5Serializer.class)
218 public static class F {
219 @RestPost
220 public Object a1(@FormData(name="f1",def="1") Integer f1) {
221 assertNotNull(f1);
222 return f1;
223 }
224 @RestPost
225 public Object a2(@FormData(name="f1",def="1") Optional<Integer> f1) {
226 assertNotNull(f1);
227 return f1;
228 }
229 @RestPost
230 public Object b1(@FormData(name="f1",def="a=2,b=bar") ABean f1) {
231 assertNotNull(f1);
232 return f1;
233 }
234 @RestPost
235 public Object b2(@FormData(name="f1",def="a=2,b=bar") Optional<ABean> f1) {
236 assertNotNull(f1);
237 return f1;
238 }
239 @RestPost
240 public Object c1(@FormData(name="f1",def="@((a=2,b=bar))") List<ABean> f1) {
241 assertNotNull(f1);
242 return f1;
243 }
244 @RestPost
245 public Object c2(@FormData(name="f1",def="@((a=2,b=bar))") Optional<List<ABean>> f1) {
246 assertNotNull(f1);
247 return f1;
248 }
249 @RestPost
250 public Object d(@FormData(name="f1",def="@((a=2,b=bar))") List<Optional<ABean>> f1) {
251 return f1;
252 }
253 }
254
255 @Test void f01_defaultParams() throws Exception {
256 var f = MockRestClient.create(F.class).accept("application/json").contentType("application/x-www-form-urlencoded").build();
257
258 f.post("/a1", "f1=123")
259 .run()
260 .assertStatus(200)
261 .assertContent("123");
262 f.post("/a1", "")
263 .run()
264 .assertStatus(200)
265 .assertContent("1");
266 f.post("/a2", "f1=123")
267 .run()
268 .assertStatus(200)
269 .assertContent("123");
270 f.post("/a2", "")
271 .run()
272 .assertStatus(200)
273 .assertContent("1");
274
275 f.post("/b1", "f1=a=1,b=foo")
276 .run()
277 .assertStatus(200)
278 .assertContent("{a:1,b:'foo'}");
279 f.post("/b1", "")
280 .run()
281 .assertStatus(200)
282 .assertContent("{a:2,b:'bar'}");
283 f.post("/b2", "f1=a=1,b=foo")
284 .run()
285 .assertStatus(200)
286 .assertContent("{a:1,b:'foo'}");
287 f.post("/b2", "")
288 .run()
289 .assertStatus(200)
290 .assertContent("{a:2,b:'bar'}");
291
292 f.post("/c1", "f1=@((a=1,b=foo))")
293 .run()
294 .assertStatus(200)
295 .assertContent("[{a:1,b:'foo'}]");
296 f.post("/c1", "null")
297 .run()
298 .assertStatus(200)
299 .assertContent("[{a:2,b:'bar'}]");
300 f.post("/c2", "f1=@((a=1,b=foo))")
301 .run()
302 .assertStatus(200)
303 .assertContent("[{a:1,b:'foo'}]");
304 f.post("/c2", "null")
305 .run()
306 .assertStatus(200)
307 .assertContent("[{a:2,b:'bar'}]");
308
309
310 f.post("/d", "f1=@((a=1,b=foo))")
311 .run()
312 .assertStatus(200)
313 .assertContent("[{a:1,b:'foo'}]");
314 f.post("/d", "null")
315 .run()
316 .assertStatus(200)
317 .assertContent("[{a:2,b:'bar'}]");
318 }
319 }