Previously, using Spring Boot 3.3.7 & Spring Cloud 2023.0.3, it was possible to mutate a request inside of a void method.

For example, simply by calling mutate on an ServerHttpRequest object, it was possible to update the request without reassigning the variable.

In the screenshot below, I am able to mutate the request headers on the original object (request), without reassigning the variable.

Image

However, with the latest Spring Boot 3.4.2 & Spring Cloud 2024.0.0, this is no longer working. Now, it looks like the request object must have it's pointer reassigned.

Image

This seems to have been asked as-well on StackOverflow. However, the suggestion to reassign the variable seems to require unnecessary refactor.

Is this a bug or just something the community will have to deal with?

Here's an example in our application where this ability was previously useful:

Image

Image

POC Code:


@ExtendWith(MockitoExtension.class)
class HeadersUtilTest {

  @Test
  @DisplayName("Should Add Header to Request")
  void shouldAddHeaderToRequest() {
    ServerHttpRequest request = MockServerHttpRequest.post("/unit-test").build();

    ServerHttpRequest mutated = request.mutate().header("x", "y").build();

    boolean worksMutated = mutated.getHeaders().containsKey("x");
    assertTrue(worksMutated);

    boolean worksOriginal = request.getHeaders().containsKey("x");  // used to work on 3.3.7 , is broken on 3.4.2
    assertTrue(worksOriginal);
}

Comment From: bclozel

This works as designed. This previous behavior was a bug and was probably fixed by #33666. I think this was raised already in #34246.

I'm sorry but we can't reinstate the previous behavior. You'll have to use the mutate API as intended, creating a new instance as requests are meant to be immutable.