SpringCloud之服务提供者

一、环境搭建

  • 我们会使用一个Dept部门模块做一个微服务通用案例Consumer消费者(Client)通过REST调用Provider提供者(Server)提供的服务。

一个父工程带着多个Moudule子模块

SpringCloud父工程(Project)下初次带着3个子模块(Module)

  • Springcloud-api 【封装的整体entity/接口/公共配置等】
  • Springcloud-consumer-dept-80 【服务消费者】
  • Springcloud-provider-dept-8001 【服务提供者】

二、SpringCloud版本选择

大版本说明

SpringBoot

SpringCloud

关系

1.2.x

Angel版本(天使)

兼容SpringBoot1.2x

1.3.x

Brixton版本(布里克斯顿)

兼容SpringBoot1.3x,也兼容SpringBoot1.4x

1.4.x

Camden版本(卡姆登)

兼容SpringBoot1.4x,也兼容SpringBoot1.5x

1.5.x

Dalston版本(多尔斯顿)

兼容SpringBoot1.5x,不兼容SpringBoot2.0x

1.5.x

Edgware版本(埃奇韦尔)

兼容SpringBoot1.5x,不兼容SpringBoot2.0x

2.0.x

Finchley版本(芬奇利)

兼容SpringBoot2.0x,不兼容SpringBoot1.5x

2.1.x

Greenwich版本(格林威治)

2.2.x, 2.3.x (Starting with SR5)

Hoxton(霍斯顿)

2.4.x

2020.0.x aka Ilford

实际开发版本关系

spring-boot-starter-parent

spring-cloud-dependencles

版本号

发布日期

版本号

发布日期

1.5.2.RELEASE

2017-03

Dalston.RC1

2017-x

1.5.9.RELEASE

2017-11

Edgware.RELEASE

2017-11

1.5.16.RELEASE

2018-04

Edgware.SR5

2018-10

1.5.20.RELEASE

2018-09

Edgware.SR5

2018-10

2.0.2.RELEASE

2018-05

Fomchiey.BULD-SNAPSHOT

2018-x

2.0.6.RELEASE

2018-10

Fomchiey-SR2

2018-10

2.1.4.RELEASE

2019-04

Greenwich.SR1

2019-03

2.3.x,2.2.x

Hoxton.SR10

2.4.x

2020.0 Release Notes

使用倒数第三个,新版本的依赖有改变,还没有仔细研究过

三、创建工程之服务提供者

  • 新建父工程项目springcloud,切记Packageing是pom模式
  • 主要是定义POM文件,将后续各个子模块公用的jar包等统一提取出来,类似一个抽象父类

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.latte</groupId>
<artifactId>springcloud</artifactId>
<version>1.0-SNAPSHOT</version>
<modules>
<module>springcloudapi</module>
<module>springcloudproviderdept8001</module>
<module>springcloudconsumerdept80</module>
<module>springcloudeureka7001</module>
<module>springcloud-eureka-7002</module>
<module>springcloud-eureka-7003</module>
<module>springcloudproviderdept8002</module>
<module>springcloudproviderdept8003</module>
<module>springcloud-consumer-fdept-feign</module>
<module>springcloud-provider-dept-hystrix-8001</module>
<module>springcloud-consumer-hystrix-dashboard</module>
<module>springcloud-zuul</module>
<module>pringcloud-config-server-3366</module>
<module>springcloud-config-client-3355</module>
<module>springcloud-config-eureka-7001</module>
<module>springcloud-config-dept-8001</module>
</modules>
<!--打包方式 pom-->
<packaging>pom</packaging>
<properties>
<project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
<maven.compiler.source>1.8</maven.compiler.source>
<maven.compiler.target>1.8</maven.compiler.target>
<junit.version>4.12</junit.version>
<log4j.version>1.2.17</log4j.version>
<lombok.version>1.18.8</lombok.version>
</properties>


<dependencyManagement>
<dependencies>
<!--springCloud的依赖-->
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-dependencies</artifactId>
<version>Greenwich.SR1</version>
<type>pom</type>
<scope>import</scope>
</dependency>
<!--SpringBoot-->
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-dependencies</artifactId>
<version>2.1.4.RELEASE</version>
<type>pom</type>
<scope>import</scope>
</dependency>

