Note that there are some explanatory texts on larger screens.

plurals
  1. PO
    primarykey
    data
    text
    <p>I wouldn't walk this manually if I were you. After generating a lexer and parser, ANTLR would also have generated a file called <code>CfscriptBaseListener</code> that has empty methods for all of your parser rules. You can let ANTLR walk your tree and attach a custom tree-listener in which you override only those methods/rules you're interested in.</p> <p>In your case, you probably want to be notified whenever a new function is created (to create a new scope) and you'll probably be interested in variable assignments (<code>variableStatement</code> and <code>nonVarVariableStatement</code>). Your listener, let's call is <code>VarListener</code> will keep track of all scopes as ANTLR walks the tree.</p> <p>I did change 1 rule slightly (I added <code>objectLiteralEntry</code>):</p> <pre>objectLiteral : '{' (objectLiteralEntry (',' objectLiteralEntry)*)? '}' ; objectLiteralEntry : Identifier '=' expression ; </pre> <p>which makes life easier in the following demo:</p> <h2>VarListener.java</h2> <pre class="lang-java prettyprint-override"><code>public class VarListener extends CfscriptBaseListener { private Stack&lt;Scope&gt; scopes; public VarListener() { scopes = new Stack&lt;Scope&gt;(); scopes.push(new Scope(null)); } @Override public void enterVariableStatement(CfscriptParser.VariableStatementContext ctx) { String varName = ctx.variableName().getText(); Scope scope = scopes.peek(); scope.add(varName); } @Override public void enterNonVarVariableStatement(CfscriptParser.NonVarVariableStatementContext ctx) { String varName = ctx.variableName().getText(); checkVarName(varName); } @Override public void enterObjectLiteralEntry(CfscriptParser.ObjectLiteralEntryContext ctx) { String varName = ctx.Identifier().getText(); checkVarName(varName); } @Override public void enterFunctionDeclaration(CfscriptParser.FunctionDeclarationContext ctx) { scopes.push(new Scope(scopes.peek())); } @Override public void exitFunctionDeclaration(CfscriptParser.FunctionDeclarationContext ctx) { scopes.pop(); } private void checkVarName(String varName) { Scope scope = scopes.peek(); if(scope.inScope(varName)) { System.out.println("OK : " + varName); } else { System.out.println("Oops : " + varName); } } } </code></pre> <p>A <code>Scope</code> object could be as simple as:</p> <h2>Scope.java</h2> <pre class="lang-java prettyprint-override"><code>class Scope extends HashSet&lt;String&gt; { final Scope parent; public Scope(Scope parent) { this.parent = parent; } boolean inScope(String varName) { if(super.contains(varName)) { return true; } return parent == null ? false : parent.inScope(varName); } } </code></pre> <p>Now, to test this all, here's a small main class:</p> <h2>Main.java</h2> <pre class="lang-java prettyprint-override"><code>import org.antlr.v4.runtime.*; import org.antlr.v4.runtime.tree.*; public class Main { public static void main(String[] args) throws Exception { CfscriptLexer lexer = new CfscriptLexer(new ANTLRFileStream("Test.cfc")); CfscriptParser parser = new CfscriptParser(new CommonTokenStream(lexer)); ParseTree tree = parser.component(); ParseTreeWalker.DEFAULT.walk(new VarListener(), tree); } } </code></pre> <p>If you run this <code>Main</code> class, the following will be printed:</p> <pre>Oops : testing Oops : testingagain OK : test Oops : mystuff Oops : interior Oops : third Oops : other Oops : something</pre> <p>Without a doubt, this is not exactly what you want and I probably goofed up some scoping rules of Coldfusion. But I think this will give you some insight in how to solve your problem properly. I think the code is pretty self explanatory, but if this is not the case, don't hesitate to ask for clarification.</p> <p>HTH</p>
    singulars
    1. This table or related slice is empty.
    plurals
    1. This table or related slice is empty.
    1. This table or related slice is empty.
    1. This table or related slice is empty.
    1. VO
      singulars
      1. This table or related slice is empty.
    2. VO
      singulars
      1. This table or related slice is empty.
    3. VO
      singulars
      1. This table or related slice is empty.
 

Querying!

 
Guidance

SQuiL has stopped working due to an internal error.

If you are curious you may find further information in the browser console, which is accessible through the devtools (F12).

Reload