使用深度學習庫DJL和Spring Boot在微服務中實現機器學習 - idk.dev

banq發表於2020-05-10

通過DJL和Spring Boot進行機器學習是一種簡單而強大的方法,通過DJL和DJL提供的便捷抽象層,將現有的經過實踐測試的微服務技術堆疊SpringBoot與MXNet,PyTorch和Tensorflow等最成熟的深度學習框架相結合。

Spring Boot是用於微服務開發的最流行和廣泛使用的開源框架之一,它簡化了分散式系統的實現。

儘管此框架具有廣泛的吸引力,但幾乎沒有其他選項可以輕鬆地將其與機器學習(ML)整合。現有的解決方案(例如庫存API)通常無法滿足定製的應用程式要求,並且開發定製的解決方案既耗時又不具成本效益。

在這篇部落格文章中,我們將演示Java使用者如何使用Spring Boot Starter for Deep Java Library(DJL)將ML整合到他們的Spring應用程式中。我們將回顧如何將這些框架付諸實踐,並將ML功能整合到微服務中,展示圍繞物件檢測和分類的常見深度學習用例。

DJL概述

深度Java庫(DJL)是用於深度學習的開源,高階別,與框架無關的Java API。它被設計為易於入門,並且對於Java開發人員來說易於使用。DJL提供了本機Java開發經驗和功能,就像其他任何常規Java庫一樣。

DJL是基於最流行的AI/ML框架(例如Apache MXNet,PyTorch和TensorFlow)提供了便利的抽象層。使用DJL API,您將獲得一個統一且一致的API層,可以與所有這些框架進行互動,從而使您可以換出您選擇的框架,而不會影響客戶端程式碼。

將這種獨特的功能與豐富的模型Zoo倉庫(具有預先訓練的模型的倉庫)相結合,可使ML工程師能夠為手頭任務找到最佳模型,而無需考慮基礎模型的實現。

有關DJL的更多資訊,請參考DJL GitHub儲存庫和常見問題解答。

DJL Spring Boot Starter

Spring Boot Starter是您專案中所需的所有Spring和相關技術的一站式商店,不必搜尋示例程式碼和依賴描述符的複製貼上負載。請參閱官方的Spring Boot文件以獲取有關啟動器的更多資訊。

按照此定義,DJL Spring Boot Starter提供了在Spring中作為單個工件開始使用DJL所需的所有依賴項。除了依賴關係管理之外,啟動程式還包括一個自動配置,該配置使得可以根據使用者提供的配置檔案自動關聯依賴關係,並使它們在Spring Application上下文中可以作為bean使用。

依賴管理

DJL庫是特定於平臺的,但是它提供了基於目標作業系統自動查詢正確依賴關係的方法。DJL也可以使用不同的基礎引擎(例如MXNet,PyTorch或TensorFlow)進行配置;使用者應在使用啟動器之前做出選擇。但是,即使做出選擇,也可以通過修改Maven(或Gradle)依賴項來更改基礎引擎以及目標作業系統體系結構,而不會影響程式碼。

這是一個針對Linux架構的MXNet依賴關係的示例,它針對容器工作負載進行了優化:

<parent>
  <artifactId>spring-boot-starter-parent</artifactId>
  <groupId>org.springframework.boot</groupId>
  <version>2.2.6.RELEASE</version>
</parent>

<properties>
  <java.version>11</java.version> <!-- 11 is the lowest supported java version, however 12 and 13 should work fine -->
  <jna.version>5.3.0</jna.version> <!-- Required to override default JNA version for Spring Boot parent-->
</properties> 

<dependency>
  <groupId>ai.djl.spring</groupId>
  <artifactId>djl-spring-boot-starter-mxnet-linux-x86_64</artifactId>
  <version>${djl.starter.version}</version> <!-- e.g. 0.2 -->
</dependency>

如果使用PyTorch作為底層引擎,依賴關係是:

<dependency>
  <groupId>ai.djl.spring</groupId>
  <artifactId>djl-spring-boot-starter-pytorch-auto</artifactId>
  <version>${djl.starter.version}</version> <!-- e.g. 0.2 and above -->
</dependency>

Spring自動配置

一旦在Spring Boot應用程式中正確配置了依賴項,下一步就是配置bean並正確地連線它們以進行注入。配置與DJL相關的bean並使它們在Spring應用程式上下文中可用是相當容易的,但是它需要庫的內部知識以及各個類的特殊性才能進行適當的作用域確定-一些bean是執行緒安全的,其他bean應該是執行緒安全的。範圍取決於每個請求/執行緒。為了協助進行此配置,DJL Spring Boot啟動器提供了自動配置。