<!--数据库-->
<dependency>
<groupId>mysql</groupId>
<artifactId>mysql-connector-java</artifactId>
<version>5.1.46</version>
</dependency>
<dependency>
<groupId>com.alibaba</groupId>
<artifactId>druid</artifactId>
<version>1.1.10</version>
</dependency>
<!--SpringBoot 启动器-->
<dependency>
<groupId>org.mybatis.spring.boot</groupId>
<artifactId>mybatis-spring-boot-starter</artifactId>
<version>1.3.2</version>
</dependency>
<!--日志测试~-->
<dependency>
<groupId>ch.qos.logback</groupId>
<artifactId>logback-core</artifactId>
<version>1.2.3</version>
</dependency>
<!--junit~-->
<dependency>
<groupId>junit</groupId>
<artifactId>junit</artifactId>
<version>${junit.version}</version>
</dependency>
<!--log4j~-->
<dependency>
<groupId>log4j</groupId>
<artifactId>log4j</artifactId>
<version>${log4j.version}</version>
</dependency>
<!--lombok~-->
<dependency>
<groupId>org.projectlombok</groupId>
<artifactId>lombok</artifactId>
<version>${lombok.version}</version>
</dependency>


</dependencies>
</dependencyManagement>

</project>

创建 springcloudapi

public class Dept implements Serializable{
private Long deptno;//主键
private String dname;

//表示:存在哪个数据库的字段,一个服务对应一个数据库,同一个信息可能存在不同的数据库
private String db_source;

public Dept(String dname) {
this.dname = dname;
}

public Dept() {
}

@Override
public String toString() {
return "Dept{" +
"deptno=" + deptno +
", dname='" + dname + '\'' +
", db_source='" + db_source + '\'' +
'}';
}

public Long getDeptno() {
return deptno;
}

public void setDeptno(Long deptno) {
this.deptno = deptno;
}

public String getDname() {
return dname;
}

public void setDname(String dname) {
this.dname = dname;
}

public String getDb_source() {
return db_source;
}

public void setDb_source(String db_source) {
this.db_source = db_source;
}
}

创建springcloud-provider-dept-8001

<dependencies>
<!--我们需要拿到实体类,所以要配置api module-->
<dependency>
<groupId>com.latte</groupId>
<artifactId>springcloud-api</artifactId>
<version>1.0-SNAPSHOT</version>
</dependency>

<!--junit-->
<dependency>
<groupId>junit</groupId>
<artifactId>junit</artifactId>
</dependency>
<!--数据库-->
<dependency>
<groupId>mysql</groupId>
<artifactId>mysql-connector-java</artifactId>
</dependency>
<!--数据源-->
<dependency>
<groupId>com.alibaba</groupId>
<artifactId>druid</artifactId>
</dependency>
<!--logback-->
<dependency>
<groupId>ch.qos.logback</groupId>
<artifactId>logback-core</artifactId>
</dependency>
<!--mybatis-->
<dependency>
<groupId>org.mybatis.spring.boot</groupId>
<artifactId>mybatis-spring-boot-starter</artifactId>
</dependency>
<!--test-->
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-test</artifactId>
</dependency>
<!--web-->
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-web</artifactId>
</dependency>
<!--jetty(类似tomcat)-->
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-jetty</artifactId>
</dependency>
<!--热部署工具-->
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-devtools</artifactId>
</dependency>
</dependencies>

application.yml

server:
port: 8001

