admin 管理员组

文章数量: 887177


2024年1月5日发(作者:legacy是什么意思翻译)

1、 Spring cloud简介

按照官方的话说:Spring Cloud 为开发者提供了在分布式系统(如配置管理、服务发现、断路器、智能路由、微代理、控制总线、一次性 Token、全局锁、决策竞选、分布式会话和集群状态)操作的开发工具。最关键的是它足够简单,一般的开发人员只需要几天时间就可以学会它的基本用法。

本教程包括7个例子和相关短文,都是最简单的用法,也是默认最基本的用法,在实际生产环境中也可以用上,当然是初步使用。

本文7个例子包括:

1)一个基本的spring boot应用。

2)分布式配置管理服务端

3)分布式配置管理客户端(微服务应用)

4)服务注册服务端

5)服务注册发现客户端(微服务应用)

6)spring boot风格的web前端应用

7)使用docker发布应用

开源项目地址:/zhou666/spring-cloud-7simple

2、 使用spring boot创建一个应用

Spring Boot是Spring团队推出的新框架,它所使用的核心技术还是Spring框架,主要是Spring 4.x,所以如果熟悉spring 4的人,能够更快的接受和学会这个框架。Spring boot可以看做是在spring框架基础上再包了一层,这一层包含方便开发者进行配置管理和快速开发的模块,以及提供了一些开箱即用的工具,比如监控等。

Spring Boot官方文档有中文翻译版:

/qibaoguang/Spring-Boot-Reference-Guide

要实现一个spring boot开发环境和传统的应用没有区别,这里用的是:

IDE:myeclipse 10

JDK:jdk1.7

WINDOWS:mvn 3

在桌面windows环境里需要单独安装方便我们使用命令行进行打包和操作。Eclipse环境里也需要安装mvn插件,当然如果使用的是myeclipse,那么自带的mvn环境就足够了。以下是建立spring boot helloworld应用的步骤。注意这是一个web应用,使用了嵌入式的tomcat。

1) 首选建立一个最简单的maven工程,如下图:

这个应用只有一个类,编写代码如下:

@Controller

@SpringBootApplication

public class SampleController {

@ResponseBody

@RequestMapping(value = "/")

String home() {

return "Hello World!";

}

public static void main(String[] args) throws Exception {

(, args);

}

}

@SpringBootApplication相当于@Configuration、@EnableAutoConfiguration和 @ComponentScan,你也可以同时使用这3个注解。其中@Configuration、@ComponentScan是spring框架的语法,在spring 3.x就有了,用于代码方式创建配置信息和扫描包。@EnableAutoConfiguration是spring boot语法,表示将使用自动配置。你如果下载了spring boot源码,就会看到spring boot实现了很多starter应用,这些starter就是一些配置信息(有点类似于docker,一组环境一种应用的概念),spring boot看到引入的starter包,就可以计算如果自动配置你的应用。

2) 配置

这个应用不需要配置文件,写完class后就可以直接配置文件了,当然先配置也一样。Pom文件配置如下:

cloud-simple-helloword

0.0.1

jar

xsi:schemaLocation="/POM/4.0.0

4.0.0

spring-boot-starter-parent

E

xmlns:xsi="/2001/XMLSchema-instance"

/xsd/">

cloud-simple-helloword

spring-boot-starter-web

spring-boot-maven-plugin

pom文件配置完,你就可以运行应用了,点击F11,或者在SampleController类右键“Run Java Application”就可以看到应用启动并运行了。

你会看到helloworld字样,这是一个web应用,使用了嵌入式的tomcat。 此时在浏览器输入localhost:8080/, 在pom配置中我们仅仅使用了spring-boot-starter-web依赖,spring boot会根据此依赖下载相关jar包并初始化基本的运行环境,比如说绑定端口8080等。

spring boot封装所有配置信息为键值类型,你想改变默认配置,只需要向应用传入这个键值对就可以,比如我们想改变绑定端口为8081,那么你在main方法里传入“—=8081”即可,或者干脆使用:

