基於 SOFAArk 和 SOFADashboard 實現動態模塊管控 | Meetup#2 回顧

做者:衛恆(宋國磊),SOFATracer 以及 SOFADashboard 開源負責人。
本文根據 5月26日 SOFA Meetup#2上海站 《使用 SOFAStack 快速構建微服務》主題分享整理,着重分享如何使用 SOFADashboard 來管控 SOFAArk ,對於 SOFAArk 中的一些基礎概念和知識不過多涉及;建議你們在閱讀以前,先了解下 SOFAArk 的相關基本知識。
現場回顧視頻以及 PPT 見文末連接。

46.jpg

前言

SOFAArk  是一款基於 Java 實現的輕量級類隔離容器,主要提供類隔離和應用(模塊)合併部署能力,由螞蟻金服開源貢獻。SOFAArk0.6.0 版本  提供了很是豐富的功能特性,其中最核心的當屬多應用(模塊)合併部署這個能力。SOFAArk 自己提供了多種方式來支持多應用(模塊)合併部署 ,包括基於命令行的管控,基於 API 的管控等。本篇將結合 SOFA 開源的管控端組件 SOFADashboard ,來實現 SOFAArk 提供的合併部署和動態模塊推送的功能。java

案例工程地址 :git

github.com/sofastack-g…github

背景

複雜項目一般須要跨團隊協做開發,各自負責不一樣的組件,而衆所周知,協調跨團隊合做開發會遇到很多問題;好比各自技術棧不統一致使的依賴衝突,又好比往同一個 Git 倉庫提交代碼經常致使 merge 衝突。所以,若是能讓每一個團隊將負責的功能組件當成一個個單獨的應用開發,運行時合併部署,經過統一的編程界面交互,那麼將極大的提高開發效率及應用可擴展性。SOFAArk 提出了一種特殊的包結構 -- Ark Biz,用戶可使用 Maven 插件將應用打包成 Biz,容許多 Biz 在 SOFAArk 容器之上合併部署,並經過統一的編程界面交互。web

image.png

案例模型

本篇所演示案例是上圖的一個簡化版,從總體上能夠體現 SOFAArk多應用合併部署的能力。主要包括已經幾個工程:spring

  • sofa-dashboard-ark-hostapp : 宿主應用
  • sofa-dashboard-ark-facade : 提供接口 API
  • sofa-dashboard-ark-provider :提供接口 API 的具體實現,將發佈一個 JVM 服務

sofa-dashboard-ark-hostapp 和 sofa-dashboard-ark-provider 均做爲 SOFAArk 中的 ark-biz 存在;sofa-dashboard-ark-hostapp 做爲宿主應用對外提供服務。sql

image.png

上圖的模型中,在宿主應用不重啓的狀況下,實現 provider 模塊的動態替換,從而實現版本升級。編程

在宿主應用啓動時,provider 1.0.0 以靜態合併部署方式「寄宿」到宿主應用中,這部分實際上與 SOFADashboard 管控是沒有什麼關係的,爲了案例效果,在下面的案例中,關於靜態合併部署的操做也會涉及到。bootstrap

最終的工程結構圖以下:springboot

image.png

環境準備

本文須要啓動 SOFADashboard 服務端,具體請參考 : Quick Start [5] ;其餘基礎設施環境如 Zookeeper 、Mysql 等需提早準備。bash

工程構建

本篇將經過 step by step 的方式來構建整個工程,爲你們在實際的應用過程當中提供一種簡單的思路,同時也幫助你們更好的理解 SOFAArk 中的一些點。

sofa-dashboard-ark-facade

基礎 API 提供模塊,不須要依賴任何其餘二方或者三方 JAR,這裏僅提供一個接口。

public interface SofaJvmService {
    String test();
}複製代碼

sofa-dashboard-ark-provider

這個模塊是 JVM 服務的提供方,也是後面須要在宿主應用中進行替換演示的模塊包,這個模塊自己也是一個 Web 應用。這裏就來一步步分解下,如何將一個普通的 SpringBoot 工程改形成一個 ark-biz 工程。

