微服务列表
- 购物车
- 登录验证
- 产品2
集群列表
- web集群:ribbon客户端负载均衡,请求来自于硬件负载F5或者nginx,(本机运行)
- Eureka Server集群,3实例192.168.0.117~192.168.0.119,端口号10000
- 微服务集群:集成Eureka Client
- 购物车微服务3实例192.168.0.117~192.168.0.119,服务命名micro-cart
- 登录验证微服务3实例192.168.0.117~192.168.0.119,服务命名micro-login
- 产品微服务3实例192.168.0.117~192.168.0.119,服务命名micro-product
- redis集群(暂时单机)
- mysql主备(暂时单机)
- 全局配置中心
Eureka Server集群
- 代码:https://gitee.com/steveGuRen/spring-cloud-example/tree/master/Spring-cloud-eurekaserver
三个实例配置文件如下,这里并没有用类似ognl表达式的配置,配置文件依次是application-eureka119.yml~application-eureka117.yml
server:
port: 10000
eureka:
instance:
hostname: 192.168.0.119
client:
serviceUrl:
defaultZone: http://192.168.0.117:10000/eureka/,http://192.168.0.118:10000/eureka/,http://192.168.0.119:10000/eureka/
server:
port: 10000
eureka:
instance:
hostname: 192.168.0.118
client:
serviceUrl:
defaultZone: http://192.168.0.117:10000/eureka/,http://192.168.0.118:10000/eureka/,http://192.168.0.119:10000/eureka/
server:
port: 10000
eureka:
instance:
hostname: 192.168.0.117
client:
serviceUrl:
defaultZone: http://192.168.0.117:10000/eureka/,http://192.168.0.118:10000/eureka/,http://192.168.0.119:10000/eureka/
编译后用如下分别用以下命令执行jar文件,执行时指定spring.profiles.active参数,spring.profiles.active的用法可以自行百度
java -jar ~/spring-cloud-example/Spring-cloud-eurekaserver/target/Spring-cloud-eurekaserver-0.0.1-SNAPSHOT.jar --spring.profiles.active=euraka117
java -jar ~/spring-cloud-example/Spring-cloud-eurekaserver/target/Spring-cloud-eurekaserver-0.0.1-SNAPSHOT.jar --spring.profiles.active=euraka118
java -jar ~/spring-cloud-example/Spring-cloud-eurekaserver/target/Spring-cloud-eurekaserver-0.0.1-SNAPSHOT.jar --spring.profiles.active=euraka119
登录验证微服务实现
代码:https://gitee.com/steveGuRen/spring-cloud-example/tree/master/Spring-cloud-micro-CardRecord
三个配置文件如下:application-117.yml~application-119.xml,分别对应IP地址192.168.0.117到119的配置
集成了Eureka client和server的依赖,由于是登录验证服务,所以用redis来保存session,将状态保存在存储集群,目前还是单机,微服务继续保持无状态(stateless),从而能够轻易的进行水平扩展
spring session的注解配置以及redis的注解配置还有datasource的注解配置可以查看com.example.demo.config里面的3个配置类下面的代码关键的是用了@EnableDiscoveryClient注解,用于将该项目spring mvc的@RequestMapping对应的服务地址注册到Eureka server集群
package com.example.demo;
import org.mybatis.spring.annotation.MapperScan;
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.cloud.client.discovery.EnableDiscoveryClient;
@SpringBootApplication
@MapperScan("com.example.demo")
@EnableDiscoveryClient
public class SpringCloudMicroCardRecordApplication {
public static void main(String[] args) {
SpringApplication.run(SpringCloudMicroCardRecordApplication.class, args);
}
}
- 下面的代码使用spring session保存session,实际上spring session只要引用相关的依赖配置好redis的相关配置即可,难度不高。
@Controller
@RequestMapping("/account")
@ResponseBody
public class AccountController {
@Autowired
private RedisService redisService;
@Autowired
private AccountService accountService;
private String PRIFIX_USER_SESSION = "PRIFIX_USER_SESSION";
@RequestMapping(value = "login", method = RequestMethod.POST)
public ResourceSupport login(HttpServletRequest request, String username, String password) {
Account accont = accountService.login(username, password);
ResultResource result = new ResultResource();
if (accont != null) {
//TODO save login info to redis and return
String key = PRIFIX_USER_SESSION + ":" + accont.getName() + ":name";
request.getSession().setAttribute(key, accont.getName());
result.setSuccess(true);
return result;
} else {
//TODO return failed result
result.setSuccess(false);
return result;
}
}
}
- Eureka集群和微服务集群都启动后,可以看到instances currently registered with Eureka里面有两个实例,实例名实际上显示的是yml里面配置的spring.application.name的名字,然后还能看到对应的数量以及对应的服务实例地址,按f12浏览器调试可以看到里面暴露的具体访问地址
Web集群
-
代码:https://gitee.com/steveGuRen/spring-cloud-example/tree/master/Spring-cloud-web
剩下的就是web集群了,web集群、微服务集群、Eureka server集群的关系如下图,由于只是模拟,所以Web集群和微服务集群的ip地址是一样的,Web集群使用Ribbon客户端负载均衡
首先使用RestTemplate作为请求微服务的框架,Ribbon通过一个加上了@LoadBalanced注解的RestTemplate对象来实现负载均衡
@SpringBootApplication
@EnableDiscoveryClient
public class SpringCloudWebApplication {
@Bean
@LoadBalanced
RestTemplate restTemplate() {
return new RestTemplate();
}
public static void main(String[] args) {
SpringApplication.run(SpringCloudWebApplication.class, args);
}
}
- 通过http://[服务名称大写]/[服务地址]的格式,可以使用restTemplate诸如postForEntity的方法实现微服务的远程请求,Ribbon默认会以轮询的方式去进行将请求分配到不同的微服务实例上面去
@RestController
public class SimpleController {
@Autowired
RestTemplate restTemplate;
@RequestMapping(value = "/account/login", method = RequestMethod.POST)
@ResponseBody
public String login(Account loginInfo) {
ResponseEntity<String> response = restTemplate.postForEntity("http://MONO-ESHOP-MICRO-LOGIN/account/login", loginInfo, String.class);
return response.getBody();
}
}
- aplication.yml配置
server:
port: 8081
servlet:
context-path: /
tomcat:
uri-encoding: UTF-8
eureka:
client:
serviceUrl:
defaultZone: http://192.168.0.117:10000/eureka/,http://192.168.0.118:10000/eureka/,http://192.168.0.119:10000/eureka/
spring:
application:
name: web
redis:
host: 192.168.0.117
port: 6379
password: