001/**
002 * Copyright (c) 2025-2026, Michael Yang 杨福海 (fuhai999@gmail.com).
003 * <p>
004 * Licensed under the GNU Lesser General Public License (LGPL) ,Version 3.0 (the "License");
005 * you may not use this file except in compliance with the License.
006 * You may obtain a copy of the License at
007 * <p>
008 * http://www.gnu.org/licenses/lgpl-3.0.txt
009 * <p>
010 * Unless required by applicable law or agreed to in writing, software
011 * distributed under the License is distributed on an "AS IS" BASIS,
012 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
013 * See the License for the specific language governing permissions and
014 * limitations under the License.
015 */
016package dev.tinyflow.core.node;
017
018import com.agentsflex.core.chain.Chain;
019import com.agentsflex.core.chain.Parameter;
020import com.agentsflex.core.chain.node.BaseNode;
021import com.agentsflex.core.util.Maps;
022import com.agentsflex.core.util.StringUtil;
023import com.jfinal.template.Engine;
024import com.jfinal.template.Template;
025
026import java.io.ByteArrayOutputStream;
027import java.util.List;
028import java.util.Map;
029
030public class TemplateNode extends BaseNode {
031
032    private static final Engine engine;
033    private String template;
034
035    static {
036        engine = Engine.create("template", e -> {
037            e.addSharedStaticMethod(StringUtil.class);
038        });
039    }
040
041    public String getTemplate() {
042        return template;
043    }
044
045    public void setTemplate(String template) {
046        this.template = template;
047    }
048
049
050    @Override
051    protected Map<String, Object> execute(Chain chain) {
052        Map<String, Object> parameters = chain.getParameterValues(this);
053
054        ByteArrayOutputStream result = new ByteArrayOutputStream();
055
056        Template templateByString = engine.getTemplateByString(template);
057        templateByString.render(parameters, result);
058
059        String outputDef = "output";
060        List<Parameter> outputDefs = getOutputDefs();
061        if (outputDefs != null && !outputDefs.isEmpty()) {
062            String parameterName = outputDefs.get(0).getName();
063            if (StringUtil.hasText(parameterName)) outputDef = parameterName;
064        }
065
066        return Maps.of(outputDef, result.toString());
067    }
068
069
070    @Override
071    public String toString() {
072        return "TemplateNode{" +
073                "template='" + template + '\'' +
074                ", description='" + description + '\'' +
075                ", parameters=" + parameters +
076                ", outputDefs=" + outputDefs +
077                ", id='" + id + '\'' +
078                ", name='" + name + '\'' +
079                ", async=" + async +
080                ", inwardEdges=" + inwardEdges +
081                ", outwardEdges=" + outwardEdges +
082                ", condition=" + condition +
083                ", memory=" + memory +
084                ", nodeStatus=" + nodeStatus +
085                '}';
086    }
087}