[FLINK-40644][state/forst] Close the remote stream when a CachedDataInputStream is closed - #29168
Open
seungjoo-choi-bucketplace wants to merge 1 commit into
Conversation
…nputStream is closed FileCacheEntry#open hands the original (remote) stream over to the CachedDataInputStream and keeps no other reference to it, but close() only closed the cached local stream. Every remote stream that had read from S3 kept its leased connection of the S3A connection pool, so each close of a stream on a still-cached file (table cache eviction, compaction file deletion, stream pool overflow) leaked one connection until the pool was exhausted and all reads blocked in AbstractConnPool.getPoolEntryBlocking. Close the original stream as well (keeping the first exception and attaching the second as suppressed), and close a pooled stream of ByteBufferReadableFSDataInputStream when its positioned read fails, since it is neither returned to the pool nor closed otherwise. Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com>
Collaborator
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.
What is the purpose of the change
Fixes FLINK-40644: with the ForSt file cache,
CachedDataInputStream.close()only closes the cached (local) stream and never closes the original remote stream it wraps.FileCacheEntry#openhands the remote stream over to the wrapper and keeps no other reference, so nothing ever closes it. Every remote stream that has read from S3 holds a leased connection of the S3A HTTP connection pool, and the pool is not GC-aware, so each close leaks one connection for the lifetime of the TaskManager. Once the pool is exhausted all reads block inAbstractConnPool.getPoolEntryBlockingand the job fails withTimeout waiting for connection from poolafters3.connection.timeout, restarts, and repeats.Streams are closed while their file is still cached whenever the RocksDB table cache evicts an SST (
state.backend.forst.files.opensmaller than the number of live files), when compaction input files are deleted, and when the per-file stream pool ofByteBufferReadableFSDataInputStreamoverflows.readFully(long, ByteBuffer)has a related gap: a pooled stream that throws while reading is neither returned to the pool nor closed.Brief change log
CachedDataInputStream#close: close the original stream as well; if both the cached and the original stream fail to close, propagate the first exception with the second attached as suppressed.ByteBufferReadableFSDataInputStream#readFully(long, ByteBuffer): close the pooled stream when the positioned read fails.CachedDataInputStreamTestandByteBufferReadableFSDataInputStreamTest.Verifying this change
This change added tests and can be verified as follows:
CachedDataInputStreamTest: a stream opened throughFileCacheEntry#opencloses its original stream onclose()(idempotently); when both a cached and an original stream are present both are closed; when the cached stream fails to close the original stream is still closed and the second exception is suppressed. The first test fails on master (original stream must be closed).ByteBufferReadableFSDataInputStreamTest: a pooled stream whose positioned read throws is closed byreadFully. Fails on master.s3.connection.maximum=96(~2 days with 1024); with the fix deployed as a class override the count stays in the single digits across hundreds of thousands of cache misses.Does this pull request potentially affect one of the following parts:
@Public(Evolving): noDocumentation
FLINK-40645 (#29169) fixes the other half of the same stream life cycle (closed streams staying registered in
FileCacheEntry#openedStreams) and touches the same method; the two changes are independent. The analysis and the patch were prepared with AI assistance (Claude Code) and validated in production as described above.🤖 Generated with Claude Code