2525import java .nio .charset .Charset ;
2626import java .nio .charset .StandardCharsets ;
2727import java .security .Principal ;
28+ import java .text .SimpleDateFormat ;
2829import java .util .ArrayList ;
2930import java .util .Arrays ;
31+ import java .util .Collection ;
32+ import java .util .Date ;
3033import java .util .LinkedHashMap ;
3134import java .util .List ;
3235import java .util .Locale ;
3336import java .util .Map ;
37+ import java .util .TimeZone ;
3438
3539import jakarta .servlet .ServletContext ;
3640import jakarta .servlet .ServletRequest ;
8387public abstract class AbstractMockHttpServletRequestBuilder <B extends AbstractMockHttpServletRequestBuilder <B >>
8488implements ConfigurableSmartRequestBuilder <B >, Mergeable {
8589
90+ private static final SimpleDateFormat simpleDateFormat ;
91+
92+ static {
93+ simpleDateFormat = new SimpleDateFormat ("EEE, dd MMM yyyy HH:mm:ss zzz" , Locale .US );
94+ simpleDateFormat .setTimeZone (TimeZone .getTimeZone ("GMT" ));
95+ }
96+
97+
8698private final HttpMethod method ;
8799
88100private @ Nullable String uriTemplate ;
@@ -109,7 +121,7 @@ public abstract class AbstractMockHttpServletRequestBuilder<B extends AbstractMo
109121
110122private @ Nullable String contentType ;
111123
112- private final MultiValueMap < String , Object > headers = new LinkedMultiValueMap <> ();
124+ private final HttpHeaders headers = new HttpHeaders ();
113125
114126private final MultiValueMap <String , String > parameters = new LinkedMultiValueMap <>();
115127
@@ -320,7 +332,7 @@ public B contentType(String contentType) {
320332 */
321333public B accept (MediaType ... mediaTypes ) {
322334Assert .notEmpty (mediaTypes , "'mediaTypes' must not be empty" );
323- this .headers .set ( "Accept" , MediaType . toString ( Arrays .asList (mediaTypes ) ));
335+ this .headers .setAccept ( Arrays .asList (mediaTypes ));
324336return self ();
325337}
326338
@@ -342,7 +354,26 @@ public B accept(String... mediaTypes) {
342354 * @param values one or more header values
343355 */
344356public B header (String name , Object ... values ) {
345- this .headers .addAll (name , Arrays .asList (values ));
357+
358+ // Prior to 7.0, header values were passed as Objects to MockHttpServletRequest.
359+ // Here we add some formatting for backwards compatibility.
360+
361+ if (values .length == 1 ) {
362+ Object value = values [0 ];
363+ if (value instanceof Collection <?> collection ) {
364+ values = collection .toArray ();
365+ }
366+ }
367+
368+ for (Object value : values ) {
369+ if (value instanceof Date date ) {
370+ this .headers .add (name , simpleDateFormat .format (date ));
371+ }
372+ else {
373+ this .headers .add (name , String .valueOf (value ));
374+ }
375+ }
376+
346377return self ();
347378}
348379
@@ -665,12 +696,13 @@ public Object merge(@Nullable Object parent) {
665696this .contentType = parentBuilder .contentType ;
666697}
667698
668- for (Map .Entry <String , List <Object >> entry : parentBuilder .headers .entrySet ()) {
669- String headerName = entry .getKey ();
670- if (!this .headers .containsKey (headerName )) {
671- this .headers .put (headerName , entry .getValue ());
672- }
673- }
699+ parentBuilder .headers .forEach ((headerName , values ) -> {
700+ values .forEach (value -> {
701+ if (!this .headers .containsHeader (headerName )) {
702+ this .headers .put (headerName , values );
703+ }
704+ });
705+ });
674706for (Map .Entry <String , List <String >> entry : parentBuilder .parameters .entrySet ()) {
675707String paramName = entry .getKey ();
676708if (!this .parameters .containsKey (paramName )) {
@@ -796,9 +828,7 @@ public final MockHttpServletRequest buildRequest(ServletContext servletContext)
796828
797829if (this .version != null ) {
798830Assert .state (this .versionInserter != null , "No ApiVersionInserter" );
799- HttpHeaders httpHeaders = new HttpHeaders ();
800- this .versionInserter .insertVersion (this .version , httpHeaders );
801- httpHeaders .forEach ((name , values ) -> values .forEach (value -> this .headers .add (name , value )));
831+ this .versionInserter .insertVersion (this .version , this .headers );
802832}
803833
804834this .headers .forEach ((name , values ) -> {
@@ -808,8 +838,8 @@ public final MockHttpServletRequest buildRequest(ServletContext servletContext)
808838});
809839
810840if (!ObjectUtils .isEmpty (this .content ) &&
811- !this .headers .containsKey (HttpHeaders .CONTENT_LENGTH ) &&
812- !this .headers .containsKey (HttpHeaders .TRANSFER_ENCODING )) {
841+ !this .headers .containsHeader (HttpHeaders .CONTENT_LENGTH ) &&
842+ !this .headers .containsHeader (HttpHeaders .TRANSFER_ENCODING )) {
813843
814844request .addHeader (HttpHeaders .CONTENT_LENGTH , this .content .length );
815845}
0 commit comments