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

   # Description
   
   [CAMEL-26478](https://issues.apache.org/jira/browse/CAMEL-26478), found 
through a failing test with virtual threads, under 
[CAMEL-25132](https://issues.apache.org/jira/browse/CAMEL-25132).
   
   With `camel.threads.virtual.enabled=true`, `BoundedExecutorService` limits a 
pool to `maxQueueSize` permits. A parallel split runs in the executor and 
submits its items to it, so with a low `maxQueueSize` it waits for a permit it 
holds itself.
   
   - With `CallerRuns`, the default, each wait lasts until `keepAliveTime` 
expires.
   - With `Block`, the wait has no timeout, so from reading the code it hangs 
forever. This was not run on the old code end to end; 
`testNestedTaskRunsInlineWithBlockPolicy` shows it at the executor level.
   - With a split `timeout`, the unfinished items are dropped with **no 
exception**, so messages are lost. In `SplitTimeoutCancelTaskTest`, 1 of 4 
messages arrived.
   
   Measured before this change, `maxQueueSize=1`, one exchange:
   
   | `keepAliveTime` | 4 items | 20 items |
   |---|---|---|
   | 1 s | 7 s | 39 s |
   | 3 s | 21 s | 117 s |
   
   With platform threads, the same settings took a few milliseconds.
   
   ## The change
   
   A task of this executor that finds no free permit no longer waits, unless 
the policy is `Abort`:
   
   - It **runs the work itself**, as `CallerRunsPolicy` does on platform 
threads.
   - **Past a depth of 64 it hands the work to a new task, without a permit.** 
A parallel split submits itself again for each item, so running everything 
inline overflows the stack: a first version of this change stopped after 1068 
items of a 20000 item split and hung with no exception. Queueing the work to 
run later would avoid that, but it would deadlock a task that waits for what it 
submitted.
   
   `Abort` waits and fails as before, so nothing is lost silently. A submitter 
outside the executor waits as before, so backpressure does not change.
   
   The hand-off can exceed `maxQueueSize`, which the class already documents 
for caller-run tasks. Measured below, the items of a split peaked at 2 to 3 
running at once with `maxQueueSize` 1 and 2.
   
   The meaning of `maxQueueSize` and `keepAliveTime` for virtual threads is 
deliberate (CAMEL-23602), so I left both alone. There is an upgrade guide entry.
   
   ## Measurements
   
   Virtual threads, JDK 25 macOS arm64, not JMH, default `keepAliveTime` of 60 
s:
   
   | `maxQueueSize` | items | time | peak items running |
   |---|---|---|---|
   | 1 | 20000 | 25 to 84 ms | 2 to 3 |
   | 1 | 200000 | 131 to 162 ms | 2 |
   | 2 | 200000 | 220 to 295 ms | 2 to 3 |
   
   All items arrived, streaming and not. Concurrent exchanges were measured on 
the first version only, before the depth limit: 32 threads, 6400 exchanges, 
`maxQueueSize=1`, all 25600 items arrived.
   
   ## Tests
   
   6 new tests in `BoundedExecutorServiceTest`. The 2 inline tests failed 
before the change. `testTaskThatResubmitsItselfDoesNotOverflowTheStack` failed 
with a `StackOverflowError` on the first version. The other 3 are guards for 
what must not change, and pass either way: `Abort` is still rejected, a free 
permit is still used, and a task of another executor still waits.
   
   Verified:
   
   - Full suites with platform threads: `camel-util` 331 tests, `camel-core` 
8672 (44 skipped, not reviewed one by one), 0 failures.
   - 725 tests selected by name with virtual threads (split, multicast, 
recipient list, thread and executor tests): 4 failures. 
`SplitTimeoutCancelTaskTest` passes now. `ThreadsCoreAndMaxPoolInvalidTest`, 
`ThreadsZeroInCoreAndMaxPoolTest` and `ThreadsKeepAliveTimeTest` are addressed 
by #28821. 
`SplitterParallelAsyncProcessorIssueTest.testSplitParallelProcessingMaxThreads` 
fails the same way without this change; I did not look into it further.
   
   Component modules were not run.
   
   # 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).
   
   # 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.
   
   Not run from the root folder: I ran `mvn install -Dquickly -pl 
core/camel-core -am`, and `git status` showed only the changed files afterwards.
   
   # 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.
   
   🤖 Generated with [Claude Code](https://claude.com/claude-code) on behalf of 
Adriano Machado (@ammachado)
   
   _This was generated by an AI agent and may contain inaccuracies. Please 
verify before relying on it._


-- 
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