[fix][broker] Add internalAddConsumer to help track StackOverflowError issue - #24920
[fix][broker] Add internalAddConsumer to help track StackOverflowError issue#24920Technoboy- wants to merge 3 commits into
internalAddConsumer to help track StackOverflowError issue#24920Conversation
| try { | ||
| removeConsumer(actConsumer); | ||
| } catch (BrokerServiceException e) { | ||
| log.warn("[{}] Remove inactive exclusive consumer {}", this.topicName, consumer); | ||
| } |
There was a problem hiding this comment.
I don't think that this is the correct solution. The consumer gets removed when the connection is closed:
Closing gets triggered in the liveness check:
pulsar/pulsar-broker/src/main/java/org/apache/pulsar/broker/service/ServerCnx.java
Lines 3715 to 3721 in acad78c
I'd suppose that there's a race condition that isn't properly handled.
There was a problem hiding this comment.
checkConnectionLivenessreturnedfalse.- The active consumer was not removed.
Seems we should fix the behaviour of checkConnectionLiveness or remove consumers if the connection is inactive
There was a problem hiding this comment.
yes, but no dump file now. I just raise this patch to test if there are some tests can't pass
There was a problem hiding this comment.
@lhotari @poorbarcode Could you please check if there's any other information that needs to be added?
There was a problem hiding this comment.
@lhotari I think the previous change here is correct: bcb763b
channelInactive is not synchronized with addConsumer, so there is a race condition.
isActive = falseis called:addConsumeris called on a new consumerconsumer.close()is called:
Then step 2 will always fail with StackOverflowError.
2025-10-28T22:54:08,431+0000 [configuration-metadata-store-14-1] ERROR org.apache.pulsar.broker.service.persistent.PersistentTopic - [persistent://public/default/test-partition-0] Failed to create subscription: test-subscription
java.util.concurrent.CompletionException: java.lang.StackOverflowError
From the thread name, we can see the StackOverflowError error happens in the metadata store thread. However, if the consumer's connection (ServerCnx) is active, the future will always complete in a Netty event loop thread, whose name starts with pulsar-io.
There was a problem hiding this comment.
After thinking for a while, removing the consumer immediately might not be a good idea, I opened a PR that adds a test and a retry based solution. PTAL @poorbarcode @Technoboy- @lhotari #24934
Codecov Report❌ Patch coverage is
Additional details and impacted files@@ Coverage Diff @@
## master #24920 +/- ##
=============================================
+ Coverage 38.74% 74.22% +35.48%
- Complexity 13265 33866 +20601
=============================================
Files 1856 1913 +57
Lines 145165 149433 +4268
Branches 16848 17359 +511
=============================================
+ Hits 56238 110923 +54685
+ Misses 81385 29642 -51743
- Partials 7542 8868 +1326
Flags with carried forward coverage won't be shown. Click here to find out more.
🚀 New features to boost your workflow:
|
internalAddConsumer to help track StackOverflowError issue
| log.warn("Added consumer failed with attempt count {}, consumers: {}, active consumer: {}," | ||
| + "active state : {}", | ||
| addConsumerFailedAttemptCount, consumers, actConsumer, actConsumer.cnx().isActive()); | ||
| addConsumerFailedAttemptCount = 0; |
There was a problem hiding this comment.
Add code to reset the counter also when the consumer has been successfully added
There was a problem hiding this comment.
Perhaps a solution where the counter is passed as a parameter in the call stack would be more reliable?
|
Problem fixed by #24934 |
Motivation
We see the below StackOverflowError log, but we don't have the heapdump for it, so try to add
internalAddConsumerto log to help find the root cause.Documentation
docdoc-requireddoc-not-neededdoc-complete