Spring Boot POM 详解



        正如这幅图所展示的那样,在Spring IO Framework体系中,Spring Boot处在Execution layer,来看看官方对这层的解释:


    The Spring IO Execution layer provides domain-specific runtimes (DSRs) for applications built on the IO Foundation modules. A DSR may run standalone without requiring deployment to an external container.


        还是引用官方的话来阐述一下Spring Boot主要是做什么的:


    Spring Boot reduces the effort needed to create production-ready, DevOps-friendly, XML-free Spring applications. It simplifies bootstrapping of Spring projects with minimal code, implements an extensible set of operational features such as automated health checking and metrics endpoints, and supports embedded containers enabling the creation of self-contained executables.

        来看看这里的几个关键词:


        Production-ready,DevOps-friendly - 主要集中在Spring Boot Actuator模块,提供线上监控运维相关的特性,比方说health checking,metrics endpoints,或者通过提供诸如maven exec,或者类似one jar那种的self-contained executables。


        XML-free - 预定义了很多Annotation,配置元编程风格。

        Spring Boot给我的感觉更像是Spring社区的DevOps平台,集成并提供了诸如依赖管理,部署自动化,监控运维等特性。


        Ok,到了这篇文章的重点部分。接下来,我们来分析一下Spring Boot是如何组织管理依赖的。来看一下它项目代码的POM结构。


       首先是根目录的Pom,如:

        <groupId>org.springframework.boot</groupId>
	<artifactId>spring-boot-build</artifactId>
	<version>1.2.1.BUILD-SNAPSHOT</version>
	<packaging>pom</packaging>
	<name>Spring Boot Build</name>

       挺简洁的,除了声明了antrun,surefire和replacer插件外,就定义了包括default,integration,ci在内的三个profile。里面值得关注几个点:

       1. 默认profile里面声明了一系列堪称最小依赖modules,如下:

<modules>
        <module>spring-boot-dependencies</module>
        <module>spring-boot-parent</module>
        <module>spring-boot-versions</module>
        <module>spring-boot-tools</module>
        <module>spring-boot</module>
        <module>spring-boot-autoconfigure</module>
        <module>spring-boot-actuator</module>
        <module>spring-boot-docs</module>
        <module>spring-boot-starters</module>
        <module>spring-boot-cli</module>
</modules>

     这里面的关系,尤其是父子模块关系,后面会介绍。


     2. 大家可以关注一下com.google.code.maven-replacer-plugin这个插件,主要是做属性文件替换的,和alibaba开源的antx maven插件有些类似。当然如果你热衷于maven的resources的filter机制,相信你会更喜欢这个replacer插件。


    下面,我们来看看上面提到的父子模块关系, spring-boot-dependencies是一个parent pom,如下配置:

<groupId>org.springframework.boot</groupId>
  <artifactId>spring-boot-dependencies</artifactId>
  <version>1.2.1.BUILD-SNAPSHOT</version>
  <packaging>pom</packaging>

     它强制了maven版本,如:
<prerequisites>
    <maven>3.0.2</maven>
  </prerequisites>

    并用dependencyManagement声明了一堆的依赖,如:

