CacheElement.java 4.22 KB
package it.softecspa.fileproxy.cache;


import it.softecspa.PortalSettings;
import it.softecspa.database.dbconnect.SQLTimeoutException;
import it.softecspa.fileproxy.DatabaseBalancer.Balancer;
import it.softecspa.fileproxy.services.ServerCacheFactory.CacheKey;
import it.softecspa.fileproxy.services.common.EnterpriseLog;

import java.sql.SQLException;
import java.util.Collection;
import java.util.SortedMap;
import java.util.TreeMap;

import org.apache.log4j.Logger;

public abstract class CacheElement<K, V> {

	protected Logger log = Logger.getLogger(getClass());
	
	// Flag che indicase la cache è stata caricata
	private boolean loaded;
	// Contenitore delle coppie chiave/valore
	private SortedMap<K,V> container;
	// Nome della cache che la identifica univocamente
	private CacheKey uniqueName;
	
	// --------------------------------
	private Balancer balancer;
	
	
	
	public CacheElement(CacheKey name, Balancer balancer) {
		this.uniqueName = name;
		this.balancer = balancer;
		this.container = new TreeMap<K, V>();
	}
		
	
	/**
	 * La cache è spirata, deve essere ricaricata
	 * @return
	 */
	public boolean isExpired() {
		return !loaded;
	}
	
	/**
	 * La cache non è valida, non è caricata
	 * @return
	 */
	public boolean isLoaded() {
		return loaded;
	}
	
	/**
	 * Restituisce il container
	 * @return
	 */
	protected SortedMap<K, V> getContainer() {
		return container;
	}
	/*
	private void setContainer(Hashtable<K, V> values) {
		this.container = values;
	}
	*/
	
	/**
	 * Esegue il reload della cache
	 */
	public synchronized void load() {
		flush();
		
		// Eseguo la chiamata vera e propria per i caricamento
		/*
		 * 2013-05-07, m.veroni - Riscontrato errore che impedisce il reload in caso di errore di caricamento
		 */
		try {
			log.info("Load '"+getUniqueName()+"' cache container from "+balancer.toString()+" database");
			loaded = load(container, balancer);
		} catch (CacheException e) {
			loaded = false;
			
			// SQLTimeoutException, nessun invio di mail
			if ((e.getCause()!=null && e.getCause() instanceof SQLTimeoutException)) {
				log.fatal("SQLTimeoutException loading cache (DB TIMEOUT):" + e.getCause());
				return;
			}
			
			// SQLException, invio della mail
			if ((e.getCause()!=null && e.getCause() instanceof SQLException)) {
				EnterpriseLog elog = new EnterpriseLog(e.getCause().getMessage(), e);
				elog.write();
				elog.sendEmail(PortalSettings.MAIL_SQL_ERROR_ENABLE, "Error loading cache table");
				return;
			}
			
			log.fatal("Error in table cache: "+e.toString(),e);	
			EnterpriseLog elog = new EnterpriseLog(e.getCause().getMessage(), e);
			elog.write();
			elog.sendEmail(PortalSettings.MAIL_SQL_ERROR_ENABLE, "Error loading cache table");			
		}
    }
	
	
	/**
	 * Esegue il caricamento della cache a partire dal database
	 * In caso di esito positivo è restituito TRUE
	 * In caso di errore è restituito un FALSE
	 * @param container
	 * @param balancer
	 * @return
	 */
	protected abstract boolean load(SortedMap<K, V> container, Balancer balancer) throws CacheException;

	protected abstract String[] getTables();
	
	/**
	 * Pulisce il contenitore e lo obbliga ad un successivo reload 
	 */
	public synchronized void flush() {
		if (log.isDebugEnabled()) log.debug("Flush '"+getUniqueName()+"' cache container ("+balancer.name()+" balance)");
		container.clear();
		loaded = false;
	}

	
	public Balancer getBalancer() {
		return balancer;
	}


	public CacheKey getUniqueName() {
		return uniqueName;
	}

	
	
	/**
	 * Restituisce i valori di un altro container
	 * @param uniqueName
	 * @param balancer
	 * @return
	 * @throws CacheException
	 */
	protected Collection<V> getOtherContainerValues(CacheKey uniqueName, Balancer balancer) throws CacheException {
		CacheContainer cacheContainer = CacheContainer.getInstance();
		
		SortedMap<?, V> other = cacheContainer.getContainer(uniqueName, balancer);
		if (other==null) return null;		
		
		// Faccio una doppia verifica nel caso di errori di caricamento
		CacheElement<?,V> cacheElement = cacheContainer.getCacheElement(uniqueName, balancer);
		if (cacheElement.isExpired()) return null;
		
		//
		return other.values();
	}
	
	
}