@@ -239,20 +239,34 @@ private boolean waitForCacheRemovalWithCleanup(
239239 long startTime = System .nanoTime ();
240240 long remainingNanos = timeoutNanos ;
241241
242+ LOG .error ("Starting cache removal wait, initial latch count: {}" , latch .getCount ());
243+
244+ // First check if the latch is already at 0
245+ if (latch .getCount () == 0 ) {
246+ LOG .error ("Cache removal latch already at 0, returning success immediately" );
247+ return true ;
248+ }
249+
242250 while (remainingNanos > 0 && latch .getCount () > 0 ) {
243251 // Wait for a short period
244252 long waitTime = Math .min (remainingNanos , TimeUnit .SECONDS .toNanos (5 ));
253+ LOG .error (
254+ "Waiting for cache removal latch, current count: {}, wait time: {}s" ,
255+ latch .getCount (),
256+ TimeUnit .NANOSECONDS .toSeconds (waitTime ));
257+
245258 boolean success =
246259 Uninterruptibles .awaitUninterruptibly (latch , waitTime , TimeUnit .NANOSECONDS );
247260
248261 if (success ) {
249- LOG .error ("Cache removal latch triggered successfully" );
262+ LOG .error ("Cache removal latch triggered successfully, final count: {}" , latch . getCount () );
250263 return true ;
251264 }
252265
253266 // If we haven't succeeded yet, try to force cache cleanup
254267 LOG .error (
255- "Cache removal latch not triggered yet, forcing cleanup. Current cache size: {}" ,
268+ "Cache removal latch not triggered yet (count: {}), forcing cleanup. Current cache size: {}" ,
269+ latch .getCount (),
256270 getPreparedCacheSize (session ));
257271
258272 try {
@@ -268,9 +282,10 @@ private boolean waitForCacheRemovalWithCleanup(
268282 }
269283
270284 LOG .error (
271- "Cache removal latch failed to trigger within timeout. Final cache size: {}" ,
285+ "Cache removal latch failed to trigger within timeout. Final latch count: {}, cache size: {}" ,
286+ latch .getCount (),
272287 getPreparedCacheSize (session ));
273- return false ;
288+ return latch . getCount () == 0 ; // Return true if latch reached 0 even if await timed out
274289 }
275290
276291 private void invalidationResultSetTest (
@@ -313,15 +328,7 @@ private void invalidationTestInner(
313328
314329 setupTestSchema .accept (session );
315330
316- PreparedStatement stmt1 = session .prepare (preparedStmtQueryType1 );
317- PreparedStatement stmt2 = session .prepare (preparedStmtQueryType2 );
318- ByteBuffer queryId2 = stmt2 .getId ();
319- assertThat (getPreparedCacheSize (session )).isEqualTo (2 );
320-
321- LOG .error ("Prepared statements in cache:" );
322- LOG .error (" Statement 1: {} (queryId: {})" , preparedStmtQueryType1 , stmt1 .getId ());
323- LOG .error (" Statement 2: {} (queryId: {})" , preparedStmtQueryType2 , stmt2 .getId ());
324-
331+ // Set up event handlers BEFORE creating prepared statements to avoid race conditions
325332 CountDownLatch preparedStmtCacheRemoveLatch = new CountDownLatch (1 );
326333 CountDownLatch typeChangeEventLatch = new CountDownLatch (expectedChangedTypes .size ());
327334
@@ -333,6 +340,8 @@ private void invalidationTestInner(
333340 new AtomicReference <>(Optional .empty ());
334341 AtomicReference <Optional <String >> removedQueryEventError =
335342 new AtomicReference <>(Optional .empty ());
343+
344+ LOG .error ("Registering event handlers before creating prepared statements" );
336345 ctx .getEventBus ()
337346 .register (
338347 TypeChangeEvent .class ,
@@ -367,9 +376,24 @@ private void invalidationTestInner(
367376 LOG .warn (
368377 "Multiple PreparedStatementRemovalEvents received, ignoring subsequent ones" );
369378 }
379+ LOG .error (
380+ "About to countdown preparedStmtCacheRemoveLatch, current count: {}" ,
381+ preparedStmtCacheRemoveLatch .getCount ());
370382 preparedStmtCacheRemoveLatch .countDown ();
383+ LOG .error (
384+ "Countdown completed, new count: {}" , preparedStmtCacheRemoveLatch .getCount ());
371385 });
372386
387+ // Now create the prepared statements
388+ PreparedStatement stmt1 = session .prepare (preparedStmtQueryType1 );
389+ PreparedStatement stmt2 = session .prepare (preparedStmtQueryType2 );
390+ ByteBuffer queryId2 = stmt2 .getId ();
391+ assertThat (getPreparedCacheSize (session )).isEqualTo (2 );
392+
393+ LOG .error ("Prepared statements in cache:" );
394+ LOG .error (" Statement 1: {} (queryId: {})" , preparedStmtQueryType1 , stmt1 .getId ());
395+ LOG .error (" Statement 2: {} (queryId: {})" , preparedStmtQueryType2 , stmt2 .getId ());
396+
373397 // alter test_type_caching_2 to trigger cache invalidation and above events
374398 LOG .error ("Executing ALTER TYPE test_type_caching_2 add i blob" );
375399 LOG .error ("Expected to invalidate statement 2 (queryId: {}) due to type change" , queryId2 );
@@ -380,10 +404,6 @@ private void invalidationTestInner(
380404 Uninterruptibles .sleepUninterruptibly (500 , TimeUnit .MILLISECONDS );
381405 session .checkSchemaAgreement ();
382406
383- // Additional delay to allow event processing to complete
384- LOG .error ("Waiting for event processing to complete..." );
385- Uninterruptibles .sleepUninterruptibly (1000 , TimeUnit .MILLISECONDS );
386-
387407 // wait for latches and fail if they don't reach zero before timeout
388408 // Use longer timeout for cache removal as it depends on complex event chain
389409 boolean typeChangeSuccess =
0 commit comments