use of org.codehaus.groovy.ast.AnnotationNode in project groovy-core by groovy.
the class MemoizedASTTransformation method visit.
public void visit(ASTNode[] nodes, final SourceUnit source) {
init(nodes, source);
AnnotationNode annotationNode = (AnnotationNode) nodes[0];
AnnotatedNode annotatedNode = (AnnotatedNode) nodes[1];
if (MY_TYPE.equals(annotationNode.getClassNode()) && annotatedNode instanceof MethodNode) {
MethodNode methodNode = (MethodNode) annotatedNode;
if (methodNode.isAbstract()) {
addError("Annotation " + MY_TYPE_NAME + " cannot be used for abstract methods.", methodNode);
return;
}
if (methodNode.isVoidMethod()) {
addError("Annotation " + MY_TYPE_NAME + " cannot be used for void methods.", methodNode);
return;
}
ClassNode ownerClassNode = methodNode.getDeclaringClass();
MethodNode delegatingMethod = buildDelegatingMethod(methodNode, ownerClassNode);
ownerClassNode.addMethod(delegatingMethod);
int modifiers = FieldNode.ACC_PRIVATE | FieldNode.ACC_FINAL;
if (methodNode.isStatic()) {
modifiers = modifiers | FieldNode.ACC_STATIC;
}
int protectedCacheSize = getMemberIntValue(annotationNode, PROTECTED_CACHE_SIZE_NAME);
int maxCacheSize = getMemberIntValue(annotationNode, MAX_CACHE_SIZE_NAME);
MethodCallExpression memoizeClosureCallExpression = buildMemoizeClosureCallExpression(delegatingMethod, protectedCacheSize, maxCacheSize);
String memoizedClosureFieldName = buildUniqueName(ownerClassNode, CLOSURE_LABEL, methodNode);
FieldNode memoizedClosureField = new FieldNode(memoizedClosureFieldName, modifiers, newClass(ClassHelper.CLOSURE_TYPE), null, memoizeClosureCallExpression);
ownerClassNode.addField(memoizedClosureField);
BlockStatement newCode = new BlockStatement();
MethodCallExpression closureCallExpression = callX(fieldX(memoizedClosureField), CLOSURE_CALL_METHOD_NAME, args(methodNode.getParameters()));
closureCallExpression.setImplicitThis(false);
newCode.addStatement(returnS(closureCallExpression));
methodNode.setCode(newCode);
VariableScopeVisitor visitor = new VariableScopeVisitor(source);
visitor.visitClass(ownerClassNode);
}
}
use of org.codehaus.groovy.ast.AnnotationNode in project groovy-core by groovy.
the class PackageScopeASTTransformation method visit.
public void visit(ASTNode[] nodes, SourceUnit source) {
init(nodes, source);
AnnotatedNode parent = (AnnotatedNode) nodes[1];
AnnotationNode node = (AnnotationNode) nodes[0];
boolean legacyMode = LEGACY_TYPE_NAME.equals(node.getClassNode().getName());
if (!MY_TYPE.equals(node.getClassNode()) && !legacyMode)
return;
Expression value = node.getMember("value");
if (parent instanceof ClassNode) {
List<groovy.transform.PackageScopeTarget> targets;
if (value == null)
targets = Collections.singletonList(legacyMode ? PackageScopeTarget.FIELDS : PackageScopeTarget.CLASS);
else
targets = determineTargets(value);
visitClassNode((ClassNode) parent, targets);
parent.getAnnotations();
} else {
if (value != null) {
addError("Error during " + MY_TYPE_NAME + " processing: " + TARGET_CLASS_NAME + " only allowed at class level.", parent);
return;
}
if (parent instanceof MethodNode) {
visitMethodNode((MethodNode) parent);
} else if (parent instanceof FieldNode) {
visitFieldNode((FieldNode) parent);
}
}
}
use of org.codehaus.groovy.ast.AnnotationNode in project groovy-core by groovy.
the class BaseScriptASTTransformation method visit.
public void visit(ASTNode[] nodes, SourceUnit source) {
init(nodes, source);
AnnotatedNode parent = (AnnotatedNode) nodes[1];
AnnotationNode node = (AnnotationNode) nodes[0];
if (!MY_TYPE.equals(node.getClassNode()))
return;
if (parent instanceof DeclarationExpression) {
changeBaseScriptTypeFromDeclaration((DeclarationExpression) parent, node);
} else if (parent instanceof ImportNode || parent instanceof PackageNode) {
changeBaseScriptTypeFromPackageOrImport(source, parent, node);
} else if (parent instanceof ClassNode) {
changeBaseScriptTypeFromClass((ClassNode) parent, node);
}
}
use of org.codehaus.groovy.ast.AnnotationNode in project groovy-core by groovy.
the class AsmClassGenerator method visitAnnotationAttributes.
/**
* Generate the annotation attributes.
* @param an the node with an annotation
* @param av the visitor to use
*/
private void visitAnnotationAttributes(AnnotationNode an, AnnotationVisitor av) {
Map<String, Object> constantAttrs = new HashMap<String, Object>();
Map<String, PropertyExpression> enumAttrs = new HashMap<String, PropertyExpression>();
Map<String, Object> atAttrs = new HashMap<String, Object>();
Map<String, ListExpression> arrayAttrs = new HashMap<String, ListExpression>();
for (String name : an.getMembers().keySet()) {
Expression expr = an.getMember(name);
if (expr instanceof AnnotationConstantExpression) {
atAttrs.put(name, ((AnnotationConstantExpression) expr).getValue());
} else if (expr instanceof ConstantExpression) {
constantAttrs.put(name, ((ConstantExpression) expr).getValue());
} else if (expr instanceof ClassExpression) {
constantAttrs.put(name, Type.getType(BytecodeHelper.getTypeDescription((expr.getType()))));
} else if (expr instanceof PropertyExpression) {
enumAttrs.put(name, (PropertyExpression) expr);
} else if (expr instanceof ListExpression) {
arrayAttrs.put(name, (ListExpression) expr);
} else if (expr instanceof ClosureExpression) {
ClassNode closureClass = controller.getClosureWriter().getOrAddClosureClass((ClosureExpression) expr, ACC_PUBLIC);
constantAttrs.put(name, Type.getType(BytecodeHelper.getTypeDescription(closureClass)));
}
}
for (Map.Entry entry : constantAttrs.entrySet()) {
av.visit((String) entry.getKey(), entry.getValue());
}
for (Map.Entry entry : enumAttrs.entrySet()) {
PropertyExpression propExp = (PropertyExpression) entry.getValue();
av.visitEnum((String) entry.getKey(), BytecodeHelper.getTypeDescription(propExp.getObjectExpression().getType()), String.valueOf(((ConstantExpression) propExp.getProperty()).getValue()));
}
for (Map.Entry entry : atAttrs.entrySet()) {
AnnotationNode atNode = (AnnotationNode) entry.getValue();
AnnotationVisitor av2 = av.visitAnnotation((String) entry.getKey(), BytecodeHelper.getTypeDescription(atNode.getClassNode()));
visitAnnotationAttributes(atNode, av2);
av2.visitEnd();
}
visitArrayAttributes(an, arrayAttrs, av);
}
use of org.codehaus.groovy.ast.AnnotationNode in project groovy-core by groovy.
the class AnnotationConstantExpression method visit.
public void visit(GroovyCodeVisitor visitor) {
AnnotationNode node = (AnnotationNode) getValue();
Map<String, Expression> attrs = node.getMembers();
for (Expression expr : attrs.values()) {
expr.visit(visitor);
}
super.visit(visitor);
}
Aggregations