[java-oidc-common] branch main updated: JCOMOIDC-154 - Mechanism for invalidating current metadata cache contents
Codeberg
noreply at shibboleth.net
Mon Sep 28 10:51:57 UTC 2026
This is an automated email from the git hooks/post-receive script.
codeberg pushed a commit to branch main
in repository java-oidc-common.
View the commit online:
https://codeberg.org/Shibboleth/java-oidc-common/commit/f1c87f1041560910a68fa88836a5122bcc983719
The following commit(s) were added to refs/heads/main by this push:
new f1c87f10 JCOMOIDC-154 - Mechanism for invalidating current metadata cache contents
f1c87f10 is described below
commit f1c87f1041560910a68fa88836a5122bcc983719
Author: Phil Smart <philip.smart at jisc.ac.uk>
AuthorDate: Mon Sep 28 11:51:49 2026 +0100
JCOMOIDC-154 - Mechanism for invalidating current metadata cache
contents
- Add a clearAll mechanism to the MetadataCache which defaults to a
no-op implementation.
https://shibboleth.atlassian.net/browse/JCOMOIDC-154
---
.../oidc/metadata/cache/MetadataCache.java | 18 ++++++++++
.../metadata/cache/impl/BatchMetadataCache.java | 16 +++++++++
.../metadata/cache/impl/DynamicMetadataCache.java | 40 +++++++++++++++++++++-
.../cache/impl/BatchMetadataCacheTest.java | 21 ++++++++++++
.../cache/impl/DynamicMetadataCacheTest.java | 14 ++++++++
5 files changed, 108 insertions(+), 1 deletion(-)
diff --git a/oidc-common-metadata-api/src/main/java/net/shibboleth/oidc/metadata/cache/MetadataCache.java b/oidc-common-metadata-api/src/main/java/net/shibboleth/oidc/metadata/cache/MetadataCache.java
index 99f03a50..a53ef19b 100644
--- a/oidc-common-metadata-api/src/main/java/net/shibboleth/oidc/metadata/cache/MetadataCache.java
+++ b/oidc-common-metadata-api/src/main/java/net/shibboleth/oidc/metadata/cache/MetadataCache.java
@@ -47,5 +47,23 @@ public interface MetadataCache<U> {
*/
@Nonnull @NonnullElements public List<U> get(@Nonnull @NotEmpty final CriteriaSet criteria)
throws MetadataCacheException;
+
+ /**
+ * Clear all entries from the cache.
+ *
+ * <p>The default, for implementations that do not override this method, is false: the cache has not been
+ * cleared.</p>
+ *
+ * <p>The implementing method is required to be thread safe.</p>
+ *
+ * @return true if all entries of the cache were successfully cleared, false otherwise.
+ *
+ * @since 3.4.0
+ *
+ * TODO: remove the default in 4.0.0
+ */
+ default boolean clearAll() {
+ return false;
+ }
}
diff --git a/oidc-common-metadata-impl/src/main/java/net/shibboleth/oidc/metadata/cache/impl/BatchMetadataCache.java b/oidc-common-metadata-impl/src/main/java/net/shibboleth/oidc/metadata/cache/impl/BatchMetadataCache.java
index 8c91f316..fc2cef7f 100644
--- a/oidc-common-metadata-impl/src/main/java/net/shibboleth/oidc/metadata/cache/impl/BatchMetadataCache.java
+++ b/oidc-common-metadata-impl/src/main/java/net/shibboleth/oidc/metadata/cache/impl/BatchMetadataCache.java
@@ -369,6 +369,22 @@ public class BatchMetadataCache<IdentifierType, MetadataType>
return new CacheLoadingContext(getBackingStore().getLastUpdate(), getBackingStore().getLastRefresh());
}
+
+ @Override
+ public boolean clearAll() {
+ readWriteLock.writeLock().lock();
+ try {
+ log.debug("{} Clearing all entries from the cache", getLogPrefix());
+ invalidateAll();
+ return true;
+ } catch (final Exception e){
+ log.error("{} Unable to clear cache entries", getLogPrefix(), e);
+ return false;
+ } finally {
+ readWriteLock.writeLock().unlock();
+ }
+ }
+
/**
* Reload the entire backing-store cache using the loading strategy.
*
diff --git a/oidc-common-metadata-impl/src/main/java/net/shibboleth/oidc/metadata/cache/impl/DynamicMetadataCache.java b/oidc-common-metadata-impl/src/main/java/net/shibboleth/oidc/metadata/cache/impl/DynamicMetadataCache.java
index dc0de286..104e71d5 100644
--- a/oidc-common-metadata-impl/src/main/java/net/shibboleth/oidc/metadata/cache/impl/DynamicMetadataCache.java
+++ b/oidc-common-metadata-impl/src/main/java/net/shibboleth/oidc/metadata/cache/impl/DynamicMetadataCache.java
@@ -17,6 +17,7 @@ package net.shibboleth.oidc.metadata.cache.impl;
import java.time.Duration;
import java.time.Instant;
+import java.util.ArrayList;
import java.util.Collections;
import java.util.HashSet;
import java.util.List;
@@ -437,6 +438,44 @@ public class DynamicMetadataCache<IdentifierType, MetadataType>
MetricsSupport.stopTimer(contextResolve);
}
+ }
+
+ /**
+ * {@inheritDoc}
+ *
+ * <p>Clearing a dynamic cache, using per entity locking, does not guarantee the cache is cleared by the point
+ * the method returns to the caller. That is, another entity may have been added during cache clearance: there
+ * is no overall locking of the cache.</p>
+ *
+ * <p>Consequently, the returned boolean cannot be used to determine whether the cache is empty. It indicates
+ * only whether all entries present in the backing store at the start of execution were successfully
+ * invalidated.</p>
+ */
+ @Override
+ public boolean clearAll() {
+ // Use a new arraylist of identifiers, so we do not iterate and remove over the same list
+ final var identifiers =
+ new ArrayList<>(getBackingStore().getIndexedValues().keySet());
+
+ boolean allCleared = true;
+ for (final var identifier : identifiers) {
+ final MetadataManagementData<IdentifierType> mgmtData = getBackingStore().getManagementData(identifier);
+ if (mgmtData == null) {
+ log.warn("{} No management data found for cache entry '{}', unable to remove",
+ getLogPrefix(), identifier);
+ allCleared = false;
+ continue;
+ }
+ final StampedLock sl = mgmtData.getStampLock();
+ final long stamp = sl.writeLock();
+ try {
+ invalidate(identifier);
+ getBackingStore().removeManagementData(identifier);
+ } finally {
+ sl.unlock(stamp);
+ }
+ }
+ return allCleared;
}
/**
@@ -651,7 +690,6 @@ public class DynamicMetadataCache<IdentifierType, MetadataType>
}
}
-
/**
* Cleanup task that removes expired and idle metadata from the backing store.
diff --git a/oidc-common-metadata-impl/src/test/java/net/shibboleth/oidc/metadata/cache/impl/BatchMetadataCacheTest.java b/oidc-common-metadata-impl/src/test/java/net/shibboleth/oidc/metadata/cache/impl/BatchMetadataCacheTest.java
index 4e1ca562..353240dc 100644
--- a/oidc-common-metadata-impl/src/test/java/net/shibboleth/oidc/metadata/cache/impl/BatchMetadataCacheTest.java
+++ b/oidc-common-metadata-impl/src/test/java/net/shibboleth/oidc/metadata/cache/impl/BatchMetadataCacheTest.java
@@ -431,6 +431,27 @@ public class BatchMetadataCacheTest {
Thread.sleep(10000);
}
+
+ @Test
+ public void testClearingCache() throws Exception {
+ cache.initialize();
+
+ final Issuer iss = new Issuer("http://www.example.org");
+ // Add an entry
+ cache.getBackingStore().getIndexedValues().put(iss, List.of(
+ new OIDCProviderMetadata(new Issuer("http://www.example.org"), List.of(SubjectType.PUBLIC),
+ new URI("http://www.example.org/metadata"))));
+ List<OIDCProviderMetadata> metadata =
+ cache.get(new CriteriaSet(new IssuerIDCriterion(new Issuer("http://www.example.org"))));
+ assertTrue(metadata.isEmpty() == false);
+
+ // Now clear the cache
+ assertTrue(cache.clearAll());
+
+ metadata = cache.get(new CriteriaSet(new IssuerIDCriterion(new Issuer("http://www.example.org"))));
+ assertTrue(metadata.isEmpty() == true);
+
+ }
@Test
public void testGetAndLoad_Success()throws Exception {
diff --git a/oidc-common-metadata-impl/src/test/java/net/shibboleth/oidc/metadata/cache/impl/DynamicMetadataCacheTest.java b/oidc-common-metadata-impl/src/test/java/net/shibboleth/oidc/metadata/cache/impl/DynamicMetadataCacheTest.java
index 9853a623..61d11955 100644
--- a/oidc-common-metadata-impl/src/test/java/net/shibboleth/oidc/metadata/cache/impl/DynamicMetadataCacheTest.java
+++ b/oidc-common-metadata-impl/src/test/java/net/shibboleth/oidc/metadata/cache/impl/DynamicMetadataCacheTest.java
@@ -333,6 +333,20 @@ public class DynamicMetadataCacheTest {
}
+ @Test
+ public void testClearAll() throws MetadataCacheException, ComponentInitializationException {
+ cache.initialize();
+ final List<OIDCProviderMetadata> metadata =
+ cache.get(new CriteriaSet(new IssuerIDCriterion(new Issuer("the-issuer"))));
+ assertTrue(metadata.isEmpty() == false);
+ assertFalse(cache.getBackingStore().getIndexedValues().isEmpty());
+ assertFalse(cache.getBackingStore().getOrderedValues().isEmpty());
+ assertTrue(cache.clearAll());
+ assertTrue(cache.getBackingStore().getIndexedValues().isEmpty());
+ assertTrue(cache.getBackingStore().getOrderedValues().isEmpty());
+ assertTrue(cache.getBackingStore().getManagementDataIdentifiers().isEmpty());
+ }
+
@Test
public void testGetNotCached_WrongIdentifier_Fail() throws MetadataCacheException, ComponentInitializationException {
final ManuallyTriggeredScheduledExecutorService scheduler = new ManuallyTriggeredScheduledExecutorService();
--
To stop receiving notification emails like this one, please contact
the administrator of this repository.
More information about the commits
mailing list