@Override
    public synchronized AuthenticationDataProvider getAuthData() throws PulsarClientException {
        if (this.cachedToken == null || this.cachedToken.isExpired()) {
            TokenResult tr = this.flow.authenticate();
            this.cachedToken = new CachedToken(tr);
        }
        return this.cachedToken.getAuthData();
    }
@Test
    public void testGetAuthData() throws Exception {
        AuthenticationDataProvider data;
        TokenResult tr = TokenResult.builder().accessToken(TEST_ACCESS_TOKEN).expiresIn(TEST_EXPIRES_IN).build();
        doReturn(tr).when(this.flow).authenticate();
        data = this.auth.getAuthData();
        verify(this.flow, times(1)).authenticate();
        assertEquals(data.getCommandData(), tr.getAccessToken());

        // cache hit
        data = this.auth.getAuthData();
        verify(this.flow, times(1)).authenticate();
        assertEquals(data.getCommandData(), tr.getAccessToken());

        // cache miss
        clock.advance(Duration.ofSeconds(TEST_EXPIRES_IN));
        data = this.auth.getAuthData();
        verify(this.flow, times(2)).authenticate();
        assertEquals(data.getCommandData(), tr.getAccessToken());
    }