該元件與依賴項元件分開,並且需要顯式依賴項。我們這樣做的原因有兩個:

  1. 一些開發人員更喜歡完全控制配置選項,並且可能不希望Spring“自動魔術”。在這種情況下,入門者將僅支援基本的依賴關係集,並允許開發人員顯式地連線元件。
  2. 自動配置元件對於所有DJL配置都是通用的:無論基礎目標作業系統或實際引擎如何,自動配置元件均保持不變。因此,使用相同的自動配置,開發人員可以將基礎依賴項交換為一步操作,而不會對程式碼產生任何影響。

在Maven中宣告對自動配置的依賴:

<dependency>
  <groupId>ai.djl.spring</groupId>
  <artifactId>djl-spring-boot-starter-autoconfigure</artifactId>
  <version>${djl.starter.version}</version>
</dependency>

宣告依賴關係後,Spring Boot框架將自動找到配置並連線所需的元件。目前,為了進行推理,它將從模型儲存庫中查詢模型,並建立一個隨時可用於進行推理的預測器。

使用者可通過定義標準的Spring配置(application.yml或application.properties)模型來使用其中一個受支援的應用程式型別:

  QUESTION_ANSWER(NLP.QUESTION_ANSWER),
  TEXT_CLASSIFICATION(NLP.TEXT_CLASSIFICATION),
  IMAGE_CLASSIFICATION(CV.IMAGE_CLASSIFICATION),
  OBJECT_DETECTION(CV.OBJECT_DETECTION),
  ACTION_RECOGNITION(CV.ACTION_RECOGNITION),
  INSTANCE_SEGMENTATION(CV.INSTANCE_SEGMENTATION),
  POSE_ESTIMATION(CV.POSE_ESTIMATION),
  SEMANTIC_SEGMENTATION(CV.SEMANTIC_SEGMENTATION);

例如,為了在影像中執行物件檢測,使用者可以將應用程式型別設定為OBJECT_DETECTION。與DJL相關的配置應在djl根目錄下命名,例如如果application.properties使用的話,配置djl.application-type=OBJECT_DETECTION。

這是yamlDJL自動配置的配置示例:

djl:
    # Define application type
    application-type: OBJECT_DETECTION
    # Define input data type, a model may accept multiple input data type
    input-class: java.awt.image.BufferedImage
    # Define output data type, a model may generate different out put
    output-class: ai.djl.modality.cv.output.DetectedObjects
    # Define filters that matches your application's need
    model-filter:
      size: 512
      backbone: mobilenet1.0
    # Override default pre-processing/post-processing behavior
    arguments:
      threshold: 0.5 # Display all results with probability of 0.5 and above

IDE支援

配置建立不必完全是手動的,DJL Spring Boot Starter通過Spring IDE外掛(已在IntelliJ IDEA上進行了測試,但有望在具有STS和NetBeans IDE的Eclipse中執行)為大多數IDE提供了一個配置內容助手。

對於IntelliJ,您可以使用Ctrl + Space來自動完成,並使用Ctrl + J來獲取任何屬性的快速文件。

簡單的應用演練

以下是基於Simple Spring Boot應用程式的程式碼示例,該示例演示了使用DJL和MXNet進行單次物件檢測。

每個Maven依賴項部分都設定了依賴項。配置設定與application.yml示例中的相同。

注入預測器以進行物件檢測

@Resource
  private Supplier<Predictor> predictorProvider;

建議在try-with-resources塊中使用predictor以確保每次使用後都將其關閉,因此剛注入的predictor供供者能方便例項化。

Java中的物件檢測

try (var predictor = predictorProvider.get()) {
    var results = predictor.predict(ImageIO.read(this.getClass()
          .getResourceAsStream("/puppy-in-white-and-red-polka.jpg")));

    for(var result : results.items()) {
        LOG.info("results: {}", result.toString());
    }
}

上面的程式碼將在提供的影像(預期在類路徑中)上執行物件檢測,並將結果以以下形式輸出到記錄器:

a.d.s.e.console.ConsoleApplication: results: class: "dog", probability: 0.90820, bounds: {x=0.487, y=0.057, width=0.425, height=0.484}

構建和執行

假設您已簽出儲存庫,並且現在位於儲存庫的根目錄中:

> git clone git@github.com:awslabs/djl-spring-boot-starter.git 
> cd djl-spring-boot-starter/djl-spring-boot-console-sample
> ../mvnw package
> ../mvnw spring-boot:run

或者,您可以使用以下java -jar命令直接執行它:

java -jar target/djl-spring-boot-console-sample-${version}.jar

更復雜的應用示例

以下是基於REST API示例的程式碼示例,該示例利用DJL Spring Boot Starter演示了RESTful API實現,該實現可以從Amazon Simple Storage Service(Amazon S3)儲存桶中獲取影像並將物件檢測結果儲存回S3中。詳情點選標題見原文。

 

相關文章