You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@camel.apache.org by da...@apache.org on 2026/09/02 11:34:50 UTC
(camel) branch backport/CAMEL-24460-4.22.x created (now b2a5b71bae8f)
This is an automated email from the ASF dual-hosted git repository.
davsclaus pushed a change to branch backport/CAMEL-24460-4.22.x
in repository https://gitbox.apache.org/repos/asf/camel.git
at b2a5b71bae8f CAMEL-24460: Mark ProducerTemplate body, header and property values as @Nullable
This branch includes the following new commits:
new b2a5b71bae8f CAMEL-24460: Mark ProducerTemplate body, header and property values as @Nullable
The 1 revisions listed above as "new" are entirely new to this
repository and will be described in separate emails. The revisions
listed as "add" were already present in the repository and have only
been added to this reference.
(camel) 01/01: CAMEL-24460: Mark ProducerTemplate body, header and property values as @Nullable
Posted by da...@apache.org.
This is an automated email from the ASF dual-hosted git repository.
davsclaus pushed a commit to branch backport/CAMEL-24460-4.22.x
in repository https://gitbox.apache.org/repos/asf/camel.git
commit b2a5b71bae8fea005b97d354b0fdf09e784e168f
Author: Claus Ibsen <cl...@gmail.com>
AuthorDate: Wed Sep 2 13:32:49 2026 +0200
CAMEL-24460: Mark ProducerTemplate body, header and property values as @Nullable
The org.apache.camel package is @NullMarked, so unannotated reference
parameters are treated as non-null under JSpecify. Camel supports null
message bodies at runtime, and the sibling FluentProducerTemplate already
annotates its withBody/withHeader/withExchangeProperty values as @Nullable.
ProducerTemplate was missed in that rollout.
Align ProducerTemplate by marking body, header value and property value
parameters as @Nullable. Header/property names and the headers Map stay
non-null (keys cannot be null). Annotation-only change with no runtime or
binary compatibility impact. Adds a test driving a null body, header value
and property value through the API end-to-end.
Closes #26032
Co-authored-by: Claude Opus 4.8 <no...@anthropic.com>
(cherry picked from commit 01b6fd55c000e1b012bfc2aa71eaaab5de79096b)
---
.../java/org/apache/camel/ProducerTemplate.java | 121 ++++++++++++---------
.../camel/impl/DefaultProducerTemplateTest.java | 30 +++++
2 files changed, 97 insertions(+), 54 deletions(-)
diff --git a/core/camel-api/src/main/java/org/apache/camel/ProducerTemplate.java b/core/camel-api/src/main/java/org/apache/camel/ProducerTemplate.java
index 6406786c81d3..09f62b7d851b 100644
--- a/core/camel-api/src/main/java/org/apache/camel/ProducerTemplate.java
+++ b/core/camel-api/src/main/java/org/apache/camel/ProducerTemplate.java
@@ -190,7 +190,7 @@ public interface ProducerTemplate extends Service {
* @param body the payload to send
* @throws CamelExecutionException if the processing of the exchange failed
*/
- void sendBody(Object body) throws CamelExecutionException;
+ void sendBody(@Nullable Object body) throws CamelExecutionException;
/**
* Sends the body to the default endpoint with a specified header and header value <br/>
@@ -204,7 +204,7 @@ public interface ProducerTemplate extends Service {
* @param headerValue the header value
* @throws CamelExecutionException if the processing of the exchange failed
*/
- void sendBodyAndHeader(Object body, String header, Object headerValue) throws CamelExecutionException;
+ void sendBodyAndHeader(@Nullable Object body, String header, @Nullable Object headerValue) throws CamelExecutionException;
/**
* Sends the body to the default endpoint with a specified property and property value <br/>
@@ -218,7 +218,8 @@ public interface ProducerTemplate extends Service {
* @param propertyValue the property value
* @throws CamelExecutionException if the processing of the exchange failed
*/
- void sendBodyAndProperty(Object body, String property, Object propertyValue) throws CamelExecutionException;
+ void sendBodyAndProperty(@Nullable Object body, String property, @Nullable Object propertyValue)
+ throws CamelExecutionException;
/**
* Sends the body to the default endpoint with the specified headers and header values <br/>
@@ -231,7 +232,7 @@ public interface ProducerTemplate extends Service {
* @param headers the headers
* @throws CamelExecutionException if the processing of the exchange failed
*/
- void sendBodyAndHeaders(Object body, Map<String, Object> headers) throws CamelExecutionException;
+ void sendBodyAndHeaders(@Nullable Object body, Map<String, Object> headers) throws CamelExecutionException;
// Allow sending to arbitrary endpoints
// -----------------------------------------------------------------------
@@ -349,7 +350,7 @@ public interface ProducerTemplate extends Service {
* @param body the payload
* @throws CamelExecutionException if the processing of the exchange failed
*/
- void sendBody(Endpoint endpoint, Object body) throws CamelExecutionException;
+ void sendBody(Endpoint endpoint, @Nullable Object body) throws CamelExecutionException;
/**
* Send the body to an endpoint <br/>
@@ -362,7 +363,7 @@ public interface ProducerTemplate extends Service {
* @param body the payload
* @throws CamelExecutionException if the processing of the exchange failed
*/
- void sendBody(String endpointUri, Object body) throws CamelExecutionException;
+ void sendBody(String endpointUri, @Nullable Object body) throws CamelExecutionException;
/**
* Send the body to an endpoint with the given {@link ExchangePattern} returning any result output body <br/>
@@ -379,7 +380,7 @@ public interface ProducerTemplate extends Service {
* @throws CamelExecutionException if the processing of the exchange failed
*/
@Nullable
- Object sendBody(Endpoint endpoint, ExchangePattern pattern, Object body) throws CamelExecutionException;
+ Object sendBody(Endpoint endpoint, ExchangePattern pattern, @Nullable Object body) throws CamelExecutionException;
/**
* Send the body to an endpoint returning any result output body <br/>
@@ -396,7 +397,7 @@ public interface ProducerTemplate extends Service {
* @throws CamelExecutionException if the processing of the exchange failed
*/
@Nullable
- Object sendBody(String endpointUri, ExchangePattern pattern, Object body) throws CamelExecutionException;
+ Object sendBody(String endpointUri, ExchangePattern pattern, @Nullable Object body) throws CamelExecutionException;
/**
* Sends the body to an endpoint with a specified header and header value <br/>
@@ -411,7 +412,8 @@ public interface ProducerTemplate extends Service {
* @param headerValue the header value
* @throws CamelExecutionException if the processing of the exchange failed
*/
- void sendBodyAndHeader(String endpointUri, Object body, String header, Object headerValue) throws CamelExecutionException;
+ void sendBodyAndHeader(String endpointUri, @Nullable Object body, String header, @Nullable Object headerValue)
+ throws CamelExecutionException;
/**
* Sends the body to an endpoint with a specified header and header value <br/>
@@ -426,7 +428,8 @@ public interface ProducerTemplate extends Service {
* @param headerValue the header value
* @throws CamelExecutionException if the processing of the exchange failed
*/
- void sendBodyAndHeader(Endpoint endpoint, Object body, String header, Object headerValue) throws CamelExecutionException;
+ void sendBodyAndHeader(Endpoint endpoint, @Nullable Object body, String header, @Nullable Object headerValue)
+ throws CamelExecutionException;
/**
* Sends the body to an endpoint with a specified header and header value <br/>
@@ -446,8 +449,8 @@ public interface ProducerTemplate extends Service {
*/
@Nullable
Object sendBodyAndHeader(
- Endpoint endpoint, ExchangePattern pattern, Object body,
- String header, Object headerValue)
+ Endpoint endpoint, ExchangePattern pattern, @Nullable Object body,
+ String header, @Nullable Object headerValue)
throws CamelExecutionException;
/**
@@ -468,8 +471,8 @@ public interface ProducerTemplate extends Service {
*/
@Nullable
Object sendBodyAndHeader(
- String endpoint, ExchangePattern pattern, Object body,
- String header, Object headerValue)
+ String endpoint, ExchangePattern pattern, @Nullable Object body,
+ String header, @Nullable Object headerValue)
throws CamelExecutionException;
/**
@@ -485,7 +488,7 @@ public interface ProducerTemplate extends Service {
* @param propertyValue the property value
* @throws CamelExecutionException if the processing of the exchange failed
*/
- void sendBodyAndProperty(String endpointUri, Object body, String property, Object propertyValue)
+ void sendBodyAndProperty(String endpointUri, @Nullable Object body, String property, @Nullable Object propertyValue)
throws CamelExecutionException;
/**
@@ -501,7 +504,7 @@ public interface ProducerTemplate extends Service {
* @param propertyValue the property value
* @throws CamelExecutionException if the processing of the exchange failed
*/
- void sendBodyAndProperty(Endpoint endpoint, Object body, String property, Object propertyValue)
+ void sendBodyAndProperty(Endpoint endpoint, @Nullable Object body, String property, @Nullable Object propertyValue)
throws CamelExecutionException;
/**
@@ -522,8 +525,8 @@ public interface ProducerTemplate extends Service {
*/
@Nullable
Object sendBodyAndProperty(
- Endpoint endpoint, ExchangePattern pattern, Object body,
- String property, Object propertyValue)
+ Endpoint endpoint, ExchangePattern pattern, @Nullable Object body,
+ String property, @Nullable Object propertyValue)
throws CamelExecutionException;
/**
@@ -544,8 +547,8 @@ public interface ProducerTemplate extends Service {
*/
@Nullable
Object sendBodyAndProperty(
- String endpoint, ExchangePattern pattern, Object body,
- String property, Object propertyValue)
+ String endpoint, ExchangePattern pattern, @Nullable Object body,
+ String property, @Nullable Object propertyValue)
throws CamelExecutionException;
/**
@@ -560,7 +563,8 @@ public interface ProducerTemplate extends Service {
* @param headers headers
* @throws CamelExecutionException if the processing of the exchange failed
*/
- void sendBodyAndHeaders(String endpointUri, Object body, Map<String, Object> headers) throws CamelExecutionException;
+ void sendBodyAndHeaders(String endpointUri, @Nullable Object body, Map<String, Object> headers)
+ throws CamelExecutionException;
/**
* Sends the body to an endpoint with the specified headers and header values <br/>
@@ -574,7 +578,8 @@ public interface ProducerTemplate extends Service {
* @param headers headers
* @throws CamelExecutionException if the processing of the exchange failed
*/
- void sendBodyAndHeaders(Endpoint endpoint, Object body, Map<String, Object> headers) throws CamelExecutionException;
+ void sendBodyAndHeaders(Endpoint endpoint, @Nullable Object body, Map<String, Object> headers)
+ throws CamelExecutionException;
/**
* Sends the body to an endpoint with the specified headers and header values <br/>
@@ -593,7 +598,7 @@ public interface ProducerTemplate extends Service {
*/
@Nullable
Object sendBodyAndHeaders(
- String endpointUri, ExchangePattern pattern, Object body,
+ String endpointUri, ExchangePattern pattern, @Nullable Object body,
Map<String, Object> headers)
throws CamelExecutionException;
@@ -614,7 +619,7 @@ public interface ProducerTemplate extends Service {
*/
@Nullable
Object sendBodyAndHeaders(
- Endpoint endpoint, ExchangePattern pattern, Object body,
+ Endpoint endpoint, ExchangePattern pattern, @Nullable Object body,
Map<String, Object> headers)
throws CamelExecutionException;
@@ -662,7 +667,7 @@ public interface ProducerTemplate extends Service {
* @throws CamelExecutionException if the processing of the exchange failed
*/
@Nullable
- Object requestBody(Object body) throws CamelExecutionException;
+ Object requestBody(@Nullable Object body) throws CamelExecutionException;
/**
* Sends the body to the default endpoint and returns the result content Uses an {@link ExchangePattern#InOut}
@@ -677,7 +682,7 @@ public interface ProducerTemplate extends Service {
* @return the result (see class javadoc)
* @throws CamelExecutionException if the processing of the exchange failed
*/
- <T> @Nullable T requestBody(Object body, Class<T> type) throws CamelExecutionException;
+ <T> @Nullable T requestBody(@Nullable Object body, Class<T> type) throws CamelExecutionException;
/**
* Send the body to an endpoint returning any result output body. Uses an {@link ExchangePattern#InOut} message
@@ -693,7 +698,7 @@ public interface ProducerTemplate extends Service {
* @throws CamelExecutionException if the processing of the exchange failed
*/
@Nullable
- Object requestBody(Endpoint endpoint, Object body) throws CamelExecutionException;
+ Object requestBody(Endpoint endpoint, @Nullable Object body) throws CamelExecutionException;
/**
* Send the body to an endpoint returning any result output body. Uses an {@link ExchangePattern#InOut} message
@@ -709,7 +714,7 @@ public interface ProducerTemplate extends Service {
* @return the result (see class javadoc)
* @throws CamelExecutionException if the processing of the exchange failed
*/
- <T> @Nullable T requestBody(Endpoint endpoint, Object body, Class<T> type) throws CamelExecutionException;
+ <T> @Nullable T requestBody(Endpoint endpoint, @Nullable Object body, Class<T> type) throws CamelExecutionException;
/**
* Send the body to an endpoint returning any result output body. Uses an {@link ExchangePattern#InOut} message
@@ -725,7 +730,7 @@ public interface ProducerTemplate extends Service {
* @throws CamelExecutionException if the processing of the exchange failed
*/
@Nullable
- Object requestBody(String endpointUri, Object body) throws CamelExecutionException;
+ Object requestBody(String endpointUri, @Nullable Object body) throws CamelExecutionException;
/**
* Send the body to an endpoint returning any result output body. Uses an {@link ExchangePattern#InOut} message
@@ -741,7 +746,7 @@ public interface ProducerTemplate extends Service {
* @return the result (see class javadoc)
* @throws CamelExecutionException if the processing of the exchange failed
*/
- <T> @Nullable T requestBody(String endpointUri, Object body, Class<T> type) throws CamelExecutionException;
+ <T> @Nullable T requestBody(String endpointUri, @Nullable Object body, Class<T> type) throws CamelExecutionException;
/**
* Sends the body to the default endpoint and returns the result content Uses an {@link ExchangePattern#InOut}
@@ -758,7 +763,8 @@ public interface ProducerTemplate extends Service {
* @throws CamelExecutionException if the processing of the exchange failed
*/
@Nullable
- Object requestBodyAndHeader(Object body, String header, Object headerValue) throws CamelExecutionException;
+ Object requestBodyAndHeader(@Nullable Object body, String header, @Nullable Object headerValue)
+ throws CamelExecutionException;
/**
* Send the body to an endpoint returning any result output body. Uses an {@link ExchangePattern#InOut} message
@@ -776,7 +782,7 @@ public interface ProducerTemplate extends Service {
* @throws CamelExecutionException if the processing of the exchange failed
*/
@Nullable
- Object requestBodyAndHeader(Endpoint endpoint, Object body, String header, Object headerValue)
+ Object requestBodyAndHeader(Endpoint endpoint, @Nullable Object body, String header, @Nullable Object headerValue)
throws CamelExecutionException;
/**
@@ -795,7 +801,8 @@ public interface ProducerTemplate extends Service {
* @return the result (see class javadoc)
* @throws CamelExecutionException if the processing of the exchange failed
*/
- <T> @Nullable T requestBodyAndHeader(Endpoint endpoint, Object body, String header, Object headerValue, Class<T> type)
+ <T> @Nullable T requestBodyAndHeader(
+ Endpoint endpoint, @Nullable Object body, String header, @Nullable Object headerValue, Class<T> type)
throws CamelExecutionException;
/**
@@ -814,7 +821,7 @@ public interface ProducerTemplate extends Service {
* @throws CamelExecutionException if the processing of the exchange failed
*/
@Nullable
- Object requestBodyAndHeader(String endpointUri, Object body, String header, Object headerValue)
+ Object requestBodyAndHeader(String endpointUri, @Nullable Object body, String header, @Nullable Object headerValue)
throws CamelExecutionException;
/**
@@ -833,7 +840,8 @@ public interface ProducerTemplate extends Service {
* @return the result (see class javadoc)
* @throws CamelExecutionException if the processing of the exchange failed
*/
- <T> @Nullable T requestBodyAndHeader(String endpointUri, Object body, String header, Object headerValue, Class<T> type)
+ <T> @Nullable T requestBodyAndHeader(
+ String endpointUri, @Nullable Object body, String header, @Nullable Object headerValue, Class<T> type)
throws CamelExecutionException;
/**
@@ -851,7 +859,8 @@ public interface ProducerTemplate extends Service {
* @throws CamelExecutionException if the processing of the exchange failed
*/
@Nullable
- Object requestBodyAndHeaders(String endpointUri, Object body, Map<String, Object> headers) throws CamelExecutionException;
+ Object requestBodyAndHeaders(String endpointUri, @Nullable Object body, Map<String, Object> headers)
+ throws CamelExecutionException;
/**
* Sends the body to an endpoint with the specified headers and header values. Uses an {@link ExchangePattern#InOut}
@@ -868,7 +877,7 @@ public interface ProducerTemplate extends Service {
* @return the result (see class javadoc)
* @throws CamelExecutionException if the processing of the exchange failed
*/
- <T> @Nullable T requestBodyAndHeaders(String endpointUri, Object body, Map<String, Object> headers, Class<T> type)
+ <T> @Nullable T requestBodyAndHeaders(String endpointUri, @Nullable Object body, Map<String, Object> headers, Class<T> type)
throws CamelExecutionException;
/**
@@ -886,7 +895,8 @@ public interface ProducerTemplate extends Service {
* @throws CamelExecutionException if the processing of the exchange failed
*/
@Nullable
- Object requestBodyAndHeaders(Endpoint endpoint, Object body, Map<String, Object> headers) throws CamelExecutionException;
+ Object requestBodyAndHeaders(Endpoint endpoint, @Nullable Object body, Map<String, Object> headers)
+ throws CamelExecutionException;
/**
* Sends the body to the default endpoint and returns the result content Uses an {@link ExchangePattern#InOut}
@@ -902,7 +912,7 @@ public interface ProducerTemplate extends Service {
* @throws CamelExecutionException if the processing of the exchange failed
*/
@Nullable
- Object requestBodyAndHeaders(Object body, Map<String, Object> headers) throws CamelExecutionException;
+ Object requestBodyAndHeaders(@Nullable Object body, Map<String, Object> headers) throws CamelExecutionException;
/**
* Sends the body to an endpoint with the specified headers and header values. Uses an {@link ExchangePattern#InOut}
@@ -919,7 +929,7 @@ public interface ProducerTemplate extends Service {
* @return the result (see class javadoc)
* @throws CamelExecutionException if the processing of the exchange failed
*/
- <T> @Nullable T requestBodyAndHeaders(Endpoint endpoint, Object body, Map<String, Object> headers, Class<T> type)
+ <T> @Nullable T requestBodyAndHeaders(Endpoint endpoint, @Nullable Object body, Map<String, Object> headers, Class<T> type)
throws CamelExecutionException;
// Asynchronous methods
@@ -962,7 +972,7 @@ public interface ProducerTemplate extends Service {
* @param body the body to send
* @return a handle to be used to get the response in the future
*/
- CompletableFuture<Object> asyncSendBody(String endpointUri, Object body);
+ CompletableFuture<Object> asyncSendBody(String endpointUri, @Nullable Object body);
/**
* Sends an asynchronous body to the given endpoint. Uses an {@link ExchangePattern#InOut} message exchange pattern.
@@ -971,7 +981,7 @@ public interface ProducerTemplate extends Service {
* @param body the body to send
* @return a handle to be used to get the response in the future
*/
- CompletableFuture<Object> asyncRequestBody(String endpointUri, Object body);
+ CompletableFuture<Object> asyncRequestBody(String endpointUri, @Nullable Object body);
/**
* Sends an asynchronous body to the given endpoint. Uses an {@link ExchangePattern#InOut} message exchange pattern.
@@ -982,7 +992,8 @@ public interface ProducerTemplate extends Service {
* @param headerValue the header value
* @return a handle to be used to get the response in the future
*/
- CompletableFuture<Object> asyncRequestBodyAndHeader(String endpointUri, Object body, String header, Object headerValue);
+ CompletableFuture<Object> asyncRequestBodyAndHeader(
+ String endpointUri, @Nullable Object body, String header, @Nullable Object headerValue);
/**
* Sends an asynchronous body to the given endpoint. Uses an {@link ExchangePattern#InOut} message exchange pattern.
@@ -992,7 +1003,8 @@ public interface ProducerTemplate extends Service {
* @param headers headers
* @return a handle to be used to get the response in the future
*/
- CompletableFuture<Object> asyncRequestBodyAndHeaders(String endpointUri, Object body, Map<String, Object> headers);
+ CompletableFuture<Object> asyncRequestBodyAndHeaders(
+ String endpointUri, @Nullable Object body, Map<String, Object> headers);
/**
* Sends an asynchronous body to the given endpoint. Uses an {@link ExchangePattern#InOut} message exchange pattern.
@@ -1002,7 +1014,7 @@ public interface ProducerTemplate extends Service {
* @param type the expected response type
* @return a handle to be used to get the response in the future
*/
- <T> CompletableFuture<T> asyncRequestBody(String endpointUri, Object body, Class<T> type);
+ <T> CompletableFuture<T> asyncRequestBody(String endpointUri, @Nullable Object body, Class<T> type);
/**
* Sends an asynchronous body to the given endpoint. Uses an {@link ExchangePattern#InOut} message exchange pattern.
@@ -1015,7 +1027,7 @@ public interface ProducerTemplate extends Service {
* @return a handle to be used to get the response in the future
*/
<T> CompletableFuture<T> asyncRequestBodyAndHeader(
- String endpointUri, Object body, String header, Object headerValue, Class<T> type);
+ String endpointUri, @Nullable Object body, String header, @Nullable Object headerValue, Class<T> type);
/**
* Sends an asynchronous body to the given endpoint. Uses an {@link ExchangePattern#InOut} message exchange pattern.
@@ -1027,7 +1039,7 @@ public interface ProducerTemplate extends Service {
* @return a handle to be used to get the response in the future
*/
<T> CompletableFuture<T> asyncRequestBodyAndHeaders(
- String endpointUri, Object body, Map<String, Object> headers, Class<T> type);
+ String endpointUri, @Nullable Object body, Map<String, Object> headers, Class<T> type);
/**
* Sends an asynchronous exchange to the given endpoint.
@@ -1059,7 +1071,7 @@ public interface ProducerTemplate extends Service {
* @param body the body to send
* @return a handle to be used to get the response in the future
*/
- CompletableFuture<Object> asyncSendBody(Endpoint endpoint, Object body);
+ CompletableFuture<Object> asyncSendBody(Endpoint endpoint, @Nullable Object body);
/**
* Sends an asynchronous body to the given endpoint. Uses an {@link ExchangePattern#InOut} message exchange pattern.
@@ -1068,7 +1080,7 @@ public interface ProducerTemplate extends Service {
* @param body the body to send
* @return a handle to be used to get the response in the future
*/
- CompletableFuture<Object> asyncRequestBody(Endpoint endpoint, Object body);
+ CompletableFuture<Object> asyncRequestBody(Endpoint endpoint, @Nullable Object body);
/**
* Sends an asynchronous body to the given endpoint. Uses an {@link ExchangePattern#InOut} message exchange pattern.
@@ -1079,7 +1091,8 @@ public interface ProducerTemplate extends Service {
* @param headerValue the header value
* @return a handle to be used to get the response in the future
*/
- CompletableFuture<Object> asyncRequestBodyAndHeader(Endpoint endpoint, Object body, String header, Object headerValue);
+ CompletableFuture<Object> asyncRequestBodyAndHeader(
+ Endpoint endpoint, @Nullable Object body, String header, @Nullable Object headerValue);
/**
* Sends an asynchronous body to the given endpoint. Uses an {@link ExchangePattern#InOut} message exchange pattern.
@@ -1089,7 +1102,7 @@ public interface ProducerTemplate extends Service {
* @param headers headers
* @return a handle to be used to get the response in the future
*/
- CompletableFuture<Object> asyncRequestBodyAndHeaders(Endpoint endpoint, Object body, Map<String, Object> headers);
+ CompletableFuture<Object> asyncRequestBodyAndHeaders(Endpoint endpoint, @Nullable Object body, Map<String, Object> headers);
/**
* Sends an asynchronous body to the given endpoint. Uses an {@link ExchangePattern#InOut} message exchange pattern.
@@ -1099,7 +1112,7 @@ public interface ProducerTemplate extends Service {
* @param type the expected response type
* @return a handle to be used to get the response in the future
*/
- <T> CompletableFuture<T> asyncRequestBody(Endpoint endpoint, Object body, Class<T> type);
+ <T> CompletableFuture<T> asyncRequestBody(Endpoint endpoint, @Nullable Object body, Class<T> type);
/**
* Sends an asynchronous body to the given endpoint. Uses an {@link ExchangePattern#InOut} message exchange pattern.
@@ -1112,7 +1125,7 @@ public interface ProducerTemplate extends Service {
* @return a handle to be used to get the response in the future
*/
<T> CompletableFuture<T> asyncRequestBodyAndHeader(
- Endpoint endpoint, Object body, String header, Object headerValue, Class<T> type);
+ Endpoint endpoint, @Nullable Object body, String header, @Nullable Object headerValue, Class<T> type);
/**
* Sends an asynchronous body to the given endpoint. Uses an {@link ExchangePattern#InOut} message exchange pattern.
@@ -1124,7 +1137,7 @@ public interface ProducerTemplate extends Service {
* @return a handle to be used to get the response in the future
*/
<T> CompletableFuture<T> asyncRequestBodyAndHeaders(
- Endpoint endpoint, Object body, Map<String, Object> headers, Class<T> type);
+ Endpoint endpoint, @Nullable Object body, Map<String, Object> headers, Class<T> type);
/**
* Gets the response body from the future handle, will wait until the response is ready.
diff --git a/core/camel-core/src/test/java/org/apache/camel/impl/DefaultProducerTemplateTest.java b/core/camel-core/src/test/java/org/apache/camel/impl/DefaultProducerTemplateTest.java
index e8c18119298c..ebfd4ad60912 100644
--- a/core/camel-core/src/test/java/org/apache/camel/impl/DefaultProducerTemplateTest.java
+++ b/core/camel-core/src/test/java/org/apache/camel/impl/DefaultProducerTemplateTest.java
@@ -34,6 +34,7 @@ import org.junit.jupiter.api.Test;
import static org.awaitility.Awaitility.await;
import static org.junit.jupiter.api.Assertions.assertEquals;
+import static org.junit.jupiter.api.Assertions.assertNull;
import static org.junit.jupiter.api.Assertions.assertSame;
import static org.junit.jupiter.api.Assertions.assertThrows;
import static org.junit.jupiter.api.Assertions.assertTrue;
@@ -257,6 +258,33 @@ public class DefaultProducerTemplateTest extends ContextTestSupport {
producer.stop();
}
+ @Test
+ public void testNullBodyAndValues() throws Exception {
+ // ProducerTemplate marks body, header value and property value parameters as @Nullable;
+ // verify null values are accepted and routed end-to-end (CAMEL-24460)
+ MockEndpoint mock = getMockEndpoint("mock:echo");
+ mock.expectedMessageCount(3);
+
+ // null body
+ template.sendBody("direct:echo", null);
+ // null body and null header value (header key must be non-null, value may be null)
+ template.sendBodyAndHeader("direct:echo", null, "foo", null);
+ // null body and null property value
+ template.sendBodyAndProperty("direct:echo", null, "bar", null);
+
+ assertMockEndpointsSatisfied();
+
+ // all three bodies are null
+ for (Exchange exchange : mock.getExchanges()) {
+ assertNull(exchange.getIn().getBody(), "Body should be null");
+ }
+
+ // null header value propagated
+ assertNull(mock.getExchanges().get(1).getIn().getHeader("foo"), "Header value should be null");
+ // null property value propagated
+ assertNull(mock.getExchanges().get(2).getProperty("bar"), "Property value should be null");
+ }
+
@Override
protected RouteBuilder createRouteBuilder() {
return new RouteBuilder() {
@@ -287,6 +315,8 @@ public class DefaultProducerTemplateTest extends ContextTestSupport {
}).to("mock:result");
from("direct:inout").transform(constant(123));
+
+ from("direct:echo").to("mock:echo");
}
};
}