NATS學習 -- 概念學習之訊息(Message)與發布訂閱(Publish Subscribe)

來源:互聯網
上載者:User

標籤:

1 理論篇1.1 來自官方的介紹

NATS acts as a central nervous system for distributed systems such as mobile devices, IoT networks, enterprise microservices and cloud native infrastructure. Unlike traditional enterprise messaging systems, NATS provides an always on ‘dial-tone’.

NATS在分布式系統中扮演一個中央神經系統,這些分布式系統包括行動裝置,物聯網,企業微服務和原生雲基礎設施。不同於傳統的企業級訊息系統,NATS提供永遠線上服務。

NATS was created by Derek Collison, Founder and CEO at Apcera. Derek has spent over twenty years designing, building and using publish-subscribe messaging systems. Learn why traditional enterprise messaging systems don’t work for today’s distributed infrastructure, in this talk from Derek at SCALE on designing a new cloud-native messaging framework.

1.2 NATS 的訊息(Message)

NATS messaging involves the electronic exchange of data among computer applications.

NATS provides a layer between the application and the underlying physical network. Application data is encoded as a message and sent by the publisher. The message is received, decoded, and processed by one or more subscribers. A subscriber can process a NATS message asynchronously or synchronously.

NATS的訊息是指在不同電腦應用程式之間的訊息互動。

NATS在應用與底層網路之間提供了一個抽象層。應用資料被封裝為訊息(message)並由發行者發送。訊息被一個或多個訂閱者接收,解碼並且處理。訂閱者可以非同步或同步地處理訊息。

1.2.1 Asynchronous processing

Asynchronous processing uses a callback message handler to process messages. When a message arrives, the registered callback handler receives control to process the message. The client or consuming application is not blocked from performing other work while it is waiting for a message. Asynchronous processing lets you create multi-threaded dispatching designs.

非同步訊息處理

非同步訊息處理使用一個訊息回調處理器來處理訊息,當訊息到達的時候,已經註冊的回調處理器來處理該訊息。用戶端或消費者程式不會從其他事件中阻塞在等待訊息的時候。非同步訊息處理可以讓程式員建立多線程的分發設計。

1.2.2 Synchronous processing

Synchronous processing requires that application code explicitly call a method to process an incoming message. Typically an explicit call is a blocking call that suspends processing until a message becomes available. If no message is available, the period for which the message processing call blocks is set by the client. Synchronous processing is typically used by a server whose purpose is to wait for and process incoming request messages, and to send replies to the requesting application.

同步訊息處理

同步訊息處理需要應用程式代碼顯示地調用函數來處理到達的訊息。通常顯示的函數調用是一個阻塞的調用,它會等待一知道訊息可用。如果沒有可用的訊息,用戶端在調用訊息的時候就會一直處於阻塞狀態。同步訊息處理通常是由一個伺服器端充當,它的職責就是等待並處理到達的訊息,並且給發送訊息的一方發送回複內容。

1.3 NATS的發布訂閱(Publish Subscribe)

NATS implements a publish subscribe messaging model. NATS publish subscribe is a one-to-many communication. A publisher sends a message on a subject. Any active subscriber listening on that subject receives the message. Subscribers can register interest in wildcard subjects.

NATS實現了一個基於發布訂閱的訊息模型。NATS的發布訂閱模型是一個一對多的通訊模型。訊息的發行者發送訊息到一個主體(subject),任何的活動的訂閱者堅挺這個主題並收到訊息。訂閱者可以使用萬用字元註冊感興趣的主題。

If a subscriber is not listening on the subject (no subject match), or is not active when the message is sent, the message is not received. NATS is a fire-and-forget messaging system. If you need higher levels of service, you build it into the client.

如果訂閱者沒有監聽的主題(或者沒有匹配的主題),或者不線上,當訊息發送的時候它將不會收到訊息。NATS是一個一勞永逸的訊息系統。如果需要更高的服務,將它內建在用戶端。

In an asynchronous exchange, messages are delivered to the subscriber’s message handler. If there is no handler, the subscription is synchronous and the client may be blocked until it can process the message.

在非同步訊息處理中,訊息將會被發送到訂閱者的訊息回調處理器上,如果沒有訊息回調處理器,這個訂閱者就是同步的,用戶端將會阻塞,知道它處理了訊息。

2 實踐篇

首先確保NATS伺服器程式已經搭建好了。

參考

http://blog.csdn.net/frankcheng5143/article/details/51141804

2.1 啟動服務

在命令列輸入

gnastd

2.2 用戶端程式的編寫

依賴的jar包

<dependency>  <groupId>io.nats</groupId>  <artifactId>jnats</artifactId>  <version>0.4.1</version></dependency>

其他依賴

沒有日誌它會報錯,這裡我用的是log4j

<dependency>    <groupId>org.slf4j</groupId>    <artifactId>slf4j-api</artifactId>    <version>1.7.21</version></dependency><dependency>    <groupId>org.slf4j</groupId>    <artifactId>slf4j-log4j12</artifactId>    <version>1.7.21</version></dependency><dependency>    <groupId>log4j</groupId>    <artifactId>log4j</artifactId>    <version>1.2.17</version></dependency>

