模拟@SpringBootApplication注解实现插件化开发

在我们使用SpringBoot以及SpringCloud的一系列组件(比如说Eureka)的时候,我们都是只需要添加注解@Enablexxx就可以引入对应的模块(对于EurekaServer仅需使用@EnableEurekaServer注解),非常方便快捷。这其实对于我们抽取一些通用的功能非常有利,避免了每次都要写或者复制同样的代码,提高开发效率。
在探究原理之后,我做了一个自己的实现。我们来看一下使用效果:


使用效果图.png

运行效果图.gif

我们来探究一下原理实现:
首先介绍一下Spring的JavaBean注解:
@Component
@Controller
@Service
@Configuration
@Import
@ImportResource
@Bean
此次略过介绍,有空再补
1. 创建一个Admin模块项目(SpringBoot项目),pom.xml如下

<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
    xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
    <modelVersion>4.0.0</modelVersion>

    <groupId>com.sanisy</groupId>
    <artifactId>admin-demo</artifactId>
    <version>0.0.1-SNAPSHOT</version>
    <packaging>jar</packaging>

    <name>admin-demo</name>
    <description>Demo project for Spring Boot</description>

    <parent>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-parent</artifactId>
        <version>2.0.1.RELEASE</version>
        <relativePath/> <!-- lookup parent from repository -->
    </parent>

    <properties>
        <project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
        <project.reporting.outputEncoding>UTF-8</project.reporting.outputEncoding>
        <java.version>1.8</java.version>
    </properties>

    <dependencies>
        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-freemarker</artifactId>
        </dependency>
        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-web</artifactId>
        </dependency>

        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-devtools</artifactId>
            <scope>runtime</scope>
        </dependency>
        <dependency>
            <groupId>org.projectlombok</groupId>
            <artifactId>lombok</artifactId>
            <optional>true</optional>
        </dependency>
        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-test</artifactId>
            <scope>test</scope>
        </dependency>
    </dependencies>

    <build>
        <plugins>
            <plugin>
                <groupId>org.apache.maven.plugins</groupId>
                <artifactId>maven-source-plugin</artifactId>
                <version>2.2.1</version>
            </plugin>
        </plugins>
    </build>
</project>

项目目录结构如下

Admin模块整体结构.png

LoginController代码

package com.sanisy.controller;

import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestMethod;
import org.springframework.web.bind.annotation.ResponseBody;

/**
 * Created by Sanisy on 2018/4/30.
 */
@Slf4j
@Controller
@RequestMapping(value = "/admin/login")
public class LoginController {

    /**
     * 登录页
     */
    @Value("${login.page}")
    private String loginPage;

    /**
     * 登录页
     * @return
     */
    @RequestMapping(value = "/page")
    public String loginPage() {
        log.info("This is login page:{}", loginPage);
        return loginPage;
    }

    /**
     * 用户登录
     * @param userName
     * @param password
     * @return
     */
    @RequestMapping(value = "/login", method = RequestMethod.POST)
    @ResponseBody
    public String login(String userName, String password) {
        if (!"admin".equals(userName) || !"123456".equals(password)) {
            log.info("login fail,userName={},password={}", userName, password);
            return "login fail:userName or password error!!!";
        }

        return "login success, welcome to come here!";
    }
}

AdminAutoConfiguration代码

package com.sanisy.annotations;

import org.springframework.context.annotation.ComponentScan;

/**
 * Created by Sanisy on 2018/5/1.
 */
@ComponentScan(basePackages =
        {
                "com.sanisy",
                "com.sanisy.controller",
        })
public class AdminAutoConfiguration {
}

EnableAdminDemo代码

package com.sanisy.annotations;

import org.springframework.context.annotation.Configuration;
import org.springframework.context.annotation.Import;

import java.lang.annotation.ElementType;
import java.lang.annotation.Retention;
import java.lang.annotation.RetentionPolicy;
import java.lang.annotation.Target;