# mybatis配置
mybatis:
# springcloudapi 模块下的包
type-aliases-package: com.latte.domain
# 本模块下的mybatis-config.xml核心配置文件类路径
config-location: classpath:mybatis/mybatis-config.xml
# 本模块下的mapper配置文件类路径
mapper-locations: classpath:mybatis/mapper/*.xml

# spring配置
spring:
application:
#项目名
name: springcloud-provider-dept
datasource:
# 德鲁伊数据源
type: com.alibaba.druid.pool.DruidDataSource
driver-class-name: com.mysql.jdbc.Driver
url: jdbc:mysql://localhost:3306/springcloud?useUnicode=true&characterEncoding=utf-8
username: root
password: "123456"

mybatis-config.xml(可有可无,可以直接配置到上面的yml文件)

<?xml version="1.0" encoding="UTF-8" ?>
<!DOCTYPE configuration
PUBLIC "-//mybatis.org//DTD Config 3.0//EN" "http://mybatis.org/dtd/mybatis-3-config.dtd">

<configuration>
<settings>
<!--开启二级缓存-->
<setting name="cacheEnabled" value="true"/>
</settings>
</configuration>

DeptMapper.xml

<?xml version="1.0" encoding="UTF-8" ?>
<!DOCTYPE mapper PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN" "http://mybatis.org/dtd/mybatis-3-mapper.dtd" >
<mapper namespace="com.latte.dao.DeptDao">
<insert id="addDept" parameterType="Dept">
insert into dept (dname, db_source)
values (#{dname},DATABASE())
</insert>

<select id="queryById" resultType="Dept" parameterType="Long">
select * from dept where deptno = #{deptno};
</select>

<select id="queryAll" resultType="Dept">
select * from dept;
</select>
</mapper>

DeptController

//提供Restful服务
@RestController
public class DeptController {

@Autowired
private DeptService deptService;

@PostMapping("/dept/add")
public boolean addDept(Dept dept) {
return deptService.addDept(dept);
}

@GetMapping("/dept/get/{id}")
public Dept get(@PathVariable("id") Long id) {
Dept dept = deptService.queryById(id);
if (dept == null) {
throw new RuntimeException("Fail");
}
return dept;
}

@GetMapping("/dept/list")
public List<Dept> queryAll() {
return deptService.queryAll();
}
@Mapper
@Repository
public interface DeptDao {

public boolean addDept(Dept dept);

public Dept queryById(Long id);

public List<Dept> queryAll();
}
@Service
public class DeptServiceImpl implements DeptService {
@Autowired
private DeptDao deptDao;

@Override
public boolean addDept(Dept dept) {
return deptDao.addDept(dept);
}

@Override
public Dept queryById(Long id) {
return deptDao.queryById(id);
}

@Override
public List<Dept> queryAll() {
return deptDao.queryAll();
}
}
public interface DeptService {

public boolean addDept(Dept dept);

public Dept queryById(Long id);

public List<Dept> queryAll();
}

启动类

@SpringBootApplication
public class DeptProvider_8001 {
public static void main(String[] args) {
SpringApplication.run(DeptProvider_8001.class,args);
}
}

创建springcloud-consumer-dept-80
pom.xml

<dependencies>
<!--我们需要拿到实体类,所以要配置api module-->
<dependency>
<groupId>com.latte</groupId>
<artifactId>springcloud-api</artifactId>
<version>1.0-SNAPSHOT</version>
</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>
</dependency>
</dependencies>

application.yml

server:
port: 80

springcloud-consumer-dept-80访问springcloud-provider-dept-8001下的controller使用REST方式

DeptConsumerController.java

@RestController
public class DeptConsumerController {

/**
* 理解:消费者,不应该有service层~
* RestTemplate .... 供我们直接调用就可以了! 注册到Spring中
* (地址:url, 实体:Map ,Class<T> responseType)
* <p>
* 提供多种便捷访问远程http服务的方法,简单的Restful服务模板~
*/
@Autowired
private RestTemplate restTemplate;
/**
* 服务提供方地址前缀
*
*/
private static final String REST_URL_PREFIX = "http://localhost:8001";
/**
* 消费方添加部门信息
* @param dept
* @return
*/
@RequestMapping("/consumer/dept/add")
public boolean add(Dept dept) {
// postForObject(服务提供方地址(接口),参数实体,返回类型.class)
return restTemplate.postForObject(REST_URL_PREFIX + "/dept/add", dept, Boolean.class);
}

/**
* 消费方根据id查询部门信息
* @param id
* @return
*/
@RequestMapping("/consumer/dept/get/{id}")
public Dept get(@PathVariable("id") Long id) {
// getForObject(服务提供方地址(接口),返回类型.class)
return restTemplate.getForObject(REST_URL_PREFIX + "/dept/get/" + id, Dept.class);
}

/**
* 消费方查询部门信息列表
* @return
*/
@RequestMapping("/consumer/dept/list")
public List<Dept> list() {
return restTemplate.getForObject(REST_URL_PREFIX + "/dept/list", List.class);
}
}

使用RestTemplete先需要放入Spring容器中

ConfigBean.java

@Configuration
public class ConfigBean {//@Configuration -- spring applicationContext.xml
@Bean
public RestTemplate getRestTemplate(){
return new RestTemplate();
}
}

SpringCloud之服务提供者_springcloud