首頁>技術>

架構模式是軟體架構中在給定環境下常遇到問題的通用的、可重用的解決方案。類似於軟體設計模式但覆蓋範圍更廣,致力於軟體工程中不同問題,如計算機硬體效能限制、高可用性、業務風險極小化。一些架構模式在軟體框架被實現。- 維基百科

分層架構Pipeline架構事件驅動架構分層架構

分層架構模式

分層架構模式工作中用的比較多,常見的有MVC等,透過分層將職責劃分到某一層上,層次清晰,架構明瞭。

我們以MVC來舉例說明:controller -> service -> dao

@RestController@RequestMapping("/order")public class OrderController {    @Autowired    private OrderService orderService;    /**     * 新增訂單     * @param order     * @return     */    @PostMapping("/add")    public Response addOrder(Order order) {        orderService.add(order);        return Response.success();    }}
public interface OrderService {    /**     *  新增訂單     * @param order     * @return     */    boolean add(Order order);}
public interface OrderRepository {    int save(Order order);}

按照依賴方向,上層依次依賴下層,每一層處理不同到邏輯。

Pipeline架構

Pipeline架構模式

Pipeline架構也稱為管道或流水線架構,處理流程成線性,各個環節有相應到元件處理,從前到後順序執行。

概念說明:

source: 資料來源,通常使用流資料為源,比如:KafkaSource;

channel:通道或管道,用於處理或轉換資料,比如:JsonChannel;

Component: 元件,用於執行邏輯的最小單元,source,channel,sink都是一個Component;

Pipeline: 管道或流水線,一個Pipeline由上面的元件組成,不同的業務可以組裝成不同的Pipeline;

程式碼實現:數字資料來源 -> 累加 -> 轉成字串 -> 落地

/** *  元件 */public interface Component<T> {    /**     *  元件名稱     * @return     */    String getName();    /**     *  獲取下游元件     * @return     */    Collection<Component> getDownStrems();    /**     *  元件執行     */    void execute(T o);}
public abstract class AbstractComponent<T, R> implements Component<T>{    @Override    public void execute(T o) {        // 當前元件執行        R r = doExecute(o);        System.out.println(getName() + " receive " + o + " return " + r);        // 獲取下游元件,並執行        Collection<Component> downStreams = getDownStrems();        if (!CollectionUtils.isEmpty(downStreams)) {            downStreams.forEach(c -> c.execute(r));        }    }    protected abstract R doExecute(T o);}
/** *  資料來源 */public abstract class Source<T, R> extends AbstractComponent<T, R>{}
/** *  管道/通道 * @param <T> */public abstract class Channel<T, R> extends AbstractComponent<T, R> {}
/** *  資料落地 * @param <T> */public abstract class Sink<T, R> extends AbstractComponent<T, R> {}
public class IntegerSource extends Source<Integer,  Integer>{    @Override    protected Integer doExecute(Integer o) {        return o;    }    @Override    public String getName() {        return "Integer-Source";    }    @Override    public Collection<Component> getDownStrems() {        return Collections.singletonList(new IncrChannel());    }}
public class IncrChannel extends Channel<Integer, Integer> {    @Override    protected Integer doExecute(Integer o) {        return o + 1;    }    @Override    public String getName() {        return "Incr-Channel";    }    @Override    public Collection<Component> getDownStrems() {        return Collections.singletonList(new StringChannel());    }}
public class StringChannel extends Channel<Integer, String> {    @Override    protected String doExecute(Integer o) {        return "str" + o;    }    @Override    public String getName() {        return "String-Channel";    }    @Override    public Collection<Component> getDownStrems() {        return Collections.singletonList(new StringSink());    }}
public class StringSink extends Sink<String, Void>{    @Override    protected Void doExecute(String o) {        return null;    }    @Override    public String getName() {        return "String-Sink";    }    @Override    public Collection<Component> getDownStrems() {        return null;    }}
/** *  流水線 */public class Pipeline {    /**     *  資料來源     */    private Source source;    public Pipeline(Source source) {        this.source = source;    }    /**     *  啟動     */    public void start() {        source.execute(1);    }}

測試:

public class PipelineTest {    @Test    public void test() {        Pipeline pipeline = new Pipeline(new IntegerSource());        pipeline.start();    }}

執行結果:

Integer-Source receive 1 return 1

Incr-Channel receive 1 return 2

String-Channel receive 2 return str2

String-Sink receive str2 return null

事件驅動架構

事件驅動模式

事件驅動是以某個具體事件為觸發條件,從而貫穿這個處理流程。通常事件驅動屬於釋出訂閱模式或觀察者模式, 用於非同步處理,解耦業務邏輯。具體實現有程序內的和分散式的方式,比如:EventBus, MQ等等。

程式碼舉例:

public class OrderEventListener implements Listener<OrderEvent> {    @Override    public void onEvent(OrderEvent event) {        System.out.println("receive event: " + event);    }}
public class EventBus {    private final static List<Listener> listeners = new ArrayList<>();    /**     *  註冊監聽器     * @param listener     */    public static void registerListener(Listener listener) {        listeners.add(listener);    }    /**     *  釋出事件     * @param event     */    public void publishEvent(Event event) {        // 收到並處理事件        listeners.forEach(l -> {            l.onEvent(event);        });    }}

測試:

@Componentpublic class OrderEventListener  {    @Async    @EventListener(OrderEvent.class)    public void onEvent(OrderEvent event) {        System.out.println("receive event: " + event);    }}
public class EventTest {    @Autowired    private ApplicationContext context;    @Test    public void publishEvent() {        OrderEvent event = new OrderEvent("order_1", OrderState.PENDING_PAYMENT);        context.publishEvent(event);    }}
總結

以上透過程式碼例項簡單說明了工作中常用到的架構模式,但是模式不是固定的,工作中需結合實際情況按需使用即可。

20
  • BSA-TRITC(10mg/ml) TRITC-BSA 牛血清白蛋白改性標記羅丹明
  • 教你怎麼用 Python 自動整理檔案