一、新建一個 SpringBoot 工程

新建 SpringBoot 工程推薦的方式有兩種,一種是在 start.spring.io/ 進行下載,另一種是基於 IDEA 的 Spring 插件來生成;此處不在過多描述過程。

二、工程基本能力實現

  • 引入 sofa-dashboard-ark-facade 依賴,先將須要提供的 JVM 服務實現:
@SofaService
@Service
public class SofaJvmServiceImpl implements SofaJvmService {
    @Override
    public String test() {
        return "first version biz";
    }
}複製代碼

NOTE: SofaService 的做用是將一個 Bean 發佈成一個 JVM 服務, 因此這裏須要加上 Spring 提供的 @Service 註解將 SofaJvmServiceImpl 標註爲一個 Bean。

  • 配置文件:
spring.application.name=biz-ark-test
server.port=8800
logging.path=./logs複製代碼

三、配置打包插件,將應用打包成 ark-biz

根據官方文檔,可使用 sofa-ark-maven-plugin 插件將一個普通的工程打包成一個 ark biz 包。這裏直接給出本篇中工程的配置:

<plugin>
   <groupId>com.alipay.sofa</groupId>
   <artifactId>sofa-ark-maven-plugin</artifactId>
   <version>0.6.0</version>
   <executions>
     <execution>
       <!--goal executed to generate executable-ark-jar -->
       <goals>
         <goal>repackage</goal>
       </goals>
       <!--ark-biz 包的打包配置  -->
       <configuration>
         <!--是否打包、安裝和發佈 ark biz,詳細參考 Ark Biz 文檔,默認爲false-->
         <attach>true</attach>
         <!--ark 包和 ark biz 的打包存放目錄,默認爲工程 build 目錄-->
         <outputDirectory>target</outputDirectory>
         <!--default none-->
         <arkClassifier>executable-ark</arkClassifier>
         <!-- ark-biz 包的啓動優先級,值越小,優先級越高-->
         <priority>200</priority>
         <!--設置應用的根目錄,用於讀取 ${base.dir}/conf/ark/bootstrap.application 配置文件,默認爲 ${project.basedir}-->
         <baseDir>../</baseDir>
       </configuration>
     </execution>
   </executions>
</plugin>複製代碼

四、工程依賴

從前面背景介紹中的設計理念圖中能夠看出,動態合併部署須要依賴的插件核心有兩個,一個是 runtime plugin,一個是 config plugin(沒有涉及到 RPC 服務相關);因爲 provider 並非做爲宿主應用,其自己不須要具有動態配置的能力,所以這裏僅須要引入 runtime plugin 來爲當前 ark-biz 工程提供運行時環境便可。

<!-- runtime plugin -->
<dependency>
    <groupId>com.alipay.sofa</groupId>
    <artifactId>runtime-sofa-boot-plugin</artifactId>
</dependency>

<!-- 其餘依賴 -->
<dependency>
    <groupId>com.alipay.sofa</groupId>
    <artifactId>healthcheck-sofa-boot-starter</artifactId>
</dependency>

<dependency>
    <groupId>com.glmapper.bridge.boot</groupId>
    <artifactId>sofa-dashboard-ark-facade</artifactId>
</dependency>複製代碼

五、編譯打包

執行 mvn clean package ,以後會在當前模塊的 target 目錄下生成 xxx-ark-biz.jar 的包。

image.png

sofa-dashboard-ark-host

前面已經構建好了所須要的一些基礎工程,sofa-dashboard-ark-host 做爲宿主應用,指望其具有的能力有如下幾個:

  • 提供能夠直觀的 check 模塊變動後的結果
  • 提供可以給 provider 1.0.0 版本 ark-biz 包運行的宿主環境
  • 可以經過 SOFAArk 提供的狀態 endpoint 查看插件狀態
  • 可以支持 Zookeeper 下發指令,控制 Biz 的生命週期

基於以上幾點功能,下面來分步驟實現。

一、提供一個簡單的 Rest 接口來 check 結果

