http://git-wip-us.apache.org/repos/asf/oozie/blob/8a0a6487/fluent-job/fluent-job-api/src/test/java/org/apache/oozie/fluentjob/api/mapping/TestExplicitNodeMapping.java
----------------------------------------------------------------------
diff --git 
a/fluent-job/fluent-job-api/src/test/java/org/apache/oozie/fluentjob/api/mapping/TestExplicitNodeMapping.java
 
b/fluent-job/fluent-job-api/src/test/java/org/apache/oozie/fluentjob/api/mapping/TestExplicitNodeMapping.java
new file mode 100644
index 0000000..47eb9c3
--- /dev/null
+++ 
b/fluent-job/fluent-job-api/src/test/java/org/apache/oozie/fluentjob/api/mapping/TestExplicitNodeMapping.java
@@ -0,0 +1,47 @@
+/**
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License.  You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.apache.oozie.fluentjob.api.mapping;
+
+import org.apache.oozie.fluentjob.api.generated.workflow.ACTION;
+import org.apache.oozie.fluentjob.api.action.MapReduceAction;
+import org.apache.oozie.fluentjob.api.action.MapReduceActionBuilder;
+import org.apache.oozie.fluentjob.api.dag.End;
+import org.apache.oozie.fluentjob.api.dag.ExplicitNode;
+import org.junit.Test;
+
+import static org.junit.Assert.assertEquals;
+import static org.junit.Assert.assertNotNull;
+
+public class TestExplicitNodeMapping {
+    @Test
+    public void testMappingExplicitNode() {
+        final MapReduceAction mrAction = 
MapReduceActionBuilder.create().withName("map-reduce-action").build();
+        final ExplicitNode node = new ExplicitNode(mrAction.getName(), 
mrAction);
+
+        final End end = new End("end");
+
+        end.addParent(node);
+
+        final ACTION action = DozerBeanMapperSingleton.instance().map(node, 
ACTION.class);
+
+        assertEquals(mrAction.getName(), action.getName());
+        assertEquals(end.getName(), action.getOk().getTo());
+        assertNotNull(action.getMapReduce());
+    }
+}

http://git-wip-us.apache.org/repos/asf/oozie/blob/8a0a6487/fluent-job/fluent-job-api/src/test/java/org/apache/oozie/fluentjob/api/mapping/TestFSActionMapping.java
----------------------------------------------------------------------
diff --git 
a/fluent-job/fluent-job-api/src/test/java/org/apache/oozie/fluentjob/api/mapping/TestFSActionMapping.java
 
b/fluent-job/fluent-job-api/src/test/java/org/apache/oozie/fluentjob/api/mapping/TestFSActionMapping.java
new file mode 100644
index 0000000..c43ca0a
--- /dev/null
+++ 
b/fluent-job/fluent-job-api/src/test/java/org/apache/oozie/fluentjob/api/mapping/TestFSActionMapping.java
@@ -0,0 +1,77 @@
+/**
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License.  You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.apache.oozie.fluentjob.api.mapping;
+
+import com.google.common.collect.ImmutableList;
+import org.apache.oozie.fluentjob.api.generated.workflow.FS;
+import org.apache.oozie.fluentjob.api.action.Chgrp;
+import org.apache.oozie.fluentjob.api.action.ChgrpBuilder;
+import org.apache.oozie.fluentjob.api.action.Chmod;
+import org.apache.oozie.fluentjob.api.action.ChmodBuilder;
+import org.apache.oozie.fluentjob.api.action.Delete;
+import org.apache.oozie.fluentjob.api.action.FSAction;
+import org.apache.oozie.fluentjob.api.action.FSActionBuilder;
+import org.apache.oozie.fluentjob.api.action.Mkdir;
+import org.apache.oozie.fluentjob.api.action.Move;
+import org.apache.oozie.fluentjob.api.action.Touchz;
+import org.junit.Test;
+
+import java.util.Arrays;
+import java.util.List;
+
+import static org.junit.Assert.assertEquals;
+
+public class TestFSActionMapping {
+    @Test
+    public void testMappingFSAction() {
+        final String nameNode = "${nameNode}";
+        final ImmutableList<String> jobXmls = new 
ImmutableList.Builder<String>().add("jobXml1").add("jobXml2").build();
+
+        final Delete delete = new Delete("path", true);
+        final Mkdir mkdir = new Mkdir("path");
+        final Move move = new Move("from", "to");
+        final Chmod chmod = new ChmodBuilder().withPermissions("511").build();
+        final Touchz touchz = new Touchz("path");
+        final Chgrp chgrp = new 
ChgrpBuilder().withGroup("user:group:").build();
+
+        final FSActionBuilder builder = FSActionBuilder.create()
+                .withNameNode(nameNode);
+
+        for (final String jobXml : jobXmls) {
+            builder.withJobXml(jobXml);
+        }
+
+        builder.withDelete(delete)
+                .withMkdir(mkdir)
+                .withMove(move)
+                .withChmod(chmod)
+                .withTouchz(touchz)
+                .withChgrp(chgrp);
+
+        final FSAction action = builder.build();
+
+        final FS fsAction = DozerBeanMapperSingleton.instance().map(action, 
FS.class);
+
+        assertEquals(nameNode, fsAction.getNameNode());
+        assertEquals(jobXmls, fsAction.getJobXml());
+
+        final List<Object> expectedList = Arrays.asList(delete, mkdir, move, 
chmod, touchz, chgrp);
+        assertEquals(expectedList.size(), 
fsAction.getDeleteOrMkdirOrMove().size());
+    }
+}

http://git-wip-us.apache.org/repos/asf/oozie/blob/8a0a6487/fluent-job/fluent-job-api/src/test/java/org/apache/oozie/fluentjob/api/mapping/TestForkMapping.java
----------------------------------------------------------------------
diff --git 
a/fluent-job/fluent-job-api/src/test/java/org/apache/oozie/fluentjob/api/mapping/TestForkMapping.java
 
b/fluent-job/fluent-job-api/src/test/java/org/apache/oozie/fluentjob/api/mapping/TestForkMapping.java
new file mode 100644
index 0000000..8526744
--- /dev/null
+++ 
b/fluent-job/fluent-job-api/src/test/java/org/apache/oozie/fluentjob/api/mapping/TestForkMapping.java
@@ -0,0 +1,70 @@
+/**
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License.  You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.apache.oozie.fluentjob.api.mapping;
+
+import org.apache.oozie.fluentjob.api.generated.workflow.FORK;
+import org.apache.oozie.fluentjob.api.generated.workflow.FORKTRANSITION;
+import org.apache.oozie.fluentjob.api.dag.Decision;
+import org.apache.oozie.fluentjob.api.dag.DecisionJoin;
+import org.apache.oozie.fluentjob.api.dag.ExplicitNode;
+import org.apache.oozie.fluentjob.api.dag.Fork;
+import org.apache.oozie.fluentjob.api.dag.NodeBase;
+import org.junit.Test;
+
+import java.util.List;
+
+import static org.junit.Assert.assertEquals;
+
+public class TestForkMapping extends TestControlNodeMappingBase {
+    @Test
+    public void testMappingFork() {
+        final String name = "fork";
+        final Fork fork = new Fork(name);
+
+        final NodeBase child1 = new ExplicitNode("child1", null);
+        final NodeBase child2 = new ExplicitNode("child2", null);
+
+        child1.addParent(fork);
+        child2.addParent(fork);
+
+        final FORK mappedFork = DozerBeanMapperSingleton.instance().map(fork, 
FORK.class);
+
+        assertEquals(name, mappedFork.getName());
+
+        final List<FORKTRANSITION> transitions = mappedFork.getPath();
+        assertEquals(child1.getName(), transitions.get(0).getStart());
+        assertEquals(child2.getName(), transitions.get(1).getStart());
+    }
+
+    @Test
+    public void testMappingForkWithDecisionJoin() {
+        final String childName = "child";
+        final Fork fork = new Fork("fork");
+
+        final NodeBase decisionJoin = new DecisionJoin("decisionJoin", new 
Decision("decision"));
+        decisionJoin.addParent(fork);
+
+        final NodeBase child = new ExplicitNode(childName, null);
+        child.addParent(decisionJoin);
+
+        final FORK mappedFork = DozerBeanMapperSingleton.instance().map(fork, 
FORK.class);
+
+        assertEquals(childName, mappedFork.getPath().get(0).getStart());
+    }
+}

http://git-wip-us.apache.org/repos/asf/oozie/blob/8a0a6487/fluent-job/fluent-job-api/src/test/java/org/apache/oozie/fluentjob/api/mapping/TestGlobalMapping.java
----------------------------------------------------------------------
diff --git 
a/fluent-job/fluent-job-api/src/test/java/org/apache/oozie/fluentjob/api/mapping/TestGlobalMapping.java
 
b/fluent-job/fluent-job-api/src/test/java/org/apache/oozie/fluentjob/api/mapping/TestGlobalMapping.java
new file mode 100644
index 0000000..8501813
--- /dev/null
+++ 
b/fluent-job/fluent-job-api/src/test/java/org/apache/oozie/fluentjob/api/mapping/TestGlobalMapping.java
@@ -0,0 +1,56 @@
+/**
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License.  You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.apache.oozie.fluentjob.api.mapping;
+
+import org.apache.oozie.fluentjob.api.generated.workflow.GLOBAL;
+import org.apache.oozie.fluentjob.api.action.LauncherBuilder;
+import org.apache.oozie.fluentjob.api.generated.workflow.GLOBAL;
+import org.apache.oozie.fluentjob.api.workflow.Global;
+import org.apache.oozie.fluentjob.api.workflow.GlobalBuilder;
+import org.junit.Test;
+
+import static org.junit.Assert.assertEquals;
+
+public class TestGlobalMapping {
+    private static final String DEFAULT = "default";
+
+    @Test
+    public void testMappingGlobal() {
+        final Global source = GlobalBuilder.create()
+                .withResourceManager(DEFAULT)
+                .withNameNode(DEFAULT)
+                .withJobXml(DEFAULT)
+                .withConfigProperty("key1", "value1")
+                .withLauncher(new LauncherBuilder()
+                        .withMemoryMb(1024L)
+                        .withVCores(1L)
+                        .build())
+                .build();
+
+        final GLOBAL destination = 
DozerBeanMapperSingleton.instance().map(source, GLOBAL.class);
+
+        assertEquals(DEFAULT, destination.getResourceManager());
+        assertEquals(DEFAULT, destination.getNameNode());
+        assertEquals(DEFAULT, destination.getJobXml().get(0));
+        assertEquals("key1", 
destination.getConfiguration().getProperty().get(0).getName());
+        assertEquals("value1", 
destination.getConfiguration().getProperty().get(0).getValue());
+        assertEquals(1024L, 
destination.getLauncher().getMemoryMbOrVcoresOrJavaOpts().get(0).getValue());
+        assertEquals(1L, 
destination.getLauncher().getMemoryMbOrVcoresOrJavaOpts().get(1).getValue());
+    }
+}

http://git-wip-us.apache.org/repos/asf/oozie/blob/8a0a6487/fluent-job/fluent-job-api/src/test/java/org/apache/oozie/fluentjob/api/mapping/TestGraphMapping.java
----------------------------------------------------------------------
diff --git 
a/fluent-job/fluent-job-api/src/test/java/org/apache/oozie/fluentjob/api/mapping/TestGraphMapping.java
 
b/fluent-job/fluent-job-api/src/test/java/org/apache/oozie/fluentjob/api/mapping/TestGraphMapping.java
new file mode 100644
index 0000000..0563ec6
--- /dev/null
+++ 
b/fluent-job/fluent-job-api/src/test/java/org/apache/oozie/fluentjob/api/mapping/TestGraphMapping.java
@@ -0,0 +1,255 @@
+/**
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License.  You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.apache.oozie.fluentjob.api.mapping;
+
+import org.apache.oozie.fluentjob.api.Condition;
+import org.apache.oozie.fluentjob.api.action.EmailActionBuilder;
+import org.apache.oozie.fluentjob.api.action.ErrorHandler;
+import org.apache.oozie.fluentjob.api.action.FSAction;
+import org.apache.oozie.fluentjob.api.action.FSActionBuilder;
+import org.apache.oozie.fluentjob.api.action.MapReduceAction;
+import org.apache.oozie.fluentjob.api.action.MapReduceActionBuilder;
+import org.apache.oozie.fluentjob.api.action.Node;
+import org.apache.oozie.fluentjob.api.generated.workflow.ACTION;
+import org.apache.oozie.fluentjob.api.generated.workflow.ACTIONTRANSITION;
+import org.apache.oozie.fluentjob.api.generated.workflow.CASE;
+import org.apache.oozie.fluentjob.api.generated.workflow.DECISION;
+import org.apache.oozie.fluentjob.api.generated.workflow.DEFAULT;
+import org.apache.oozie.fluentjob.api.generated.workflow.END;
+import org.apache.oozie.fluentjob.api.generated.workflow.FORK;
+import org.apache.oozie.fluentjob.api.generated.workflow.FORKTRANSITION;
+import org.apache.oozie.fluentjob.api.generated.workflow.JOIN;
+import org.apache.oozie.fluentjob.api.generated.workflow.KILL;
+import org.apache.oozie.fluentjob.api.generated.workflow.ObjectFactory;
+import org.apache.oozie.fluentjob.api.generated.workflow.START;
+import org.apache.oozie.fluentjob.api.generated.workflow.SWITCH;
+import org.apache.oozie.fluentjob.api.generated.workflow.WORKFLOWAPP;
+import org.apache.oozie.fluentjob.api.dag.Decision;
+import org.apache.oozie.fluentjob.api.dag.DecisionJoin;
+import org.apache.oozie.fluentjob.api.dag.End;
+import org.apache.oozie.fluentjob.api.dag.ExplicitNode;
+import org.apache.oozie.fluentjob.api.dag.Fork;
+import org.apache.oozie.fluentjob.api.dag.Graph;
+import org.apache.oozie.fluentjob.api.dag.Join;
+import org.apache.oozie.fluentjob.api.dag.Start;
+import org.apache.oozie.fluentjob.api.workflow.Workflow;
+import org.apache.oozie.fluentjob.api.workflow.WorkflowBuilder;
+import org.junit.Test;
+
+import java.util.Arrays;
+import java.util.List;
+
+import static org.junit.Assert.assertEquals;
+
+public class TestGraphMapping {
+    private static final ObjectFactory OBJECT_FACTORY = new ObjectFactory();
+
+    @Test
+    public void testMappingGraphFromWorkflow() {
+        final String errorHandlerName = "error-handler";
+
+        final EmailActionBuilder emailBuilder = 
EmailActionBuilder.create().withName(errorHandlerName)
+                .withRecipient("[email protected]")
+                .withSubject("Subject")
+                .withBody("Email body.");
+
+        final ErrorHandler errorHandler = 
ErrorHandler.buildAsErrorHandler(emailBuilder);
+
+        final MapReduceAction mrAction = MapReduceActionBuilder.create()
+                .withName("map-reduce-action")
+                .build();
+        final FSAction fsAction = FSActionBuilder.create()
+                .withName("fs-action")
+                .withParent(mrAction)
+                .withErrorHandler(errorHandler)
+                .build();
+
+        final Workflow workflow = new 
WorkflowBuilder().withName("workflow-name").withDagContainingNode(mrAction).build();
+
+        final Graph graph = new Graph(workflow);
+
+        final WORKFLOWAPP workflowapp = 
DozerBeanMapperSingleton.instance().map(graph, WORKFLOWAPP.class);
+
+        final WORKFLOWAPP expectedWorkflowapp = 
OBJECT_FACTORY.createWORKFLOWAPP();
+        expectedWorkflowapp.setName(workflow.getName());
+
+        final START start = OBJECT_FACTORY.createSTART();
+        start.setTo(mrAction.getName());
+        expectedWorkflowapp.setStart(start);
+
+        final END end = OBJECT_FACTORY.createEND();
+        end.setName("end");
+        expectedWorkflowapp.setEnd(end);
+
+        final List<Object> actions = 
expectedWorkflowapp.getDecisionOrForkOrJoin();
+
+        final ACTION actionMr = convertEmailActionByHand((ExplicitNode) 
graph.getNodeByName(mrAction.getName()));
+
+        final ACTION actionFs = convertEmailActionByHand((ExplicitNode) 
graph.getNodeByName(fsAction.getName()));
+
+        final ACTIONTRANSITION error = actionFs.getError();
+        error.setTo(errorHandlerName);
+
+        final Node emailErrorHandlerNode = emailBuilder.build();
+        final ExplicitNode emailErrorHandlerExplicitNode
+                = new ExplicitNode(emailErrorHandlerNode.getName(), 
emailErrorHandlerNode);
+        final ACTION errorHandlerAction = 
convertEmailActionByHand(emailErrorHandlerExplicitNode);
+
+        final KILL kill = createKill();
+
+        final ACTIONTRANSITION okAndError = 
OBJECT_FACTORY.createACTIONTRANSITION();
+        okAndError.setTo(kill.getName());
+
+        errorHandlerAction.setOk(okAndError);
+        errorHandlerAction.setError(okAndError);
+
+        actions.add(kill);
+        actions.add(actionMr);
+        actions.add(errorHandlerAction);
+        actions.add(actionFs);
+
+        assertEquals(expectedWorkflowapp, workflowapp);
+    }
+
+    @Test
+    public void testMappingGraphFromNodes() {
+        final String workflowName = "test-workflow";
+        final String condition = "condition";
+
+        final ExplicitNode A = new ExplicitNode("A", 
EmailActionBuilder.create().build());
+        final ExplicitNode B = new ExplicitNode("B", 
EmailActionBuilder.create().build());
+        final ExplicitNode C = new ExplicitNode("C", 
EmailActionBuilder.create().build());
+        final ExplicitNode D = new ExplicitNode("D", 
EmailActionBuilder.create().build());
+        final ExplicitNode E = new ExplicitNode("E", 
EmailActionBuilder.create().build());
+
+        final Start start = new Start("start");
+        final End end = new End("end");
+        final Fork fork = new Fork("fork1");
+        final Join join = new Join("join1", fork);
+        final Decision decision = new Decision("decision");
+        final DecisionJoin decisionJoin = new DecisionJoin("decisionJoin", 
decision);
+
+        // TODO: Unfortunately the order of the elements counts.
+        end.addParent(join);
+        join.addParent(decisionJoin);
+        join.addParent(C);
+        decisionJoin.addParent(D);
+        decisionJoin.addParent(E);
+        D.addParentWithCondition(decision, 
Condition.actualCondition(condition));
+        E.addParentDefaultConditional(decision);
+        decision.addParent(B);
+        B.addParent(fork);
+        C.addParent(fork);
+        fork.addParent(A);
+        A.addParent(start);
+
+        final GraphNodes graphNodes = new GraphNodes(workflowName,
+                null,
+                null,
+                null,
+                start,
+                end,
+                Arrays.asList(A, B, C, D, E, fork, join, decision, 
decisionJoin));
+
+
+        final WORKFLOWAPP expectedWorkflowApp = 
OBJECT_FACTORY.createWORKFLOWAPP();
+        expectedWorkflowApp.setName(workflowName);
+
+        final START startJaxb = OBJECT_FACTORY.createSTART();
+        startJaxb.setTo(start.getChild().getName());
+        expectedWorkflowApp.setStart(startJaxb);
+
+        final END endJaxb = OBJECT_FACTORY.createEND();
+        endJaxb.setName(end.getName());
+        expectedWorkflowApp.setEnd(endJaxb);
+
+        final List<Object> nodesInWorkflowApp = 
expectedWorkflowApp.getDecisionOrForkOrJoin();
+
+        final FORK forkJaxb = OBJECT_FACTORY.createFORK();
+        forkJaxb.setName(fork.getName());
+        final List<FORKTRANSITION> transitions = forkJaxb.getPath();
+        final FORKTRANSITION transitionB = 
OBJECT_FACTORY.createFORKTRANSITION();
+        transitionB.setStart(B.getName());
+        final FORKTRANSITION transitionC = 
OBJECT_FACTORY.createFORKTRANSITION();
+        transitionC.setStart(C.getName());
+        transitions.add(transitionB);
+        transitions.add(transitionC);
+
+        final ACTION actionA = convertEmailActionByHand(A);
+
+        final ACTION actionB = convertEmailActionByHand(B);
+
+        final ACTION actionC = convertEmailActionByHand(C);
+
+        final DECISION decisionJaxb = OBJECT_FACTORY.createDECISION();
+        decisionJaxb.setName(decision.getName());
+        final SWITCH _switch = OBJECT_FACTORY.createSWITCH();
+        final List<CASE> cases = _switch.getCase();
+        final CASE _case = OBJECT_FACTORY.createCASE();
+        _case.setTo(D.getName());
+        _case.setValue(condition);
+        cases.add(_case);
+        final DEFAULT _default = OBJECT_FACTORY.createDEFAULT();
+        _default.setTo(E.getName());
+        _switch.setDefault(_default);
+        decisionJaxb.setSwitch(_switch);
+
+        final ACTION actionD = convertEmailActionByHand(D);
+
+        final ACTION actionE = convertEmailActionByHand(E);
+
+        final JOIN joinJaxb = OBJECT_FACTORY.createJOIN();
+        joinJaxb.setName(join.getName());
+        joinJaxb.setTo(end.getName());
+
+        // TODO: Unfortunately the order of the elements counts.
+        nodesInWorkflowApp.add(createKill());
+        nodesInWorkflowApp.add(actionA);
+        nodesInWorkflowApp.add(actionB);
+        nodesInWorkflowApp.add(actionC);
+        nodesInWorkflowApp.add(actionD);
+        nodesInWorkflowApp.add(actionE);
+        nodesInWorkflowApp.add(forkJaxb);
+        nodesInWorkflowApp.add(joinJaxb);
+        nodesInWorkflowApp.add(decisionJaxb);
+
+        final WORKFLOWAPP workflowapp = 
DozerBeanMapperSingleton.instance().map(graphNodes, WORKFLOWAPP.class);
+
+        assertEquals(expectedWorkflowApp, workflowapp);
+    }
+
+    private ACTION convertEmailActionByHand(final ExplicitNode node) {
+        final ACTION action = DozerBeanMapperSingleton.instance().map(node, 
ACTION.class);
+
+        final ACTIONTRANSITION error = OBJECT_FACTORY.createACTIONTRANSITION();
+        error.setTo(createKill().getName());
+        action.setError(error);
+
+        return action;
+    }
+
+    private KILL createKill() {
+        final KILL kill = OBJECT_FACTORY.createKILL();
+
+        kill.setName("kill");
+        kill.setMessage("Action failed, error 
message[${wf:errorMessage(wf:lastErrorNode())}]");
+
+        return kill;
+    }
+}

http://git-wip-us.apache.org/repos/asf/oozie/blob/8a0a6487/fluent-job/fluent-job-api/src/test/java/org/apache/oozie/fluentjob/api/mapping/TestHive2ActionMapping.java
----------------------------------------------------------------------
diff --git 
a/fluent-job/fluent-job-api/src/test/java/org/apache/oozie/fluentjob/api/mapping/TestHive2ActionMapping.java
 
b/fluent-job/fluent-job-api/src/test/java/org/apache/oozie/fluentjob/api/mapping/TestHive2ActionMapping.java
new file mode 100644
index 0000000..a807e60
--- /dev/null
+++ 
b/fluent-job/fluent-job-api/src/test/java/org/apache/oozie/fluentjob/api/mapping/TestHive2ActionMapping.java
@@ -0,0 +1,84 @@
+/**
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License.  You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.apache.oozie.fluentjob.api.mapping;
+
+import org.apache.oozie.fluentjob.api.action.Hive2Action;
+import org.apache.oozie.fluentjob.api.action.Hive2ActionBuilder;
+import org.apache.oozie.fluentjob.api.action.LauncherBuilder;
+import org.apache.oozie.fluentjob.api.action.PrepareBuilder;
+import org.apache.oozie.fluentjob.api.generated.action.hive2.ACTION;
+import org.junit.Test;
+
+import java.util.Arrays;
+import java.util.List;
+
+import static org.junit.Assert.assertEquals;
+import static org.junit.Assert.assertNotNull;
+
+public class TestHive2ActionMapping {
+
+    @Test
+    public void testMappingHive2Action() {
+        final String resourceManager = "${resourceManager}";
+        final String nameNode = "${nameNode}";
+        final List<String> args = Arrays.asList("arg1", "arg2");
+
+        final Hive2ActionBuilder builder = Hive2ActionBuilder.create();
+
+        builder.withResourceManager(resourceManager)
+                .withNameNode(nameNode)
+                .withPrepare(new PrepareBuilder()
+                        .withDelete("/path/to/delete")
+                        .withMkdir("/path/to/mkdir")
+                        .build())
+                .withLauncher(new LauncherBuilder()
+                        .withMemoryMb(1024)
+                        .withVCores(2)
+                        .withQueue("default")
+                        .withSharelib("default")
+                        .withViewAcl("default")
+                        .withModifyAcl("default")
+                        .build());
+
+        for (final String arg : args) {
+            builder.withArg(arg);
+        }
+
+        builder.withConfigProperty("propertyName1", "propertyValue1")
+                .withConfigProperty("propertyName2", "propertyValue2");
+
+        final Hive2Action action = builder.build();
+
+        final ACTION hive2 = DozerBeanMapperSingleton.instance().map(action, 
ACTION.class);
+
+        assertEquals(resourceManager, hive2.getResourceManager());
+        assertEquals(nameNode, hive2.getNameNode());
+        assertNotNull(hive2.getPrepare());
+        assertEquals("/path/to/delete", 
hive2.getPrepare().getDelete().get(0).getPath());
+        assertEquals("/path/to/mkdir", 
hive2.getPrepare().getMkdir().get(0).getPath());
+        assertNotNull(hive2.getConfiguration());
+        assertEquals(args, hive2.getArgument());
+        assertEquals(1024L, 
hive2.getLauncher().getMemoryMbOrVcoresOrJavaOpts().get(0).getValue());
+        assertEquals(2L, 
hive2.getLauncher().getMemoryMbOrVcoresOrJavaOpts().get(1).getValue());
+        assertEquals("default", 
hive2.getLauncher().getMemoryMbOrVcoresOrJavaOpts().get(2).getValue());
+        assertEquals("default", 
hive2.getLauncher().getMemoryMbOrVcoresOrJavaOpts().get(3).getValue());
+        assertEquals("default", 
hive2.getLauncher().getMemoryMbOrVcoresOrJavaOpts().get(4).getValue());
+        assertEquals("default", 
hive2.getLauncher().getMemoryMbOrVcoresOrJavaOpts().get(5).getValue());
+    }
+}

http://git-wip-us.apache.org/repos/asf/oozie/blob/8a0a6487/fluent-job/fluent-job-api/src/test/java/org/apache/oozie/fluentjob/api/mapping/TestHiveActionMapping.java
----------------------------------------------------------------------
diff --git 
a/fluent-job/fluent-job-api/src/test/java/org/apache/oozie/fluentjob/api/mapping/TestHiveActionMapping.java
 
b/fluent-job/fluent-job-api/src/test/java/org/apache/oozie/fluentjob/api/mapping/TestHiveActionMapping.java
new file mode 100644
index 0000000..95e6da3
--- /dev/null
+++ 
b/fluent-job/fluent-job-api/src/test/java/org/apache/oozie/fluentjob/api/mapping/TestHiveActionMapping.java
@@ -0,0 +1,84 @@
+/**
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License.  You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.apache.oozie.fluentjob.api.mapping;
+
+import org.apache.oozie.fluentjob.api.action.HiveAction;
+import org.apache.oozie.fluentjob.api.action.HiveActionBuilder;
+import org.apache.oozie.fluentjob.api.action.LauncherBuilder;
+import org.apache.oozie.fluentjob.api.action.PrepareBuilder;
+import org.apache.oozie.fluentjob.api.generated.action.hive.ACTION;
+import org.junit.Test;
+
+import java.util.Arrays;
+import java.util.List;
+
+import static org.junit.Assert.assertEquals;
+import static org.junit.Assert.assertNotNull;
+
+public class TestHiveActionMapping {
+
+    @Test
+    public void testMappingHiveAction() {
+        final String resourceManager = "${resourceManager}";
+        final String nameNode = "${nameNode}";
+        final List<String> args = Arrays.asList("arg1", "arg2");
+
+        final HiveActionBuilder builder = HiveActionBuilder.create();
+
+        builder.withResourceManager(resourceManager)
+                .withNameNode(nameNode)
+                .withPrepare(new PrepareBuilder()
+                        .withDelete("/path/to/delete")
+                        .withMkdir("/path/to/mkdir")
+                        .build())
+                .withLauncher(new LauncherBuilder()
+                        .withMemoryMb(1024)
+                        .withVCores(2)
+                        .withQueue("default")
+                        .withSharelib("default")
+                        .withViewAcl("default")
+                        .withModifyAcl("default")
+                        .build());
+
+        for (final String arg : args) {
+            builder.withArg(arg);
+        }
+
+        builder.withConfigProperty("propertyName1", "propertyValue1")
+                .withConfigProperty("propertyName2", "propertyValue2");
+
+        final HiveAction action = builder.build();
+
+        final ACTION hive = DozerBeanMapperSingleton.instance().map(action, 
ACTION.class);
+
+        assertEquals(resourceManager, hive.getResourceManager());
+        assertEquals(nameNode, hive.getNameNode());
+        assertNotNull(hive.getPrepare());
+        assertEquals("/path/to/delete", 
hive.getPrepare().getDelete().get(0).getPath());
+        assertEquals("/path/to/mkdir", 
hive.getPrepare().getMkdir().get(0).getPath());
+        assertNotNull(hive.getConfiguration());
+        assertEquals(args, hive.getArgument());
+        assertEquals(1024L, 
hive.getLauncher().getMemoryMbOrVcoresOrJavaOpts().get(0).getValue());
+        assertEquals(2L, 
hive.getLauncher().getMemoryMbOrVcoresOrJavaOpts().get(1).getValue());
+        assertEquals("default", 
hive.getLauncher().getMemoryMbOrVcoresOrJavaOpts().get(2).getValue());
+        assertEquals("default", 
hive.getLauncher().getMemoryMbOrVcoresOrJavaOpts().get(3).getValue());
+        assertEquals("default", 
hive.getLauncher().getMemoryMbOrVcoresOrJavaOpts().get(4).getValue());
+        assertEquals("default", 
hive.getLauncher().getMemoryMbOrVcoresOrJavaOpts().get(5).getValue());
+    }
+}

http://git-wip-us.apache.org/repos/asf/oozie/blob/8a0a6487/fluent-job/fluent-job-api/src/test/java/org/apache/oozie/fluentjob/api/mapping/TestJavaActionMapping.java
----------------------------------------------------------------------
diff --git 
a/fluent-job/fluent-job-api/src/test/java/org/apache/oozie/fluentjob/api/mapping/TestJavaActionMapping.java
 
b/fluent-job/fluent-job-api/src/test/java/org/apache/oozie/fluentjob/api/mapping/TestJavaActionMapping.java
new file mode 100644
index 0000000..ba79298
--- /dev/null
+++ 
b/fluent-job/fluent-job-api/src/test/java/org/apache/oozie/fluentjob/api/mapping/TestJavaActionMapping.java
@@ -0,0 +1,95 @@
+/**
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License.  You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.apache.oozie.fluentjob.api.mapping;
+
+import org.apache.oozie.fluentjob.api.generated.workflow.JAVA;
+import org.apache.oozie.fluentjob.api.action.JavaAction;
+import org.apache.oozie.fluentjob.api.action.JavaActionBuilder;
+import org.apache.oozie.fluentjob.api.action.LauncherBuilder;
+import org.apache.oozie.fluentjob.api.action.PrepareBuilder;
+import org.apache.oozie.fluentjob.api.generated.workflow.JAVA;
+import org.junit.Test;
+
+import java.util.Arrays;
+import java.util.List;
+
+import static org.junit.Assert.assertEquals;
+import static org.junit.Assert.assertNotNull;
+
+public class TestJavaActionMapping {
+
+    public static final String DEFAULT = "default";
+
+    @Test
+    public void testMappingJavaAction() {
+        final String resourceManager = "${resourceManager}";
+        final String nameNode = "${nameNode}";
+        final List<String> args = Arrays.asList("arg1", "arg2");
+
+        final JavaActionBuilder builder = JavaActionBuilder.create();
+
+        builder.withResourceManager(resourceManager)
+                .withNameNode(nameNode)
+                .withPrepare(new PrepareBuilder()
+                        .withDelete("/path/to/delete")
+                        .withMkdir("/path/to/mkdir")
+                        .build())
+                .withLauncher(new LauncherBuilder()
+                        .withMemoryMb(1024)
+                        .withVCores(2)
+                        .withQueue(DEFAULT)
+                        .withSharelib(DEFAULT)
+                        .withViewAcl(DEFAULT)
+                        .withModifyAcl(DEFAULT)
+                        .build())
+                .withMainClass(DEFAULT)
+                .withJavaOptsString(DEFAULT)
+                .withJavaOpt(DEFAULT)
+                .withCaptureOutput(true);
+
+        for (final String arg : args) {
+            builder.withArg(arg);
+        }
+
+        builder.withConfigProperty("propertyName1", "propertyValue1")
+                .withConfigProperty("propertyName2", "propertyValue2");
+
+        final JavaAction action = builder.build();
+
+        final JAVA java = DozerBeanMapperSingleton.instance().map(action, 
JAVA.class);
+
+        assertEquals(resourceManager, java.getResourceManager());
+        assertEquals(nameNode, java.getNameNode());
+        assertNotNull(java.getPrepare());
+        assertEquals("/path/to/delete", 
java.getPrepare().getDelete().get(0).getPath());
+        assertEquals("/path/to/mkdir", 
java.getPrepare().getMkdir().get(0).getPath());
+        assertNotNull(java.getConfiguration());
+        assertEquals(args, java.getArg());
+        assertEquals(1024L, 
java.getLauncher().getMemoryMbOrVcoresOrJavaOpts().get(0).getValue());
+        assertEquals(2L, 
java.getLauncher().getMemoryMbOrVcoresOrJavaOpts().get(1).getValue());
+        assertEquals(DEFAULT, 
java.getLauncher().getMemoryMbOrVcoresOrJavaOpts().get(2).getValue());
+        assertEquals(DEFAULT, 
java.getLauncher().getMemoryMbOrVcoresOrJavaOpts().get(3).getValue());
+        assertEquals(DEFAULT, 
java.getLauncher().getMemoryMbOrVcoresOrJavaOpts().get(4).getValue());
+        assertEquals(DEFAULT, 
java.getLauncher().getMemoryMbOrVcoresOrJavaOpts().get(5).getValue());
+        assertEquals(DEFAULT, java.getMainClass());
+        assertEquals(DEFAULT, java.getJavaOpts());
+        assertEquals(DEFAULT, java.getJavaOpt().get(0));
+        assertNotNull(java.getCaptureOutput());
+    }
+}

http://git-wip-us.apache.org/repos/asf/oozie/blob/8a0a6487/fluent-job/fluent-job-api/src/test/java/org/apache/oozie/fluentjob/api/mapping/TestJoinMapping.java
----------------------------------------------------------------------
diff --git 
a/fluent-job/fluent-job-api/src/test/java/org/apache/oozie/fluentjob/api/mapping/TestJoinMapping.java
 
b/fluent-job/fluent-job-api/src/test/java/org/apache/oozie/fluentjob/api/mapping/TestJoinMapping.java
new file mode 100644
index 0000000..fd8184d
--- /dev/null
+++ 
b/fluent-job/fluent-job-api/src/test/java/org/apache/oozie/fluentjob/api/mapping/TestJoinMapping.java
@@ -0,0 +1,64 @@
+/**
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License.  You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.apache.oozie.fluentjob.api.mapping;
+
+import org.apache.oozie.fluentjob.api.generated.workflow.JOIN;
+import org.apache.oozie.fluentjob.api.dag.Decision;
+import org.apache.oozie.fluentjob.api.dag.DecisionJoin;
+import org.apache.oozie.fluentjob.api.dag.ExplicitNode;
+import org.apache.oozie.fluentjob.api.dag.Fork;
+import org.apache.oozie.fluentjob.api.dag.Join;
+import org.apache.oozie.fluentjob.api.dag.NodeBase;
+import org.junit.Test;
+
+import static org.junit.Assert.assertEquals;
+
+public class TestJoinMapping extends TestControlNodeMappingBase {
+    @Test
+    public void testMappingJoin() {
+        final String joinName = "join";
+        final String childName = "child";
+        final Join join = new Join(joinName, new Fork("fork"));
+
+        final NodeBase child = new ExplicitNode(childName, null);
+
+        child.addParent(join);
+
+        final JOIN mappedJoin = DozerBeanMapperSingleton.instance().map(join, 
JOIN.class);
+
+        assertEquals(joinName, mappedJoin.getName());
+        assertEquals(childName, mappedJoin.getTo());
+    }
+
+    @Test
+    public void testMappingJoinWithDecisionJoin() {
+        final String childName = "child";
+        final Join join = new Join("join", new Fork("fork"));
+
+        final NodeBase decisionJoin = new DecisionJoin("decisionJoin", new 
Decision("decision"));
+        decisionJoin.addParent(join);
+
+        final NodeBase child = new ExplicitNode(childName, null);
+        child.addParent(decisionJoin);
+
+        final JOIN mappedJoin = DozerBeanMapperSingleton.instance().map(join, 
JOIN.class);
+
+        assertEquals(childName, mappedJoin.getTo());
+    }
+}

http://git-wip-us.apache.org/repos/asf/oozie/blob/8a0a6487/fluent-job/fluent-job-api/src/test/java/org/apache/oozie/fluentjob/api/mapping/TestMapReduceActionMapping.java
----------------------------------------------------------------------
diff --git 
a/fluent-job/fluent-job-api/src/test/java/org/apache/oozie/fluentjob/api/mapping/TestMapReduceActionMapping.java
 
b/fluent-job/fluent-job-api/src/test/java/org/apache/oozie/fluentjob/api/mapping/TestMapReduceActionMapping.java
new file mode 100644
index 0000000..356fe7d
--- /dev/null
+++ 
b/fluent-job/fluent-job-api/src/test/java/org/apache/oozie/fluentjob/api/mapping/TestMapReduceActionMapping.java
@@ -0,0 +1,96 @@
+/**
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License.  You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.apache.oozie.fluentjob.api.mapping;
+
+import org.apache.oozie.fluentjob.api.generated.workflow.MAPREDUCE;
+import org.apache.oozie.fluentjob.api.action.MapReduceAction;
+import org.apache.oozie.fluentjob.api.action.MapReduceActionBuilder;
+import org.apache.oozie.fluentjob.api.action.PipesBuilder;
+import org.apache.oozie.fluentjob.api.action.PrepareBuilder;
+import org.apache.oozie.fluentjob.api.action.StreamingBuilder;
+import org.apache.oozie.fluentjob.api.generated.workflow.MAPREDUCE;
+import org.junit.Rule;
+import org.junit.Test;
+import org.junit.rules.ExpectedException;
+
+import java.util.Arrays;
+import java.util.List;
+
+import static org.junit.Assert.assertEquals;
+import static org.junit.Assert.assertNotNull;
+
+
+public class TestMapReduceActionMapping {
+    @Rule
+    public final ExpectedException expectedException = 
ExpectedException.none();
+
+    @Test
+    public void testMappingMapReduceAction() {
+        final String resourceManager = "${resourceManager}";
+        final String nameNode = "${nameNode}";
+
+        final List<String> jobXmls = Arrays.asList("job1.xml", "job2.xml");
+
+        final String configClass = "${configClass}";
+
+        final List<String> files = Arrays.asList("file1", "file2");
+
+        final List<String> archives = Arrays.asList("archive1", "archive2");
+
+        final MapReduceActionBuilder builder = MapReduceActionBuilder.create();
+
+        builder.withResourceManager(resourceManager)
+                .withNameNode(nameNode)
+                .withPrepare(new PrepareBuilder().build())
+                .withStreaming(new StreamingBuilder().build())
+                .withPipes(new PipesBuilder().build());
+
+        for (final String jobXml : jobXmls) {
+            builder.withJobXml(jobXml);
+        }
+
+        builder.withConfigProperty("propertyName1", "propertyValue1")
+                .withConfigProperty("propertyName2", "propertyValue2");
+
+        builder.withConfigClass(configClass);
+
+        for (final String file : files) {
+            builder.withFile(file);
+        }
+
+        for (final String archive : archives) {
+            builder.withArchive(archive);
+        }
+
+        final MapReduceAction action = builder.build();
+
+        final MAPREDUCE mapreduce = 
DozerBeanMapperSingleton.instance().map(action, MAPREDUCE.class);
+
+        assertEquals(resourceManager, mapreduce.getResourceManager());
+        assertEquals(nameNode, mapreduce.getNameNode());
+        assertNotNull(mapreduce.getPrepare());
+        assertNotNull(mapreduce.getStreaming());
+        assertNotNull(mapreduce.getPipes());
+        assertEquals(jobXmls, mapreduce.getJobXml());
+        assertNotNull(mapreduce.getConfiguration());
+        assertEquals(configClass, mapreduce.getConfigClass());
+        assertEquals(files, mapreduce.getFile());
+        assertEquals(archives, mapreduce.getArchive());
+    }
+}

http://git-wip-us.apache.org/repos/asf/oozie/blob/8a0a6487/fluent-job/fluent-job-api/src/test/java/org/apache/oozie/fluentjob/api/mapping/TestMappings.java
----------------------------------------------------------------------
diff --git 
a/fluent-job/fluent-job-api/src/test/java/org/apache/oozie/fluentjob/api/mapping/TestMappings.java
 
b/fluent-job/fluent-job-api/src/test/java/org/apache/oozie/fluentjob/api/mapping/TestMappings.java
new file mode 100644
index 0000000..dd844be
--- /dev/null
+++ 
b/fluent-job/fluent-job-api/src/test/java/org/apache/oozie/fluentjob/api/mapping/TestMappings.java
@@ -0,0 +1,59 @@
+/**
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License.  You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.apache.oozie.fluentjob.api.mapping;
+
+import org.apache.oozie.fluentjob.api.generated.workflow.WORKFLOWAPP;
+import org.apache.oozie.fluentjob.api.action.MapReduceAction;
+import org.apache.oozie.fluentjob.api.action.MapReduceActionBuilder;
+import org.apache.oozie.fluentjob.api.dag.Graph;
+import org.apache.oozie.fluentjob.api.workflow.Workflow;
+import org.apache.oozie.fluentjob.api.workflow.WorkflowBuilder;
+import org.dozer.DozerBeanMapper;
+import org.junit.Test;
+
+import java.util.ArrayList;
+import java.util.List;
+
+import static org.junit.Assert.assertEquals;
+
+public class TestMappings {
+
+    @Test
+    public void 
whenWorkflowWithOneMRActionIsCreatedWORKFLOWAPPIsMappedCorrectly() {
+        final MapReduceAction mr1 = 
MapReduceActionBuilder.create().withName("mr1").build();
+
+        final Workflow workflow = new WorkflowBuilder()
+                .withName("Workflow_to_map")
+                .withDagContainingNode(mr1)
+                .build();
+        final Graph graph = new Graph(workflow);
+
+        final List<String> mappingFiles = new ArrayList<>();
+        mappingFiles.add("dozer_config.xml");
+        mappingFiles.add("mappingGraphToWORKFLOWAPP.xml");
+        mappingFiles.add("action_mappings.xml");
+
+        final DozerBeanMapper mapper = new DozerBeanMapper();
+        mapper.setMappingFiles(mappingFiles);
+
+        final WORKFLOWAPP workflowapp = mapper.map(graph, WORKFLOWAPP.class);
+
+        assertEquals("API and JAXB workflows should have the same names", 
workflow.getName(), workflowapp.getName());
+    }
+}

http://git-wip-us.apache.org/repos/asf/oozie/blob/8a0a6487/fluent-job/fluent-job-api/src/test/java/org/apache/oozie/fluentjob/api/mapping/TestMkdirMapping.java
----------------------------------------------------------------------
diff --git 
a/fluent-job/fluent-job-api/src/test/java/org/apache/oozie/fluentjob/api/mapping/TestMkdirMapping.java
 
b/fluent-job/fluent-job-api/src/test/java/org/apache/oozie/fluentjob/api/mapping/TestMkdirMapping.java
new file mode 100644
index 0000000..b19bfec
--- /dev/null
+++ 
b/fluent-job/fluent-job-api/src/test/java/org/apache/oozie/fluentjob/api/mapping/TestMkdirMapping.java
@@ -0,0 +1,38 @@
+/**
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License.  You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.apache.oozie.fluentjob.api.mapping;
+
+import org.apache.oozie.fluentjob.api.generated.workflow.MKDIR;
+import org.apache.oozie.fluentjob.api.action.Mkdir;
+import org.junit.Test;
+
+import static org.junit.Assert.assertEquals;
+
+public class TestMkdirMapping {
+
+    @Test
+    public void testMappingMkdir() {
+        final String path = "path/to/location";
+        final Mkdir mkdir = new Mkdir(path);
+
+        final MKDIR mkdirJAXB = DozerBeanMapperSingleton.instance().map(mkdir, 
MKDIR.class);
+
+        assertEquals(path, mkdirJAXB.getPath());
+    }
+}

http://git-wip-us.apache.org/repos/asf/oozie/blob/8a0a6487/fluent-job/fluent-job-api/src/test/java/org/apache/oozie/fluentjob/api/mapping/TestParametersMapping.java
----------------------------------------------------------------------
diff --git 
a/fluent-job/fluent-job-api/src/test/java/org/apache/oozie/fluentjob/api/mapping/TestParametersMapping.java
 
b/fluent-job/fluent-job-api/src/test/java/org/apache/oozie/fluentjob/api/mapping/TestParametersMapping.java
new file mode 100644
index 0000000..902d02e
--- /dev/null
+++ 
b/fluent-job/fluent-job-api/src/test/java/org/apache/oozie/fluentjob/api/mapping/TestParametersMapping.java
@@ -0,0 +1,47 @@
+/**
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License.  You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.apache.oozie.fluentjob.api.mapping;
+
+import org.apache.oozie.fluentjob.api.generated.workflow.PARAMETERS;
+import org.apache.oozie.fluentjob.api.workflow.Parameters;
+import org.apache.oozie.fluentjob.api.workflow.ParametersBuilder;
+import org.junit.Test;
+
+import static org.junit.Assert.assertEquals;
+import static org.junit.Assert.assertNull;
+
+public class TestParametersMapping {
+
+    @Test
+    public void testMappingParameters() {
+        final Parameters source = ParametersBuilder.create()
+                .withParameter("name1", "value1")
+                .withParameter("name2", "value2", "description2")
+                .build();
+
+        final PARAMETERS destination = 
DozerBeanMapperSingleton.instance().map(source, PARAMETERS.class);
+
+        assertEquals("name1", destination.getProperty().get(0).getName());
+        assertEquals("value1", destination.getProperty().get(0).getValue());
+        assertNull(destination.getProperty().get(0).getDescription());
+        assertEquals("name2", destination.getProperty().get(1).getName());
+        assertEquals("value2", destination.getProperty().get(1).getValue());
+        assertEquals("description2", 
destination.getProperty().get(1).getDescription());
+    }
+}

http://git-wip-us.apache.org/repos/asf/oozie/blob/8a0a6487/fluent-job/fluent-job-api/src/test/java/org/apache/oozie/fluentjob/api/mapping/TestPigActionMapping.java
----------------------------------------------------------------------
diff --git 
a/fluent-job/fluent-job-api/src/test/java/org/apache/oozie/fluentjob/api/mapping/TestPigActionMapping.java
 
b/fluent-job/fluent-job-api/src/test/java/org/apache/oozie/fluentjob/api/mapping/TestPigActionMapping.java
new file mode 100644
index 0000000..daf67ca
--- /dev/null
+++ 
b/fluent-job/fluent-job-api/src/test/java/org/apache/oozie/fluentjob/api/mapping/TestPigActionMapping.java
@@ -0,0 +1,84 @@
+/**
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License.  You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.apache.oozie.fluentjob.api.mapping;
+
+import org.apache.oozie.fluentjob.api.action.LauncherBuilder;
+import org.apache.oozie.fluentjob.api.action.PigAction;
+import org.apache.oozie.fluentjob.api.action.PigActionBuilder;
+import org.apache.oozie.fluentjob.api.action.PrepareBuilder;
+import org.apache.oozie.fluentjob.api.generated.workflow.PIG;
+import org.junit.Test;
+
+import java.util.Arrays;
+import java.util.List;
+
+import static org.junit.Assert.assertEquals;
+import static org.junit.Assert.assertNotNull;
+
+public class TestPigActionMapping {
+
+    @Test
+    public void testMappingPigAction() {
+        final String resourceManager = "${resourceManager}";
+        final String nameNode = "${nameNode}";
+        final List<String> args = Arrays.asList("arg1", "arg2");
+
+        final PigActionBuilder builder = PigActionBuilder.create();
+
+        builder.withResourceManager(resourceManager)
+                .withNameNode(nameNode)
+                .withPrepare(new PrepareBuilder()
+                        .withDelete("/path/to/delete")
+                        .withMkdir("/path/to/mkdir")
+                        .build())
+                .withLauncher(new LauncherBuilder()
+                        .withMemoryMb(1024)
+                        .withVCores(2)
+                        .withQueue("default")
+                        .withSharelib("default")
+                        .withViewAcl("default")
+                        .withModifyAcl("default")
+                        .build());
+
+        for (final String arg : args) {
+            builder.withArg(arg);
+        }
+
+        builder.withConfigProperty("propertyName1", "propertyValue1")
+                .withConfigProperty("propertyName2", "propertyValue2");
+
+        final PigAction action = builder.build();
+
+        final PIG pig = DozerBeanMapperSingleton.instance().map(action, 
PIG.class);
+
+        assertEquals(resourceManager, pig.getResourceManager());
+        assertEquals(nameNode, pig.getNameNode());
+        assertNotNull(pig.getPrepare());
+        assertEquals("/path/to/delete", 
pig.getPrepare().getDelete().get(0).getPath());
+        assertEquals("/path/to/mkdir", 
pig.getPrepare().getMkdir().get(0).getPath());
+        assertNotNull(pig.getConfiguration());
+        assertEquals(args, pig.getArgument());
+        assertEquals(1024L, 
pig.getLauncher().getMemoryMbOrVcoresOrJavaOpts().get(0).getValue());
+        assertEquals(2L, 
pig.getLauncher().getMemoryMbOrVcoresOrJavaOpts().get(1).getValue());
+        assertEquals("default", 
pig.getLauncher().getMemoryMbOrVcoresOrJavaOpts().get(2).getValue());
+        assertEquals("default", 
pig.getLauncher().getMemoryMbOrVcoresOrJavaOpts().get(3).getValue());
+        assertEquals("default", 
pig.getLauncher().getMemoryMbOrVcoresOrJavaOpts().get(4).getValue());
+        assertEquals("default", 
pig.getLauncher().getMemoryMbOrVcoresOrJavaOpts().get(5).getValue());
+    }
+}

http://git-wip-us.apache.org/repos/asf/oozie/blob/8a0a6487/fluent-job/fluent-job-api/src/test/java/org/apache/oozie/fluentjob/api/mapping/TestPipesMapping.java
----------------------------------------------------------------------
diff --git 
a/fluent-job/fluent-job-api/src/test/java/org/apache/oozie/fluentjob/api/mapping/TestPipesMapping.java
 
b/fluent-job/fluent-job-api/src/test/java/org/apache/oozie/fluentjob/api/mapping/TestPipesMapping.java
new file mode 100644
index 0000000..9cbab8f
--- /dev/null
+++ 
b/fluent-job/fluent-job-api/src/test/java/org/apache/oozie/fluentjob/api/mapping/TestPipesMapping.java
@@ -0,0 +1,57 @@
+/**
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License.  You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.apache.oozie.fluentjob.api.mapping;
+
+import org.apache.oozie.fluentjob.api.generated.workflow.PIPES;
+import org.apache.oozie.fluentjob.api.action.Pipes;
+import org.apache.oozie.fluentjob.api.action.PipesBuilder;
+import org.junit.Test;
+
+import static org.junit.Assert.assertEquals;
+
+public class TestPipesMapping {
+
+    @Test
+    public void testMappingPipes() {
+        final String map = "map";
+        final String reduce = "reduce";
+        final String inputformat = "inputformat";
+        final String partitioner = "partitioner";
+        final String writer = "writer";
+        final String program = "program";
+
+        final Pipes pipes = new PipesBuilder()
+                .withMap(map)
+                .withReduce(reduce)
+                .withInputformat(inputformat)
+                .withPartitioner(partitioner)
+                .withWriter(writer)
+                .withProgram(program)
+                .build();
+
+        final PIPES pipesJAXB = DozerBeanMapperSingleton.instance().map(pipes, 
PIPES.class);
+
+        assertEquals(map, pipesJAXB.getMap());
+        assertEquals(reduce, pipesJAXB.getReduce());
+        assertEquals(inputformat, pipesJAXB.getInputformat());
+        assertEquals(partitioner, pipesJAXB.getPartitioner());
+        assertEquals(writer, pipesJAXB.getWriter());
+        assertEquals(program, pipesJAXB.getProgram());
+    }
+}

http://git-wip-us.apache.org/repos/asf/oozie/blob/8a0a6487/fluent-job/fluent-job-api/src/test/java/org/apache/oozie/fluentjob/api/mapping/TestPrepareMapping.java
----------------------------------------------------------------------
diff --git 
a/fluent-job/fluent-job-api/src/test/java/org/apache/oozie/fluentjob/api/mapping/TestPrepareMapping.java
 
b/fluent-job/fluent-job-api/src/test/java/org/apache/oozie/fluentjob/api/mapping/TestPrepareMapping.java
new file mode 100644
index 0000000..d4c343f
--- /dev/null
+++ 
b/fluent-job/fluent-job-api/src/test/java/org/apache/oozie/fluentjob/api/mapping/TestPrepareMapping.java
@@ -0,0 +1,65 @@
+/**
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License.  You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.apache.oozie.fluentjob.api.mapping;
+
+import org.apache.oozie.fluentjob.api.generated.workflow.DELETE;
+import org.apache.oozie.fluentjob.api.generated.workflow.MKDIR;
+import org.apache.oozie.fluentjob.api.generated.workflow.PREPARE;
+import org.apache.oozie.fluentjob.api.action.Prepare;
+import org.apache.oozie.fluentjob.api.action.PrepareBuilder;
+import org.junit.Test;
+
+import java.util.List;
+
+import static org.junit.Assert.assertEquals;
+
+public class TestPrepareMapping {
+
+    @Test
+    public void testMappingPrepare() {
+        final String deletePath1 = "path/to/delete/location1";
+        final String deletePath2 = "path/to/delete/location2";
+
+        final String mkdirPath1 = "path/to/mkdir/location1";
+        final String mkdirPath2 = "path/to/mkdir/location2";
+
+        final Prepare prepare = new PrepareBuilder()
+                .withDelete(deletePath1, false)
+                .withDelete(deletePath2, false)
+                .withMkdir(mkdirPath1)
+                .withMkdir(mkdirPath2)
+                .build();
+
+        final PREPARE prepareJAXB = 
DozerBeanMapperSingleton.instance().map(prepare, PREPARE.class);
+
+        final List<DELETE> deletesJAXB = prepareJAXB.getDelete();
+        final DELETE delete1JAXB = deletesJAXB.get(0);
+        final DELETE delete2JAXB = deletesJAXB.get(1);
+
+        final List<MKDIR> mkdirsJAXB = prepareJAXB.getMkdir();
+        final MKDIR mkdir1JAXB = mkdirsJAXB.get(0);
+        final MKDIR mkdir2JAXB = mkdirsJAXB.get(1);
+
+        assertEquals(deletePath1, delete1JAXB.getPath());
+        assertEquals(deletePath2, delete2JAXB.getPath());
+
+        assertEquals(mkdirPath1, mkdir1JAXB.getPath());
+        assertEquals(mkdirPath2, mkdir2JAXB.getPath());
+    }
+}

http://git-wip-us.apache.org/repos/asf/oozie/blob/8a0a6487/fluent-job/fluent-job-api/src/test/java/org/apache/oozie/fluentjob/api/mapping/TestShellActionMapping.java
----------------------------------------------------------------------
diff --git 
a/fluent-job/fluent-job-api/src/test/java/org/apache/oozie/fluentjob/api/mapping/TestShellActionMapping.java
 
b/fluent-job/fluent-job-api/src/test/java/org/apache/oozie/fluentjob/api/mapping/TestShellActionMapping.java
new file mode 100644
index 0000000..20972ca
--- /dev/null
+++ 
b/fluent-job/fluent-job-api/src/test/java/org/apache/oozie/fluentjob/api/mapping/TestShellActionMapping.java
@@ -0,0 +1,92 @@
+/**
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License.  You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.apache.oozie.fluentjob.api.mapping;
+
+import org.apache.oozie.fluentjob.api.action.LauncherBuilder;
+import org.apache.oozie.fluentjob.api.action.PrepareBuilder;
+import org.apache.oozie.fluentjob.api.action.ShellAction;
+import org.apache.oozie.fluentjob.api.action.ShellActionBuilder;
+import org.apache.oozie.fluentjob.api.generated.action.shell.ACTION;
+import org.junit.Test;
+
+import java.util.Arrays;
+import java.util.List;
+
+import static org.junit.Assert.assertEquals;
+import static org.junit.Assert.assertNotNull;
+
+public class TestShellActionMapping {
+
+    public static final String DEFAULT = "default";
+
+    @Test
+    public void testMappingShellAction() {
+        final String resourceManager = "${resourceManager}";
+        final String nameNode = "${nameNode}";
+        final List<String> args = Arrays.asList("arg1", "arg2");
+
+        final ShellActionBuilder builder = ShellActionBuilder.create();
+
+        builder.withResourceManager(resourceManager)
+                .withNameNode(nameNode)
+                .withPrepare(new PrepareBuilder()
+                        .withDelete("/path/to/delete")
+                        .withMkdir("/path/to/mkdir")
+                        .build())
+                .withLauncher(new LauncherBuilder()
+                        .withMemoryMb(1024)
+                        .withVCores(2)
+                        .withQueue(DEFAULT)
+                        .withSharelib(DEFAULT)
+                        .withViewAcl(DEFAULT)
+                        .withModifyAcl(DEFAULT)
+                        .build())
+                .withExecutable(DEFAULT)
+                .withEnvironmentVariable(DEFAULT)
+                .withCaptureOutput(true);
+
+        for (final String arg : args) {
+            builder.withArgument(arg);
+        }
+
+        builder.withConfigProperty("propertyName1", "propertyValue1")
+                .withConfigProperty("propertyName2", "propertyValue2");
+
+        final ShellAction action = builder.build();
+
+        final ACTION shell = DozerBeanMapperSingleton.instance().map(action, 
ACTION.class);
+
+        assertEquals(resourceManager, shell.getResourceManager());
+        assertEquals(nameNode, shell.getNameNode());
+        assertNotNull(shell.getPrepare());
+        assertEquals("/path/to/delete", 
shell.getPrepare().getDelete().get(0).getPath());
+        assertEquals("/path/to/mkdir", 
shell.getPrepare().getMkdir().get(0).getPath());
+        assertNotNull(shell.getConfiguration());
+        assertEquals(args, shell.getArgument());
+        assertEquals(1024L, 
shell.getLauncher().getMemoryMbOrVcoresOrJavaOpts().get(0).getValue());
+        assertEquals(2L, 
shell.getLauncher().getMemoryMbOrVcoresOrJavaOpts().get(1).getValue());
+        assertEquals(DEFAULT, 
shell.getLauncher().getMemoryMbOrVcoresOrJavaOpts().get(2).getValue());
+        assertEquals(DEFAULT, 
shell.getLauncher().getMemoryMbOrVcoresOrJavaOpts().get(3).getValue());
+        assertEquals(DEFAULT, 
shell.getLauncher().getMemoryMbOrVcoresOrJavaOpts().get(4).getValue());
+        assertEquals(DEFAULT, 
shell.getLauncher().getMemoryMbOrVcoresOrJavaOpts().get(5).getValue());
+        assertEquals(DEFAULT, shell.getExec());
+        assertEquals(DEFAULT, shell.getEnvVar().get(0));
+        assertNotNull(shell.getCaptureOutput());
+    }
+}

http://git-wip-us.apache.org/repos/asf/oozie/blob/8a0a6487/fluent-job/fluent-job-api/src/test/java/org/apache/oozie/fluentjob/api/mapping/TestSparkActionMapping.java
----------------------------------------------------------------------
diff --git 
a/fluent-job/fluent-job-api/src/test/java/org/apache/oozie/fluentjob/api/mapping/TestSparkActionMapping.java
 
b/fluent-job/fluent-job-api/src/test/java/org/apache/oozie/fluentjob/api/mapping/TestSparkActionMapping.java
new file mode 100644
index 0000000..2b003b7
--- /dev/null
+++ 
b/fluent-job/fluent-job-api/src/test/java/org/apache/oozie/fluentjob/api/mapping/TestSparkActionMapping.java
@@ -0,0 +1,98 @@
+/**
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License.  You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.apache.oozie.fluentjob.api.mapping;
+
+import org.apache.oozie.fluentjob.api.action.LauncherBuilder;
+import org.apache.oozie.fluentjob.api.action.PrepareBuilder;
+import org.apache.oozie.fluentjob.api.action.SparkAction;
+import org.apache.oozie.fluentjob.api.action.SparkActionBuilder;
+import org.apache.oozie.fluentjob.api.generated.action.spark.ACTION;
+import org.junit.Test;
+
+import java.util.Arrays;
+import java.util.List;
+
+import static org.junit.Assert.assertEquals;
+import static org.junit.Assert.assertNotNull;
+
+public class TestSparkActionMapping {
+
+    public static final String DEFAULT = "default";
+
+    @Test
+    public void testMappingSparkAction() {
+        final String resourceManager = "${resourceManager}";
+        final String nameNode = "${nameNode}";
+        final List<String> args = Arrays.asList("arg1", "arg2");
+
+        final SparkActionBuilder builder = SparkActionBuilder.create();
+
+        builder.withResourceManager(resourceManager)
+                .withNameNode(nameNode)
+                .withPrepare(new PrepareBuilder()
+                        .withDelete("/path/to/delete")
+                        .withMkdir("/path/to/mkdir")
+                        .build())
+                .withLauncher(new LauncherBuilder()
+                        .withMemoryMb(1024)
+                        .withVCores(2)
+                        .withQueue(DEFAULT)
+                        .withSharelib(DEFAULT)
+                        .withViewAcl(DEFAULT)
+                        .withModifyAcl(DEFAULT)
+                        .build())
+                .withMaster(DEFAULT)
+                .withMode(DEFAULT)
+                .withActionName(DEFAULT)
+                .withActionClass(DEFAULT)
+                .withJar(DEFAULT)
+                .withSparkOpts(DEFAULT);
+
+        for (final String arg : args) {
+            builder.withArg(arg);
+        }
+
+        builder.withConfigProperty("propertyName1", "propertyValue1")
+                .withConfigProperty("propertyName2", "propertyValue2");
+
+        final SparkAction action = builder.build();
+
+        final ACTION spark = DozerBeanMapperSingleton.instance().map(action, 
ACTION.class);
+
+        assertEquals(resourceManager, spark.getResourceManager());
+        assertEquals(nameNode, spark.getNameNode());
+        assertNotNull(spark.getPrepare());
+        assertEquals("/path/to/delete", 
spark.getPrepare().getDelete().get(0).getPath());
+        assertEquals("/path/to/mkdir", 
spark.getPrepare().getMkdir().get(0).getPath());
+        assertNotNull(spark.getConfiguration());
+        assertEquals(args, spark.getArg());
+        assertEquals(1024L, 
spark.getLauncher().getMemoryMbOrVcoresOrJavaOpts().get(0).getValue());
+        assertEquals(2L, 
spark.getLauncher().getMemoryMbOrVcoresOrJavaOpts().get(1).getValue());
+        assertEquals(DEFAULT, 
spark.getLauncher().getMemoryMbOrVcoresOrJavaOpts().get(2).getValue());
+        assertEquals(DEFAULT, 
spark.getLauncher().getMemoryMbOrVcoresOrJavaOpts().get(3).getValue());
+        assertEquals(DEFAULT, 
spark.getLauncher().getMemoryMbOrVcoresOrJavaOpts().get(4).getValue());
+        assertEquals(DEFAULT, 
spark.getLauncher().getMemoryMbOrVcoresOrJavaOpts().get(5).getValue());
+        assertEquals(DEFAULT, spark.getMaster());
+        assertEquals(DEFAULT, spark.getMode());
+        assertEquals(DEFAULT, spark.getName());
+        assertEquals(DEFAULT, spark.getClazz());
+        assertEquals(DEFAULT, spark.getJar());
+        assertEquals(DEFAULT, spark.getSparkOpts());
+    }
+}

http://git-wip-us.apache.org/repos/asf/oozie/blob/8a0a6487/fluent-job/fluent-job-api/src/test/java/org/apache/oozie/fluentjob/api/mapping/TestSqoopActionMapping.java
----------------------------------------------------------------------
diff --git 
a/fluent-job/fluent-job-api/src/test/java/org/apache/oozie/fluentjob/api/mapping/TestSqoopActionMapping.java
 
b/fluent-job/fluent-job-api/src/test/java/org/apache/oozie/fluentjob/api/mapping/TestSqoopActionMapping.java
new file mode 100644
index 0000000..75348e8
--- /dev/null
+++ 
b/fluent-job/fluent-job-api/src/test/java/org/apache/oozie/fluentjob/api/mapping/TestSqoopActionMapping.java
@@ -0,0 +1,89 @@
+/**
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License.  You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.apache.oozie.fluentjob.api.mapping;
+
+import org.apache.oozie.fluentjob.api.generated.action.sqoop.ACTION;
+import org.apache.oozie.fluentjob.api.action.LauncherBuilder;
+import org.apache.oozie.fluentjob.api.action.PrepareBuilder;
+import org.apache.oozie.fluentjob.api.action.SqoopAction;
+import org.apache.oozie.fluentjob.api.action.SqoopActionBuilder;
+import org.apache.oozie.fluentjob.api.generated.action.sqoop.ACTION;
+import org.junit.Test;
+
+import java.util.Arrays;
+import java.util.List;
+
+import static org.junit.Assert.assertEquals;
+import static org.junit.Assert.assertNotNull;
+
+public class TestSqoopActionMapping {
+
+    public static final String DEFAULT = "default";
+
+    @Test
+    public void testMappingSqoopAction() {
+        final String resourceManager = "${resourceManager}";
+        final String nameNode = "${nameNode}";
+        final List<String> args = Arrays.asList("arg1", "arg2");
+
+        final SqoopActionBuilder builder = SqoopActionBuilder.create();
+
+        builder.withResourceManager(resourceManager)
+                .withNameNode(nameNode)
+                .withPrepare(new PrepareBuilder()
+                        .withDelete("/path/to/delete")
+                        .withMkdir("/path/to/mkdir")
+                        .build())
+                .withLauncher(new LauncherBuilder()
+                        .withMemoryMb(1024)
+                        .withVCores(2)
+                        .withQueue(DEFAULT)
+                        .withSharelib(DEFAULT)
+                        .withViewAcl(DEFAULT)
+                        .withModifyAcl(DEFAULT)
+                        .build())
+                .withCommand(DEFAULT);
+
+        for (final String arg : args) {
+            builder.withArgument(arg);
+        }
+
+        builder.withConfigProperty("propertyName1", "propertyValue1")
+                .withConfigProperty("propertyName2", "propertyValue2");
+
+        final SqoopAction action = builder.build();
+
+        final ACTION sqoop = DozerBeanMapperSingleton.instance().map(action, 
ACTION.class);
+
+        assertEquals(resourceManager, sqoop.getResourceManager());
+        assertEquals(nameNode, sqoop.getNameNode());
+        assertNotNull(sqoop.getPrepare());
+        assertEquals("/path/to/delete", 
sqoop.getPrepare().getDelete().get(0).getPath());
+        assertEquals("/path/to/mkdir", 
sqoop.getPrepare().getMkdir().get(0).getPath());
+        assertNotNull(sqoop.getConfiguration());
+        assertEquals(args, sqoop.getArg());
+        assertEquals(1024L, 
sqoop.getLauncher().getMemoryMbOrVcoresOrJavaOpts().get(0).getValue());
+        assertEquals(2L, 
sqoop.getLauncher().getMemoryMbOrVcoresOrJavaOpts().get(1).getValue());
+        assertEquals(DEFAULT, 
sqoop.getLauncher().getMemoryMbOrVcoresOrJavaOpts().get(2).getValue());
+        assertEquals(DEFAULT, 
sqoop.getLauncher().getMemoryMbOrVcoresOrJavaOpts().get(3).getValue());
+        assertEquals(DEFAULT, 
sqoop.getLauncher().getMemoryMbOrVcoresOrJavaOpts().get(4).getValue());
+        assertEquals(DEFAULT, 
sqoop.getLauncher().getMemoryMbOrVcoresOrJavaOpts().get(5).getValue());
+        assertEquals(DEFAULT, sqoop.getCommand());
+    }
+}

http://git-wip-us.apache.org/repos/asf/oozie/blob/8a0a6487/fluent-job/fluent-job-api/src/test/java/org/apache/oozie/fluentjob/api/mapping/TestSshActionMapping.java
----------------------------------------------------------------------
diff --git 
a/fluent-job/fluent-job-api/src/test/java/org/apache/oozie/fluentjob/api/mapping/TestSshActionMapping.java
 
b/fluent-job/fluent-job-api/src/test/java/org/apache/oozie/fluentjob/api/mapping/TestSshActionMapping.java
new file mode 100644
index 0000000..e47fb1f
--- /dev/null
+++ 
b/fluent-job/fluent-job-api/src/test/java/org/apache/oozie/fluentjob/api/mapping/TestSshActionMapping.java
@@ -0,0 +1,59 @@
+/**
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License.  You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.apache.oozie.fluentjob.api.mapping;
+
+import org.apache.oozie.fluentjob.api.action.SshAction;
+import org.apache.oozie.fluentjob.api.action.SshActionBuilder;
+import org.apache.oozie.fluentjob.api.generated.action.ssh.ACTION;
+import org.junit.Test;
+
+import java.util.Arrays;
+import java.util.List;
+
+import static org.junit.Assert.assertEquals;
+import static org.junit.Assert.assertNotNull;
+
+public class TestSshActionMapping {
+
+    public static final String DEFAULT = "default";
+
+    @Test
+    public void testMappingSshAction() {
+        final List<String> args = Arrays.asList("arg1", "arg2");
+
+        final SshActionBuilder builder = SshActionBuilder.create();
+
+        builder.withHost(DEFAULT)
+                .withCommand(DEFAULT)
+                .withCaptureOutput(true);
+
+        for (final String arg : args) {
+            builder.withArg(arg);
+        }
+
+        final SshAction action = builder.build();
+
+        final ACTION ssh = DozerBeanMapperSingleton.instance().map(action, 
ACTION.class);
+
+        assertEquals(DEFAULT, ssh.getHost());
+        assertEquals(DEFAULT, ssh.getCommand());
+        assertEquals(args, ssh.getArgs());
+        assertNotNull(ssh.getCaptureOutput());
+    }
+}

http://git-wip-us.apache.org/repos/asf/oozie/blob/8a0a6487/fluent-job/fluent-job-api/src/test/java/org/apache/oozie/fluentjob/api/mapping/TestStartMapping.java
----------------------------------------------------------------------
diff --git 
a/fluent-job/fluent-job-api/src/test/java/org/apache/oozie/fluentjob/api/mapping/TestStartMapping.java
 
b/fluent-job/fluent-job-api/src/test/java/org/apache/oozie/fluentjob/api/mapping/TestStartMapping.java
new file mode 100644
index 0000000..ffd477b
--- /dev/null
+++ 
b/fluent-job/fluent-job-api/src/test/java/org/apache/oozie/fluentjob/api/mapping/TestStartMapping.java
@@ -0,0 +1,61 @@
+/**
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License.  You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.apache.oozie.fluentjob.api.mapping;
+
+import org.apache.oozie.fluentjob.api.generated.workflow.START;
+import org.apache.oozie.fluentjob.api.dag.Decision;
+import org.apache.oozie.fluentjob.api.dag.DecisionJoin;
+import org.apache.oozie.fluentjob.api.dag.ExplicitNode;
+import org.apache.oozie.fluentjob.api.dag.NodeBase;
+import org.apache.oozie.fluentjob.api.dag.Start;
+import org.junit.Test;
+
+import static org.junit.Assert.assertEquals;
+
+public class TestStartMapping extends TestControlNodeMappingBase {
+
+    @Test
+    public void testMappingStart() {
+        final String childName = "child";
+        final Start start = new Start("start");
+        final NodeBase child = new ExplicitNode(childName, null);
+
+        child.addParent(start);
+
+        final START mappedStart = 
DozerBeanMapperSingleton.instance().map(start, START.class);
+
+        assertEquals(childName, mappedStart.getTo());
+    }
+
+    @Test
+    public void testMappingStartWithDecisionJoin() {
+        final String childName = "child";
+        final Start start = new Start("start");
+
+        final NodeBase decisionJoin = new DecisionJoin("decisionJoin", new 
Decision("decision"));
+        decisionJoin.addParent(start);
+
+        final NodeBase child = new ExplicitNode(childName, null);
+        child.addParent(decisionJoin);
+
+        final START mappedStart = 
DozerBeanMapperSingleton.instance().map(start, START.class);
+
+        assertEquals(childName, mappedStart.getTo());
+    }
+}

http://git-wip-us.apache.org/repos/asf/oozie/blob/8a0a6487/fluent-job/fluent-job-api/src/test/java/org/apache/oozie/fluentjob/api/mapping/TestStreamingMapping.java
----------------------------------------------------------------------
diff --git 
a/fluent-job/fluent-job-api/src/test/java/org/apache/oozie/fluentjob/api/mapping/TestStreamingMapping.java
 
b/fluent-job/fluent-job-api/src/test/java/org/apache/oozie/fluentjob/api/mapping/TestStreamingMapping.java
new file mode 100644
index 0000000..60509f5
--- /dev/null
+++ 
b/fluent-job/fluent-job-api/src/test/java/org/apache/oozie/fluentjob/api/mapping/TestStreamingMapping.java
@@ -0,0 +1,64 @@
+/**
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License.  You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.apache.oozie.fluentjob.api.mapping;
+
+import org.apache.oozie.fluentjob.api.generated.workflow.STREAMING;
+import org.apache.oozie.fluentjob.api.action.Streaming;
+import org.apache.oozie.fluentjob.api.action.StreamingBuilder;
+import org.junit.Test;
+
+import java.util.Arrays;
+import java.util.List;
+
+import static org.junit.Assert.assertEquals;
+
+public class TestStreamingMapping {
+
+    @Test
+    public void testMappingStreaming() {
+        final String mapper = "mapper";
+        final String reducer = "reducer";
+        final String recordReader = "recordReader";
+        final List<String> recordReaderMappings = Arrays.asList("mapping1", 
"mapping2");
+        final List<String> envs = Arrays.asList("env1", "env2");
+
+        final StreamingBuilder builder = new StreamingBuilder();
+        builder.withMapper(mapper)
+                .withReducer(reducer)
+                .withRecordReader(recordReader);
+
+        for (final String recordReaderMapping : recordReaderMappings) {
+            builder.withRecordReaderMapping(recordReaderMapping);
+        }
+
+        for (final String env : envs) {
+            builder.withEnv(env);
+        }
+
+        final Streaming streaming = builder.build();
+
+        final STREAMING streamingJAXB = 
DozerBeanMapperSingleton.instance().map(streaming, STREAMING.class);
+
+        assertEquals(mapper, streamingJAXB.getMapper());
+        assertEquals(reducer, streamingJAXB.getReducer());
+        assertEquals(recordReader, streamingJAXB.getRecordReader());
+        assertEquals(recordReaderMappings, 
streamingJAXB.getRecordReaderMapping());
+        assertEquals(envs, streamingJAXB.getEnv());
+    }
+}

Reply via email to