<properties>
    <!-- Spring Boot -->
    <spring-boot.version>1.2.1.BUILD-SNAPSHOT</spring-boot.version>
    <!-- Third Party -->
    <activemq.version>5.10.0</activemq.version>
    <aspectj.version>1.8.4</aspectj.version>
    <atomikos.version>3.9.3</atomikos.version>
    <bitronix.version>2.1.4</bitronix.version>
    <commons-beanutils.version>1.9.2</commons-beanutils.version>
    <commons-collections.version>3.2.1</commons-collections.version>
    <commons-dbcp.version>1.4</commons-dbcp.version>
    <commons-dbcp2.version>2.0.1</commons-dbcp2.version>
    <commons-digester.version>2.1</commons-digester.version>
    <commons-pool.version>1.6</commons-pool.version>
    <commons-pool2.version>2.2</commons-pool2.version>
    <crashub.version>1.3.0</crashub.version>
    <dropwizard-metrics.version>3.1.0</dropwizard-metrics.version>
    <flyway.version>3.0</flyway.version>
    <freemarker.version>2.3.21</freemarker.version>
    <gemfire.version>7.0.2</gemfire.version>
    <glassfish-el.version>3.0.0</glassfish-el.version>
    <gradle.version>1.6</gradle.version>
    <groovy.version>2.3.8</groovy.version>
    <gson.version>2.3</gson.version>
    <h2.version>1.4.183</h2.version>
    <hamcrest.version>1.3</hamcrest.version>
    <hibernate.version>4.3.7.Final</hibernate.version>
    <hibernate-entitymanager.version>${hibernate.version}</hibernate-entitymanager.version>
    <hibernate-validator.version>5.1.3.Final</hibernate-validator.version>
    <hikaricp.version>2.2.5</hikaricp.version>
    <hornetq.version>2.4.5.Final</hornetq.version>
    <hsqldb.version>2.3.2</hsqldb.version>
    <httpasyncclient.version>4.0.2</httpasyncclient.version>
    <httpclient.version>4.3.6</httpclient.version>
    <jackson.version>2.4.4</jackson.version>
    <janino.version>2.6.1</janino.version>
    <javassist.version>3.18.1-GA</javassist.version> <!-- Same as Hibernate -->
    <javax-cache.version>1.0.0</javax-cache.version>
    <javax-mail.version>1.5.2</javax-mail.version>
    <javax-transaction.version>1.2</javax-transaction.version>
    <jaxen.version>1.1.6</jaxen.version>
    <jdom2.version>2.0.5</jdom2.version>
    <jedis.version>2.5.2</jedis.version>
    <jersey.version>2.14</jersey.version>
    <jetty.version>9.2.4.v20141103</jetty.version>
    <jetty-jsp.version>2.2.0.v201112011158</jetty-jsp.version>
    <joda-time.version>2.5</joda-time.version>
    <jolokia.version>1.2.3</jolokia.version>
    <json-path.version>0.9.1</json-path.version>
    <jstl.version>1.2</jstl.version>
    <junit.version>4.12</junit.version>
    <liquibase.version>3.3.0</liquibase.version>
    <log4j.version>1.2.17</log4j.version>
    <log4j2.version>2.1</log4j2.version>
    <logback.version>1.1.2</logback.version>
    <mockito.version>1.10.8</mockito.version>
    <mongodb.version>2.12.4</mongodb.version>
    <mysql.version>5.1.34</mysql.version>
    <reactor.version>1.1.5.RELEASE</reactor.version>
    <reactor-spring.version>1.1.3.RELEASE</reactor-spring.version>
    <servlet-api.version>3.1.0</servlet-api.version>
    <simple-json.version>1.1.1</simple-json.version>
    <slf4j.version>1.7.8</slf4j.version>
    <snakeyaml.version>1.14</snakeyaml.version>
    <solr.version>4.7.2</solr.version>
    <spock.version>0.7-groovy-2.0</spock.version>
    <spring.version>4.1.3.RELEASE</spring.version>
    <spring-amqp.version>1.4.1.RELEASE</spring-amqp.version>
    <spring-cloud-connectors.version>1.1.0.RELEASE</spring-cloud-connectors.version>
    <spring-batch.version>3.0.2.RELEASE</spring-batch.version>
    <spring-data-releasetrain.version>Evans-SR1</spring-data-releasetrain.version>
    <spring-hateoas.version>0.16.0.RELEASE</spring-hateoas.version>
    <spring-integration.version>4.1.1.RELEASE</spring-integration.version>
    <spring-loaded.version>1.2.1.RELEASE</spring-loaded.version>
    <spring-mobile.version>1.1.3.RELEASE</spring-mobile.version>
    <spring-security.version>3.2.5.RELEASE</spring-security.version>
    <spring-security-jwt.version>1.0.2.RELEASE</spring-security-jwt.version>
    <spring-social.version>1.1.0.RELEASE</spring-social.version>
    <spring-social-facebook.version>1.1.1.RELEASE</spring-social-facebook.version>
    <spring-social-linkedin.version>1.0.1.RELEASE</spring-social-linkedin.version>
    <spring-social-twitter.version>1.1.0.RELEASE</spring-social-twitter.version>
    <spring-ws.version>2.2.0.RELEASE</spring-ws.version>
    <sun-mail.version>${javax-mail.version}</sun-mail.version>
    <thymeleaf.version>2.1.3.RELEASE</thymeleaf.version>
    <thymeleaf-extras-springsecurity3.version>2.1.1.RELEASE</thymeleaf-extras-springsecurity3.version>
    <thymeleaf-extras-conditionalcomments.version>2.1.1.RELEASE</thymeleaf-extras-conditionalcomments.version>
    <thymeleaf-layout-dialect.version>1.2.7</thymeleaf-layout-dialect.version>
    <thymeleaf-extras-data-attribute.version>1.3</thymeleaf-extras-data-attribute.version>
    <tomcat.version>8.0.15</tomcat.version>
    <undertow.version>1.1.1.Final</undertow.version>
    <velocity.version>1.7</velocity.version>
    <velocity-tools.version>2.0</velocity-tools.version>
    <wsdl4j.version>1.6.3</wsdl4j.version>
  </properties>

     

     问题来了,spring是如何测试并管理这些非spring生态圈依赖的?奥秘一切尽在下面的示例代码(原理比较简单,请参考文献2):

   

