cache per le chiamate IS
This commit is contained in:
parent
7020180804
commit
7abf8eac7a
|
@ -0,0 +1,22 @@
|
|||
|
||||
package org.gcube.portlets.user.cloudcomputing;
|
||||
|
||||
import java.io.IOException;
|
||||
|
||||
import javax.portlet.PortletException;
|
||||
import javax.portlet.RenderRequest;
|
||||
import javax.portlet.RenderResponse;
|
||||
|
||||
import com.liferay.portal.kernel.log.LogFactoryUtil;
|
||||
|
||||
public class CC_MethodsListPortlet extends CC_Portlet {
|
||||
|
||||
private static com.liferay.portal.kernel.log.Log _log = LogFactoryUtil
|
||||
.getLog(CC_MethodsListPortlet.class);
|
||||
|
||||
public void render(RenderRequest renderRequest, RenderResponse renderResponse)
|
||||
throws PortletException, IOException {
|
||||
super.render(renderRequest, renderResponse);
|
||||
}
|
||||
|
||||
}
|
|
@ -17,5 +17,4 @@ public class CC_MethodsMonitorPortlet extends CC_Portlet {
|
|||
throws PortletException, IOException {
|
||||
super.render(renderRequest, renderResponse);
|
||||
}
|
||||
|
||||
}
|
||||
|
|
|
@ -13,6 +13,7 @@ import javax.servlet.http.HttpServletRequest;
|
|||
import org.gcube.common.portal.PortalContext;
|
||||
import org.gcube.portlets.user.cloudcomputing.config.CC_Config;
|
||||
import org.gcube.portlets.user.cloudcomputing.is.IsClient;
|
||||
import org.gcube.portlets.user.cloudcomputing.is.IsClientFactory;
|
||||
import org.gcube.portlets.user.cloudcomputing.is.IsServerConfig;
|
||||
|
||||
import com.liferay.portal.kernel.log.LogFactoryUtil;
|
||||
|
@ -22,7 +23,7 @@ import com.liferay.util.bridges.mvc.MVCPortlet;
|
|||
public class CC_Portlet extends MVCPortlet {
|
||||
private static com.liferay.portal.kernel.log.Log _log = LogFactoryUtil.getLog(CC_Portlet.class);
|
||||
|
||||
private static CC_Config configuration = null;
|
||||
private CC_Config configuration = null;
|
||||
|
||||
public final static String IS_AUTH_RESOURCE_NAME = "IAM";
|
||||
public final static String IS_AUTH_CATEGORY = "Service";
|
||||
|
@ -59,15 +60,17 @@ public class CC_Portlet extends MVCPortlet {
|
|||
String host = base_url.getHost();
|
||||
config.gateway = host;
|
||||
|
||||
IsServerConfig auth_config = IsClient.serviceConfigFromIS(IS_AUTH_RESOURCE_NAME,
|
||||
IsClient isclient = IsClientFactory.getSingleton();
|
||||
|
||||
IsServerConfig auth_config = isclient.serviceConfigFromIS(IS_AUTH_RESOURCE_NAME,
|
||||
IS_AUTH_CATEGORY, IS_AUTH_ENTRYPOINT);
|
||||
config.auth_url = auth_config.getServerUrl();
|
||||
|
||||
IsServerConfig ccp_config = IsClient.serviceConfigFromIS(IS_CCP_RESOURCE_NAME,
|
||||
IsServerConfig ccp_config = isclient.serviceConfigFromIS(IS_CCP_RESOURCE_NAME,
|
||||
IS_CCP_CATEGORY, IS_CCP_ENTRYPOINT);
|
||||
config.ccp_url = ccp_config.getServerUrl();
|
||||
|
||||
IsServerConfig cdn_config = IsClient.serviceConfigFromIS(IS_CCP_RESOURCE_NAME,
|
||||
IsServerConfig cdn_config = isclient.serviceConfigFromIS(IS_CCP_RESOURCE_NAME,
|
||||
IS_CCP_CATEGORY, IS_CDN_ENTRYPOINT);
|
||||
config.cdn_url = cdn_config.getServerUrl();
|
||||
|
||||
|
|
|
@ -0,0 +1,103 @@
|
|||
package org.gcube.portlets.user.cloudcomputing.is;
|
||||
|
||||
|
||||
import java.io.Serializable;
|
||||
import java.rmi.ServerException;
|
||||
import java.util.List;
|
||||
import java.util.concurrent.TimeUnit;
|
||||
|
||||
import org.gcube.common.resources.gcore.ServiceEndpoint;
|
||||
|
||||
import com.liferay.portal.kernel.cache.MultiVMPoolUtil;
|
||||
import com.liferay.portal.kernel.cache.PortalCache;
|
||||
import com.liferay.portal.kernel.log.LogFactoryUtil;
|
||||
|
||||
/**
|
||||
* Utility class to query EndPoints and search for AccessPoints from IS
|
||||
*
|
||||
* @author Alfredo Oliviero (ISTI - CNR)
|
||||
*/
|
||||
|
||||
public class CacheIsClient extends IsClient {
|
||||
private static com.liferay.portal.kernel.log.Log logger = LogFactoryUtil.getLog(CacheIsClient.class);
|
||||
private static CacheIsClient _singleInstance;
|
||||
|
||||
// Class to represent a cache entry
|
||||
|
||||
static CacheIsClient getSingleton() {
|
||||
if (_singleInstance == null) {
|
||||
_singleInstance = new CacheIsClient();
|
||||
}
|
||||
return _singleInstance;
|
||||
}
|
||||
|
||||
|
||||
private static class CacheEntry implements Serializable {
|
||||
List<ServiceEndpoint> endpoints;
|
||||
long timestamp;
|
||||
|
||||
CacheEntry(List<ServiceEndpoint> endpoints, long timestamp) {
|
||||
this.endpoints = endpoints;
|
||||
this.timestamp = timestamp;
|
||||
}
|
||||
}
|
||||
|
||||
// Define the cache name
|
||||
private static final String CACHE_NAME = "my-cache";
|
||||
private PortalCache<Serializable, Serializable> portalCache = MultiVMPoolUtil.getCache(CACHE_NAME);
|
||||
|
||||
// Method to get the cache key
|
||||
private String getCacheKey(String resourceName, String category) {
|
||||
return resourceName + ":" + category;
|
||||
}
|
||||
|
||||
// Main method with caching and locking
|
||||
public synchronized List<ServiceEndpoint> getEndpointsFromISWithCache(String resource_name, String category) throws ServerException {
|
||||
String key = getCacheKey(resource_name, category);
|
||||
long currentTime = System.currentTimeMillis();
|
||||
|
||||
logger.info("Request received for resource: " + resource_name + ", category: " + category);
|
||||
|
||||
synchronized (key.intern()) {
|
||||
logger.info("Acquired lock for key: " + key);
|
||||
|
||||
// Check if the entry is present in the cache and is valid
|
||||
CacheEntry cacheEntry = (CacheEntry)portalCache.get(key);
|
||||
if (cacheEntry != null) {
|
||||
if (currentTime - cacheEntry.timestamp <= TimeUnit.MINUTES.toMillis(10)) {
|
||||
// If the cache value is still valid, return it
|
||||
logger.info("Cache hit for key: " + key);
|
||||
return cacheEntry.endpoints;
|
||||
} else {
|
||||
// Otherwise, remove the expired entry
|
||||
logger.info("Cache expired for key: " + key);
|
||||
portalCache.remove(key);
|
||||
}
|
||||
}
|
||||
|
||||
// If not present in the cache or is expired, make the request
|
||||
logger.info("Cache miss for key: " + key + ". Making request to external service.");
|
||||
List<ServiceEndpoint> endpoints;
|
||||
try {
|
||||
endpoints = super.getEndpointsFromIS(resource_name, category);
|
||||
} catch (ServerException e) {
|
||||
logger.error("Error fetching data from external service for key: " + key, e);
|
||||
throw e;
|
||||
}
|
||||
|
||||
// Update the cache with the new result and timestamp
|
||||
logger.info("Updating cache for key: " + key);
|
||||
portalCache.put(key, new CacheEntry(endpoints, currentTime));
|
||||
|
||||
return endpoints;
|
||||
}
|
||||
}
|
||||
// Metodo principale con caching e locking
|
||||
public List<ServiceEndpoint> getEndpointsFromIS(String resource_name, String category) throws ServerException {
|
||||
logger.info("@@@ cached getEndpointsFromIS: " + resource_name + ":" + category);
|
||||
|
||||
return getEndpointsFromISWithCache(resource_name, category);
|
||||
}
|
||||
|
||||
|
||||
}
|
|
@ -0,0 +1,114 @@
|
|||
package org.gcube.portlets.user.cloudcomputing.is;
|
||||
|
||||
import java.rmi.ServerException;
|
||||
import java.util.List;
|
||||
import java.util.concurrent.ConcurrentHashMap;
|
||||
import java.util.concurrent.TimeUnit;
|
||||
import java.util.concurrent.locks.Lock;
|
||||
import java.util.concurrent.locks.ReentrantLock;
|
||||
|
||||
import org.gcube.common.resources.gcore.ServiceEndpoint;
|
||||
|
||||
import com.liferay.portal.kernel.log.LogFactoryUtil;
|
||||
|
||||
/**
|
||||
* Utility class to query EndPoints and search for AccessPoints from IS
|
||||
*
|
||||
* @author Alfredo Oliviero (ISTI - CNR)
|
||||
*/
|
||||
|
||||
public class CacheIsClient extends IsClient {
|
||||
private static com.liferay.portal.kernel.log.Log logger = LogFactoryUtil.getLog(CacheIsClient.class);
|
||||
|
||||
private static CacheIsClient _singleInstance = null;
|
||||
|
||||
public int CACHE_DURATION_SECONDS = 1 * 10;
|
||||
|
||||
static CacheIsClient getSingleton() {
|
||||
if (_singleInstance == null) {
|
||||
_singleInstance = new CacheIsClient();
|
||||
}
|
||||
return _singleInstance;
|
||||
}
|
||||
|
||||
private static class CacheEntry {
|
||||
List<ServiceEndpoint> endpoints;
|
||||
long timestamp;
|
||||
|
||||
CacheEntry(List<ServiceEndpoint> endpoints, long timestamp) {
|
||||
this.endpoints = endpoints;
|
||||
this.timestamp = timestamp;
|
||||
}
|
||||
}
|
||||
|
||||
// Mappa per mantenere la cache
|
||||
private ConcurrentHashMap<String, CacheEntry> cache = new ConcurrentHashMap<>();
|
||||
// Mappa per mantenere i lock
|
||||
private ConcurrentHashMap<String, Lock> locks = new ConcurrentHashMap<>();
|
||||
|
||||
// Metodo per ottenere la chiave della cache
|
||||
private String getCacheKey(String resourceName, String category) {
|
||||
return resourceName + ":" + category;
|
||||
}
|
||||
|
||||
// Metodo principale con caching e locking
|
||||
public List<ServiceEndpoint> getEndpointsFromIS(String resource_name, String category) throws ServerException {
|
||||
return getEndpointsFromISWithCache(resource_name, category);
|
||||
}
|
||||
|
||||
|
||||
// Main method with caching and locking
|
||||
public List<ServiceEndpoint> getEndpointsFromISWithCache(String resource_name, String category) throws ServerException {
|
||||
String key = getCacheKey(resource_name, category);
|
||||
long currentTime = System.currentTimeMillis();
|
||||
|
||||
logger.info("Request received for resource: " + resource_name + ", category: " + category);
|
||||
|
||||
// Get or create a lock for the specific key
|
||||
Lock lock = locks.computeIfAbsent(key, k -> new ReentrantLock());
|
||||
logger.info("Lock object created/retrieved for key: " + key);
|
||||
|
||||
// Acquire the lock
|
||||
logger.info("### Acquiring lock for key: " + key);
|
||||
lock.lock();
|
||||
try {
|
||||
logger.info("### Lock acquired for key: " + key);
|
||||
// Check if the entry is present in the cache and is valid
|
||||
if (cache.containsKey(key)) {
|
||||
CacheEntry cacheEntry = cache.get(key);
|
||||
if (currentTime - cacheEntry.timestamp <= TimeUnit.MINUTES.toMillis(10)) {
|
||||
// If the cache value is still valid, return it
|
||||
logger.info(">>> Cache hit for key: " + key);
|
||||
return cacheEntry.endpoints;
|
||||
} else {
|
||||
// Otherwise, remove the expired entry
|
||||
logger.info(">>> Cache expired for key: " + key);
|
||||
cache.remove(key);
|
||||
}
|
||||
}
|
||||
|
||||
// If not present in the cache or is expired, make the request
|
||||
logger.info(">>> Cache miss for key: " + key + ". Making request to external service.");
|
||||
List<ServiceEndpoint> endpoints;
|
||||
try {
|
||||
endpoints = getEndpointsFromIS(resource_name, category);
|
||||
} catch (ServerException e) {
|
||||
logger.error( "Error fetching data from external service for key: " + key, e);
|
||||
throw e;
|
||||
}
|
||||
|
||||
// Update the cache with the new result and timestamp
|
||||
logger.info("Updating cache for key: " + key);
|
||||
cache.put(key, new CacheEntry(endpoints, currentTime));
|
||||
|
||||
return endpoints;
|
||||
} finally {
|
||||
// Release the lock
|
||||
logger.info("### Releasing lock for key: " + key);
|
||||
lock.unlock();
|
||||
// Remove the lock from the map to avoid memory leaks
|
||||
logger.info("### Removing lock from map for key: " + key);
|
||||
locks.remove(key);
|
||||
}
|
||||
}
|
||||
}
|
|
@ -29,6 +29,15 @@ import com.liferay.portal.kernel.log.LogFactoryUtil;
|
|||
public class IsClient {
|
||||
private static com.liferay.portal.kernel.log.Log logger = LogFactoryUtil.getLog(IsClient.class);
|
||||
|
||||
private static IsClient _singleInstance = null;
|
||||
|
||||
static IsClient getSingleton() {
|
||||
if (_singleInstance == null) {
|
||||
_singleInstance = new IsClient();
|
||||
}
|
||||
return _singleInstance;
|
||||
}
|
||||
|
||||
/**
|
||||
* obatins from IS the list of ServiceEndpoint matching the parameters
|
||||
*
|
||||
|
@ -42,10 +51,10 @@ public class IsClient {
|
|||
* @throws Exception
|
||||
*/
|
||||
|
||||
public static ServiceEndpoint getFirstEndopintsFromIS(String resource_name, String category)
|
||||
public ServiceEndpoint getFirstEndopintsFromIS(String resource_name, String category)
|
||||
throws ServerException {
|
||||
|
||||
List<ServiceEndpoint> endpoints = getEndopintsFromIS(resource_name, category);
|
||||
List<ServiceEndpoint> endpoints = getEndpointsFromIS(resource_name, category);
|
||||
if (endpoints == null || endpoints.size() == 0) {
|
||||
logger.error("Unable to retrieve service endpoint " + resource_name);
|
||||
return null;
|
||||
|
@ -55,8 +64,10 @@ public class IsClient {
|
|||
|
||||
}
|
||||
|
||||
public static List<ServiceEndpoint> getEndopintsFromIS(String resource_name, String category
|
||||
/* , boolean root_service, Secret secret */) throws ServerException {
|
||||
public List<ServiceEndpoint> getEndpointsFromIS(String resource_name, String category
|
||||
) throws ServerException {
|
||||
logger.info("@@@ not cached getEndpointsFromIS: " + resource_name + ":" + category);
|
||||
|
||||
SimpleQuery query = queryFor(ServiceEndpoint.class);
|
||||
|
||||
if (resource_name != null) {
|
||||
|
@ -74,6 +85,7 @@ public class IsClient {
|
|||
ScopeProvider.instance.set(infrastructure);
|
||||
|
||||
try {
|
||||
logger.info (" IS CLIENT Requiring " + resource_name + ":"+ category);
|
||||
// if (root_service) {
|
||||
|
||||
// endpoints = AuthorizedTasks.executeSafely(() -> {
|
||||
|
@ -107,10 +119,10 @@ public class IsClient {
|
|||
* @throws ServerException
|
||||
* @throws Exception
|
||||
*/
|
||||
public static List<ServiceEndpoint.AccessPoint> getAccessPointsFromIS(String resource_name, String category,
|
||||
public List<ServiceEndpoint.AccessPoint> getAccessPointsFromIS(String resource_name, String category,
|
||||
String endPointName/* , boolean is_root_service, Secret secret */) throws ServerException {
|
||||
|
||||
List<ServiceEndpoint> resources = getEndopintsFromIS(resource_name, category/* , is_root_service, secret */);
|
||||
List<ServiceEndpoint> resources = getEndpointsFromIS(resource_name, category/* , is_root_service, secret */);
|
||||
|
||||
if (resources.size() == 0) {
|
||||
logger.error("There is no Runtime Resource having name " + resource_name + " and Category "
|
||||
|
@ -142,7 +154,7 @@ public class IsClient {
|
|||
* @throws ServerException
|
||||
* @throws Exception
|
||||
*/
|
||||
public static ServiceEndpoint.AccessPoint getFirstAccessPointFromIS(String resource_name, String category,
|
||||
public ServiceEndpoint.AccessPoint getFirstAccessPointFromIS(String resource_name, String category,
|
||||
String entryPointName/* , boolean root_service, Secret secret */) throws ServerException {
|
||||
|
||||
List<ServiceEndpoint.AccessPoint> access_points = getAccessPointsFromIS(resource_name, category,
|
||||
|
@ -175,7 +187,7 @@ public class IsClient {
|
|||
* @return
|
||||
* @throws Exception
|
||||
*/
|
||||
public static IsServerConfig serviceConfigFromIS(String resourceName, String category, String endPointName
|
||||
public IsServerConfig serviceConfigFromIS(String resourceName, String category, String endPointName
|
||||
/* , boolean is_root_service, Secret secret */)
|
||||
throws ServerException {
|
||||
|
||||
|
|
|
@ -0,0 +1,32 @@
|
|||
package org.gcube.portlets.user.cloudcomputing.is;
|
||||
|
||||
import com.liferay.portal.kernel.log.LogFactoryUtil;
|
||||
|
||||
// import org.gcube.common.security.AuthorizedTasks;
|
||||
// import org.gcube.common.security.secrets.Secret;
|
||||
|
||||
/**
|
||||
* Utility class to query EndPoints and search for AccessPoints from IS
|
||||
*
|
||||
* @author Alfredo Oliviero (ISTI - CNR)
|
||||
*/
|
||||
|
||||
public class IsClientFactory {
|
||||
private static com.liferay.portal.kernel.log.Log logger = LogFactoryUtil.getLog(IsClientFactory.class);
|
||||
static boolean cache_enabled = true;
|
||||
|
||||
public static IsClient getSingleton(){
|
||||
return getSingleton(cache_enabled);
|
||||
}
|
||||
|
||||
public static IsClient getSingleton(boolean use_cache){
|
||||
if (use_cache) {
|
||||
logger.info("@@@ IsClientFactory cache enabled");
|
||||
return CacheIsClient.getSingleton();
|
||||
} else {
|
||||
logger.info("@@@ IsClientFactory cache not enabled");
|
||||
|
||||
return IsClient.getSingleton();
|
||||
}
|
||||
}
|
||||
}
|
Loading…
Reference in New Issue