From 368f2dd010defaf5f4b6deb70f45285cee8f244d Mon Sep 17 00:00:00 2001 From: Michael Williamson Date: Sun, 25 Oct 2015 19:18:09 +0000 Subject: Remove lombok --- .../couscous/ast/visitors/NodeVisitors.java | 32 +-- .../backends/python/PythonCodeGenerator.java | 190 +++++---------- .../couscous/backends/python/PythonCompiler.java | 43 ++-- .../couscous/backends/python/PythonSerializer.java | 80 +++---- .../backends/python/ast/PythonAssignmentNode.java | 58 ++++- .../python/ast/PythonAttributeAccessNode.java | 58 ++++- .../python/ast/PythonBooleanLiteralNode.java | 42 +++- .../backends/python/ast/PythonCallNode.java | 60 ++++- .../backends/python/ast/PythonClassNode.java | 67 +++++- .../ast/PythonConditionalExpressionNode.java | 70 +++++- .../python/ast/PythonFunctionDefinitionNode.java | 76 +++++- .../backends/python/ast/PythonGetSliceNode.java | 59 ++++- .../backends/python/ast/PythonImportAliasNode.java | 44 +++- .../backends/python/ast/PythonImportNode.java | 59 ++++- .../python/ast/PythonIntegerLiteralNode.java | 43 +++- .../backends/python/ast/PythonModuleNode.java | 48 +++- .../backends/python/ast/PythonReturnNode.java | 45 +++- .../python/ast/PythonStringLiteralNode.java | 46 +++- .../python/ast/PythonVariableReferenceNode.java | 46 +++- .../couscous/frontends/java/JavaFrontend.java | 20 +- .../couscous/frontends/java/JavaParser.java | 18 +- .../couscous/frontends/java/JavaReader.java | 263 +++++++++------------ .../interpreter/ConditionMustBeBoolean.java | 48 +++- .../zwobble/couscous/interpreter/Environment.java | 61 ++--- .../zwobble/couscous/interpreter/Evaluator.java | 59 +++-- .../org/zwobble/couscous/interpreter/Executor.java | 82 +++---- .../zwobble/couscous/interpreter/Interpreter.java | 20 +- .../zwobble/couscous/interpreter/JavaProject.java | 4 +- .../couscous/interpreter/MapBackedProject.java | 15 +- .../zwobble/couscous/interpreter/NoSuchField.java | 47 +++- .../zwobble/couscous/interpreter/NoSuchMethod.java | 48 +++- .../zwobble/couscous/interpreter/UnboundField.java | 48 +++- .../couscous/interpreter/UnboundVariable.java | 48 +++- .../couscous/interpreter/UnexpectedValueType.java | 60 ++++- .../couscous/interpreter/VariableNotInScope.java | 48 +++- .../interpreter/WrongNumberOfArguments.java | 54 ++++- .../values/BooleanInterpreterValue.java | 51 ++-- .../values/BoxedIntegerInterpreterValue.java | 4 +- .../couscous/interpreter/values/ConcreteType.java | 158 ++++--------- .../couscous/interpreter/values/FieldValue.java | 52 +++- .../values/IntegerInterpreterValue.java | 63 +++-- .../interpreter/values/MethodCallArguments.java | 24 +- .../couscous/interpreter/values/MethodValue.java | 54 ++++- .../interpreter/values/ObjectInterpreterValue.java | 20 +- .../interpreter/values/StaticMethodValue.java | 55 ++++- .../interpreter/values/StringInterpreterValue.java | 72 +++--- .../interpreter/values/UnitInterpreterValue.java | 25 +- .../org/zwobble/couscous/values/BooleanValue.java | 43 +++- .../org/zwobble/couscous/values/IntegerValue.java | 42 +++- .../org/zwobble/couscous/values/StringValue.java | 49 +++- .../zwobble/couscous/tests/BackendEvalTests.java | 33 ++- .../zwobble/couscous/tests/BackendMethodTests.java | 76 +++--- .../zwobble/couscous/tests/JavaToPythonTests.java | 46 ++-- .../backends/python/PythonCompilerEvalTests.java | 22 +- .../tests/backends/python/PythonMethodRunner.java | 65 ++--- .../backends/python/PythonSerializerTests.java | 77 +++--- .../tests/frontends/java/JavaReaderTests.java | 86 +++---- .../couscous/tests/interpreter/EvaluatorTests.java | 42 ++-- .../tests/interpreter/InterpreterMethodTests.java | 41 ++-- .../zwobble/couscous/tests/util/ExtraAsserts.java | 7 +- .../zwobble/couscous/tests/util/ExtraFiles.java | 6 +- 61 files changed, 2062 insertions(+), 1260 deletions(-) (limited to 'src') diff --git a/src/main/java/org/zwobble/couscous/ast/visitors/NodeVisitors.java b/src/main/java/org/zwobble/couscous/ast/visitors/NodeVisitors.java index bb5b054..9424e39 100644 --- a/src/main/java/org/zwobble/couscous/ast/visitors/NodeVisitors.java +++ b/src/main/java/org/zwobble/couscous/ast/visitors/NodeVisitors.java @@ -4,6 +4,7 @@ import org.zwobble.couscous.ast.AssignmentNode; import org.zwobble.couscous.ast.ClassNode; import org.zwobble.couscous.ast.ConstructorCallNode; import org.zwobble.couscous.ast.ConstructorNode; +import org.zwobble.couscous.ast.ExpressionNode; import org.zwobble.couscous.ast.ExpressionStatementNode; import org.zwobble.couscous.ast.FieldAccessNode; import org.zwobble.couscous.ast.LiteralNode; @@ -12,16 +13,15 @@ import org.zwobble.couscous.ast.MethodCallNode; import org.zwobble.couscous.ast.MethodNode; import org.zwobble.couscous.ast.Node; import org.zwobble.couscous.ast.ReturnNode; +import org.zwobble.couscous.ast.StatementNode; import org.zwobble.couscous.ast.StaticMethodCallNode; import org.zwobble.couscous.ast.TernaryConditionalNode; import org.zwobble.couscous.ast.ThisReferenceNode; import org.zwobble.couscous.ast.VariableReferenceNode; -import lombok.val; - public class NodeVisitors { public static void visitAll(Node node, NodeVisitor visitor) { - node.accept(new NodeVisitor() { + node.accept(new NodeVisitor(){ @Override public void visit(LiteralNode literal) { visitor.visit(literal); @@ -31,7 +31,7 @@ public class NodeVisitors { public void visit(VariableReferenceNode variableReference) { visitor.visit(variableReference); } - + @Override public void visit(ThisReferenceNode reference) { visitor.visit(reference); @@ -56,7 +56,7 @@ public class NodeVisitors { public void visit(MethodCallNode methodCall) { visitor.visit(methodCall); methodCall.getReceiver().accept(this); - for (val argument : methodCall.getArguments()) { + for (ExpressionNode argument : methodCall.getArguments()) { argument.accept(this); } } @@ -64,19 +64,19 @@ public class NodeVisitors { @Override public void visit(StaticMethodCallNode staticMethodCall) { visitor.visit(staticMethodCall); - for (val argument : staticMethodCall.getArguments()) { + for (ExpressionNode argument : staticMethodCall.getArguments()) { argument.accept(this); } } - + @Override public void visit(ConstructorCallNode call) { visitor.visit(call); - for (val argument : call.getArguments()) { + for (ExpressionNode argument : call.getArguments()) { argument.accept(this); } } - + @Override public void visit(FieldAccessNode fieldAccess) { visitor.visit(fieldAccess); @@ -99,29 +99,29 @@ public class NodeVisitors { visitor.visit(localVariableDeclaration); localVariableDeclaration.getInitialValue().accept(this); } - + @Override public void visit(ClassNode classNode) { visitor.visit(classNode); classNode.getConstructor().accept(this); - for (val method : classNode.getMethods()) { + for (MethodNode method : classNode.getMethods()) { method.accept(this); } } - + @Override public void visit(MethodNode methodNode) { - for (val statement : methodNode.getBody()) { + for (StatementNode statement : methodNode.getBody()) { statement.accept(this); } } - + @Override public void visit(ConstructorNode constructorNode) { - for (val statement : constructorNode.getBody()) { + for (StatementNode statement : constructorNode.getBody()) { statement.accept(this); } } }); } -} +} \ No newline at end of file diff --git a/src/main/java/org/zwobble/couscous/backends/python/PythonCodeGenerator.java b/src/main/java/org/zwobble/couscous/backends/python/PythonCodeGenerator.java index cc2b116..01e62c1 100644 --- a/src/main/java/org/zwobble/couscous/backends/python/PythonCodeGenerator.java +++ b/src/main/java/org/zwobble/couscous/backends/python/PythonCodeGenerator.java @@ -1,10 +1,10 @@ package org.zwobble.couscous.backends.python; +import java.util.Iterator; import java.util.List; import java.util.Set; import java.util.stream.Collectors; import java.util.stream.Stream; - import org.zwobble.couscous.ast.AssignmentNode; import org.zwobble.couscous.ast.ClassNode; import org.zwobble.couscous.ast.ConstructorCallNode; @@ -28,6 +28,7 @@ import org.zwobble.couscous.ast.visitors.NodeVisitorWithEmptyDefaults; import org.zwobble.couscous.ast.visitors.NodeVisitors; import org.zwobble.couscous.ast.visitors.StatementNodeMapper; import org.zwobble.couscous.backends.python.ast.PythonBlock; +import org.zwobble.couscous.backends.python.ast.PythonClassNode; import org.zwobble.couscous.backends.python.ast.PythonExpressionNode; import org.zwobble.couscous.backends.python.ast.PythonFunctionDefinitionNode; import org.zwobble.couscous.backends.python.ast.PythonImportNode; @@ -40,13 +41,11 @@ import org.zwobble.couscous.values.PrimitiveValue; import org.zwobble.couscous.values.PrimitiveValueVisitor; import org.zwobble.couscous.values.StringValue; import org.zwobble.couscous.values.UnitValue; - import com.google.common.base.Strings; import com.google.common.collect.ImmutableList; import com.google.common.collect.ImmutableSet; import com.google.common.collect.Iterables; import com.google.common.collect.Iterators; - import static com.google.common.collect.Iterators.singletonIterator; import static java.util.Arrays.asList; import static org.zwobble.couscous.backends.python.ast.PythonAssignmentNode.pythonAssignment; @@ -64,54 +63,38 @@ import static org.zwobble.couscous.backends.python.ast.PythonReturnNode.pythonRe import static org.zwobble.couscous.backends.python.ast.PythonStringLiteralNode.pythonStringLiteral; import static org.zwobble.couscous.backends.python.ast.PythonVariableReferenceNode.pythonVariableReference; -import lombok.val; - public class PythonCodeGenerator { + + public static PythonModuleNode generateCode(ClassNode classNode) { - val imports = generateImports(classNode).iterator(); - - val constructor = generateConstructor(classNode.getConstructor()); - - val pythonMethods = Iterables.transform( - classNode.getMethods(), - PythonCodeGenerator::generateFunction); - - - val pythonBody = Iterables.concat( - asList(constructor), - pythonMethods); - - val pythonClass = pythonClass( - classNode.getSimpleName(), - ImmutableList.copyOf(pythonBody)); - - return pythonModule(ImmutableList.copyOf(Iterators.concat( - imports, - singletonIterator(pythonClass)))); + Iterator imports = generateImports(classNode).iterator(); + PythonFunctionDefinitionNode constructor = generateConstructor(classNode.getConstructor()); + Iterable pythonMethods = Iterables.transform(classNode.getMethods(), PythonCodeGenerator::generateFunction); + Iterable pythonBody = Iterables.concat(asList(constructor), pythonMethods); + PythonClassNode pythonClass = pythonClass(classNode.getSimpleName(), ImmutableList.copyOf(pythonBody)); + return pythonModule(ImmutableList.copyOf(Iterators.concat(imports, singletonIterator(pythonClass)))); } - + private static Stream generateImports(ClassNode classNode) { - val classes = findReferencedClasses(classNode); - return classes.stream() - .map(name -> pythonImport( - Strings.repeat(".", packageDepth(classNode) + 1) + name.getQualifiedName(), - asList(pythonImportAlias(name.getSimpleName())))); + final java.util.Set classes = findReferencedClasses(classNode); + return classes.stream().map(name -> pythonImport(Strings.repeat(".", packageDepth(classNode) + 1) + name.getQualifiedName(), asList(pythonImportAlias(name.getSimpleName())))); } private static int packageDepth(ClassNode classNode) { int depth = 0; - val qualifiedName = classNode.getName().getQualifiedName(); + final java.lang.String qualifiedName = classNode.getName().getQualifiedName(); for (int index = 0; index < qualifiedName.length(); index++) { if (qualifiedName.charAt(index) == '.') { - depth += 1; + depth += 1; } } return depth; } private static Set findReferencedClasses(ClassNode classNode) { - val imports = ImmutableSet.builder(); - NodeVisitors.visitAll(classNode, new NodeVisitorWithEmptyDefaults() { + ImmutableSet.Builder imports = ImmutableSet.builder(); + NodeVisitors.visitAll(classNode, new NodeVisitorWithEmptyDefaults(){ + @Override public void visit(StaticMethodCallNode staticMethodCall) { imports.add(staticMethodCall.getClassName()); @@ -126,22 +109,23 @@ public class PythonCodeGenerator { } public static PythonExpressionNode generateCode(PrimitiveValue value) { - return value.accept(new PrimitiveValueVisitor() { + return value.accept(new PrimitiveValueVisitor(){ + @Override public PythonExpressionNode visit(IntegerValue value) { return pythonIntegerLiteral(value.getValue()); } - + @Override public PythonExpressionNode visit(StringValue value) { return pythonStringLiteral(value.getValue()); } - + @Override public PythonExpressionNode visit(BooleanValue value) { return pythonBooleanLiteral(value.getValue()); } - + @Override public PythonExpressionNode visit(UnitValue unitValue) { throw new UnsupportedOperationException(); @@ -149,45 +133,18 @@ public class PythonCodeGenerator { }); } - private static PythonFunctionDefinitionNode generateConstructor( - ConstructorNode constructor) { - val explicitArgumentNames = Iterables.transform( - constructor.getArguments(), - argument -> argument.getName()); - - val argumentNames = Iterables.concat( - asList("self"), - explicitArgumentNames); - - val pythonBody = constructor.getBody() - .stream() - .map(PythonCodeGenerator::generateStatement) - .collect(Collectors.toList()); - - return pythonFunctionDefinition( - "__init__", - ImmutableList.copyOf(argumentNames), - new PythonBlock(pythonBody)); + private static PythonFunctionDefinitionNode generateConstructor(ConstructorNode constructor) { + Iterable explicitArgumentNames = Iterables.transform(constructor.getArguments(), argument -> argument.getName()); + Iterable argumentNames = Iterables.concat(asList("self"), explicitArgumentNames); + List pythonBody = constructor.getBody().stream().map(PythonCodeGenerator::generateStatement).collect(Collectors.toList()); + return pythonFunctionDefinition("__init__", ImmutableList.copyOf(argumentNames), new PythonBlock(pythonBody)); } private static PythonFunctionDefinitionNode generateFunction(MethodNode method) { - val explicitArgumentNames = Iterables.transform( - method.getArguments(), - argument -> argument.getName()); - - val argumentNames = Iterables.concat( - method.isStatic() ? asList() : asList("self"), - explicitArgumentNames); - - val pythonBody = method.getBody() - .stream() - .map(PythonCodeGenerator::generateStatement) - .collect(Collectors.toList()); - - return pythonFunctionDefinition( - method.getName(), - ImmutableList.copyOf(argumentNames), - new PythonBlock(pythonBody)); + Iterable explicitArgumentNames = Iterables.transform(method.getArguments(), argument -> argument.getName()); + Iterable argumentNames = Iterables.concat(method.isStatic() ? asList() : asList("self"), explicitArgumentNames); + List pythonBody = method.getBody().stream().map(PythonCodeGenerator::generateStatement).collect(Collectors.toList()); + return pythonFunctionDefinition(method.getName(), ImmutableList.copyOf(argumentNames), new PythonBlock(pythonBody)); } private static PythonStatementNode generateStatement(StatementNode statement) { @@ -195,28 +152,26 @@ public class PythonCodeGenerator { } private static class StatementGenerator implements StatementNodeMapper { + + @Override public PythonStatementNode visit(ReturnNode returnNode) { return pythonReturn(generateExpression(returnNode.getValue())); } - + @Override public PythonStatementNode visit(ExpressionStatementNode expressionStatement) { if (expressionStatement.getExpression() instanceof AssignmentNode) { - val assignment = (AssignmentNode) expressionStatement.getExpression(); - return pythonAssignment( - assignment.getTarget().accept(EXPRESSION_GENERATOR), - generateExpression(assignment.getValue())); + final org.zwobble.couscous.ast.AssignmentNode assignment = (AssignmentNode)expressionStatement.getExpression(); + return pythonAssignment(assignment.getTarget().accept(EXPRESSION_GENERATOR), generateExpression(assignment.getValue())); } else { - throw new UnsupportedOperationException(); + throw new UnsupportedOperationException(); } } - + @Override public PythonStatementNode visit(LocalVariableDeclarationNode declaration) { - return pythonAssignment( - pythonVariableReference(declaration.getDeclaration().getName()), - generateExpression(declaration.getInitialValue())); + return pythonAssignment(pythonVariableReference(declaration.getDeclaration().getName()), generateExpression(declaration.getInitialValue())); } } @@ -225,89 +180,74 @@ public class PythonCodeGenerator { } private static List generateExpressions(Iterable expressions) { - return ImmutableList.copyOf( - Iterables.transform(expressions, PythonCodeGenerator::generateExpression)); + return ImmutableList.copyOf(Iterables.transform(expressions, PythonCodeGenerator::generateExpression)); } - private static final ExpressionGenerator EXPRESSION_GENERATOR = new ExpressionGenerator(); private static class ExpressionGenerator implements ExpressionNodeMapper { + + @Override public PythonExpressionNode visit(LiteralNode literal) { return generateCode(literal.getValue()); } - + @Override public PythonVariableReferenceNode visit(VariableReferenceNode variableReference) { return pythonVariableReference(variableReference.getReferent().getName()); } - + @Override public PythonExpressionNode visit(ThisReferenceNode reference) { return pythonVariableReference("self"); } - + @Override public PythonExpressionNode visit(AssignmentNode assignment) { throw new UnsupportedOperationException(); } - + @Override public PythonExpressionNode visit(TernaryConditionalNode ternaryConditional) { - return pythonConditionalExpression( - generateExpression(ternaryConditional.getCondition()), - generateExpression(ternaryConditional.getIfTrue()), - generateExpression(ternaryConditional.getIfFalse())); + return pythonConditionalExpression(generateExpression(ternaryConditional.getCondition()), generateExpression(ternaryConditional.getIfTrue()), generateExpression(ternaryConditional.getIfFalse())); } - + @Override public PythonExpressionNode visit(MethodCallNode methodCall) { - val receiver = generateExpression(methodCall.getReceiver()); - val arguments = generateExpressions(methodCall.getArguments()); + final org.zwobble.couscous.backends.python.ast.PythonExpressionNode receiver = generateExpression(methodCall.getReceiver()); + final java.util.List arguments = generateExpressions(methodCall.getArguments()); if (isPrimitive(methodCall.getReceiver())) { - val primitiveMethodGenerator = PrimitiveMethods.getPrimitiveMethod( - methodCall.getReceiver().getType(), - methodCall.getMethodName()).get(); + final org.zwobble.couscous.backends.python.PrimitiveMethods.PrimitiveMethodGenerator primitiveMethodGenerator = PrimitiveMethods.getPrimitiveMethod(methodCall.getReceiver().getType(), methodCall.getMethodName()).get(); return primitiveMethodGenerator.generate(receiver, arguments); } else { - return pythonCall( - pythonAttributeAccess(receiver, methodCall.getMethodName()), - arguments); + return pythonCall(pythonAttributeAccess(receiver, methodCall.getMethodName()), arguments); } } - + @Override public PythonExpressionNode visit(StaticMethodCallNode staticMethodCall) { - val className = staticMethodCall.getClassName(); - val classReference = pythonVariableReference(className.getSimpleName()); - - val methodReference = pythonAttributeAccess( - classReference, - staticMethodCall.getMethodName()); - - val arguments = generateExpressions(staticMethodCall.getArguments()); - + final org.zwobble.couscous.ast.TypeName className = staticMethodCall.getClassName(); + final org.zwobble.couscous.backends.python.ast.PythonVariableReferenceNode classReference = pythonVariableReference(className.getSimpleName()); + final org.zwobble.couscous.backends.python.ast.PythonAttributeAccessNode methodReference = pythonAttributeAccess(classReference, staticMethodCall.getMethodName()); + final java.util.List arguments = generateExpressions(staticMethodCall.getArguments()); return pythonCall(methodReference, arguments); } - + @Override public PythonExpressionNode visit(ConstructorCallNode call) { - val className = call.getType(); - val classReference = pythonVariableReference(className.getSimpleName()); - val arguments = generateExpressions(call.getArguments()); - + final org.zwobble.couscous.ast.TypeName className = call.getType(); + final org.zwobble.couscous.backends.python.ast.PythonVariableReferenceNode classReference = pythonVariableReference(className.getSimpleName()); + final java.util.List arguments = generateExpressions(call.getArguments()); return pythonCall(classReference, arguments); } - + @Override public PythonExpressionNode visit(FieldAccessNode fieldAccess) { - return pythonAttributeAccess( - generateExpression(fieldAccess.getLeft()), - fieldAccess.getFieldName()); + return pythonAttributeAccess(generateExpression(fieldAccess.getLeft()), fieldAccess.getFieldName()); } } private static boolean isPrimitive(ExpressionNode value) { return PrimitiveMethods.isPrimitive(value.getType()); } -} +} \ No newline at end of file diff --git a/src/main/java/org/zwobble/couscous/backends/python/PythonCompiler.java b/src/main/java/org/zwobble/couscous/backends/python/PythonCompiler.java index 8787d81..c5ea3e3 100644 --- a/src/main/java/org/zwobble/couscous/backends/python/PythonCompiler.java +++ b/src/main/java/org/zwobble/couscous/backends/python/PythonCompiler.java @@ -5,62 +5,55 @@ import java.io.IOException; import java.nio.file.Files; import java.nio.file.Path; import java.util.List; - import org.zwobble.couscous.ast.TypeName; import org.zwobble.couscous.ast.ClassNode; - import static java.util.Arrays.asList; import static org.zwobble.couscous.backends.python.PythonCodeGenerator.generateCode; import static org.zwobble.couscous.backends.python.PythonSerializer.serialize; -import lombok.SneakyThrows; -import lombok.val; - public class PythonCompiler { private final Path root; private final String packageName; - + public PythonCompiler(Path root, String packageName) { this.root = root; this.packageName = packageName; } public void compile(List classes) { - for (val classNode : classes) { + for (ClassNode classNode : classes) { compileClass(classNode); } - writeClass(TypeName.of("java.lang.Integer"), - "class Integer(object):\n" + - " def parseInt(value):\n" + - " return int(value)" - ); + writeClass(TypeName.of("java.lang.Integer"), "class Integer(object):\n def parseInt(value):\n return int(value)"); } - + private Path pathForClass(TypeName className) { - return root - .resolve(packageName) + return root.resolve(packageName) .resolve(className.getQualifiedName().replace(".", File.separator) + ".py"); } - + private void compileClass(ClassNode classNode) { writeClass(classNode.getName(), serialize(generateCode(classNode))); } - - @SneakyThrows + private void writeClass(TypeName name, String contents) { - val path = pathForClass(name); - Files.createDirectories(path.getParent()); - createPythonPackages(path.getParent()); - Files.write(path, asList(contents)); + try { + final java.nio.file.Path path = pathForClass(name); + Files.createDirectories(path.getParent()); + createPythonPackages(path.getParent()); + Files.write(path, asList(contents)); + } catch (final java.lang.Throwable $ex) { + throw new RuntimeException($ex); + } } - + private void createPythonPackages(Path packagePath) throws IOException { while (packagePath.startsWith(root)) { - val packageFile = packagePath.resolve("__init__.py"); + final java.nio.file.Path packageFile = packagePath.resolve("__init__.py"); if (!packageFile.toFile().exists()) { Files.createFile(packageFile); } packagePath = packagePath.getParent(); } } -} +} \ No newline at end of file diff --git a/src/main/java/org/zwobble/couscous/backends/python/PythonSerializer.java b/src/main/java/org/zwobble/couscous/backends/python/PythonSerializer.java index 249d9fa..1674e1f 100644 --- a/src/main/java/org/zwobble/couscous/backends/python/PythonSerializer.java +++ b/src/main/java/org/zwobble/couscous/backends/python/PythonSerializer.java @@ -2,7 +2,6 @@ package org.zwobble.couscous.backends.python; import java.util.List; import java.util.function.Consumer; - import org.zwobble.couscous.backends.python.ast.PythonAssignmentNode; import org.zwobble.couscous.backends.python.ast.PythonAttributeAccessNode; import org.zwobble.couscous.backends.python.ast.PythonBlock; @@ -19,19 +18,17 @@ import org.zwobble.couscous.backends.python.ast.PythonModuleNode; import org.zwobble.couscous.backends.python.ast.PythonNode; import org.zwobble.couscous.backends.python.ast.PythonPassNode; import org.zwobble.couscous.backends.python.ast.PythonReturnNode; +import org.zwobble.couscous.backends.python.ast.PythonStatementNode; import org.zwobble.couscous.backends.python.ast.PythonStringLiteralNode; import org.zwobble.couscous.backends.python.ast.PythonVariableReferenceNode; import org.zwobble.couscous.backends.python.ast.visitors.PythonNodeVisitor; import org.zwobble.couscous.util.Action; - import static com.google.common.collect.Iterables.skip; -import lombok.val; - public class PythonSerializer implements PythonNodeVisitor { public static String serialize(PythonNode node) { - val writer = new PythonWriter(); - val serializer = new PythonSerializer(writer); + PythonWriter writer = new PythonWriter(); + PythonSerializer serializer = new PythonSerializer(writer); serializer.write(node); return writer.asString(); } @@ -50,22 +47,22 @@ public class PythonSerializer implements PythonNodeVisitor { public void visit(PythonIntegerLiteralNode integerLiteral) { writer.writeInteger(integerLiteral.getValue()); } - + @Override public void visit(PythonStringLiteralNode stringLiteral) { writer.writeStringLiteral(stringLiteral.getValue()); } - + @Override public void visit(PythonBooleanLiteralNode booleanLiteral) { writer.writeKeyword(booleanLiteral.getValue() ? "True" : "False"); } - + @Override public void visit(PythonVariableReferenceNode reference) { writer.writeIdentifier(reference.getName()); } - + @Override public void visit(PythonConditionalExpressionNode conditional) { writeParenthesised(conditional.getTrueValue()); @@ -78,14 +75,14 @@ public class PythonSerializer implements PythonNodeVisitor { writer.writeSpace(); writeParenthesised(conditional.getFalseValue()); } - + @Override public void visit(PythonAttributeAccessNode attributeAccess) { writeParenthesised(attributeAccess.getLeft()); writer.writeSymbol("."); writer.writeIdentifier(attributeAccess.getAttributeName()); } - + @Override public void visit(PythonCallNode call) { writeParenthesised(call.getCallee()); @@ -96,7 +93,7 @@ public class PythonSerializer implements PythonNodeVisitor { }); writer.writeSymbol(")"); } - + @Override public void visit(PythonGetSliceNode getSlice) { writeParenthesised(getSlice.getReceiver()); @@ -106,7 +103,7 @@ public class PythonSerializer implements PythonNodeVisitor { }); writer.writeSymbol("]"); } - + @Override public void visit(PythonReturnNode pythonReturn) { writer.writeStatement(() -> { @@ -115,14 +112,14 @@ public class PythonSerializer implements PythonNodeVisitor { write(pythonReturn.getValue()); }); } - + @Override public void visit(PythonPassNode pass) { writer.writeStatement(() -> { - writer.writeKeyword("pass"); + writer.writeKeyword("pass"); }); } - + @Override public void visit(PythonClassNode pythonClass) { writer.writeStatement(() -> { @@ -135,7 +132,7 @@ public class PythonSerializer implements PythonNodeVisitor { writeBlock(pythonClass.getBody()); }); } - + @Override public void visit(PythonFunctionDefinitionNode functionDefinition) { writer.writeStatement(() -> { @@ -148,7 +145,7 @@ public class PythonSerializer implements PythonNodeVisitor { writeBlock(functionDefinition.getBody()); }); } - + @Override public void visit(PythonAssignmentNode assignment) { writer.writeStatement(() -> { @@ -157,10 +154,9 @@ public class PythonSerializer implements PythonNodeVisitor { writer.writeSymbol("="); writer.writeSpace(); write(assignment.getValue()); - }); } - + @Override public void visit(PythonImportNode importNode) { writer.writeStatement(() -> { @@ -170,38 +166,32 @@ public class PythonSerializer implements PythonNodeVisitor { writer.writeSpace(); writer.writeKeyword("import"); writer.writeSpace(); - writeWithSeparator( - importNode.getAliases(), - alias -> { - writer.writeIdentifier(alias.getName()); - }, - () -> { - writer.writeSymbol(","); - writer.writeSpace(); - }); + writeWithSeparator(importNode.getAliases(), alias -> { + writer.writeIdentifier(alias.getName()); + }, () -> { + writer.writeSymbol(","); + writer.writeSpace(); + }); }); } - + private void writeParenthesised(PythonExpressionNode expression) { writer.writeSymbol("("); write(expression); writer.writeSymbol(")"); } - + private void writeArgumentNames(PythonFunctionDefinitionNode functionDefinition) { - writeWithSeparator( - functionDefinition.getArgumentNames(), - writer::writeIdentifier, - () -> { - writer.writeSymbol(","); - writer.writeSpace(); - }); + writeWithSeparator(functionDefinition.getArgumentNames(), writer::writeIdentifier, () -> { + writer.writeSymbol(","); + writer.writeSpace(); + }); } - + private void writeWithSeparator(List values, Consumer writeValue, Action separator) { if (!values.isEmpty()) { writeValue.accept(values.get(0)); - for (val value : skip(values, 1)) { + for (T value : skip(values, 1)) { separator.run(); writeValue.accept(value); } @@ -210,16 +200,16 @@ public class PythonSerializer implements PythonNodeVisitor { @Override public void visit(PythonModuleNode module) { - for (val statement : module.getStatements()) { + for (PythonStatementNode statement : module.getStatements()) { write(statement); } } - + private void writeBlock(PythonBlock body) { writer.startBlock(); - for (val statement : body) { + for (PythonStatementNode statement : body) { write(statement); } writer.endBlock(); } -} +} \ No newline at end of file diff --git a/src/main/java/org/zwobble/couscous/backends/python/ast/PythonAssignmentNode.java b/src/main/java/org/zwobble/couscous/backends/python/ast/PythonAssignmentNode.java index 9c5b20a..37ca7b7 100644 --- a/src/main/java/org/zwobble/couscous/backends/python/ast/PythonAssignmentNode.java +++ b/src/main/java/org/zwobble/couscous/backends/python/ast/PythonAssignmentNode.java @@ -2,15 +2,59 @@ package org.zwobble.couscous.backends.python.ast; import org.zwobble.couscous.backends.python.ast.visitors.PythonNodeVisitor; -import lombok.Value; - -@Value(staticConstructor="pythonAssignment") -public class PythonAssignmentNode implements PythonStatementNode { - PythonExpressionNode target; - PythonExpressionNode value; +public final class PythonAssignmentNode implements PythonStatementNode { + private final PythonExpressionNode target; + private final PythonExpressionNode value; @Override public void accept(PythonNodeVisitor visitor) { visitor.visit(this); } -} + + private PythonAssignmentNode(final PythonExpressionNode target, final PythonExpressionNode value) { + this.target = target; + this.value = value; + } + + public static PythonAssignmentNode pythonAssignment(final PythonExpressionNode target, final PythonExpressionNode value) { + return new PythonAssignmentNode(target, value); + } + + public PythonExpressionNode getTarget() { + return this.target; + } + + public PythonExpressionNode getValue() { + return this.value; + } + + @java.lang.Override + public boolean equals(final java.lang.Object o) { + if (o == this) return true; + if (!(o instanceof PythonAssignmentNode)) return false; + final PythonAssignmentNode other = (PythonAssignmentNode)o; + final java.lang.Object this$target = this.getTarget(); + final java.lang.Object other$target = other.getTarget(); + if (this$target == null ? other$target != null : !this$target.equals(other$target)) return false; + final java.lang.Object this$value = this.getValue(); + final java.lang.Object other$value = other.getValue(); + if (this$value == null ? other$value != null : !this$value.equals(other$value)) return false; + return true; + } + + @java.lang.Override + public int hashCode() { + final int PRIME = 59; + int result = 1; + final java.lang.Object $target = this.getTarget(); + result = result * PRIME + ($target == null ? 43 : $target.hashCode()); + final java.lang.Object $value = this.getValue(); + result = result * PRIME + ($value == null ? 43 : $value.hashCode()); + return result; + } + + @java.lang.Override + public java.lang.String toString() { + return "PythonAssignmentNode(target=" + this.getTarget() + ", value=" + this.getValue() + ")"; + } +} \ No newline at end of file diff --git a/src/main/java/org/zwobble/couscous/backends/python/ast/PythonAttributeAccessNode.java b/src/main/java/org/zwobble/couscous/backends/python/ast/PythonAttributeAccessNode.java index ccd795f..bb46af3 100644 --- a/src/main/java/org/zwobble/couscous/backends/python/ast/PythonAttributeAccessNode.java +++ b/src/main/java/org/zwobble/couscous/backends/python/ast/PythonAttributeAccessNode.java @@ -2,15 +2,59 @@ package org.zwobble.couscous.backends.python.ast; import org.zwobble.couscous.backends.python.ast.visitors.PythonNodeVisitor; -import lombok.Value; - -@Value(staticConstructor="pythonAttributeAccess") -public class PythonAttributeAccessNode implements PythonExpressionNode { - PythonExpressionNode left; - String attributeName; +public final class PythonAttributeAccessNode implements PythonExpressionNode { + private final PythonExpressionNode left; + private final String attributeName; @Override public void accept(PythonNodeVisitor visitor) { visitor.visit(this); } -} + + private PythonAttributeAccessNode(final PythonExpressionNode left, final String attributeName) { + this.left = left; + this.attributeName = attributeName; + } + + public static PythonAttributeAccessNode pythonAttributeAccess(final PythonExpressionNode left, final String attributeName) { + return new PythonAttributeAccessNode(left, attributeName); + } + + public PythonExpressionNode getLeft() { + return this.left; + } + + public String getAttributeName() { + return this.attributeName; + } + + @java.lang.Override + public boolean equals(final java.lang.Object o) { + if (o == this) return true; + if (!(o instanceof PythonAttributeAccessNode)) return false; + final PythonAttributeAccessNode other = (PythonAttributeAccessNode)o; + final java.lang.Object this$left = this.getLeft(); + final java.lang.Object other$left = other.getLeft(); + if (this$left == null ? other$left != null : !this$left.equals(other$left)) return false; + final java.lang.Object this$attributeName = this.getAttributeName(); + final java.lang.Object other$attributeName = other.getAttributeName(); + if (this$attributeName == null ? other$attributeName != null : !this$attributeName.equals(other$attributeName)) return false; + return true; + } + + @java.lang.Override + public int hashCode() { + final int PRIME = 59; + int result = 1; + final java.lang.Object $left = this.getLeft(); + result = result * PRIME + ($left == null ? 43 : $left.hashCode()); + final java.lang.Object $attributeName = this.getAttributeName(); + result = result * PRIME + ($attributeName == null ? 43 : $attributeName.hashCode()); + return result; + } + + @java.lang.Override + public java.lang.String toString() { + return "PythonAttributeAccessNode(left=" + this.getLeft() + ", attributeName=" + this.getAttributeName() + ")"; + } +} \ No newline at end of file diff --git a/src/main/java/org/zwobble/couscous/backends/python/ast/PythonBooleanLiteralNode.java b/src/main/java/org/zwobble/couscous/backends/python/ast/PythonBooleanLiteralNode.java index 349ab4b..3f3d9a0 100644 --- a/src/main/java/org/zwobble/couscous/backends/python/ast/PythonBooleanLiteralNode.java +++ b/src/main/java/org/zwobble/couscous/backends/python/ast/PythonBooleanLiteralNode.java @@ -2,14 +2,8 @@ package org.zwobble.couscous.backends.python.ast; import org.zwobble.couscous.backends.python.ast.visitors.PythonNodeVisitor; -import lombok.AccessLevel; -import lombok.Getter; -import lombok.Value; - -@Value(staticConstructor="pythonBooleanLiteral") -public class PythonBooleanLiteralNode implements PythonExpressionNode { - @Getter(value = AccessLevel.NONE) - boolean value; +public final class PythonBooleanLiteralNode implements PythonExpressionNode { + private final boolean value; public boolean getValue() { return value; @@ -19,4 +13,34 @@ public class PythonBooleanLiteralNode implements PythonExpressionNode { public void accept(PythonNodeVisitor visitor) { visitor.visit(this); } -} + + private PythonBooleanLiteralNode(final boolean value) { + this.value = value; + } + + public static PythonBooleanLiteralNode pythonBooleanLiteral(final boolean value) { + return new PythonBooleanLiteralNode(value); + } + + @java.lang.Override + public boolean equals(final java.lang.Object o) { + if (o == this) return true; + if (!(o instanceof PythonBooleanLiteralNode)) return false; + final PythonBooleanLiteralNode other = (PythonBooleanLiteralNode)o; + if (this.getValue() != other.getValue()) return false; + return true; + } + + @java.lang.Override + public int hashCode() { + final int PRIME = 59; + int result = 1; + result = result * PRIME + (this.getValue() ? 79 : 97); + return result; + } + + @java.lang.Override + public java.lang.String toString() { + return "PythonBooleanLiteralNode(value=" + this.getValue() + ")"; + } +} \ No newline at end of file diff --git a/src/main/java/org/zwobble/couscous/backends/python/ast/PythonCallNode.java b/src/main/java/org/zwobble/couscous/backends/python/ast/PythonCallNode.java index 92c8b20..6cc5b11 100644 --- a/src/main/java/org/zwobble/couscous/backends/python/ast/PythonCallNode.java +++ b/src/main/java/org/zwobble/couscous/backends/python/ast/PythonCallNode.java @@ -1,19 +1,61 @@ package org.zwobble.couscous.backends.python.ast; import java.util.List; - import org.zwobble.couscous.backends.python.ast.visitors.PythonNodeVisitor; -import lombok.Value; - -@Value(staticConstructor="pythonCall") -public class PythonCallNode implements PythonExpressionNode { - PythonExpressionNode callee; - List arguments; - +public final class PythonCallNode implements PythonExpressionNode { + private final PythonExpressionNode callee; + private final List arguments; @Override public void accept(PythonNodeVisitor visitor) { visitor.visit(this); } -} + + private PythonCallNode(final PythonExpressionNode callee, final List arguments) { + this.callee = callee; + this.arguments = arguments; + } + + public static PythonCallNode pythonCall(final PythonExpressionNode callee, final List arguments) { + return new PythonCallNode(callee, arguments); + } + + public PythonExpressionNode getCallee() { + return this.callee; + } + + public List getArguments() { + return this.arguments; + } + + @java.lang.Override + public boolean equals(final java.lang.Object o) { + if (o == this) return true; + if (!(o instanceof PythonCallNode)) return false; + final PythonCallNode other = (PythonCallNode)o; + final java.lang.Object this$callee = this.getCallee(); + final java.lang.Object other$callee = other.getCallee(); + if (this$callee == null ? other$callee != null : !this$callee.equals(other$callee)) return false; + final java.lang.Object this$arguments = this.getArguments(); + final java.lang.Object other$arguments = other.getArguments(); + if (this$arguments == null ? other$arguments != null : !this$arguments.equals(other$arguments)) return false; + return true; + } + + @java.lang.Override + public int hashCode() { + final int PRIME = 59; + int result = 1; + final java.lang.Object $callee = this.getCallee(); + result = result * PRIME + ($callee == null ? 43 : $callee.hashCode()); + final java.lang.Object $arguments = this.getArguments(); + result = result * PRIME + ($arguments == null ? 43 : $arguments.hashCode()); + return result; + } + + @java.lang.Override + public java.lang.String toString() { + return "PythonCallNode(callee=" + this.getCallee() + ", arguments=" + this.getArguments() + ")"; + } +} \ No newline at end of file diff --git a/src/main/java/org/zwobble/couscous/backends/python/ast/PythonClassNode.java b/src/main/java/org/zwobble/couscous/backends/python/ast/PythonClassNode.java index 3ed7eba..8fe2ffe 100644 --- a/src/main/java/org/zwobble/couscous/backends/python/ast/PythonClassNode.java +++ b/src/main/java/org/zwobble/couscous/backends/python/ast/PythonClassNode.java @@ -1,15 +1,11 @@ package org.zwobble.couscous.backends.python.ast; import java.util.List; - import org.zwobble.couscous.backends.python.ast.visitors.PythonNodeVisitor; - import com.google.common.collect.ImmutableList; -import lombok.Value; - -@Value(staticConstructor="pythonClass") -public class PythonClassNode implements PythonStatementNode { +public final class PythonClassNode implements PythonStatementNode { + public static Builder builder(String name) { return new Builder(name); } @@ -17,7 +13,7 @@ public class PythonClassNode implements PythonStatementNode { public static class Builder { private final String name; private final ImmutableList.Builder statements; - + public Builder(String name) { this.name = name; this.statements = ImmutableList.builder(); @@ -26,7 +22,7 @@ public class PythonClassNode implements PythonStatementNode { public PythonClassNode build() { return new PythonClassNode(name, new PythonBlock(statements.build())); } - + public Builder statement(PythonStatementNode statement) { statements.add(statement); return this; @@ -36,13 +32,58 @@ public class PythonClassNode implements PythonStatementNode { public static PythonClassNode pythonClass(String name, List body) { return new PythonClassNode(name, new PythonBlock(body)); } - - String name; - PythonBlock body; + private final String name; + private final PythonBlock body; @Override public void accept(PythonNodeVisitor visitor) { visitor.visit(this); } - -} + + private PythonClassNode(final String name, final PythonBlock body) { + this.name = name; + this.body = body; + } + + public static PythonClassNode pythonClass(final String name, final PythonBlock body) { + return new PythonClassNode(name, body); + } + + public String getName() { + return this.name; + } + + public PythonBlock getBody() { + return this.body; + } + + @java.lang.Override + public boolean equals(final java.lang.Object o) { + if (o == this) return true; + if (!(o instanceof PythonClassNode)) return false; + final PythonClassNode other = (PythonClassNode)o; + final java.lang.Object this$name = this.getName(); + final java.lang.Object other$name = other.getName(); + if (this$name == null ? other$name != null : !this$name.equals(other$name)) return false; + final java.lang.Object this$body = this.getBody(); + final java.lang.Object other$body = other.getBody(); + if (this$body == null ? other$body != null : !this$body.equals(other$body)) return false; + return true; + } + + @java.lang.Override + public int hashCode() { + final int PRIME = 59; + int result = 1; + final java.lang.Object $name = this.getName(); + result = result * PRIME + ($name == null ? 43 : $name.hashCode()); + final java.lang.Object $body = this.getBody(); + result = result * PRIME + ($body == null ? 43 : $body.hashCode()); + return result; + } + + @java.lang.Override + public java.lang.String toString() { + return "PythonClassNode(name=" + this.getName() + ", body=" + this.getBody() + ")"; + } +} \ No newline at end of file diff --git a/src/main/java/org/zwobble/couscous/backends/python/ast/PythonConditionalExpressionNode.java b/src/main/java/org/zwobble/couscous/backends/python/ast/PythonConditionalExpressionNode.java index e39dce1..13f5e99 100644 --- a/src/main/java/org/zwobble/couscous/backends/python/ast/PythonConditionalExpressionNode.java +++ b/src/main/java/org/zwobble/couscous/backends/python/ast/PythonConditionalExpressionNode.java @@ -2,16 +2,70 @@ package org.zwobble.couscous.backends.python.ast; import org.zwobble.couscous.backends.python.ast.visitors.PythonNodeVisitor; -import lombok.Value; - -@Value(staticConstructor="pythonConditionalExpression") -public class PythonConditionalExpressionNode implements PythonExpressionNode { - PythonExpressionNode condition; - PythonExpressionNode trueValue; - PythonExpressionNode falseValue; +public final class PythonConditionalExpressionNode implements PythonExpressionNode { + private final PythonExpressionNode condition; + private final PythonExpressionNode trueValue; + private final PythonExpressionNode falseValue; @Override public void accept(PythonNodeVisitor visitor) { visitor.visit(this); } -} + + private PythonConditionalExpressionNode(final PythonExpressionNode condition, final PythonExpressionNode trueValue, final PythonExpressionNode falseValue) { + this.condition = condition; + this.trueValue = trueValue; + this.falseValue = falseValue; + } + + public static PythonConditionalExpressionNode pythonConditionalExpression(final PythonExpressionNode condition, final PythonExpressionNode trueValue, final PythonExpressionNode falseValue) { + return new PythonConditionalExpressionNode(condition, trueValue, falseValue); + } + + public PythonExpressionNode getCondition() { + return this.condition; + } + + public PythonExpressionNode getTrueValue() { + return this.trueValue; + } + + public PythonExpressionNode getFalseValue() { + return this.falseValue; + } + + @java.lang.Override + public boolean equals(final java.lang.Object o) { + if (o == this) return true; + if (!(o instanceof PythonConditionalExpressionNode)) return false; + final PythonConditionalExpressionNode other = (PythonConditionalExpressionNode)o; + final java.lang.Object this$condition = this.getCondition(); + final java.lang.Object other$condition = other.getCondition(); + if (this$condition == null ? other$condition != null : !this$condition.equals(other$condition)) return false; + final java.lang.Object this$trueValue = this.getTrueValue(); + final java.lang.Object other$trueValue = other.getTrueValue(); + if (this$trueValue == null ? other$trueValue != null : !this$trueValue.equals(other$trueValue)) return false; + final java.lang.Object this$falseValue = this.getFalseValue(); + final java.lang.Object other$falseValue = other.getFalseValue(); + if (this$falseValue == null ? other$falseValue != null : !this$falseValue.equals(other$falseValue)) return false; + return true; + } + + @java.lang.Override + public int hashCode() { + final int PRIME = 59; + int result = 1; + final java.lang.Object $condition = this.getCondition(); + result = result * PRIME + ($condition == null ? 43 : $condition.hashCode()); + final java.lang.Object $trueValue = this.getTrueValue(); + result = result * PRIME + ($trueValue == null ? 43 : $trueValue.hashCode()); + final java.lang.Object $falseValue = this.getFalseValue(); + result = result * PRIME + ($falseValue == null ? 43 : $falseValue.hashCode()); + return result; + } + + @java.lang.Override + public java.lang.String toString() { + return "PythonConditionalExpressionNode(condition=" + this.getCondition() + ", trueValue=" + this.getTrueValue() + ", falseValue=" + this.getFalseValue() + ")"; + } +} \ No newline at end of file diff --git a/src/main/java/org/zwobble/couscous/backends/python/ast/PythonFunctionDefinitionNode.java b/src/main/java/org/zwobble/couscous/backends/python/ast/PythonFunctionDefinitionNode.java index a7983d6..8c50ebd 100644 --- a/src/main/java/org/zwobble/couscous/backends/python/ast/PythonFunctionDefinitionNode.java +++ b/src/main/java/org/zwobble/couscous/backends/python/ast/PythonFunctionDefinitionNode.java @@ -1,15 +1,11 @@ package org.zwobble.couscous.backends.python.ast; import java.util.List; - import org.zwobble.couscous.backends.python.ast.visitors.PythonNodeVisitor; - import com.google.common.collect.ImmutableList; -import lombok.Value; - -@Value(staticConstructor="pythonFunctionDefinition") -public class PythonFunctionDefinitionNode implements PythonStatementNode { +public final class PythonFunctionDefinitionNode implements PythonStatementNode { + public static Builder builder(String name) { return new Builder(name); } @@ -24,7 +20,7 @@ public class PythonFunctionDefinitionNode implements PythonStatementNode { this.argumentNames = ImmutableList.builder(); this.body = ImmutableList.builder(); } - + public Builder argument(String argumentName) { argumentNames.add(argumentName); return this; @@ -34,13 +30,69 @@ public class PythonFunctionDefinitionNode implements PythonStatementNode { return pythonFunctionDefinition(name, argumentNames.build(), new PythonBlock(body.build())); } } - - String name; - List argumentNames; - PythonBlock body; + private final String name; + private final List argumentNames; + private final PythonBlock body; @Override public void accept(PythonNodeVisitor visitor) { visitor.visit(this); } -} + + private PythonFunctionDefinitionNode(final String name, final List argumentNames, final PythonBlock body) { + this.name = name; + this.argumentNames = argumentNames; + this.body = body; + } + + public static PythonFunctionDefinitionNode pythonFunctionDefinition(final String name, final List argumentNames, final PythonBlock body) { + return new PythonFunctionDefinitionNode(name, argumentNames, body); + } + + public String getName() { + return this.name; + } + + public List getArgumentNames() { + return this.argumentNames; + } + + public PythonBlock getBody() { + return this.body; + } + + @java.lang.Override + public boolean equals(final java.lang.Object o) { + if (o == this) return true; + if (!(o instanceof PythonFunctionDefinitionNode)) return false; + final PythonFunctionDefinitionNode other = (PythonFunctionDefinitionNode)o; + final java.lang.Object this$name = this.getName(); + final java.lang.Object other$name = other.getName(); + if (this$name == null ? other$name != null : !this$name.equals(other$name)) return false; + final java.lang.Object this$argumentNames = this.getArgumentNames(); + final java.lang.Object other$argumentNames = other.getArgumentNames(); + if (this$argumentNames == null ? other$argumentNames != null : !this$argumentNames.equals(other$argumentNames)) return false; + final java.lang.Object this$body = this.getBody(); + final java.lang.Object other$body = other.getBody(); + if (this$body == null ? other$body != null : !this$body.equals(other$body)) return false; + return true; + } + + @java.lang.Override + public int hashCode() { + final int PRIME = 59; + int result = 1; + final java.lang.Object $name = this.getName(); + result = result * PRIME + ($name == null ? 43 : $name.hashCode()); + final java.lang.Object $argumentNames = this.getArgumentNames(); + result = result * PRIME + ($argumentNames == null ? 43 : $argumentNames.hashCode()); + final java.lang.Object $body = this.getBody(); + result = result * PRIME + ($body == null ? 43 : $body.hashCode()); + return result; + } + + @java.lang.Override + public java.lang.String toString() { + return "PythonFunctionDefinitionNode(name=" + this.getName() + ", argumentNames=" + this.getArgumentNames() + ", body=" + this.getBody() + ")"; + } +} \ No newline at end of file diff --git a/src/main/java/org/zwobble/couscous/backends/python/ast/PythonGetSliceNode.java b/src/main/java/org/zwobble/couscous/backends/python/ast/PythonGetSliceNode.java index 27c191e..2298086 100644 --- a/src/main/java/org/zwobble/couscous/backends/python/ast/PythonGetSliceNode.java +++ b/src/main/java/org/zwobble/couscous/backends/python/ast/PythonGetSliceNode.java @@ -1,18 +1,61 @@ package org.zwobble.couscous.backends.python.ast; import java.util.List; - import org.zwobble.couscous.backends.python.ast.visitors.PythonNodeVisitor; -import lombok.Value; - -@Value(staticConstructor="pythonGetSlice") -public class PythonGetSliceNode implements PythonExpressionNode { - PythonExpressionNode receiver; - List arguments; +public final class PythonGetSliceNode implements PythonExpressionNode { + private final PythonExpressionNode receiver; + private final List arguments; @Override public void accept(PythonNodeVisitor visitor) { visitor.visit(this); } -} + + private PythonGetSliceNode(final PythonExpressionNode receiver, final List arguments) { + this.receiver = receiver; + this.arguments = arguments; + } + + public static PythonGetSliceNode pythonGetSlice(final PythonExpressionNode receiver, final List arguments) { + return new PythonGetSliceNode(receiver, arguments); + } + + public PythonExpressionNode getReceiver() { + return this.receiver; + } + + public List getArguments() { + return this.arguments; + } + + @java.lang.Override + public boolean equals(final java.lang.Object o) { + if (o == this) return true; + if (!(o instanceof PythonGetSliceNode)) return false; + final PythonGetSliceNode other = (PythonGetSliceNode)o; + final java.lang.Object this$receiver = this.getReceiver(); + final java.lang.Object other$receiver = other.getReceiver(); + if (this$receiver == null ? other$receiver != null : !this$receiver.equals(other$receiver)) return false; + final java.lang.Object this$arguments = this.getArguments(); + final java.lang.Object other$arguments = other.getArguments(); + if (this$arguments == null ? other$arguments != null : !this$arguments.equals(other$arguments)) return false; + return true; + } + + @java.lang.Override + public int hashCode() { + final int PRIME = 59; + int result = 1; + final java.lang.Object $receiver = this.getReceiver(); + result = result * PRIME + ($receiver == null ? 43 : $receiver.hashCode()); + final java.lang.Object $arguments = this.getArguments(); + result = result * PRIME + ($arguments == null ? 43 : $arguments.hashCode()); + return result; + } + + @java.lang.Override + public java.lang.String toString() { + return "PythonGetSliceNode(receiver=" + this.getReceiver() + ", arguments=" + this.getArguments() + ")"; + } +} \ No newline at end of file diff --git a/src/main/java/org/zwobble/couscous/backends/python/ast/PythonImportAliasNode.java b/src/main/java/org/zwobble/couscous/backends/python/ast/PythonImportAliasNode.java index 9fb531a..783eb4e 100644 --- a/src/main/java/org/zwobble/couscous/backends/python/ast/PythonImportAliasNode.java +++ b/src/main/java/org/zwobble/couscous/backends/python/ast/PythonImportAliasNode.java @@ -1,8 +1,42 @@ package org.zwobble.couscous.backends.python.ast; -import lombok.Value; +public final class PythonImportAliasNode { + private final String name; -@Value(staticConstructor="pythonImportAlias") -public class PythonImportAliasNode { - String name; -} + private PythonImportAliasNode(final String name) { + this.name = name; + } + + public static PythonImportAliasNode pythonImportAlias(final String name) { + return new PythonImportAliasNode(name); + } + + public String getName() { + return this.name; + } + + @java.lang.Override + public boolean equals(final java.lang.Object o) { + if (o == this) return true; + if (!(o instanceof PythonImportAliasNode)) return false; + final PythonImportAliasNode other = (PythonImportAliasNode)o; + final java.lang.Object this$name = this.getName(); + final java.lang.Object other$name = other.getName(); + if (this$name == null ? other$name != null : !this$name.equals(other$name)) return false; + return true; + } + + @java.lang.Override + public int hashCode() { + final int PRIME = 59; + int result = 1; + final java.lang.Object $name = this.getName(); + result = result * PRIME + ($name == null ? 43 : $name.hashCode()); + return result; + } + + @java.lang.Override + public java.lang.String toString() { + return "PythonImportAliasNode(name=" + this.getName() + ")"; + } +} \ No newline at end of file diff --git a/src/main/java/org/zwobble/couscous/backends/python/ast/PythonImportNode.java b/src/main/java/org/zwobble/couscous/backends/python/ast/PythonImportNode.java index c639829..4916cf7 100644 --- a/src/main/java/org/zwobble/couscous/backends/python/ast/PythonImportNode.java +++ b/src/main/java/org/zwobble/couscous/backends/python/ast/PythonImportNode.java @@ -1,18 +1,61 @@ package org.zwobble.couscous.backends.python.ast; import java.util.List; - import org.zwobble.couscous.backends.python.ast.visitors.PythonNodeVisitor; -import lombok.Value; - -@Value(staticConstructor="pythonImport") -public class PythonImportNode implements PythonStatementNode { - String moduleName; - List aliases; +public final class PythonImportNode implements PythonStatementNode { + private final String moduleName; + private final List aliases; @Override public void accept(PythonNodeVisitor visitor) { visitor.visit(this); } -} + + private PythonImportNode(final String moduleName, final List aliases) { + this.moduleName = moduleName; + this.aliases = aliases; + } + + public static PythonImportNode pythonImport(final String moduleName, final List aliases) { + return new PythonImportNode(moduleName, aliases); + } + + public String getModuleName() { + return this.moduleName; + } + + public List getAliases() { + return this.aliases; + } + + @java.lang.Override + public boolean equals(final java.lang.Object o) { + if (o == this) return true; + if (!(o instanceof PythonImportNode)) return false; + final PythonImportNode other = (PythonImportNode)o; + final java.lang.Object this$moduleName = this.getModuleName(); + final java.lang.Object other$moduleName = other.getModuleName(); + if (this$moduleName == null ? other$moduleName != null : !this$moduleName.equals(other$moduleName)) return false; + final java.lang.Object this$aliases = this.getAliases(); + final java.lang.Object other$aliases = other.getAliases(); + if (this$aliases == null ? other$aliases != null : !this$aliases.equals(other$aliases)) return false; + return true; + } + + @java.lang.Override + public int hashCode() { + final int PRIME = 59; + int result = 1; + final java.lang.Object $moduleName = this.getModuleName(); + result = result * PRIME + ($moduleName == null ? 43 : $moduleName.hashCode()); + final java.lang.Object $aliases = this.getAliases(); + result = result * PRIME + ($aliases == null ? 43 : $aliases.hashCode()); + return result; + } + + @java.lang.Override + public java.lang.String toString() { + return "PythonImportNode(moduleName=" + this.getModuleName() + ", aliases=" + this.getAliases() + ")"; + } +} \ No newline at end of file diff --git a/src/main/java/org/zwobble/couscous/backends/python/ast/PythonIntegerLiteralNode.java b/src/main/java/org/zwobble/couscous/backends/python/ast/PythonIntegerLiteralNode.java index 1c273d7..459ad6d 100644 --- a/src/main/java/org/zwobble/couscous/backends/python/ast/PythonIntegerLiteralNode.java +++ b/src/main/java/org/zwobble/couscous/backends/python/ast/PythonIntegerLiteralNode.java @@ -2,14 +2,45 @@ package org.zwobble.couscous.backends.python.ast; import org.zwobble.couscous.backends.python.ast.visitors.PythonNodeVisitor; -import lombok.Value; - -@Value(staticConstructor="pythonIntegerLiteral") -public class PythonIntegerLiteralNode implements PythonExpressionNode { - int value; +public final class PythonIntegerLiteralNode implements PythonExpressionNode { + private final int value; @Override public void accept(PythonNodeVisitor visitor) { visitor.visit(this); } -} + + private PythonIntegerLiteralNode(final int value) { + this.value = value; + } + + public static PythonIntegerLiteralNode pythonIntegerLiteral(final int value) { + return new PythonIntegerLiteralNode(value); + } + + public int getValue() { + return this.value; + } + + @java.lang.Override + public boolean equals(final java.lang.Object o) { + if (o == this) return true; + if (!(o instanceof PythonIntegerLiteralNode)) return false; + final PythonIntegerLiteralNode other = (PythonIntegerLiteralNode)o; + if (this.getValue() != other.getValue()) return false; + return true; + } + + @java.lang.Override + public int hashCode() { + final int PRIME = 59; + int result = 1; + result = result * PRIME + this.getValue(); + return result; + } + + @java.lang.Override + public java.lang.String toString() { + return "PythonIntegerLiteralNode(value=" + this.getValue() + ")"; + } +} \ No newline at end of file diff --git a/src/main/java/org/zwobble/couscous/backends/python/ast/PythonModuleNode.java b/src/main/java/org/zwobble/couscous/backends/python/ast/PythonModuleNode.java index b3fd728..a95b6c5 100644 --- a/src/main/java/org/zwobble/couscous/backends/python/ast/PythonModuleNode.java +++ b/src/main/java/org/zwobble/couscous/backends/python/ast/PythonModuleNode.java @@ -1,18 +1,50 @@ package org.zwobble.couscous.backends.python.ast; import java.util.List; - import org.zwobble.couscous.backends.python.ast.visitors.PythonNodeVisitor; -import lombok.Value; - -@Value(staticConstructor="pythonModule") -public class PythonModuleNode implements PythonNode { - List statements; +public final class PythonModuleNode implements PythonNode { + private final List statements; @Override public void accept(PythonNodeVisitor visitor) { visitor.visit(this); } - -} + + private PythonModuleNode(final List statements) { + this.statements = statements; + } + + public static PythonModuleNode pythonModule(final List statements) { + return new PythonModuleNode(statements); + } + + public List getStatements() { + return this.statements; + } + + @java.lang.Override + public boolean equals(final java.lang.Object o) { + if (o == this) return true; + if (!(o instanceof PythonModuleNode)) return false; + final PythonModuleNode other = (PythonModuleNode)o; + final java.lang.Object this$statements = this.getStatements(); + final java.lang.Object other$statements = other.getStatements(); + if (this$statements == null ? other$statements != null : !this$statements.equals(other$statements)) return false; + return true; + } + + @java.lang.Override + public int hashCode() { + final int PRIME = 59; + int result = 1; + final java.lang.Object $statements = this.getStatements(); + result = result * PRIME + ($statements == null ? 43 : $statements.hashCode()); + return result; + } + + @java.lang.Override + public java.lang.String toString() { + return "PythonModuleNode(statements=" + this.getStatements() + ")"; + } +} \ No newline at end of file diff --git a/src/main/java/org/zwobble/couscous/backends/python/ast/PythonReturnNode.java b/src/main/java/org/zwobble/couscous/backends/python/ast/PythonReturnNode.java index adb4168..1967dd3 100644 --- a/src/main/java/org/zwobble/couscous/backends/python/ast/PythonReturnNode.java +++ b/src/main/java/org/zwobble/couscous/backends/python/ast/PythonReturnNode.java @@ -2,15 +2,48 @@ package org.zwobble.couscous.backends.python.ast; import org.zwobble.couscous.backends.python.ast.visitors.PythonNodeVisitor; -import lombok.Value; - -@Value(staticConstructor="pythonReturn") -public class PythonReturnNode implements PythonStatementNode { - PythonExpressionNode value; +public final class PythonReturnNode implements PythonStatementNode { + private final PythonExpressionNode value; @Override public void accept(PythonNodeVisitor visitor) { visitor.visit(this); } -} + private PythonReturnNode(final PythonExpressionNode value) { + this.value = value; + } + + public static PythonReturnNode pythonReturn(final PythonExpressionNode value) { + return new PythonReturnNode(value); + } + + public PythonExpressionNode getValue() { + return this.value; + } + + @java.lang.Override + public boolean equals(final java.lang.Object o) { + if (o == this) return true; + if (!(o instanceof PythonReturnNode)) return false; + final PythonReturnNode other = (PythonReturnNode)o; + final java.lang.Object this$value = this.getValue(); + final java.lang.Object other$value = other.getValue(); + if (this$value == null ? other$value != null : !this$value.equals(other$value)) return false; + return true; + } + + @java.lang.Override + public int hashCode() { + final int PRIME = 59; + int result = 1; + final java.lang.Object $value = this.getValue(); + result = result * PRIME + ($value == null ? 43 : $value.hashCode()); + return result; + } + + @java.lang.Override + public java.lang.String toString() { + return "PythonReturnNode(value=" + this.getValue() + ")"; + } +} \ No newline at end of file diff --git a/src/main/java/org/zwobble/couscous/backends/python/ast/PythonStringLiteralNode.java b/src/main/java/org/zwobble/couscous/backends/python/ast/PythonStringLiteralNode.java index bd35621..3907555 100644 --- a/src/main/java/org/zwobble/couscous/backends/python/ast/PythonStringLiteralNode.java +++ b/src/main/java/org/zwobble/couscous/backends/python/ast/PythonStringLiteralNode.java @@ -2,14 +2,48 @@ package org.zwobble.couscous.backends.python.ast; import org.zwobble.couscous.backends.python.ast.visitors.PythonNodeVisitor; -import lombok.Value; - -@Value(staticConstructor="pythonStringLiteral") -public class PythonStringLiteralNode implements PythonExpressionNode { - String value; +public final class PythonStringLiteralNode implements PythonExpressionNode { + private final String value; @Override public void accept(PythonNodeVisitor visitor) { visitor.visit(this); } -} + + private PythonStringLiteralNode(final String value) { + this.value = value; + } + + public static PythonStringLiteralNode pythonStringLiteral(final String value) { + return new PythonStringLiteralNode(value); + } + + public String getValue() { + return this.value; + } + + @java.lang.Override + public boolean equals(final java.lang.Object o) { + if (o == this) return true; + if (!(o instanceof PythonStringLiteralNode)) return false; + final PythonStringLiteralNode other = (PythonStringLiteralNode)o; + final java.lang.Object this$value = this.getValue(); + final java.lang.Object other$value = other.getValue(); + if (this$value == null ? other$value != null : !this$value.equals(other$value)) return false; + return true; + } + + @java.lang.Override + public int hashCode() { + final int PRIME = 59; + int result = 1; + final java.lang.Object $value = this.getValue(); + result = result * PRIME + ($value == null ? 43 : $value.hashCode()); + return result; + } + + @java.lang.Override + public java.lang.String toString() { + return "PythonStringLiteralNode(value=" + this.getValue() + ")"; + } +} \ No newline at end of file diff --git a/src/main/java/org/zwobble/couscous/backends/python/ast/PythonVariableReferenceNode.java b/src/main/java/org/zwobble/couscous/backends/python/ast/PythonVariableReferenceNode.java index a67da73..4edad3e 100644 --- a/src/main/java/org/zwobble/couscous/backends/python/ast/PythonVariableReferenceNode.java +++ b/src/main/java/org/zwobble/couscous/backends/python/ast/PythonVariableReferenceNode.java @@ -2,14 +2,48 @@ package org.zwobble.couscous.backends.python.ast; import org.zwobble.couscous.backends.python.ast.visitors.PythonNodeVisitor; -import lombok.Value; - -@Value(staticConstructor="pythonVariableReference") -public class PythonVariableReferenceNode implements PythonExpressionNode { - String name; +public final class PythonVariableReferenceNode implements PythonExpressionNode { + private final String name; @Override public void accept(PythonNodeVisitor visitor) { visitor.visit(this); } -} + + private PythonVariableReferenceNode(final String name) { + this.name = name; + } + + public static PythonVariableReferenceNode pythonVariableReference(final String name) { + return new PythonVariableReferenceNode(name); + } + + public String getName() { + return this.name; + } + + @java.lang.Override + public boolean equals(final java.lang.Object o) { + if (o == this) return true; + if (!(o instanceof PythonVariableReferenceNode)) return false; + final PythonVariableReferenceNode other = (PythonVariableReferenceNode)o; + final java.lang.Object this$name = this.getName(); + final java.lang.Object other$name = other.getName(); + if (this$name == null ? other$name != null : !this$name.equals(other$name)) return false; + return true; + } + + @java.lang.Override + public int hashCode() { + final int PRIME = 59; + int result = 1; + final java.lang.Object $name = this.getName(); + result = result * PRIME + ($name == null ? 43 : $name.hashCode()); + return result; + } + + @java.lang.Override + public java.lang.String toString() { + return "PythonVariableReferenceNode(name=" + this.getName() + ")"; + } +} \ No newline at end of file diff --git a/src/main/java/org/zwobble/couscous/frontends/java/JavaFrontend.java b/src/main/java/org/zwobble/couscous/frontends/java/JavaFrontend.java index 8b92cec..d7bd54f 100644 --- a/src/main/java/org/zwobble/couscous/frontends/java/JavaFrontend.java +++ b/src/main/java/org/zwobble/couscous/frontends/java/JavaFrontend.java @@ -6,22 +6,24 @@ import java.nio.file.Path; import java.util.List; import java.util.stream.Collectors; import java.util.stream.Stream; - import org.zwobble.couscous.ast.ClassNode; -import lombok.val; - public class JavaFrontend { public static List readSourceDirectory(Path directoryPath) throws IOException { - val reader = new JavaReader(); - + JavaReader reader = new JavaReader(); return findJavaFiles(directoryPath) - .map(javaFile -> reader.readClassFromFile(directoryPath, javaFile)) + .map(javaFile -> { + // TODO: unwrap exception in outer scope + try { + return reader.readClassFromFile(directoryPath, javaFile); + } catch (Exception e) { + throw new RuntimeException(e); + } + }) .collect(Collectors.toList()); } private static Stream findJavaFiles(Path directoryPath) throws IOException { - return Files.walk(directoryPath) - .filter(path -> path.toFile().isFile() && path.toString().endsWith(".java")); + return Files.walk(directoryPath).filter(path -> path.toFile().isFile() && path.toString().endsWith(".java")); } -} +} \ No newline at end of file diff --git a/src/main/java/org/zwobble/couscous/frontends/java/JavaParser.java b/src/main/java/org/zwobble/couscous/frontends/java/JavaParser.java index d171761..0f8d963 100644 --- a/src/main/java/org/zwobble/couscous/frontends/java/JavaParser.java +++ b/src/main/java/org/zwobble/couscous/frontends/java/JavaParser.java @@ -2,18 +2,15 @@ package org.zwobble.couscous.frontends.java; import java.io.IOException; import java.nio.ByteBuffer; +import java.nio.CharBuffer; import java.nio.file.Files; import java.nio.file.Path; - import org.eclipse.jdt.core.JavaCore; import org.eclipse.jdt.core.dom.AST; import org.eclipse.jdt.core.dom.ASTParser; import org.eclipse.jdt.core.dom.CompilationUnit; - import com.google.common.base.Charsets; -import lombok.val; - public class JavaParser { private final ASTParser parser; @@ -22,20 +19,15 @@ public class JavaParser { parser.setBindingsRecovery(true); parser.setKind(ASTParser.K_COMPILATION_UNIT); parser.setCompilerOptions(JavaCore.getOptions()); - parser.setEnvironment( - new String[] {"/usr/lib/jvm/java-8-openjdk-amd64/jre/lib/rt.jar"}, - new String[0], - new String[0], - false); + parser.setEnvironment(new String[]{"/usr/lib/jvm/java-8-openjdk-amd64/jre/lib/rt.jar"}, new String[0], new String[0], false); parser.setResolveBindings(true); } public CompilationUnit parseCompilationUnit(Path root, Path sourcePath) throws IOException { parser.setUnitName("/" + root.relativize(sourcePath).toString()); - - val javaFileBytes = Files.readAllBytes(sourcePath); - val source = Charsets.UTF_8.decode(ByteBuffer.wrap(javaFileBytes)); + final byte[] javaFileBytes = Files.readAllBytes(sourcePath); + CharBuffer source = Charsets.UTF_8.decode(ByteBuffer.wrap(javaFileBytes)); parser.setSource(source.array()); return (CompilationUnit)parser.createAST(null); } -} +} \ No newline at end of file diff --git a/src/main/java/org/zwobble/couscous/frontends/java/JavaReader.java b/src/main/java/org/zwobble/couscous/frontends/java/JavaReader.java index 12c9b6e..36c6b9c 100644 --- a/src/main/java/org/zwobble/couscous/frontends/java/JavaReader.java +++ b/src/main/java/org/zwobble/couscous/frontends/java/JavaReader.java @@ -1,8 +1,8 @@ package org.zwobble.couscous.frontends.java; +import java.io.IOException; import java.nio.file.Path; import java.util.List; - import org.eclipse.jdt.core.dom.ASTNode; import org.eclipse.jdt.core.dom.Assignment; import org.eclipse.jdt.core.dom.BooleanLiteral; @@ -15,6 +15,7 @@ import org.eclipse.jdt.core.dom.FieldAccess; import org.eclipse.jdt.core.dom.FieldDeclaration; import org.eclipse.jdt.core.dom.IAnnotationBinding; import org.eclipse.jdt.core.dom.IBinding; +import org.eclipse.jdt.core.dom.IMethodBinding; import org.eclipse.jdt.core.dom.ITypeBinding; import org.eclipse.jdt.core.dom.IVariableBinding; import org.eclipse.jdt.core.dom.MethodDeclaration; @@ -47,272 +48,236 @@ import org.zwobble.couscous.ast.StaticMethodCallNode; import org.zwobble.couscous.ast.TernaryConditionalNode; import org.zwobble.couscous.ast.ThisReferenceNode; import org.zwobble.couscous.ast.TypeName; - import com.google.common.collect.Lists; - import static java.util.Arrays.asList; import static org.zwobble.couscous.ast.ExpressionStatementNode.expressionStatement; import static org.zwobble.couscous.ast.LocalVariableDeclarationNode.localVariableDeclaration; import static org.zwobble.couscous.ast.VariableDeclaration.var; import static org.zwobble.couscous.ast.VariableReferenceNode.reference; -import lombok.SneakyThrows; -import lombok.val; - public class JavaReader { + private final JavaParser parser = new JavaParser(); - @SneakyThrows - public ClassNode readClassFromFile(Path root, Path sourcePath) { - val ast = parser.parseCompilationUnit(root, sourcePath); + public ClassNode readClassFromFile(Path root, Path sourcePath) throws IOException { + CompilationUnit ast = parser.parseCompilationUnit(root, sourcePath); return readCompilationUnit(ast); } - + private static ClassNode readCompilationUnit(CompilationUnit ast) { - val name = generateClassName(ast); - - val classBuilder = new ClassNodeBuilder(name); - - val type = (TypeDeclaration)ast.types().get(0); - + String name = generateClassName(ast); + ClassNodeBuilder classBuilder = new ClassNodeBuilder(name); + TypeDeclaration type = (TypeDeclaration)ast.types().get(0); readFields(type, classBuilder); readMethods(type, classBuilder); - - return classBuilder - .build(); + return classBuilder.build(); } - + private static void readFields(TypeDeclaration type, ClassNodeBuilder classBuilder) { - for (val field : type.getFields()) { + for (FieldDeclaration field : type.getFields()) { readField(field, classBuilder); } } - + private static void readField(FieldDeclaration field, ClassNodeBuilder classBuilder) { - for (val fragment : field.fragments()) { - val name = ((VariableDeclarationFragment)fragment).getName().getIdentifier(); - classBuilder.field(name, typeOf(field.getType())); + for (Object fragment : field.fragments()) { + String name = ((VariableDeclarationFragment)fragment).getName().getIdentifier(); + classBuilder.field(name, typeOf(field.getType())); } } - + private static void readMethods(TypeDeclaration type, ClassNodeBuilder classBuilder) { - for (val method : type.getMethods()) { + for (MethodDeclaration method : type.getMethods()) { readMethod(classBuilder, method); } } - + private static void readMethod(ClassNodeBuilder classBuilder, MethodDeclaration method) { if (method.isConstructor()) { classBuilder.constructor(builder -> buildMethod(method, builder)); } else { - classBuilder.method( - method.getName().getIdentifier(), - true, - builder -> buildMethod(method, builder)); + classBuilder.method(method.getName().getIdentifier(), true, builder -> buildMethod(method, builder)); } } - - private static MethodBuilder buildMethod( - MethodDeclaration method, - MethodBuilder builder) { + + private static MethodBuilder buildMethod(MethodDeclaration method, MethodBuilder builder) { for (IAnnotationBinding annotation : method.resolveBinding().getAnnotations()) { builder.annotation(typeOf(annotation.getAnnotationType())); } for (Object parameterObject : method.parameters()) { - val parameter = (SingleVariableDeclaration)parameterObject; - builder.argument( - parameter.resolveBinding().getKey(), - parameter.getName().getIdentifier(), - typeOf(parameter.resolveBinding())); + SingleVariableDeclaration parameter = (SingleVariableDeclaration)parameterObject; + builder.argument(parameter.resolveBinding().getKey(), parameter.getName().getIdentifier(), typeOf(parameter.resolveBinding())); } for (Object statement : method.getBody().statements()) { for (StatementNode intermediateStatement : readStatement((Statement)statement)) { - builder.statement(intermediateStatement); + builder.statement(intermediateStatement); } - } return builder; } - + private static List readStatement(Statement statement) { switch (statement.getNodeType()) { - case ASTNode.RETURN_STATEMENT: - return asList(readReturnStatement((ReturnStatement)statement)); - case ASTNode.EXPRESSION_STATEMENT: - return asList(readExpressionStatement((ExpressionStatement)statement)); - case ASTNode.VARIABLE_DECLARATION_STATEMENT: - return readVariableDeclarationStatement((VariableDeclarationStatement)statement); - default: - throw new RuntimeException("Unsupported statement: " + statement.getClass()); + case ASTNode.RETURN_STATEMENT: + return asList(readReturnStatement((ReturnStatement)statement)); + + case ASTNode.EXPRESSION_STATEMENT: + return asList(readExpressionStatement((ExpressionStatement)statement)); + + case ASTNode.VARIABLE_DECLARATION_STATEMENT: + return readVariableDeclarationStatement((VariableDeclarationStatement)statement); + + default: + throw new RuntimeException("Unsupported statement: " + statement.getClass()); + } } - + private static StatementNode readReturnStatement(ReturnStatement statement) { return ReturnNode.returns(readExpression(statement.getExpression())); } - + private static StatementNode readExpressionStatement(ExpressionStatement statement) { return expressionStatement(readExpression(statement.getExpression())); } - + private static List readVariableDeclarationStatement(VariableDeclarationStatement statement) { @SuppressWarnings("unchecked") - val fragments = (List)statement.fragments(); - val type = typeOf(statement.getType()); - return Lists.transform(fragments, fragment -> - localVariableDeclaration( - fragment.resolveBinding().getKey(), - fragment.getName().getIdentifier(), - type, - readExpression(fragment.getInitializer()))); + List fragments = (List)statement.fragments(); + TypeName type = typeOf(statement.getType()); + return Lists.transform(fragments, fragment -> localVariableDeclaration(fragment.resolveBinding().getKey(), fragment.getName().getIdentifier(), type, readExpression(fragment.getInitializer()))); } - + private static ExpressionNode readExpression(Expression expression) { switch (expression.getNodeType()) { - case ASTNode.BOOLEAN_LITERAL: - return readBooleanLiteral((BooleanLiteral)expression); - case ASTNode.NUMBER_LITERAL: - return readNumberLiteral((NumberLiteral)expression); - case ASTNode.STRING_LITERAL: - return readStringLiteral((StringLiteral)expression); - case ASTNode.SIMPLE_NAME: - return readSimpleName((SimpleName)expression); - case ASTNode.THIS_EXPRESSION: - return readThisExpression((ThisExpression)expression); - case ASTNode.FIELD_ACCESS: - return readFieldAccess((FieldAccess)expression); - case ASTNode.METHOD_INVOCATION: - return readMethodInvocation((MethodInvocation)expression); - case ASTNode.CLASS_INSTANCE_CREATION: - return readClassInstanceCreation((ClassInstanceCreation)expression); - case ASTNode.CONDITIONAL_EXPRESSION: - return readConditionalExpression((ConditionalExpression)expression); - case ASTNode.ASSIGNMENT: - return readAssignment((Assignment)expression); - default: - throw new RuntimeException("Unsupported expression: " + expression.getClass()); + case ASTNode.BOOLEAN_LITERAL: + return readBooleanLiteral((BooleanLiteral)expression); + + case ASTNode.NUMBER_LITERAL: + return readNumberLiteral((NumberLiteral)expression); + + case ASTNode.STRING_LITERAL: + return readStringLiteral((StringLiteral)expression); + + case ASTNode.SIMPLE_NAME: + return readSimpleName((SimpleName)expression); + + case ASTNode.THIS_EXPRESSION: + return readThisExpression((ThisExpression)expression); + + case ASTNode.FIELD_ACCESS: + return readFieldAccess((FieldAccess)expression); + + case ASTNode.METHOD_INVOCATION: + return readMethodInvocation((MethodInvocation)expression); + + case ASTNode.CLASS_INSTANCE_CREATION: + return readClassInstanceCreation((ClassInstanceCreation)expression); + + case ASTNode.CONDITIONAL_EXPRESSION: + return readConditionalExpression((ConditionalExpression)expression); + + case ASTNode.ASSIGNMENT: + return readAssignment((Assignment)expression); + + default: + throw new RuntimeException("Unsupported expression: " + expression.getClass()); + } } - + private static ExpressionNode readBooleanLiteral(BooleanLiteral expression) { return LiteralNode.literal(expression.booleanValue()); } - + private static LiteralNode readNumberLiteral(NumberLiteral expression) { return LiteralNode.literal(Integer.parseInt(expression.getToken())); } - + private static ExpressionNode readStringLiteral(StringLiteral expression) { return LiteralNode.literal(expression.getLiteralValue()); } - + private static ExpressionNode readSimpleName(SimpleName expression) { - val binding = expression.resolveBinding(); + IBinding binding = expression.resolveBinding(); if (binding.getKind() == IBinding.VARIABLE) { return readVariableBinding((IVariableBinding)binding); } else { throw new RuntimeException("Unsupported binding: " + binding.getClass()); } } - + private static ExpressionNode readVariableBinding(IVariableBinding binding) { - val type = typeOf(binding); + TypeName type = typeOf(binding); if (binding.getDeclaringClass() == null) { - return reference(var( - binding.getKey(), - binding.getName(), - type)); + return reference(var(binding.getKey(), binding.getName(), type)); } else { - return FieldAccessNode.fieldAccess( - ThisReferenceNode.thisReference(typeOf(binding.getDeclaringClass())), - binding.getName(), - type); + return FieldAccessNode.fieldAccess(ThisReferenceNode.thisReference(typeOf(binding.getDeclaringClass())), binding.getName(), type); } } - + private static ExpressionNode readThisExpression(ThisExpression expression) { return ThisReferenceNode.thisReference(typeOf(expression)); } private static ExpressionNode readFieldAccess(FieldAccess expression) { - return FieldAccessNode.fieldAccess( - readExpression(expression.getExpression()), - expression.getName().getIdentifier(), - typeOf(expression)); + return FieldAccessNode.fieldAccess(readExpression(expression.getExpression()), expression.getName().getIdentifier(), typeOf(expression)); } - + private static ExpressionNode readMethodInvocation(MethodInvocation expression) { - val methodName = expression.getName().getIdentifier(); - val arguments = readArguments(expression.arguments()); + String methodName = expression.getName().getIdentifier(); + List arguments = readArguments(expression.arguments()); if (expression.getExpression() == null) { - val methodBinding = expression.resolveMethodBinding(); - val receiverType = typeOf(methodBinding.getDeclaringClass()); + IMethodBinding methodBinding = expression.resolveMethodBinding(); + TypeName receiverType = typeOf(methodBinding.getDeclaringClass()); if ((methodBinding.getModifiers() & Modifier.STATIC) != 0) { - return StaticMethodCallNode.staticMethodCall( - receiverType, methodName, arguments); + return StaticMethodCallNode.staticMethodCall(receiverType, methodName, arguments); } else { - return MethodCallNode.methodCall( - ThisReferenceNode.thisReference(receiverType), - methodName, - arguments, - typeOf(expression)); + return MethodCallNode.methodCall(ThisReferenceNode.thisReference(receiverType), methodName, arguments, typeOf(expression)); } } else if (expression.getExpression().getNodeType() == ASTNode.SIMPLE_NAME) { - val receiver = expression.getExpression(); + Expression receiver = expression.getExpression(); return StaticMethodCallNode.staticMethodCall(typeOf(receiver), methodName, arguments); } else { - return MethodCallNode.methodCall( - readExpression(expression.getExpression()), - methodName, - arguments, - typeOf(expression)); + return MethodCallNode.methodCall(readExpression(expression.getExpression()), methodName, arguments, typeOf(expression)); } } - + private static ExpressionNode readClassInstanceCreation(ClassInstanceCreation expression) { - return ConstructorCallNode.constructorCall( - typeOf(expression), - readArguments(expression.arguments())); + return ConstructorCallNode.constructorCall(typeOf(expression), readArguments(expression.arguments())); } - - @SuppressWarnings({ "unchecked", "rawtypes" }) + + @SuppressWarnings({"unchecked", "rawtypes"}) private static List readArguments(final List javaArguments) { - return Lists.transform( - (List)javaArguments, - JavaReader::readExpression); + return Lists.transform((List)javaArguments, JavaReader::readExpression); } - + private static ExpressionNode readConditionalExpression(ConditionalExpression expression) { - return TernaryConditionalNode.ternaryConditional( - readExpression(expression.getExpression()), - readExpression(expression.getThenExpression()), - readExpression(expression.getElseExpression())); + return TernaryConditionalNode.ternaryConditional(readExpression(expression.getExpression()), readExpression(expression.getThenExpression()), readExpression(expression.getElseExpression())); } - + private static ExpressionNode readAssignment(Assignment expression) { - return AssignmentNode.assign( - (AssignableExpressionNode)readExpression(expression.getLeftHandSide()), - readExpression(expression.getRightHandSide())); + return AssignmentNode.assign((AssignableExpressionNode)readExpression(expression.getLeftHandSide()), readExpression(expression.getRightHandSide())); } - + private static String generateClassName(CompilationUnit ast) { - val type = (TypeDeclaration)ast.types().get(0); + TypeDeclaration type = (TypeDeclaration)ast.types().get(0); return ast.getPackage().getName().getFullyQualifiedName() + "." + type.getName().getFullyQualifiedName(); } - + private static TypeName typeOf(Expression expression) { return typeOf(expression.resolveTypeBinding()); } - + private static TypeName typeOf(IVariableBinding variableBinding) { return typeOf(variableBinding.getType()); } - + private static TypeName typeOf(Type type) { return typeOf(type.resolveBinding()); } - + private static TypeName typeOf(ITypeBinding typeBinding) { return TypeName.of(typeBinding.getQualifiedName()); } -} +} \ No newline at end of file diff --git a/src/main/java/org/zwobble/couscous/interpreter/ConditionMustBeBoolean.java b/src/main/java/org/zwobble/couscous/interpreter/ConditionMustBeBoolean.java index 7f2e901..b9cf32a 100644 --- a/src/main/java/org/zwobble/couscous/interpreter/ConditionMustBeBoolean.java +++ b/src/main/java/org/zwobble/couscous/interpreter/ConditionMustBeBoolean.java @@ -2,13 +2,45 @@ package org.zwobble.couscous.interpreter; import org.zwobble.couscous.interpreter.values.InterpreterValue; -import lombok.EqualsAndHashCode; -import lombok.Value; - -@Value -@EqualsAndHashCode(callSuper=false) -public class ConditionMustBeBoolean extends InterpreterException { +public final class ConditionMustBeBoolean extends InterpreterException { private static final long serialVersionUID = 1L; + private final InterpreterValue actual; + + public ConditionMustBeBoolean(final InterpreterValue actual) { + this.actual = actual; + } + + public InterpreterValue getActual() { + return this.actual; + } + + @java.lang.Override + public java.lang.String toString() { + return "ConditionMustBeBoolean(actual=" + this.getActual() + ")"; + } + + @java.lang.Override + public boolean equals(final java.lang.Object o) { + if (o == this) return true; + if (!(o instanceof ConditionMustBeBoolean)) return false; + final ConditionMustBeBoolean other = (ConditionMustBeBoolean)o; + if (!other.canEqual((java.lang.Object)this)) return false; + final java.lang.Object this$actual = this.getActual(); + final java.lang.Object other$actual = other.getActual(); + if (this$actual == null ? other$actual != null : !this$actual.equals(other$actual)) return false; + return true; + } + + protected boolean canEqual(final java.lang.Object other) { + return other instanceof ConditionMustBeBoolean; + } - InterpreterValue actual; -} + @java.lang.Override + public int hashCode() { + final int PRIME = 59; + int result = 1; + final java.lang.Object $actual = this.getActual(); + result = result * PRIME + ($actual == null ? 43 : $actual.hashCode()); + return result; + } +} \ No newline at end of file diff --git a/src/main/java/org/zwobble/couscous/interpreter/Environment.java b/src/main/java/org/zwobble/couscous/interpreter/Environment.java index 675cfda..b1d59e2 100644 --- a/src/main/java/org/zwobble/couscous/interpreter/Environment.java +++ b/src/main/java/org/zwobble/couscous/interpreter/Environment.java @@ -2,33 +2,22 @@ package org.zwobble.couscous.interpreter; import java.util.Map; import java.util.Optional; - import org.zwobble.couscous.ast.TypeName; import org.zwobble.couscous.ast.VariableDeclaration; import org.zwobble.couscous.ast.VariableNode; import org.zwobble.couscous.interpreter.values.ConcreteType; import org.zwobble.couscous.interpreter.values.InterpreterValue; - import static java.util.stream.Collectors.toMap; -import lombok.AllArgsConstructor; -import lombok.Getter; -import lombok.Setter; -import lombok.val; - public class Environment { private final Project project; private final Optional thisValue; private final Map stackFrame; - - public Environment( - Project project, - Optional thisValue, - Map> stackFrame) { + + public Environment(Project project, Optional thisValue, Map> stackFrame) { this.project = project; this.thisValue = thisValue; - this.stackFrame = stackFrame.entrySet() - .stream() + this.stackFrame = stackFrame.entrySet().stream() .collect(toMap( entry -> entry.getKey().getId(), entry -> VariableEntry.of(entry.getKey().getType(), entry.getValue()))); @@ -37,47 +26,65 @@ public class Environment { public Optional getThis() { return thisValue; } - + public InterpreterValue get(String variableId) { checkVariableIsInScope(variableId); - val entry = stackFrame.get(variableId); + final org.zwobble.couscous.interpreter.Environment.VariableEntry entry = stackFrame.get(variableId); return entry.getValue().orElseThrow(() -> new UnboundVariable(variableId)); } - + public void put(String variableId, InterpreterValue value) { checkVariableIsInScope(variableId); checkVariableType(variableId, value); stackFrame.get(variableId).setValue(Optional.of(value)); } - + public void put(VariableNode variable, InterpreterValue value) { put(variable.getDeclaration().getId(), value); } - + public ConcreteType findClass(TypeName className) { return project.findClass(className); } - + public Environment withStackFrame(Optional thisValue, Map> stackFrame) { return new Environment(project, thisValue, stackFrame); } - + private void checkVariableIsInScope(String variableId) { if (!stackFrame.containsKey(variableId)) { throw new VariableNotInScope(variableId); } } - + private void checkVariableType(String variableId, InterpreterValue value) { - val variableType = stackFrame.get(variableId).getType(); + TypeName variableType = stackFrame.get(variableId).getType(); InterpreterTypes.checkIsInstance(variableType, value); } - @AllArgsConstructor(staticName="of") - @Getter - @Setter private static class VariableEntry { private final TypeName type; private Optional value; + + private VariableEntry(final TypeName type, final Optional value) { + this.type = type; + this.value = value; + } + + public static VariableEntry of(final TypeName type, final Optional value) { + return new VariableEntry(type, value); + } + + public TypeName getType() { + return this.type; + } + + public Optional getValue() { + return this.value; + } + + public void setValue(final Optional value) { + this.value = value; + } } -} +} \ No newline at end of file diff --git a/src/main/java/org/zwobble/couscous/interpreter/Evaluator.java b/src/main/java/org/zwobble/couscous/interpreter/Evaluator.java index 1bc1ab8..2122f01 100644 --- a/src/main/java/org/zwobble/couscous/interpreter/Evaluator.java +++ b/src/main/java/org/zwobble/couscous/interpreter/Evaluator.java @@ -2,7 +2,6 @@ package org.zwobble.couscous.interpreter; import java.util.List; import java.util.stream.Collectors; - import org.zwobble.couscous.ast.AssignmentNode; import org.zwobble.couscous.ast.ConstructorCallNode; import org.zwobble.couscous.ast.ExpressionNode; @@ -16,18 +15,17 @@ import org.zwobble.couscous.ast.VariableReferenceNode; import org.zwobble.couscous.ast.visitors.AssignableExpressionNodeVisitor; import org.zwobble.couscous.ast.visitors.ExpressionNodeMapper; import org.zwobble.couscous.interpreter.values.BooleanInterpreterValue; +import org.zwobble.couscous.interpreter.values.ConcreteType; import org.zwobble.couscous.interpreter.values.InterpreterValue; import org.zwobble.couscous.interpreter.values.InterpreterValues; -import lombok.val; - public class Evaluator implements ExpressionNodeMapper { public static InterpreterValue eval(Environment environment, ExpressionNode expression) { return new Evaluator(environment).eval(expression); } private final Environment environment; - + private Evaluator(Environment environment) { this.environment = environment; } @@ -35,29 +33,29 @@ public class Evaluator implements ExpressionNodeMapper { public InterpreterValue eval(ExpressionNode expression) { return expression.accept(this); } - + @Override public InterpreterValue visit(LiteralNode literal) { return InterpreterValues.value(literal.getValue()); } - + @Override public InterpreterValue visit(VariableReferenceNode variableReference) { return environment.get(variableReference.getReferentId()); } - + @Override public InterpreterValue visit(ThisReferenceNode reference) { return environment.getThis().get(); } - + @Override public InterpreterValue visit(AssignmentNode assignment) { - val value = eval(assignment.getValue()); - assignment.getTarget().accept(new AssignableExpressionNodeVisitor() { + InterpreterValue value = eval(assignment.getValue()); + assignment.getTarget().accept(new AssignableExpressionNodeVisitor(){ @Override public void visit(FieldAccessNode fieldAccess) { - val left = eval(fieldAccess.getLeft()); + InterpreterValue left = eval(fieldAccess.getLeft()); left.setField(fieldAccess.getFieldName(), value); } @@ -68,51 +66,48 @@ public class Evaluator implements ExpressionNodeMapper { }); return value; } - + @Override public InterpreterValue visit(TernaryConditionalNode ternaryConditional) { - val condition = eval(ternaryConditional.getCondition()); + InterpreterValue condition = eval(ternaryConditional.getCondition()); if (!(condition instanceof BooleanInterpreterValue)) { throw new ConditionMustBeBoolean(condition); } - val branch = ((BooleanInterpreterValue)condition).getValue() - ? ternaryConditional.getIfTrue() - : ternaryConditional.getIfFalse(); + final org.zwobble.couscous.ast.ExpressionNode branch = ((BooleanInterpreterValue)condition).getValue() ? ternaryConditional.getIfTrue() : ternaryConditional.getIfFalse(); return eval(branch); } - + @Override public InterpreterValue visit(MethodCallNode methodCall) { - val receiver = eval(methodCall.getReceiver()); - val type = receiver.getType(); - val arguments = evalArguments(methodCall.getArguments()); + InterpreterValue receiver = eval(methodCall.getReceiver()); + ConcreteType type = receiver.getType(); + List arguments = evalArguments(methodCall.getArguments()); return type.callMethod(environment, receiver, methodCall.getMethodName(), arguments); } - + @Override public InterpreterValue visit(StaticMethodCallNode staticMethodCall) { - val clazz = environment.findClass(staticMethodCall.getClassName()); - val arguments = evalArguments(staticMethodCall.getArguments()); + ConcreteType clazz = environment.findClass(staticMethodCall.getClassName()); + List arguments = evalArguments(staticMethodCall.getArguments()); return clazz.callStaticMethod(environment, staticMethodCall.getMethodName(), arguments); } - + @Override public InterpreterValue visit(ConstructorCallNode call) { - val clazz = environment.findClass(call.getType()); - val arguments = evalArguments(call.getArguments()); + ConcreteType clazz = environment.findClass(call.getType()); + List arguments = evalArguments(call.getArguments()); return clazz.callConstructor(environment, arguments); } - + @Override public InterpreterValue visit(FieldAccessNode fieldAccess) { - val left = eval(fieldAccess.getLeft()); + InterpreterValue left = eval(fieldAccess.getLeft()); return left.getField(fieldAccess.getFieldName()); } - + private List evalArguments(List arguments) { - return arguments - .stream() + return arguments.stream() .map(argument -> eval(argument)) .collect(Collectors.toList()); } -} +} \ No newline at end of file diff --git a/src/main/java/org/zwobble/couscous/interpreter/Executor.java b/src/main/java/org/zwobble/couscous/interpreter/Executor.java index 5c26244..e47106d 100644 --- a/src/main/java/org/zwobble/couscous/interpreter/Executor.java +++ b/src/main/java/org/zwobble/couscous/interpreter/Executor.java @@ -3,7 +3,6 @@ package org.zwobble.couscous.interpreter; import java.util.List; import java.util.Optional; import java.util.stream.Stream; - import org.zwobble.couscous.ast.CallableNode; import org.zwobble.couscous.ast.ExpressionStatementNode; import org.zwobble.couscous.ast.LocalVariableDeclarationNode; @@ -13,72 +12,55 @@ import org.zwobble.couscous.ast.VariableNode; import org.zwobble.couscous.ast.visitors.StatementNodeMapper; import org.zwobble.couscous.interpreter.values.InterpreterValue; import org.zwobble.couscous.interpreter.values.UnitInterpreterValue; - import static org.zwobble.couscous.interpreter.Evaluator.eval; -import lombok.val; - public class Executor implements StatementNodeMapper> { - public static InterpreterValue callMethod( - Environment environment, - CallableNode method, - Optional thisValue, - PositionalArguments arguments) { - - val innerEnvironment = buildEnvironment(environment, method, thisValue, arguments); - - for (val statement : method.getBody()) { - val result = exec(innerEnvironment, statement); + + public static InterpreterValue callMethod(Environment environment, CallableNode method, Optional thisValue, PositionalArguments arguments) { + final org.zwobble.couscous.interpreter.Environment innerEnvironment = buildEnvironment(environment, method, thisValue, arguments); + for (final org.zwobble.couscous.ast.StatementNode statement : method.getBody()) { + final java.util.Optional result = exec(innerEnvironment, statement); if (result.isPresent()) { return result.get(); } } return UnitInterpreterValue.UNIT; } - - private static Environment buildEnvironment( - final Environment environment, - final CallableNode method, - Optional thisValue, - PositionalArguments arguments) { - - val stackFrame = new StackFrameBuilder(); + + private static Environment buildEnvironment(final Environment environment, final CallableNode method, Optional thisValue, PositionalArguments arguments) { + final org.zwobble.couscous.interpreter.StackFrameBuilder stackFrame = new StackFrameBuilder(); for (int index = 0; index < method.getArguments().size(); index++) { stackFrame.declare(method.getArguments().get(index), arguments.get(index)); } - - findDeclarations(method.getBody()).forEach(declaration -> - stackFrame.declare(declaration)); - + findDeclarations(method.getBody()).forEach(declaration -> stackFrame.declare(declaration)); return environment.withStackFrame(thisValue, stackFrame.build()); } private static Stream findDeclarations(List body) { - return body.stream() - .flatMap(statement -> statement.accept(new StatementNodeMapper>() { - @Override - public Stream visit(ReturnNode returnNode) { - return Stream.empty(); - } - - @Override - public Stream visit(ExpressionStatementNode expressionStatement) { - return Stream.empty(); - } - - @Override - public Stream visit(LocalVariableDeclarationNode localVariableDeclaration) { - return Stream.of(localVariableDeclaration); - } - })); + return body.stream().flatMap(statement -> statement.accept(new StatementNodeMapper>(){ + + @Override + public Stream visit(ReturnNode returnNode) { + return Stream.empty(); + } + + @Override + public Stream visit(ExpressionStatementNode expressionStatement) { + return Stream.empty(); + } + + @Override + public Stream visit(LocalVariableDeclarationNode localVariableDeclaration) { + return Stream.of(localVariableDeclaration); + } + })); } - + public static Optional exec(Environment environment, StatementNode statement) { return statement.accept(new Executor(environment)); } - private final Environment environment; - + private Executor(Environment environment) { this.environment = environment; } @@ -87,17 +69,17 @@ public class Executor implements StatementNodeMapper> public Optional visit(ReturnNode returnNode) { return Optional.of(eval(environment, returnNode.getValue())); } - + @Override public Optional visit(ExpressionStatementNode expressionStatement) { eval(environment, expressionStatement.getExpression()); return Optional.empty(); } - + @Override public Optional visit(LocalVariableDeclarationNode localVariableDeclaration) { - val value = eval(environment, localVariableDeclaration.getInitialValue()); + final org.zwobble.couscous.interpreter.values.InterpreterValue value = eval(environment, localVariableDeclaration.getInitialValue()); environment.put(localVariableDeclaration, value); return Optional.empty(); } -} +} \ No newline at end of file diff --git a/src/main/java/org/zwobble/couscous/interpreter/Interpreter.java b/src/main/java/org/zwobble/couscous/interpreter/Interpreter.java index 0506a59..e5f6482 100644 --- a/src/main/java/org/zwobble/couscous/interpreter/Interpreter.java +++ b/src/main/java/org/zwobble/couscous/interpreter/Interpreter.java @@ -3,32 +3,30 @@ package org.zwobble.couscous.interpreter; import java.util.List; import java.util.Optional; import java.util.stream.Collectors; - import org.zwobble.couscous.ast.TypeName; import org.zwobble.couscous.ast.ExpressionNode; import org.zwobble.couscous.interpreter.values.InterpreterValue; - import com.google.common.collect.ImmutableMap; - import static org.zwobble.couscous.ast.LiteralNode.literal; import static org.zwobble.couscous.ast.StaticMethodCallNode.staticMethodCall; import static org.zwobble.couscous.interpreter.Evaluator.eval; -import lombok.val; - public class Interpreter { private Project project; - + public Interpreter(Project project) { this.project = project; } public InterpreterValue run(TypeName className, String methodName, List arguments) { - val argumentExpressions = arguments - .stream() - .map(argument -> literal(argument.toPrimitiveValue().get())) + List argumentExpressions = arguments.stream() + .map(argument -> literal(argument.toPrimitiveValue().get())) .collect(Collectors.toList()); - return eval(new Environment(project, Optional.empty(), ImmutableMap.of()), + return eval( + new Environment( + project, + Optional.empty(), + ImmutableMap.of()), staticMethodCall(className, methodName, argumentExpressions)); } -} +} \ No newline at end of file diff --git a/src/main/java/org/zwobble/couscous/interpreter/JavaProject.java b/src/main/java/org/zwobble/couscous/interpreter/JavaProject.java index fd01053..e6b6df1 100644 --- a/src/main/java/org/zwobble/couscous/interpreter/JavaProject.java +++ b/src/main/java/org/zwobble/couscous/interpreter/JavaProject.java @@ -8,8 +8,6 @@ import org.zwobble.couscous.interpreter.values.ConcreteType; import com.google.common.collect.Iterables; -import lombok.val; - public class JavaProject { public static MapBackedProject.Builder builder() { return MapBackedProject.builder() @@ -17,7 +15,7 @@ public class JavaProject { } public static Project of(List classNodes) { - val concreteTypes = Iterables.transform(classNodes, ConcreteType::fromNode); + Iterable concreteTypes = Iterables.transform(classNodes, ConcreteType::fromNode); return builder() .addClasses(concreteTypes) .build(); diff --git a/src/main/java/org/zwobble/couscous/interpreter/MapBackedProject.java b/src/main/java/org/zwobble/couscous/interpreter/MapBackedProject.java index 7206b1a..7f16b8f 100644 --- a/src/main/java/org/zwobble/couscous/interpreter/MapBackedProject.java +++ b/src/main/java/org/zwobble/couscous/interpreter/MapBackedProject.java @@ -1,15 +1,12 @@ package org.zwobble.couscous.interpreter; import java.util.Map; - import org.zwobble.couscous.ast.TypeName; import org.zwobble.couscous.interpreter.values.ConcreteType; - import com.google.common.collect.ImmutableMap; -import lombok.val; - public class MapBackedProject implements Project { + public static Builder builder() { return new Builder(); } @@ -27,7 +24,7 @@ public class MapBackedProject implements Project { } public Builder addClasses(Iterable classes) { - for (val clazz : classes) { + for (ConcreteType clazz : classes) { addClass(clazz); } return this; @@ -37,9 +34,8 @@ public class MapBackedProject implements Project { return new MapBackedProject(classes.build()); } } - private Map classes; - + public MapBackedProject(Map classes) { this.classes = classes; } @@ -47,10 +43,9 @@ public class MapBackedProject implements Project { @Override public ConcreteType findClass(TypeName name) { if (classes.containsKey(name)) { - return classes.get(name); + return classes.get(name); } else { throw new IllegalArgumentException("Cannot find class: " + name); } - } -} +} \ No newline at end of file diff --git a/src/main/java/org/zwobble/couscous/interpreter/NoSuchField.java b/src/main/java/org/zwobble/couscous/interpreter/NoSuchField.java index 31feaab..03b714f 100644 --- a/src/main/java/org/zwobble/couscous/interpreter/NoSuchField.java +++ b/src/main/java/org/zwobble/couscous/interpreter/NoSuchField.java @@ -1,12 +1,43 @@ package org.zwobble.couscous.interpreter; -import lombok.EqualsAndHashCode; -import lombok.Value; - -@Value -@EqualsAndHashCode(callSuper=false) -public class NoSuchField extends InterpreterException { +public final class NoSuchField extends InterpreterException { private static final long serialVersionUID = 1L; + private final String fieldName; + + public NoSuchField(final String fieldName) { + this.fieldName = fieldName; + } + + public String getFieldName() { + return this.fieldName; + } + + public java.lang.String toString() { + return "NoSuchField(fieldName=" + this.getFieldName() + ")"; + } + + @java.lang.Override + public boolean equals(final java.lang.Object o) { + if (o == this) return true; + if (!(o instanceof NoSuchField)) return false; + final NoSuchField other = (NoSuchField)o; + if (!other.canEqual((java.lang.Object)this)) return false; + final java.lang.Object this$fieldName = this.getFieldName(); + final java.lang.Object other$fieldName = other.getFieldName(); + if (this$fieldName == null ? other$fieldName != null : !this$fieldName.equals(other$fieldName)) return false; + return true; + } + + protected boolean canEqual(final java.lang.Object other) { + return other instanceof NoSuchField; + } - String fieldName; -} + @java.lang.Override + public int hashCode() { + final int PRIME = 59; + int result = 1; + final java.lang.Object $fieldName = this.getFieldName(); + result = result * PRIME + ($fieldName == null ? 43 : $fieldName.hashCode()); + return result; + } +} \ No newline at end of file diff --git a/src/main/java/org/zwobble/couscous/interpreter/NoSuchMethod.java b/src/main/java/org/zwobble/couscous/interpreter/NoSuchMethod.java index e69c978..ddddd71 100644 --- a/src/main/java/org/zwobble/couscous/interpreter/NoSuchMethod.java +++ b/src/main/java/org/zwobble/couscous/interpreter/NoSuchMethod.java @@ -1,12 +1,44 @@ package org.zwobble.couscous.interpreter; -import lombok.EqualsAndHashCode; -import lombok.Value; - -@Value -@EqualsAndHashCode(callSuper=false) -public class NoSuchMethod extends InterpreterException { +public final class NoSuchMethod extends InterpreterException { private static final long serialVersionUID = 1L; + private final String methodName; + + public NoSuchMethod(final String methodName) { + this.methodName = methodName; + } + + public String getMethodName() { + return this.methodName; + } + + @java.lang.Override + public java.lang.String toString() { + return "NoSuchMethod(methodName=" + this.getMethodName() + ")"; + } + + @java.lang.Override + public boolean equals(final java.lang.Object o) { + if (o == this) return true; + if (!(o instanceof NoSuchMethod)) return false; + final NoSuchMethod other = (NoSuchMethod)o; + if (!other.canEqual((java.lang.Object)this)) return false; + final java.lang.Object this$methodName = this.getMethodName(); + final java.lang.Object other$methodName = other.getMethodName(); + if (this$methodName == null ? other$methodName != null : !this$methodName.equals(other$methodName)) return false; + return true; + } + + protected boolean canEqual(final java.lang.Object other) { + return other instanceof NoSuchMethod; + } - String methodName; -} + @java.lang.Override + public int hashCode() { + final int PRIME = 59; + int result = 1; + final java.lang.Object $methodName = this.getMethodName(); + result = result * PRIME + ($methodName == null ? 43 : $methodName.hashCode()); + return result; + } +} \ No newline at end of file diff --git a/src/main/java/org/zwobble/couscous/interpreter/UnboundField.java b/src/main/java/org/zwobble/couscous/interpreter/UnboundField.java index 2efca06..1d21071 100644 --- a/src/main/java/org/zwobble/couscous/interpreter/UnboundField.java +++ b/src/main/java/org/zwobble/couscous/interpreter/UnboundField.java @@ -1,12 +1,44 @@ package org.zwobble.couscous.interpreter; -import lombok.EqualsAndHashCode; -import lombok.Value; - -@Value -@EqualsAndHashCode(callSuper=false) -public class UnboundField extends InterpreterException { +public final class UnboundField extends InterpreterException { private static final long serialVersionUID = 1L; + private final String fieldName; + + public UnboundField(final String fieldName) { + this.fieldName = fieldName; + } + + public String getFieldName() { + return this.fieldName; + } + + @java.lang.Override + public java.lang.String toString() { + return "UnboundField(fieldName=" + this.getFieldName() + ")"; + } + + @java.lang.Override + public boolean equals(final java.lang.Object o) { + if (o == this) return true; + if (!(o instanceof UnboundField)) return false; + final UnboundField other = (UnboundField)o; + if (!other.canEqual((java.lang.Object)this)) return false; + final java.lang.Object this$fieldName = this.getFieldName(); + final java.lang.Object other$fieldName = other.getFieldName(); + if (this$fieldName == null ? other$fieldName != null : !this$fieldName.equals(other$fieldName)) return false; + return true; + } + + protected boolean canEqual(final java.lang.Object other) { + return other instanceof UnboundField; + } - String fieldName; -} + @java.lang.Override + public int hashCode() { + final int PRIME = 59; + int result = 1; + final java.lang.Object $fieldName = this.getFieldName(); + result = result * PRIME + ($fieldName == null ? 43 : $fieldName.hashCode()); + return result; + } +} \ No newline at end of file diff --git a/src/main/java/org/zwobble/couscous/interpreter/UnboundVariable.java b/src/main/java/org/zwobble/couscous/interpreter/UnboundVariable.java index 684a3b9..e0131f0 100644 --- a/src/main/java/org/zwobble/couscous/interpreter/UnboundVariable.java +++ b/src/main/java/org/zwobble/couscous/interpreter/UnboundVariable.java @@ -1,12 +1,44 @@ package org.zwobble.couscous.interpreter; -import lombok.EqualsAndHashCode; -import lombok.Value; - -@Value -@EqualsAndHashCode(callSuper=false) -public class UnboundVariable extends InterpreterException { +public final class UnboundVariable extends InterpreterException { private static final long serialVersionUID = 1L; + private final String variableId; + + public UnboundVariable(final String variableId) { + this.variableId = variableId; + } + + public String getVariableId() { + return this.variableId; + } + + @java.lang.Override + public java.lang.String toString() { + return "UnboundVariable(variableId=" + this.getVariableId() + ")"; + } + + @java.lang.Override + public boolean equals(final java.lang.Object o) { + if (o == this) return true; + if (!(o instanceof UnboundVariable)) return false; + final UnboundVariable other = (UnboundVariable)o; + if (!other.canEqual((java.lang.Object)this)) return false; + final java.lang.Object this$variableId = this.getVariableId(); + final java.lang.Object other$variableId = other.getVariableId(); + if (this$variableId == null ? other$variableId != null : !this$variableId.equals(other$variableId)) return false; + return true; + } + + protected boolean canEqual(final java.lang.Object other) { + return other instanceof UnboundVariable; + } - String variableId; -} + @java.lang.Override + public int hashCode() { + final int PRIME = 59; + int result = 1; + final java.lang.Object $variableId = this.getVariableId(); + result = result * PRIME + ($variableId == null ? 43 : $variableId.hashCode()); + return result; + } +} \ No newline at end of file diff --git a/src/main/java/org/zwobble/couscous/interpreter/UnexpectedValueType.java b/src/main/java/org/zwobble/couscous/interpreter/UnexpectedValueType.java index 827b9e9..2b40728 100644 --- a/src/main/java/org/zwobble/couscous/interpreter/UnexpectedValueType.java +++ b/src/main/java/org/zwobble/couscous/interpreter/UnexpectedValueType.java @@ -2,14 +2,56 @@ package org.zwobble.couscous.interpreter; import org.zwobble.couscous.ast.TypeName; -import lombok.EqualsAndHashCode; -import lombok.Value; - -@Value -@EqualsAndHashCode(callSuper=false) -public class UnexpectedValueType extends InterpreterException { +public final class UnexpectedValueType extends InterpreterException { private static final long serialVersionUID = 1L; + private final TypeName expected; + private final TypeName actual; + + public UnexpectedValueType(final TypeName expected, final TypeName actual) { + this.expected = expected; + this.actual = actual; + } + + public TypeName getExpected() { + return this.expected; + } + + public TypeName getActual() { + return this.actual; + } + + @java.lang.Override + public java.lang.String toString() { + return "UnexpectedValueType(expected=" + this.getExpected() + ", actual=" + this.getActual() + ")"; + } + + @java.lang.Override + public boolean equals(final java.lang.Object o) { + if (o == this) return true; + if (!(o instanceof UnexpectedValueType)) return false; + final UnexpectedValueType other = (UnexpectedValueType)o; + if (!other.canEqual((java.lang.Object)this)) return false; + final java.lang.Object this$expected = this.getExpected(); + final java.lang.Object other$expected = other.getExpected(); + if (this$expected == null ? other$expected != null : !this$expected.equals(other$expected)) return false; + final java.lang.Object this$actual = this.getActual(); + final java.lang.Object other$actual = other.getActual(); + if (this$actual == null ? other$actual != null : !this$actual.equals(other$actual)) return false; + return true; + } + + protected boolean canEqual(final java.lang.Object other) { + return other instanceof UnexpectedValueType; + } - TypeName expected; - TypeName actual; -} + @java.lang.Override + public int hashCode() { + final int PRIME = 59; + int result = 1; + final java.lang.Object $expected = this.getExpected(); + result = result * PRIME + ($expected == null ? 43 : $expected.hashCode()); + final java.lang.Object $actual = this.getActual(); + result = result * PRIME + ($actual == null ? 43 : $actual.hashCode()); + return result; + } +} \ No newline at end of file diff --git a/src/main/java/org/zwobble/couscous/interpreter/VariableNotInScope.java b/src/main/java/org/zwobble/couscous/interpreter/VariableNotInScope.java index 17ab6af..54b66bd 100644 --- a/src/main/java/org/zwobble/couscous/interpreter/VariableNotInScope.java +++ b/src/main/java/org/zwobble/couscous/interpreter/VariableNotInScope.java @@ -1,12 +1,44 @@ package org.zwobble.couscous.interpreter; -import lombok.EqualsAndHashCode; -import lombok.Value; - -@Value -@EqualsAndHashCode(callSuper=false) -public class VariableNotInScope extends InterpreterException { +public final class VariableNotInScope extends InterpreterException { private static final long serialVersionUID = 1L; + private final String variableId; + + public VariableNotInScope(final String variableId) { + this.variableId = variableId; + } + + public String getVariableId() { + return this.variableId; + } + + @java.lang.Override + public java.lang.String toString() { + return "VariableNotInScope(variableId=" + this.getVariableId() + ")"; + } + + @java.lang.Override + public boolean equals(final java.lang.Object o) { + if (o == this) return true; + if (!(o instanceof VariableNotInScope)) return false; + final VariableNotInScope other = (VariableNotInScope)o; + if (!other.canEqual((java.lang.Object)this)) return false; + final java.lang.Object this$variableId = this.getVariableId(); + final java.lang.Object other$variableId = other.getVariableId(); + if (this$variableId == null ? other$variableId != null : !this$variableId.equals(other$variableId)) return false; + return true; + } + + protected boolean canEqual(final java.lang.Object other) { + return other instanceof VariableNotInScope; + } - String variableId; -} + @java.lang.Override + public int hashCode() { + final int PRIME = 59; + int result = 1; + final java.lang.Object $variableId = this.getVariableId(); + result = result * PRIME + ($variableId == null ? 43 : $variableId.hashCode()); + return result; + } +} \ No newline at end of file diff --git a/src/main/java/org/zwobble/couscous/interpreter/WrongNumberOfArguments.java b/src/main/java/org/zwobble/couscous/interpreter/WrongNumberOfArguments.java index 06d8079..800aabb 100644 --- a/src/main/java/org/zwobble/couscous/interpreter/WrongNumberOfArguments.java +++ b/src/main/java/org/zwobble/couscous/interpreter/WrongNumberOfArguments.java @@ -1,13 +1,49 @@ package org.zwobble.couscous.interpreter; -import lombok.EqualsAndHashCode; -import lombok.Value; - -@Value -@EqualsAndHashCode(callSuper=false) -public class WrongNumberOfArguments extends InterpreterException { +public final class WrongNumberOfArguments extends InterpreterException { private static final long serialVersionUID = 1L; + private final int expected; + private final int actual; + + public WrongNumberOfArguments(final int expected, final int actual) { + this.expected = expected; + this.actual = actual; + } + + public int getExpected() { + return this.expected; + } + + public int getActual() { + return this.actual; + } + + @java.lang.Override + public java.lang.String toString() { + return "WrongNumberOfArguments(expected=" + this.getExpected() + ", actual=" + this.getActual() + ")"; + } + + @java.lang.Override + public boolean equals(final java.lang.Object o) { + if (o == this) return true; + if (!(o instanceof WrongNumberOfArguments)) return false; + final WrongNumberOfArguments other = (WrongNumberOfArguments)o; + if (!other.canEqual((java.lang.Object)this)) return false; + if (this.getExpected() != other.getExpected()) return false; + if (this.getActual() != other.getActual()) return false; + return true; + } + + protected boolean canEqual(final java.lang.Object other) { + return other instanceof WrongNumberOfArguments; + } - int expected; - int actual; -} + @java.lang.Override + public int hashCode() { + final int PRIME = 59; + int result = 1; + result = result * PRIME + this.getExpected(); + result = result * PRIME + this.getActual(); + return result; + } +} \ No newline at end of file diff --git a/src/main/java/org/zwobble/couscous/interpreter/values/BooleanInterpreterValue.java b/src/main/java/org/zwobble/couscous/interpreter/values/BooleanInterpreterValue.java index 7bb108c..8245f87 100644 --- a/src/main/java/org/zwobble/couscous/interpreter/values/BooleanInterpreterValue.java +++ b/src/main/java/org/zwobble/couscous/interpreter/values/BooleanInterpreterValue.java @@ -1,44 +1,61 @@ package org.zwobble.couscous.interpreter.values; import java.util.Optional; - import org.zwobble.couscous.interpreter.NoSuchField; import org.zwobble.couscous.values.PrimitiveValue; import org.zwobble.couscous.values.PrimitiveValues; -import lombok.AccessLevel; -import lombok.Getter; -import lombok.Value; - -@Value -public class BooleanInterpreterValue implements InterpreterValue { - private static final ConcreteType TYPE = ConcreteType.builder(BooleanInterpreterValue.class, "Boolean") - .build(); +public final class BooleanInterpreterValue implements InterpreterValue { + private static final ConcreteType TYPE = ConcreteType.builder(BooleanInterpreterValue.class, "Boolean").build(); + private final boolean value; - @Getter(value = AccessLevel.NONE) - boolean value; - public boolean getValue() { return value; } - + @Override public ConcreteType getType() { return TYPE; } - + @Override public Optional toPrimitiveValue() { return Optional.of(PrimitiveValues.value(value)); } - + @Override public InterpreterValue getField(String fieldName) { throw new NoSuchField(fieldName); } - + @Override public void setField(String fieldName, InterpreterValue value) { throw new NoSuchField(fieldName); } -} + + public BooleanInterpreterValue(final boolean value) { + this.value = value; + } + + @java.lang.Override + public boolean equals(final java.lang.Object o) { + if (o == this) return true; + if (!(o instanceof BooleanInterpreterValue)) return false; + final BooleanInterpreterValue other = (BooleanInterpreterValue)o; + if (this.getValue() != other.getValue()) return false; + return true; + } + + @java.lang.Override + public int hashCode() { + final int PRIME = 59; + int result = 1; + result = result * PRIME + (this.getValue() ? 79 : 97); + return result; + } + + @java.lang.Override + public java.lang.String toString() { + return "BooleanInterpreterValue(value=" + this.getValue() + ")"; + } +} \ No newline at end of file diff --git a/src/main/java/org/zwobble/couscous/interpreter/values/BoxedIntegerInterpreterValue.java b/src/main/java/org/zwobble/couscous/interpreter/values/BoxedIntegerInterpreterValue.java index a6ba5e1..458eca7 100644 --- a/src/main/java/org/zwobble/couscous/interpreter/values/BoxedIntegerInterpreterValue.java +++ b/src/main/java/org/zwobble/couscous/interpreter/values/BoxedIntegerInterpreterValue.java @@ -4,13 +4,11 @@ import org.zwobble.couscous.values.StringValue; import static java.util.Arrays.asList; -import lombok.val; - public class BoxedIntegerInterpreterValue { public static final ConcreteType TYPE = ConcreteType.classBuilder("java.lang.Integer") .staticMethod("parseInt", asList(StringValue.REF), (environment, arguments) -> { - val value = (StringInterpreterValue)arguments.get(0); + StringInterpreterValue value = (StringInterpreterValue)arguments.get(0); return new IntegerInterpreterValue(Integer.parseInt(value.getValue())); }) diff --git a/src/main/java/org/zwobble/couscous/interpreter/values/ConcreteType.java b/src/main/java/org/zwobble/couscous/interpreter/values/ConcreteType.java index 2c64031..a61ec27 100644 --- a/src/main/java/org/zwobble/couscous/interpreter/values/ConcreteType.java +++ b/src/main/java/org/zwobble/couscous/interpreter/values/ConcreteType.java @@ -5,7 +5,6 @@ import java.util.Map; import java.util.Optional; import java.util.function.BiFunction; import java.util.stream.Collectors; - import org.zwobble.couscous.ast.ClassNode; import org.zwobble.couscous.ast.FormalArgumentNode; import org.zwobble.couscous.ast.TypeName; @@ -16,32 +15,27 @@ import org.zwobble.couscous.interpreter.NoSuchMethod; import org.zwobble.couscous.interpreter.PositionalArguments; import org.zwobble.couscous.interpreter.WrongNumberOfArguments; import org.zwobble.couscous.util.Casts; - import com.google.common.collect.ImmutableList; import com.google.common.collect.ImmutableMap; - import static java.util.stream.Collectors.toMap; -import lombok.val; - public class ConcreteType { + public static ConcreteType.Builder builder(Class interpreterValueType, TypeName reference) { return new Builder<>(interpreterValueType, reference); } - + public static ConcreteType.Builder builder(Class interpreterValueType, String name) { return builder(interpreterValueType, TypeName.of(name)); } - + public static ConcreteType.Builder classBuilder(String name) { return builder(ObjectInterpreterValue.class, name); } public static class Builder { - private final ImmutableMap.Builder methods = - ImmutableMap.builder(); - private final ImmutableMap.Builder staticMethods = - ImmutableMap.builder(); + private final ImmutableMap.Builder methods = ImmutableMap.builder(); + private final ImmutableMap.Builder staticMethods = ImmutableMap.builder(); private final Class interpreterValueType; private final TypeName name; @@ -50,112 +44,51 @@ public class ConcreteType { this.name = name; } - public Builder method( - String name, - List argumentsTypes, - BiFunction, InterpreterValue> method) { + public Builder method(String name, List argumentsTypes, BiFunction, InterpreterValue> method) { methods.put(name, new MethodValue(argumentsTypes, (environment, arguments) -> { - return Casts.tryCast(interpreterValueType, arguments.getReceiver()) - .map(typedReceiver -> - method.apply(environment, MethodCallArguments.of(typedReceiver, arguments.getPositionalArguments()))) - .orElseThrow(() -> new RuntimeException("receiver is of wrong type")); + return Casts.tryCast(interpreterValueType, arguments.getReceiver()).map(typedReceiver -> method.apply(environment, MethodCallArguments.of(typedReceiver, arguments.getPositionalArguments()))).orElseThrow(() -> new RuntimeException("receiver is of wrong type")); })); return this; } - public Builder staticMethod( - String name, - List argumentsTypes, - BiFunction method) { + public Builder staticMethod(String name, List argumentsTypes, BiFunction method) { staticMethods.put(name, new StaticMethodValue(argumentsTypes, method)); return this; } public ConcreteType build() { - return new ConcreteType( - name, - ImmutableMap.of(), - new MethodValue( - ImmutableList.of(), - (environment, arguments) -> InterpreterValues.UNIT), - methods.build(), - staticMethods.build()); + return new ConcreteType(name, ImmutableMap.of(), new MethodValue(ImmutableList.of(), (environment, arguments) -> InterpreterValues.UNIT), methods.build(), staticMethods.build()); } } public static ConcreteType fromNode(ClassNode classNode) { - val fields = classNode.getFields().stream() - .collect(toMap( - field -> field.getName(), - field -> new FieldValue(field.getName(), field.getType()))); - - val constructor = new MethodValue( - getArgumentTypes(classNode.getConstructor().getArguments()), - (environment, arguments) -> Executor.callMethod( - environment, - classNode.getConstructor(), - Optional.of(arguments.getReceiver()), - arguments.getPositionalArguments())); - - val methods = classNode.getMethods().stream() - .filter(method -> !method.isStatic()) - .collect(toMap( - method -> method.getName(), - method -> { - val argumentTypes = getArgumentTypes(method.getArguments()); - - return new MethodValue(argumentTypes, (environment, arguments) -> { - return Executor.callMethod( - environment, - method, - Optional.of(arguments.getReceiver()), - arguments.getPositionalArguments()); - }); - })); - - val staticMethods = classNode.getMethods() - .stream() - .filter(method -> method.isStatic()) - .collect(toMap( - method -> method.getName(), - method -> { - val argumentTypes = getArgumentTypes(method.getArguments()); - - return new StaticMethodValue(argumentTypes, (environment, arguments) -> { - return Executor.callMethod( - environment, - method, - Optional.empty(), - arguments); - }); - })); - return new ConcreteType( - classNode.getName(), - fields, - constructor, - methods, - staticMethods); + final java.util.Map fields = classNode.getFields().stream().collect(toMap(field -> field.getName(), field -> new FieldValue(field.getName(), field.getType()))); + final org.zwobble.couscous.interpreter.values.MethodValue constructor = new MethodValue(getArgumentTypes(classNode.getConstructor().getArguments()), (environment, arguments) -> Executor.callMethod(environment, classNode.getConstructor(), Optional.of(arguments.getReceiver()), arguments.getPositionalArguments())); + final java.util.Map methods = classNode.getMethods().stream().filter(method -> !method.isStatic()).collect(toMap(method -> method.getName(), method -> { + List argumentTypes = getArgumentTypes(method.getArguments()); + return new MethodValue(argumentTypes, (environment, arguments) -> { + return Executor.callMethod(environment, method, Optional.of(arguments.getReceiver()), arguments.getPositionalArguments()); + }); + })); + final java.util.Map staticMethods = classNode.getMethods().stream().filter(method -> method.isStatic()).collect(toMap(method -> method.getName(), method -> { + List argumentTypes = getArgumentTypes(method.getArguments()); + return new StaticMethodValue(argumentTypes, (environment, arguments) -> { + return Executor.callMethod(environment, method, Optional.empty(), arguments); + }); + })); + return new ConcreteType(classNode.getName(), fields, constructor, methods, staticMethods); } private static List getArgumentTypes(List arguments) { - return arguments - .stream() - .map(arg -> arg.getType()) - .collect(Collectors.toList()); + return arguments.stream().map(arg -> arg.getType()).collect(Collectors.toList()); } - private final TypeName name; private final Map fields; private final MethodValue constructor; private final Map methods; private final Map staticMethods; - - public ConcreteType( - TypeName name, - Map fields, - MethodValue constructor, - Map methods, - Map staticMethods) { + + public ConcreteType(TypeName name, Map fields, MethodValue constructor, Map methods, Map staticMethods) { this.name = name; this.fields = fields; this.constructor = constructor; @@ -170,27 +103,21 @@ public class ConcreteType { public Optional getField(String fieldName) { return Optional.ofNullable(fields.get(fieldName)); } - + public InterpreterValue callMethod(Environment environment, InterpreterValue receiver, String methodName, List arguments) { - val method = findMethod(methods, methodName, arguments); - return method.apply( - environment, - MethodCallArguments.of(receiver, new PositionalArguments(arguments))); + final org.zwobble.couscous.interpreter.values.MethodValue method = findMethod(methods, methodName, arguments); + return method.apply(environment, MethodCallArguments.of(receiver, new PositionalArguments(arguments))); } - + public InterpreterValue callStaticMethod(Environment environment, String methodName, List arguments) { - val method = findMethod(staticMethods, methodName, arguments); + final org.zwobble.couscous.interpreter.values.StaticMethodValue method = findMethod(staticMethods, methodName, arguments); return method.apply(environment, new PositionalArguments(arguments)); } - - public InterpreterValue callConstructor( - Environment environment, - List arguments) { - val object = new ObjectInterpreterValue(this); + + public InterpreterValue callConstructor(Environment environment, List arguments) { + final org.zwobble.couscous.interpreter.values.ObjectInterpreterValue object = new ObjectInterpreterValue(this); checkMethodArguments(constructor, arguments); - constructor.apply( - environment, - MethodCallArguments.of(object, new PositionalArguments(arguments))); + constructor.apply(environment, MethodCallArguments.of(object, new PositionalArguments(arguments))); return object; } @@ -198,20 +125,17 @@ public class ConcreteType { if (!methods.containsKey(methodName)) { throw new NoSuchMethod(methodName); } - val method = methods.get(methodName); + final T method = methods.get(methodName); checkMethodArguments(method, arguments); return method; } - - private static void checkMethodArguments( - final Callable method, - List arguments) { + + private static void checkMethodArguments(final Callable method, List arguments) { if (method.getArgumentTypes().size() != arguments.size()) { throw new WrongNumberOfArguments(method.getArgumentTypes().size(), arguments.size()); } - for (int index = 0; index < arguments.size(); index++) { - val formalArgumentType = method.getArgumentTypes().get(index); + final org.zwobble.couscous.ast.TypeName formalArgumentType = method.getArgumentTypes().get(index); InterpreterTypes.checkIsInstance(formalArgumentType, arguments.get(index)); } } @@ -220,4 +144,4 @@ public class ConcreteType { public String toString() { return "ConcreteType<" + name + ">"; } -} +} \ No newline at end of file diff --git a/src/main/java/org/zwobble/couscous/interpreter/values/FieldValue.java b/src/main/java/org/zwobble/couscous/interpreter/values/FieldValue.java index d778144..4ee1c95 100644 --- a/src/main/java/org/zwobble/couscous/interpreter/values/FieldValue.java +++ b/src/main/java/org/zwobble/couscous/interpreter/values/FieldValue.java @@ -2,10 +2,50 @@ package org.zwobble.couscous.interpreter.values; import org.zwobble.couscous.ast.TypeName; -import lombok.Value; +public final class FieldValue { + private final String name; + private final TypeName type; -@Value -public class FieldValue { - String name; - TypeName type; -} + public FieldValue(final String name, final TypeName type) { + this.name = name; + this.type = type; + } + + public String getName() { + return this.name; + } + + public TypeName getType() { + return this.type; + } + + @java.lang.Override + public boolean equals(final java.lang.Object o) { + if (o == this) return true; + if (!(o instanceof FieldValue)) return false; + final FieldValue other = (FieldValue)o; + final java.lang.Object this$name = this.getName(); + final java.lang.Object other$name = other.getName(); + if (this$name == null ? other$name != null : !this$name.equals(other$name)) return false; + final java.lang.Object this$type = this.getType(); + final java.lang.Object other$type = other.getType(); + if (this$type == null ? other$type != null : !this$type.equals(other$type)) return false; + return true; + } + + @java.lang.Override + public int hashCode() { + final int PRIME = 59; + int result = 1; + final java.lang.Object $name = this.getName(); + result = result * PRIME + ($name == null ? 43 : $name.hashCode()); + final java.lang.Object $type = this.getType(); + result = result * PRIME + ($type == null ? 43 : $type.hashCode()); + return result; + } + + @java.lang.Override + public java.lang.String toString() { + return "FieldValue(name=" + this.getName() + ", type=" + this.getType() + ")"; + } +} \ No newline at end of file diff --git a/src/main/java/org/zwobble/couscous/interpreter/values/IntegerInterpreterValue.java b/src/main/java/org/zwobble/couscous/interpreter/values/IntegerInterpreterValue.java index 95b05aa..bd214cb 100644 --- a/src/main/java/org/zwobble/couscous/interpreter/values/IntegerInterpreterValue.java +++ b/src/main/java/org/zwobble/couscous/interpreter/values/IntegerInterpreterValue.java @@ -1,48 +1,67 @@ package org.zwobble.couscous.interpreter.values; import java.util.Optional; - import org.zwobble.couscous.interpreter.NoSuchField; import org.zwobble.couscous.values.IntegerValue; import org.zwobble.couscous.values.PrimitiveValue; import org.zwobble.couscous.values.PrimitiveValues; import org.zwobble.couscous.values.StringValue; - import static java.util.Arrays.asList; -import lombok.Value; -import lombok.val; - -@Value -public class IntegerInterpreterValue implements InterpreterValue { - public static final ConcreteType TYPE = ConcreteType.builder(IntegerInterpreterValue.class, IntegerValue.REF) - .staticMethod("parseInt", asList(StringValue.REF), - (environment, arguments) -> { - val value = (StringInterpreterValue)arguments.get(0); - return new IntegerInterpreterValue(Integer.parseInt(value.getValue())); - }) - - .build(); - - int value; - +public final class IntegerInterpreterValue implements InterpreterValue { + public static final ConcreteType TYPE = ConcreteType.builder(IntegerInterpreterValue.class, IntegerValue.REF).staticMethod("parseInt", asList(StringValue.REF), (environment, arguments) -> { + StringInterpreterValue value = (StringInterpreterValue)arguments.get(0); + return new IntegerInterpreterValue(Integer.parseInt(value.getValue())); + }).build(); + private final int value; + @Override public ConcreteType getType() { return TYPE; } - + @Override public Optional toPrimitiveValue() { return Optional.of(PrimitiveValues.value(value)); } - + @Override public InterpreterValue getField(String fieldName) { throw new NoSuchField(fieldName); } - + @Override public void setField(String fieldName, InterpreterValue value) { throw new NoSuchField(fieldName); } -} + + public IntegerInterpreterValue(final int value) { + this.value = value; + } + + public int getValue() { + return this.value; + } + + @java.lang.Override + public boolean equals(final java.lang.Object o) { + if (o == this) return true; + if (!(o instanceof IntegerInterpreterValue)) return false; + final IntegerInterpreterValue other = (IntegerInterpreterValue)o; + if (this.getValue() != other.getValue()) return false; + return true; + } + + @java.lang.Override + public int hashCode() { + final int PRIME = 59; + int result = 1; + result = result * PRIME + this.getValue(); + return result; + } + + @java.lang.Override + public java.lang.String toString() { + return "IntegerInterpreterValue(value=" + this.getValue() + ")"; + } +} \ No newline at end of file diff --git a/src/main/java/org/zwobble/couscous/interpreter/values/MethodCallArguments.java b/src/main/java/org/zwobble/couscous/interpreter/values/MethodCallArguments.java index 9f3e937..23af57f 100644 --- a/src/main/java/org/zwobble/couscous/interpreter/values/MethodCallArguments.java +++ b/src/main/java/org/zwobble/couscous/interpreter/values/MethodCallArguments.java @@ -2,11 +2,6 @@ package org.zwobble.couscous.interpreter.values; import org.zwobble.couscous.interpreter.PositionalArguments; -import lombok.AllArgsConstructor; -import lombok.Getter; - -@AllArgsConstructor(staticName="of") -@Getter public class MethodCallArguments { private final T receiver; private final PositionalArguments positionalArguments; @@ -14,4 +9,21 @@ public class MethodCallArguments { public InterpreterValue get(int index) { return positionalArguments.get(index); } -} + + private MethodCallArguments(final T receiver, final PositionalArguments positionalArguments) { + this.receiver = receiver; + this.positionalArguments = positionalArguments; + } + + public static MethodCallArguments of(final T receiver, final PositionalArguments positionalArguments) { + return new MethodCallArguments(receiver, positionalArguments); + } + + public T getReceiver() { + return this.receiver; + } + + public PositionalArguments getPositionalArguments() { + return this.positionalArguments; + } +} \ No newline at end of file diff --git a/src/main/java/org/zwobble/couscous/interpreter/values/MethodValue.java b/src/main/java/org/zwobble/couscous/interpreter/values/MethodValue.java index b5068fc..81964fb 100644 --- a/src/main/java/org/zwobble/couscous/interpreter/values/MethodValue.java +++ b/src/main/java/org/zwobble/couscous/interpreter/values/MethodValue.java @@ -2,21 +2,53 @@ package org.zwobble.couscous.interpreter.values; import java.util.List; import java.util.function.BiFunction; - import org.zwobble.couscous.ast.TypeName; import org.zwobble.couscous.interpreter.Environment; -import lombok.AccessLevel; -import lombok.Getter; -import lombok.Value; - -@Value -public class MethodValue implements Callable { - List argumentTypes; - @Getter(value=AccessLevel.NONE) - BiFunction, InterpreterValue> apply; +public final class MethodValue implements Callable { + private final List argumentTypes; + private final BiFunction, InterpreterValue> apply; public InterpreterValue apply(Environment environment, MethodCallArguments arguments) { return apply.apply(environment, arguments); } -} + + public MethodValue(final List argumentTypes, final BiFunction, InterpreterValue> apply) { + this.argumentTypes = argumentTypes; + this.apply = apply; + } + + public List getArgumentTypes() { + return this.argumentTypes; + } + + @java.lang.Override + public boolean equals(final java.lang.Object o) { + if (o == this) return true; + if (!(o instanceof MethodValue)) return false; + final MethodValue other = (MethodValue)o; + final java.lang.Object this$argumentTypes = this.getArgumentTypes(); + final java.lang.Object other$argumentTypes = other.getArgumentTypes(); + if (this$argumentTypes == null ? other$argumentTypes != null : !this$argumentTypes.equals(other$argumentTypes)) return false; + final java.lang.Object this$apply = this.apply; + final java.lang.Object other$apply = other.apply; + if (this$apply == null ? other$apply != null : !this$apply.equals(other$apply)) return false; + return true; + } + + @java.lang.Override + public int hashCode() { + final int PRIME = 59; + int result = 1; + final java.lang.Object $argumentTypes = this.getArgumentTypes(); + result = result * PRIME + ($argumentTypes == null ? 43 : $argumentTypes.hashCode()); + final java.lang.Object $apply = this.apply; + result = result * PRIME + ($apply == null ? 43 : $apply.hashCode()); + return result; + } + + @java.lang.Override + public java.lang.String toString() { + return "MethodValue(argumentTypes=" + this.getArgumentTypes() + ", apply=" + this.apply + ")"; + } +} \ No newline at end of file diff --git a/src/main/java/org/zwobble/couscous/interpreter/values/ObjectInterpreterValue.java b/src/main/java/org/zwobble/couscous/interpreter/values/ObjectInterpreterValue.java index b248398..bebd5f7 100644 --- a/src/main/java/org/zwobble/couscous/interpreter/values/ObjectInterpreterValue.java +++ b/src/main/java/org/zwobble/couscous/interpreter/values/ObjectInterpreterValue.java @@ -3,18 +3,15 @@ package org.zwobble.couscous.interpreter.values; import java.util.HashMap; import java.util.Map; import java.util.Optional; - import org.zwobble.couscous.interpreter.InterpreterTypes; import org.zwobble.couscous.interpreter.NoSuchField; import org.zwobble.couscous.interpreter.UnboundField; import org.zwobble.couscous.values.PrimitiveValue; -import lombok.val; - public class ObjectInterpreterValue implements InterpreterValue { private final ConcreteType type; private final Map fields; - + public ObjectInterpreterValue(ConcreteType type) { this.type = type; this.fields = new HashMap<>(); @@ -24,26 +21,27 @@ public class ObjectInterpreterValue implements InterpreterValue { public ConcreteType getType() { return type; } - + @Override public Optional toPrimitiveValue() { return Optional.empty(); } - + @Override public InterpreterValue getField(String fieldName) { type.getField(fieldName).orElseThrow(() -> new NoSuchField(fieldName)); if (fields.containsKey(fieldName)) { - return fields.get(fieldName); + return fields.get(fieldName); } else { throw new UnboundField(fieldName); } } - + @Override public void setField(String fieldName, InterpreterValue value) { - val field = type.getField(fieldName).orElseThrow(() -> new NoSuchField(fieldName)); + FieldValue field = type.getField(fieldName) + .orElseThrow(() -> new NoSuchField(fieldName)); InterpreterTypes.checkIsInstance(field.getType(), value); - fields.put(fieldName, value); + fields.put(fieldName, value); } -} +} \ No newline at end of file diff --git a/src/main/java/org/zwobble/couscous/interpreter/values/StaticMethodValue.java b/src/main/java/org/zwobble/couscous/interpreter/values/StaticMethodValue.java index 37f3c56..302582c 100644 --- a/src/main/java/org/zwobble/couscous/interpreter/values/StaticMethodValue.java +++ b/src/main/java/org/zwobble/couscous/interpreter/values/StaticMethodValue.java @@ -2,23 +2,54 @@ package org.zwobble.couscous.interpreter.values; import java.util.List; import java.util.function.BiFunction; - import org.zwobble.couscous.ast.TypeName; import org.zwobble.couscous.interpreter.PositionalArguments; import org.zwobble.couscous.interpreter.Environment; -import lombok.AccessLevel; -import lombok.Getter; -import lombok.Value; - -@Value -public class StaticMethodValue implements Callable { - List argumentTypes; - @Getter(value=AccessLevel.NONE) - BiFunction apply; +public final class StaticMethodValue implements Callable { + private final List argumentTypes; + private final BiFunction apply; public InterpreterValue apply(Environment environment, PositionalArguments arguments) { return apply.apply(environment, arguments); } - -} + + public StaticMethodValue(final List argumentTypes, final BiFunction apply) { + this.argumentTypes = argumentTypes; + this.apply = apply; + } + + public List getArgumentTypes() { + return this.argumentTypes; + } + + @java.lang.Override + public boolean equals(final java.lang.Object o) { + if (o == this) return true; + if (!(o instanceof StaticMethodValue)) return false; + final StaticMethodValue other = (StaticMethodValue)o; + final java.lang.Object this$argumentTypes = this.getArgumentTypes(); + final java.lang.Object other$argumentTypes = other.getArgumentTypes(); + if (this$argumentTypes == null ? other$argumentTypes != null : !this$argumentTypes.equals(other$argumentTypes)) return false; + final java.lang.Object this$apply = this.apply; + final java.lang.Object other$apply = other.apply; + if (this$apply == null ? other$apply != null : !this$apply.equals(other$apply)) return false; + return true; + } + + @java.lang.Override + public int hashCode() { + final int PRIME = 59; + int result = 1; + final java.lang.Object $argumentTypes = this.getArgumentTypes(); + result = result * PRIME + ($argumentTypes == null ? 43 : $argumentTypes.hashCode()); + final java.lang.Object $apply = this.apply; + result = result * PRIME + ($apply == null ? 43 : $apply.hashCode()); + return result; + } + + @java.lang.Override + public java.lang.String toString() { + return "StaticMethodValue(argumentTypes=" + this.getArgumentTypes() + ", apply=" + this.apply + ")"; + } +} \ No newline at end of file diff --git a/src/main/java/org/zwobble/couscous/interpreter/values/StringInterpreterValue.java b/src/main/java/org/zwobble/couscous/interpreter/values/StringInterpreterValue.java index 15bde43..42ee713 100644 --- a/src/main/java/org/zwobble/couscous/interpreter/values/StringInterpreterValue.java +++ b/src/main/java/org/zwobble/couscous/interpreter/values/StringInterpreterValue.java @@ -1,53 +1,71 @@ package org.zwobble.couscous.interpreter.values; import java.util.Optional; - import org.zwobble.couscous.interpreter.NoSuchField; import org.zwobble.couscous.values.IntegerValue; import org.zwobble.couscous.values.PrimitiveValue; import org.zwobble.couscous.values.PrimitiveValues; import org.zwobble.couscous.values.StringValue; - import static java.util.Arrays.asList; -import lombok.Value; -import lombok.val; - -@Value -public class StringInterpreterValue implements InterpreterValue { - public static final ConcreteType TYPE = ConcreteType.builder(StringInterpreterValue.class, StringValue.REF) - .method("length", asList(), - (environment, arguments) -> - new IntegerInterpreterValue(arguments.getReceiver().value.length())) - - .method("substring", asList(IntegerValue.REF, IntegerValue.REF), - (environment, arguments) -> { - val startIndex = (IntegerInterpreterValue)arguments.get(0); - val endIndex = (IntegerInterpreterValue)arguments.get(1); - return new StringInterpreterValue(arguments.getReceiver().value.substring(startIndex.getValue(), endIndex.getValue())); - }) - - .build(); - - String value; - +public final class StringInterpreterValue implements InterpreterValue { + public static final ConcreteType TYPE = ConcreteType.builder(StringInterpreterValue.class, StringValue.REF).method("length", asList(), (environment, arguments) -> new IntegerInterpreterValue(arguments.getReceiver().value.length())).method("substring", asList(IntegerValue.REF, IntegerValue.REF), (environment, arguments) -> { + IntegerInterpreterValue startIndex = (IntegerInterpreterValue)arguments.get(0); + IntegerInterpreterValue endIndex = (IntegerInterpreterValue)arguments.get(1); + return new StringInterpreterValue(arguments.getReceiver().value.substring(startIndex.getValue(), endIndex.getValue())); + }).build(); + private final String value; + @Override public ConcreteType getType() { return TYPE; } - + @Override public Optional toPrimitiveValue() { return Optional.of(PrimitiveValues.value(value)); } - + @Override public InterpreterValue getField(String fieldName) { throw new NoSuchField(fieldName); } - + @Override public void setField(String fieldName, InterpreterValue value) { throw new NoSuchField(fieldName); } -} + + public StringInterpreterValue(final String value) { + this.value = value; + } + + public String getValue() { + return this.value; + } + + @java.lang.Override + public boolean equals(final java.lang.Object o) { + if (o == this) return true; + if (!(o instanceof StringInterpreterValue)) return false; + final StringInterpreterValue other = (StringInterpreterValue)o; + final java.lang.Object this$value = this.getValue(); + final java.lang.Object other$value = other.getValue(); + if (this$value == null ? other$value != null : !this$value.equals(other$value)) return false; + return true; + } + + @java.lang.Override + public int hashCode() { + final int PRIME = 59; + int result = 1; + final java.lang.Object $value = this.getValue(); + result = result * PRIME + ($value == null ? 43 : $value.hashCode()); + return result; + } + + @java.lang.Override + public java.lang.String toString() { + return "StringInterpreterValue(value=" + this.getValue() + ")"; + } +} \ No newline at end of file diff --git a/src/main/java/org/zwobble/couscous/interpreter/values/UnitInterpreterValue.java b/src/main/java/org/zwobble/couscous/interpreter/values/UnitInterpreterValue.java index 1c184a4..2d4ef9c 100644 --- a/src/main/java/org/zwobble/couscous/interpreter/values/UnitInterpreterValue.java +++ b/src/main/java/org/zwobble/couscous/interpreter/values/UnitInterpreterValue.java @@ -1,40 +1,39 @@ package org.zwobble.couscous.interpreter.values; import java.util.Optional; - import org.zwobble.couscous.interpreter.NoSuchField; import org.zwobble.couscous.values.PrimitiveValue; import org.zwobble.couscous.values.PrimitiveValues; -import lombok.ToString; - -@ToString public class UnitInterpreterValue implements InterpreterValue { - private static final ConcreteType TYPE = ConcreteType.builder(UnitInterpreterValue.class, "Unit") - .build(); - - public static final UnitInterpreterValue UNIT = new UnitInterpreterValue(); + private static final ConcreteType TYPE = ConcreteType.builder(UnitInterpreterValue.class, "Unit").build(); + public static final UnitInterpreterValue UNIT = new UnitInterpreterValue(); private UnitInterpreterValue() { } - + @Override public ConcreteType getType() { return TYPE; } - + @Override public Optional toPrimitiveValue() { return Optional.of(PrimitiveValues.UNIT); } - + @Override public InterpreterValue getField(String fieldName) { throw new NoSuchField(fieldName); } - + @Override public void setField(String fieldName, InterpreterValue value) { throw new NoSuchField(fieldName); } -} + + @java.lang.Override + public java.lang.String toString() { + return "UnitInterpreterValue()"; + } +} \ No newline at end of file diff --git a/src/main/java/org/zwobble/couscous/values/BooleanValue.java b/src/main/java/org/zwobble/couscous/values/BooleanValue.java index 6f18e36..5e6191f 100644 --- a/src/main/java/org/zwobble/couscous/values/BooleanValue.java +++ b/src/main/java/org/zwobble/couscous/values/BooleanValue.java @@ -2,28 +2,47 @@ package org.zwobble.couscous.values; import org.zwobble.couscous.ast.TypeName; -import lombok.AccessLevel; -import lombok.Getter; -import lombok.Value; - -@Value -public class BooleanValue implements PrimitiveValue { +public final class BooleanValue implements PrimitiveValue { public static final TypeName REF = TypeName.of("boolean"); - - @Getter(value = AccessLevel.NONE) - boolean value; + private final boolean value; public boolean getValue() { return value; } - + @Override public T accept(PrimitiveValueVisitor visitor) { return visitor.visit(this); } - + @Override public TypeName getType() { return REF; } -} + + public BooleanValue(final boolean value) { + this.value = value; + } + + @java.lang.Override + public boolean equals(final java.lang.Object o) { + if (o == this) return true; + if (!(o instanceof BooleanValue)) return false; + final BooleanValue other = (BooleanValue)o; + if (this.getValue() != other.getValue()) return false; + return true; + } + + @java.lang.Override + public int hashCode() { + final int PRIME = 59; + int result = 1; + result = result * PRIME + (this.getValue() ? 79 : 97); + return result; + } + + @java.lang.Override + public java.lang.String toString() { + return "BooleanValue(value=" + this.getValue() + ")"; + } +} \ No newline at end of file diff --git a/src/main/java/org/zwobble/couscous/values/IntegerValue.java b/src/main/java/org/zwobble/couscous/values/IntegerValue.java index 794ad8c..e897668 100644 --- a/src/main/java/org/zwobble/couscous/values/IntegerValue.java +++ b/src/main/java/org/zwobble/couscous/values/IntegerValue.java @@ -2,21 +2,47 @@ package org.zwobble.couscous.values; import org.zwobble.couscous.ast.TypeName; -import lombok.Value; - -@Value -public class IntegerValue implements PrimitiveValue { +public final class IntegerValue implements PrimitiveValue { public static final TypeName REF = TypeName.of("int"); + private final int value; - int value; - @Override public T accept(PrimitiveValueVisitor visitor) { return visitor.visit(this); } - + @Override public TypeName getType() { return REF; } -} + + public IntegerValue(final int value) { + this.value = value; + } + + public int getValue() { + return this.value; + } + + @java.lang.Override + public boolean equals(final java.lang.Object o) { + if (o == this) return true; + if (!(o instanceof IntegerValue)) return false; + final IntegerValue other = (IntegerValue)o; + if (this.getValue() != other.getValue()) return false; + return true; + } + + @java.lang.Override + public int hashCode() { + final int PRIME = 59; + int result = 1; + result = result * PRIME + this.getValue(); + return result; + } + + @java.lang.Override + public java.lang.String toString() { + return "IntegerValue(value=" + this.getValue() + ")"; + } +} \ No newline at end of file diff --git a/src/main/java/org/zwobble/couscous/values/StringValue.java b/src/main/java/org/zwobble/couscous/values/StringValue.java index b912fd3..73e3191 100644 --- a/src/main/java/org/zwobble/couscous/values/StringValue.java +++ b/src/main/java/org/zwobble/couscous/values/StringValue.java @@ -2,25 +2,54 @@ package org.zwobble.couscous.values; import org.zwobble.couscous.ast.TypeName; -import lombok.Value; - -@Value -public class StringValue implements PrimitiveValue { +public final class StringValue implements PrimitiveValue { + public static StringValue of(String value) { return new StringValue(value); } - public static final TypeName REF = TypeName.of("java.lang.String"); - - String value; - + private final String value; + @Override public T accept(PrimitiveValueVisitor visitor) { return visitor.visit(this); } - + @Override public TypeName getType() { return REF; } -} + + public StringValue(final String value) { + this.value = value; + } + + public String getValue() { + return this.value; + } + + @java.lang.Override + public boolean equals(final java.lang.Object o) { + if (o == this) return true; + if (!(o instanceof StringValue)) return false; + final StringValue other = (StringValue)o; + final java.lang.Object this$value = this.getValue(); + final java.lang.Object other$value = other.getValue(); + if (this$value == null ? other$value != null : !this$value.equals(other$value)) return false; + return true; + } + + @java.lang.Override + public int hashCode() { + final int PRIME = 59; + int result = 1; + final java.lang.Object $value = this.getValue(); + result = result * PRIME + ($value == null ? 43 : $value.hashCode()); + return result; + } + + @java.lang.Override + public java.lang.String toString() { + return "StringValue(value=" + this.getValue() + ")"; + } +} \ No newline at end of file diff --git a/src/test/java/org/zwobble/couscous/tests/BackendEvalTests.java b/src/test/java/org/zwobble/couscous/tests/BackendEvalTests.java index 169e0f3..20d1881 100644 --- a/src/test/java/org/zwobble/couscous/tests/BackendEvalTests.java +++ b/src/test/java/org/zwobble/couscous/tests/BackendEvalTests.java @@ -5,6 +5,7 @@ import java.util.List; import org.junit.Test; import org.zwobble.couscous.ast.ClassNode; import org.zwobble.couscous.ast.ExpressionNode; +import org.zwobble.couscous.ast.FormalArgumentNode; import org.zwobble.couscous.values.IntegerValue; import org.zwobble.couscous.values.PrimitiveValue; import org.zwobble.couscous.values.StringValue; @@ -27,8 +28,6 @@ import static org.zwobble.couscous.ast.VariableReferenceNode.reference; import static org.zwobble.couscous.tests.TestIds.ANY_ID; import static org.zwobble.couscous.values.PrimitiveValues.value; -import lombok.val; - public abstract class BackendEvalTests { @Test public void canEvaluateLiterals() { @@ -40,19 +39,19 @@ public abstract class BackendEvalTests { @Test public void whenConditionIsTrueThenValueOfConditionalTernaryIsTrueBranch() { - val result = evalExpression(ternaryConditional(literal(true), literal("T"), literal("F"))); + PrimitiveValue result = evalExpression(ternaryConditional(literal(true), literal("T"), literal("F"))); assertEquals(value("T"), result); } @Test public void whenConditionIsFalseThenValueOfConditionalTernaryIsFalseBranch() { - val result = evalExpression(ternaryConditional(literal(false), literal("T"), literal("F"))); + PrimitiveValue result = evalExpression(ternaryConditional(literal(false), literal("T"), literal("F"))); assertEquals(value("F"), result); } @Test public void canCallMethodWithNoArgumentsOnBuiltin() { - val result = evalExpression(methodCall( + PrimitiveValue result = evalExpression(methodCall( literal("hello"), "length", asList(), @@ -62,7 +61,7 @@ public abstract class BackendEvalTests { @Test public void canCallMethodWithArgumentsOnBuiltin() { - val result = evalExpression(methodCall( + PrimitiveValue result = evalExpression(methodCall( literal("hello"), "substring", asList(literal(1), literal(4)), @@ -72,43 +71,43 @@ public abstract class BackendEvalTests { @Test public void canCallBuiltinStaticMethod() { - val result = evalExpression( + PrimitiveValue result = evalExpression( staticMethodCall("java.lang.Integer", "parseInt", literal("42"))); assertEquals(value(42), result); } @Test public void canCallStaticMethodFromUserDefinedStaticMethod() { - val classNode = ClassNode.builder("com.example.Example") + ClassNode classNode = ClassNode.builder("com.example.Example") .staticMethod("main", method -> method .statement(returns(staticMethodCall("java.lang.Integer", "parseInt", literal("42"))))) .build(); - val result = evalExpression(asList(classNode), + PrimitiveValue result = evalExpression(asList(classNode), staticMethodCall("com.example.Example", "main")); assertEquals(value(42), result); } @Test public void canCallInstanceMethodWithNoArgumentsOnUserDefinedClass() { - val classNode = ClassNode.builder("com.example.Example") + ClassNode classNode = ClassNode.builder("com.example.Example") .method("main", method -> method .statement(returns(literal(42)))) .build(); - val result = evalExpression(asList(classNode), + PrimitiveValue result = evalExpression(asList(classNode), methodCall(constructorCall(classNode.getName(), asList()), "main", asList(), IntegerValue.REF)); assertEquals(value(42), result); } @Test public void canCallInstanceMethodWithArgumentsOnUserDefinedClass() { - val argument = formalArg(var(ANY_ID, "x", IntegerValue.REF)); - val classNode = ClassNode.builder("com.example.Example") + FormalArgumentNode argument = formalArg(var(ANY_ID, "x", IntegerValue.REF)); + ClassNode classNode = ClassNode.builder("com.example.Example") .method("main", method -> method .argument(argument) .statement(returns(reference(argument)))) .build(); - val result = evalExpression( + PrimitiveValue result = evalExpression( asList(classNode), methodCall( constructorCall(classNode.getName(), asList()), @@ -121,8 +120,8 @@ public abstract class BackendEvalTests { @Test public void constructorIsExecutedOnConstruction() { - val argument = formalArg(var(ANY_ID, "x", IntegerValue.REF)); - val classNode = ClassNode.builder("com.example.Example") + FormalArgumentNode argument = formalArg(var(ANY_ID, "x", IntegerValue.REF)); + ClassNode classNode = ClassNode.builder("com.example.Example") .field("value", IntegerValue.REF) .constructor(constructor -> constructor .argument(argument) @@ -134,7 +133,7 @@ public abstract class BackendEvalTests { fieldAccess(method.thisReference(), "value", IntegerValue.REF)))) .build(); - val result = evalExpression( + PrimitiveValue result = evalExpression( asList(classNode), methodCall( constructorCall(classNode.getName(), asList(literal(42))), diff --git a/src/test/java/org/zwobble/couscous/tests/BackendMethodTests.java b/src/test/java/org/zwobble/couscous/tests/BackendMethodTests.java index 0f463ca..f1af3a9 100644 --- a/src/test/java/org/zwobble/couscous/tests/BackendMethodTests.java +++ b/src/test/java/org/zwobble/couscous/tests/BackendMethodTests.java @@ -2,12 +2,13 @@ package org.zwobble.couscous.tests; import org.junit.Test; import org.zwobble.couscous.ast.ClassNode; +import org.zwobble.couscous.ast.FormalArgumentNode; import org.zwobble.couscous.ast.LiteralNode; +import org.zwobble.couscous.ast.LocalVariableDeclarationNode; import org.zwobble.couscous.ast.MethodNode; import org.zwobble.couscous.values.PrimitiveValue; import org.zwobble.couscous.values.PrimitiveValues; import org.zwobble.couscous.values.StringValue; - import static java.util.Arrays.asList; import static org.junit.Assert.assertEquals; import static org.zwobble.couscous.ast.AssignmentNode.assign; @@ -22,88 +23,75 @@ import static org.zwobble.couscous.ast.VariableReferenceNode.reference; import static org.zwobble.couscous.tests.TestIds.ANY_ID; import static org.zwobble.couscous.values.PrimitiveValues.value; -import lombok.val; - public abstract class BackendMethodTests { @Test public void methodWithNoStatementsReturnsUnit() { - val method = staticMethod("hello"); - val result = runMethod(method); - + MethodNode.Builder method = staticMethod("hello"); + final java.lang.Object result = runMethod(method); assertEquals(PrimitiveValues.UNIT, result); } @Test public void canReturnLiteralValue() { - val method = staticMethod("hello") + MethodNode.Builder method = staticMethod("hello") .statement(returns(literal("hello, world!"))); - val result = runMethod(method); - + final java.lang.Object result = runMethod(method); assertEquals(value("hello, world!"), result); } + @Test public void canPassValueToMethod() { - val arg = formalArg(var(ANY_ID, "x", StringValue.REF)); - val method = staticMethod("hello") + FormalArgumentNode arg = formalArg(var(ANY_ID, "x", StringValue.REF)); + MethodNode.Builder method = staticMethod("hello") .argument(arg) .statement(returns(reference(arg))); - val result = runMethod(method, value("hello, world!")); - + final java.lang.Object result = runMethod(method, value("hello, world!")); assertEquals(value("hello, world!"), result); } @Test public void canReassignValueToArgument() { - val arg = formalArg(var(ANY_ID, "x", StringValue.REF)); - val method = staticMethod("hello") + FormalArgumentNode arg = formalArg(var(ANY_ID, "x", StringValue.REF)); + MethodNode.Builder method = staticMethod("hello") .argument(arg) - .statement(expressionStatement(assign(reference(arg), LiteralNode.literal("[updated value]")))) + .statement(expressionStatement(assign( + reference(arg), + literal("[updated value]")))) .statement(returns(reference(arg))); - val result = runMethod(method, value("[initial value]")); - + final java.lang.Object result = runMethod(method, value("[initial value]")); assertEquals(value("[updated value]"), result); } @Test public void canDeclareVariable() { - val localVariableDeclaration = localVariableDeclaration( - ANY_ID, "x", StringValue.REF, LiteralNode.literal("[initial value]")); - val method = staticMethod("hello") + LocalVariableDeclarationNode localVariableDeclaration = localVariableDeclaration(ANY_ID, "x", StringValue.REF, LiteralNode.literal("[initial value]")); + MethodNode.Builder method = staticMethod("hello") .statement(localVariableDeclaration) .statement(returns(reference(localVariableDeclaration))); - val result = runMethod(method); - + final java.lang.Object result = runMethod(method); assertEquals(value("[initial value]"), result); } @Test public void canDeclareVariableAndThenAssignValues() { - val localVariableDeclaration = localVariableDeclaration( - ANY_ID, "x", StringValue.REF, LiteralNode.literal("[initial value]")); - val method = staticMethod("hello") + LocalVariableDeclarationNode localVariableDeclaration = localVariableDeclaration(ANY_ID, "x", StringValue.REF, LiteralNode.literal("[initial value]")); + MethodNode.Builder method = staticMethod("hello") .statement(localVariableDeclaration) - .statement(expressionStatement(assign(reference(localVariableDeclaration), LiteralNode.literal("[updated value]")))) + .statement(expressionStatement(assign( + reference(localVariableDeclaration), + literal("[updated value]")))) .statement(returns(reference(localVariableDeclaration))); - val result = runMethod(method); - + final java.lang.Object result = runMethod(method); assertEquals(value("[updated value]"), result); } - + protected PrimitiveValue runMethod(MethodNode.Builder methodBuilder, PrimitiveValue... arguments) { - val method = methodBuilder.build(); - val className = "com.example.Program"; - val classNode = ClassNode.builder(className) - .method(method) - .build(); - - val runner = buildMethodRunner(); - return runner.runMethod( - asList(classNode), - classNode.getName(), - method.getName(), - asList(arguments)); + MethodNode method = methodBuilder.build(); + String className = "com.example.Program"; + ClassNode classNode = ClassNode.builder(className).method(method).build(); + MethodRunner runner = buildMethodRunner(); + return runner.runMethod(asList(classNode), classNode.getName(), method.getName(), asList(arguments)); } protected abstract MethodRunner buildMethodRunner(); - -} +} \ No newline at end of file diff --git a/src/test/java/org/zwobble/couscous/tests/JavaToPythonTests.java b/src/test/java/org/zwobble/couscous/tests/JavaToPythonTests.java index 6732f47..74b0ae4 100644 --- a/src/test/java/org/zwobble/couscous/tests/JavaToPythonTests.java +++ b/src/test/java/org/zwobble/couscous/tests/JavaToPythonTests.java @@ -1,54 +1,40 @@ package org.zwobble.couscous.tests; import java.nio.file.Files; +import java.util.List; import org.junit.Test; +import org.zwobble.couscous.ast.ClassNode; import org.zwobble.couscous.ast.TypeName; import org.zwobble.couscous.frontends.java.JavaFrontend; import org.zwobble.couscous.tests.backends.python.PythonMethodRunner; import org.zwobble.couscous.values.PrimitiveValue; - import static java.util.Arrays.asList; import static org.junit.Assert.assertEquals; import static org.zwobble.couscous.tests.util.ExtraFiles.deleteRecursively; import static org.zwobble.couscous.values.PrimitiveValues.value; -import lombok.SneakyThrows; -import lombok.val; - public class JavaToPythonTests { @Test public void canEvaluateLiterals() { assertEquals(value("hello"), evalExpression("\"hello\"")); assertEquals(value(42), evalExpression("42")); } - - @SneakyThrows + private PrimitiveValue evalExpression(String expressionSource) { - val javaClass = - "package com.example;" + - "public class Example {" + - " public static Object main() {" + - " return " + expressionSource + ";" + - " }" + - "}"; - - val directoryPath = Files.createTempDirectory(null); try { - Files.createDirectories(directoryPath.resolve("com/example")); - Files.write( - directoryPath.resolve("com/example/Example.java"), - asList(javaClass)); - - val classNodes = JavaFrontend.readSourceDirectory(directoryPath); - - return new PythonMethodRunner().runMethod( - classNodes, - TypeName.of("com.example.Example"), - "main", - asList()); - } finally { - deleteRecursively(directoryPath.toFile()); + final java.lang.String javaClass = "package com.example;" + "public class Example {" + " public static Object main() {" + " return " + expressionSource + ";" + " }" + "}"; + final java.nio.file.Path directoryPath = Files.createTempDirectory(null); + try { + Files.createDirectories(directoryPath.resolve("com/example")); + Files.write(directoryPath.resolve("com/example/Example.java"), asList(javaClass)); + List classNodes = JavaFrontend.readSourceDirectory(directoryPath); + return new PythonMethodRunner().runMethod(classNodes, TypeName.of("com.example.Example"), "main", asList()); + } finally { + deleteRecursively(directoryPath.toFile()); + } + } catch (final java.lang.Throwable $ex) { + throw new RuntimeException($ex); } } -} +} \ No newline at end of file diff --git a/src/test/java/org/zwobble/couscous/tests/backends/python/PythonCompilerEvalTests.java b/src/test/java/org/zwobble/couscous/tests/backends/python/PythonCompilerEvalTests.java index c273638..c5c7aab 100644 --- a/src/test/java/org/zwobble/couscous/tests/backends/python/PythonCompilerEvalTests.java +++ b/src/test/java/org/zwobble/couscous/tests/backends/python/PythonCompilerEvalTests.java @@ -1,39 +1,31 @@ package org.zwobble.couscous.tests.backends.python; import java.util.List; - import org.zwobble.couscous.ast.ClassNode; import org.zwobble.couscous.ast.ExpressionNode; import org.zwobble.couscous.ast.MethodNode; import org.zwobble.couscous.ast.ReturnNode; import org.zwobble.couscous.tests.BackendEvalTests; import org.zwobble.couscous.values.PrimitiveValue; - import com.google.common.collect.ImmutableList; import com.google.common.collect.Iterables; - import static java.util.Arrays.asList; -import lombok.val; - public class PythonCompilerEvalTests extends BackendEvalTests { @Override - protected PrimitiveValue evalExpression( - List classes, - ExpressionNode expression) { - - val programNode = ClassNode.builder("Program") + protected PrimitiveValue evalExpression(List classes, ExpressionNode expression) { + ClassNode programNode = ClassNode.builder("Program") .method(MethodNode.staticMethod("run") .statement(ReturnNode.returns(expression)) .build()) .build(); - - val runner = new PythonMethodRunner(); - + PythonMethodRunner runner = new PythonMethodRunner(); return runner.runMethod( - ImmutableList.copyOf(Iterables.concat(classes, asList(programNode))), + ImmutableList.copyOf(Iterables.concat( + classes, + asList(programNode))), programNode.getName(), "run", ImmutableList.of()); } -} +} \ No newline at end of file diff --git a/src/test/java/org/zwobble/couscous/tests/backends/python/PythonMethodRunner.java b/src/test/java/org/zwobble/couscous/tests/backends/python/PythonMethodRunner.java index 50f0a0a..1fc0d03 100644 --- a/src/test/java/org/zwobble/couscous/tests/backends/python/PythonMethodRunner.java +++ b/src/test/java/org/zwobble/couscous/tests/backends/python/PythonMethodRunner.java @@ -4,8 +4,8 @@ import java.io.IOException; import java.io.InputStream; import java.io.InputStreamReader; import java.nio.file.Files; +import java.nio.file.Path; import java.util.List; - import org.zwobble.couscous.ast.ClassNode; import org.zwobble.couscous.ast.TypeName; import org.zwobble.couscous.backends.python.PythonCodeGenerator; @@ -14,59 +14,44 @@ import org.zwobble.couscous.backends.python.PythonSerializer; import org.zwobble.couscous.tests.MethodRunner; import org.zwobble.couscous.values.PrimitiveValue; import org.zwobble.couscous.values.PrimitiveValues; - import com.google.common.base.Charsets; import com.google.common.base.Joiner; import com.google.common.io.CharStreams; - import static java.lang.Integer.parseInt; import static org.zwobble.couscous.tests.util.ExtraFiles.deleteRecursively; import static org.zwobble.couscous.values.PrimitiveValues.value; -import lombok.SneakyThrows; -import lombok.val; - public class PythonMethodRunner implements MethodRunner { @Override - @SneakyThrows - public PrimitiveValue runMethod( - List classNodes, - TypeName className, - String methodName, - List arguments) { - val directoryPath = Files.createTempDirectory(null); - val compiler = new PythonCompiler(directoryPath, "couscous"); + public PrimitiveValue runMethod(List classNodes, TypeName className, String methodName, List arguments) { try { - compiler.compile(classNodes); - - val argumentsString = Joiner.on(", ").join(arguments.stream() - .map(PythonCodeGenerator::generateCode) - .map(PythonSerializer::serialize) - .iterator()); - - val program = "from couscous." + className.getQualifiedName() + " import " + className.getSimpleName() + - ";print(repr(" + className.getSimpleName() + "." + methodName + "(" + argumentsString + ")))"; - - val process = new ProcessBuilder("python3.4", "-c", program) - .directory(directoryPath.toFile()) - .start(); - val exitCode = process.waitFor(); - val output = readString(process.getInputStream()).trim(); - val stderrOutput = readString(process.getErrorStream()); - if (exitCode != 0) { - throw new RuntimeException("stderr was: " + stderrOutput); - } else { - return readPrimitive(output); + Path directoryPath = Files.createTempDirectory(null); + PythonCompiler compiler = new PythonCompiler(directoryPath, "couscous"); + try { + compiler.compile(classNodes); + String argumentsString = Joiner.on(", ").join(arguments.stream().map(PythonCodeGenerator::generateCode).map(PythonSerializer::serialize).iterator()); + String program = "from couscous." + className.getQualifiedName() + " import " + className.getSimpleName() + ";print(repr(" + className.getSimpleName() + "." + methodName + "(" + argumentsString + ")))"; + Process process = new ProcessBuilder("python3.4", "-c", program).directory(directoryPath.toFile()).start(); + int exitCode = process.waitFor(); + String output = readString(process.getInputStream()).trim(); + String stderrOutput = readString(process.getErrorStream()); + if (exitCode != 0) { + throw new RuntimeException("stderr was: " + stderrOutput); + } else { + return readPrimitive(output); + } + } finally { + deleteRecursively(directoryPath.toFile()); } - } finally { - deleteRecursively(directoryPath.toFile()); + } catch (final java.lang.Throwable $ex) { + throw new RuntimeException($ex); } } - + private PrimitiveValue readPrimitive(String output) { if (output.equals("None")) { return PrimitiveValues.UNIT; - } else if (output.startsWith("'")) { + } else if (output.startsWith("\'")) { return value(output.substring(1, output.length() - 1)); } else if (output.equals("True")) { return value(true); @@ -76,8 +61,8 @@ public class PythonMethodRunner implements MethodRunner { return value(parseInt(output)); } } - + private String readString(final InputStream stream) throws IOException { return CharStreams.toString(new InputStreamReader(stream, Charsets.UTF_8)); } -} +} \ No newline at end of file diff --git a/src/test/java/org/zwobble/couscous/tests/backends/python/PythonSerializerTests.java b/src/test/java/org/zwobble/couscous/tests/backends/python/PythonSerializerTests.java index 46e0aa1..24b2e9a 100644 --- a/src/test/java/org/zwobble/couscous/tests/backends/python/PythonSerializerTests.java +++ b/src/test/java/org/zwobble/couscous/tests/backends/python/PythonSerializerTests.java @@ -3,6 +3,7 @@ package org.zwobble.couscous.tests.backends.python; import org.junit.Test; import org.zwobble.couscous.backends.python.ast.PythonClassNode; import org.zwobble.couscous.backends.python.ast.PythonFunctionDefinitionNode; +import org.zwobble.couscous.backends.python.ast.PythonModuleNode; import static java.util.Arrays.asList; import static org.junit.Assert.assertEquals; @@ -22,19 +23,17 @@ import static org.zwobble.couscous.backends.python.ast.PythonReturnNode.pythonRe import static org.zwobble.couscous.backends.python.ast.PythonStringLiteralNode.pythonStringLiteral; import static org.zwobble.couscous.backends.python.ast.PythonVariableReferenceNode.pythonVariableReference; -import lombok.val; - public class PythonSerializerTests { @Test public void integersAreNotBoxed() { - val output = serialize(pythonIntegerLiteral(42)); + String output = serialize(pythonIntegerLiteral(42)); assertEquals("42", output); } @Test public void stringsAreNotBoxed() { // TODO: escaping - val output = serialize(pythonStringLiteral("blah")); + String output = serialize(pythonStringLiteral("blah")); assertEquals("\"blah\"", output); } @@ -51,104 +50,82 @@ public class PythonSerializerTests { @Test public void conditionalExpressionIsSerializedUsingParenthesisedSubExpression() { - assertEquals("(1) if (True) else (2)", serialize( - pythonConditionalExpression( - pythonBooleanLiteral(true), - pythonIntegerLiteral(1), - pythonIntegerLiteral(2)))); + assertEquals("(1) if (True) else (2)", serialize(pythonConditionalExpression(pythonBooleanLiteral(true), pythonIntegerLiteral(1), pythonIntegerLiteral(2)))); } @Test public void attributeAccessIsSerializedUsingParenthesisedSubExpression() { - assertEquals("(x).y", serialize( - pythonAttributeAccess( - pythonVariableReference("x"), - "y"))); + assertEquals("(x).y", serialize(pythonAttributeAccess(pythonVariableReference("x"), "y"))); } @Test public void callIsSerializedUsingParenthesisedSubExpression() { - assertEquals("(f)(x, y)", serialize( - pythonCall( - pythonVariableReference("f"), - asList( - pythonVariableReference("x"), - pythonVariableReference("y"))))); + assertEquals("(f)(x, y)", serialize(pythonCall(pythonVariableReference("f"), asList(pythonVariableReference("x"), pythonVariableReference("y"))))); } @Test public void getSliceIsSerializedUsingParenthesisedSubExpression() { - assertEquals("(x)[y:z]", serialize( - pythonGetSlice( - pythonVariableReference("x"), - asList( - pythonVariableReference("y"), - pythonVariableReference("z"))))); + assertEquals("(x)[y:z]", serialize(pythonGetSlice(pythonVariableReference("x"), asList(pythonVariableReference("y"), pythonVariableReference("z"))))); } @Test public void returnKeywordIsUsedForReturns() { - val output = serialize(pythonReturn(pythonIntegerLiteral(42))); + String output = serialize(pythonReturn(pythonIntegerLiteral(42))); assertEquals("return 42\n", output); } @Test public void passStatementIsSerializedAsPassKeyword() { - val output = serialize(PASS); + final java.lang.Object output = serialize(PASS); assertEquals("pass\n", output); } @Test public void emptyFunctionHasPassStatement() { - val function = PythonFunctionDefinitionNode.builder("empty").build(); - val output = serialize(function); + PythonFunctionDefinitionNode function = PythonFunctionDefinitionNode.builder("empty").build(); + String output = serialize(function); assertEquals("def empty():\n pass\n", output); } @Test public void functionArgumentsAreSerializedWithName() { - val function = PythonFunctionDefinitionNode.builder("empty") + PythonFunctionDefinitionNode function = PythonFunctionDefinitionNode.builder("empty") .argument("one") .argument("two") .build(); - val output = serialize(function); + String output = serialize(function); assertEquals("def empty(one, two):\n pass\n", output); } @Test public void emptyClassHasPassStatement() { - val classNode = PythonClassNode.builder("Empty") - .build(); - val output = serialize(classNode); + PythonClassNode classNode = PythonClassNode.builder("Empty").build(); + String output = serialize(classNode); assertEquals("class Empty(object):\n pass\n", output); } @Test public void bodiesOfBlocksAreIndented() { - val classNode = PythonClassNode.builder("Foo") + PythonClassNode classNode = PythonClassNode.builder("Foo") .statement(PythonFunctionDefinitionNode.builder("one").build()) .statement(PythonFunctionDefinitionNode.builder("two").build()) .build(); - val output = serialize(classNode); - val expectedOutput = - "class Foo(object):\n" + - " def one():\n" + - " pass\n" + - " def two():\n" + - " pass\n"; + String output = serialize(classNode); + String expectedOutput = "class Foo(object):\n def one():\n pass\n def two():\n pass\n"; assertEquals(expectedOutput, output); } @Test public void assignmentIsSerializedWithEqualsSymbolSeparatingTargetAndValue() { - val output = serialize(pythonAssignment( - pythonVariableReference("x"), pythonIntegerLiteral(42))); + String output = serialize(pythonAssignment( + pythonVariableReference("x"), + pythonIntegerLiteral(42))); assertEquals("x = 42\n", output); } @Test public void importIsSerializedUsingImportKeyword() { - val output = serialize(pythonImport( + String output = serialize(pythonImport( "com.example", asList(pythonImportAlias("Program")))); assertEquals("from com.example import Program\n", output); @@ -156,16 +133,16 @@ public class PythonSerializerTests { @Test public void importAliasesAreSeparatedByCommas() { - val output = serialize(pythonImport( + String output = serialize(pythonImport( "com.example", - asList(pythonImportAlias("Program"), pythonImportAlias("Runner")))); + asList(pythonImportAlias("Program"),pythonImportAlias("Runner")))); assertEquals("from com.example import Program, Runner\n", output); } @Test public void moduleIsSerializedStatements() { - val classNode = pythonModule(asList(PASS)); - val output = serialize(classNode); + PythonModuleNode classNode = pythonModule(asList(PASS)); + String output = serialize(classNode); assertEquals("pass\n", output); } -} +} \ No newline at end of file diff --git a/src/test/java/org/zwobble/couscous/tests/frontends/java/JavaReaderTests.java b/src/test/java/org/zwobble/couscous/tests/frontends/java/JavaReaderTests.java index 8c9ee95..d01830f 100644 --- a/src/test/java/org/zwobble/couscous/tests/frontends/java/JavaReaderTests.java +++ b/src/test/java/org/zwobble/couscous/tests/frontends/java/JavaReaderTests.java @@ -1,12 +1,16 @@ package org.zwobble.couscous.tests.frontends.java; import java.nio.file.Files; +import java.nio.file.Path; import java.util.List; import org.junit.Test; import org.zwobble.couscous.ast.ClassNode; +import org.zwobble.couscous.ast.ConstructorNode; import org.zwobble.couscous.ast.ExpressionNode; +import org.zwobble.couscous.ast.FormalArgumentNode; import org.zwobble.couscous.ast.LocalVariableDeclarationNode; +import org.zwobble.couscous.ast.MethodNode; import org.zwobble.couscous.ast.ReturnNode; import org.zwobble.couscous.ast.StatementNode; import org.zwobble.couscous.ast.ThisReferenceNode; @@ -33,9 +37,6 @@ import static org.zwobble.couscous.ast.ThisReferenceNode.thisReference; import static org.zwobble.couscous.ast.VariableReferenceNode.reference; import static org.zwobble.couscous.tests.util.ExtraFiles.deleteRecursively; -import lombok.SneakyThrows; -import lombok.val; - public class JavaReaderTests { @Test public void canReadLiterals() { @@ -54,7 +55,7 @@ public class JavaReaderTests { @Test public void canReadFieldDeclarations() { - val classNode = readClass( + ClassNode classNode = readClass( "private String name;"); assertEquals( @@ -73,13 +74,13 @@ public class JavaReaderTests { } private void canReadFieldReference(String expression) { - val classNode = readClass( + ClassNode classNode = readClass( "private String name;" + "public String getName() {" + " return " + expression + ";" + "}"); - val returnNode = (ReturnNode) classNode.getMethods().get(0).getBody().get(0); + ReturnNode returnNode = (ReturnNode) classNode.getMethods().get(0).getBody().get(0); assertEquals( fieldAccess( thisReference(TypeName.of("com.example.Example")), @@ -97,11 +98,11 @@ public class JavaReaderTests { @Test public void canReadImplicitInstanceMethodCalls() { - val classNode = readClass( + ClassNode classNode = readClass( "public String loop() {" + " return loop();" + "}"); - val returnNode = (ReturnNode) classNode.getMethods().get(0).getBody().get(0); + ReturnNode returnNode = (ReturnNode) classNode.getMethods().get(0).getBody().get(0); assertEquals( methodCall( @@ -121,11 +122,11 @@ public class JavaReaderTests { @Test public void canReadImplicitStaticMethodCalls() { - val classNode = readClass( + ClassNode classNode = readClass( "public static String loop() {" + " return loop();" + "}"); - val returnNode = (ReturnNode) classNode.getMethods().get(0).getBody().get(0); + ReturnNode returnNode = (ReturnNode) classNode.getMethods().get(0).getBody().get(0); assertEquals( staticMethodCall( @@ -151,13 +152,13 @@ public class JavaReaderTests { @Test public void canReadAssignments() { - val classNode = readClass( + ClassNode classNode = readClass( "private String name;" + "public String getName() {" + " return name = \"blah\";" + "}"); - val returnNode = (ReturnNode) classNode.getMethods().get(0).getBody().get(0); + ReturnNode returnNode = (ReturnNode) classNode.getMethods().get(0).getBody().get(0); assertEquals( assign( fieldAccess( @@ -170,13 +171,13 @@ public class JavaReaderTests { @Test public void canDeclareAndReferenceLocalVariables() { - val statements = readStatements("int x = 4; return x;"); + List statements = readStatements("int x = 4; return x;"); - val declaration = (LocalVariableDeclarationNode) statements.get(0); + LocalVariableDeclarationNode declaration = (LocalVariableDeclarationNode) statements.get(0); assertEquals("x", declaration.getName()); assertEquals(IntegerValue.REF, declaration.getType()); assertEquals(literal(4), declaration.getInitialValue()); - val returnNode = (ReturnNode) statements.get(1); + ReturnNode returnNode = (ReturnNode) statements.get(1); assertEquals( reference(declaration), returnNode.getValue()); @@ -184,18 +185,18 @@ public class JavaReaderTests { @Test public void canDeclareAndReferenceArguments() { - val classNode = readClass( + ClassNode classNode = readClass( "public String identity(int value) {" + " return value;" + "}"); - val method = classNode.getMethods().get(0); - val argument = method.getArguments().get(0); + MethodNode method = classNode.getMethods().get(0); + FormalArgumentNode argument = method.getArguments().get(0); assertEquals("value", argument.getName()); assertEquals(TypeName.of("int"), argument.getType()); assertEquals(1, method.getArguments().size()); - val returnNode = (ReturnNode)method.getBody().get(0); + ReturnNode returnNode = (ReturnNode)method.getBody().get(0); assertEquals(reference(argument), returnNode.getValue()); } @@ -212,13 +213,13 @@ public class JavaReaderTests { @Test public void canDeclareConstructor() { - val classNode = readClass( + ClassNode classNode = readClass( "private final String name;" + "public Example() {" + " this.name = \"Flaws\";" + "}"); - val constructor = classNode.getConstructor(); + ConstructorNode constructor = classNode.getConstructor(); assertEquals(asList(), constructor.getArguments()); @@ -234,28 +235,28 @@ public class JavaReaderTests { @Test public void canDeclareStaticMethodWithAnnotation() { - val classNode = readClass( + ClassNode classNode = readClass( "@Deprecated public void doNothing() {}"); - val method = classNode.getMethods().get(0); + MethodNode method = classNode.getMethods().get(0); assertEquals( asList(annotation(TypeName.of("java.lang.Deprecated"))), method.getAnnotations()); } private ExpressionNode readExpressionInInstanceMethod(String expressionSource) { - val javaClass = + String javaClass = "public Object main() {" + " return " + expressionSource + ";" + "}"; - val classNode = readClass(javaClass); - val returnStatement = (ReturnNode) classNode.getMethods().get(0).getBody().get(0); + ClassNode classNode = readClass(javaClass); + ReturnNode returnStatement = (ReturnNode) classNode.getMethods().get(0).getBody().get(0); return returnStatement.getValue(); } private ExpressionNode readExpression(String expressionSource) { - val returnStatement = (ReturnNode) readStatement("return " + expressionSource + ";"); + ReturnNode returnStatement = (ReturnNode) readStatement("return " + expressionSource + ";"); return returnStatement.getValue(); } @@ -264,33 +265,36 @@ public class JavaReaderTests { } private List readStatements(String statementsSource) { - val javaClass = + String javaClass = "public static Object main() {" + statementsSource + "}"; - val classNode = readClass(javaClass); + ClassNode classNode = readClass(javaClass); return classNode.getMethods().get(0).getBody(); } - @SneakyThrows private ClassNode readClass(String classBody) { - val javaClass = + String javaClass = "package com.example;" + "public class Example {" + classBody + "}"; - - val directoryPath = Files.createTempDirectory(null); - val sourcePath = directoryPath.resolve("com/example/Example.java"); try { - Files.createDirectories(directoryPath.resolve("com/example")); - Files.write(sourcePath, asList(javaClass)); - - val reader = new JavaReader(); - return reader.readClassFromFile(directoryPath, sourcePath); - } finally { - deleteRecursively(directoryPath.toFile()); + + Path directoryPath = Files.createTempDirectory(null); + Path sourcePath = directoryPath.resolve("com/example/Example.java"); + try { + Files.createDirectories(directoryPath.resolve("com/example")); + Files.write(sourcePath, asList(javaClass)); + + JavaReader reader = new JavaReader(); + return reader.readClassFromFile(directoryPath, sourcePath); + } finally { + deleteRecursively(directoryPath.toFile()); + } + } catch (Exception exception) { + throw new RuntimeException(exception); } } } diff --git a/src/test/java/org/zwobble/couscous/tests/interpreter/EvaluatorTests.java b/src/test/java/org/zwobble/couscous/tests/interpreter/EvaluatorTests.java index 2231bf0..a80934c 100644 --- a/src/test/java/org/zwobble/couscous/tests/interpreter/EvaluatorTests.java +++ b/src/test/java/org/zwobble/couscous/tests/interpreter/EvaluatorTests.java @@ -6,6 +6,7 @@ import java.util.Optional; import org.junit.Test; import org.zwobble.couscous.ast.ClassNode; import org.zwobble.couscous.ast.ExpressionNode; +import org.zwobble.couscous.ast.FormalArgumentNode; import org.zwobble.couscous.interpreter.ConditionMustBeBoolean; import org.zwobble.couscous.interpreter.Environment; import org.zwobble.couscous.interpreter.JavaProject; @@ -17,6 +18,7 @@ import org.zwobble.couscous.interpreter.UnboundField; import org.zwobble.couscous.interpreter.UnexpectedValueType; import org.zwobble.couscous.interpreter.WrongNumberOfArguments; import org.zwobble.couscous.interpreter.values.IntegerInterpreterValue; +import org.zwobble.couscous.interpreter.values.InterpreterValue; import org.zwobble.couscous.interpreter.values.StringInterpreterValue; import org.zwobble.couscous.tests.BackendEvalTests; import org.zwobble.couscous.values.IntegerValue; @@ -41,23 +43,21 @@ import static org.zwobble.couscous.interpreter.values.InterpreterValues.value; import static org.zwobble.couscous.tests.TestIds.ANY_ID; import static org.zwobble.couscous.tests.util.ExtraAsserts.assertThrows; -import lombok.val; - public class EvaluatorTests extends BackendEvalTests { @Test public void valueOfAssignmentExpressionIsNewValue() { - val arg = formalArg(var(ANY_ID, "x", StringValue.REF)); - val environment = new Environment( + FormalArgumentNode arg = formalArg(var(ANY_ID, "x", StringValue.REF)); + Environment environment = new Environment( new MapBackedProject(ImmutableMap.of()), Optional.empty(), new StackFrameBuilder().declare(arg, value("[initial value]")).build()); - val result = eval(environment, assign(arg, literal("[updated value]"))); + InterpreterValue result = eval(environment, assign(arg, literal("[updated value]"))); assertEquals(new StringInterpreterValue("[updated value]"), result); } @Test public void errorIfConditionIsNotBoolean() { - val exception = assertThrows(ConditionMustBeBoolean.class, + ConditionMustBeBoolean exception = assertThrows(ConditionMustBeBoolean.class, () -> eval(emptyEnvironment(), ternaryConditional(literal(1), literal("T"), literal("F")))); assertEquals(new ConditionMustBeBoolean(new IntegerInterpreterValue(1)), exception); @@ -65,7 +65,7 @@ public class EvaluatorTests extends BackendEvalTests { @Test public void errorIfMethodDoesNotExist() { - val exception = assertThrows(NoSuchMethod.class, + NoSuchMethod exception = assertThrows(NoSuchMethod.class, () -> eval(emptyEnvironment(), methodCall( literal("hello"), @@ -77,7 +77,7 @@ public class EvaluatorTests extends BackendEvalTests { @Test public void errorIfWrongNumberOfArgumentsArePassed() { - val exception = assertThrows(WrongNumberOfArguments.class, + WrongNumberOfArguments exception = assertThrows(WrongNumberOfArguments.class, () -> eval(emptyEnvironment(), methodCall( literal("hello"), @@ -89,7 +89,7 @@ public class EvaluatorTests extends BackendEvalTests { @Test public void errorIfArgumentIsWrongType() { - val exception = assertThrows(UnexpectedValueType.class, + UnexpectedValueType exception = assertThrows(UnexpectedValueType.class, () -> eval(emptyEnvironment(), methodCall( literal("hello"), @@ -101,13 +101,13 @@ public class EvaluatorTests extends BackendEvalTests { @Test public void errorIfConstructorArgumentIsWrongType() { - val argument = formalArg(var(ANY_ID, "x", IntegerValue.REF)); - val classNode = ClassNode.builder("com.example.Example") + FormalArgumentNode argument = formalArg(var(ANY_ID, "x", IntegerValue.REF)); + ClassNode classNode = ClassNode.builder("com.example.Example") .constructor(constructor -> constructor .argument(argument)) .build(); - val exception = assertThrows(UnexpectedValueType.class, + UnexpectedValueType exception = assertThrows(UnexpectedValueType.class, () -> evalExpression( asList(classNode), constructorCall( @@ -119,10 +119,10 @@ public class EvaluatorTests extends BackendEvalTests { @Test public void cannotGetValueOfUndeclaredField() { - val classNode = ClassNode.builder("com.example.Example") + ClassNode classNode = ClassNode.builder("com.example.Example") .build(); - val exception = assertThrows(NoSuchField.class, + NoSuchField exception = assertThrows(NoSuchField.class, () -> evalExpression( asList(classNode), fieldAccess( @@ -137,11 +137,11 @@ public class EvaluatorTests extends BackendEvalTests { @Test public void cannotGetValueOfUnbounddField() { - val classNode = ClassNode.builder("com.example.Example") + ClassNode classNode = ClassNode.builder("com.example.Example") .field("value", IntegerValue.REF) .build(); - val exception = assertThrows(UnboundField.class, + UnboundField exception = assertThrows(UnboundField.class, () -> evalExpression( asList(classNode), fieldAccess( @@ -156,14 +156,14 @@ public class EvaluatorTests extends BackendEvalTests { @Test public void cannotSetValueOfUndeclaredField() { - val classNode = ClassNode.builder("com.example.Example") + ClassNode classNode = ClassNode.builder("com.example.Example") .constructor(constructor -> constructor .statement(assignStatement( fieldAccess(constructor.thisReference(), "value", IntegerValue.REF), literal(42)))) .build(); - val exception = assertThrows(NoSuchField.class, + NoSuchField exception = assertThrows(NoSuchField.class, () -> evalExpression( asList(classNode), constructorCall( @@ -175,7 +175,7 @@ public class EvaluatorTests extends BackendEvalTests { @Test public void cannotSetValueOfFieldWithWrongType() { - val classNode = ClassNode.builder("com.example.Example") + ClassNode classNode = ClassNode.builder("com.example.Example") .field("value", IntegerValue.REF) .constructor(constructor -> constructor .statement(assignStatement( @@ -183,7 +183,7 @@ public class EvaluatorTests extends BackendEvalTests { literal("")))) .build(); - val exception = assertThrows(UnexpectedValueType.class, + UnexpectedValueType exception = assertThrows(UnexpectedValueType.class, () -> evalExpression( asList(classNode), constructorCall( @@ -205,7 +205,7 @@ public class EvaluatorTests extends BackendEvalTests { List classes, ExpressionNode expression) { - val environment = new Environment( + Environment environment = new Environment( JavaProject.of(classes), Optional.empty(), ImmutableMap.of()); diff --git a/src/test/java/org/zwobble/couscous/tests/interpreter/InterpreterMethodTests.java b/src/test/java/org/zwobble/couscous/tests/interpreter/InterpreterMethodTests.java index 118d657..50188ce 100644 --- a/src/test/java/org/zwobble/couscous/tests/interpreter/InterpreterMethodTests.java +++ b/src/test/java/org/zwobble/couscous/tests/interpreter/InterpreterMethodTests.java @@ -5,14 +5,19 @@ import java.util.stream.Collectors; import org.junit.Test; import org.zwobble.couscous.ast.ClassNode; +import org.zwobble.couscous.ast.FormalArgumentNode; import org.zwobble.couscous.ast.LiteralNode; +import org.zwobble.couscous.ast.LocalVariableDeclarationNode; +import org.zwobble.couscous.ast.MethodNode; import org.zwobble.couscous.ast.TypeName; import org.zwobble.couscous.interpreter.Interpreter; import org.zwobble.couscous.interpreter.JavaProject; +import org.zwobble.couscous.interpreter.Project; import org.zwobble.couscous.interpreter.UnboundVariable; import org.zwobble.couscous.interpreter.UnexpectedValueType; import org.zwobble.couscous.interpreter.VariableNotInScope; import org.zwobble.couscous.interpreter.WrongNumberOfArguments; +import org.zwobble.couscous.interpreter.values.InterpreterValue; import org.zwobble.couscous.interpreter.values.InterpreterValues; import org.zwobble.couscous.tests.BackendMethodTests; import org.zwobble.couscous.tests.MethodRunner; @@ -34,14 +39,12 @@ import static org.zwobble.couscous.tests.TestIds.ANY_ID; import static org.zwobble.couscous.tests.util.ExtraAsserts.assertThrows; import static org.zwobble.couscous.values.PrimitiveValues.value; -import lombok.val; - public class InterpreterMethodTests extends BackendMethodTests { @Test public void errorIfWrongNumberOfArgumentsArePassed() { - val method = staticMethod("hello"); + MethodNode.Builder method = staticMethod("hello"); - val exception = assertThrows(WrongNumberOfArguments.class, + WrongNumberOfArguments exception = assertThrows(WrongNumberOfArguments.class, () -> runMethod(method, value("hello, world!"))); assertEquals(new WrongNumberOfArguments(0, 1), exception); @@ -49,12 +52,12 @@ public class InterpreterMethodTests extends BackendMethodTests { @Test public void errorIfTryingToAssignValueOfWrongTypeToVariable() { - val arg = formalArg(var(ANY_ID, "x", StringValue.REF)); - val method = staticMethod("hello") + FormalArgumentNode arg = formalArg(var(ANY_ID, "x", StringValue.REF)); + MethodNode.Builder method = staticMethod("hello") .argument(arg) .statement(expressionStatement(assign(reference(arg), literal(0)))); - val exception = assertThrows(UnexpectedValueType.class, + UnexpectedValueType exception = assertThrows(UnexpectedValueType.class, () -> runMethod(method, value(""))); assertEquals(new UnexpectedValueType(StringValue.REF, IntegerValue.REF), exception); @@ -62,12 +65,12 @@ public class InterpreterMethodTests extends BackendMethodTests { @Test public void errorIfTryingToAssignToVariableNotInScope() { - val localVariableDeclaration = localVariableDeclaration( + LocalVariableDeclarationNode localVariableDeclaration = localVariableDeclaration( ANY_ID, "x", StringValue.REF, literal("")); - val method = staticMethod("hello") + MethodNode.Builder method = staticMethod("hello") .statement(expressionStatement(assign(reference(localVariableDeclaration), LiteralNode.literal("[updated value]")))); - val exception = assertThrows(VariableNotInScope.class, + VariableNotInScope exception = assertThrows(VariableNotInScope.class, () -> runMethod(method)); assertEquals(new VariableNotInScope(ANY_ID), exception); @@ -75,12 +78,12 @@ public class InterpreterMethodTests extends BackendMethodTests { @Test public void errorIfTryingToGetValueOfVariableNotInScope() { - val localVariableDeclaration = localVariableDeclaration( + LocalVariableDeclarationNode localVariableDeclaration = localVariableDeclaration( ANY_ID, "x", StringValue.REF, literal("")); - val method = staticMethod("hello") + MethodNode.Builder method = staticMethod("hello") .statement(returns(reference(localVariableDeclaration))); - val exception = assertThrows(VariableNotInScope.class, + VariableNotInScope exception = assertThrows(VariableNotInScope.class, () -> runMethod(method)); assertEquals(new VariableNotInScope(ANY_ID), exception); @@ -88,13 +91,13 @@ public class InterpreterMethodTests extends BackendMethodTests { @Test public void errorIfTryingToGetValueOfUnboundVariable() { - val localVariableDeclaration = localVariableDeclaration( + LocalVariableDeclarationNode localVariableDeclaration = localVariableDeclaration( ANY_ID, "x", StringValue.REF, literal("")); - val method = staticMethod("hello") + MethodNode.Builder method = staticMethod("hello") .statement(returns(reference(localVariableDeclaration))) .statement(localVariableDeclaration); - val exception = assertThrows(UnboundVariable.class, + UnboundVariable exception = assertThrows(UnboundVariable.class, () -> runMethod(method)); assertEquals(new UnboundVariable(ANY_ID), exception); @@ -110,9 +113,9 @@ public class InterpreterMethodTests extends BackendMethodTests { String methodName, List arguments) { - val project = JavaProject.of(classNodes); - val interpreter = new Interpreter(project); - val argumentValues = arguments.stream() + Project project = JavaProject.of(classNodes); + Interpreter interpreter = new Interpreter(project); + List argumentValues = arguments.stream() .map(InterpreterValues::value) .collect(Collectors.toList()); diff --git a/src/test/java/org/zwobble/couscous/tests/util/ExtraAsserts.java b/src/test/java/org/zwobble/couscous/tests/util/ExtraAsserts.java index c5f1668..e620d7f 100644 --- a/src/test/java/org/zwobble/couscous/tests/util/ExtraAsserts.java +++ b/src/test/java/org/zwobble/couscous/tests/util/ExtraAsserts.java @@ -3,15 +3,12 @@ package org.zwobble.couscous.tests.util; import org.zwobble.couscous.util.Action; import org.zwobble.couscous.util.Casts; -import lombok.SneakyThrows; - public class ExtraAsserts { - @SneakyThrows - public static T assertThrows(Class exceptionType, Action action) { + public static T assertThrows(Class exceptionType, Action action) throws T { try { action.run(); throw new AssertionError("Expected exception"); - } catch (Exception exception) { + } catch (RuntimeException exception) { return Casts.tryCast(exceptionType, exception) .orElseThrow(() -> exception); } diff --git a/src/test/java/org/zwobble/couscous/tests/util/ExtraFiles.java b/src/test/java/org/zwobble/couscous/tests/util/ExtraFiles.java index 032e22c..339a084 100644 --- a/src/test/java/org/zwobble/couscous/tests/util/ExtraFiles.java +++ b/src/test/java/org/zwobble/couscous/tests/util/ExtraFiles.java @@ -2,15 +2,13 @@ package org.zwobble.couscous.tests.util; import java.io.File; -import lombok.val; - public class ExtraFiles { public static void deleteRecursively(File file) { if (file.isDirectory()) { - for (val child : file.listFiles()) { + for (File child : file.listFiles()) { deleteRecursively(child); } } file.delete(); } -} +} \ No newline at end of file -- cgit v1.2.3