PDGGK opened a new pull request, #10195:
URL: https://github.com/apache/paimon/pull/10195

   ### Purpose
   
   `ExpireSnapshotsImpl.expireUntil` waits for asynchronous expiration work 
through methods that call `Future.get()`. If the caller is interrupted while 
one of those waits is in progress, `get()` throws `InterruptedException` and 
clears the thread's interrupt status.
   
   Today `expireUntil` catches that exception together with 
`ExecutionException` and wraps both:
   
   ```java
   try {
       return innerExpireUntil(earliestId, endExclusiveId);
   } catch (ExecutionException | InterruptedException e) {
       throw new RuntimeException(e);
   }
   ```
   
   The caller therefore receives the same failure, but the thread no longer 
looks interrupted.
   
   Inside Paimon, the current synchronous callers propagate this 
`RuntimeException` unchanged. The asynchronous maintenance path in 
`TableCommitImpl` catches it, but that path is interrupted by `close()` calling 
`shutdownNow()`, where the worker is already exiting. So this is primarily a 
cancellation-contract consistency fix for callers that embed snapshot 
expiration in a cancellable task and catch the resulting exception.
   
   Other Paimon future-waiting code such as `ThreadPoolUtils`, 
`AsyncPositionOutputStream`, and `BlockPrefetcher` already restores the 
interrupt status before wrapping an `InterruptedException`.
   
   ### What changes
   
   Catch `InterruptedException` separately, restore the interrupt status, and 
keep the existing `RuntimeException` wrapping. `ExecutionException` handling is 
unchanged.
   
   The same combined-catch shape also exists in the Kafka and Pulsar CDC action 
utilities while discovering topics. Those are separate connector 
metadata-discovery paths, so they are intentionally left out of this 
snapshot-expiration change.
   
   ### Tests
   
   `ExpireSnapshotsInterruptStatusTest` blocks an asynchronous snapshot read 
with latches, interrupts the expiration caller while it waits, and checks both 
the wrapped `InterruptedException` and the caller's interrupt status. No sleeps 
are used.
   
   On `master`, the exception assertion succeeds and the interrupt-status 
assertion fails:
   
   ```
   Expecting value to be true but was false
   ```
   
   With the fix the test passes. As a mutation check, removing only 
`Thread.currentThread().interrupt()` makes the same assertion fail again.
   
   ```bash
   mvn -B -pl paimon-core -am test \
     -Dtest='ExpireSnapshotsInterruptStatusTest' \
     -Dsurefire.failIfNoSpecifiedTests=false \
     -DskipITs
   ```
   
   1 test, 0 failures; reactor `BUILD SUCCESS`. Checkstyle, Spotless, and `git 
diff --check` are clean.
   
   ### API and Compatibility
   
   No public API, storage format, or configuration change. Successful 
expiration and `ExecutionException` behavior are unchanged.
   


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