use of org.codehaus.groovy.ast.ASTNode in project egradle by de-jcup.
the class GradleBuildScriptResultBuilder method start.
protected void start(CompletableFuture<EGradleBuildscriptResult> future, String buildScript, String pathToGradle) throws EGradleBuildScriptException {
Exception error = null;
File dir = new File(pathToGradle, "lib");
List<URL> list = new ArrayList<>();
File[] jarFiles = dir.listFiles(new FileFilter() {
@Override
public boolean accept(File file) {
return file != null && file.isFile() && file.getName().endsWith(".jar");
}
});
for (File file : jarFiles) {
try {
addFileToList(list, file);
} catch (MalformedURLException e) {
throw new EGradleBuildScriptException("Was not able to parse buildscript because of missing library: " + file, e);
}
}
URL[] urls = (URL[]) list.toArray(new URL[list.size()]);
URLClassLoader child = new URLClassLoader(urls);
Thread.currentThread().setContextClassLoader(child);
StringBuilder buildscriptWrapper = createBuildscriptWrapper(buildScript);
try {
Class<?> classToLoad;
classToLoad = Class.forName("de.jcup.egradle.library.access.ASTBuilderCaller", true, child);
Method method = classToLoad.getDeclaredMethod("build", String.class);
Object instance = classToLoad.newInstance();
@SuppressWarnings("unchecked") List<ASTNode> result = (List<ASTNode>) method.invoke(instance, buildscriptWrapper.toString());
completeFutureByResults(future, result);
if (future.isDone()) {
return;
}
error = new EGradleBuildScriptException("Did not found expected buildscript closure!");
} catch (InvocationTargetException | ClassNotFoundException | NoSuchMethodException | InstantiationException | IllegalAccessException e) {
error = new EGradleBuildScriptException("Reflection problems", e);
} catch (SecurityException e) {
error = new EGradleBuildScriptException("Security problems", e);
}
if (error != null) {
future.complete(new EGradleBuildscriptResult(error));
}
}
use of org.codehaus.groovy.ast.ASTNode in project micronaut-core by micronaut-projects.
the class MicronautAstBuilder method compile.
/**
* Performs the String source to {@link java.util.List} of {@link org.codehaus.groovy.ast.ASTNode}.
*
* @param script
* a Groovy script in String form
* @param compilePhase
* the int based CompilePhase to compile it to.
* @param statementsOnly
* @return {@link java.util.List} of {@link org.codehaus.groovy.ast.ASTNode}
*/
public List<ASTNode> compile(String script, CompilePhase compilePhase, boolean statementsOnly) {
final String scriptClassName = makeScriptClassName();
GroovyCodeSource codeSource = new GroovyCodeSource(script, scriptClassName + ".groovy", "/groovy/script");
codeSource.setCachable(false);
CompilationUnit cu = new CompilationUnit(CompilerConfiguration.DEFAULT, codeSource.getCodeSource(), AccessController.doPrivileged((PrivilegedAction<GroovyClassLoader>) GroovyClassLoader::new));
cu.addSource(codeSource.getName(), script);
cu.compile(compilePhase.getPhaseNumber());
// collect all the ASTNodes into the result, possibly ignoring the script body if desired
List<ASTNode> result = cu.getAST().getModules().stream().reduce(new LinkedList<>(), (acc, node) -> {
BlockStatement statementBlock = node.getStatementBlock();
if (null != statementBlock) {
acc.add(statementBlock);
}
acc.addAll(node.getClasses().stream().filter(c -> !(statementsOnly && scriptClassName.equals(c.getName()))).collect(Collectors.toList()));
return acc;
}, (o1, o2) -> o1);
return result;
}
use of org.codehaus.groovy.ast.ASTNode in project groovy-core by groovy.
the class StaticTypeCheckingVisitor method visitBinaryExpression.
@Override
public void visitBinaryExpression(BinaryExpression expression) {
BinaryExpression enclosingBinaryExpression = typeCheckingContext.getEnclosingBinaryExpression();
typeCheckingContext.pushEnclosingBinaryExpression(expression);
try {
final Expression leftExpression = expression.getLeftExpression();
final Expression rightExpression = expression.getRightExpression();
int op = expression.getOperation().getType();
leftExpression.visit(this);
SetterInfo setterInfo = removeSetterInfo(leftExpression);
if (setterInfo != null) {
if (ensureValidSetter(expression, leftExpression, rightExpression, setterInfo)) {
return;
}
} else {
rightExpression.visit(this);
}
ClassNode lType = getType(leftExpression);
ClassNode rType = getType(rightExpression);
if (isNullConstant(rightExpression)) {
if (!isPrimitiveType(lType))
// primitive types should be ignored as they will result in another failure
rType = UNKNOWN_PARAMETER_TYPE;
}
BinaryExpression reversedBinaryExpression = new BinaryExpression(rightExpression, expression.getOperation(), leftExpression);
ClassNode resultType = op == KEYWORD_IN ? getResultType(rType, op, lType, reversedBinaryExpression) : getResultType(lType, op, rType, expression);
if (op == KEYWORD_IN) {
// in case of the "in" operator, the receiver and the arguments are reversed
// so we use the reversedExpression and get the target method from it
storeTargetMethod(expression, (MethodNode) reversedBinaryExpression.getNodeMetaData(StaticTypesMarker.DIRECT_METHOD_CALL_TARGET));
} else if (op == LEFT_SQUARE_BRACKET && leftExpression instanceof VariableExpression && leftExpression.getNodeMetaData(StaticTypesMarker.INFERRED_TYPE) == null) {
storeType(leftExpression, lType);
}
if (resultType == null) {
resultType = lType;
}
// if left expression is a closure shared variable, a second pass should be done
if (leftExpression instanceof VariableExpression) {
VariableExpression leftVar = (VariableExpression) leftExpression;
if (leftVar.isClosureSharedVariable()) {
// if left expression is a closure shared variable, we should check it twice
// see GROOVY-5874
typeCheckingContext.secondPassExpressions.add(new SecondPassExpression<Void>(expression));
}
}
if (lType.isUsingGenerics() && missesGenericsTypes(resultType) && isAssignment(op)) {
// unchecked assignment
// examples:
// List<A> list = new LinkedList()
// List<A> list = []
// Iterable<A> list = new LinkedList()
// in that case, the inferred type of the binary expression is the type of the RHS
// "completed" with generics type information available in the LHS
ClassNode completedType = GenericsUtils.parameterizeType(lType, resultType.getPlainNodeReference());
resultType = completedType;
}
if (isArrayOp(op) && enclosingBinaryExpression != null && enclosingBinaryExpression.getLeftExpression() == expression && isAssignment(enclosingBinaryExpression.getOperation().getType()) && !lType.isArray()) {
// left hand side of an assignment : map['foo'] = ...
Expression enclosingBE_rightExpr = enclosingBinaryExpression.getRightExpression();
if (!(enclosingBE_rightExpr instanceof ClosureExpression)) {
enclosingBE_rightExpr.visit(this);
}
ClassNode[] arguments = { rType, getType(enclosingBE_rightExpr) };
List<MethodNode> nodes = findMethod(lType.redirect(), "putAt", arguments);
if (nodes.size() == 1) {
typeCheckMethodsWithGenericsOrFail(lType, arguments, nodes.get(0), enclosingBE_rightExpr);
} else if (nodes.isEmpty()) {
addNoMatchingMethodError(lType, "putAt", arguments, enclosingBinaryExpression);
}
}
boolean isEmptyDeclaration = expression instanceof DeclarationExpression && rightExpression instanceof EmptyExpression;
if (!isEmptyDeclaration && isAssignment(op)) {
if (rightExpression instanceof ConstructorCallExpression) {
inferDiamondType((ConstructorCallExpression) rightExpression, lType);
}
ClassNode originType = getOriginalDeclarationType(leftExpression);
typeCheckAssignment(expression, leftExpression, originType, rightExpression, resultType);
// and we must update the result type
if (!implementsInterfaceOrIsSubclassOf(getWrapper(resultType), getWrapper(originType))) {
resultType = originType;
} else if (lType.isUsingGenerics() && !lType.isEnum() && hasRHSIncompleteGenericTypeInfo(resultType)) {
// for example, LHS is List<ConcreteClass> and RHS is List<T> where T is a placeholder
resultType = lType;
}
// make sure we keep primitive types
if (isPrimitiveType(originType) && resultType.equals(getWrapper(originType))) {
resultType = originType;
}
// if we are in an if/else branch, keep track of assignment
if (typeCheckingContext.ifElseForWhileAssignmentTracker != null && leftExpression instanceof VariableExpression && !isNullConstant(rightExpression)) {
Variable accessedVariable = ((VariableExpression) leftExpression).getAccessedVariable();
if (accessedVariable instanceof VariableExpression) {
VariableExpression var = (VariableExpression) accessedVariable;
List<ClassNode> types = typeCheckingContext.ifElseForWhileAssignmentTracker.get(var);
if (types == null) {
types = new LinkedList<ClassNode>();
ClassNode type = var.getNodeMetaData(StaticTypesMarker.INFERRED_TYPE);
types.add(type);
typeCheckingContext.ifElseForWhileAssignmentTracker.put(var, types);
}
types.add(resultType);
}
}
storeType(leftExpression, resultType);
// if right expression is a ClosureExpression, store parameter type information
if (leftExpression instanceof VariableExpression) {
if (rightExpression instanceof ClosureExpression) {
Parameter[] parameters = ((ClosureExpression) rightExpression).getParameters();
leftExpression.putNodeMetaData(StaticTypesMarker.CLOSURE_ARGUMENTS, parameters);
} else if (rightExpression instanceof VariableExpression && ((VariableExpression) rightExpression).getAccessedVariable() instanceof Expression && ((Expression) ((VariableExpression) rightExpression).getAccessedVariable()).getNodeMetaData(StaticTypesMarker.CLOSURE_ARGUMENTS) != null) {
Variable targetVariable = findTargetVariable((VariableExpression) leftExpression);
if (targetVariable instanceof ASTNode) {
((ASTNode) targetVariable).putNodeMetaData(StaticTypesMarker.CLOSURE_ARGUMENTS, ((Expression) ((VariableExpression) rightExpression).getAccessedVariable()).getNodeMetaData(StaticTypesMarker.CLOSURE_ARGUMENTS));
}
}
}
} else if (op == KEYWORD_INSTANCEOF) {
pushInstanceOfTypeInfo(leftExpression, rightExpression);
}
if (!isEmptyDeclaration) {
storeType(expression, resultType);
}
} finally {
typeCheckingContext.popEnclosingBinaryExpression();
}
}
use of org.codehaus.groovy.ast.ASTNode in project groovy-core by groovy.
the class AbstractTypeCheckingExtension method makeDynamic.
/**
* Used to instruct the type checker that the call is a dynamic method call.
* Calling this method automatically sets the handled flag to true.
* @param call the method call which is a dynamic method call
* @param returnType the expected return type of the dynamic call
* @return a virtual method node with the same name as the expected call
*/
public MethodNode makeDynamic(MethodCall call, ClassNode returnType) {
TypeCheckingContext.EnclosingClosure enclosingClosure = context.getEnclosingClosure();
MethodNode enclosingMethod = context.getEnclosingMethod();
((ASTNode) call).putNodeMetaData(StaticTypesMarker.DYNAMIC_RESOLUTION, returnType);
if (enclosingClosure != null) {
enclosingClosure.getClosureExpression().putNodeMetaData(StaticTypesMarker.DYNAMIC_RESOLUTION, Boolean.TRUE);
} else {
enclosingMethod.putNodeMetaData(StaticTypesMarker.DYNAMIC_RESOLUTION, Boolean.TRUE);
}
setHandled(true);
if (debug) {
LOG.info("Turning " + call.getText() + " into a dynamic method call returning " + returnType.toString(false));
}
return new MethodNode(call.getMethodAsString(), 0, returnType, Parameter.EMPTY_ARRAY, ClassNode.EMPTY_ARRAY, EmptyStatement.INSTANCE);
}
use of org.codehaus.groovy.ast.ASTNode in project groovy-core by groovy.
the class BytecodeSequence method visit.
/**
* Delegates to the visit method used for this class.
* If the visitor is a ClassGenerator, then
* {@link ClassGenerator#visitBytecodeSequence(BytecodeSequence)}
* is called with this instance. If the visitor is no
* ClassGenerator, then this method will call visit on
* each ASTNode element sorted by this class. If one
* element is a BytecodeInstruction, then it will be skipped
* as it is no ASTNode.
*
* @param visitor the visitor
* @see ClassGenerator
*/
public void visit(GroovyCodeVisitor visitor) {
if (visitor instanceof ClassGenerator) {
ClassGenerator gen = (ClassGenerator) visitor;
gen.visitBytecodeSequence(this);
return;
}
for (Iterator iterator = instructions.iterator(); iterator.hasNext(); ) {
Object part = (Object) iterator.next();
if (part instanceof ASTNode) {
((ASTNode) part).visit(visitor);
}
}
}
Aggregations