You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@camel.apache.org by je...@apache.org on 2022/03/13 18:03:34 UTC
[camel] branch main updated: CAMEL-17608: camel-salesforce: Use sObjectName option better
This is an automated email from the ASF dual-hosted git repository.
jeremyross pushed a commit to branch main
in repository https://gitbox.apache.org/repos/asf/camel.git
The following commit(s) were added to refs/heads/main by this push:
new 27300d1 CAMEL-17608: camel-salesforce: Use sObjectName option better
27300d1 is described below
commit 27300d1b5689242ce55f6df1528daad01e2c1164
Author: Jeremy Ross <je...@gmail.com>
AuthorDate: Sun Mar 13 13:01:49 2022 -0500
CAMEL-17608: camel-salesforce: Use sObjectName option better
---
.../internal/processor/AbstractRestProcessor.java | 102 +++++++++------------
.../salesforce/RestApiIntegrationTest.java | 71 ++++++--------
.../ROOT/pages/camel-3x-upgrade-guide-3_16.adoc | 6 ++
3 files changed, 78 insertions(+), 101 deletions(-)
diff --git a/components/camel-salesforce/camel-salesforce-component/src/main/java/org/apache/camel/component/salesforce/internal/processor/AbstractRestProcessor.java b/components/camel-salesforce/camel-salesforce-component/src/main/java/org/apache/camel/component/salesforce/internal/processor/AbstractRestProcessor.java
index b9e9570..0f0fdb2 100644
--- a/components/camel-salesforce/camel-salesforce-component/src/main/java/org/apache/camel/component/salesforce/internal/processor/AbstractRestProcessor.java
+++ b/components/camel-salesforce/camel-salesforce-component/src/main/java/org/apache/camel/component/salesforce/internal/processor/AbstractRestProcessor.java
@@ -325,18 +325,8 @@ public abstract class AbstractRestProcessor extends AbstractSalesforceProcessor
}
private void processGetSobject(final Exchange exchange, final AsyncCallback callback) throws SalesforceException {
- String sObjectName;
- String sObjectIdValue;
- // determine parameters from input AbstractSObject
- final AbstractSObjectBase sObjectBase = exchange.getIn().getBody(AbstractSObjectBase.class);
- if (sObjectBase != null) {
- sObjectName = sObjectBase.getClass().getSimpleName();
- sObjectIdValue = sObjectBase.getId();
- } else {
- sObjectName = getParameter(SOBJECT_NAME, exchange, IGNORE_BODY, NOT_OPTIONAL);
- sObjectIdValue = getParameter(SOBJECT_ID, exchange, USE_BODY, NOT_OPTIONAL);
- }
- final String sObjectId = sObjectIdValue;
+ String sObjectName = determineSObjectName(exchange);
+ final String sObjectId = determineSObjectId(exchange);
// use sObject name to load class
setResponseClass(exchange, sObjectName);
@@ -353,33 +343,20 @@ public abstract class AbstractRestProcessor extends AbstractSalesforceProcessor
}
private void processCreateSobject(final Exchange exchange, final AsyncCallback callback) throws SalesforceException {
- String sObjectName;
- // determine parameters from input AbstractSObject
- AbstractSObjectBase sObjectBase = exchange.getIn().getBody(AbstractSObjectBase.class);
- if (sObjectBase != null) {
- sObjectName = sObjectBase.getClass().getSimpleName();
- } else {
- sObjectName = getParameter(SOBJECT_NAME, exchange, IGNORE_BODY, NOT_OPTIONAL);
- }
+ String sObjectName = determineSObjectName(exchange);
restClient.createSObject(sObjectName, getRequestStream(exchange), determineHeaders(exchange),
processWithResponseCallback(exchange, callback));
}
private void processUpdateSobject(final Exchange exchange, final AsyncCallback callback) throws SalesforceException {
- String sObjectName;
- // determine parameters from input AbstractSObject
+ String sObjectName = determineSObjectName(exchange);
+ String sObjectId = determineSObjectId(exchange);
final AbstractSObjectBase sObjectBase = exchange.getIn().getBody(AbstractSObjectBase.class);
- String sObjectId;
+ // raw payloads will not be AbstractSObjectBase
if (sObjectBase != null) {
- sObjectName = sObjectBase.getClass().getSimpleName();
- // remember the sObject Id
- sObjectId = sObjectBase.getId();
- // clear base object fields, which cannot be updated
sObjectBase.clearBaseFields();
- } else {
- sObjectName = getParameter(SOBJECT_NAME, exchange, IGNORE_BODY, NOT_OPTIONAL);
- sObjectId = getParameter(SOBJECT_ID, exchange, IGNORE_BODY, NOT_OPTIONAL);
+
}
final String finalsObjectId = sObjectId;
@@ -394,18 +371,9 @@ public abstract class AbstractRestProcessor extends AbstractSalesforceProcessor
}
private void processDeleteSobject(final Exchange exchange, final AsyncCallback callback) throws SalesforceException {
- String sObjectName;
- // determine parameters from input AbstractSObject
+ String sObjectName = determineSObjectName(exchange);
+ final String sObjectId = determineSObjectId(exchange);
final AbstractSObjectBase sObjectBase = exchange.getIn().getBody(AbstractSObjectBase.class);
- String sObjectIdValue;
- if (sObjectBase != null) {
- sObjectName = sObjectBase.getClass().getSimpleName();
- sObjectIdValue = sObjectBase.getId();
- } else {
- sObjectName = getParameter(SOBJECT_NAME, exchange, IGNORE_BODY, NOT_OPTIONAL);
- sObjectIdValue = getParameter(SOBJECT_ID, exchange, USE_BODY, NOT_OPTIONAL);
- }
- final String sObjectId = sObjectIdValue;
restClient.deleteSObject(sObjectName, sObjectId, determineHeaders(exchange), new RestClient.ResponseCallback() {
@Override
@@ -417,7 +385,7 @@ public abstract class AbstractRestProcessor extends AbstractSalesforceProcessor
}
private void processGetSobjectWithId(final Exchange exchange, final AsyncCallback callback) throws SalesforceException {
- String sObjectName;
+ String sObjectName = determineSObjectName(exchange);
Object oldValue = null;
String sObjectExtIdValue;
final String sObjectExtIdName = getParameter(SOBJECT_EXT_ID_NAME, exchange, IGNORE_BODY, NOT_OPTIONAL);
@@ -425,11 +393,9 @@ public abstract class AbstractRestProcessor extends AbstractSalesforceProcessor
// determine parameters from input AbstractSObject
final AbstractSObjectBase sObjectBase = exchange.getIn().getBody(AbstractSObjectBase.class);
if (sObjectBase != null) {
- sObjectName = sObjectBase.getClass().getSimpleName();
oldValue = getAndClearPropertyValue(sObjectBase, sObjectExtIdName);
sObjectExtIdValue = oldValue.toString();
} else {
- sObjectName = getParameter(SOBJECT_NAME, exchange, IGNORE_BODY, NOT_OPTIONAL);
sObjectExtIdValue = getParameter(SOBJECT_EXT_ID_VALUE, exchange, USE_BODY, NOT_OPTIONAL);
}
@@ -448,7 +414,7 @@ public abstract class AbstractRestProcessor extends AbstractSalesforceProcessor
}
private void processUpsertSobject(final Exchange exchange, final AsyncCallback callback) throws SalesforceException {
- String sObjectName;
+ String sObjectName = determineSObjectName(exchange);
String sObjectExtIdValue;
final String sObjectExtIdName = getParameter(SOBJECT_EXT_ID_NAME, exchange, IGNORE_BODY, NOT_OPTIONAL);
@@ -456,13 +422,11 @@ public abstract class AbstractRestProcessor extends AbstractSalesforceProcessor
Object oldValue = null;
final AbstractSObjectBase sObjectBase = exchange.getIn().getBody(AbstractSObjectBase.class);
if (sObjectBase != null) {
- sObjectName = sObjectBase.getClass().getSimpleName();
oldValue = getAndClearPropertyValue(sObjectBase, sObjectExtIdName);
sObjectExtIdValue = oldValue.toString();
// clear base object fields, which cannot be updated
sObjectBase.clearBaseFields();
} else {
- sObjectName = getParameter(SOBJECT_NAME, exchange, IGNORE_BODY, NOT_OPTIONAL);
sObjectExtIdValue = getParameter(SOBJECT_EXT_ID_VALUE, exchange, IGNORE_BODY, NOT_OPTIONAL);
}
@@ -478,7 +442,7 @@ public abstract class AbstractRestProcessor extends AbstractSalesforceProcessor
}
private void processDeleteSobjectWithId(final Exchange exchange, final AsyncCallback callback) throws SalesforceException {
- String sObjectName;
+ String sObjectName = determineSObjectName(exchange);
final String sObjectExtIdName = getParameter(SOBJECT_EXT_ID_NAME, exchange, IGNORE_BODY, NOT_OPTIONAL);
// determine parameters from input AbstractSObject
@@ -486,11 +450,9 @@ public abstract class AbstractRestProcessor extends AbstractSalesforceProcessor
final AbstractSObjectBase sObjectBase = exchange.getIn().getBody(AbstractSObjectBase.class);
String sObjectExtIdValue;
if (sObjectBase != null) {
- sObjectName = sObjectBase.getClass().getSimpleName();
oldValue = getAndClearPropertyValue(sObjectBase, sObjectExtIdName);
sObjectExtIdValue = oldValue.toString();
} else {
- sObjectName = getParameter(SOBJECT_NAME, exchange, IGNORE_BODY, NOT_OPTIONAL);
sObjectExtIdValue = getParameter(SOBJECT_EXT_ID_VALUE, exchange, USE_BODY, NOT_OPTIONAL);
}
@@ -506,21 +468,13 @@ public abstract class AbstractRestProcessor extends AbstractSalesforceProcessor
}
private void processGetBlobField(final Exchange exchange, final AsyncCallback callback) throws SalesforceException {
- String sObjectName;
+ String sObjectName = determineSObjectName(exchange);
// get blob field name
final String sObjectBlobFieldName = getParameter(SOBJECT_BLOB_FIELD_NAME, exchange, IGNORE_BODY, NOT_OPTIONAL);
// determine parameters from input AbstractSObject
final AbstractSObjectBase sObjectBase = exchange.getIn().getBody(AbstractSObjectBase.class);
- String sObjectIdValue;
- if (sObjectBase != null) {
- sObjectName = sObjectBase.getClass().getSimpleName();
- sObjectIdValue = sObjectBase.getId();
- } else {
- sObjectName = getParameter(SOBJECT_NAME, exchange, IGNORE_BODY, NOT_OPTIONAL);
- sObjectIdValue = getParameter(SOBJECT_ID, exchange, USE_BODY, NOT_OPTIONAL);
- }
- final String sObjectId = sObjectIdValue;
+ String sObjectId = determineSObjectId(exchange);
restClient.getBlobField(sObjectName, sObjectId, sObjectBlobFieldName, determineHeaders(exchange),
new RestClient.ResponseCallback() {
@@ -633,6 +587,34 @@ public abstract class AbstractRestProcessor extends AbstractSalesforceProcessor
restClient.limits(determineHeaders(exchange), processWithResponseCallback(exchange, callback));
}
+ private String determineSObjectName(Exchange exchange) throws SalesforceException {
+ String sObjectName = getParameter(SOBJECT_NAME, exchange, IGNORE_BODY, IS_OPTIONAL);
+
+ if (sObjectName == null) {
+ // determine parameters from input AbstractSObject
+ AbstractSObjectBase sObjectBase = exchange.getIn().getBody(AbstractSObjectBase.class);
+ if (sObjectBase != null) {
+ sObjectName = sObjectBase.getClass().getSimpleName();
+ } else {
+ throw new IllegalArgumentException(
+ "Unable to determine sObject name. Body must be of AbstractSObjectBase " +
+ "(base class of generated DTOs) or sObjectName option must be supplied.");
+ }
+ }
+ return sObjectName;
+ }
+
+ private String determineSObjectId(Exchange exchange) throws SalesforceException {
+ String sObjectIdValue;
+ final AbstractSObjectBase sObjectBase = exchange.getIn().getBody(AbstractSObjectBase.class);
+ if (sObjectBase != null) {
+ sObjectIdValue = sObjectBase.getId();
+ } else {
+ sObjectIdValue = getParameter(SOBJECT_ID, exchange, USE_BODY, NOT_OPTIONAL);
+ }
+ return sObjectIdValue;
+ }
+
@SuppressWarnings("unchecked")
private Map<String, Object> getQueryParams(Exchange exchange) {
diff --git a/components/camel-salesforce/camel-salesforce-component/src/test/java/org/apache/camel/component/salesforce/RestApiIntegrationTest.java b/components/camel-salesforce/camel-salesforce-component/src/test/java/org/apache/camel/component/salesforce/RestApiIntegrationTest.java
index 722cd70..2814779 100644
--- a/components/camel-salesforce/camel-salesforce-component/src/test/java/org/apache/camel/component/salesforce/RestApiIntegrationTest.java
+++ b/components/camel-salesforce/camel-salesforce-component/src/test/java/org/apache/camel/component/salesforce/RestApiIntegrationTest.java
@@ -158,7 +158,8 @@ public class RestApiIntegrationTest extends AbstractSalesforceTestBase {
account.setName("Child Test");
String accountExternalId = UUID.randomUUID().toString();
account.setExternal_Id__c(accountExternalId);
- CreateSObjectResult accountResult = template().requestBody("direct:createSObject", account, CreateSObjectResult.class);
+ CreateSObjectResult accountResult
+ = template().requestBody("salesforce:createSObject", account, CreateSObjectResult.class);
accountId = accountResult.getId();
final Account accountRef = new Account();
@@ -166,7 +167,8 @@ public class RestApiIntegrationTest extends AbstractSalesforceTestBase {
final Contact contact = new Contact();
contact.setAccount(accountRef);
contact.setLastName("RelationshipTest");
- CreateSObjectResult contactResult = template().requestBody("direct:createSObject", contact, CreateSObjectResult.class);
+ CreateSObjectResult contactResult
+ = template().requestBody("salesforce:createSObject", contact, CreateSObjectResult.class);
contactId = contactResult.getId();
}
@@ -229,7 +231,7 @@ public class RestApiIntegrationTest extends AbstractSalesforceTestBase {
merchandise.setPrice__c(2000.0);
merchandise.setTotal_Inventory__c(50.0);
final CreateSObjectResult result
- = template().requestBody("direct:createSObject", merchandise, CreateSObjectResult.class);
+ = template().requestBody("salesforce:createSObject", merchandise, CreateSObjectResult.class);
assertNotNull(result);
assertTrue(result.getSuccess(), "Create success");
@@ -241,11 +243,12 @@ public class RestApiIntegrationTest extends AbstractSalesforceTestBase {
// also need to set the Id
merchandise.setId(result.getId());
- assertNotNull(template().requestBodyAndHeader("direct:updateSObject", merchandise, SalesforceEndpointConfig.SOBJECT_ID,
- result.getId()));
+ assertNotNull(
+ template().requestBodyAndHeader("salesforce:updateSObject", merchandise, SalesforceEndpointConfig.SOBJECT_ID,
+ result.getId()));
// delete the newly created SObject
- assertNotNull(template().requestBody("direct:deleteSObject", result.getId()));
+ assertNotNull(template().requestBody("salesforce:deleteSObject?sObjectName=Merchandise__c", result.getId()));
}
@Test
@@ -255,7 +258,7 @@ public class RestApiIntegrationTest extends AbstractSalesforceTestBase {
String accountExternalId = UUID.randomUUID().toString();
account.setExternal_Id__c(accountExternalId);
final CreateSObjectResult accountResult
- = template().requestBody("direct:createSObject", account, CreateSObjectResult.class);
+ = template().requestBody("salesforce:createSObject", account, CreateSObjectResult.class);
assertNotNull(accountResult);
assertTrue(accountResult.getSuccess(), "Create success");
@@ -265,15 +268,15 @@ public class RestApiIntegrationTest extends AbstractSalesforceTestBase {
contact.setAccount(accountRef);
contact.setLastName("RelationshipTest");
final CreateSObjectResult contactResult
- = template().requestBody("direct:createSObject", contact, CreateSObjectResult.class);
+ = template().requestBody("salesforce:createSObject", contact, CreateSObjectResult.class);
assertNotNull(contactResult);
assertTrue(contactResult.getSuccess(), "Create success");
// delete the Contact
- template().requestBodyAndHeader("direct:deleteSObject", contactResult.getId(), "sObjectName", "Contact");
+ template().requestBodyAndHeader("salesforce:deleteSObject", contactResult.getId(), "sObjectName", "Contact");
// delete the Account
- template().requestBodyAndHeader("direct:deleteSObject", accountResult.getId(), "sObjectName", "Account");
+ template().requestBodyAndHeader("salesforce:deleteSObject", accountResult.getId(), "sObjectName", "Account");
}
@Test
@@ -282,7 +285,7 @@ public class RestApiIntegrationTest extends AbstractSalesforceTestBase {
account.setName("Account 1");
account.setSite("test site");
final CreateSObjectResult accountResult
- = template().requestBody("direct:createSObject", account, CreateSObjectResult.class);
+ = template().requestBody("salesforce:createSObject", account, CreateSObjectResult.class);
assertNotNull(accountResult);
assertTrue(accountResult.getSuccess(), "Create success");
@@ -299,7 +302,7 @@ public class RestApiIntegrationTest extends AbstractSalesforceTestBase {
assertNull(updatedAccount.getSite());
// delete the Account
- template().requestBodyAndHeader("direct:deleteSObject", accountResult.getId(), "sObjectName", "Account");
+ template().requestBodyAndHeader("salesforce:deleteSObject", accountResult.getId(), "sObjectName", "Account");
}
@Test
@@ -307,7 +310,7 @@ public class RestApiIntegrationTest extends AbstractSalesforceTestBase {
final Contact contact = new Contact();
contact.setLastName("RelationshipTest");
final CreateSObjectResult contactResult
- = template().requestBody("direct:createSObject", contact, CreateSObjectResult.class);
+ = template().requestBody("salesforce:createSObject", contact, CreateSObjectResult.class);
assertNotNull(contactResult);
assertTrue(contactResult.getSuccess(), "Create success");
@@ -316,7 +319,7 @@ public class RestApiIntegrationTest extends AbstractSalesforceTestBase {
String accountExternalId = UUID.randomUUID().toString();
account.setExternal_Id__c(accountExternalId);
final CreateSObjectResult accountResult
- = template().requestBody("direct:createSObject", account, CreateSObjectResult.class);
+ = template().requestBody("salesforce:createSObject", account, CreateSObjectResult.class);
assertNotNull(accountResult);
assertTrue(accountResult.getSuccess(), "Create success");
@@ -330,10 +333,10 @@ public class RestApiIntegrationTest extends AbstractSalesforceTestBase {
assertNotNull(updateContactResult);
// delete the Contact
- template().requestBodyAndHeader("direct:deleteSObject", contactResult.getId(), "sObjectName", "Contact");
+ template().requestBodyAndHeader("salesforce:deleteSObject", contactResult.getId(), "sObjectName", "Contact");
// delete the Account
- template().requestBodyAndHeader("direct:deleteSObject", accountResult.getId(), "sObjectName", "Account");
+ template().requestBodyAndHeader("salesforce:deleteSObject", accountResult.getId(), "sObjectName", "Account");
}
@Test
@@ -341,7 +344,7 @@ public class RestApiIntegrationTest extends AbstractSalesforceTestBase {
final Task taken = new Task();
taken.setDescription("Task1");
taken.setActivityDate(ZonedDateTime.of(1700, 1, 2, 3, 4, 5, 6, ZoneId.systemDefault()));
- final CreateSObjectResult result = template().requestBody("direct:createSObject", taken, CreateSObjectResult.class);
+ final CreateSObjectResult result = template().requestBody("salesforce:createSObject", taken, CreateSObjectResult.class);
assertNotNull(result);
assertTrue(result.getSuccess(), "Create success");
@@ -350,11 +353,11 @@ public class RestApiIntegrationTest extends AbstractSalesforceTestBase {
taken.setId(result.getId());
taken.setActivityDate(ZonedDateTime.of(1991, 1, 2, 3, 4, 5, 6, ZoneId.systemDefault()));
- assertNotNull(template().requestBodyAndHeader("direct:updateSObject", taken, SalesforceEndpointConfig.SOBJECT_ID,
+ assertNotNull(template().requestBodyAndHeader("salesforce:updateSObject", taken, SalesforceEndpointConfig.SOBJECT_ID,
result.getId()));
// delete the newly created SObject
- assertNotNull(template().requestBody("direct:deleteSObjectTaken", result.getId()));
+ assertNotNull(template().requestBody("salesforce:deleteSObject?sObjectName=Task", result.getId()));
}
@Test
@@ -367,7 +370,8 @@ public class RestApiIntegrationTest extends AbstractSalesforceTestBase {
assertTrue(result.getSuccess());
// get line item with Name 1
- lineItem = template().requestBody("direct:getSObjectWithId", lineItemId, Line_Item__c.class);
+ lineItem = template().requestBody("salesforce:getSObjectWithId?sObjectIdName=Name&sObjectName=Line_Item__c",
+ lineItemId, Line_Item__c.class);
assertNotNull(lineItem);
// test insert with id
@@ -425,7 +429,7 @@ public class RestApiIntegrationTest extends AbstractSalesforceTestBase {
headers.put(SalesforceEndpointConfig.SOBJECT_NAME, "Document");
headers.put(SalesforceEndpointConfig.SOBJECT_EXT_ID_NAME, "Name");
final Document document
- = template().requestBodyAndHeaders("direct:getSObjectWithId", TEST_DOCUMENT_ID, headers, Document.class);
+ = template().requestBodyAndHeaders("salesforce:getSObjectWithId", TEST_DOCUMENT_ID, headers, Document.class);
assertNotNull(document);
// get Body field for this document
@@ -616,7 +620,7 @@ public class RestApiIntegrationTest extends AbstractSalesforceTestBase {
CreateSObjectResult result = null;
try {
merchandise.clearBaseFields();
- result = template().requestBody("direct:createSObject", merchandise, CreateSObjectResult.class);
+ result = template().requestBody("salesforce:createSObject", merchandise, CreateSObjectResult.class);
assertNotNull(result);
assertNotNull(result.getId());
@@ -624,7 +628,7 @@ public class RestApiIntegrationTest extends AbstractSalesforceTestBase {
// note that the request SObject overrides settings on the endpoint
// for LineItem__c
try {
- template().requestBody("direct:getSObjectWithId", merchandise, Merchandise__c.class);
+ template().requestBody("salesforce:getSObjectWithId?sObjectIdName=Name", merchandise, Merchandise__c.class);
fail("Expected SalesforceException with statusCode 300");
} catch (final CamelExecutionException e) {
final Throwable cause = e.getCause();
@@ -638,7 +642,7 @@ public class RestApiIntegrationTest extends AbstractSalesforceTestBase {
} finally {
// delete the test clone
if (result != null) {
- template().requestBody("direct:deleteSObject", result.getId());
+ template().requestBody("salesforce:deleteSObject?sObjectName=Merchandise__c", result.getId());
}
}
}
@@ -657,7 +661,7 @@ public class RestApiIntegrationTest extends AbstractSalesforceTestBase {
// required field Total_Inventory__c is missing
CreateSObjectResult result = null;
try {
- result = template().requestBody("direct:createSObject", merchandise, CreateSObjectResult.class);
+ result = template().requestBody("salesforce:createSObject", merchandise, CreateSObjectResult.class);
fail("Expected SalesforceException with statusCode 400");
} catch (final CamelExecutionException e) {
final Throwable cause = e.getCause();
@@ -669,7 +673,7 @@ public class RestApiIntegrationTest extends AbstractSalesforceTestBase {
} finally {
// delete the clone if created
if (result != null) {
- template().requestBody("direct:deleteSObject", result.getId());
+ template().requestBody("salesforce:deleteSObject", result.getId());
}
}
}
@@ -733,21 +737,6 @@ public class RestApiIntegrationTest extends AbstractSalesforceTestBase {
from("direct:getSObject")
.to("salesforce:getSObject?sObjectName=Merchandise__c&sObjectFields=Description__c,Price__c");
- // testCreateSObject
- from("direct:createSObject").to("salesforce:createSObject?sObjectName=Merchandise__c");
-
- // testUpdateSObject
- from("direct:updateSObject").to("salesforce:updateSObject?sObjectName=Merchandise__c");
-
- // testDeleteSObject
- from("direct:deleteSObject").to("salesforce:deleteSObject?sObjectName=Merchandise__c");
-
- from("direct:deleteSObjectTaken").to("salesforce:deleteSObject?sObjectName=Task");
-
- // testGetSObjectWithId
- from("direct:getSObjectWithId")
- .to("salesforce:getSObjectWithId?sObjectName=Line_Item__c&sObjectIdName=Name");
-
// testUpsertSObject
from("direct:deleteLineItems")
.to("salesforce:query?sObjectQuery=SELECT Id FROM Line_Item__C&sObjectClass="
diff --git a/docs/user-manual/modules/ROOT/pages/camel-3x-upgrade-guide-3_16.adoc b/docs/user-manual/modules/ROOT/pages/camel-3x-upgrade-guide-3_16.adoc
index b4e4f6b..8b2bfcf 100644
--- a/docs/user-manual/modules/ROOT/pages/camel-3x-upgrade-guide-3_16.adoc
+++ b/docs/user-manual/modules/ROOT/pages/camel-3x-upgrade-guide-3_16.adoc
@@ -375,3 +375,9 @@ This component was deprecated and is removed on this version. Users should migra
=== camel-testcontainers-spring-junit5
This component was deprecated and is removed on this version. Users should migrate to xref:test-infra.adoc[camel-test-infra].
+
+=== camel-salesforce
+
+The `sObjectName` query parameter and header now take precedence over the class name of the `AbstractSObjectBase` DTO for
+determining the name of the SObject. We suggest testing your existing routes to identify any potential issues. See
+https://issues.apache.org/jira/browse/CAMEL-17608 for more details.