思路分析

发送方:商品微服务

  • 什么时候发?

    当商品服务对商品进行写操作:增、删、改的时候,需要发送一条消息,通知其它服务。

  • 发送什么内容?

    对商品的增删改时其它服务可能需要新的商品数据,但是如果消息内容中包含全部商品信息,数据量太大,而且并不是每个服务都需要全部的信息。因此我们只发送商品id,其它服务可以根据id查询自己需要的信息。

接收方:搜索微服务、静态页微服务

接收消息后如何处理?

  • 搜索微服务:

    • 增/改:添加新的数据到索引库

    • 删:删除索引库数据

  • 静态页微服务:

    • 增/改:创建新的静态页

    • 删:删除原来的静态页

商品服务发送消息

我们先在商品微服务learn-item-service中实现发送消息。

引入依赖

<dependency><groupId>org.springframework.boot</groupId><artifactId>spring-boot-starter-amqp</artifactId>
</dependency>

配置文件

我们在application.yml中添加一些有关RabbitMQ的配置:

spring:rabbitmq:host: 192.168.56.101username: learnpassword: learnvirtual-host: /learntemplate:exchange: learn.item.exchangepublisher-confirms: true
  • template:有关AmqpTemplate的配置

    • exchange:缺省的交换机名称,此处配置后,发送消息如果不指定交换机就会使用这个

  • publisher-confirms:生产者确认机制,确保消息会正确发送,如果发送失败会有错误回执,从而触发重试

改造GoodsService

在GoodsService中封装一个发送消息到mq的方法:(需要注入AmqpTemplate模板)

private void sendMessage(Long id, String type){// 发送消息try {this.amqpTemplate.convertAndSend("item." + type, id);} catch (Exception e) {logger.error("{}商品消息发送异常,商品id:{}", type, id, e);}
}

这里没有指定交换机,因此默认发送到了配置中的:leyou.item.exchange

注意:这里要把所有异常都try起来,不能让消息的发送影响到正常的业务逻辑

然后在新增的时候调用:

修改的时候调用:

搜索服务接收消息

搜索服务接收到消息后要做的事情:

  • 增:添加新的数据到索引库

  • 删:删除索引库数据

  • 改:修改索引库数据

因为索引库的新增和修改方法是合二为一的,因此我们可以将这两类消息一同处理,删除另外处理。

引入依赖

<dependency><groupId>org.springframework.boot</groupId><artifactId>spring-boot-starter-amqp</artifactId>
</dependency>

添加配置

spring:rabbitmq:host: 192.168.56.101username: learnpassword: learnvirtual-host: /learn

这里只是接收消息而不发送,所以不用配置template相关内容。

编写监听器

代码:

@Component
public class GoodsListener {@Autowiredprivate SearchService searchService;/*** 处理insert和update的消息** @param id* @throws Exception*/@RabbitListener(bindings = @QueueBinding(value = @Queue(value = "learn.create.index.queue", durable = "true"),exchange = @Exchange(value = "learn.item.exchange",ignoreDeclarationExceptions = "true",type = ExchangeTypes.TOPIC),key = {"item.insert", "item.update"}))public void listenCreate(Long id) throws Exception {if (id == null) {return;}// 创建或更新索引this.searchService.createIndex(id);}/*** 处理delete的消息** @param id*/@RabbitListener(bindings = @QueueBinding(value = @Queue(value = "learn.delete.index.queue", durable = "true"),exchange = @Exchange(value = "learn.item.exchange",ignoreDeclarationExceptions = "true",type = ExchangeTypes.TOPIC),key = "item.delete"))public void listenDelete(Long id) {if (id == null) {return;}// 删除索引this.searchService.deleteIndex(id);}
}

编写创建和删除索引方法

这里因为要创建和删除索引,我们需要在SearchService中拓展两个方法,创建和删除索引:

public void createIndex(Long id) throws IOException {Spu spu = this.goodsClient.querySpuById(id);// 构建商品Goods goods = this.buildGoods(spu);// 保存数据到索引库this.goodsRepository.save(goods);
}public void deleteIndex(Long id) {this.goodsRepository.deleteById(id);
}

创建索引的方法可以从之前导入数据的测试类中拷贝和改造。

静态页服务接收消息

商品静态页服务接收到消息后的处理:

  • 增:创建新的静态页

  • 删:删除原来的静态页

  • 改:创建新的静态页并覆盖原来的

不过,我们编写的创建静态页的方法也具备覆盖以前页面的功能,因此:增和改的消息可以放在一个方法中处理,删除消息放在另一个方法处理。

引入依赖

<dependency><groupId>org.springframework.boot</groupId><artifactId>spring-boot-starter-amqp</artifactId>
</dependency>

添加配置

spring:rabbitmq:host: 192.168.56.101username: learnpassword: learnvirtual-host: /learn

这里只是接收消息而不发送,所以不用配置template相关内容。

编写监听器

代码:

@Component
public class GoodsListener {@Autowiredprivate GoodsHtmlService goodsHtmlService;@RabbitListener(bindings = @QueueBinding(value = @Queue(value = "learn.create.web.queue", durable = "true"),exchange = @Exchange(value = "learn.item.exchange",ignoreDeclarationExceptions = "true",type = ExchangeTypes.TOPIC),key = {"item.insert", "item.update"}))public void listenCreate(Long id) throws Exception {if (id == null) {return;}// 创建页面goodsHtmlService.createHtml(id);}@RabbitListener(bindings = @QueueBinding(value = @Queue(value = "learn.delete.web.queue", durable = "true"),exchange = @Exchange(value = "learn.item.exchange",ignoreDeclarationExceptions = "true",type = ExchangeTypes.TOPIC),key = "item.delete"))public void listenDelete(Long id) {if (id == null) {return;}// 删除页面goodsHtmlService.deleteHtml(id);}
}

添加删除页面方法

public void deleteHtml(Long id) {File file = new File("C:\\project\\nginx-1.14.0\\html\\item\\", id + ".html");file.deleteOnExit();
}

测试

3.5.1.查看RabbitMQ控制台

重新启动项目,并且登录RabbitMQ管理界面:http://192.168.56.101:15672

可以看到,交换机已经创建出来了:

队列也已经创建完毕:

并且队列都已经绑定到交换机:

使用rabbitMQ实现数据同步相关推荐

