package es.ejie.frmk.presentacion.operacion.paso;

import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

import org.apache.struts.action.Action;
import org.apache.struts.action.ActionForm;
import org.apache.struts.action.ActionForward;
import org.apache.struts.action.ActionMapping;
import org.apache.struts.action.RedirectingActionForward;

import es.ejie.frmk.infraestructura.traza.Q70TraceLevel;
import es.ejie.frmk.infraestructura.traza.Q70Traza;
import es.ejie.frmk.listeners.base.Q70ListenerUtils;
import es.ejie.frmk.presentacion.base.Q70PasosOPMapping;
import es.ejie.frmk.presentacion.operacion.Q70OperacionDePresentacionException;

/**
 * Esta clase recoge la URL absoluta de un paso de OP remoto (destino) del atributo "parameter" del paso origen y 
 * reencamina el flujo hacia él.
 * <p>
 * Para ello delega en las clases que la extienden la modalidad de reencaminamiento hacia ese paso remoto. Esas clases
 * deberán implementar el método abstracto <code>process</code>
 * <p>
 * Esta clase no es usada por las aplicaciones directamente como un paso más, sino que deberán utilizar alguna de las
 * clases que la extienden (por ejemplo: <code>Q70ActionRedirectOP</code>).
 */

public abstract class Q70ActionRemoto extends Action {

	/**
	 * Constante que indica el componente al que pertenece dicha clase. Es
	 * necesario para el uso del log de trazas.
	 */
	private static final String COMPONENTE = "OPERACION_PRESENTACION";

	/**
	 * Instancia del log de trazas
	 */
	private static Q70Traza tr = Q70Traza.getSingleton();
	
	/**
	 * El método recoge la URL absoluta de destino, y delega en el método <code>process</code> implementado
	 * por las clases que extiendan de la clase <code>Q70ActionRemoto</code>.
	 * <p>
	 * @param mapping Configuración de los pasos de una operacion de presentacion.
	 * @param form Bean de Formulario de la página anterior.
	 * @param request Petición a atender
	 * @param response Respuesta a generar
	 * @return ActionForward Reenvío a próximo paso de OP a encaminar
	 * @throws Exception 
	 * 
	 * @see org.apache.struts.action.Action#execute(org.apache.struts.action.ActionMapping, org.apache.struts.action.ActionForm, javax.servlet.http.HttpServletRequest, javax.servlet.http.HttpServletResponse)
	 */
	public ActionForward execute(ActionMapping mapping, ActionForm form, HttpServletRequest request, HttpServletResponse response) throws Exception
	{
		RedirectingActionForward retVal = null;
		String pathRemoto = null;
		Q70PasosOPMapping opMapping = (Q70PasosOPMapping)mapping;
		
		try {
			//Recuperamos la URL del atributo parameter del fichero de configuración
			String parameter = mapping.getParameter();
			if (parameter==null || parameter.length() < 1)
			{
				if (tr.isTraceActive())
				{
					tr.trace(COMPONENTE, Q70TraceLevel.ERROR, "No se ha definido la URI de la operación remota en el atributo parameter del fichero XML de configuración de la operación de presentación.");
				}
				throw new Q70OperacionDePresentacionException (this.getClass().toString(),"execute","No se ha definido la URI de la operación remota en el atributo parameter del fichero XML de configuración de la operación de presentación.",null);
			}
			//Recuperamos la URI bien construida (sin máscara)
			pathRemoto = Q70ListenerUtils.getRemoteURI(parameter,request.getSession());
			
			retVal = procces(opMapping, pathRemoto, request, form);
		} catch (Exception e) {
			if (tr.isTraceActive())
			{
				tr.trace(COMPONENTE, Q70TraceLevel.ERROR, "Excepción recogida por Action de Operacion de Presentacion que invoca a una operación remota.");
			}
			throw new Q70OperacionDePresentacionException (this.getClass().toString(),"execute","Excepción recogida por Action de Operacion de Presentacion que invoca a una operación remota.",e);
		}
		
		return (ActionForward)retVal; 
	}
	/**
	 * El método deberá ser sobrecargado por las clases que extiendan de <code>Q70ActionRemoto</code>.
	 * <p>
	 * Deberá implementar la solución concreta a la redirección al paso de OP remoto cuya URL absoluta conoce.
	 * <p>
	 * @param mapping Configuración de los pasos de una operacion de presentacion.
	 * @param pathRemoto URL absoluta a la que redireccionar.
	 * @param request Petición a atender
	 * @param form Bean de Formulario de la página
	 * @return Reenvío a próximo paso de OP remoto a encaminar
	 * @throws Q70OperacionDePresentacionException
	 */
	protected abstract RedirectingActionForward procces(Q70PasosOPMapping mapping, String pathRemoto, HttpServletRequest request, ActionForm form) throws Q70OperacionDePresentacionException;
}
