allthingssecurity opened a new pull request, #29404:
URL: https://github.com/apache/camel/pull/29404

   # Description
   
   [CAMEL-26707](https://issues.apache.org/jira/browse/CAMEL-26707)
   
   `markRollbackOnly()` and `markRollbackOnlyLast()` mark the exchange for 
rollback without an exception, so the unit of work runs the on completions as 
successful (`isFailed()` only checks the exception). 
`IdempotentOnCompletion.onComplete` then confirmed the message id (or added it, 
with `eager=false`) and `removeOnFailure` had no effect; `completionEager` 
calls the same `onComplete`.
   
   A consumer that does not commit a rollback only exchange (such as the SQL 
consumer, which skips `onConsume`, or a transacted JMS consumer) redelivers the 
message. The Idempotent Consumer then found the message id and dropped the 
redelivery as a duplicate (only logged at DEBUG), and the consumer committed 
it: the message was never processed. This happens with the default options, 
with any repository that is not enlisted in the transaction that is rolled back.
   
   The SQL consumer already treats a rollback only exchange as failed: 
`SqlConsumer` ("a rollback only exchange (without an exception) did not 
complete successfully either; markRollbackOnlyLast reaches the consumer as the 
last transaction when no transacted() EIP consumed the flag, so honor it too", 
CAMEL-25527 / CAMEL-25588), and `PipelineHelper.continueProcessing` checks 
`isRollbackOnly() || isRollbackOnlyLast()`.
   
   Change: `IdempotentOnCompletion.onComplete` handles an exchange with 
`isRollbackOnly()` or `isRollbackOnlyLast()` as failed (`onFailedMessage`), as 
it already does for an exchange handled by a dead letter channel. An exception 
still goes to `onFailure`, and `removeOnFailure=false` still keeps the message 
id. The `IdempotentConsumerCallback` of `completionEager` goes through 
`onComplete` too, so it needs no change.
   
   `markRollbackOnlyLast` and `transacted()`: the transaction error handler 
clears the flag when it rolls back the transaction of the block, so when the 
unit of work is done the exchange is not rollback only any more, and the 
message id is kept as before (in a route with a single `transacted()`, the 
redelivery is still dropped as before; this change does not address that). With 
`completionEager=true` inside that block, the eager callback runs before the 
flag is cleared, so the message id is removed although an outer transaction 
commits; the work protected by that block was rolled back, and a repository 
enlisted in it loses the message id with the rollback anyway.
   
   With a consumer that commits a rollback only exchange anyway, such as the 
file consumer, the visible change is that a later message with the same id is 
processed instead of dropped as a duplicate. The upgrade guide says so.
   
   Behaviour change, so there is an entry in the 4.24 upgrade guide (the way 
back is `removeOnFailure=false`).
   
   Tests: `IdempotentConsumerRollbackOnlyTest` (memory repository, no 
database), five tests: `markRollbackOnly()`, `markRollbackOnlyLast()`, 
`completionEager(true)` and `eager(false)` each remove (or do not add) the 
message id, and the redelivered message is processed; the control with 
`removeOnFailure(false)` keeps the message id and the redelivery is a 
duplicate, as for a failed exchange.
   
   On main 4 of the 5 tests fail (the message id stays, so the redelivery is 
dropped); the `removeOnFailure(false)` control passes on both. With the fix 
5/5, and 100/100 over 20 runs. camel-core Idempotent Consumer, rollback 
(`MarkRollbackOnlyTest` etc.), file idempotent and aggregator tests: 392 run 
(offline, together with the other camel-core change of this batch, which 
touches different files), 0 failures; the camel-management idempotent tests 
(`ManagedMemoryIdempotent*`, `ManagedFileIdempotent*`) pass.
   
   # Target
   
   - [x] I checked that the commit is targeting the correct branch (Camel 4 
uses the `main` branch)
   
   # Tracking
   - [x] If this is a large change, bug fix, or code improvement, I checked 
there is a [JIRA issue](https://issues.apache.org/jira/browse/CAMEL) filed for 
the change (usually before you start working on it): 
[CAMEL-26707](https://issues.apache.org/jira/browse/CAMEL-26707).
   
   # Apache Camel coding standards and style
   
   - [x] I checked that each commit in the pull request has a meaningful 
subject line and body.
   - [ ] I have run `mvn clean install -DskipTests` locally from root folder 
and I have committed all auto-generated changes.
     (I built the core modules with the formatter and import-sort plugins and 
ran the related camel-core tests; no generated file changes. I did not run the 
full root build.)
   
   # AI-assisted contributions
   
   - [x] If this PR includes AI-generated code, commits have proper 
co-authorship attribution (e.g., `Co-authored-by` trailers) and the PR 
description identifies the AI tool used.
     This PR was prepared with Claude Code (Claude Opus 5.5). The commit 
carries a `Co-Authored-By` trailer.
   
   _Claude Code on behalf of allthingssecurity_
   
   🤖 Generated with [Claude Code](https://claude.com/claude-code)
   


-- 
This is an automated message from the Apache Git Service.
To respond to the message, please log on to GitHub and use the
URL above to go to the specific comment.

To unsubscribe, e-mail: [email protected]

For queries about this service, please contact Infrastructure at:
[email protected]

Reply via email to