  1. rabbitmq的使用已经数据同步

    0.学习目标 了解常见的MQ产品 了解RabbitMQ的5种消息模型 会使用Spring AMQP 利用MQ实现搜索和静态页的数据同步 1.RabbitMQ 1.1.搜索与商品服务的问题 目前我们已经 ...

  2. RabbitMQ实现ElasticSearch和MySQL数据同步

    RabbitMQ实现ElasticSearch和MySQL数据同步 提示:写完文章后,目录可以自动生成,如何生成可参考右边的帮助文档 文章目录 RabbitMQ实现ElasticSearch和MySQ ...

  3. 【javaWeb微服务架构项目——乐优商城day11】——利用RabbitMQ实现搜索和静态页的数据同步

    文章目录 0.学习目标 1.RabbitMQ 1.1.搜索与商品服务的问题 1.2.消息队列(MQ) 1.2.1.什么是消息队列 1.2.2.AMQP和JMS 1.2.3.常见MQ产品 1.2.4.R ...

  4. RabbitMQ镜像集群与ShovelFederation跨集群数据同步

    部署环境与版本 安装包下载地址: Erlang语言依赖下载链接:http://erlang.org/download/otp_src_21.1.tar.gz RabbitMQ 3.7.8版本下载链接: ...

  5. mysql同步binlog_利用MySQL的Binlog实现数据同步与订阅(下)

    利用MySQL的Binlog实现数据同步与订阅(下)​blog.yuanpei.me 终于到这个系列的最后一篇,在前两篇博客中,我们分别了介绍了Binlog的概念和事件总线(EventBus)的实现, ...

  6. MySQL -> ES 数据同步 配置步骤

    部署 MySQL -> ES 数据同步 (mysql 同步到 ES 是支持 多表查询 后把结果同步到ES 中的同一个索引中的) 1.服务器: 内网ip:192.168.0.60 登录name+k ...

  7. mysql同步数据到另一张表_mysql:Otter跨机房数据同步(单向)

    重要说明:需要同步的表必须要有主键 主键 主键 otter是一款基于Java且免费.开源基于数据库增量日志解析,准实时同步到本机房或异地机房的mysql/oracle数据库的解决方案. Otter目前 ...

  8. 服务器多个网站开启quarz,GitHub - WuLex/QuartzSynchroData: 多个不同站点服务器数据同步到总服务器(数据中心)...

    QuartzSynchroData 多个不同站点服务器sqlserver数据库 同步到总服务器上的数据库 (数据中心) 目前支持40多个数据库(在数据库配置表DBconfig配置了)的同步,每天每个服 ...

  9. canal+Kafka实现mysql与redis数据同步

    前言 上篇文章简单介绍canal概念,本文结合常见的缓存业务去讲解canal使用.在实际开发过程中,通常都会把数据往redis缓存中保存一份,做下简单的查询优化.如果这时候数据库数据发生变更操作,就不 ...

最新文章

  1. Linux执行mount挂载覆盖文件的还原
  2. iOS开发之Masonry框架源码解析
  3. leetcode Number of 1 Bits
  4. 每一种创伤,都是一种成熟
  5. elk 第二篇 , 为elk加入redis, 替换下beats(个人感觉不错2)
  6. js src 变量_Js基础学习笔记(一)
  7. spark.mllib:bagging方法
  8. 排序算法——随机快速排序
  9. java list 改变变量的值_3、list改变指针还是改变值
  10. 与时间有关的10个短语
  11. extjs 表格数据重新加载_将【金数据】实时获取到Excel的小技能
  12. 【51单片机】往返流水灯代码
  13. c语言怎么编程打开文件,怎么用c语言打开文件
  14. oracle三大连接方式,oracle的三种连接方式
  15. Deepin 深度操作系统安装教程
  16. 北斗导航:太空中最亮的“中国星”
  17. 美赛BOOM数学建模1-2蒙特卡洛法
  18. win10如何添加或禁用开机自启动项
  19. Fidder基础知识
  20. 工作中遇到的问题和一些经验总结

热门文章

  1. 上传第三方jar包到nexus
  2. delphi程序项目创建和保存
  3. HNOI2017 游记
  4. 2017广东工业大学程序设计竞赛决赛--Problem B: 占点游戏
  5. Java基础以及与C++的一些对比
  6. 常用Redis命令总结
  7. Flex容器拖动(Bordercontainer为例)
  8. 通向架构师的道路(第十天)之Axis2 Web Service(一)
  9. 最短编辑距离问题理解
  10. shell后台执行命令-crontab