实战SpringCloud相应式微效劳系列教程(第十章)相应式RESTful效劳完全代码示例
2019-11-18杂谈搜奇网64°c
A+ A-本文为实战SpringCloud相应式微效劳系列教程第十章,本章给出相应式RESTful效劳完全代码示例。发起没有之前基本的童鞋,先看之前的章节,章节目次放在文末。
1.搭建相应式RESTful效劳。
在前面章节中我们讲了怎样运用 Spring Initializer初始化相应式web运用,本节中就不再做过量引见(请回忆第九章内容)。
在进修本章内容之前须要相识mongodb以及redis,mongodb以及redis可查阅相干材料举行周全相识,并在当地环境搭建mongodb和redis。
2.application.yml文件设置
server:
port: 9801
spring:
application:
name: advert
data:
mongodb:
uri: mongodb://localhost:27017/db_advert
http:
encoding:
force: true
charset: UTF-8
enabled: true
redis:
host: 127.0.0.1
password: 123456
logback:
level: info
以上设置代码是我们现在进修的相应式RESTful效劳的悉数设置,设置比较简单,spring.data.mongodb.uri: mongodb://localhost:27017/db_advert
和spring.data.redis
是我们效劳的中心设置,我们晓得传统的数据库是不支持相应式数据读取的,所以这里运用mongodb和redis替代。
3.集成相应式的MongoDB
springboot 自身供应了cassandra/couchbase/mongodb/redis这几个NoSQL数据库的相应式驱动:
壅塞式的spring-boot-starter-data-mongodb 改成相应式的mongodb依靠spring-boot-starter-data-mongodb-reactive:
<dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-data-mongodb-reactive</artifactId> </dependency>
(1)编写实体类:
/** * 广告投放 */ @Document(collection="advert")//鸠合名 @Data @Builder @NoArgsConstructor @AllArgsConstructor public class Advert implements Serializable { private static final long serialVersionUID = -8985545025018238754L; /** * 主键 */ @Id private String id; /** * 内容 */ private String content; /** * 发布人 */ private Long userId; /** * 建立时候 */ private Date creatData; /** * 图片地点 */ private String imgUrl; /** * 视频地点 */ private String videoUrl; /** * 广告范例(视频图片) */ private String advertType; /** * 本日投放区域 */ private String launchArea; /** * 投放时长(小时为单元) */ private int durationTime; /** * 广告范例 */ private int classify; /** * 计费体式格局 */ private int billingMode; /** * 展现位置(首页轮播,其他轮播,首页其他位置,其他) */ private int displayPosition; /** * 广告主题 */ private String advertTitle; /** * 是不是须要自定义展现页面 */ private int isCustom; /** * 索引关键词 */ private String keyWords; }
个中@document把一个java类声明为mongodb的文档,能够经由过程collection参数指定这个类对应的文档,标注在实体类上,类似于hibernate的entity注解。其他注解均为lombok的注解。
(2)编写repository接口
import com.shmc.advert.model.po.Advert; import org.springframework.data.mongodb.repository.ReactiveMongoRepository; import org.springframework.data.mongodb.repository.Tailable; import org.springframework.stereotype.Repository; import reactor.core.publisher.Flux; @Repository public interface AdvertRepository extends ReactiveMongoRepository<Advert,Long> { @Tailable Flux<Advert> findBy(); }
个中@Repository是org.springframework.stereotype.Repository的注解,这个人人应当都很熟习了不做诠释。
从以上代码中我们能够清晰看到AdvertRepository 继续了ReactiveMongoRepository,ReactiveMongoRepository恰是我们依靠的maven相应式mongodb-reactive中的类,个中@Tailable注解,该注解类似于Linux中的tail ,能够将DB的变化以相应式流的体式格局猎取到并推送给前端。
除了能够继续ReactiveMongoRepository以外我们还能够经由过程注入MongoTemplate来操纵mongodb,然则MongoTemplate做不到及时监控和主动推送。如:
@Autowired
MongoTemplate mongoTemplate;
(3)编写Service接口以及完成类
Service接口:
import com.shmc.advert.model.po.Advert; import reactor.core.publisher.Flux; import reactor.core.publisher.Mono; public interface AdvertService { Mono<Advert> saveAdvert(Advert advert); Mono<Advert> findById(String id); Flux<Advert> findAll(); Flux<Advert> findByAll(); }
Service完成类:
@Service public class AdvertServiceImpl implements AdvertService { @Autowired MongoTemplate mongoTemplate; @Autowired private AdvertRepository advertRepository; @Override public Mono<Advert> saveAdvert(Advert advert){ advert.setId(new IdWorker().nextId()); advert.setCreatData(new Date()); mongoTemplate.insert(advert); return Mono.just(advert); } @Override public Mono<Advert> findById(String id){ Query query = new Query(Criteria.where("id").is(id)); return Mono.just(mongoTemplate.findOne(query,Advert.class)); } @Override public Flux<Advert> findAll(){ return advertRepository.findAll(); } @Override public Flux<Advert> findByAll(){ return advertRepository.findBy(); } }
(4)编写Controller
import com.shmc.advert.model.po.Advert; import com.shmc.advert.service.AdvertService; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.http.MediaType; import org.springframework.web.bind.annotation.*; import reactor.core.publisher.Flux; import reactor.core.publisher.Mono; import java.time.Duration; @RestController @RequestMapping("/advert") public class AdvertController { @Autowired private AdvertService advertService; @PostMapping("/saveAdvert") public Mono<Advert> saveAdvert(@RequestBody Advert advert){ return advertService.saveAdvert(advert); } @GetMapping("/findById/{id}") public Mono<Advert> findById(@PathVariable String id){ return advertService.findById(id); } /** * 以stream+json流的体式格局推送到客户端 * @return */ @GetMapping(value = "/findAllPreSec", produces = MediaType.APPLICATION_STREAM_JSON_VALUE) public Flux<Advert> findAllPreSec() { return advertService.findAll().delayElements(Duration.ofSeconds(1)); } /** * 数据变动 * @return */ @GetMapping(value = "/findByAll", produces = MediaType.APPLICATION_STREAM_JSON_VALUE) public Flux<Advert> findByAll(){ return advertService.findByAll(); } }
至此基于RESTful的相应式效劳我们悉数完成了,启动顺序接见“/advert/findAllPreSec"接口和”/advert/findByAll“接口就能够看到相应式的数据推送了。
findAllPreSec这个要领。运用了delayElements使得每隔一秒钟猎取一条数据发送给客户端,以“异步相应式流”的体式格局逐条推送。
这里指定了MediaType是APPLICATION_STREAM_JSON,即application/stream+json花样。
在浏览器中就能够看到每隔一秒涌现一条纪录。运转顺序,接见findByAll接口,然后测试挪用save接口增加advert数据,或许直接经由过程MongoDB Compass客户端增加Stu数据,就会看到在页面中及时看到新增加的数据了。
下一章会吧代码上传到gitee,列位看官若有须要请自行下载。
系列章节目次
实战SpringCloud相应式微效劳系列教程(第一章)
实战SpringCloud相应式微效劳系列教程(第二章)
实战SpringCloud相应式微效劳系列教程(第三章)
实战SpringCloud相应式微效劳系列教程(第四章)
实战SpringCloud相应式微效劳系列教程(第五章)
实战SpringCloud相应式微效劳系列教程(第六章)
实战SpringCloud相应式微效劳系列教程(第七章)
实战SpringCloud相应式微效劳系列教程(第八章)
实战SpringCloud相应式微效劳系列教程(第九章)