(, "--=8081");

3) 部署spring boot应用

要部署运行spring boot应用,首选要打包spring boot应用,你在pom文件中看到的spring-boot-maven-plugin插件就是打包spring boot应用的。

进入工程目录运行mvn package,如:

D:cloud-simple-helloword>mvn package

打包过后就可以进入target目录使用java原生命令执行这个应用了。

D:cloud-simple-hellowordtarget>java -jar --=8081

如此,你就看到一个基于jar包的web应用启动了。

Spring boot提供的一些开箱即用的应用非常容易使用,比如监控,你只需要在pom文件中引入:

spring-boot-starter-actuator

引入之后,spring boot是默认开启监控的,运行应用你可以在浏览器中输入:

localhost:8080/health

就可以看到默认的监控信息了:

{"status":"UP","diskSpace":{"status":"UP","total":0,"free":91618398208,"threshold":10485760}}

信息包括程序执行状态以及基本的磁盘信息。

3、 使用spring cloud实现分布式配置管理

本文涉及到的项目:

cloud-config-repo:配置文件存放的文件夹

cloud-simple-service:一个使用mybatis的数据库应用

分布式配置管理应该是分布式系统和微服务应用的第一步。想象一下如果你有几十个服务或应用需要配置,而且每个服务还分为开发、测试、生产等不同维度的配置,那工作量是相当大的,而且还容易出错。如果能把各个应用的配置信息集中管理起来,使用一套机制或系统来管理,那么将极大的提高系统开发的生产效率,同时也会提高系统开发环境和生产环境运行的一致性。

在传统开发中我们往往需要自己开发“配置管理服务器”,你可以使用redis、ldap、zookeeper、db等来存放统一配置信息,然后开发一个管理界面来进行管理。传统的做法没什么问题,和spring cloud所提供的配置管理方案相比,就是前者需要自己开发,而后者直接简单使用现成的组件即可。当然还有很重要的一点,spring 配置管理模块由于是spring boot核心来实现的,因此做了大量的工作,可以把一些启动参数进行外部配置,这在传统的方案中是很难办到的,因为涉及到要改写第三方组件的问题,难度很大。比如web应用的绑定端口,传统应用只能在tomcat配置文件里改,而spring cloud却可以放到远程,类似的还有数据库连接、安全框架配置等。

要使用spring cloud分布式配置文件总体上分为3个大的步骤,首选你需要创建存放配置文件的仓库,然后创建一个配置文件服务器,该服务器将配置文件信息转化为rest接口数据,然后创建一个应用服务,该服务演示使用分布式配置文件信息。

1)创建配置文件存放仓库

Spring cloud使用git或svn存放配置文件,默认情况下使用git,因此你需要安装git私服或者直接使用互联网上的github或者a,这里推荐使用a。本文示例使用的是a,创建好git工程后,也就是文章开头所提到的工程,在此工程再创建一个文件夹cloud-config-repo来存放配置文件。然后创建两个配置文件:

ties

ties

这两个文件分别对应开发环境和测试环境所需要的配置信息,配置信息如下:

=jdbc:mysql://10.0.12.170:3306/test?useUnicode=true&characterEncoding=utf-8

me=csst

rd=csst

:DEBUG

配置信息提供了数据库连接参数等,这是因为后面的应用服务中使用到了数据库。

2)创建spring cloud配置服务器

配置文件仓库创建好了后,就需要创建配置管理服务器,如前所述该服务器只是将配置文件转换为rest接口服务,不做其它用途。这个服务器的功能也是spring cloud提供的,所以我们只需要引入相关jar包,稍微设置一下即可。创建该服务应用,你需要首选创建一个空的maven工程:

然后在这个工程中增加一个类,命名为:ConfigServerApplication,代码如下:

@SpringBootApplication

@EnableConfigServer

public class ConfigServerApplication {

public static void main(String[] args) {

(, args);

}

}

可以看到,我们只需要用@EnableConfigServer激活该应用为配置文件服务器即可。如此以来该应用启动后就会完成前面提到的功能,即:读取远程配置文件,转换为rest接口服务。

