[fix][client] Don't close a shared DNS resolver group's address resolver when a client closes - #26723
Merged
Conversation
…er group when a client closes A DnsResolverGroupImpl hands the same Netty resolver to every client that runs on the same event loop, and keeps it until the group closes. PulsarClientImpl.close() closed that resolver also when the group was shared, through PulsarClientSharedResources or the broker's brokerClientSharedDnsResolverGroup, so every other client on that event loop, and every client created on it later, failed its DNS lookups with a closed channel. The client now closes the address resolver only when it created the resolver group itself. Assisted-by: Claude Code (claude-opus-5-5)
lhotari
requested review from
Technoboy-,
dao-jun,
david-streamlio,
merlimat and
nodece
September 26, 2026 21:13
void-ptr974
reviewed
Sep 27, 2026
nodece
approved these changes
Sep 28, 2026
3 tasks done
ascentstream-bot
pushed a commit
to ascentstream/pulsar
that referenced
this pull request
Oct 1, 2026
…ver when a client closes (apache#26723) (cherry picked from commit 986853d)
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Motivation
A
DnsResolverGroupImplwraps Netty'sDnsAddressResolverGroup, whosegetResolver(executor)hands the same resolver to every caller on the same event loop and keeps it until the group is closed.PulsarClientImpl.close()nevertheless closed theAddressResolverit got from the group, also when the group was shared and not owned by the client:PulsarClientSharedResources(theDnsResolvershared resource), andPulsarService.createClientImplgives every broker-side client the sharedbrokerClientSharedDnsResolverGroupand the broker'sioEventLoopGroup.Closing one such client closes the resolver's UDP channel for every other client on that event loop. Because the closed resolver stays in the group's map, clients created later on that event loop get the closed resolver too. Their lookups keep working only while the name is in the resolver's DNS cache. After that, each lookup fails at once with:
In the broker,
BrokerService.closeAndRemoveReplicationClient, which runs when a cluster is deleted, closes that cluster's replication client. From then on, until the broker restarts, the broker clients on that client's event loop can't resolve uncached hostnames. These include the broker's internal client, the replication clients of the other clusters and the namespace clients. For example, reconnecting to a remote cluster fails once the cache entry has expired. Applications that sharePulsarClientSharedResourcesacross clients and close some of them are affected in the same way.The shared DNS resolver group was added in #24784, so this affects 4.1.2 and later 4.1.x releases, and 4.2.0 and later.
Modifications
PulsarClientImpl.close()closes the address resolver only when the client created the resolver group itself (dnsResolverGroupLocalInstance). A shared group's resolvers are closed when the group is closed, byPulsarClientSharedResources.close()orPulsarService.close().Verifying this change
This change added tests and can be verified as follows:
PulsarClientImplTest.testClosingClientLeavesSharedDnsResolverOpenForOtherClientsbuilds two clients fromPulsarClientSharedResourceson a single event loop, with a DNS server that never answers. It closes one client and checks that the other client's lookup still sends a query to the DNS server. Without the fix the test fails, because the closed resolver never sends the query.Does this pull request potentially affect one of the following parts:
If the box was checked, please highlight the changes