From aefba802d5b360f7d7ba6655b6eaae0f6098bdea Mon Sep 17 00:00:00 2001 From: John Blum Date: Thu, 7 Jun 2018 23:21:39 -0700 Subject: [PATCH] SGF-752 - Add ability to configure SecurityManager on CacheFactoryBean. --- .../data/gemfire/CacheFactoryBean.java | 67 ++++++++++++++++--- .../client/ClientCacheFactoryBean.java | 2 +- .../data/gemfire/CacheFactoryBeanTest.java | 67 ++++++++++++++----- .../client/ClientCacheFactoryBeanTest.java | 2 +- 4 files changed, 111 insertions(+), 27 deletions(-) diff --git a/src/main/java/org/springframework/data/gemfire/CacheFactoryBean.java b/src/main/java/org/springframework/data/gemfire/CacheFactoryBean.java index 82b45320..9270e0d0 100644 --- a/src/main/java/org/springframework/data/gemfire/CacheFactoryBean.java +++ b/src/main/java/org/springframework/data/gemfire/CacheFactoryBean.java @@ -53,6 +53,7 @@ import org.apache.geode.internal.datasource.ConfigProperty; import org.apache.geode.internal.jndi.JNDIInvoker; import org.apache.geode.pdx.PdxSerializable; import org.apache.geode.pdx.PdxSerializer; +import org.apache.geode.security.SecurityManager; import org.springframework.beans.factory.BeanFactory; import org.springframework.beans.factory.DisposableBean; import org.springframework.beans.factory.FactoryBean; @@ -158,6 +159,8 @@ public class CacheFactoryBean extends AbstractFactoryBeanSupport private String cacheResolutionMessagePrefix; private String pdxDiskStoreName; + private org.apache.geode.security.SecurityManager securityManager; + private TransactionWriter transactionWriter; /** @@ -296,11 +299,12 @@ public class CacheFactoryBean extends AbstractFactoryBeanSupport * @see #fetchCache() * @see #resolveProperties() * @see #createFactory(java.util.Properties) - * @see #prepareFactory(Object) + * @see #configureFactory(Object) * @see #createCache(Object) */ @SuppressWarnings("unchecked") protected T resolveCache() { + try { this.cacheResolutionMessagePrefix = "Found existing"; return (T) fetchCache(); @@ -308,7 +312,7 @@ public class CacheFactoryBean extends AbstractFactoryBeanSupport catch (CacheClosedException ex) { this.cacheResolutionMessagePrefix = "Created new"; initDynamicRegionFactory(); - return (T) createCache(prepareFactory(initializeFactory(createFactory(resolveProperties())))); + return (T) createCache(configureFactory(initializeFactory(createFactory(resolveProperties())))); } } @@ -387,20 +391,20 @@ public class CacheFactoryBean extends AbstractFactoryBeanSupport * * @param factory {@link CacheFactory} used to create the {@link Cache}. * @return the prepared and initialized {@link CacheFactory}. - * @see #initializePdx(CacheFactory) + * @see #configurePdx(CacheFactory) */ - protected Object prepareFactory(Object factory) { - return initializePdx((CacheFactory) factory); + protected Object configureFactory(Object factory) { + return configureSecurity(configurePdx((CacheFactory) factory)); } /** - * Configure PDX for the given {@link CacheFactory}. + * Configures PDX for this peer {@link Cache} instance. * - * @param cacheFactory {@link CacheFactory} used to configure PDX. + * @param cacheFactory {@link CacheFactory} used to configure the peer {@link Cache} with PDX. * @return the given {@link CacheFactory}. * @see org.apache.geode.cache.CacheFactory */ - private CacheFactory initializePdx(CacheFactory cacheFactory) { + private CacheFactory configurePdx(CacheFactory cacheFactory) { Optional.ofNullable(getPdxSerializer()).ifPresent(cacheFactory::setPdxSerializer); @@ -417,7 +421,32 @@ public class CacheFactoryBean extends AbstractFactoryBeanSupport } /** - * Creates a new {@link Cache} instance using the provided factory. + * Configures security for this peer {@link Cache} instance. + * + * @param cacheFactory {@link CacheFactory} used to configure the peer {@link Cache} with security. + * @return the given {@link CacheFactory}. + * @see org.apache.geode.cache.CacheFactory + */ + private CacheFactory configureSecurity(CacheFactory cacheFactory) { + + Optional.ofNullable(getSecurityManager()).ifPresent(cacheFactory::setSecurityManager); + + return cacheFactory; + } + + /** + * Post processes the {@link CacheFactory} used to create the {@link Cache}. + * + * @param factory {@link CacheFactory} used to create the {@link Cache}. + * @return the post processed {@link CacheFactory}. + * @see org.apache.geode.cache.CacheFactory + */ + protected Object postProcess(Object factory) { + return factory; + } + + /** + * Creates a new {@link Cache} instance using the provided {@link Object factory}. * * @param parameterized {@link Class} type extension of {@link GemFireCache}. * @param factory instance of {@link CacheFactory}. @@ -1175,6 +1204,26 @@ public class CacheFactoryBean extends AbstractFactoryBeanSupport return searchTimeout; } + /** + * Configures the {@link org.apache.geode.security.SecurityManager} used to secure this cache. + * + * @param securityManager {@link org.apache.geode.security.SecurityManager} used to secure this cache. + * @see org.apache.geode.security.SecurityManager + */ + public void setSecurityManager(SecurityManager securityManager) { + this.securityManager = securityManager; + } + + /** + * Returns the {@link org.apache.geode.security.SecurityManager} used to secure this cache. + * + * @return the {@link org.apache.geode.security.SecurityManager} used to secure this cache. + * @see org.apache.geode.security.SecurityManager + */ + public SecurityManager getSecurityManager() { + return securityManager; + } + /** * Sets the list of TransactionListeners used to configure the Cache to receive transaction events after * the transaction is processed (committed, rolled back). diff --git a/src/main/java/org/springframework/data/gemfire/client/ClientCacheFactoryBean.java b/src/main/java/org/springframework/data/gemfire/client/ClientCacheFactoryBean.java index 00b5021e..9482a4eb 100644 --- a/src/main/java/org/springframework/data/gemfire/client/ClientCacheFactoryBean.java +++ b/src/main/java/org/springframework/data/gemfire/client/ClientCacheFactoryBean.java @@ -243,7 +243,7 @@ public class ClientCacheFactoryBean extends CacheFactoryBean implements Applicat * @see #initializePdx(ClientCacheFactory) */ @Override - protected Object prepareFactory(Object factory) { + protected Object configureFactory(Object factory) { return initializePool(initializePdx((ClientCacheFactory) factory)); } diff --git a/src/test/java/org/springframework/data/gemfire/CacheFactoryBeanTest.java b/src/test/java/org/springframework/data/gemfire/CacheFactoryBeanTest.java index a6a8420f..3c053678 100644 --- a/src/test/java/org/springframework/data/gemfire/CacheFactoryBeanTest.java +++ b/src/test/java/org/springframework/data/gemfire/CacheFactoryBeanTest.java @@ -20,6 +20,7 @@ import static org.hamcrest.Matchers.equalTo; import static org.hamcrest.Matchers.instanceOf; import static org.hamcrest.Matchers.is; import static org.hamcrest.Matchers.notNullValue; +import static org.hamcrest.Matchers.nullValue; import static org.hamcrest.Matchers.sameInstance; import static org.junit.Assert.assertEquals; import static org.junit.Assert.assertFalse; @@ -437,11 +438,45 @@ public class CacheFactoryBeanTest { } @Test - public void prepareFactoryWithUnspecifiedPdxOptions() { + @SuppressWarnings("unchecked") + public void initializesFactoryWitCacheFactoryInitializer() { CacheFactory mockCacheFactory = mock(CacheFactory.class); - assertThat(new CacheFactoryBean().prepareFactory(mockCacheFactory), is(sameInstance(mockCacheFactory))); + CacheFactoryBean.CacheFactoryInitializer mockCacheFactoryInitializer = + mock(CacheFactoryBean.CacheFactoryInitializer.class); + + CacheFactoryBean cacheFactoryBean = new CacheFactoryBean(); + + cacheFactoryBean.setCacheFactoryInitializer(mockCacheFactoryInitializer); + + assertThat(cacheFactoryBean.getCacheFactoryInitializer(), is(equalTo(mockCacheFactoryInitializer))); + assertThat(cacheFactoryBean.initializeFactory(mockCacheFactory), is(sameInstance(mockCacheFactory))); + + verify(mockCacheFactoryInitializer, times(1)).initialize(eq(mockCacheFactory)); + verifyZeroInteractions(mockCacheFactory); + } + + @Test + public void initializeFactoryWhenNoCacheFactoryInitializerIsPresentIsNullSafe() { + + CacheFactory mockCacheFactory = mock(CacheFactory.class); + + CacheFactoryBean cacheFactoryBean = new CacheFactoryBean(); + + assertThat(cacheFactoryBean.getCacheFactoryInitializer(), + is(nullValue(CacheFactoryBean.CacheFactoryInitializer.class))); + assertThat(cacheFactoryBean.initializeFactory(mockCacheFactory), is(sameInstance(mockCacheFactory))); + + verifyZeroInteractions(mockCacheFactory); + } + + @Test + public void configureFactoryWithUnspecifiedPdxOptions() { + + CacheFactory mockCacheFactory = mock(CacheFactory.class); + + assertThat(new CacheFactoryBean().configureFactory(mockCacheFactory), is(sameInstance(mockCacheFactory))); verify(mockCacheFactory, never()).setPdxDiskStore(any(String.class)); verify(mockCacheFactory, never()).setPdxIgnoreUnreadFields(any(Boolean.class)); @@ -451,7 +486,7 @@ public class CacheFactoryBeanTest { } @Test - public void prepareFactoryWithSpecificPdxOptions() { + public void configureFactoryWithSpecificPdxOptions() { CacheFactoryBean cacheFactoryBean = new CacheFactoryBean(); @@ -461,7 +496,7 @@ public class CacheFactoryBeanTest { CacheFactory mockCacheFactory = mock(CacheFactory.class); - assertThat(cacheFactoryBean.prepareFactory(mockCacheFactory), is(sameInstance(mockCacheFactory))); + assertThat(cacheFactoryBean.configureFactory(mockCacheFactory), is(sameInstance(mockCacheFactory))); verify(mockCacheFactory, never()).setPdxDiskStore(any(String.class)); verify(mockCacheFactory, times(1)).setPdxIgnoreUnreadFields(eq(false)); @@ -471,7 +506,7 @@ public class CacheFactoryBeanTest { } @Test - public void prepareFactoryWithAllPdxOptions() { + public void configureFactoryWithAllPdxOptions() { CacheFactoryBean cacheFactoryBean = new CacheFactoryBean(); @@ -483,7 +518,7 @@ public class CacheFactoryBeanTest { CacheFactory mockCacheFactory = mock(CacheFactory.class); - assertThat(cacheFactoryBean.prepareFactory(mockCacheFactory), is(sameInstance(mockCacheFactory))); + assertThat(cacheFactoryBean.configureFactory(mockCacheFactory), is(sameInstance(mockCacheFactory))); verify(mockCacheFactory, times(1)).setPdxDiskStore(eq("testPdxDiskStoreName")); verify(mockCacheFactory, times(1)).setPdxIgnoreUnreadFields(eq(false)); @@ -493,26 +528,26 @@ public class CacheFactoryBeanTest { } @Test - public void createCacheWithExistingCache() throws Exception { + public void configureFactoryWithSecurityManager() { CacheFactory mockCacheFactory = mock(CacheFactory.class); + org.apache.geode.security.SecurityManager mockSecurityManager = + mock(org.apache.geode.security.SecurityManager.class); + CacheFactoryBean cacheFactoryBean = new CacheFactoryBean(); - cacheFactoryBean.setCache(mockCache); + cacheFactoryBean.setSecurityManager(mockSecurityManager); - assertThat(cacheFactoryBean.getCache(), is(sameInstance(mockCache))); + assertThat(cacheFactoryBean.getSecurityManager(), is(sameInstance(mockSecurityManager))); + assertThat(cacheFactoryBean.configureFactory(mockCacheFactory), is(sameInstance(mockCacheFactory))); - Cache actualCache = cacheFactoryBean.createCache(mockCacheFactory); - - assertThat(actualCache, is(sameInstance(mockCache))); - - verify(mockCacheFactory, never()).create(); - verifyZeroInteractions(mockCache); + verify(mockCacheFactory, times(1)).setSecurityManager(eq(mockSecurityManager)); + verifyZeroInteractions(mockSecurityManager); } @Test - public void createCacheWithNoExistingCache() { + public void createCacheWithCacheFactory() { CacheFactory mockCacheFactory = mock(CacheFactory.class); diff --git a/src/test/java/org/springframework/data/gemfire/client/ClientCacheFactoryBeanTest.java b/src/test/java/org/springframework/data/gemfire/client/ClientCacheFactoryBeanTest.java index 3b07c715..e53017cb 100644 --- a/src/test/java/org/springframework/data/gemfire/client/ClientCacheFactoryBeanTest.java +++ b/src/test/java/org/springframework/data/gemfire/client/ClientCacheFactoryBeanTest.java @@ -273,7 +273,7 @@ public class ClientCacheFactoryBeanTest { } }; - assertThat(clientCacheFactoryBean.prepareFactory(mockClientCacheFactory), + assertThat(clientCacheFactoryBean.configureFactory(mockClientCacheFactory), is(sameInstance(mockClientCacheFactory))); assertThat(initializePdxCalled.get(), is(true)); assertThat(initializePoolCalled.get(), is(true));