You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@plc4x.apache.org by jf...@apache.org on 2019/05/04 15:47:37 UTC

[plc4x] 01/02: Code generator is able to build Classes.

This is an automated email from the ASF dual-hosted git repository.

jfeinauer pushed a commit to branch feature/code-gen
in repository https://gitbox.apache.org/repos/asf/plc4x.git

commit 4e8ef998f7379f44c05103ec8e1bb9e832a1a2c8
Author: Julian Feinauer <j....@pragmaticminds.de>
AuthorDate: Sat May 4 17:21:47 2019 +0200

    Code generator is able to build Classes.
---
 .../plc4x/codegen/version2/AbstractNode.java       |  14 ++
 .../codegen/version2/AssignementExpression.java    |  29 +++
 .../plc4x/codegen/version2/BinaryExpression.java   |  43 ++++
 .../org/apache/plc4x/codegen/version2/Block.java   |  29 +++
 .../plc4x/codegen/version2/CallExpression.java     |  44 ++++
 .../plc4x/codegen/version2/ClassDefinition.java    |  29 +++
 .../apache/plc4x/codegen/version2/CodeWriter.java  |  57 +++++
 .../codegen/version2/ConditionalStatement.java     |  16 ++
 .../plc4x/codegen/version2/ConstantNode.java       |  24 +++
 .../codegen/version2/ConstructorDeclaration.java   |  18 ++
 .../codegen/version2/DeclarationStatement.java     |  33 +++
 .../apache/plc4x/codegen/version2/Expression.java  |   9 +
 .../plc4x/codegen/version2/FieldDeclaration.java   |  20 ++
 .../plc4x/codegen/version2/FieldReference.java     |  16 ++
 .../apache/plc4x/codegen/version2/Generator.java   |  42 ++++
 .../apache/plc4x/codegen/version2/IfStatement.java |  36 ++++
 .../plc4x/codegen/version2/JavaGenerator.java      | 221 +++++++++++++++++++
 .../org/apache/plc4x/codegen/version2/Method.java  |  51 +++++
 .../plc4x/codegen/version2/MethodDefinition.java   |  42 ++++
 .../plc4x/codegen/version2/NewExpression.java      |  26 +++
 .../org/apache/plc4x/codegen/version2/Node.java    |   9 +
 .../apache/plc4x/codegen/version2/NodeVisitor.java |  10 +
 .../codegen/version2/ParameterExpression.java      |  23 ++
 .../plc4x/codegen/version2/PhpGenerator.java       |  89 ++++++++
 .../apache/plc4x/codegen/version2/Primitive.java   |  19 ++
 .../plc4x/codegen/version2/ReturnStatement.java    |  22 ++
 .../apache/plc4x/codegen/version2/Statement.java   |   4 +
 .../apache/plc4x/codegen/version2/TypeNode.java    |  17 ++
 .../apache/plc4x/codegen/version2/TypeUtil.java    |  11 +
 .../plc4x/codegen/version2/JavaGeneratorTest.java  | 236 +++++++++++++++++++++
 .../plc4x/codegen/version2/PhpGeneratorTest.java   |  23 ++
 31 files changed, 1262 insertions(+)

