Spring Boot与Eclipse MicroProfile比较


到目前为止,您可能已经听说过Eclipse MicroProfile(MP)。它是一个社区驱动的计划,用于定义企业Java 微服务的规范。MicroProfile仅用了两年时间,但它已经提供了八项创新规范并且正在快速发展。它提供指标,API文档,运行状况检查,容错,分布式跟踪等。有了它,您可以充分利用尖端的云原生技术,并以供应商中立的方式实现!
对于熟悉Spring Boot的开发人员,我们准备了本文,它将使用Spring Boot和MicroProfile开发应用程序的基础知识进行了比较。我们写了两个应用程序,每个解决方案一个。在本文中,我们将介绍它们之间的差异。您可以在GitHub找到这两个项目的源代码。
对于MicroProfile应用程序,我们使用Thorntail(以前称为Wildfly Swarm),但除了设置部分,Open Liberty,Payara,TomEE或任何其他实现看起来完全相同。
在本文中,我们假设您了解Spring Boot,并且我们专注于MicroProfile中的不同之处。

设置项目
我们使用Maven设置了两个应用程序。
使用Thorntail,项目的设置与Spring Boot非常相似。第一个区别在于项目包装。虽然我们使用jar(默认包装)Spring Boot应用程序,但我们需要将其设置Thorntail应用程序的打包WAR。
我们的Spring Boot应用程序使用名为的BOM文件spring-boot-dependencies。Thorntail也提供BOM文件。我们选择了bom,列出了所有稳定,经过良好测试的Thorntail元素。例如,如果您想进行实验,可以使用  bom-all。
Spring Boot和Thorntail都使用Maven插件将用户的类,资源和所选解决方案的所有位打包成一个胖JAR。对于Thorntail,该插件被调用thorntail-maven-plugin。下面的清单显示了其声明以及Thorntail BOM的声明。

<project ...>
 ...
 <packaging>war</packaging>

<dependencyManagement>
 <dependencies>
   <dependency>
     <groupId>io.thorntail</groupId>
     <artifactId>bom</artifactId>
     <version>${version.thorntail}</version>
     <type>pom</type>
     <scope>import</scope>
   </dependency>
 </dependencies>
</dependencyManagement>
...
<build>
 <plugins>
   <plugin>
     <groupId>io.thorntail</groupId>
     <artifactId>thorntail-maven-plugin</artifactId>
     <version>${version.thorntail}</version>
     <executions>
       <execution>
         <goals>
           <goal>package</goal>
         </goals>
       </execution>
     </executions>
   </plugin>
 </plugins>
</build>

定义了基础知识后,我们可以选择我们需要的功能。
相对于我们选择的Spring Boot spring-boot-starter-web,我们microprofile只是为Thorntail 添加一个依赖项。

<dependency>
 <groupId>io.thorntail</groupId>
 <artifactId>microprofile</artifactId>
</dependency>

您可以查看GitHub项目中的最终pom.xml 文件  。
设置项目还有一个不同之处:应该放置静态资源的地方。我们的Spring Boot应用程序将静态资源保留在  src/main/resources/static目录中,而Thorntail应用程序则需要将它们放入src/main/webapp。

公开REST端点
从Spring应用程序公开REST API的最惯用方法是使用Spring MVC。MicroProfile是利用JAX-RS实现相同功能。
首先,对于JAX-RS,Application需要一个类。它扩展  javax.ws.rs.core.Application并可以为所有JAX-RS端点提供全局路径前缀。在我们的例子中它是:

@ApplicationPath("/api")
public class ApplicationConfig extends Application {
}

那么这只是翻译资源类注释的问题。
以下Spring MVC代码:

@RestController
@RequestMapping(value = "/api/greeting", produces = MediaType.APPLICATION_JSON_VALUE)
public class GreetingController {

   @GetMapping
   public Greeting greeting(@RequestParam(value = "name", defaultValue = "World") String name) {
      ...
   }

转换为以下MicroProfile代码:

@Path("/greeting") // 1
@Produces(MediaType.APPLICATION_JSON) // 2
public class GreetingResource {

   @GET // 3
   public Response greeting(@QueryParam("name") @DefaultValue("World") String name) {  // 4
      ...
   }

逐行解释:

  1. JAX-RS端点类应该注释@Path。此注释也是为端点提供任何前缀的位置。
  2. @Produces如果我们想要指定响应的内容类型,则必须使用单独的注释。它有一个名为的对应项,@Consumes用于指定接受的请求实体类型
  3. 处理请求的方法@GET,@POST,@DELETE,@PUT,或者@HEAD,取决于他们是为了处理HTTP方法。
  4. 我们的端点使用查询参数。为了使它工作,我们在Spring MVC中使用了一个注释@RequestParam。对于MicroProfile,要使用的注释是@QueryParam。为了提供默认值,我们添加了一个@DefaultValue注释。

有关javax.ws.rs其他可用注释,请参阅  包。
重要的是还要提到@Context注释。有了它,您可以将HTTP标头或安全上下文等值注入方法或端点。

依赖注入
Spring的核心是它的依赖注入。使用MicroProfile,您可以使用CDI。
这主要意味着使用@Inject注释而不是Spring的@Autowired 注释:

@Inject
   private GreetingGenerator generator;

与Spring类似,CDI有一个bean的概念,这些bean生活在一定的作用域内,@Scope是用于控制作用域的,为Spring的Bean概念将转换为  @ApplicationScoped,@RequestScoped等等CDI注释。
这里是一个GreetingGenerator 类:

@ApplicationScoped
public class GreetingGenerator {
 …
}

查看  javax.enterprise.context软件包以获取所有可用选项的列表。
转换非常简单。唯一的问题是默认作用域不同。在Spring中,默认范围是单例,在CDI中它是@Dependent- 与Spring的原型相对应的作用域。

配置
在我们的Spring应用程序中,我们使用@Value注释注入配置值。使用MicroProfile Config,我们可以实现:

@Inject
@ConfigProperty(name = "greeting.message")
private String message;

上面的message字段的值将取自META-INF/microprofile-config.properties。它可以被环境变量或系统属性覆盖。MicroProfile Config还提供了一种简单的机制来定义自定义ConfigSource配置值的附加源。

执行
要获取代码,请克隆GitHub存储库:

git clone https://github.com/michalszynkiewicz/from-spring-to-microprofile/

存储库包含两个独立目录中的两个项目。要构建其中任何一个,请导航到相应的目录并运行以下命令:

mvn clean package

Spring Boot和Thorntail都生成了一个超级JAR。要运行Thorntail,请进入目标目录并执行以下命令:

java -jar microprofile-from-spring-1.0-SNAPSHOT-thorntail.jar

现在,当您在浏览器中访问http:// localhost:8080时,应该会看到所选应用程序公开的网页。您可以通过浏览器试用该应用程序,也可以直接在http:// localhost:8080 / api / greeting?name = put-your-name-here访问REST API 。

MicroProfile特点
虽然两个示例应用程序的代码非常相似,但MicroProfile具有更多功能。
根据配置,MicroProfile应用程序还会公开:

  • REST端点的OpenAPI文档,位于http:// localhost:8080 / openapi
  • 应用程序指标,包括http:// localhost:8080 / metrics上的线程计数,堆使用情况等
  • 可以在http:// localhost:8080 / healthcheck上使用Kubernetes进行健康检查

此外,在不修改配置的情况下,它可以使用其他MicroProfile规范,例如Fault Tolerance或类型安全的REST客户端。