当然,需要配置远程配置文件读取路径,在ties中:

=8888

=/zhou666/

Paths=cloud-config-repo

其中是配置当前web应用绑定8888端口,指定配置文件所在的git工程路径,searchPaths表示将搜索该文件夹下的配置文件(我们的配置文件放在spring-cloud-7simple这个工程的cloud-config-repo文件夹下)。

最后,还需要在pom文件中增加配置服务器的相关依赖:

spring-cloud-config-server

如此以来,配置文件服务器就建立好了,可以直接启动了,服务端口是8888,应用只需要绑定改服务器的uri和端口号就可以拿到配置信息了。

3) 创建一个服务使用该远程配置

现在可以创建一个服务使用该远程配置了,你可以在远程配置中定义一个简单的自定义信息,比如:

e=helloword

然后使用前面我们提到的spring boot helloworld应用来读取这个信息。当然,限于篇幅我们直接使用比较复杂的一个服务来演示这个配置管理器的使用,这个服务需要用到数据库访问,数据库访问层我们使用的是mybaits,数据表只有一个,DDL如下:

CREATE TABLE `user` (

`id` varchar(50) NOT NULL DEFAULT '',

`username` varchar(50) DEFAULT NULL,

PRIMARY KEY (`id`)

) ENGINE=InnoDB DEFAULT CHARSET=utf8;

创建好数据表后,回到我的应用服务:

该服务使用DataSourceProperties封装了mybatis加载配置信息。要拿到远程配置信息,需要设置配置管理服务器地址,该配置设置在:

ties

该配置文件信息如下:

=127.0.0.1:${:8888}

=cloud-config

e=${e:dev}

其中指定远程加载配置信息的地址,就是前面我们刚建立的配置管理服务器的地址,绑定端口8888,其中:8888,表示如果在命令行提供了参数,我们就用这个端口,否则就用8888端口。表示配置文件名称,查看我们前面创建配置文件,是这个名称:

ties

可以分成两部分: {application}- {profile}.properties

所以我们配置为cloud-config,e为dev,其中dev表示开发配置文件,配置文件仓库里还有一个测试环境的配置文件,切换该配置文件只需要将dev改为test即可,当然这个参数也可以由启动时命令行传入,如:

java -jar --e =test

此时应用就会加载测试环境下的配置信息。

4、 Spring cloud实现服务注册及发现

服务注册与发现对于微服务系统来说非常重要。有了服务发现与注册,你就不需要整天改服务调用的配置文件了,你只需要使用服务的标识符,就可以访问到服务。

cloud-eureka-server:eureka注册服务器

cloud-simple-service:一个使用mybatis的数据库应用,服务端

服务注册管理器原理如下图所示:

所有的服务端及访问服务的客户端都需要连接到注册管理器(eureka服务器)。服务在启动时会自动注册自己到eureka服务器,每一个服务都有一个名字,这个名字会被注册到eureka服务器。使用服务的一方只需要使用该名字加上方法名就可以调用到服务。

Spring cloud的服务注册及发现,不仅仅只有eureka,还支持Zookeeper和Consul。默认情况下是eureka,spring

封装了eureka,使其非常简单易用,只需要比传统应用增加一行代码就可以使用了,这一行代码就是一个注解。我们按以下步骤实现服务注册和发现功能。

1)首选需要建立eureka服务器

创建spring cloud eureka服务器和创建之前那个配置文件服务器类似,你只需要创建一个空的maven工程,并引入spring boot的相关starter即可,然后创建一个近乎空的执行类,工程如下图:

在EurekaServer类中我们加入如下代码:

@SpringBootApplication

@EnableEurekaServer

public class EurekaServer {

public static void main(String[] args) {

(, args);

}

}

可以看到只需要使用@EnableEurekaServer注解就可以让应用变为Eureka服务器,这是因为spring boot封装了Eureka Server,让你可以嵌入到应用中直接使用。至于真正的EurekaServer是Netflix公司的开源项目,也是可以单独下载使用的。

