You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@groovy.apache.org by su...@apache.org on 2017/06/10 03:56:51 UTC
groovy git commit: Minor refactoring
Repository: groovy
Updated Branches:
refs/heads/master 2019d3cd3 -> f227b267e
Minor refactoring
Project: http://git-wip-us.apache.org/repos/asf/groovy/repo
Commit: http://git-wip-us.apache.org/repos/asf/groovy/commit/f227b267
Tree: http://git-wip-us.apache.org/repos/asf/groovy/tree/f227b267
Diff: http://git-wip-us.apache.org/repos/asf/groovy/diff/f227b267
Branch: refs/heads/master
Commit: f227b267e22e5bc99808a7cc39999f745734381e
Parents: 2019d3c
Author: sunlan <su...@apache.org>
Authored: Sat Jun 10 11:56:36 2017 +0800
Committer: sunlan <su...@apache.org>
Committed: Sat Jun 10 11:56:36 2017 +0800
----------------------------------------------------------------------
src/main/org/codehaus/groovy/ast/ASTNode.java | 91 ++----------
.../groovy/ast/NodeMetaDataHandler.java | 137 +++++++++++++++++++
.../apache/groovy/parser/antlr4/GroovyParser.g4 | 53 ++-----
.../apache/groovy/parser/antlr4/AstBuilder.java | 48 +++----
4 files changed, 175 insertions(+), 154 deletions(-)
----------------------------------------------------------------------
http://git-wip-us.apache.org/repos/asf/groovy/blob/f227b267/src/main/org/codehaus/groovy/ast/ASTNode.java
----------------------------------------------------------------------
diff --git a/src/main/org/codehaus/groovy/ast/ASTNode.java b/src/main/org/codehaus/groovy/ast/ASTNode.java
index 058af78..a192e68 100644
--- a/src/main/org/codehaus/groovy/ast/ASTNode.java
+++ b/src/main/org/codehaus/groovy/ast/ASTNode.java
@@ -18,10 +18,8 @@
*/
package org.codehaus.groovy.ast;
-import org.codehaus.groovy.GroovyBugError;
import org.codehaus.groovy.util.ListHashMap;
-import java.util.Collections;
import java.util.Map;
/**
@@ -46,13 +44,13 @@ import java.util.Map;
* @author <a href="mailto:james@coredevelopers.net">James Strachan</a>
* @author <a href="mailto:blackdrag@gmx.org">Jochen "blackdrag" Theodorou</a>
*/
-public class ASTNode {
+public class ASTNode implements NodeMetaDataHandler {
private int lineNumber = -1;
private int columnNumber = -1;
private int lastLineNumber = -1;
private int lastColumnNumber = -1;
- private ListHashMap metaDataMap = null;
+ private Map metaDataMap = null;
public void visit(GroovyCodeVisitor visitor) {
throw new RuntimeException("No visit() method implemented for class: " + getClass().getName());
@@ -108,93 +106,22 @@ public class ASTNode {
this.lastColumnNumber = node.getLastColumnNumber();
this.lineNumber = node.getLineNumber();
}
-
- /**
- * Gets the node meta data.
- *
- * @param key - the meta data key
- * @return the node meta data value for this key
- */
- public <T> T getNodeMetaData(Object key) {
- if (metaDataMap == null) {
- return (T) null;
- }
- return (T) metaDataMap.get(key);
- }
/**
* Copies all node meta data from the other node to this one
* @param other - the other node
*/
public void copyNodeMetaData(ASTNode other) {
- if (other.metaDataMap == null) {
- return;
- }
- if (metaDataMap == null) {
- metaDataMap = new ListHashMap();
- }
- metaDataMap.putAll(other.metaDataMap);
- }
-
- /**
- * Sets the node meta data.
- *
- * @param key - the meta data key
- * @param value - the meta data value
- * @throws GroovyBugError if key is null or there is already meta
- * data under that key
- */
- public void setNodeMetaData(Object key, Object value) {
- if (key==null) throw new GroovyBugError("Tried to set meta data with null key on "+this+".");
- if (metaDataMap == null) {
- metaDataMap = new ListHashMap();
- }
- Object old = metaDataMap.put(key,value);
- if (old!=null) throw new GroovyBugError("Tried to overwrite existing meta data "+this+".");
+ copyNodeMetaData((NodeMetaDataHandler) other);
}
- /**
- * Sets the node meta data but allows overwriting values.
- *
- * @param key - the meta data key
- * @param value - the meta data value
- * @return the old node meta data value for this key
- * @throws GroovyBugError if key is null
- */
- public Object putNodeMetaData(Object key, Object value) {
- if (key == null) throw new GroovyBugError("Tried to set meta data with null key on " + this + ".");
- if (metaDataMap == null) {
- metaDataMap = new ListHashMap();
- }
- return metaDataMap.put(key, value);
- }
-
- /**
- * Removes a node meta data entry.
- *
- * @param key - the meta data key
- * @throws GroovyBugError if the key is null
- */
- public void removeNodeMetaData(Object key) {
- if (key==null) throw new GroovyBugError("Tried to remove meta data with null key "+this+".");
- if (metaDataMap == null) {
- return;
- }
- metaDataMap.remove(key);
- }
-
- /**
- * Returns an unmodifiable view of the current node metadata.
- * @return the node metadata. Always not null.
- */
- public Map<?,?> getNodeMetaData() {
- if (metaDataMap==null) {
- return Collections.emptyMap();
- }
- return Collections.unmodifiableMap(metaDataMap);
+ @Override
+ public ListHashMap getMetaDataMap() {
+ return (ListHashMap) metaDataMap;
}
- public ListHashMap getMetaDataMap() {
- return metaDataMap;
+ @Override
+ public void setMetaDataMap(Map<?, ?> metaDataMap) {
+ this.metaDataMap = metaDataMap;
}
}
http://git-wip-us.apache.org/repos/asf/groovy/blob/f227b267/src/main/org/codehaus/groovy/ast/NodeMetaDataHandler.java
----------------------------------------------------------------------
diff --git a/src/main/org/codehaus/groovy/ast/NodeMetaDataHandler.java b/src/main/org/codehaus/groovy/ast/NodeMetaDataHandler.java
new file mode 100644
index 0000000..280cd6b
--- /dev/null
+++ b/src/main/org/codehaus/groovy/ast/NodeMetaDataHandler.java
@@ -0,0 +1,137 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package org.codehaus.groovy.ast;
+
+import org.codehaus.groovy.GroovyBugError;
+import org.codehaus.groovy.util.ListHashMap;
+
+import java.util.Collections;
+import java.util.Map;
+
+/**
+ * An interface to mark a node being able to handle metadata
+ */
+public interface NodeMetaDataHandler {
+ /**
+ * Gets the node meta data.
+ *
+ * @param key - the meta data key
+ * @return the node meta data value for this key
+ */
+ default <T> T getNodeMetaData(Object key) {
+ Map<?, ?> metaDataMap = this.getMetaDataMap();
+
+ if (metaDataMap == null) {
+ return (T) null;
+ }
+ return (T) metaDataMap.get(key);
+ }
+
+ /**
+ * Copies all node meta data from the other node to this one
+ *
+ * @param other - the other node
+ */
+ default void copyNodeMetaData(NodeMetaDataHandler other) {
+ Map otherMetaDataMap = other.getMetaDataMap();
+ if (otherMetaDataMap == null) {
+ return;
+ }
+ Map metaDataMap = this.getMetaDataMap();
+ if (metaDataMap == null) {
+ metaDataMap = new ListHashMap();
+ this.setMetaDataMap(metaDataMap);
+ }
+
+ metaDataMap.putAll(otherMetaDataMap);
+ }
+
+ /**
+ * Sets the node meta data.
+ *
+ * @param key - the meta data key
+ * @param value - the meta data value
+ * @throws GroovyBugError if key is null or there is already meta
+ * data under that key
+ */
+ default void setNodeMetaData(Object key, Object value) {
+ if (key == null) throw new GroovyBugError("Tried to set meta data with null key on " + this + ".");
+
+ Map metaDataMap = this.getMetaDataMap();
+ if (metaDataMap == null) {
+ metaDataMap = new ListHashMap();
+ this.setMetaDataMap(metaDataMap);
+ }
+ Object old = metaDataMap.put(key, value);
+ if (old != null) throw new GroovyBugError("Tried to overwrite existing meta data " + this + ".");
+ }
+
+ /**
+ * Sets the node meta data but allows overwriting values.
+ *
+ * @param key - the meta data key
+ * @param value - the meta data value
+ * @return the old node meta data value for this key
+ * @throws GroovyBugError if key is null
+ */
+ default Object putNodeMetaData(Object key, Object value) {
+ if (key == null) throw new GroovyBugError("Tried to set meta data with null key on " + this + ".");
+
+ Map metaDataMap = this.getMetaDataMap();
+ if (metaDataMap == null) {
+ metaDataMap = new ListHashMap();
+ this.setMetaDataMap(metaDataMap);
+ }
+ return metaDataMap.put(key, value);
+ }
+
+ /**
+ * Removes a node meta data entry.
+ *
+ * @param key - the meta data key
+ * @throws GroovyBugError if the key is null
+ */
+ default void removeNodeMetaData(Object key) {
+ if (key == null) throw new GroovyBugError("Tried to remove meta data with null key " + this + ".");
+
+ Map metaDataMap = this.getMetaDataMap();
+ if (metaDataMap == null) {
+ return;
+ }
+ metaDataMap.remove(key);
+ }
+
+ /**
+ * Returns an unmodifiable view of the current node metadata.
+ *
+ * @return the node metadata. Always not null.
+ */
+ default Map<?, ?> getNodeMetaData() {
+ Map metaDataMap = this.getMetaDataMap();
+
+ if (metaDataMap == null) {
+ return Collections.emptyMap();
+ }
+ return Collections.unmodifiableMap(metaDataMap);
+ }
+
+ Map<?, ?> getMetaDataMap();
+
+ void setMetaDataMap(Map<?, ?> metaDataMap);
+}
http://git-wip-us.apache.org/repos/asf/groovy/blob/f227b267/subprojects/parser-antlr4/src/main/antlr4/org/apache/groovy/parser/antlr4/GroovyParser.g4
----------------------------------------------------------------------
diff --git a/subprojects/parser-antlr4/src/main/antlr4/org/apache/groovy/parser/antlr4/GroovyParser.g4 b/subprojects/parser-antlr4/src/main/antlr4/org/apache/groovy/parser/antlr4/GroovyParser.g4
index cfdd3c1..6f644ef 100644
--- a/subprojects/parser-antlr4/src/main/antlr4/org/apache/groovy/parser/antlr4/GroovyParser.g4
+++ b/subprojects/parser-antlr4/src/main/antlr4/org/apache/groovy/parser/antlr4/GroovyParser.g4
@@ -41,14 +41,13 @@ options {
@header {
import java.util.Map;
- import org.codehaus.groovy.util.ListHashMap;
+ import org.codehaus.groovy.ast.NodeMetaDataHandler;
import org.apache.groovy.parser.antlr4.SemanticPredicates;
- import org.codehaus.groovy.GroovyBugError;
}
@members {
- public static class GroovyParserRuleContext extends ParserRuleContext {
+ public static class GroovyParserRuleContext extends ParserRuleContext implements NodeMetaDataHandler {
private Map metaDataMap = null;
public GroovyParserRuleContext() {}
@@ -57,50 +56,14 @@ options {
super(parent, invokingStateNumber);
}
- /**
- * Gets the node meta data.
- *
- * @param key - the meta data key
- * @return the node meta data value for this key
- */
- public <T> T getNodeMetaData(Object key) {
- if (metaDataMap == null) {
- return (T) null;
- }
- return (T) metaDataMap.get(key);
+ @Override
+ public Map<?, ?> getMetaDataMap() {
+ return this.metaDataMap;
}
- /**
- * Sets the node meta data.
- *
- * @param key - the meta data key
- * @param value - the meta data value
- * @throws GroovyBugError if key is null or there is already meta
- * data under that key
- */
- public void setNodeMetaData(Object key, Object value) {
- if (key==null) throw new GroovyBugError("Tried to set meta data with null key on "+this+".");
- if (metaDataMap == null) {
- metaDataMap = new ListHashMap();
- }
- Object old = metaDataMap.put(key,value);
- if (old!=null) throw new GroovyBugError("Tried to overwrite existing meta data "+this+".");
- }
-
- /**
- * Sets the node meta data but allows overwriting values.
- *
- * @param key - the meta data key
- * @param value - the meta data value
- * @return the old node meta data value for this key
- * @throws GroovyBugError if key is null
- */
- public Object putNodeMetaData(Object key, Object value) {
- if (key == null) throw new GroovyBugError("Tried to set meta data with null key on " + this + ".");
- if (metaDataMap == null) {
- metaDataMap = new ListHashMap();
- }
- return metaDataMap.put(key, value);
+ @Override
+ public void setMetaDataMap(Map<?, ?> metaDataMap) {
+ this.metaDataMap = metaDataMap;
}
}
http://git-wip-us.apache.org/repos/asf/groovy/blob/f227b267/subprojects/parser-antlr4/src/main/java/org/apache/groovy/parser/antlr4/AstBuilder.java
----------------------------------------------------------------------
diff --git a/subprojects/parser-antlr4/src/main/java/org/apache/groovy/parser/antlr4/AstBuilder.java b/subprojects/parser-antlr4/src/main/java/org/apache/groovy/parser/antlr4/AstBuilder.java
index 17a6c16..7ac33a0 100644
--- a/subprojects/parser-antlr4/src/main/java/org/apache/groovy/parser/antlr4/AstBuilder.java
+++ b/subprojects/parser-antlr4/src/main/java/org/apache/groovy/parser/antlr4/AstBuilder.java
@@ -47,6 +47,7 @@ import org.codehaus.groovy.ast.ImportNode;
import org.codehaus.groovy.ast.InnerClassNode;
import org.codehaus.groovy.ast.MethodNode;
import org.codehaus.groovy.ast.ModuleNode;
+import org.codehaus.groovy.ast.NodeMetaDataHandler;
import org.codehaus.groovy.ast.PackageNode;
import org.codehaus.groovy.ast.Parameter;
import org.codehaus.groovy.ast.PropertyNode;
@@ -1713,7 +1714,7 @@ public class AstBuilder extends GroovyParserBaseVisitor<Object> implements Groov
(PropertyExpression) baseExpr, arguments),
arguments);
- } else if (baseExpr instanceof MethodCallExpression && !isTrue(baseExpr, IS_INSIDE_PARENTHESES)) { // e.g. m {} a, b OR m(...) a, b
+ } else if (baseExpr instanceof MethodCallExpression && !isInsideParentheses(baseExpr)) { // e.g. m {} a, b OR m(...) a, b
if (asBoolean(arguments)) {
// The error should never be thrown.
throw new GroovyBugError("When baseExpr is a instance of MethodCallExpression, which should follow NO argumentList");
@@ -1721,7 +1722,7 @@ public class AstBuilder extends GroovyParserBaseVisitor<Object> implements Groov
methodCallExpression = (MethodCallExpression) baseExpr;
} else if (
- !isTrue(baseExpr, IS_INSIDE_PARENTHESES)
+ !isInsideParentheses(baseExpr)
&& (baseExpr instanceof VariableExpression /* e.g. m 1, 2 */
|| baseExpr instanceof GStringExpression /* e.g. "$m" 1, 2 */
|| (baseExpr instanceof ConstantExpression && isTrue(baseExpr, IS_STRING)) /* e.g. "m" 1, 2 */)
@@ -1821,8 +1822,6 @@ public class AstBuilder extends GroovyParserBaseVisitor<Object> implements Groov
public Expression visitParExpression(ParExpressionContext ctx) {
Expression expression = this.visitExpressionInPar(ctx.expressionInPar());
- expression.putNodeMetaData(IS_INSIDE_PARENTHESES, true);
-
Integer insideParenLevel = expression.getNodeMetaData(INSIDE_PARENTHESES_LEVEL);
if (asBoolean((Object) insideParenLevel)) {
insideParenLevel++;
@@ -1963,7 +1962,7 @@ public class AstBuilder extends GroovyParserBaseVisitor<Object> implements Groov
Expression argumentsExpr = this.visitArguments(ctx.arguments());
this.configureAST(argumentsExpr, ctx);
- if (isTrue(baseExpr, IS_INSIDE_PARENTHESES)) { // e.g. (obj.x)(), (obj.@x)()
+ if (isInsideParentheses(baseExpr)) { // e.g. (obj.x)(), (obj.@x)()
MethodCallExpression methodCallExpression =
new MethodCallExpression(
baseExpr,
@@ -2409,7 +2408,7 @@ public class AstBuilder extends GroovyParserBaseVisitor<Object> implements Groov
ExpressionContext expressionCtx = ctx.expression();
Expression expression = (Expression) this.visit(expressionCtx);
- Boolean insidePar = isTrue(expression, IS_INSIDE_PARENTHESES);
+ Boolean insidePar = isInsideParentheses(expression);
switch (ctx.op.getType()) {
case ADD: {
@@ -2601,7 +2600,7 @@ public class AstBuilder extends GroovyParserBaseVisitor<Object> implements Groov
Expression leftExpr = (Expression) this.visit(ctx.left);
if (leftExpr instanceof VariableExpression
- && isTrue(leftExpr, IS_INSIDE_PARENTHESES)) { // it is a special multiple assignment whose variable count is only one, e.g. (a) = [1]
+ && isInsideParentheses(leftExpr)) { // it is a special multiple assignment whose variable count is only one, e.g. (a) = [1]
if ((Integer) leftExpr.getNodeMetaData(INSIDE_PARENTHESES_LEVEL) > 1) {
throw createParsingFailedException("Nested parenthesis is not allowed in multiple assignment, e.g. ((a)) = b", ctx);
@@ -2620,7 +2619,7 @@ public class AstBuilder extends GroovyParserBaseVisitor<Object> implements Groov
!(
(leftExpr instanceof VariableExpression
// && !(THIS_STR.equals(leftExpr.getText()) || SUPER_STR.equals(leftExpr.getText())) // commented, e.g. this = value // this will be transformed to $this
- && !isTrue(leftExpr, IS_INSIDE_PARENTHESES)) // e.g. p = 123
+ && !isInsideParentheses(leftExpr)) // e.g. p = 123
|| leftExpr instanceof PropertyExpression // e.g. obj.p = 123
@@ -2893,7 +2892,7 @@ public class AstBuilder extends GroovyParserBaseVisitor<Object> implements Groov
Expression expression = (Expression) this.visit(ctx.primary());
// if the key is variable and not inside parentheses, convert it to a constant, e.g. [a:1, b:2]
- if (expression instanceof VariableExpression && !isTrue(expression, IS_INSIDE_PARENTHESES)) {
+ if (expression instanceof VariableExpression && !isInsideParentheses(expression)) {
expression =
this.configureAST(
new ConstantExpression(((VariableExpression) expression).getName()),
@@ -3940,6 +3939,16 @@ public class AstBuilder extends GroovyParserBaseVisitor<Object> implements Groov
return moduleNode.getStatementBlock().isEmpty() && moduleNode.getMethods().isEmpty() && moduleNode.getClasses().isEmpty();
}
+ private boolean isInsideParentheses(NodeMetaDataHandler nodeMetaDataHandler) {
+ Integer insideParenLevel = nodeMetaDataHandler.getNodeMetaData(INSIDE_PARENTHESES_LEVEL);
+
+ if (asBoolean((Object) insideParenLevel)) {
+ return insideParenLevel > 0;
+ }
+
+ return false;
+ }
+
private void addEmptyReturnStatement() {
moduleNode.addStatement(ReturnStatement.RETURN_NULL_OR_VOID);
}
@@ -4103,29 +4112,15 @@ public class AstBuilder extends GroovyParserBaseVisitor<Object> implements Groov
return astNode;
}
- private boolean isTrue(GroovyParserRuleContext ctx, String key) {
- Object nmd = ctx.getNodeMetaData(key);
-
- if (null == nmd) {
- return false;
- }
-
- if (!(nmd instanceof Boolean)) {
- throw new GroovyBugError(ctx + " ctx meta data[" + key + "] is not an instance of Boolean");
- }
-
- return (Boolean) nmd;
- }
-
- private boolean isTrue(ASTNode node, String key) {
- Object nmd = node.getNodeMetaData(key);
+ private boolean isTrue(NodeMetaDataHandler nodeMetaDataHandler, String key) {
+ Object nmd = nodeMetaDataHandler.getNodeMetaData(key);
if (null == nmd) {
return false;
}
if (!(nmd instanceof Boolean)) {
- throw new GroovyBugError(node + " node meta data[" + key + "] is not an instance of Boolean");
+ throw new GroovyBugError(nodeMetaDataHandler + " node meta data[" + key + "] is not an instance of Boolean");
}
return (Boolean) nmd;
@@ -4348,7 +4343,6 @@ public class AstBuilder extends GroovyParserBaseVisitor<Object> implements Groov
private static final Set<String> PRIMITIVE_TYPE_SET = Collections.unmodifiableSet(new HashSet<>(Arrays.asList("boolean", "char", "byte", "short", "int", "long", "float", "double")));
private static final Logger LOGGER = Logger.getLogger(AstBuilder.class.getName());
- private static final String IS_INSIDE_PARENTHESES = "_IS_INSIDE_PARENTHESES";
private static final String INSIDE_PARENTHESES_LEVEL = "_INSIDE_PARENTHESES_LEVEL";
private static final String IS_INSIDE_INSTANCEOF_EXPR = "_IS_INSIDE_INSTANCEOF_EXPR";