spring-cloud+ nacos+feign 增删改查(多表)
环境准备
- 数据库
学生自行创建数据库,根据提供的sql创建表和数据,每个表单独一个数据库 - 后台
学生自行搭建SpringCloud+Feign+Nacos+GateWay+MyBatis后台环境 - 前台
学生自行创建前台vue环境,实现测试要求
后端:以book和category为例
如图所示:book 是主,category是从
book.pom文件 和category.pom文件
<properties>
<maven.compiler.source>8</maven.compiler.source>
<maven.compiler.target>8</maven.compiler.target>
</properties>
<dependencies>
<!--这个是你自己的 feign-apl -->
<dependency>
<groupId>book-parent</groupId>
<artifactId>feign-api</artifactId>
<version>1.0-SNAPSHOT</version>
</dependency>
<!--阿里 spring cloud-->
<dependency>
<groupId>com.alibaba.cloud</groupId>
<artifactId>spring-cloud-starter-alibaba-nacos-discovery</artifactId>
</dependency>
<!--通用mapper-->
<dependency>
<groupId>tk.mybatis</groupId>
<artifactId>mapper-spring-boot-starter</artifactId>
</dependency>
<!--spring boot 启动器-->
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-web</artifactId>
</dependency>
<!--mysql 启动器-->
<dependency>
<groupId>mysql</groupId>
<artifactId>mysql-connector-java</artifactId>
</dependency>
<!--mybatis-->
<dependency>
<groupId>org.mybatis.spring.boot</groupId>
<artifactId>mybatis-spring-boot-starter</artifactId>
</dependency>
<!--nacos配置管理依赖-->
<dependency>
<groupId>com.alibaba.cloud</groupId>
<artifactId>spring-cloud-starter-alibaba-nacos-config</artifactId>
</dependency>
</dependencies>
<build>
<finalName>app</finalName>
<plugins>
<plugin>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-maven-plugin</artifactId>
</plugin>
</plugins>
</build>
feign(远程调用)和getaway(网关)
红色的不用写 那是过滤器
feign 和getaway的pom文件
<properties>
<maven.compiler.source>8</maven.compiler.source>
<maven.compiler.target>8</maven.compiler.target>
</properties>
<dependencies>
<dependency>
<groupId>com.alibaba.cloud</groupId>
<artifactId>spring-cloud-alibaba-dependencies</artifactId>
<version>2.2.6.RELEASE</version>
<type>pom</type>
<scope>import</scope>
</dependency>
<!--引入feign的starter依赖-->
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-starter-openfeign</artifactId>
<version>2.2.6.RELEASE</version>
</dependency>
<!-- 时间所需的jar @JsonFormat(pattern = "yyyy-MM-dd HH:mm:ss",timezone = "GMT+8")-->
<dependency>
<groupId>com.alibaba.cloud</groupId>
<artifactId>spring-cloud-starter-alibaba-nacos-discovery</artifactId>
</dependency>
<!--mybatis-->
<dependency>
<groupId>org.mybatis.spring.boot</groupId>
<artifactId>mybatis-spring-boot-starter</artifactId>
</dependency>
<!-- 通用mysql-->
<dependency>
<groupId>tk.mybatis</groupId>
<artifactId>mapper-spring-boot-starter</artifactId>
</dependency>
<dependency>
<groupId>com.github.pagehelper</groupId>
<artifactId>pagehelper-spring-boot-starter</artifactId>
<version>1.2.5</version>
</dependency>
</dependencies>
getaway·:内容
<dependencies>
<!--网关-->
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-starter-gateway</artifactId>
<version>2.2.6.RELEASE</version>
</dependency>
<!--nacos服务发现依赖-->
<dependency>
<groupId>com.alibaba.cloud</groupId>
<artifactId>spring-cloud-starter-alibaba-nacos-discovery</artifactId>
<version>2.2.6.RELEASE</version>
</dependency>
</dependencies>
父类(项目类)
<parent>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-parent</artifactId>
<version>2.3.9.RELEASE</version>
<relativePath/>
</parent>
<properties>
<maven.compiler.source>8</maven.compiler.source>
<maven.compiler.target>8</maven.compiler.target>
<project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
<project.reporting.outputEncoding>UTF-8</project.reporting.outputEncoding>
<java.version>1.8</java.version>
<spring-cloud.version>Hoxton.SR10</spring-cloud.version>
<mysql.version>8.0.27</mysql.version>
<mybatis.version>2.1.1</mybatis.version>
<mapper.starter.version>2.0.2</mapper.starter.version>
</properties>
<dependencyManagement>
<dependencies>
<!-- springCloud 阿里 -->
<dependency>
<groupId>com.alibaba.cloud</groupId>
<artifactId>spring-cloud-alibaba-dependencies</artifactId>
<version>2.2.6.RELEASE</version>
<type>pom</type>
<scope>import</scope>
</dependency>
<!-- mysql驱动 -->
<dependency>
<groupId>mysql</groupId>
<artifactId>mysql-connector-java</artifactId>
<version>${mysql.version}</version>
</dependency>
<!--mybatis-->
<dependency>
<groupId>org.mybatis.spring.boot</groupId>
<artifactId>mybatis-spring-boot-starter</artifactId>
<version>${mybatis.version}</version>
</dependency>
<!-- 通用Mapper启动器 -->
<dependency>
<groupId>tk.mybatis</groupId>
<artifactId>mapper-spring-boot-starter</artifactId>
<version>${mapper.starter.version}</version>
</dependency>
</dependencies>
</dependencyManagement>
<dependencies>
<dependency>
<groupId>org.projectlombok</groupId>
<artifactId>lombok</artifactId>
</dependency>
</dependencies>
创建数据库:一个表 一个数据库
好了环境准备,已经做完了下面就是写代码了
BookController.java
package com.czxy.controller;
import com.czxy.Vo.BookVo;
import com.czxy.domain.Book;
import com.czxy.service.BookService;
import com.github.pagehelper.PageInfo;
import org.springframework.web.bind.annotation.*;
import javax.annotation.Resource;
import java.util.List;
@RestController
@RequestMapping("/book")
public class BookController {
@Resource
private BookService bookService;
@GetMapping
public List<Book> findSchoolAll(){
List<Book> list = bookService.findSchoolAll();
return list;
}
@GetMapping("/{id}")
public Book findSchoolById(@PathVariable("id") Integer id){
Book book = bookService.findSchoolById(id);
return book;
}
@PutMapping
Integer Up(@RequestBody Book book){
Integer up = bookService.Up(book);
return up;
}
@PostMapping("/{pageNum}/{pageSize}")
PageInfo<Book> pageIn(
@PathVariable Integer pageNum,
@PathVariable Integer pageSize,
@RequestBody BookVo bookVo
){
PageInfo<Book> bookPageInfo = bookService.pageIn(pageNum, pageSize, bookVo);
return bookPageInfo;
}
@PostMapping
Integer insert(@RequestBody Book book){
Integer insert = bookService.insert(book);
return insert;
}
@DeleteMapping("/{id}")
Integer daleTe(@PathVariable("id") Integer id){
Integer daleTe = bookService.daleTe(id);
return daleTe;
}
@DeleteMapping("/batchDelete/{ids}")
void daleAll(@PathVariable("ids") String ids){
bookService.daleAll(ids);
}
}
BookMapper.java
package com.czxy.dao;
import com.czxy.domain.Book;
import com.czxy.domain.Category;
import tk.mybatis.mapper.common.Mapper;
@org.apache.ibatis.annotations.Mapper
public interface BookMapper extends Mapper<Book> {
}
bookservice.java
package com.czxy.service;
import com.czxy.Vo.BookVo;
import com.czxy.dao.BookMapper;
import com.czxy.domain.Book;
import com.czxy.domain.Category;
import com.czxy.feign.BookFeign;
import com.czxy.feign.CategoryClient;
import com.github.pagehelper.PageHelper;
import com.github.pagehelper.PageInfo;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;
import tk.mybatis.mapper.entity.Example;
import javax.annotation.Resource;
import java.util.List;
@Service
@Transactional
public class BookService implements BookFeign {
@Resource
private BookMapper bookMapper;
@Resource
private CategoryClient categoryClient;
@Override
public List<Book> findSchoolAll() {
List<Book> list = bookMapper.selectAll();
for (Book book : list) {
Category category = categoryClient.queryByTid(book.getCid());
book.setCategory(category);
}
return list;
}
@Override
public Book findSchoolById(Integer id) {
Book book = bookMapper.selectByPrimaryKey(id);
Category category = categoryClient.queryByTid(book.getCid());
book.setCategory(category);
return book;
}
@Override
public Integer Up(Book book) {
int i = bookMapper.updateByPrimaryKey(book);
return i;
}
@Override
public Integer daleTe(Integer id) {
int i = bookMapper.deleteByPrimaryKey(id);
return i;
}
@Override
public void daleAll(String ids) {
String[] split = ids.split(",");
for (String s : split) {
bookMapper.deleteByPrimaryKey(s);
}
}
@Override
public PageInfo<Book> pageIn(Integer pageNum, Integer pageSize, BookVo bookVo) {
Example example = new Example(Book.class);
Example.Criteria criteria = example.createCriteria();
if (bookVo.getCid()!=null && !"".equals(bookVo.getCid())){
criteria.andEqualTo("cid",bookVo.getCid());
}
if (bookVo.getName()!=null&& !"".equals(bookVo.getName())){
criteria.andLike("name","%"+bookVo.getName()+"%");
}
if (bookVo.getStaPrice()!= null && !"".equals(bookVo.getStaPrice())){
criteria.andGreaterThanOrEqualTo("price",bookVo.getStaPrice());
}
if (bookVo.getEntPrice()!= null && !"".equals(bookVo.getEntPrice())){
criteria.andLessThanOrEqualTo("price",bookVo.getEntPrice());
}
PageHelper.startPage(pageNum,pageSize);
List<Book> list = bookMapper.selectByExample(example);
for (Book book : list) {
Category category = categoryClient.queryByTid(book.getCid());
book.setCategory(category);
}
return new PageInfo<>(list);
}
@Override
public Integer insert(Book book) {
int insert = bookMapper.insert(book);
return insert;
}
}
启动类:BookApplication
package com.czxy;
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.cloud.openfeign.EnableFeignClients;
@EnableFeignClients(basePackages = "com.czxy.feign")
@SpringBootApplication
public class BookApplication {
public static void main(String[] args) {
SpringApplication.run(BookApplication.class,args);
}
}
B:application.yml
server:
port: 8081
spring:
application:
name: bookservice
datasource:
url: jdbc:mysql://localhost:3306/cloud-book?useUnicode=true&characterEncoding=utf8&serverTimezone=UTC&useSSL=false
username: root
password: 123456
driver-class-name: com.mysql.cj.jdbc.Driver
cloud:
nacos:
server-addr: localhost:8848 # Nacos地址
config:
file-extension: yaml # 文件后缀名
mybatis:
type-aliases-package: com.czxy.domain
configuration:
map-underscore-to-camel-case: true
logging:
level:
cn.itcast: debug
pattern:
dateformat: MM-dd HH:mm:ss:SSS
feign:
client:
config:
default: # 这里用default就是全局配置,如果是写服务名称,则是针对某个微服务的配置
loggerLevel: FULL # 日志级别
CategoryController.java
package com.czxy.controller;
import com.czxy.dao.CategoryMapper;
import com.czxy.domain.Book;
import com.czxy.domain.Category;
import com.czxy.service.CategoryService;
import org.springframework.web.bind.annotation.*;
import javax.annotation.Resource;
import java.util.List;
@RestController
@RequestMapping("/category")
public class CategoryController {
@Resource
private CategoryService categoryService;
@GetMapping
List<Category> All(){
List<Category> all = categoryService.All();
return all;
}
@PostMapping
Integer insert(@RequestBody Category category){
return categoryService.insert(category);
}
@GetMapping("/{cid}")
Category queryByTid(@PathVariable Integer cid){
Category category = categoryService.queryByTid(cid);
return category;
}
@PutMapping
Integer Up(@RequestBody Category category){
return categoryService.Up(category);
}
@DeleteMapping("/{cid}")
Integer Up(@PathVariable("cid") Integer cid){
return categoryService.date(cid);
}
}
CategoryService.java
package com.czxy.service;
import com.czxy.dao.CategoryMapper;
import com.czxy.domain.Category;
import com.czxy.feign.CategoryClient;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;
import javax.annotation.Resource;
import java.util.List;
@Service
@Transactional
public class CategoryService implements CategoryClient {
@Resource
private CategoryMapper categoryMapper;
@Override
public Category queryByTid(Integer cid) {
Category category = categoryMapper.selectByPrimaryKey(cid);
return category;
}
@Override
public List<Category> All() {
List<Category> categories = categoryMapper.selectAll();
return categories;
}
@Override
public Integer insert(Category category) {
return categoryMapper.insert(category);
}
@Override
public Integer Up(Category category) {
return categoryMapper.updateByPrimaryKey(category);
}
@Override
public Integer date(Integer cid) {
return categoryMapper.deleteByPrimaryKey(cid);
}
}
CategoryMapper.java
package com.czxy.dao;
import com.czxy.domain.Category;
import tk.mybatis.mapper.common.Mapper;
@org.apache.ibatis.annotations.Mapper
public interface CategoryMapper extends Mapper<Category> {
}
CategoryApplication.java
package com.czxy;
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.cloud.openfeign.EnableFeignClients;
@EnableFeignClients(basePackages = "com.czxy.feign")
@SpringBootApplication
public class CategoryApplication {
public static void main(String[] args) {
SpringApplication.run(CategoryApplication.class,args);
}
}
C:application.yml
server:
port: 8082
spring:
application:
name: categoryservice
datasource:
url: jdbc:mysql://localhost:3306/cloud-category?useUnicode=true&characterEncoding=utf8&serverTimezone=UTC&useSSL=false
username: root
password: 123456
driver-class-name: com.mysql.cj.jdbc.Driver
cloud:
nacos:
server-addr: localhost:8848 # Nacos地址
config:
file-extension: yaml # 文件后缀名
mybatis:
type-aliases-package: com.czxy.domain
configuration:
map-underscore-to-camel-case: true
logging:
level:
cn.itcast: debug
pattern:
dateformat: MM-dd HH:mm:ss:SSS
feign:
client:
config:
default: # 这里用default就是全局配置,如果是写服务名称,则是针对某个微服务的配置
loggerLevel: FULL # 日志级别
在feign中创建实体类:book
在feign中创建实体类:category
BookFeign.java
package com.czxy.feign;
import com.czxy.Vo.BookVo;
import com.czxy.domain.Book;
import com.github.pagehelper.PageInfo;
import org.springframework.cloud.openfeign.FeignClient;
import org.springframework.web.bind.annotation.*;
import java.util.List;
//微服务的地址
@FeignClient(value="bookservice")
public interface BookFeign {
//todo 查询所有
@GetMapping("/book")
public List<Book> findSchoolAll();
//todo 分页查询+ 模糊查询
@PostMapping("/book/{pageNum}/{pageSize}")
PageInfo<Book>pageIn(
@PathVariable Integer pageNum,
@PathVariable Integer pageSize,
@RequestBody BookVo bookVo
);
//todo 添加
@PostMapping("/book")
Integer insert(@RequestBody Book book);
//todo 根据id 查询
@GetMapping("/book/{id}")
public Book findSchoolById(@PathVariable("id") Integer id);
//todo 修改
@PutMapping("/book")
Integer Up(@RequestBody Book book);
//todo 删除
@DeleteMapping("/book/{id}")
Integer daleTe(@PathVariable("id") Integer id);
//todo 批量删除
@DeleteMapping("/book/batchDelete/{ids}")
void daleAll(@PathVariable("ids") String ids);
}
CategoryClient.java
package com.czxy.feign;
import com.czxy.domain.Category;
import org.springframework.cloud.openfeign.FeignClient;
import org.springframework.web.bind.annotation.*;
import java.util.List;
//微服务的地址
@FeignClient(value = "categoryservice")
public interface CategoryClient {
//todo 根据id 查询
@GetMapping("/category/{cid}")
Category queryByTid(@PathVariable Integer cid);
//todo 查询所有
@GetMapping("/category")
List<Category> All();
//todo 添加
@PostMapping("/category")
Integer insert(@RequestBody Category category);
//todo 修改
@PutMapping("/category")
Integer Up(@RequestBody Category category);
//todo 删除
@DeleteMapping("/category/{cid}")
Integer date(@PathVariable Integer cid);
}
分页所需要的Vo类
getaway的启动类
G:application.yml
server:
port: 10010 # 网关端口
spring:
application:
name: gateway # 服务名称
cloud:
nacos:
server-addr: localhost:8848 # Nacos地址
gateway:
routes: # 网关路由配置
- id: book-service # 路由id,自定义,只要唯一即可
# uri: http://127.0.0.1:8082 # 路由的目标地址 http就是固定地址
uri: lb://bookservice/ # 路由的目标地址 lb就是负载均衡,后面跟服务名称
predicates: # 路由断言,也就是判断请求是否符合路由规则的条件
- Path=/book/** # 这个是按照路径匹配,只要以/user/开头就符合要求
- id: category-service # 路由id,自定义,只要唯一即可
# uri: http://127.0.0.1:8082 # 路由的目标地址 http就是固定地址
uri: lb://categoryservice/ # 路由的目标地址 lb就是负载均衡,后面跟服务名称
predicates: # 路由断言,也就是判断请求是否符合路由规则的条件
- Path=/category/** # 这个是按照路径匹配,只要以/user/开头就符合要求
# 网关解决跨域
globalcors: # 全局的跨域处理
add-to-simple-url-handler-mapping: true # 解决options请求被拦截问题
corsConfigurations:
'[/**]':
allowedOrigins: # 允许哪些网站的跨域请求
- "http://localhost:8080"
allowedMethods: # 允许的跨域ajax的请求方式
- "GET"
- "POST"
- "DELETE"
- "PUT"
- "OPTIONS"
allowedHeaders: "*" # 允许在请求中携带的头信息
allowCredentials: true # 是否允许携带cookie
maxAge: 360000 # 这次跨域检测的有效期