在ties配置文件中使用如下配置:

=8761

me=localhost

erWithEureka=false

egistry=false

tZone=${me}:${}/eureka/

其中配置eureka服务器端口号。Eureka的配置属性都在开源项目spring-cloud-netflix-master中定义(spring boot连文档都没有,只能看源码了),在这个项目中有两个类EurekaInstanceConfigBean 和EurekaClientConfigBean,分别含有ce和相关属性的解释和定义。从中可以看到,

registerWithEureka表示是否注册自身到eureka服务器,因为当前这个应用就是eureka服务器,没必要注册自身,所以这里是false。fetchRegistry表示是否从eureka服务器获取注册信息,同上,这里不需要。defaultZone就比较重要了,是设置eureka服务器所在的地址,查询服务和注册服务都需要依赖这个地址。

做完这些后当然,还要改一下pom文件,增加eureka-server的starter即可:

spring-cloud-starter-eureka-server

如此eureka服务器就完成了,在命令行启动就可以了。

2)让服务使用eureka服务器

让服务使用eureka服务器,只需添加@EnableDiscoveryClient注解就可以了。回到我们在上篇文章中实现的cloud-simple-service微服务应用。在main方法所在的Application类中,添加@EnableDiscoveryClient注解。然后在配置文件中添加:

tZone=localhost:8761/eureka/

=cloud-simple-service

其中defaultZone是指定eureka服务器的地址,无论是注册还是发现服务都需要这个地址。是指定进行服务注册时该服务的名称。这个名称就是后面调用服务时的服务标识符(这是服务发现的功能,我们在后面章节具体介绍)。当然,pom文件也需要增加:

spring-cloud-starter-eureka

如此以来该服务启动后会自动注册到eureka服务器。如果在该服务中还需要调用别的服务,那么直接使用那个服务的服务名称加方法名构成的url即可,具体我们将在下章结合ui端的应用具体介绍。

5、 综合使用spring cloud技术实现微服务应用

在之前的章节,我们已经实现了配置服务器、注册服务器、微服务服务端,实现了服务注册与发现。这一章我们将实现微服务的客户端,以及联调、实现整个spring cloud框架应用。

本文涉及到的项目包括:

cloud-config-server:配置服务器

cloud-eureka-server:eureka注册服务器

cloud-simple-service:一个使用mybatis的数据库应用,服务端

cloud-simple-ui:webui客户端

我们先来看看如何实现webui客户端。在spring boot中,已经不推荐使用jsp,所以你如果使用jsp来实现webui端,将会很麻烦。这可能跟现在的开发主流偏重移动端有关,跟微服务有关,跟整个时代当前的技术需求有关。单纯以html来作为客户端,有很多好处,比如更利于使用高速缓存;使后台服务无状态话,更利于处理高并发;更利于页面作为服务,小服务组合成大服务等。

我们首选来创建webui应用,参考git cloud-simple-ui工程:

这个应用包括前端html页面,还包括一个后台controller浅层。这是一个前端应用,为什么要包括controller浅层?这是因为这个controller浅层是用来做服务组合的,因为一个页面可能涉及到调用多个服务,而这些服务又有可能涉及事务和并发问题,所以还是需要靠java来完成。当然,也可以单独编写一个api gateway来实现这一层,可以使用go、语言等,也可以使用java/netty(主流还是java,因为开发部署效率高)。

Controller层的WebApplication就是这个应用的入口,代码如下:

@SpringBootApplication

@EnableDiscoveryClient

@EnableCircuitBreaker

public class WebApplication {

public static void main(String[] args) throws Exception {

(, args);

}

}

这些注解大都在前面提到过用法:

@SpringBootApplication相当于@Configuration、@EnableAutoConfiguration、@ComponentScan三个注解合用。

@EnableDiscoveryClient配置本应用将使用服务注册和服务发现,注意:注册和发现用这一个注解。

@EnableCircuitBreaker表示启用断路器,断路器依赖于服务注册和发现。