/**
 * Created by Sanisy on 2018/4/30.
 */
@Retention(RetentionPolicy.RUNTIME)
@Target(ElementType.TYPE)
@Configuration
@Import(AdminAutoConfiguration.class)
public @interface EnableAdminDemo {

}

以上代码完成后执行maven命令:

1.将项目打包成jar包:mvn clean install
2.将jar包部署到本地maven仓库:mvn install:install-file -Dfile=E:\Study\Workspaces\Idea\admin-demo\target\admin-demo-0.0.1-SNAPSHOT.jar -DgroupId=com.sanisy -DartifactId=admin-demo -Dversion=2.0.2 -Dpackaging
=jar

2. 使用Admin模块
创建一个新的SpringBoot项目(这里是enable-demo),pom.xml文件如下

<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
    xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
    <modelVersion>4.0.0</modelVersion>

    <groupId>com.dodo</groupId>
    <artifactId>enable-demo</artifactId>
    <version>0.0.1-SNAPSHOT</version>
    <packaging>jar</packaging>

    <name>enable-demo</name>
    <description>Demo project for Spring Boot</description>

    <parent>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-parent</artifactId>
        <version>2.0.1.RELEASE</version>
        <relativePath/> <!-- lookup parent from repository -->
    </parent>

    <properties>
        <project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
        <project.reporting.outputEncoding>UTF-8</project.reporting.outputEncoding>
        <java.version>1.8</java.version>
    </properties>

    <dependencies>
        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-freemarker</artifactId>
        </dependency>
        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-web</artifactId>
        </dependency>

        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-devtools</artifactId>
            <scope>runtime</scope>
        </dependency>
        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-test</artifactId>
            <scope>test</scope>
        </dependency>

        <dependency>
            <groupId>org.projectlombok</groupId>
            <artifactId>lombok</artifactId>
            <optional>true</optional>
        </dependency>

        <!--引入Admin模块依赖-->
        <dependency>
            <groupId>com.sanisy</groupId>
            <artifactId>admin-demo</artifactId>
            <version>2.0.2</version>
        </dependency>
    </dependencies>

    <build>
        <plugins>
            <plugin>
                <groupId>org.springframework.boot</groupId>
                <artifactId>spring-boot-maven-plugin</artifactId>
            </plugin>
        </plugins>
    </build>
</project>

工程目录结构如下

enable-demo目录结构.png

通过@EnableAdminDemo注解使用Admin模块

package com.dodo;

import com.sanisy.annotations.EnableAdminDemo;
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;

@SpringBootApplication
@EnableAdminDemo
public class EnableDemoApplication {

    public static void main(String[] args) {
        SpringApplication.run(EnableDemoApplication.class, args);
    }
}
最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
平台声明:文章内容(如有图片或视频亦包括在内)由作者上传并发布,文章内容仅代表作者本人观点,简书系信息发布平台,仅提供信息存储服务。

推荐阅读更多精彩内容

  • Spring Boot 参考指南 介绍 转载自:https://www.gitbook.com/book/qbgb...
    毛宇鹏阅读 46,958评论 6 342
  • Android 自定义View的各种姿势1 Activity的显示之ViewRootImpl详解 Activity...
    passiontim阅读 173,353评论 25 708
  • Spring Cloud为开发人员提供了快速构建分布式系统中一些常见模式的工具(例如配置管理,服务发现,断路器,智...
    卡卡罗2017阅读 134,948评论 18 139
  • 用两张图告诉你,为什么你的 App 会卡顿? - Android - 掘金 Cover 有什么料? 从这篇文章中你...
    hw1212阅读 12,958评论 2 59
  • 01 二八年华,一个女子最美好的年岁从此开始,从愚笨懵懂走到心思细腻,从稚气未脱到眉目之间暗转风情。 一个女子的一...
    与故阅读 988评论 0 2