diff --git a/sandbox/code-gen/src/main/java/org/apache/plc4x/codegen/version2/AbstractNode.java b/sandbox/code-gen/src/main/java/org/apache/plc4x/codegen/version2/AbstractNode.java
new file mode 100644
index 0000000..abf44ae
--- /dev/null
+++ b/sandbox/code-gen/src/main/java/org/apache/plc4x/codegen/version2/AbstractNode.java
@@ -0,0 +1,14 @@
+package org.apache.plc4x.codegen.version2;
+
+public abstract class AbstractNode implements Node {
+
+    public final TypeNode type;
+
+    protected AbstractNode(TypeNode type) {
+        this.type = type;
+    }
+
+    public TypeNode getType() {
+        return this.type;
+    }
+}
diff --git a/sandbox/code-gen/src/main/java/org/apache/plc4x/codegen/version2/AssignementExpression.java b/sandbox/code-gen/src/main/java/org/apache/plc4x/codegen/version2/AssignementExpression.java
new file mode 100644
index 0000000..9544eed
--- /dev/null
+++ b/sandbox/code-gen/src/main/java/org/apache/plc4x/codegen/version2/AssignementExpression.java
@@ -0,0 +1,29 @@
+package org.apache.plc4x.codegen.version2;
+
+public class AssignementExpression extends Expression {
+
+    private final Expression target;
+    private final Node value;
+
+    protected AssignementExpression(Expression target, Node value) {
+        super(target.getType());
+        this.target = target;
+        this.value = value;
+    }
+
+    public Node getTarget() {
+        return target;
+    }
+
+    public Node getValue() {
+        return value;
+    }
+
+    @Override public <T> T accept(NodeVisitor<T> visitor) {
+        return null;
+    }
+
+    @Override public void write(Generator writer) {
+        writer.generate(this);
+    }
+}
diff --git a/sandbox/code-gen/src/main/java/org/apache/plc4x/codegen/version2/BinaryExpression.java b/sandbox/code-gen/src/main/java/org/apache/plc4x/codegen/version2/BinaryExpression.java
new file mode 100644
index 0000000..0aef957
--- /dev/null
+++ b/sandbox/code-gen/src/main/java/org/apache/plc4x/codegen/version2/BinaryExpression.java
@@ -0,0 +1,43 @@
+package org.apache.plc4x.codegen.version2;
+
+public class BinaryExpression extends Expression {
+
+    private final Node left;
+    private final Node right;
+    private final Operation op;
+
+    protected BinaryExpression(TypeNode type, Node left, Node right, Operation op) {
+        super(type);
+        this.left = left;
+        this.right = right;
+        this.op = op;
+    }
+
+    public Node getLeft() {
+        return left;
+    }
+
+    public Node getRight() {
+        return right;
+    }
+
+    public Operation getOp() {
+        return op;
+    }
+
+    @Override public <T> T accept(NodeVisitor<T> visitor) {
+        return null;
+    }
+
+    @Override public void write(Generator writer) {
+        writer.generate(this);
+    }
+
+    public enum Operation {
+        EQ,
+        NEQ,
+        GT,
+        LT,
+        PLUS;
+    }
+}
diff --git a/sandbox/code-gen/src/main/java/org/apache/plc4x/codegen/version2/Block.java b/sandbox/code-gen/src/main/java/org/apache/plc4x/codegen/version2/Block.java
new file mode 100644
index 0000000..dff5888
--- /dev/null
+++ b/sandbox/code-gen/src/main/java/org/apache/plc4x/codegen/version2/Block.java
@@ -0,0 +1,29 @@
+package org.apache.plc4x.codegen.version2;
+
+import java.util.Arrays;
+import java.util.List;
+
+public class Block extends Statement {
+
+    private final List<Node> statements;
+
+    public Block(List<Node> statements) {
+        this.statements = statements;
+    }
+
+    public Block(Node... statements) {
+        this(Arrays.asList(statements));
+    }
+
+    public List<Node> getStatements() {
+        return statements;
+    }
+
+    @Override public <T> T accept(NodeVisitor<T> visitor) {
+        return null;
+    }
+
+    @Override public void write(Generator writer) {
+        writer.writeBlock(this);
+    }
+}
diff --git a/sandbox/code-gen/src/main/java/org/apache/plc4x/codegen/version2/CallExpression.java b/sandbox/code-gen/src/main/java/org/apache/plc4x/codegen/version2/CallExpression.java
new file mode 100644
index 0000000..d3060a7
--- /dev/null
+++ b/sandbox/code-gen/src/main/java/org/apache/plc4x/codegen/version2/CallExpression.java
@@ -0,0 +1,44 @@
+package org.apache.plc4x.codegen.version2;
+
+import java.util.Arrays;
+import java.util.List;
+
+public class CallExpression extends Expression {
+
+    private final Method method;
+    private final Node target;
+    private final List<Node> arguments;
+
+    /**
+     * Static Method ==> target == null
+     * @param method
+     * @param target
+     * @param arguments
+     */
+    public CallExpression(Method method, Node target, Node... arguments) {
+        super(method.getReturnType());
+        this.method = method;
+        this.target = target;
+        this.arguments = Arrays.asList(arguments);
+    }
+
+    public Method getMethod() {
+        return method;
+    }
+
+    public Node getTarget() {
+        return target;
+    }
+
+    @Override public <T> T accept(NodeVisitor<T> visitor) {
+        return null;
+    }
+
+    @Override public void write(Generator writer) {
+        if (target == null) {
+            writer.generateStaticCall(method, arguments);
+        } else {
+            writer.generateCall(target, method, arguments);
+        }
+    }
+}
diff --git a/sandbox/code-gen/src/main/java/org/apache/plc4x/codegen/version2/ClassDefinition.java b/sandbox/code-gen/src/main/java/org/apache/plc4x/codegen/version2/ClassDefinition.java
new file mode 100644
index 0000000..76c33a7
--- /dev/null
+++ b/sandbox/code-gen/src/main/java/org/apache/plc4x/codegen/version2/ClassDefinition.java
@@ -0,0 +1,29 @@
+package org.apache.plc4x.codegen.version2;
+
+import java.util.List;
+
+public class ClassDefinition implements Node {
+
+    private final String namespace;
+    private final String className;
+
+    private final List<FieldDeclaration> fields;
+    private final List<ConstructorDeclaration> constructors;
+    private final List<MethodDefinition> methods;
+
+    public ClassDefinition(String namespace, String className, List<FieldDeclaration> fields, List<ConstructorDeclaration> constructors, List<MethodDefinition> methods) {
+        this.namespace = namespace;
+        this.className = className;
+        this.fields = fields;
+        this.constructors = constructors;
+        this.methods = methods;
+    }
+
+    @Override public <T> T accept(NodeVisitor<T> visitor) {
+        return null;
+    }
+
+    @Override public void write(Generator writer) {
+        writer.generateClass(this.namespace, this.className, this.fields, this.constructors, this.methods);
+    }
+}
diff --git a/sandbox/code-gen/src/main/java/org/apache/plc4x/codegen/version2/CodeWriter.java b/sandbox/code-gen/src/main/java/org/apache/plc4x/codegen/version2/CodeWriter.java
new file mode 100644
index 0000000..a2e897e
--- /dev/null
+++ b/sandbox/code-gen/src/main/java/org/apache/plc4x/codegen/version2/CodeWriter.java
@@ -0,0 +1,57 @@
+package org.apache.plc4x.codegen.version2;
+
+import java.util.stream.IntStream;
+
+/**
+ * Helper class to print code.
+ */
+public class CodeWriter {
+
+    private StringBuffer buffer = new StringBuffer();
+    private int tabSize;
+
+    private int intendationLvl = 0;
+
+    public CodeWriter(int tabSize) {
+        this.tabSize = tabSize;
+    }
+
+    public void startBlock() {
+        this.intendationLvl += tabSize;
+    }
+
+    public void endBlock() {
+        if (intendationLvl < tabSize) {
+            throw new RuntimeException("Closing a Block which is not open!");
+        }
+        this.intendationLvl -= tabSize;
+    }
+
+    public void write(String s) {
+        buffer.append(s);
+    }
+
+    public void startLine(String s) {
+        writeIntendation();
+        write(s);
+    }
+
+    public void endLine() {
+        buffer.append("\n");
+    }
+
+    public void writeLine(String s) {
+        writeIntendation();
+        buffer.append(s);
+        buffer.append("\n");
+    }
+
+    private void writeIntendation() {
+        // Write the intendation
+        IntStream.range(0, intendationLvl).forEach(i -> buffer.append(" "));
+    }
+
+    public String getCode() {
+        return buffer.toString();
+    }
+}
diff --git a/sandbox/code-gen/src/main/java/org/apache/plc4x/codegen/version2/ConditionalStatement.java b/sandbox/code-gen/src/main/java/org/apache/plc4x/codegen/version2/ConditionalStatement.java
new file mode 100644
index 0000000..9a381b1
--- /dev/null
+++ b/sandbox/code-gen/src/main/java/org/apache/plc4x/codegen/version2/ConditionalStatement.java
@@ -0,0 +1,16 @@
+package org.apache.plc4x.codegen.version2;
+
+public class ConditionalStatement extends Expression {
+
+    protected ConditionalStatement(TypeNode type) {
+        super(type);
+    }
+
+    @Override public <T> T accept(NodeVisitor<T> visitor) {
+        return null;
+    }
+
+    @Override public void write(Generator writer) {
+
+    }
+}
diff --git a/sandbox/code-gen/src/main/java/org/apache/plc4x/codegen/version2/ConstantNode.java b/sandbox/code-gen/src/main/java/org/apache/plc4x/codegen/version2/ConstantNode.java
new file mode 100644
index 0000000..df43f3c
--- /dev/null
+++ b/sandbox/code-gen/src/main/java/org/apache/plc4x/codegen/version2/ConstantNode.java
@@ -0,0 +1,24 @@
+package org.apache.plc4x.codegen.version2;
+
+public class ConstantNode extends Expression {
+
+    private Object value;
+
+    public ConstantNode(Object value) {
+        super(TypeUtil.infer(value));
+        this.value = value;
+    }
+
+    public Object getValue() {
+        return value;
+    }
+
+    @Override public <T> T accept(NodeVisitor<T> visitor) {
+        return visitor.visit(this);
+    }
+
+    @Override public void write(Generator generator) {
+        generator.generate(this);
+    }
+
+}
diff --git a/sandbox/code-gen/src/main/java/org/apache/plc4x/codegen/version2/ConstructorDeclaration.java b/sandbox/code-gen/src/main/java/org/apache/plc4x/codegen/version2/ConstructorDeclaration.java
new file mode 100644
index 0000000..084d548
--- /dev/null
+++ b/sandbox/code-gen/src/main/java/org/apache/plc4x/codegen/version2/ConstructorDeclaration.java
@@ -0,0 +1,18 @@
+package org.apache.plc4x.codegen.version2;
+
+import java.util.List;
+
+public class ConstructorDeclaration extends MethodDefinition {
+
+    public ConstructorDeclaration(List<ParameterExpression> parameters, Block body) {
+        super(null, null, parameters, body);
+    }
+
+    @Override public <T> T accept(NodeVisitor<T> visitor) {
+        return null;
+    }
+
+    @Override public void write(Generator writer) {
+        throw new UnsupportedOperationException("This should be called by the Class Implementor!");
+    }
+}
diff --git a/sandbox/code-gen/src/main/java/org/apache/plc4x/codegen/version2/DeclarationStatement.java b/sandbox/code-gen/src/main/java/org/apache/plc4x/codegen/version2/DeclarationStatement.java
new file mode 100644
index 0000000..cfc5b06
--- /dev/null
+++ b/sandbox/code-gen/src/main/java/org/apache/plc4x/codegen/version2/DeclarationStatement.java
@@ -0,0 +1,33 @@
+package org.apache.plc4x.codegen.version2;
+
+public class DeclarationStatement extends Statement {
+
+    public final ParameterExpression parameterExpression;
+    public final Expression initializer;
+
+    public DeclarationStatement(ParameterExpression parameterExpression, Expression initializer) {
+        this.parameterExpression = parameterExpression;
+        this.initializer = initializer;
+    }
+
+    public ParameterExpression getParameterExpression() {
+        return parameterExpression;
+    }
+
+    public Expression getInitializer() {
+        return initializer;
+    }
+
+    @Override public <T> T accept(NodeVisitor<T> visitor) {
+        return visitor.visit(this);
+    }
+
+    @Override public void write(Generator generator) {
+        if (initializer != null) {
+            generator.generateDeclarationWithInitializer(this);
+        } else {
+            generator.generateDeclaration(this);
+        }
+    }
+
+}
diff --git a/sandbox/code-gen/src/main/java/org/apache/plc4x/codegen/version2/Expression.java b/sandbox/code-gen/src/main/java/org/apache/plc4x/codegen/version2/Expression.java
new file mode 100644
index 0000000..77bd812
--- /dev/null
+++ b/sandbox/code-gen/src/main/java/org/apache/plc4x/codegen/version2/Expression.java
@@ -0,0 +1,9 @@
+package org.apache.plc4x.codegen.version2;
+
+public abstract class Expression extends AbstractNode {
+
+    protected Expression(TypeNode type) {
+        super(type);
+    }
+
+}
diff --git a/sandbox/code-gen/src/main/java/org/apache/plc4x/codegen/version2/FieldDeclaration.java b/sandbox/code-gen/src/main/java/org/apache/plc4x/codegen/version2/FieldDeclaration.java
new file mode 100644
index 0000000..c4f8790
--- /dev/null
+++ b/sandbox/code-gen/src/main/java/org/apache/plc4x/codegen/version2/FieldDeclaration.java
@@ -0,0 +1,20 @@
+package org.apache.plc4x.codegen.version2;
+
+public class FieldDeclaration implements Node {
+
+    private final TypeNode type;
+    private final String name;
+
+    public FieldDeclaration(TypeNode type, String name) {
+        this.type = type;
+        this.name = name;
+    }
+
+    @Override public <T> T accept(NodeVisitor<T> visitor) {
+        return null;
+    }
+
+    @Override public void write(Generator writer) {
+        writer.generateFieldDeclaration(type, name);
+    }
+}
diff --git a/sandbox/code-gen/src/main/java/org/apache/plc4x/codegen/version2/FieldReference.java b/sandbox/code-gen/src/main/java/org/apache/plc4x/codegen/version2/FieldReference.java
new file mode 100644
index 0000000..7ae8759
--- /dev/null
+++ b/sandbox/code-gen/src/main/java/org/apache/plc4x/codegen/version2/FieldReference.java
@@ -0,0 +1,16 @@
+package org.apache.plc4x.codegen.version2;
+
+public class FieldReference extends ParameterExpression {
+
+    public FieldReference(TypeNode type, String name) {
+        super(type, name);
+    }
+
+    @Override public <T> T accept(NodeVisitor<T> visitor) {
+        return null;
+    }
+
+    @Override public void write(Generator writer) {
+        writer.generateFieldReference(type, getName());
+    }
+}
diff --git a/sandbox/code-gen/src/main/java/org/apache/plc4x/codegen/version2/Generator.java b/sandbox/code-gen/src/main/java/org/apache/plc4x/codegen/version2/Generator.java
new file mode 100644
index 0000000..687164a
--- /dev/null
+++ b/sandbox/code-gen/src/main/java/org/apache/plc4x/codegen/version2/Generator.java
@@ -0,0 +1,42 @@
+package org.apache.plc4x.codegen.version2;
+
+import java.util.List;
+
+public interface Generator {
+
+    void generate(ConstantNode constantNode);
+
+    void generateDeclarationWithInitializer(DeclarationStatement declarationStatement);
+
+    void generateDeclaration(DeclarationStatement declarationStatement);
+
+    void generate(ParameterExpression parameterExpression);
+
+    void generate(Primitive primitive);
+
+    void generate(IfStatement ifStatement);
+
+    void writeBlock(Block statements);
+
+    void generate(BinaryExpression binaryExpression);
+
+    void generate(AssignementExpression assignementExpression);
+
+    void generateStaticCall(Method method, List<Node> constantNode);
+
+    void generateCall(Node target, Method method, List<Node> constantNode);
+
+    void generate(NewExpression newExpression);
+
+    void generate(MethodDefinition methodDefinition);
+
+    void generateReturn(Expression value);
+
+    void generateClass(String namespace, String className, List<FieldDeclaration> fields, List<ConstructorDeclaration> constructors, List<MethodDefinition> methods);
+
+    void generateFieldDeclaration(TypeNode type, String name);
+
+    void generateFieldReference(TypeNode type, String name);
+
+    void generateConstructor(String className, List<ParameterExpression> parameters, Block body);
+}
diff --git a/sandbox/code-gen/src/main/java/org/apache/plc4x/codegen/version2/IfStatement.java b/sandbox/code-gen/src/main/java/org/apache/plc4x/codegen/version2/IfStatement.java
new file mode 100644
index 0000000..e984f9b
--- /dev/null
+++ b/sandbox/code-gen/src/main/java/org/apache/plc4x/codegen/version2/IfStatement.java
@@ -0,0 +1,36 @@
+package org.apache.plc4x.codegen.version2;
+
+public class IfStatement extends Statement {
+
+    private Expression condition;
+    private Block body;
+    private Block orElse;
+
+    public IfStatement(Expression condition, Block body, Block orElse) {
+        // Check condition returns Binary
+        this.condition = condition;
+        this.body = body;
+        this.orElse = orElse;
+    }
+
+    public Expression getCondition() {
+        return condition;
+    }
+
+    public Block getBody() {
+        return body;
+    }
+
+    public Block getOrElse() {
+        return orElse;
+    }
+
+    @Override public <T> T accept(NodeVisitor<T> visitor) {
+        return null;
+    }
+
+    @Override public void write(Generator writer) {
+        writer.generate(this);
+    }
+
+}
diff --git a/sandbox/code-gen/src/main/java/org/apache/plc4x/codegen/version2/JavaGenerator.java b/sandbox/code-gen/src/main/java/org/apache/plc4x/codegen/version2/JavaGenerator.java
new file mode 100644
index 0000000..665500e
--- /dev/null
+++ b/sandbox/code-gen/src/main/java/org/apache/plc4x/codegen/version2/JavaGenerator.java
@@ -0,0 +1,221 @@
+package org.apache.plc4x.codegen.version2;
+
+import java.util.List;
+
+public class JavaGenerator implements Generator {
+
+    private final CodeWriter writer;
+
+    public JavaGenerator(CodeWriter writer) {
+        this.writer = writer;
+    }
+
+    @Override public void generate(ConstantNode constantNode) {
+        writer.write(constantNode.getValue().toString());
+    }
+
+    @Override public void generateDeclarationWithInitializer(DeclarationStatement declarationStatement) {
+        declarationStatement.getParameterExpression().getType().write(this);
+        writer.write(" ");
+        declarationStatement.getParameterExpression().write(this);
+        writer.write(" = ");
+        declarationStatement.getInitializer().write(this);
+    }
+
+    @Override public void generateDeclaration(DeclarationStatement declarationStatement) {
+        declarationStatement.getParameterExpression().getType().write(this);
+        writer.write(" ");
+        declarationStatement.getParameterExpression().write(this);
+    }
+
+    @Override public void generate(ParameterExpression parameterExpression) {
+        writer.write(parameterExpression.getName());
+    }
+
+    @Override public void generate(Primitive primitive) {
+        writer.write(primitive.getTypeString());
+    }
+
+    @Override public void generate(IfStatement ifStatement) {
+        writer.startLine("if (");
+        ifStatement.getCondition().write(this);
+        writer.write(") {\n");
+        writeBlock(ifStatement.getBody());
+        if (ifStatement.getOrElse() != null) {
+            writer.writeLine("} else {");
+            writeBlock(ifStatement.getOrElse());
+        }
+        writer.writeLine("}");
+    }
+
+    @Override public void writeBlock(Block statements) {
+        writer.startBlock();
+        for (Node statement : statements.getStatements()) {
+            // Dont to the wrapping for Statemetns
+            if (statement instanceof IfStatement) {
+                statement.write(this);
+            } else {
+                writer.startLine("");
+                statement.write(this);
+                writer.write(";");
+                writer.endLine();
+            }
+        }
+        writer.endBlock();
+    }
+
+    @Override public void generate(BinaryExpression binaryExpression) {
+        binaryExpression.getLeft().write(this);
+        writer.write(" ");
+        writer.write(getOperator(binaryExpression.getOp()));
+        writer.write(" ");
+        binaryExpression.getRight().write(this);
+    }
+
+    @Override public void generate(AssignementExpression assignementExpression) {
+        assignementExpression.getTarget().write(this);
+        writer.write(" = ");
+        assignementExpression.getValue().write(this);
+    }
+
+    @Override public void generateStaticCall(Method method, List<Node> arguments) {
+        writer.write(method.getType().getTypeString());
+        writer.write(".");
+        writer.write(method.getName());
+        writer.write("(");
+        generateArgumentList(arguments);
+        writer.write(")");
+    }
+
+    private void generateArgumentList(List<Node> arguments) {
+        for (int i = 0; i < arguments.size(); i++) {
+            arguments.get(i).write(this);
+            if (i < arguments.size() - 1) {
+                writer.write(", ");
+            }
+        }
+    }
+
+    @Override public void generateCall(Node target, Method method, List<Node> arguments) {
+        target.write(this);
+        writer.write(".");
+        writer.write(method.getName());
+        writer.write("(");
+        generateArgumentList(arguments);
+        writer.write(")");
+    }
+
+    @Override public void generate(NewExpression newExpression) {
+        writer.write("new ");
+        newExpression.getType().write(this);
+        writer.write("(");
+        generateArgumentList(newExpression.getArguments());
+        writer.write(")");
+    }
+
+    @Override public void generate(MethodDefinition methodDefinition) {
+        writer.startLine("public ");
+        // Special handling of VOID is necessary
+        if (methodDefinition.getResultType() == Primitive.VOID) {
+            writer.write("void");
+        } else {
+            methodDefinition.getResultType().write(this);
+        }
+        writer.write(" ");
+        writer.write(methodDefinition.getName());
+        writer.write("(");
+        for (int i = 0; i < methodDefinition.getParameters().size(); i++) {
+            methodDefinition.getParameters().get(i).getType().write(this);
+            writer.write(" ");
+            methodDefinition.getParameters().get(i).write(this);
+            if (i < methodDefinition.getParameters().size() - 1) {
+                writer.write(", ");
+            }
+        }
+        writer.write(") {");
+        writer.endLine();
+        methodDefinition.getBody().write(this);
+        writer.writeLine("}");
+    }
+
+    @Override public void generateReturn(Expression value) {
+        writer.write("return ");
+        value.write(this);
+    }
+
+    @Override public void generateClass(String namespace, String className, List<FieldDeclaration> fields, List<ConstructorDeclaration> constructors, List<MethodDefinition> methods) {
+        // Add static?!
+        // Own File?
+        writer.write("public class ");
+        writer.write(className);
+        // TODO extends / implements
+        writer.write(" {");
+        writer.endLine();
+        writer.startBlock();
+
+        writer.writeLine("");
+        // Fields
+        for (FieldDeclaration field : fields) {
+            field.write(this);
+            writer.writeLine("");
+        }
+
+        // Constructors
+        for (ConstructorDeclaration constructor : constructors) {
+            this.generateConstructor(className, constructor.getParameters(), constructor.getBody());
+            writer.writeLine("");
+        }
+
+        // Methods
+        for (MethodDefinition method : methods) {
+            method.write(this);
+            writer.writeLine("");
+        }
+
+        writer.endBlock();
+        writer.write("}");
+        writer.endLine();
+    }
+
+    @Override public void generateFieldDeclaration(TypeNode type, String name) {
+        writer.startLine("public ");
+        type.write(this);
+        writer.write(" ");
+        writer.write(name);
+        writer.write(";");
+        writer.endLine();
+    }
+
+    @Override public void generateFieldReference(TypeNode type, String name) {
+        writer.write("this.");
+        writer.write(name);
+    }
+
+    @Override public void generateConstructor(String className, List<ParameterExpression> parameters, Block body) {
+        writer.startLine("public ");
+        writer.write(className);
+        writer.write("(");
+        for (int i = 0; i < parameters.size(); i++) {
+            parameters.get(i).getType().write(this);
+            writer.write(" ");
+            parameters.get(i).write(this);
+            if (i < parameters.size() - 1) {
+                writer.write(", ");
+            }
+        }
+        writer.write(") {");
+        writer.endLine();
+        body.write(this);
+        writer.writeLine("}");
+    }
+
+    private String getOperator(BinaryExpression.Operation op) {
+        switch (op) {
+            case EQ:
+                return "==";
+            case PLUS:
+                return "+";
+        }
+        throw new UnsupportedOperationException("The Operator " + op + " is currently not implemented!");
+    }
+}
diff --git a/sandbox/code-gen/src/main/java/org/apache/plc4x/codegen/version2/Method.java b/sandbox/code-gen/src/main/java/org/apache/plc4x/codegen/version2/Method.java
new file mode 100644
index 0000000..9cfdd0c
--- /dev/null
+++ b/sandbox/code-gen/src/main/java/org/apache/plc4x/codegen/version2/Method.java
@@ -0,0 +1,51 @@
+package org.apache.plc4x.codegen.version2;
+
+import java.util.List;
+
+/**
+ * Method Declaration
+ */
+public class Method implements Node {
+
+    private final TypeNode type;    // Type where this thing is defined on
+    private final String name;
+    private final TypeNode returnType;
+    private final List<TypeNode> parameterTypes;
+    private final List<TypeNode> expressionTypes;
+
+    public Method(TypeNode type, String name, TypeNode returnType, List<TypeNode> parameterTypes, List<TypeNode> expressionTypes) {
+        this.type = type;
+        this.name = name;
+        this.returnType = returnType;
+        this.parameterTypes = parameterTypes;
+        this.expressionTypes = expressionTypes;
+    }
+
+    public TypeNode getType() {
+        return type;
+    }
+
+    public String getName() {
+        return name;
+    }
+
+    public TypeNode getReturnType() {
+        return returnType;
+    }
+
+    public List<TypeNode> getParameterTypes() {
+        return parameterTypes;
+    }
+
+    public List<TypeNode> getExpressionTypes() {
+        return expressionTypes;
+    }
+
+    @Override public <T> T accept(NodeVisitor<T> visitor) {
+        return null;
+    }
+
+    @Override public void write(Generator writer) {
+
+    }
+}
diff --git a/sandbox/code-gen/src/main/java/org/apache/plc4x/codegen/version2/MethodDefinition.java b/sandbox/code-gen/src/main/java/org/apache/plc4x/codegen/version2/MethodDefinition.java
new file mode 100644
index 0000000..b7f2249
--- /dev/null
+++ b/sandbox/code-gen/src/main/java/org/apache/plc4x/codegen/version2/MethodDefinition.java
@@ -0,0 +1,42 @@
+package org.apache.plc4x.codegen.version2;
+
+import java.util.List;
+
+public class MethodDefinition implements Node {
+
+    private final String name;
+    private final TypeNode resultType;
+    private final List<ParameterExpression> parameters;
+    private final Block body;
+
+    public MethodDefinition(String name, TypeNode resultType, List<ParameterExpression> parameters, Block body) {
+        this.name = name;
+        this.resultType = resultType;
+        this.parameters = parameters;
+        this.body = body;
+    }
+
+    public String getName() {
+        return name;
+    }
+
+    public TypeNode getResultType() {
+        return resultType;
+    }
+
+    public List<ParameterExpression> getParameters() {
+        return parameters;
+    }
+
+    public Block getBody() {
+        return body;
+    }
+
+    @Override public <T> T accept(NodeVisitor<T> visitor) {
+        return null;
+    }
+
+    @Override public void write(Generator writer) {
+        writer.generate(this);
+    }
+}
diff --git a/sandbox/code-gen/src/main/java/org/apache/plc4x/codegen/version2/NewExpression.java b/sandbox/code-gen/src/main/java/org/apache/plc4x/codegen/version2/NewExpression.java
new file mode 100644
index 0000000..1e4c467
--- /dev/null
+++ b/sandbox/code-gen/src/main/java/org/apache/plc4x/codegen/version2/NewExpression.java
@@ -0,0 +1,26 @@
+package org.apache.plc4x.codegen.version2;
+
+import java.util.Arrays;
+import java.util.List;
+
+public class NewExpression extends Expression {
+
+    private List<Node> arguments;
+
+    public NewExpression(TypeNode myClazz, Node... arguments) {
+        super(myClazz);
+        this.arguments = Arrays.asList(arguments);
+    }
+
+    public List<Node> getArguments() {
+        return arguments;
+    }
+
+    @Override public <T> T accept(NodeVisitor<T> visitor) {
+        return null;
+    }
+
+    @Override public void write(Generator writer) {
+        writer.generate(this);
+    }
+}
diff --git a/sandbox/code-gen/src/main/java/org/apache/plc4x/codegen/version2/Node.java b/sandbox/code-gen/src/main/java/org/apache/plc4x/codegen/version2/Node.java
new file mode 100644
index 0000000..e569b05
--- /dev/null
+++ b/sandbox/code-gen/src/main/java/org/apache/plc4x/codegen/version2/Node.java
@@ -0,0 +1,9 @@
+package org.apache.plc4x.codegen.version2;
+
+public interface Node {
+
+    <T> T accept(NodeVisitor<T> visitor);
+
+    void write(Generator writer);
+
+}
diff --git a/sandbox/code-gen/src/main/java/org/apache/plc4x/codegen/version2/NodeVisitor.java b/sandbox/code-gen/src/main/java/org/apache/plc4x/codegen/version2/NodeVisitor.java
new file mode 100644
index 0000000..dc690d6
--- /dev/null
+++ b/sandbox/code-gen/src/main/java/org/apache/plc4x/codegen/version2/NodeVisitor.java
@@ -0,0 +1,10 @@
+package org.apache.plc4x.codegen.version2;
+
+public interface NodeVisitor<T> {
+
+    T visit(ConstantNode constantNode);
+
+    T visit(DeclarationStatement declarationStatement);
+
+    T visit(ParameterExpression parameterExpression);
+}
diff --git a/sandbox/code-gen/src/main/java/org/apache/plc4x/codegen/version2/ParameterExpression.java b/sandbox/code-gen/src/main/java/org/apache/plc4x/codegen/version2/ParameterExpression.java
new file mode 100644
index 0000000..8216e70
--- /dev/null
+++ b/sandbox/code-gen/src/main/java/org/apache/plc4x/codegen/version2/ParameterExpression.java
@@ -0,0 +1,23 @@
+package org.apache.plc4x.codegen.version2;
+
+public class ParameterExpression extends Expression {
+
+    private final String name;
+
+    public ParameterExpression(TypeNode type, String name) {
+        super(type);
+        this.name = name;
+    }
+
+    public String getName() {
+        return name;
+    }
+
+    @Override public <T> T accept(NodeVisitor<T> visitor) {
+        return visitor.visit(this);
+    }
+
+    @Override public void write(Generator generator) {
+        generator.generate(this);
+    }
+}
diff --git a/sandbox/code-gen/src/main/java/org/apache/plc4x/codegen/version2/PhpGenerator.java b/sandbox/code-gen/src/main/java/org/apache/plc4x/codegen/version2/PhpGenerator.java
new file mode 100644
index 0000000..279a525
--- /dev/null
+++ b/sandbox/code-gen/src/main/java/org/apache/plc4x/codegen/version2/PhpGenerator.java
@@ -0,0 +1,89 @@
+package org.apache.plc4x.codegen.version2;
+
+import java.util.List;
+
+public class PhpGenerator implements Generator {
+
+    private final CodeWriter writer;
+
+    public PhpGenerator(CodeWriter writer) {
+        this.writer = writer;
+    }
+
+    @Override public void generate(ConstantNode constantNode) {
+        this.writer.write(constantNode.getValue().toString());
+    }
+
+    @Override public void generateDeclarationWithInitializer(DeclarationStatement declarationStatement) {
+        this.writer.startLine("");
+        this.writer.write("$");
+        this.writer.write(declarationStatement.getParameterExpression().getName());
+        this.writer.write(" = ");
+        declarationStatement.getInitializer().write(this);
+        this.writer.write("\n");
+    }
+
+    @Override public void generateDeclaration(DeclarationStatement declarationStatement) {
+
+    }
+
+    @Override public void generate(ParameterExpression parameterExpression) {
+        // not needed
+    }
+
+    @Override public void generate(Primitive primitive) {
+        // Not needed, php is typeless
+    }
+
+    @Override public void generate(IfStatement ifStatement) {
+
+    }
+
+    @Override public void writeBlock(Block statements) {
+
+    }
+
+    @Override public void generate(BinaryExpression binaryExpression) {
+
+    }
+
+    @Override public void generate(AssignementExpression assignementExpression) {
+
+    }
+
+    @Override public void generateStaticCall(Method method, List<Node> constantNode) {
+
+    }
+
+    @Override public void generateCall(Node target, Method method, List<Node> constantNode) {
+
+    }
+
+    @Override public void generate(NewExpression newExpression) {
+
+    }
+
+    @Override public void generate(MethodDefinition methodDefinition) {
+
+    }
+
+    @Override public void generateReturn(Expression value) {
+
+    }
+
+    @Override public void generateClass(String namespace, String className, List<FieldDeclaration> fields, List<ConstructorDeclaration> constructors, List<MethodDefinition> methods) {
+
+    }
+
+    @Override public void generateFieldDeclaration(TypeNode type, String name) {
+
+    }
+
+    @Override public void generateFieldReference(TypeNode type, String name) {
+
+    }
+
+    @Override public void generateConstructor(String className, List<ParameterExpression> parameters, Block body) {
+
+    }
+}
diff --git a/sandbox/code-gen/src/main/java/org/apache/plc4x/codegen/version2/Primitive.java b/sandbox/code-gen/src/main/java/org/apache/plc4x/codegen/version2/Primitive.java
new file mode 100644
index 0000000..67f11bb
--- /dev/null
+++ b/sandbox/code-gen/src/main/java/org/apache/plc4x/codegen/version2/Primitive.java
@@ -0,0 +1,19 @@
+package org.apache.plc4x.codegen.version2;
+
+public class Primitive extends TypeNode {
+
+    public static final TypeNode DOUBLE = new Primitive("double");
+    public static final TypeNode VOID = new Primitive("Void");
+
+    public Primitive(String typeString) {
+        super(typeString);
+    }
+
+    @Override public <T> T accept(NodeVisitor<T> visitor) {
+        return null;
+    }
+
+    @Override public void write(Generator generator) {
+        generator.generate(this);
+    }
+}
diff --git a/sandbox/code-gen/src/main/java/org/apache/plc4x/codegen/version2/ReturnStatement.java b/sandbox/code-gen/src/main/java/org/apache/plc4x/codegen/version2/ReturnStatement.java
new file mode 100644
index 0000000..0e87d6f
--- /dev/null
+++ b/sandbox/code-gen/src/main/java/org/apache/plc4x/codegen/version2/ReturnStatement.java
@@ -0,0 +1,22 @@
+package org.apache.plc4x.codegen.version2;
+
+public class ReturnStatement extends Statement {
+
+    private final Expression value;
+
+    public ReturnStatement(Expression value) {
+        this.value = value;
+    }
+
+    public Expression getValue() {
+        return value;
+    }
+
+    @Override public <T> T accept(NodeVisitor<T> visitor) {
+        return null;
+    }
+
+    @Override public void write(Generator writer) {
+        writer.generateReturn(this.getValue());
+    }
+}
diff --git a/sandbox/code-gen/src/main/java/org/apache/plc4x/codegen/version2/Statement.java b/sandbox/code-gen/src/main/java/org/apache/plc4x/codegen/version2/Statement.java
new file mode 100644
index 0000000..128baa8
--- /dev/null
+++ b/sandbox/code-gen/src/main/java/org/apache/plc4x/codegen/version2/Statement.java
@@ -0,0 +1,4 @@
+package org.apache.plc4x.codegen.version2;
+
+public abstract class Statement implements Node {
+}
diff --git a/sandbox/code-gen/src/main/java/org/apache/plc4x/codegen/version2/TypeNode.java b/sandbox/code-gen/src/main/java/org/apache/plc4x/codegen/version2/TypeNode.java
new file mode 100644
index 0000000..6623eae
--- /dev/null
+++ b/sandbox/code-gen/src/main/java/org/apache/plc4x/codegen/version2/TypeNode.java
@@ -0,0 +1,17 @@
+package org.apache.plc4x.codegen.version2;
+
+/**
+ * Stub for the Type System.
+ */
+public abstract class TypeNode implements Node {
+
+    private final String typeString;
+
+    protected TypeNode(String typeString) {
+        this.typeString = typeString;
+    }
+
+    String getTypeString() {
+        return this.typeString;
+    }
+}
diff --git a/sandbox/code-gen/src/main/java/org/apache/plc4x/codegen/version2/TypeUtil.java b/sandbox/code-gen/src/main/java/org/apache/plc4x/codegen/version2/TypeUtil.java
new file mode 100644
index 0000000..fd6a010
--- /dev/null
+++ b/sandbox/code-gen/src/main/java/org/apache/plc4x/codegen/version2/TypeUtil.java
@@ -0,0 +1,11 @@
+package org.apache.plc4x.codegen.version2;
+
+public class TypeUtil {
+
+    public static TypeNode infer(Object o) {
+        if (o instanceof Double) {
+            return Primitive.DOUBLE;
+        }
+        throw new UnsupportedOperationException("No type available for object " + o);
+    }
+}
diff --git a/sandbox/code-gen/src/test/java/org/apache/plc4x/codegen/version2/JavaGeneratorTest.java b/sandbox/code-gen/src/test/java/org/apache/plc4x/codegen/version2/JavaGeneratorTest.java
new file mode 100644
index 0000000..ae4f312
--- /dev/null
+++ b/sandbox/code-gen/src/test/java/org/apache/plc4x/codegen/version2/JavaGeneratorTest.java
@@ -0,0 +1,236 @@
+package org.apache.plc4x.codegen.version2;
+
+import org.junit.Before;
+import org.junit.Test;
+
+import java.util.Arrays;
+import java.util.Collections;
+
+import static org.junit.Assert.assertEquals;
+
+public class JavaGeneratorTest {
+
+    private CodeWriter writer;
+    private JavaGenerator generator;
+
+    @Before
+    public void setUp() throws Exception {
+        writer = new CodeWriter(4);
+        generator = new JavaGenerator(writer);
+    }
+
+    @Test
+    public void writeDeclaration() {
+        final DeclarationStatement stmt = new DeclarationStatement(new ParameterExpression(Primitive.DOUBLE, "a"), new ConstantNode(5.0));
+        stmt.write(generator);
+
+        final String code = writer.getCode();
+
+        assertEquals("double a = 5.0", code);
+    }
+
+    @Test
+    public void ifStatement() {
+        final Statement stmt = new IfStatement(
+            new BinaryExpression(Primitive.DOUBLE, new ParameterExpression(Primitive.DOUBLE, "a"),
+                new ConstantNode(10.0),
+                BinaryExpression.Operation.EQ),
+            new Block(new DeclarationStatement(new ParameterExpression(Primitive.DOUBLE, "b"), new ConstantNode(5.0))),
+            new Block(new DeclarationStatement(new ParameterExpression(Primitive.DOUBLE, "b"), new ConstantNode(3.0)))
+        );
+
+        stmt.write(generator);
+
+        final String code = writer.getCode();
+
+        assertEquals("if (a == 10.0) {\n" +
+            "    double b = 5.0;\n" +
+            "} else {\n" +
+            "    double b = 3.0;\n" +
+            "}\n", code);
+    }
+
+    @Test
+    public void IfIf() {
+        final Statement stmt = new Block(Arrays.asList(
+            new DeclarationStatement(new ParameterExpression(Primitive.DOUBLE, "c"), null),
+            new IfStatement(
+                new BinaryExpression(Primitive.DOUBLE, new ParameterExpression(Primitive.DOUBLE, "a"),
+                    new ConstantNode(10.0),
+                    BinaryExpression.Operation.EQ),
+                new Block(
+                    new IfStatement(
+                        new BinaryExpression(Primitive.DOUBLE, new ParameterExpression(Primitive.DOUBLE, "b"),
+                            new ConstantNode(10.0),
+                            BinaryExpression.Operation.EQ),
+                        new Block(
+                            new AssignementExpression(new ParameterExpression(Primitive.DOUBLE, "c"), new ConstantNode(5.0)),
+                            new DeclarationStatement(new ParameterExpression(Primitive.DOUBLE, "d"), new ConstantNode(100.0))
+                        ),
+                        null
+                    )
+                ),
+                null
+            )));
+
+        stmt.write(generator);
+
+        final String code = writer.getCode();
+
+        assertEquals("    double c;\n" +
+            "    if (a == 10.0) {\n" +
+            "        if (b == 10.0) {\n" +
+            "            c = 5.0;\n" +
+            "            double d = 100.0;\n" +
+            "        }\n" +
+            "    }\n", code);
+    }
+
+    @Test
+    public void callStaticMethod() {
+        final TypeNode myClazz = new Primitive("MyClazz");
+        Expression expr = new CallExpression(new Method(myClazz, "toString", Primitive.VOID, Collections.singletonList(Primitive.DOUBLE), Collections.EMPTY_LIST), null, new ConstantNode(5.0));
+
+        expr.write(generator);
+
+        final String code = writer.getCode();
+
+        assertEquals("MyClazz.toString(5.0)", code);
+    }
+
+    @Test
+    public void callMethod() {
+        final TypeNode myClazz = new Primitive("MyClazz");
+        Expression expr = new CallExpression(new Method(myClazz, "toString", Primitive.VOID, Collections.singletonList(Primitive.DOUBLE), Collections.EMPTY_LIST), new ParameterExpression(myClazz, "a"), new ConstantNode(5.0));
+
+        expr.write(generator);
+
+        final String code = writer.getCode();
+
+        assertEquals("a.toString(5.0)", code);
+    }
+
+    @Test
+    public void complexCallAssignment() {
+        final TypeNode myClazz = new Primitive("MyClazz");
+        final ParameterExpression instance = new ParameterExpression(myClazz, "instance");
+        final Method getNumberMethod = new Method(myClazz, "getNumber", Primitive.DOUBLE, Collections.emptyList(), Collections.emptyList());
+        final Method staticMethod = new Method(myClazz, "staticMethod", Primitive.DOUBLE, Collections.emptyList(), Collections.emptyList());
+        Statement stmt = new Block(Arrays.asList(
+            new DeclarationStatement(instance, null),
+            new AssignementExpression(instance, new NewExpression(myClazz)),
+            new AssignementExpression(instance, new NewExpression(myClazz, new NewExpression(myClazz))),
+            new DeclarationStatement(new ParameterExpression(Primitive.DOUBLE, "a"), new CallExpression(getNumberMethod, instance)),
+            new DeclarationStatement(new ParameterExpression(Primitive.DOUBLE, "b"), new CallExpression(staticMethod, null))
+        ));
+
+        stmt.write(generator);
+        final String code = writer.getCode();
+        assertEquals("    MyClazz instance;\n" +
+            "    instance = new MyClazz();\n" +
+            "    instance = new MyClazz(new MyClazz());\n" +
+            "    double a = instance.getNumber();\n" +
+            "    double b = MyClazz.staticMethod();\n", code);
+    }
+
+    @Test
+    public void writeMethodDefinition() {
+        final ParameterExpression a = new ParameterExpression(Primitive.DOUBLE, "a");
+        final ParameterExpression b = new ParameterExpression(Primitive.DOUBLE, "b");
+        final MethodDefinition decl = new MethodDefinition("add", Primitive.DOUBLE,
+            Arrays.asList(
+                a,
+                b
+            ),
+            new Block(
+                new ReturnStatement(
+                    new BinaryExpression(a.getType(), a, b, BinaryExpression.Operation.PLUS)
+                )
+            )
+        );
+
+        decl.write(generator);
+        final String code = writer.getCode();
+        assertEquals("public double add(double a, double b) {\n" +
+            "    return a + b;\n" +
+            "}\n", code);
+    }
+
+    @Test
+    public void defineClass() {
+        final FieldDeclaration current = new FieldDeclaration(Primitive.DOUBLE, "current");
+
+        final ParameterExpression a = new ParameterExpression(Primitive.DOUBLE, "a");
+        final ParameterExpression b = new ParameterExpression(Primitive.DOUBLE, "b");
+        final MethodDefinition decl = new MethodDefinition("add", Primitive.DOUBLE,
+            Arrays.asList(
+                a,
+                b
+            ),
+            new Block(
+                new ReturnStatement(
+                    new BinaryExpression(a.getType(), a, b, BinaryExpression.Operation.PLUS)
+                )
+            )
+        );
+        final FieldReference currentRef = new FieldReference(Primitive.DOUBLE, "current");
+        final MethodDefinition inc = new MethodDefinition("inc", Primitive.VOID,
+            Collections.EMPTY_LIST,
+            new Block(
+                new AssignementExpression(
+                    currentRef,
+                    new BinaryExpression(currentRef.getType(), currentRef, new ConstantNode(1.0), BinaryExpression.Operation.PLUS)
+                )
+            )
+        );
+
+        final ClassDefinition clazz = new ClassDefinition("org.apache.plc4x", "MyClazz", Arrays.asList(current), Collections.emptyList(), Arrays.asList(inc, decl));
+
+        clazz.write(generator);
+        final String code = writer.getCode();
+        assertEquals("public class MyClazz {\n" +
+            "    \n" +
+            "    public double current;\n" +
+            "    \n" +
+            "    public void inc() {\n" +
+            "        this.current = this.current + 1.0;\n" +
+            "    }\n" +
+            "    \n" +
+            "    public double add(double a, double b) {\n" +
+            "        return a + b;\n" +
+            "    }\n" +
+            "    \n" +
+            "}\n", code);
+    }
+
+    @Test
+    public void defineClassWithConstructor() {
+        final FieldDeclaration current = new FieldDeclaration(Primitive.DOUBLE, "current");
+
+        final FieldReference currentRef = new FieldReference(Primitive.DOUBLE, "current");
+
+        final ParameterExpression value = new ParameterExpression(Primitive.DOUBLE, "value");
+        final ClassDefinition clazz = new ClassDefinition("org.apache.plc4x",
+            "MyClazz",
+            Arrays.asList(current),
+            Arrays.asList(
+                new ConstructorDeclaration(
+                    Collections.singletonList(value),
+                    new Block(new AssignementExpression(currentRef, value))
+                )
+            ),
+            Collections.emptyList());
+
+        clazz.write(generator);
+        final String code = writer.getCode();
+        assertEquals("public class MyClazz {\n" +
+            "    \n" +
+            "    public double current;\n" +
+            "    \n" +
+            "    public MyClazz(double value) {\n" +
+            "        this.current = value;\n" +
+            "    }\n" +
+            "    \n" +
+            "}\n", code);
+    }
+}
\ No newline at end of file
diff --git a/sandbox/code-gen/src/test/java/org/apache/plc4x/codegen/version2/PhpGeneratorTest.java b/sandbox/code-gen/src/test/java/org/apache/plc4x/codegen/version2/PhpGeneratorTest.java
new file mode 100644
index 0000000..863c3c1
--- /dev/null
+++ b/sandbox/code-gen/src/test/java/org/apache/plc4x/codegen/version2/PhpGeneratorTest.java
@@ -0,0 +1,23 @@
+package org.apache.plc4x.codegen.version2;
+
+import org.junit.Test;
+
+import static org.junit.Assert.assertEquals;
+
+public class PhpGeneratorTest {
+
+    @Test
+    public void createSomeCode() {
+        final CodeWriter writer = new CodeWriter(4);
+
+        final DeclarationStatement stmt = new DeclarationStatement(new ParameterExpression(Primitive.DOUBLE, "a"), new ConstantNode(5.0));
+
+        final Generator generator = new PhpGenerator(writer);
+
+        stmt.write(generator);
+
+        final String code = writer.getCode();
+
+        assertEquals("$a = 5.0\n", code);
+    }
+}
\ No newline at end of file