Controller层的service包封装了服务接口访问,UserService类代码如下:

@Service

public class UserService {

@Autowired

RestTemplate restTemplate;

final String SERVICE_NAME="cloud-simple-service";

@HystrixCommand(fallbackMethod = "fallbackSearchAll")

public List searchAll() {

return Object(""+SERVICE_NAME+"/user", );

}

private List fallbackSearchAll() {

n("HystrixCommand fallbackMethod handle!");

List ls = new ArrayList();

User user = new User();

rname("TestHystrix");

(user);

return ls;

}

}

这里使用了断路器,就是@HystrixCommand注解。断路器的基本作用就是@HystrixCommand注解的方法失败后,系统将自动切换到fallbackMethod方法执行。断路器Hystrix具备回退机制、请求缓存和请求打包以及监控和配置等功能,在这里我们只是使用了它的核心功能:回退机制,使用该功能允许你快速失败并迅速恢复或者回退并优雅降级。

这里使用restTemplate进行服务调用,因为使用了服务注册和发现,所以我们只需要传入服务名称SERVICE_NAME作为url的根路径,如此restTemplate就会去EurekaServer查找服务名称所代表的服务并调用。而这个服务名称就是在服务提供端cloud-simple-service中所配置的名字,这个名字在服务启动时连同它的IP和端口号都注册到了EurekaServer。

封装好服务调用后,你只需要在Controller类里面注入这个服务即可:

@RestController

public class UserController {

@Autowired

UserService userService;

@RequestMapping(value="/users")

public ResponseEntity> readUserInfo(){

List users=All();

return new ResponseEntity>(users,);

}

}

至此这个webui应用的java端就开发完了,我们再来看页面模块。

可以看到,页面文件都放在resourcesstatic目录下面,这是spring boot默认的页面文件主文件夹,你如果在里面放一个,那么直接访问根路径localhost:8080/会直接定位到这个页面。所以这个static就相当于传统web项目里面的webapp文件夹。

在这里包括两个页面和,用户访问首页时将会加载子页面。

首页页面核心代码如下:

页面代码如下:

  • {{me}}

页面代码如下:

('users', ['ngRoute']).config(function ($routeProvider) {

$('/', {

templateUrl: '',

controller: 'userCtr'

})

}).controller('userCtr', function ($scope, $http) {

$('users').success(function (data) {

//alert(data+"");

$st = data;

});

});

这里使用了angularJS库。Angular可以绑定模型数据到页面变量,在看到的{{me}}就是它的绑定语法,这个语法根jsp或freemarker这些模板技术都类似,只不过Angular是用在客户端的,而前者是用在服务端的。

至此这个webui应用就开发完了,改一下配置文件和pom文件就可以运行了。配置文件包括配置管理服务器地址,注册服务器地址等,在ties文件中:

=127.0.0.1:${:8888}

=cloud-config

e=${e:dev}

tZone=localhost:8761/eureka/

=simple-ui-phone

这些配置我们在上一章已经提到过了,这里不再解释。因为使用了断路器,所以相比上一章的cloud-simple-service项目,需要加入hystrix依赖,只有一个starter依赖:

spring-cloud-starter-hystrix

Spring把事情做的如此简单,不管是服务注册还是断路器,连同注解加配置文件再加上依赖总共不超过十行代码。如此简单就可以使用一个分布式应用,也难怪国内外业内人员都高度重视这个框架,在简单和速度就是硬道理的今天,这个框架有着重要的意义。

剩下最重要的事情就是进行部署了,我们以此使用命令启动这些服务及应用:

1) java -jar ,启动配置服务器,固定绑定端口8888;

2) java -jar ,启动注册服务器,固定绑定端口8671;

3) java -jar --=8081 >,启动后台服务,绑定端口8081

4) java -jar --=8082 >,启动后台服务,绑定端口8082

5) java -jar --=8080 >,启动前端ui应用,绑定端口8080

运行localhost:8080/即可看到运行的结果。其中“>”表示输出日志到文件。

