@Override
 protected void entryRemoved(boolean evicted, Key k, Value oldVal, Value newVal) {
   // When a token has been removed, clean up the associated Evictor.
   if (oldVal != null && newVal == null) {
     /*
      * This is recursive, but it won't spiral out of control because LruCache is
      * thread safe and the Evictor can only be removed once.
      */
     Evictor evictor = mTokenEvictors.remove(oldVal.token);
     if (evictor != null) {
       evictor.evict();
     }
   }
 }
    public void putToken(Key k, Value v) {
      // Prepare for removal by token string.
      Evictor tokenEvictor = mTokenEvictors.get(v.token);
      if (tokenEvictor == null) {
        tokenEvictor = new Evictor();
      }
      tokenEvictor.add(k);
      mTokenEvictors.put(new Pair<>(k.account.type, v.token), tokenEvictor);

      // Prepare for removal by associated account.
      Evictor accountEvictor = mAccountEvictors.get(k.account);
      if (accountEvictor == null) {
        accountEvictor = new Evictor();
      }
      accountEvictor.add(k);
      mAccountEvictors.put(k.account, tokenEvictor);

      // Only cache the token once we can remove it directly or by account.
      put(k, v);
    }
 public void evict(Account account) {
   Evictor evictor = mAccountEvictors.get(account);
   if (evictor != null) {
     evictor.evict();
   }
 }
 public void evict(String accountType, String token) {
   Evictor evictor = mTokenEvictors.get(new Pair<>(accountType, token));
   if (evictor != null) {
     evictor.evict();
   }
 }