Vert.x Core Review

添加依賴

Maven:

<dependency>
  <groupId>io.vertx</groupId>
  <artifactId>vertx-core</artifactId>
  <version>3.9.5</version>
<dependency>
<dependency>
  <groupId>io.vertx</groupId>
  <artifactId>vertx-core</artifactId>
  <version>3.9.5</version>
<dependency>

Gradle:

dependencies {
    compile 'io.vertx:vertx-core:3.9.5'
}
dependencies {
    compile 'io.vertx:vertx-core:3.9.5'
}

重點

  • 一個Vert.x對象擁有一個Event Bus、多個Event Loop(默認為2*CPU core count)
  • 不要阻塞Event Bus
  • 一個Vert.x對象維護多個Event Loop線程

執行阻塞代碼

vertx.executeBlocking<String>(
    {
      val result = api.action()
      it.complete(result)
    },
    {
      println("result: [${it.result()}]")
    }
)

當在同一個Context中調用多次executeBlocking時會順序執行,若不想讓他順序執行,讓ordered參數設為false

並發合併

  1. CompositeFuture.all接受多個Future對象作為參數(至多六個,或傳入List),當所有Future成功返回一個成功的Future,反之則返回一個失敗的Future
  2. CompositeFuture.any與上述相似,差別在於有一個Future成功則成功,反之,全部失敗則失敗
  3. CompositeFuture.compose順序合併Future

Verticle

坑: Vertx實例會在初始化後才進行注入,所以想在Verticle中使用Vertx實例必須在start()中編寫,否則會報空指標錯誤。

編寫Verticle需繼承AbstractVerticle,其結構如下

public class MyVerticle extends AbstractVerticle{
  // Called when verticle is deployed
  // Verticle 部署時調用
  public void start(){
  }
  // Optional - called when verticle is undeployed
  // Verticle 撤銷部署時調用
  public void stop(){
  }
}

Verticle種類

  1. Stardand Verticle: 工作在Event Loop線程上
  2. Worker Verticle: 工作在Worker Pool線程上,線程安全(一個實例不會被多個執行緒執行)
  3. Multi-Threaded Worker Verticle: 工作在Worker Pool線程上,一個實例可以被多個執行緒執行,但須開發者確保線程安全

Event Bus

接收者:

MessageConsumer<String> consumer = eventBus.consumer("news.uk.sport");
consumer.handler(message -> {
  System.out.println("I have received a message: " + message.body());
  message.reply("how interesting!");
});

發送者:

eventBus.send("news.uk.sport", "Yay! Someone kicked a ball across a patch of grass", ar -> {
  if (ar.succeeded()) {
    System.out.println("Received reply: " + ar.result().body());
  }
});

本地共享Map

本地共享Map LocalMap允許您在同一個Vert.x實例中的不同Event Loop(如不同的Verticle中)之間安全共享數據。

示例

SharedData sd = vertx.sharedData();

LocalMap<String, String> map1 = sd.getLocalMap("mymap1");

map1.put("foo", "bar"); // Strings are immutable so no need to copy

LocalMap<String, Buffer> map2 = sd.getLocalMap("mymap2");

map2.put("eek", Buffer.buffer().appendInt(123)); // This buffer will be copied before adding to map

// Then... in another part of your application:
map1 = sd.getLocalMap("mymap1");

String val = map1.get("foo");

map2 = sd.getLocalMap("mymap2");

Buffer buff = map2.get("eek");

集群範圍異步Map

集群範圍異步Map(Cluster-wide asynchronous maps)允許從集群的任何節點將數據放到Map 中,並從任何其他節點讀取。

SharedData sd = vertx.sharedData();

sd.<String, String>getClusterWideMap("mymap", res -> {
  if (res.succeeded()) {
    AsyncMap<String, String> map = res.result();
  } else {
    // Something went wrong!
  }
});

將數據放入Map

map.put("foo", "bar", resPut -> {
  if (resPut.succeeded()) {
    // Successfully put the value
  } else {
    // Something went wrong!
  }
});

讀取Map

map.get("foo", resGet -> {
  if (resGet.succeeded()) {
    // Successfully got the value
    Object val = resGet.result();
  } else {
    // Something went wrong!
  }
});

文件系統

Vertx vertx = Vertx.vertx();

// Read a file
// 讀取文件
vertx.fileSystem().readFile("target/classes/readme.txt", result -> {
    if (result.succeeded()) {
        System.out.println(result.result());
    } else {
        System.err.println("Oh oh ..." + result.cause());
    }
});

// Copy a file
// 複製文件
vertx.fileSystem().copy("target/classes/readme.txt", "target/classes/readme2.txt", result -> {
    if (result.succeeded()) {
        System.out.println("File copied");
    } else {
        System.err.println("Oh oh ..." + result.cause());
    }
});

// Write a file
// 寫入文件
vertx.fileSystem().writeFile("target/classes/hello.txt", Buffer.buffer("Hello"), result -> {
    if (result.succeeded()) {
        System.out.println("File written");
    } else {
        System.err.println("Oh oh ..." + result.cause());
    }
});

// Check existence and delete
vertx.fileSystem().exists("target/classes/junk.txt", result -> {
    if (result.succeeded() && result.result()) {
        vertx.fileSystem().delete("target/classes/junk.txt", r -> {
            System.out.println("File deleted");
        });
    } else {
        System.err.println("Oh oh ... - cannot delete the file: " + result.cause());
    }
});

更多中文文檔: https://vertxchina.github.io/vertx-translation-chinese/core/Core.html

更多英文文檔: https://vertx.io/docs/vertx-core/kotlin