/* * Copyright (c) 2015 Red Hat, Inc. and/or its affiliates. * * All rights reserved. This program and the accompanying materials * are made available under the terms of the Eclipse Public License v1.0 * which accompanies this distribution, and is available at * http://www.eclipse.org/legal/epl-v10.html * * Contributors: * Cheng Fang - Initial API and implementation */ package org.jberet.job.model; import java.util.ArrayList; import java.util.List; /** * Builder class for building a single {@link Decision}. After the decision is built, the same {@code DecisionBuilder} * instance should not be reused to build another decision. * <p/> * This class does not support multi-threaded access or modification. Usage example: * <p/> * <pre> * Decision decision = new DecisionBuilder("decision1", "decider1") * .failOn("FAIL").exitStatus() * .stopOn("STOP").restartFrom(stepName).exitStatus() * .nextOn("NEXT").to(stepName) * .endOn("*").exitStatus(stepName) * .build() * </pre> * * @see JobBuilder * @see FlowBuilder * @see SplitBuilder * @see StepBuilder * * @since 1.2.0 */ public final class DecisionBuilder extends AbstractPropertiesBuilder<DecisionBuilder> { private final String id; private final String ref; private final List<Transition> transitions = new ArrayList<Transition>(); /** * Constructs a {@code DecisionBuilder} for building a {@linkplain Decision decision} with the specified {@code id} and * decider name ({@code deciderRef}). * * @param id decision id * @param deciderRef decider artifact name */ public DecisionBuilder(final String id, final String deciderRef) { this.id = id; this.ref = deciderRef; } /** * Sets {@code end} transition condition for the decision. This method does NOT return the current {@code DecisionBuilder} * instance; instead, it returns an instance of {@link org.jberet.job.model.Transition.End}, which can be further * operated on. Invoking {@link org.jberet.job.model.Transition.End#exitStatus(String...)} will end the operation on * {@code Transition.End} and return the current {@code DecisionBuilder}. For example, * <p/> * <pre> * endOn("END").exitStatus("new status for end").<other DecisionBuilder methods> * </pre> * * @param exitStatusCondition exit status condition to trigger "end" action (may contain wildcard ? and *) * @return an instance of {@code Transition.End<DecisionBuilder>} * * @see org.jberet.job.model.Transition.End * @see StepBuilder#endOn(java.lang.String) * @see FlowBuilder#endOn(String) */ public Transition.End<DecisionBuilder> endOn(final String exitStatusCondition) { final Transition.End<DecisionBuilder> end = new Transition.End<DecisionBuilder>(exitStatusCondition); end.enclosingBuilder = this; transitions.add(end); return end; } /** * Sets {@code fail} transition condition for the decision. This method does NOT return the current {@code DecisionBuilder} * instance; instead, it returns an instance of {@link org.jberet.job.model.Transition.Fail}, which can be further * operated on. Invoking {@link org.jberet.job.model.Transition.Fail#exitStatus(String...)} will end the operation on * {@code Transition.Fail} and return the current {@code DecisionBuilder}. For example, * <p/> * <pre> * failOn("FAIL").exitStatus("new status for fail").<other DecisionBuilder methods> * </pre> * * @param exitStatusCondition exit status condition to trigger "fail" action (may contain wildcard ? and *) * @return an instance of {@code Transition.Fail<DecisionBuilder>} * * @see org.jberet.job.model.Transition.Fail * @see StepBuilder#failOn(java.lang.String) * @see FlowBuilder#failOn(String) */ public Transition.Fail<DecisionBuilder> failOn(final String exitStatusCondition) { final Transition.Fail<DecisionBuilder> fail = new Transition.Fail<DecisionBuilder>(exitStatusCondition); fail.enclosingBuilder = this; transitions.add(fail); return fail; } /** * Sets {@code stop} transition condition for the decision. This method does NOT return the current {@code DecisionBuilder} * instance; instead, it returns an instance of {@link org.jberet.job.model.Transition.Stop}, which can be further * operated on. Invoking {@link org.jberet.job.model.Transition.Stop#exitStatus(String...)} will end the operation on * {@code Transition.Stop} and return the current {@code DecisionBuilder}. For example, * <p/> * <pre> * stopOn("STOP").restartFrom("step1").exitStatus().<other DecisionBuilder methods> * </pre> * * @param exitStatusCondition exit status condition to trigger "stop" action (may contain wildcard ? and *) * @return an instance of {@code Transition.Stop<DecisionBuilder>} * * @see org.jberet.job.model.Transition.Stop * @see StepBuilder#stopOn(java.lang.String) * @see FlowBuilder#stopOn(String) */ public Transition.Stop<DecisionBuilder> stopOn(final String exitStatusCondition) { final Transition.Stop<DecisionBuilder> stop = new Transition.Stop<DecisionBuilder>(exitStatusCondition, null); stop.enclosingBuilder = this; transitions.add(stop); return stop; } /** * Sets {@code next} transition condition for the decision. This method does NOT return the current {@code DecisionBuilder} * instance; instead, it returns an instance of {@link org.jberet.job.model.Transition.Next}, which can be further * operated on. Invoking {@link org.jberet.job.model.Transition.Next#to(String)} will end the operation on * {@code Transition.Next} and return the current {@code DecisionBuilder}. For example, * <p/> * <pre> * nextOn("*").to("step2").<other DecisionBuilder methods> * </pre> * @param exitStatusCondition exit status condition to trigger "next" action (may contain wildcard ? and *) * @return an instance of {@code Transition.Next<DecisionBuilder>} * * @see org.jberet.job.model.Transition.Next * @see StepBuilder#nextOn(java.lang.String) * @see FlowBuilder#nextOn(String) */ public Transition.Next<DecisionBuilder> nextOn(final String exitStatusCondition) { final Transition.Next<DecisionBuilder> nx = new Transition.Next<DecisionBuilder>(exitStatusCondition); nx.enclosingBuilder = this; transitions.add(nx); return nx; } /** * Builds the decision. * * @return a decision built by this {@code DecisionBuilder} */ public Decision build() { final Decision decision = new Decision(id, ref); decision.getTransitionElements().addAll(this.transitions); if (nameValues.size() > 0) { decision.setProperties(nameValuesToProperties()); } return decision; } }