sofa-dashboard-ark-host 自己也是一個 Web 應用,因此在這個提供一個 Rest 接口,具體實現是經過@SofaReference 調用 provider ark-biz 包中發佈的 JVM 服務。

@RestController
public class TestController {

    @SofaReference
    SofaJvmService sofaJvmService;

    @RequestMapping("test")
    public String test(){
        return sofaJvmService.test();
    }
}複製代碼

二、做爲宿主應用

  • ARK 容器配置

這部分能夠先參考閱讀 SOFAArk 配置 。本案例中簡單配置了一份 ARK 容器的配置文件。

# log 日誌目錄
logging.path=./logs
# 指定zookeeper 服務地址
com.alipay.sofa.ark.config.address=zookeeper://localhost:2181
# 指定宿主應用名
com.alipay.sofa.ark.master.biz=host-app複製代碼

com.alipay.sofa.ark.master.biz 默認狀況下是宿主應用的 artifactId。若是這裏指定了名字,則在宿主應用的插件配置裏面須要使用此名字。

  • 依賴引入

引入 sofa-ark-springboot-starter 、web-ark-plugin 以及 provider ark biz 包。

<!-- 引用ark starter-->
<dependency>
    <groupId>com.alipay.sofa</groupId>
    <artifactId>sofa-ark-springboot-starter</artifactId>
</dependency>
<!-- 引用ark web插件-->
<dependency>
    <groupId>com.alipay.sofa</groupId>
    <artifactId>web-ark-plugin</artifactId>
</dependency>
<!-- 引入 sofa-dashboard-ark-provider ark-biz ,這裏屬於靜態合併部署狀況-->
<dependency>
    <groupId>com.glmapper.bridge.boot</groupId>
    <artifactId>sofa-dashboard-ark-provider</artifactId>
    <version>1.0.0</version>
    <classifier>ark-biz</classifier>
</dependency>複製代碼
  • 插件配置
<plugin>
  <groupId>com.alipay.sofa</groupId>
  <artifactId>sofa-ark-maven-plugin</artifactId>
  <version>0.6.0</version>
  <executions>
    <execution>
      <id>default-cli</id>
      <goals>
        <goal>repackage</goal>
      </goals>
    </execution>
  </executions>
  <configuration>
    <!--指定優先級-->
    <priority>100</priority>
    <!--指定baseDir-->
    <baseDir>../</baseDir>
    <!--bizName,這裏須要和 bootstrap 中指定的master.biz 配置保持一致,默認爲 artifactId-->
    <bizName>host-app</bizName>
  </configuration>
</plugin>複製代碼

三、狀態查看

SOFAArk 提供了 /bizState 這樣一個 endpoint 用來獲取當前插件的版本及狀態信息。這裏就在宿主應用中引入actuator 依賴並進行相關配置。

<!-- 引用 actuator -->
 <dependency>
    <groupId>org.springframework.boot</groupId>
    <artifactId>spring-boot-starter-actuator</artifactId>
 </dependency>複製代碼

application.properties 中配置暴露全部端點。

management.endpoints.web.exposure.include=*複製代碼

四、提供動態配置插件能力

SOFAArk 提供了 config-ark-plugin 對接 Zookeeper 配置中心,用於運行時接受配置,達到控制 Biz 生命週期,引入以下依賴:

<!-- 引用ark 配置推送擴展插件-->
<dependency>
    <groupId>com.alipay.sofa</groupId>
    <artifactId>config-ark-plugin</artifactId>
</dependency>複製代碼

參考 SOFAArk 配置,在 SOFAArk 配置文件 conf/ark/bootstrap.properties 增長以下配置:

com.alipay.sofa.ark.config.address=zookeeper://localhost:2181複製代碼

靜態合併部署演示

基於上述全部的配置,將 host-app 打包,而後運行。

  • mvn clean install
  • java -jar sofa-dashboard-ark-hostapp-1.0.0.jar

下面能夠經過 SOFAArk 提供的 endpoint 來查看下當前應用的 biz state 信息:

image.png

