ScriptEventTransformer.java
5.2 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
/*
* Decompiled with CFR 0_118.
*
* Could not load the following classes:
* org.mozilla.javascript.CompilerEnvirons
* org.mozilla.javascript.EvaluatorException
* org.mozilla.javascript.Parser
* org.mozilla.javascript.ast.AstNode
* org.mozilla.javascript.ast.AstRoot
* org.mozilla.javascript.ast.FunctionNode
* org.mozilla.javascript.ast.Name
* org.mozilla.javascript.ast.NodeVisitor
* org.slf4j.Logger
* org.slf4j.LoggerFactory
*/
package com.adobe.forms.transformer;
import java.io.BufferedReader;
import java.io.IOException;
import java.io.Reader;
import java.io.StringReader;
import org.mozilla.javascript.CompilerEnvirons;
import org.mozilla.javascript.EvaluatorException;
import org.mozilla.javascript.Parser;
import org.mozilla.javascript.ast.AstNode;
import org.mozilla.javascript.ast.AstRoot;
import org.mozilla.javascript.ast.FunctionNode;
import org.mozilla.javascript.ast.Name;
import org.mozilla.javascript.ast.NodeVisitor;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
public class ScriptEventTransformer {
private static Logger logger = LoggerFactory.getLogger(ScriptEventTransformer.class);
public String transformScript(String sScriptText, Boolean parse) throws IOException {
if (!parse.booleanValue()) {
return sScriptText;
}
if (sScriptText == null) {
return "";
}
CompilerEnvirons compileEnv = new CompilerEnvirons();
compileEnv.setRecordingComments(false);
compileEnv.setStrictMode(false);
Parser p = new Parser(compileEnv);
AstRoot astRoot = null;
try {
astRoot = p.parse(sScriptText, null, 0);
}
catch (EvaluatorException e) {
logger.error("Error while parsing scriptText: " + sScriptText, (Throwable)e);
throw e;
}
XfaScriptEventVisitor scriptVisitor = new XfaScriptEventVisitor();
astRoot.visit((NodeVisitor)scriptVisitor);
if (!scriptVisitor.hasFunctionNode) {
return astRoot.toSource();
}
String transformedScript = "var _tf_return = undefined; \n" + scriptVisitor.oldVarsBuffer + "try{ \n" + scriptVisitor.setFunctionsBuffer + " \n " + scriptVisitor.setVarsBuffer + " \n " + "var _tf_executable = " + this.escapeSingleQuote(astRoot.toSource()) + "; \n " + "_tf_return = eval(_tf_executable); \n " + "}finally{ \n" + "_tf_return; \n" + "} \n";
return transformedScript;
}
private String escapeSingleQuote(String text) throws IOException {
String lineSeparator = System.getProperty("line.separator");
StringBuffer output = new StringBuffer();
String esText = text.replaceAll("\\\\", "\\\\\\\\").replaceAll("'", "\\\\'");
BufferedReader reader = new BufferedReader(new StringReader(esText));
String line = null;
while ((line = reader.readLine()) != null) {
output.append("'" + line + " \\n' + " + lineSeparator);
}
String result = output.toString();
int lastTerminate = result.lastIndexOf("+ " + lineSeparator);
if (lastTerminate >= 0) {
result = result.substring(0, lastTerminate);
}
return result;
}
protected static class XfaScriptEventVisitor
implements NodeVisitor {
public boolean hasFunctionNode = false;
public StringBuilder oldVarsBuffer = new StringBuilder("var oldValues = {}; \n");
public StringBuilder setFunctionsBuffer = new StringBuilder("var _tf_this = this; \n");
public StringBuilder setVarsBuffer = new StringBuilder("");
public StringBuilder resetVarsBuffer = new StringBuilder();
protected XfaScriptEventVisitor() {
}
public boolean visit(AstNode node) {
if (node instanceof FunctionNode) {
if (!this.hasFunctionNode) {
this.hasFunctionNode = true;
}
String identifier = null;
String transformedId = null;
FunctionNode functionNode = (FunctionNode)node;
if (functionNode.getFunctionName() != null && functionNode.getFunctionName().getIdentifier() != null) {
identifier = functionNode.getFunctionName().getIdentifier();
transformedId = "_tf_" + identifier;
functionNode.getFunctionName().setIdentifier(transformedId);
}
if (identifier != null && identifier.length() > 0) {
if (this.setVarsBuffer.length() > 0) {
this.setVarsBuffer.append("\n");
}
this.oldVarsBuffer.append("oldValues['" + identifier + "'] = this['" + identifier + "'];\n");
String intMdtIdentifier = "_tf_$_" + identifier;
this.setFunctionsBuffer.append("function " + intMdtIdentifier + "(){ return " + transformedId + ".apply(_tf_this, arguments); } \n");
this.setVarsBuffer.append("this['" + identifier + "'] = " + intMdtIdentifier + "; \n");
this.resetVarsBuffer.append("this['" + identifier + "'] = oldValues['" + identifier + "']; \n");
}
return false;
}
return true;
}
}
}