设计模式之-状态模式

最近接手了一个发布系统的开发需求,根据设计原型图,可以初步看出来是一个过程流转的过程,所以想到了用状态机模式来实现。

 

一个简单的发布会包括这些流程,每一个节点的执行取决于上一个节点的执行结果。如果上一个节点执行成功,则流转到下一个节点;如果上一个异常,则直接流转到异常状态,最终都会到达完成状态。所以完成的标志会是成功和异常两种来区分。

状态模式需要一个状态接口,还有一系列具体的状态实现类,这些类对应着状态流转图中的各个节点,需要做的事情可以放在具体的实现类中去。

public interface StateMachine {
void transferState(State state, Context context); }

StateMachine接口负责定义状态流转的动作,实现类需要实现方法,并且保证流程能够向后流转。

public class PreCompileState implements StateMachine {

    @Override
    public void transferState(State state, Context context) {
        StateHandler handler = StateManager.getHandler(context);
        handler.handle(context);
    }
}
public class CompileState implements StateMachine {

    @Override
    public void transferState(State state, Context context) {
        StateHandler handler = StateManager.getHandler(context);
        handler.handle(context);
    }
}
public class ExceptionState implements StateMachine {

    @Override
    public void transferState(State state, Context context) {
        StateHandler handler = StateHandlerManager.getHandler(context);
        handler.handle(context);
    }
}
public class FinishState implements StateMachine {

    @Override
    public void transferState(State state, Context context) {
        StateHandler handler = StateHandlerManager.getHandler(context);
        handler.handle(context);
    }
}

每个实现类都只负责该状态下自己的事情,拿到自己状态的handler进行实际的业务处理。

现在看下StateHandlerManager管理类做了什么。

public class StateHandlerManager {

    private static Map<State, Class<?>> clazzMap = new HashMap<>();

    public static void trigger(Context context) {

        StateHandler handler = getHandler(context);

        assert handler != null;

        handler.handle(context);
    }

    public static StateHandler getHandler(Context context) {
        StateHandler handler = getHandler(context.getState());
        if (handler == null) {
            init();
        }
        return getHandler(context.getState());
    }

    public static void init() {
        clazzMap.put(State.PRE_COMPILE, PreCompileHandler.class);
        clazzMap.put(State.COMPILE, CompileHandler.class);
        clazzMap.put(State.BACKUP, BackupHandler.class);
        clazzMap.put(State.SQL_EXECUTION, SqlExecutionHandler.class);
        clazzMap.put(State.DEPLOY, DeployHandler.class);
        clazzMap.put(State.FINISH, FinishHandler.class);
        clazzMap.put(State.EXCEPTION, ExceptionHandler.class);
    }

    public static StateHandler getHandler(State state) {
        Class<?> clazz = clazzMap.get(state);
        if (clazz == null) {
            return null;
        }
        return BeanHolder.getBean(clazz);
    }
}

 Handler做的事情如下

public interface StateHandler<T> {

    /**
     * @param t
     */
    void handle(T t);
}

这些状态节点维护了自己的业务,接下来就需要状态流转。异常处理如何确定下一步流程,其他具体流转的规则需要自己定义。之后会把源码放到GitHub上。

未完待续....

posted @ 2020-07-23 14:25  caizhenya  阅读(205)  评论(0编辑  收藏  举报