Remove "with" methods in ProblemDetail

ProblemDetail is intended to be extended with additional fields. This
commit removes its "with" methods for chained initialization to keep
it as plain as possible and avoid imposing a particular style on
subclasses.

See gh-27052
This commit is contained in:
rstoyanchev 2022-06-24 11:08:32 +01:00
parent c139f3d526
commit 98c7d8100d
7 changed files with 25 additions and 79 deletions

View File

@ -90,75 +90,10 @@ public class ProblemDetail {
}
/**
* Variant of {@link #setType(URI)} for chained initialization.
* @param type the problem type
* @return the same instance
*/
public ProblemDetail withType(URI type) {
setType(type);
return this;
}
/**
* Variant of {@link #setTitle(String)} for chained initialization.
* @param title the problem title
* @return the same instance
*/
public ProblemDetail withTitle(@Nullable String title) {
setTitle(title);
return this;
}
/**
* Variant of {@link #setStatus(int)} for chained initialization.
* @param statusCode the response status for the problem
* @return the same instance
*/
public ProblemDetail withStatus(HttpStatusCode statusCode) {
Assert.notNull(statusCode, "HttpStatus is required");
setStatus(statusCode.value());
return this;
}
/**
* Variant of {@link #setStatus(int)} for chained initialization.
* @param status the response status value for the problem
* @return the same instance
*/
public ProblemDetail withStatus(int status) {
setStatus(status);
return this;
}
/**
* Variant of {@link #setDetail(String)} for chained initialization.
* @param detail the problem detail
* @return the same instance
*/
public ProblemDetail withDetail(@Nullable String detail) {
setDetail(detail);
return this;
}
/**
* Variant of {@link #setInstance(URI)} for chained initialization.
* @param instance the problem instance URI
* @return the same instance
*/
public ProblemDetail withInstance(@Nullable URI instance) {
setInstance(instance);
return this;
}
// Setters for deserialization
/**
* Setter for the {@link #getType() problem type}.
* <p>By default, this is {@link #BLANK_TYPE}.
* @param type the problem type
* @see #withType(URI)
*/
public void setType(URI type) {
Assert.notNull(type, "'type' is required");
@ -170,17 +105,22 @@ public class ProblemDetail {
* <p>By default, if not explicitly set and the status is well-known, this
* is sourced from the {@link HttpStatus#getReasonPhrase()}.
* @param title the problem title
* @see #withTitle(String)
*/
public void setTitle(@Nullable String title) {
this.title = title;
}
/**
* Setter for the {@link #getStatus() problem status}.
* @param httpStatus the problem status
*/
public void setStatus(HttpStatus httpStatus) {
this.status = httpStatus.value();
}
/**
* Setter for the {@link #getStatus() problem status}.
* @param status the problem status
* @see #withStatus(HttpStatusCode)
* @see #withStatus(int)
*/
public void setStatus(int status) {
this.status = status;
@ -190,7 +130,6 @@ public class ProblemDetail {
* Setter for the {@link #getDetail() problem detail}.
* <p>By default, this is not set.
* @param detail the problem detail
* @see #withDetail(String)
*/
public void setDetail(@Nullable String detail) {
this.detail = detail;
@ -201,7 +140,6 @@ public class ProblemDetail {
* <p>By default, when {@code ProblemDetail} is returned from an
* {@code @ExceptionHandler} method, this is initialized to the request path.
* @param instance the problem instance
* @see #withInstance(URI)
*/
public void setInstance(@Nullable URI instance) {
this.instance = instance;
@ -219,9 +157,6 @@ public class ProblemDetail {
}
// Getters
/**
* Return the configured {@link #setType(URI) problem type}.
*/
@ -312,4 +247,14 @@ public class ProblemDetail {
return new ProblemDetail(status);
}
/**
* Create a {@code ProblemDetail} instance with the given status and detail.
*/
public static ProblemDetail forStatusAndDetail(HttpStatusCode status, String detail) {
Assert.notNull(status, "HttpStatusCode is required");
ProblemDetail problemDetail = forStatus(status.value());
problemDetail.setDetail(detail);
return problemDetail;
}
}

View File

@ -96,7 +96,7 @@ public class HttpRequestMethodNotSupportedException extends ServletException imp
this.supportedMethods = supportedMethods;
String detail = "Method '" + method + "' is not supported.";
this.body = ProblemDetail.forStatus(getStatusCode()).withDetail(detail);
this.body = ProblemDetail.forStatusAndDetail(getStatusCode(), detail);
}

View File

@ -49,7 +49,7 @@ public class MethodArgumentNotValidException extends BindException implements Er
public MethodArgumentNotValidException(MethodParameter parameter, BindingResult bindingResult) {
super(bindingResult);
this.parameter = parameter;
this.body = ProblemDetail.forStatus(getStatusCode()).withDetail("Invalid request content.");
this.body = ProblemDetail.forStatusAndDetail(getStatusCode(), "Invalid request content.");
}
@Override

View File

@ -40,7 +40,7 @@ public class MissingRequestValueException extends ServerWebInputException {
this.name = name;
this.type = type;
this.label = label;
getBody().withDetail(getReason());
getBody().setDetail(getReason());
}

View File

@ -42,7 +42,7 @@ public class UnsatisfiedRequestParameterException extends ServerWebInputExceptio
super(initReason(conditions, requestParams));
this.conditions = conditions;
this.requestParams = requestParams;
getBody().withDetail("Invalid request parameters.");
getBody().setDetail("Invalid request parameters.");
}
private static String initReason(List<String> conditions, MultiValueMap<String, String> queryParams) {

View File

@ -60,7 +60,7 @@ public class NoHandlerFoundException extends ServletException implements ErrorRe
this.httpMethod = httpMethod;
this.requestURL = requestURL;
this.headers = headers;
this.body = ProblemDetail.forStatus(getStatusCode()).withDetail(getMessage());
this.body = ProblemDetail.forStatusAndDetail(getStatusCode(), getMessage());
}
@Override

View File

@ -434,7 +434,8 @@ public class RequestResponseBodyMethodProcessorTests {
"\"title\":\"Bad Request\"," +
"\"status\":400," +
"\"detail\":null," +
"\"instance\":\"/path\"}");
"\"instance\":\"/path\"," +
"\"properties\":null}");
}
@Test // SPR-13135