这里运行了两个cloud-simple-service实例,主要是为了演示ribbon负载均衡。默认情况下使用ribbon不需要再作任何配置,不过它依赖于注册服务器。当然也可以对ribbon进行一些自定义设置,比如配置它的超时时间、重试次数等。启用了负载均衡后,当我们关掉前端页面上次指向的服务时(从日志中看),比如我们刷新页面看到它调用的是8081服务,那么我们关掉这个服务。关掉后再刷新会发现执行了断路器,过几秒再刷新,它已经切换到了8082这台服务器,这说明负载均衡起作用了。

6、 使用docker发布应用spring cloud应用

本文涉及到的项目:

cloud-simple-docker:一个简单的spring boot应用

Docker是一种虚拟机技术,准确的说是在linux虚拟机技术LXC基础上又封装了一层,可以看成是基于LXC的容器技术。可以把容器看做是一个简易版的Linux环境(包括root用户权限、进程空间、用户空间和网络空间等)和运行在其中的应用程序。容器是用来装东西的,Docker可以装载应用本身及其运行环境进容器,这是一个很小的文件,然后把这个文件扔到任何兼容的服务器上就可以运行,也是基于这一点,Docker可以同时让应用的部署、测试和分发都变得前所未有的高效和轻松!

下面例子参考“Spring Boot with Docker”官方例子。

1)建立一个简单的应用,只有一个类,包含main方法,代码如下:

@SpringBootApplication

@RestController

public class Application {

@RequestMapping("/")

public String home() {

return "Hello Docker World";

}

public static void main(String[] args) {

(, args);

}

}

2)建立Dockerfile

# 基于那个镜像

FROM /java:8

# 将本地文件夹挂载到当前容器(tomcat使用)

VOLUME /tmp

# 拷贝文件到容器

ADD /

# 打开服务端口

EXPOSE 8080

# 配置容器启动后执行的命令

ENTRYPOINT ["java","-=file:/dev/./urandom","-jar","/"]

这里特别要注意,这里的FROM采用国内的docker镜像,如果连国外的docker镜像下载,基本是不太可能下载下来的,原因大家都知道。

有了Dockerfile,就可以部署docker了。

3)部署docker示例

部署分为2步,分别是创建镜像、运行。

l 创建镜像

将编译后的jar文件考到服务器某个目录,这里是tmp目录。然后将Dockerfile也考到该目录,最后进入到该目录下运行命令:

docker build -t local/cloud-docker-hello .

别掉了后面的“.”符号,这个符号表示目录,这个命令执行成功,你会看到以下界面:

运行成功后,就创建了一个镜像,可以使用docker images来查看该镜像。

l 运行镜像

有了镜像就可以运行了,使用下面命令运行:

docker run -p 8080:8080 –t local/cloud-simple-docker

其中8080:8080表示本机端口映射到Docker实例端口。如果本机端口没有打开,还需要打开该端口,打开端口在centos 7中使用firewall-cmd命令:

firewall-cmd --zone=public --add-port=8080/tcp --permanent

firewall-cmd –reload

成功后可以使用docker ps –a查看镜像运行情况:

local/cloud-docker-hello | latest | 3ef51d55eb27 | 22 minutes ago | 667.2 MB

可以看到这个包括了java运行环境的web应用镜像是667MB。

该步骤运行结果如下:

最后使用curl命令或者直接在浏览器打开,可以直接测试该应用。使用curl命令如下:

curl localhost:8080

返回:Hello Docker World

Spring Boot with Docker例子还提供了一个maven插件docker-maven-plugin,这个插件可以直接将项目编译为docker镜像。另外这个插件还可以让你结合jenkins完成项目的持续集成和自动部署。具体来说就是jenkins自动通过git或svn拉到工程代码,然后使用maven进行编译,再调用项目中的Dockerfile生成镜像。如此以来不管是什么应用,只需要部署docker就可以了,那些配置,那些乱七八糟的环境搭建都不需要了,是很方便。


本文标签: 服务 使用 应用 配置 需要