配置注册中心:
在eurekaserver中加入依赖
- <parent>
- <groupId>org.springframework.boot</groupId>
- <artifactId>spring-boot-starter-parent</artifactId>
- <version>1.5.9.RELEASE</version>
- </parent>
- <dependencyManagement>
- <dependencies>
- <dependency>
- <groupId>org.springframework.cloud</groupId>
- <artifactId>spring-cloud-dependencies</artifactId>
- <version>Dalston.SR4</version>
- <type>pom</type>
- <scope>import</scope>
- </dependency>
- </dependencies>
- </dependencyManagement>
- <dependencies>
- <dependency>
- <groupId>org.springframework.cloud</groupId>
- <artifactId>spring-cloud-starter-eureka-server</artifactId>
- </dependency>
- </dependencies>
注册中心的资源文件application.yml
server:
port: 8761#eureka默认端口
eureka:
instance:
hostname: localhost#主机名
client:
registerWithEureka: false
fetchRegistry: false
serviceUrl:
defaultZone: http://${eureka.instance.hostname}:${server.port}/eureka/
网址:
http://cloud.spring.io/spring-cloud-static/Dalston.SR5/single/spring-cloud.html#spring-cloud-eureka-server
注册中心的启动类(EnableEurekaServer)
- package cn.et;
- import org.springframework.boot.SpringApplication;
- import org.springframework.boot.autoconfigure.SpringBootApplication;
- import org.springframework.cloud.netflix.eureka.server.EnableEurekaServer;
- @SpringBootApplication
- @EnableEurekaServer
- public class Main {
- public static void main(String[] args) {
- SpringApplication.run(Main.class, args);
- }
- }
eurekaServer的访问地址:localhost:8761 出现界面
eureka client 的配置(客户端)
- spring.mail.host=smtp.163.com
- Spring.mail.password=123456
- spring.mail.port=25
- spring.mail.protocol=smtp
- spring.mail.username=raya_l@163.com
- eureka.client.serviceUrl.defaultZone=http://localhost:8761/eureka/
- spring.application.name=email
- server.port=8081
- 在注册中的main方法上加@EnableEurekaClient启动自动注册
Eureka客户端启动类
- package cn.et;
- import org.springframework.boot.SpringApplication;
- import org.springframework.boot.autoconfigure.SpringBootApplication;
- import org.springframework.cloud.netflix.eureka.EnableEurekaClient;
- @EnableEurekaClient
- @SpringBootApplication
- public class Main {
- public static void main(String[] args) {
- SpringApplication.run(Main.class, args);
- }
- }
Ribbon
- <dependency>
- <groupId>org.springframework.cloud</groupId>
- <artifactId>spring-cloud-starter-ribbon</artifactId>
- </dependency>
@EnableEurekaClient和@EnableDiscoveryClient是一样的
Ribbon的main方法
- @SpringBootApplication
- @EnableEurekaClient
- @RibbonClient(value="EMAIL")
- /**
- * 表示当前这个服务需要调用其他的服务的名称
- * @author Administrator
- *
- */
- @Configuration
- public class Main {
- @LoadBalanced
- @Bean
- RestTemplate restTemplate() {
- return new RestTemplate();
- }
- public static void main(String[] args) {
- SpringApplication.run(Main.class, args);
- }
Ribbon用get发送和post发送
- package cn.et;
- import java.util.HashMap;
- import java.util.Map;
- import org.springframework.beans.factory.annotation.Autowired;
- import org.springframework.cloud.client.ServiceInstance;
- import org.springframework.cloud.client.loadbalancer.LoadBalancerClient;
- import org.springframework.http.HttpEntity;
- import org.springframework.http.HttpHeaders;
- import org.springframework.stereotype.Controller;
- import org.springframework.web.bind.annotation.GetMapping;
- import org.springframework.web.bind.annotation.PostMapping;
- import org.springframework.web.bind.annotation.RequestMapping;
- import org.springframework.web.bind.annotation.ResponseBody;
- import org.springframework.web.client.RestClientException;
- import org.springframework.web.client.RestTemplate;
- @Controller
- public class SendController {
- @Autowired
- private RestTemplate restTemplate;//通过restTemplate来调用ribbon
- @Autowired
- private LoadBalancerClient loadBalancer;
- /**
- * 启动多个发布者 端口不一致 程序名相同
- * 使用
- * @LoadBalanced必须添加
- * @return
- */
- @ResponseBody
- @RequestMapping("/choosePub")
- public String choosePub() {
- StringBuffer sb=new StringBuffer();
- for(int i=0;i<=10;i++) {
- ServiceInstance ss=loadBalancer.choose("EMAILSERVER");//从两个idserver中选择一个 这里涉及到选择算法
- sb.append(ss.getUri().toString()+"<br/>");
- }
- return sb.toString();
- }
- @GetMapping("/sendClient")
- public String send(String email_to,String email_subject ,String email_content){
- //调用email服务
- String controller="/send";
- //通过注册中心客户端负载均衡 获取一台主机来调用
- try {
- controller += "?email_to="+email_to+"&email_subject="+email_subject+"&email_content="+email_content;
- String result=restTemplate.getForObject("http://EMAILSERVER"+controller, String.class);
- } catch (RestClientException e) {
- // TODO Auto-generated catch block
- e.printStackTrace();
- return "redirect:/error.html";
- }
- //通过redirect返回string类型跳转,不允许spring控制器用@ResponseBody
- return "redirect:/suc.html";
- }
- /**
- * 演示post
- * @param email_to
- * @param email_subject
- * @param email_content
- * @return
- */
- @PostMapping("/sendClientpost")
- public String postsend(String email_to,String email_subject ,String email_content){
- try {
- //
- HttpHeaders headers=new HttpHeaders();
- Map<String,Object> map=new HashMap<String,Object>();
- map.put("email_to",email_to );
- map.put("email_subject", email_subject);
- map.put("email_content", email_content);
- HttpEntity<Map> request=new HttpEntity<Map>(map, headers);
- String result=restTemplate.postForObject("http://EMAILSERVER/send",request, String.class);
- } catch (RestClientException e) {
- // TODO Auto-generated catch block
- e.printStackTrace();
- return "redirect:/error.html";
- }
- return "redirect:/suc.html";
- }
- /**
- * 演示调用sendmail的/user/这个请求
- * @return
- */
- @ResponseBody
- @GetMapping("/invokeUser")
- public String invokeUser(String id){
- String resul=restTemplate.getForObject("http://EMAILSERVER/user/{id}",String.class,id);
- return resul;
- }
- }
发送邮件的控制类
- package cn.et;
- import java.util.HashMap;
- import java.util.Map;
- import org.springframework.beans.factory.annotation.Autowired;
- import org.springframework.mail.SimpleMailMessage;
- import org.springframework.mail.javamail.JavaMailSender;
- import org.springframework.web.bind.annotation.GetMapping;
- import org.springframework.web.bind.annotation.PathVariable;
- import org.springframework.web.bind.annotation.PostMapping;
- import org.springframework.web.bind.annotation.RequestBody;
- import org.springframework.web.bind.annotation.RestController;
- @RestController
- public class MailController {
- @Autowired
- private JavaMailSender jms;
- @PostMapping("/send")
- public String send(@RequestBody Map<String,Object> map){
- SimpleMailMessage mailMessage=new SimpleMailMessage();
- mailMessage.setFrom("raya_l@163.com");
- mailMessage.setTo(map.get("email_to").toString());
- mailMessage.setSubject(map.get("email_subject").toString());
- mailMessage.setText(map.get("email_content").toString());
- jms.send(mailMessage);
- return "1";
- }
- @GetMapping("/a")
- public String a(){
- return "2";
- }
- @GetMapping("/user/{userId}")
- public Map getUser(@PathVariable String userId){
- Map map=new HashMap();
- map.put("id", userId);
- map.put("name", "zs_"+userId);
- return map;
- }
- }
启动MailController
- package cn.et;
- import org.springframework.boot.SpringApplication;
- import org.springframework.boot.autoconfigure.SpringBootApplication;
- import org.springframework.cloud.client.loadbalancer.LoadBalanced;
- import org.springframework.cloud.netflix.eureka.EnableEurekaClient;
- import org.springframework.cloud.netflix.ribbon.RibbonClient;
- import org.springframework.context.annotation.Bean;
- import org.springframework.context.annotation.Configuration;
- import org.springframework.web.client.RestTemplate;
- @SpringBootApplication
- @EnableEurekaClient
- @RibbonClient(value = "EMAILSERVER")
- /**
- * 表示当前这个服务需要调用其他的服务的名称
- *
- * @author Administrator
- *
- */
- @Configuration
- public class Main {
- @LoadBalanced//启动负载均衡
- @Bean
- RestTemplate restTemplate() {
- return new RestTemplate();
- }
- public static void main(String[] args) {
- SpringApplication.run(Main.class, args);
- }
- }
定义LoadBalancerClient 可以用于测试选择的服务器的算法 负载的算法的类需要实现 IRule 接口 以下列表摘自网络
策略名 | 策略描述 |
BestAvailableRule | 选择一个最小的并发请求的server |
AvailabilityFilteringRule | 过滤掉那些因为一直连接失败的被标记为circuit tripped的后端server,并过滤掉那些高并发的的后端server(active connections 超过配置的阈值) |
WeightedResponseTimeRule | 根据相应时间分配一个weight,相应时间越长,weight越小,被选中的可能性越低。 |
RetryRule | 对选定的负载均衡策略机上重试机制。 |
RoundRobinRule | roundRobin方式轮询选择server |
RandomRule | 随机选择一个server |
ZoneAvoidanceRule | 复合判断server所在区域的性能和server的可用性选择server |
ribbon默认的配置类为 RibbonClientConfiguration 其中配置IRule的bean为
负载均衡的规则配置:
EMAILSERVER:用户名
EMAILSERVER.ribbon.NFLoadBalancerRuleClassName=com.netflix.loadbalancer.RandomRule
Feign(面向接口式)
加入依赖:
- <dependency>
- <groupId>org.springframework.cloud</groupId>
- <artifactId>spring-cloud-starter-feign</artifactId>
- </dependency>
配置文件:
- spring.application.name=EMAIL
- server.port=8888
- eureka.client.serviceUrl.defaultZone=http://localhost:8761/eureka/
- #服务器的算法(随机)
- EMAILSERVER.ribbon.NFLoadBalancerRuleClassName=com.netflix.loadbalancer.RandomRule
接口
- package cn.et;
- import java.util.Map;
- import org.springframework.cloud.netflix.feign.FeignClient;
- import org.springframework.web.bind.annotation.GetMapping;
- import org.springframework.web.bind.annotation.PathVariable;
- import org.springframework.web.bind.annotation.PostMapping;
- import org.springframework.web.bind.annotation.RequestBody;
- @FeignClient("EMAILSERVER")
- public interface IsendMail {
- @GetMapping("/user/{userId}")
- public Map getUser(@PathVariable("userId") String userId);
- @PostMapping("/send")
- public String send(@RequestBody Map<String,Object> map);
- }
控制类
- package cn.et;
- import java.util.HashMap;
- import java.util.Map;
- import org.springframework.beans.factory.annotation.Autowired;
- import org.springframework.http.HttpEntity;
- import org.springframework.http.HttpHeaders;
- import org.springframework.stereotype.Controller;
- import org.springframework.web.bind.annotation.GetMapping;
- import org.springframework.web.bind.annotation.PostMapping;
- import org.springframework.web.bind.annotation.ResponseBody;
- import org.springframework.web.client.RestClientException;
- @Controller
- public class SendController {
- @Autowired
- private IsendMail sendMail;
- @GetMapping("/sendClient")
- public String send(String email_to,String email_subject ,String email_content){
- //调用email服务
- String controller="/send";
- //通过注册中心客户端负载均衡 获取一台主机来调用
- try {
- controller += "?email_to="+email_to+"&email_subject="+email_subject+"&email_content="+email_content;
- //String result=restTemplate.getForObject("http://EMAILSERVER"+controller, String.class);
- } catch (RestClientException e) {
- // TODO Auto-generated catch block
- e.printStackTrace();
- return "redirect:/error.html";
- }
- return "redirect:/suc.html";
- }
- /**
- * 演示post
- * @param email_to
- * @param email_subject
- * @param email_content
- * @return
- */
- @PostMapping("/sendClientpost")
- public String postsend(String email_to,String email_subject ,String email_content){
- try {
- Map<String,Object> map=new HashMap<String,Object>();
- map.put("email_to",email_to );
- map.put("email_subject", email_subject);
- map.put("email_content", email_content);
- sendMail.send(map);
- } catch (RestClientException e) {
- // TODO Auto-generated catch block
- e.printStackTrace();
- return "redirect:/error.html";
- }
- return "redirect:/suc.html";
- }
- /**
- * 演示调用sendmail的/user/这个请求
- * @return
- */
- @ResponseBody
- @GetMapping("/invokeUser")
- public String invokeUser(String id){
- Map map=sendMail.getUser(id);
- return map.get("name").toString();
- }
- }
- 启动类
- package cn.et;
- import java.util.Map;
- import org.springframework.cloud.netflix.feign.FeignClient;
- import org.springframework.web.bind.annotation.GetMapping;
- import org.springframework.web.bind.annotation.PathVariable;
- import org.springframework.web.bind.annotation.PostMapping;
- import org.springframework.web.bind.annotation.RequestBody;
- @FeignClient("EMAILSERVER")
- public interface IsendMail {
- @GetMapping("/user/{userId}")
- public Map getUser(@PathVariable("userId") String userId);
- @PostMapping("/send")
- public String send(@RequestBody Map<String,Object> map);
- }