Support content negotiation for RFC 7807
Closes gh-28189
This commit is contained in:
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2002-2021 the original author or authors.
|
||||
* Copyright 2002-2022 the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
@@ -38,6 +38,7 @@ import org.springframework.core.ResolvableType;
|
||||
import org.springframework.core.codec.Hints;
|
||||
import org.springframework.http.HttpLogging;
|
||||
import org.springframework.http.MediaType;
|
||||
import org.springframework.http.ProblemDetail;
|
||||
import org.springframework.http.server.reactive.ServerHttpRequest;
|
||||
import org.springframework.http.server.reactive.ServerHttpResponse;
|
||||
import org.springframework.lang.Nullable;
|
||||
@@ -89,6 +90,8 @@ public abstract class Jackson2CodecSupport {
|
||||
|
||||
private final List<MimeType> mimeTypes;
|
||||
|
||||
private final List<MimeType> problemDetailMimeTypes;
|
||||
|
||||
|
||||
/**
|
||||
* Constructor with a Jackson {@link ObjectMapper} to use.
|
||||
@@ -96,8 +99,15 @@ public abstract class Jackson2CodecSupport {
|
||||
protected Jackson2CodecSupport(ObjectMapper objectMapper, MimeType... mimeTypes) {
|
||||
Assert.notNull(objectMapper, "ObjectMapper must not be null");
|
||||
this.defaultObjectMapper = objectMapper;
|
||||
this.mimeTypes = !ObjectUtils.isEmpty(mimeTypes) ?
|
||||
List.of(mimeTypes) : DEFAULT_MIME_TYPES;
|
||||
this.mimeTypes = (!ObjectUtils.isEmpty(mimeTypes) ? List.of(mimeTypes) : DEFAULT_MIME_TYPES);
|
||||
this.problemDetailMimeTypes = initProblemDetailMediaTypes(this.mimeTypes);
|
||||
}
|
||||
|
||||
private static List<MimeType> initProblemDetailMediaTypes(List<MimeType> supportedMimeTypes) {
|
||||
List<MimeType> mimeTypes = new ArrayList<>();
|
||||
mimeTypes.add(MediaType.APPLICATION_PROBLEM_JSON);
|
||||
mimeTypes.addAll(supportedMimeTypes);
|
||||
return Collections.unmodifiableList(mimeTypes);
|
||||
}
|
||||
|
||||
|
||||
@@ -180,7 +190,10 @@ public abstract class Jackson2CodecSupport {
|
||||
result.addAll(entry.getValue().keySet());
|
||||
}
|
||||
}
|
||||
return (CollectionUtils.isEmpty(result) ? getMimeTypes() : result);
|
||||
if (!CollectionUtils.isEmpty(result)) {
|
||||
return result;
|
||||
}
|
||||
return (ProblemDetail.class.isAssignableFrom(elementClass) ? this.problemDetailMimeTypes : getMimeTypes());
|
||||
}
|
||||
|
||||
protected boolean supportsMimeType(@Nullable MimeType mimeType) {
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2002-2021 the original author or authors.
|
||||
* Copyright 2002-2022 the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
@@ -100,12 +100,12 @@ public abstract class AbstractHttpMessageConverter<T> implements HttpMessageConv
|
||||
*/
|
||||
public void setSupportedMediaTypes(List<MediaType> supportedMediaTypes) {
|
||||
Assert.notEmpty(supportedMediaTypes, "MediaType List must not be empty");
|
||||
this.supportedMediaTypes = new ArrayList<>(supportedMediaTypes);
|
||||
this.supportedMediaTypes = Collections.unmodifiableList(new ArrayList<>(supportedMediaTypes));
|
||||
}
|
||||
|
||||
@Override
|
||||
public List<MediaType> getSupportedMediaTypes() {
|
||||
return Collections.unmodifiableList(this.supportedMediaTypes);
|
||||
return this.supportedMediaTypes;
|
||||
}
|
||||
|
||||
/**
|
||||
|
||||
@@ -53,6 +53,7 @@ import org.springframework.core.GenericTypeResolver;
|
||||
import org.springframework.http.HttpInputMessage;
|
||||
import org.springframework.http.HttpOutputMessage;
|
||||
import org.springframework.http.MediaType;
|
||||
import org.springframework.http.ProblemDetail;
|
||||
import org.springframework.http.converter.AbstractGenericHttpMessageConverter;
|
||||
import org.springframework.http.converter.HttpMessageConversionException;
|
||||
import org.springframework.http.converter.HttpMessageConverter;
|
||||
@@ -92,6 +93,8 @@ public abstract class AbstractJackson2HttpMessageConverter extends AbstractGener
|
||||
}
|
||||
|
||||
|
||||
private List<MediaType> problemDetailMediaTypes = Collections.singletonList(MediaType.APPLICATION_PROBLEM_JSON);
|
||||
|
||||
protected ObjectMapper defaultObjectMapper;
|
||||
|
||||
@Nullable
|
||||
@@ -122,6 +125,19 @@ public abstract class AbstractJackson2HttpMessageConverter extends AbstractGener
|
||||
}
|
||||
|
||||
|
||||
@Override
|
||||
public void setSupportedMediaTypes(List<MediaType> supportedMediaTypes) {
|
||||
this.problemDetailMediaTypes = initProblemDetailMediaTypes(supportedMediaTypes);
|
||||
super.setSupportedMediaTypes(supportedMediaTypes);
|
||||
}
|
||||
|
||||
private List<MediaType> initProblemDetailMediaTypes(List<MediaType> supportedMediaTypes) {
|
||||
List<MediaType> mediaTypes = new ArrayList<>();
|
||||
mediaTypes.add(MediaType.APPLICATION_PROBLEM_JSON);
|
||||
mediaTypes.addAll(supportedMediaTypes);
|
||||
return Collections.unmodifiableList(mediaTypes);
|
||||
}
|
||||
|
||||
/**
|
||||
* Configure the main {@code ObjectMapper} to use for Object conversion.
|
||||
* If not set, a default {@link ObjectMapper} instance is created.
|
||||
@@ -198,7 +214,11 @@ public abstract class AbstractJackson2HttpMessageConverter extends AbstractGener
|
||||
result.addAll(entry.getValue().keySet());
|
||||
}
|
||||
}
|
||||
return (CollectionUtils.isEmpty(result) ? getSupportedMediaTypes() : result);
|
||||
if (!CollectionUtils.isEmpty(result)) {
|
||||
return result;
|
||||
}
|
||||
return (ProblemDetail.class.isAssignableFrom(clazz) ?
|
||||
this.problemDetailMediaTypes : getSupportedMediaTypes());
|
||||
}
|
||||
|
||||
private Map<Class<?>, Map<MediaType, ObjectMapper>> getObjectMapperRegistrations() {
|
||||
|
||||
Reference in New Issue
Block a user