/** * Copyright (c) 2014, the Railo Company Ltd. * Copyright (c) 2015, Lucee Assosication Switzerland * * This library is free software; you can redistribute it and/or * modify it under the terms of the GNU Lesser General Public * License as published by the Free Software Foundation; either * version 2.1 of the License, or (at your option) any later version. * * This library 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 * Lesser General Public License for more details. * * You should have received a copy of the GNU Lesser General Public * License along with this library. If not, see <http://www.gnu.org/licenses/>. * */ package lucee.transformer.cfml.evaluator; import java.util.ArrayList; import java.util.Iterator; import java.util.List; import lucee.commons.lang.ExceptionUtil; import lucee.runtime.exp.TemplateException; import lucee.transformer.bytecode.expression.var.BIF; import lucee.transformer.bytecode.statement.tag.Tag; import lucee.transformer.library.function.FunctionLib; import lucee.transformer.library.function.FunctionLibFunction; import lucee.transformer.library.tag.TagLibTag; import lucee.transformer.util.SourceCode; /** * * Wenn der CFML Transformer waehrend des uebersetzungsprozess auf einen Tag stoesst, * prueft er mithilfe der passenden TagLib, * ob dieses Tag eine Evaluator definiert hat. * Wenn ein Evaluator definiert ist, kann der CFML Transformer diesen aber nicht sofort aufrufen, * da zuerst das komplette Dokument uebersetzt werden muss, * bevor ein Evaluator aufgerufen werden kann. * Hier kommt der EvaluatorPool zum Einsatz, * der CFMLTransfomer uebergibt den Evaluator den er von der TagLib erhalten hat, * an den EvaluatorPool weiter. * Sobald der CFMLTransfomer den uebersetzungsprozess abgeschlossen hat, * ruft er dann den EvaluatorPool auf und dieser ruft dann alle Evaluatoren auf die im uebergeben wurden. */ public final class EvaluatorPool { List<TagData> tags=new ArrayList<TagData>(); List<FunctionData> functions=new ArrayList<FunctionData>(); /** * add a tag to the pool to evaluate at the end */ public void add(TagLibTag libTag,Tag tag, FunctionLib[] flibs, SourceCode cfml) { tags.add(new TagData(libTag,tag,flibs,cfml)); } public void add(FunctionLibFunction flf,BIF bif, SourceCode cfml) { functions.add(new FunctionData(flf,bif,cfml)); } /** * Die Methode run wird aufgerufen sobald, der CFML Transformer den uebersetzungsprozess angeschlossen hat. * Die metode run rauft darauf alle Evaluatoren auf die intern gespeicher wurden und loescht den internen Speicher. * @throws TemplateException */ public void run() throws TemplateException { { // tags Iterator<TagData> it = tags.iterator(); while(it.hasNext()) { TagData td=it.next(); SourceCode cfml=td.cfml; cfml.setPos(td.pos); try { if(td.libTag.getEvaluator()!=null)td.libTag.getEvaluator().evaluate( td.tag, td.libTag, td.flibs); } catch (EvaluatorException e) { clear();//print.printST(e); throw new TemplateException(cfml,e); }catch (Throwable e) { ExceptionUtil.rethrowIfNecessary(e); clear(); throw new TemplateException(cfml,e); } } tags.clear(); } // functions Iterator<FunctionData> it = functions.iterator(); while(it.hasNext()) { FunctionData td=it.next(); SourceCode cfml=td.cfml; cfml.setPos(td.pos); try { if(td.flf.getEvaluator()!=null)td.flf.getEvaluator().evaluate( td.bif, td.flf); } catch (EvaluatorException e) { clear();//print.printST(e); throw new TemplateException(cfml,e); }catch (Throwable e) { ExceptionUtil.rethrowIfNecessary(e); clear(); throw new TemplateException(cfml,e); } } functions.clear(); } /** * internal class to store all tag related data */ static class TagData { private final TagLibTag libTag; private final Tag tag; private final FunctionLib[] flibs; private final SourceCode cfml; private final int pos; public TagData(TagLibTag libTag,Tag tag, FunctionLib[] flibs, SourceCode cfml) { this.libTag=libTag; this.tag=tag; this.flibs=flibs; this.cfml=cfml; this.pos=cfml.getPos(); } } static class FunctionData { private final FunctionLibFunction flf; private final BIF bif; private final SourceCode cfml; private final int pos; public FunctionData(FunctionLibFunction flf,BIF bif, SourceCode cfml) { this.flf=flf; this.bif=bif; this.cfml=cfml; this.pos=cfml.getPos(); } } /** * clears the ppol */ public void clear() { tags.clear(); functions.clear(); } /*public static void getPool() { // TODO Auto-generated method stub }*/ }