-
-
Save pianovwork/b360622dc76136064b0215136f402837 to your computer and use it in GitHub Desktop.
Cache based on session
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
@SpringBootApplication | |
@EnableCaching | |
@Import({ | |
CacheCleanupOnSessionDestroyingListener.class | |
}) | |
public class TestApp { | |
public static void main(String[] args) { | |
SpringApplication.run(TestApp.class, args); | |
} | |
@Bean | |
SessionBasedCacheManager cacheManager() { | |
return new SessionBasedCacheManager( | |
new ConcurrentMapCacheManager() | |
); | |
} | |
} |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
public class CacheCleanupOnSessionDestroyingListener implements HttpSessionListener { | |
private final SessionBasedCacheManager cacheManager; | |
public CacheCleanupOnSessionDestroyingListener(SessionBasedCacheManager cacheManager) { | |
this.cacheManager = cacheManager; | |
} | |
@Override | |
public void sessionCreated(HttpSessionEvent se) { | |
System.out.println(); | |
} | |
@Override | |
public void sessionDestroyed(HttpSessionEvent se) { | |
String id = se.getSession().getId(); | |
cacheManager.getCacheNames().stream() | |
.filter(name -> name.startsWith(id)) | |
.map(name -> cacheManager.getDelegate().getCache(name)) | |
.forEach(Cache::clear); | |
} | |
} |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
public class SessionBasedCacheManager implements CacheManager { | |
@Autowired | |
private HttpServletRequest request; | |
private final CacheManager delegate; | |
public SessionBasedCacheManager(CacheManager delegate) { | |
this.delegate = delegate; | |
} | |
@Override | |
public Cache getCache(String name) { | |
if (request == null) { | |
return null; | |
} | |
return delegate.getCache(request.getSession().getId() + "_" + name); | |
} | |
@Override | |
public Collection<String> getCacheNames() { | |
return delegate.getCacheNames(); | |
} | |
public CacheManager getDelegate() { | |
return delegate; | |
} | |
} |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
@RestController | |
public class TestController { | |
@Autowired | |
private HttpServletRequest request; | |
@Autowired | |
private MyService myService; | |
@Cacheable("cache_bucket") | |
@GetMapping("/test/cache") | |
public Object getFromCache() { | |
HashMap<Object, Object> map = new HashMap<>(); | |
map.put("id", myService.doSomething()); | |
map.put("session_id", request.getSession().getId()); | |
return map; | |
} | |
@DeleteMapping("/test/cache") | |
public Object deleteSession() { | |
request.getSession().invalidate(); | |
return Collections.emptyMap(); | |
} | |
} |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
package test.cache; | |
import com.cigna.ng.provider.BaseMockWebTest; | |
import org.junit.Assert; | |
import org.junit.Test; | |
import org.junit.runner.RunWith; | |
import org.mockito.Mockito; | |
import org.springframework.beans.factory.annotation.Autowired; | |
import org.springframework.boot.test.autoconfigure.web.servlet.WebMvcTest; | |
import org.springframework.boot.test.mock.mockito.MockBean; | |
import org.springframework.cache.annotation.EnableCaching; | |
import org.springframework.cache.concurrent.ConcurrentMapCacheManager; | |
import org.springframework.context.annotation.Bean; | |
import org.springframework.context.annotation.Import; | |
import org.springframework.mock.web.MockHttpSession; | |
import org.springframework.test.context.ContextConfiguration; | |
import org.springframework.test.context.junit4.SpringRunner; | |
import org.springframework.test.web.servlet.MockMvc; | |
import java.util.Map; | |
import static org.hamcrest.Matchers.is; | |
import static org.springframework.test.web.servlet.request.MockMvcRequestBuilders.delete; | |
import static org.springframework.test.web.servlet.request.MockMvcRequestBuilders.get; | |
import static org.springframework.test.web.servlet.result.MockMvcResultMatchers.status; | |
@RunWith(SpringRunner.class) | |
@WebMvcTest(secure = false) | |
@ContextConfiguration(classes = { | |
TestControllerTest.Config.class, | |
}) | |
@Import({ | |
TestController.class, | |
CacheCleanupOnSessionDestroyingListener.class | |
}) | |
public class TestControllerTest extends BaseMockWebTest { | |
@Autowired | |
MockMvc mockMvc; | |
@MockBean | |
MyService myService; | |
@Autowired | |
SessionBasedCacheManager cacheManager; | |
@Test | |
public void getFromCache() throws Exception { | |
MockHttpSession session = new MockHttpSession(); | |
session.setMaxInactiveInterval(500); | |
mockMvc.perform(get("/test/cache").session(session)) | |
.andExpect(status().isOk()); | |
mockMvc.perform(get("/test/cache").session(session)) | |
.andExpect(status().isOk()); | |
Mockito.verify(myService, Mockito.times(1)).doSomething(); | |
Assert.assertThat(getSizeOfFirstCache(), is(1)); | |
mockMvc.perform(delete("/test/cache").session(session)) | |
.andExpect(status().isOk()); | |
// todo: find a way to make listener works, maybe the problem in MockHttpSession | |
// Assert.assertThat(getSizeOfFirstCache(), is(0)); | |
} | |
private int getSizeOfFirstCache() { | |
Map map = (Map) cacheManager.getDelegate().getCache( | |
cacheManager.getCacheNames().iterator().next() | |
).getNativeCache(); | |
return map.size(); | |
} | |
@EnableCaching | |
public static class Config { | |
@Bean | |
SessionBasedCacheManager cacheManager() { | |
return new SessionBasedCacheManager( | |
new ConcurrentMapCacheManager() | |
); | |
} | |
} | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment