PluginLoader.java

/*
 * GovWay - A customizable API Gateway 
 * https://govway.org
 * 
 * Copyright (c) 2005-2024 Link.it srl (https://link.it). 
 * 
 * This program is free software: you can redistribute it and/or modify
 * it under the terms of the GNU General Public License version 3, as published by
 * the Free Software Foundation.
 *
 * This program is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 * GNU General Public License for more details.
 *
 * You should have received a copy of the GNU General Public License
 * along with this program.  If not, see <http://www.gnu.org/licenses/>.
 *
 */

package org.openspcoop2.monitor.engine.dynamic;

import org.openspcoop2.core.commons.CoreException;
import org.openspcoop2.core.plugins.constants.TipoPlugin;
import org.openspcoop2.utils.resources.Loader;
import org.slf4j.Logger;

/**
 * PluginLoader
 *
 * @author Poli Andrea (apoli@link.it)
 * @author $Author$
 * @version $Rev$, $Date$
 */
public class PluginLoader implements IPluginLoader {

	public static PluginLoader getInstance() {
		return (PluginLoader) CorePluginLoader.getInstance();
	}
	
	private PluginManager pluginManager = null;
	private Loader loader = null;
	private Logger log;
	
	public PluginLoader() {
		// nop
	}
	
	@Override
	public void init(Loader loader, Logger log) {
		this.loader = loader;
		this.log = log;
	}
	@Override
	public void init(Loader loader, Logger log, IRegistroPluginsReader registroPluginsReader, int expireSeconds) {
		init(loader, log);
		this.pluginManager = new PluginManager(registroPluginsReader, expireSeconds);
	}
	
	@Override
	public void close(Logger log) {
		if(this.pluginManager!=null) {
			try {
				this.pluginManager.close();
			}catch(Throwable t) {
				if(log!=null) {
					log.error("PluginManager close failure: "+t.getMessage(),t);
				}
			}
		}
	}
	
	public boolean isPluginManagerEnabled() {
		return this.pluginManager!=null;
	}
	public void updateFromConsoleConfig(Logger log) throws Exception {
		this.pluginManager.updateFromConsoleConfig(log);
	}
	
	
	// UTILITY
	
	@Override
	public Class<?> getDynamicClass(String className, TipoPlugin tipoPlugin, String tipo) throws CoreException {
		return getDynamicClass(className, tipoPlugin.getValue(), tipo);
	}
	@Override
	public Class<?> getDynamicClass(String className, String tipoPlugin, String tipo) throws CoreException {
		if(className==null) {
			throw new CoreException("Class not found ("+getObjectName(tipoPlugin)+" type '"+tipo+"')");
		}
		Class<?> c = null;
		if(this.isPluginManagerEnabled()) {
			if(this.pluginManager==null) {
				throw new CoreException("Plugin manager not initialized");
			}
			try {
				c = this.pluginManager.findClass(this.log, tipoPlugin, className);
			}catch(Exception e) {
				throw new CoreException("Class '"+className+"' not found in registry ("+getObjectName(tipoPlugin)+" type '"+tipo+"'): "+e.getMessage(),e);
			}
		}
		else {
			try {
				c = Class.forName(className);
			}catch(Exception e) {
				throw new CoreException("Class '"+className+"' not found in classpath: "+e.getMessage(),e);
			}	
		}
		if(c==null) {
			throw new CoreException("Class '"+className+"' not found in registry ("+getObjectName(tipoPlugin)+" type '"+tipo+"')");
		}
		return c;
	}
	
	@Override
	public <T> T newInstance(Class<T> c, TipoPlugin tipoPlugin, String tipo) throws CoreException{
		return newInstance(c, tipoPlugin.getValue(), tipo);
	}
	@Override
	@SuppressWarnings("unchecked")
	public <T> T newInstance(Class<T> c, String tipoPlugin, String tipo) throws CoreException{
		try {
			return (T) this.loader.newInstance(c);
		}catch(Throwable e) {
			throw new CoreException("Class '"+c.getClass().getName()+"' new instance error ("+getObjectName(tipoPlugin)+" type '"+tipo+"'): "+e.getMessage(),e);
		}
	}
	
	@Override
	public Object newInstance(String customTipoClasse, String tipo) throws Exception {
		Class<?> c = getDynamicClass(null, customTipoClasse, tipo);
		return newInstance(c, customTipoClasse, tipo);
	}
	
	protected String getObjectName(String tipoPluginParam) throws CoreException {
		
		TipoPlugin tipoPlugin = TipoPlugin.toEnumConstant(tipoPluginParam);
		
		if(tipoPlugin==null) {
			return tipoPluginParam;
		}
		
		switch (tipoPlugin) {
		case CONNETTORE:
			return "connector";
		case AUTENTICAZIONE:
			return "authentication";
		case AUTORIZZAZIONE:
			return "authorization";
		case AUTORIZZAZIONE_CONTENUTI:
			return "authorization content";
		case INTEGRAZIONE:
			return "integration";
		case SERVICE_HANDLER:
			return "service handler";
		case MESSAGE_HANDLER:
			return "message handler";
		case BEHAVIOUR:
			return "behaviour";
		case RATE_LIMITING:
			return "policy rate limiting";
		case ALLARME:
			return "alarm";
		case TRANSAZIONE:
			return "transaction library";
		case RICERCA:
			return "search library";
		case STATISTICA:
			return "stats library";
		case TOKEN_DYNAMIC_DISCOVERY:
			return "token dynamic discovery";
		case TOKEN_VALIDAZIONE:
			return "token validation policy";
		case TOKEN_NEGOZIAZIONE:
			return "token retrieve policy";
		case ATTRIBUTE_AUTHORITY:
			return "attribute authority";
		}
		throw new CoreException("?? Type '"+tipoPlugin+"' unsupported ??");
	}
	
}