<dependencyManagement>
    <dependencies>
        <dependency>
            <groupId>io.spring.platform</groupId>
            <artifactId>platform-bom</artifactId>
            <version>2.0.1.RELEASE</version>
            <type>pom</type>
            <scope>import</scope>
        </dependency>
    </dependencies>
</dependencyManagement>

     除了对Jar的声明依赖,该pom还对maven常见plugin做了声明依赖,用过Maven version插件的同学都会觉得这是一个很好的习惯,对吧。除此之外,里面还有一个plugin git-commit-id-plugin需要额外注意一下,用过buildnumber plugin的同学可能会很好理解该plugin的功能。


     最后来看一下 spring-boot-parent,这是一个二级parent pom,如下图:



     重点提一下几个需要注意的点:

    1. 混合使用dependencyManagement和dependencies,这个也是我比较喜欢的。


    2. 详细配置了org.eclipse.m2e插件的lifecycleMappingMetadata,这个也很重要,对那些通过maven project方式将工程导入eclipse的同学无疑是个福音。


    3. maven-enforcer-plugin插件的使用,这个也是我比较喜欢的,目前来看规则还是比较简单的,如:

<rules>
	<requireJavaVersion>
	<span style="white-space:pre">	</span><version>(1.7,)</version>
	</requireJavaVersion>
	<requireProperty>
		<property>main.basedir</property>
	</requireProperty>
	<requireProperty>
		<property>project.organization.name</property>
	</requireProperty>
	<requireProperty>
		<property>project.name</property>
	</requireProperty>
	<requireProperty>
		<property>project.description</property>
	</requireProperty>
</rules>

       

       更为详细的请参看enforcers官方文档,https://maven.apache.org/enforcer/enforcer-rules/https://maven.apache.org/enforcer/enforcer-rules/

       4. maven-jar-plugin插件的使用,对于那些通过Java package API进行兼容性判断的工具很有用。

       Ok,剩下的几个module都是在该父POM的基础上做了一些个性依赖,没什么好讲的,分析到这里就可以了。希望这篇文章能为那些立志于建立自己顶级POM的团队带来帮助。


参考文献:

1. http://docs.spring.io/spring-boot/docs/current-SNAPSHOT/reference/htmlsingle/#getting-started-introducing-spring-boot