log4j的配置

log4j.properties

#---------------------------------------------------------# Log4J Settings for log4j 1.2.x (via jakarta-commons-logging)## The five logging levels used by Log are (in order):##   1. DEBUG (the least serious)#   2. INFO#   3. WARN#   4. ERROR#   5. FATAL (the most serious)##---------------------------------------------------------# Root-Categroy#---------------------------------------------------------log4j.rootCategory=INFO, stdout, file#---------------------------------------------------------# stdout#---------------------------------------------------------log4j.appender.stdout=org.apache.log4j.ConsoleAppenderlog4j.appender.stdout.layout=org.apache.log4j.PatternLayoutlog4j.appender.stdout.layout.ConversionPattern=%d{ABSOLUTE} %5p %c{1}:%L - %m%n#---------------------------------------------------------# file (log)#---------------------------------------------------------log4j.appender.file=org.apache.log4j.DailyRollingFileAppenderlog4j.appender.file.File=/home/gwcheng/info.loglog4j.appender.file.layout=org.apache.log4j.PatternLayoutlog4j.appender.file.Append=truelog4j.appender.file.DatePattern=‘.‘yyyy-MM-dd  log4j.appender.file.layout.ConversionPattern=%d{yyyy-MM-dd HH:mm:ss:SSS} %p [%M] %c %m%n#---------------------------------------------------------# file (html)#---------------------------------------------------------#log4j.appender.html=org.apache.log4j.FileAppender#log4j.appender.html.File=### THE PATH HERE ####log4j.appender.html.layout=org.apache.log4j.HTMLLayout#---------------------------------------------------------# customer#---------------------------------------------------------# my definition io.netty=debug

好的,開始寫代碼。

這裡類比一個發行者,三個訂閱者,拓撲圖和上面的圖一樣。

2.2.1 發行者代碼

Publish.java

package com.gwc.nats.nats.test;import java.io.IOException;import java.util.ArrayList;import java.util.HashMap;import java.util.Map;import java.util.Scanner;import java.util.concurrent.TimeoutException;import io.nats.client.Connection;import io.nats.client.ConnectionFactory;import io.nats.client.Message;/** * Hello world! * @author gwcheng */public class Publish {        public static void main(String[] args) throws IOException, TimeoutException, InterruptedException {                ConnectionFactory cf = new ConnectionFactory("nats://127.0.0.1:4222");                Connection nc = cf.createConnection();                // 訊息                Message msg = new Message();                // 設定主題                msg.setSubject("foo");                            @SuppressWarnings("resource")                Scanner scanner = new Scanner(System.in);                System.out.println("請輸入字串:");                while (true) {                        String line = scanner.nextLine();                        msg.setData(line.getBytes());                        // 發布訊息                        nc.publish(msg);                }        }}
2.2.2 發行者代碼

Subscribe.java

package com.gwc.nats.nats.test;import java.io.IOException;import java.util.concurrent.TimeoutException;import io.nats.client.Connection;import io.nats.client.ConnectionFactory;import io.nats.client.Message;import io.nats.client.MessageHandler;public class Subscribe {        public static void main(String[] args) throws IOException, TimeoutException {                ConnectionFactory cf = new ConnectionFactory("nats://127.0.0.1:4222");                Connection nc = cf.createConnection();                // Lambda 運算式寫法                /*                 * nc.subscribe("foo", m -> { System.out.printf(                 * "收到的訊息:%s\n", new String(m.getData())); });                 */                nc.subscribe("foo", new MessageHandler() {                        @Override                        public void onMessage(Message msg) {                                System.out.println("收到的訊息:" + new String(msg.getData()));                        }                });        }}

寫上三個一模一樣的Subscribe,除了類名不一樣。

2.3 測試

先運行Publish,並輸入一些字元,發布到foo這個主題上,這裡沒有訂閱者,一會兒有了訂閱者也不會收到剛才發布的字元。

運行三個Subscribe

然後在Publish的console輸入一些字元,這個時候三個訂閱者都將會收到該字元

Publish

Subscribe

Subscribe1

我們讓Subscribe2 訂閱的主題不是foo,看一下運行結果

Subscribe

Subscribe1

Subscribe2

說明Subscribe2並沒有收到訊息,因為它沒有關注foo主題。

參考文獻

http://nats.io/

http://nats.io/documentation/concepts/nats-messaging/

http://nats.io/documentation/concepts/nats-pub-sub/

https://github.com/nats-io/jnats

NATS學習 -- 概念學習之訊息(Message)與發布訂閱(Publish Subscribe)

聯繫我們

該頁面正文內容均來源於網絡整理,並不代表阿里雲官方的觀點,該頁面所提到的產品和服務也與阿里云無關,如果該頁面內容對您造成了困擾,歡迎寫郵件給我們,收到郵件我們將在5個工作日內處理。

如果您發現本社區中有涉嫌抄襲的內容,歡迎發送郵件至: info-contact@alibabacloud.com 進行舉報並提供相關證據,工作人員會在 5 個工作天內聯絡您,一經查實,本站將立刻刪除涉嫌侵權內容。

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.