這裏只有宿主應用自身的 ark biz 狀態信息,實際上咱們使用了靜態合併部署。可是貌似 ark-biz 合併部署的包插件沒有在 bizState 中體現出來。訪問下 http://localhost:8085/test 咱們的 check rest 服務:

image.png

提示出來沒有可用的 JVM 服務。

這裏有個點是並不會去激活裏面的 ark biz 包,須要經過經過 終端或者 API 的方式來進行激活,實際上只是激活了宿主應用自己的 ark-biz。

經過 SOFADashboard 進行動態推送

SOFADashboard 進行推送的原理能夠參考前面背景介紹中的描述。下面主要來介紹如何使用 SOFADashboard 進行動態模塊切換。

註冊插件

將 sofa-dashboard-ark-provider 這個 ark-biz 插件註冊到 SOFADashboard:

image.png

填寫插件的基本信息:

image.png

註冊成功以後,模塊列表以下:

image.png

增長版本

點擊添加版本,彈出新增版本表單,輸入版本信息及當前版本對應的 ark biz 包文件地址;支持從文件服務器(http 協議)上拉取,也支持從本地文件(File 協議)系統獲取。下面爲了方便,使用從文件系統中獲取,配置以下:

image.png

添加成功以後,插件列表以下:

image.png

關聯應用

image.png

點擊插件列表後面的 關聯應用案例,將插件與應用進行關聯,以下:

image.png

詳情查看

點擊插件列表後面的詳情按鈕,能夠查看當前插件下全部應用信息和應用實例信息。

image.png

命令推送

SOFADashboard 提供兩種維度的命令推送:

  • 基於應用維度,當前應用全部的實例都會監聽到此命令變動;
  • 基於 IP 維度,分組維度的單 IP 場景。

下面演示基於 IP 維度的推送:

一、安裝

點擊安裝,安裝過程當中,插件狀態會發生變化, RESOLVED 狀態爲正在解析。

image.png

延遲 1~3s 以後,狀態變爲 ACTIVATED 狀態

image.png

再次訪問下 http://localhost:8085/test 咱們的 check rest 服務:

image.png

實現了在不重啓宿主應用的狀況下,實現了內部業務邏輯的變動。

二、版本切換

模塊版本 1 運行一段時間以後,出現新的需求,但願更改下模塊版本 1 中的一些邏輯。在未使用動態模塊的狀況下,通常就須要新拉一個迭代,而後將原有的邏輯修改,而後發佈上線。多是一個很是小的功能點,可是卻須要走複雜的發佈流程。

這個就能夠藉助動態模塊的方式來實現版本的動態切換。修改 sofa-dashboard-ark-provider 模塊邏輯實現,升級版本,從新打包 sofa-dashboard-ark-provider 。

在 SOFADashboard ,新增 2.0.0 版本,而且配置指定的版本 ark-biz 包的文件地址。添加成功以後以下:

image.png

進入詳情界面,切換版本到 2.0.0:

image.png

執行安裝,此時版本 2.0.0 狀態將會變爲非激活狀態:

image.png

執行點擊激活按鈕進行激活,延遲 1~3s 以後,狀態變動爲激活狀態:

image.png

再次訪問下 http://localhost:8085/test 咱們的 check rest 服務:

image.png

能夠看到,版本 2.0.0 中的邏輯已經生效了;切回到 1.0.0 ,此時 1.0.0 的狀態變成了非激活狀態:

image.png

小結

本文分享了基於 SOFAArk 和 SOFADashboard 實現動態模塊管控的能力。動態模塊在實際業務中有很是豐富的場景,對主應用不發版,不重啓的狀況下實現具體模塊的功能變動;在此基礎上也能夠實現版本灰度的能力。

本案例中,provider 也是一個獨立的應用,其做爲一個子模塊在宿主應用 hostapp 中啓動,所以也能夠基於 SOFABoot 這種能力來實現多 Web 應用的合併部署的能力。

以上就是本次分享的所有內容。

SOFA Meetup 上海站回顧資料

現場回顧視頻以及 PPT 地址:t.cn/AiKlmCmE

公衆號:金融級分佈式架構(Antfin_SOFA)

相關文章
相關標籤/搜索