2. https://dzone.com/articles/how-to-use-spring-io-platform-and-spring-boot-toge?utm_source=Top%205&utm_medium=email&utm_campaign=top5%202016-06-10

  • 2
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
Fabric Java SDK 是为 Hyperledger Fabric 区块链平台开发的 Java SDK,它提供了访问 Fabric 网络的所有必要接口,包括身份验证、链码调用、交易提交等。Spring Boot 是一个基于 Spring 框架的快速开发应用程序的工具,它提供了诸多便利的特性,如自动配置、快速开发等。 在使用 Fabric Java SDK 开发 Spring Boot 项目时,我们可以采用以下步骤: 1. 配置 Maven 依赖 在 pom.xml 文件中添加以下依赖: ```xml <dependency> <groupId>org.hyperledger.fabric-sdk-java</groupId> <artifactId>fabric-sdk-java</artifactId> <version>2.2.0</version> </dependency> <dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-web</artifactId> </dependency> ``` 2. 配置 Fabric SDK 在 Spring Boot 项目中,我们可以使用 @Configuration 注解配置 Fabric SDK。在配置中,我们需要指定以下参数: - Fabric 网络的 CA 证书 - Fabric 网络的 MSP 证书 - Fabric 网络的连接配置文件 ```java @Configuration public class FabricConfig { private static final String CONNECTION_PROFILE_PATH = "connection-profile.yaml"; private static final String MSP_PATH = "/msp"; private static final String CA_ORG1_URL = "http://localhost:7054"; private static final String CHANNEL_NAME = "mychannel"; @Bean public NetworkConfig getNetworkConfig() throws Exception { Path connectionProfilePath = Paths.get(CONNECTION_PROFILE_PATH); return NetworkConfig.fromYamlFile(connectionProfilePath.toFile()); } @Bean public User getUser(NetworkConfig networkConfig) throws Exception { UserContext userContext = new UserContext(); userContext.setName("user1"); userContext.setAffiliation("org1"); userContext.setMspId("Org1MSP"); Path mspPath = Paths.get(networkConfig.getOrganizationInfo("Org1").getMspId(), MSP_PATH); userContext.setEnrollment(new Enrollment() { @Override public PrivateKey getKey() { try { return loadPrivateKey(mspPath); } catch (Exception e) { throw new RuntimeException(e); } } @Override public String getCert() { try { return new String(loadCert(mspPath), "UTF-8"); } catch (Exception e) { throw new RuntimeException(e); } } }); return userContext; } @Bean public FabricGateway getGateway(NetworkConfig networkConfig, User user) throws Exception { Gateway.Builder builder = Gateway.createBuilder(); builder.identity(user); builder.networkConfig(networkConfig); return builder.connect().get(); } @Bean public Contract getContract(FabricGateway gateway) throws Exception { return gateway.getNetwork(CHANNEL_NAME).getContract("mychaincode"); } private byte[] loadCert(Path mspPath) throws Exception { Path certPath = mspPath.resolve(Paths.get("signcerts", "cert.pem")); return Files.readAllBytes(certPath); } private PrivateKey loadPrivateKey(Path mspPath) throws Exception { Path keyPath = mspPath.resolve(Paths.get("keystore", "priv.key")); byte[] keyBytes = Files.readAllBytes(keyPath); return getPrivateKeyFromBytes(keyBytes); } private PrivateKey getPrivateKeyFromBytes(byte[] keyBytes) throws Exception { PKCS8EncodedKeySpec spec = new PKCS8EncodedKeySpec(keyBytes); KeyFactory factory = KeyFactory.getInstance("EC"); return factory.generatePrivate(spec); } } ``` 3. 实现接口方法 在接口方法中,我们可以使用 Fabric SDK 提供的 API 实现对链码的调用、交易的提交等操作。 ```java @RestController public class MyController { private static final String CHAINCODE_NAME = "mychaincode"; private static final String FUNCTION_NAME = "invoke"; private static final String KEY = "key1"; private static final String VALUE = "value1"; @Autowired private Contract contract; @PostMapping("/set") public String setValue() throws Exception { contract.submitTransaction(FUNCTION_NAME, KEY, VALUE); return "success"; } @GetMapping("/get") public String getValue() throws Exception { byte[] result = contract.evaluateTransaction(FUNCTION_NAME, KEY); return new String(result, "UTF-8"); } } ``` 以上就是使用 Fabric Java SDK 开发 Spring Boot 项目的流程。通过这种方式,我们可以方便地实现对 Fabric 网络的访问,并快速开发出符合需求的应用程序。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值