黑马头条 08平台管理
- 1.开始准备和开发思路
- 1.1.开发网关
- 1.2编写admin-gateway 代码
 
- 2.开发登录微服务
- 2.1编写登录微服务
 
- 3.频道管理
- 4.敏感词管理
- 5.用户认证审核
- 6.自媒体文章人工审核
- 99. 最后开发中碰到的问题汇总
- 1.关于nacos 配置 问题
- 2.在开发频道管理新增频道后端无法接收到前端请求
- 3.观察了两个方法
- 4.规范性 dto 和pojo类
- 5.java中多态
 
程序源码会以压缩包形式放在这 需要的可以取用
需求和接口文档
https://javazhang.lan删zn.com/ix除9CG2k4exxc
https://javazhang.la删nzn.com/iJau除e2k4eyid
 全部代码
 htt删ps://javazhang.lan除zn.com/iPTju2kcaenc
 密码:i6it
1.开始准备和开发思路
(1)发现有登录请求都需要一个网关 作为支撑 , 所以先解决网关问题
1.1.开发网关
待完成项
- nacos 写一套配置
- 完成网关类编写
学习nacos 配置中 学到了 CORS(跨域资源共享),它是一种安全机制,可以指定哪些外部来源(域、协议或端口)可以访问其资源,当一个网页尝试从不同于他的源(即域名、协议或端口号不同)加载资源,浏览器会检查是否允许这种跨域请求
 初步nacos配置
spring:
  cloud:
    gateway:
      globalcors:
        cors-configurations:
          '[/**]': #匹配所有请求都处理ocrs跨域问题
            allowerdOrigins: "*"  #跨域处理哪些请求会被允许 
            allowedMethods:   #可以跨域请求的方法
             - GET
             - POST
             - PUT
             - DELETE
编写网关配置类
 routes: 下的 是每一个微服务 , 只有编写微服务才有对应的uri 等配置
 网关类看懂后, 参考完成的类复制粘贴即可
 一共需要 网关 配一套 nacos 微服务也有一套nacos 网关中nacos 嵌套微服务的地址,达到转发的目的
1.2编写admin-gateway 代码

 过滤器 和工具类 可以从wemedia 网关中拷贝一份
 AuthorizeFilter 类
package com.heima.admin.gateway.filter;
import com.heima.admin.gateway.util.AppJwtUtil;
import io.jsonwebtoken.*;
import org.apache.commons.lang.StringUtils;
import org.springframework.cloud.gateway.filter.GatewayFilterChain;
import org.springframework.cloud.gateway.filter.GlobalFilter;
import org.springframework.core.Ordered;
import org.springframework.http.HttpStatus;
import org.springframework.http.server.reactive.ServerHttpRequest;
import org.springframework.http.server.reactive.ServerHttpResponse;
import org.springframework.web.server.ServerWebExchange;
import reactor.core.publisher.Mono;
import javax.crypto.SecretKey;
import javax.crypto.spec.SecretKeySpec;
import java.util.*;
public class AuthorizeFilter implements Ordered, GlobalFilter {
    @Override
    public Mono<Void> filter(ServerWebExchange exchange, GatewayFilterChain chain) {
        //1.获取request 和 response 对象
        ServerHttpRequest request = exchange.getRequest();
        ServerHttpResponse response = exchange.getResponse();
        //2.判断是否是登陆
        //uri 是完整路径   path 是从完整路径里取到路径
        if (request.getURI().getPath().contains("/login")){
            //放行
            return chain.filter(exchange);
        }
        //3.获取token
        String tocken = request.getHeaders().getFirst("token");
        //4.判断token是否岑在
        if (StringUtils.isBlank(tocken)){
            response.setStatusCode(HttpStatus.UNAUTHORIZED);
            return response.setComplete();
        }
        //5.判断token是否有效
        try {
            Claims claimsBody = AppJwtUtil.getClaimsBody(tocken);
            //判断是否过期
            int i = AppJwtUtil.verifyToken(claimsBody);
            if (i ==1 || i== 2){
                response.setStatusCode(HttpStatus.UNAUTHORIZED);
                return response.setComplete();
            }
            //获取用户信息存入hader中
            Object userId = claimsBody.get("id");
            ServerHttpRequest serverHttpRequest = request.mutate().headers(httpHeaders -> {
                httpHeaders.add("userId", userId + "");
            }).build();
            //重置请求
            exchange.mutate().request(serverHttpRequest);
        }catch (Exception e){
            e.printStackTrace();
        }
        //6.放行
        return chain.filter(exchange);
    }
    /**
     * 优先级设置 值越小 优先级越大
     * @return
     */
    @Override
    public int getOrder() {
        return 0;
    }
    }
AppJwtUtil 类
package com.heima.admin.gateway.util;
import io.jsonwebtoken.*;
import javax.crypto.SecretKey;
import javax.crypto.spec.SecretKeySpec;
import java.util.*;
public class AppJwtUtil {
    //TOKEN的有效期一天
    private static final int TOKEN_TIME_OUT = 24 * 60 * 60;
    //加密KEY
    private static final String TOKEN_ENCRY_KEY="MDk4ZjZiY2Q0NjIxZDM3M2NhZGU0ZTgzMjYyN2I0ZjY";
    //最小刷新间隔S
    private static final int REFRESH_TIME = 300;
    //生产ID
    public static String getToken(Long id){
        Map<String , Object> claimMaps = new HashMap<>();
        long currentTime = System.currentTimeMillis();
        claimMaps.put("id",id);
        return Jwts.builder()
                .setId(UUID.randomUUID().toString())
                .setIssuedAt(new Date(currentTime)) //签发时间
                .setSubject("system")
                .setAudience("app")
                .compressWith(CompressionCodecs.GZIP)
                .signWith(SignatureAlgorithm.HS512 , generalKey())
                .setExpiration(new Date(currentTime + TOKEN_TIME_OUT * 1000))//过期时间戳
                .addClaims(claimMaps)
                .compact();
    }
    /**
     * 获取token中的claims信息
     *
     * @param token
     * @return
     */
    private static Jws<Claims> getJws(String token) {
        return Jwts.parser()
                .setSigningKey(generalKey())
                .parseClaimsJws(token);
    }
    /**
     * 获取payload body信息
     *
     * @param token
     * @return
     */
    public static Claims getClaimsBody(String token) {
        try {
            return getJws(token).getBody();
        }catch (ExpiredJwtException e){
            return null;
        }
    }
    /**
     * 获取hearder body信息
     *
     * @param token
     * @return
     */
    public static JwsHeader getHeaderBody(String token) {
        return getJws(token).getHeader();
    }
    /**
     * 是否过期
     *
     * @param claims
     * @return -1:有效,0:有效,1:过期,2:过期
     */
    public static int verifyToken(Claims claims) {
        if(claims==null){
            return 1;
        }
        try {
            claims.getExpiration()
                    .before(new Date());
            // 需要自动刷新TOKEN
            if((claims.getExpiration().getTime()-System.currentTimeMillis())>REFRESH_TIME*1000){
                return -1;
            }else {
                return 0;
            }
        } catch (ExpiredJwtException ex) {
            return 1;
        }catch (Exception e){
            return 2;
        }
    }
    /**
     * 由字符串生成加密key
     *
     * @return
     */
    public static SecretKey generalKey() {
        byte[] encodedKey = Base64.getEncoder().encode(TOKEN_ENCRY_KEY.getBytes());
        SecretKey key = new SecretKeySpec(encodedKey, 0, encodedKey.length, "AES");
        return key;
    }
    public static void main(String[] args) {
       /* Map map = new HashMap();
        map.put("id","11");*/
        System.out.println(AppJwtUtil.getToken(1102L));
        Jws<Claims> jws = AppJwtUtil.getJws("eyJhbGciOiJIUzUxMiIsInppcCI6IkdaSVAifQ.H4sIAAAAAAAAADWLQQqEMAwA_5KzhURNt_qb1KZYQSi0wi6Lf9942NsMw3zh6AVW2DYmDGl2WabkZgreCaM6VXzhFBfJMcMARTqsxIG9Z888QLui3e3Tup5Pb81013KKmVzJTGo11nf9n8v4nMUaEY73DzTabjmDAAAA.4SuqQ42IGqCgBai6qd4RaVpVxTlZIWC826QA9kLvt9d-yVUw82gU47HDaSfOzgAcloZedYNNpUcd18Ne8vvjQA");
        Claims claims = jws.getBody();
        System.out.println(claims.get("id"));
    }
}
主启动类 AdminWebGatewayAplication
package com.heima.admin.gateway;
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.cloud.client.discovery.EnableDiscoveryClient;
@SpringBootApplication
@EnableDiscoveryClient
public class AdminWebGatewayAplication {
    public static void main(String[] args) {
        SpringApplication.run(AdminWebGatewayAplication.class,args);
    }
}
配置文件
server:
  port: 6001
spring:
  application:
    name: leadnews-admin-web-gateway
  cloud:
    nacos:
      discovery:
        server-addr: 192.168.200.130:8848
      config:
        server-addr: 192.168.200.130:8848
        file-extension: yml
Nacos 配置
spring:
  cloud:
    gateway:
      globalcors:
        add-to-simple-url-handler-mapping: true
        corsConfigurations:
          '[/**]':
            allowedHeaders: "*"
            allowedOrigins: "*"
            allowedMethods:
              - GET
              - POST
              - DELETE
              - PUT
              - OPTION
2.开发登录微服务
别忘记按照要求 导入pojo类
 
2.1编写登录微服务
创建对应模块
 
LoginController 代码
package com.heima.adminWeb.controller.v1;
import com.heima.adminWeb.service.AwUserService;
import com.heima.model.admin.web.dto.AdminLoginDto;
import com.heima.model.common.dtos.ResponseResult;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.PostMapping;
import org.springframework.web.bind.annotation.RequestBody;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;
@RestController
@RequestMapping("/login")
@Slf4j
public class LoginController {
    @Autowired
    private AwUserService awUserService;
    @PostMapping("/in")
    public ResponseResult login(@RequestBody AdminLoginDto dto){
            log.info("dto{}",dto);
      return   awUserService.login(dto);
    }
}
AwUserMapper代码
package com.heima.adminWeb.mapper;
import com.baomidou.mybatisplus.core.mapper.BaseMapper;
import com.heima.model.admin.web.pojo.AdUser;
import org.apache.ibatis.annotations.Mapper;
@Mapper
public interface AwUserMapper extends BaseMapper<AdUser> {
}
service 和 impl 实现类
package com.heima.adminWeb.service;
import com.baomidou.mybatisplus.extension.service.IService;
import com.heima.model.admin.web.dto.AdminLoginDto;
import com.heima.model.admin.web.pojo.AdUser;
import com.heima.model.common.dtos.ResponseResult;
public interface AwUserService extends IService<AdUser> {
     ResponseResult login( AdminLoginDto dto);
}
package com.heima.adminWeb.service.impl;
import com.baomidou.mybatisplus.core.toolkit.Wrappers;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.heima.adminWeb.mapper.AwUserMapper;
import com.heima.adminWeb.service.AwUserService;
import com.heima.model.admin.web.dto.AdminLoginDto;
import com.heima.model.admin.web.pojo.AdUser;
import com.heima.model.common.dtos.ResponseResult;
import com.heima.model.common.enums.AppHttpCodeEnum;
import com.heima.utils.common.AppJwtUtil;
import org.apache.commons.lang3.StringUtils;
import org.springframework.stereotype.Service;
import org.springframework.util.DigestUtils;
import java.util.HashMap;
@Service
public class AwUserServiceImpl  extends ServiceImpl<AwUserMapper , AdUser> implements AwUserService {
    /**
     * @param dto
     * @return
     */
    @Override
    public ResponseResult login(AdminLoginDto dto) {
        //1.检查参数
        if (StringUtils.isBlank(dto.getName()) || StringUtils.isBlank(dto.getPassword()) ){
            return ResponseResult.errorResult(AppHttpCodeEnum.PARAM_INVALID);
        }
        //检查用户是否存在
        AdUser adUser = getOne(Wrappers.<AdUser>lambdaQuery().eq(AdUser::getName, dto.getName()));
        if (adUser == null){
            return ResponseResult.errorResult(AppHttpCodeEnum.DATA_NOT_EXIST);
        }
        //验证密码
        String salt = adUser.getSalt();
        String password = dto.getPassword();
        String pswd = DigestUtils.md5DigestAsHex((password + salt).getBytes());
        if (pswd.equals(adUser.getPassword())){
                //返回数据jwt
            HashMap<String, Object> map = new HashMap<>();
            map.put("token" , AppJwtUtil.getToken(adUser.getId().longValue()));
            //删除密码和盐 保护隐私
            adUser.setSalt("");
            adUser.setPassword("");
            map.put("user" , adUser);
            return ResponseResult.okResult(map);
        }else{
            return ResponseResult.errorResult(AppHttpCodeEnum.LOGIN_PASSWORD_ERROR);
        }
    }
}
主启动类
package com.heima.adminWeb;
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.cloud.client.discovery.EnableDiscoveryClient;
@SpringBootApplication
@EnableDiscoveryClient
public class AdminWebApplication {
    public static void main(String[] args) {
        SpringApplication.run(AdminWebApplication.class , args);
    }
}
配置文件
server:
  port: 51809
spring:
  application:
    name: leadnews-admin-web
  cloud:
    nacos:
      discovery:
        server-addr: 192.168.200.130:8848
      config:
        server-addr: 192.168.200.130:8848
        file-extension: yml
logging:
  level:
    root: INFO
    org.springframework.cloud.gateway: DEBUG
    org.springframework.web: DEBUG
    com.heima.adminWeb: DEBUG
  file:
    name: ./logs/${spring.application.name}.log
  pattern:
    console: "%d{yyyy-MM-dd HH:mm:ss} %-5level %logger{36} - %msg%n"
    file: "%d{yyyy-MM-dd HH:mm:ss} %-5level [%thread] %logger{36} - %msg%n"
登录Nacos配置
 复制粘贴别的配置文件即可 注意数据库改操作数据库名称
spring:
  kafka:
    bootstrap-servers: 192.168.200.130:9092
    producer:
      retries: 10
      key-serializer: org.apache.kafka.common.serialization.StringSerializer
      value-serializer: org.apache.kafka.common.serialization.StringSerializer
  datasource:
    driver-class-name: com.mysql.jdbc.Driver
    url: jdbc:mysql://localhost:3306/leadnews_admin?useUnicode=true&characterEncoding=UTF-8&serverTimezone=UTC
    username: root
    password: root
# 设置Mapper接口所对应的XML文件位置,如果你在Mapper接口中有自定义方法,需要进行该配置
mybatis-plus:
  mapper-locations: classpath*:mapper/*.xml
  # 设置别名包扫描路径,通过该属性可以给包中的类注册别名
  type-aliases-package: com.heima.model.media.pojos
minio:
  accessKey: minio
  secretKey: minio123
  bucket: leadnews
  endpoint: http://192.168.200.130:9000
  readPath: http://192.168.200.130:9000
aliyun:
  accessKeyId: LTAI5tCWHCcfvqQzu8k2oKmX
  secret: auoKUFsghimbfVQHpy7gtRyBkoR4vc
  #aliyun.scenes=porn,terrorism,ad,qrcode,live,logo
  scenes: terrorism
feign:
  # 开启feign对hystrix熔断降级的支持
  hystrix:
    enabled: true
  # 修改调用超时时间
  client:
    config:
      default:
        connectTimeout: 2000
        readTimeout: 2000
网关Nacos 自媒体微服务是下一节频道管理用到的
spring:
  cloud:
    gateway:
      globalcors:
        add-to-simple-url-handler-mapping: true
        corsConfigurations:
          '[/**]':
            allowedHeaders: "*"
            allowedOrigins: "*"
            allowedMethods:
              - GET
              - POST
              - DELETE
              - PUT
              - OPTION
      routes:
        # 平台管理登录
        - id: adminlogin
          uri: lb://leadnews-admin-web
          predicates:
            - Path=/admin/**
          filters:
            - StripPrefix= 1
                #自媒体服务
        - id: leadnews-wemedia
          uri: lb://leadnews-wemedia
          predicates:
            - Path=/wemedia/**
          filters:
            - StripPrefix= 1
3.频道管理
增删改查 频道功能 代码一起给出 主要编写图中三个类
 
 WmchannelController
package com.heima.wemedia.controller.v1;
import com.heima.model.common.dtos.ResponseResult;
import com.heima.model.wemedia.dtos.WmFindDto;
import com.heima.model.wemedia.pojos.WmChannel;
import com.heima.wemedia.service.WmChannelService;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.*;
import javax.annotation.Resource;
@RestController
@RequestMapping("/api/v1/channel")
@Slf4j
public class WmchannelController {
    @Autowired
    private WmChannelService wmChannelService;;
    @GetMapping("/channels")
    public ResponseResult findAll() {
        return wmChannelService.findAll();
    }
    //   频道管理 功能开始
    //新增频道
    @PostMapping("/save")
    public ResponseResult saveChanel(@RequestBody WmChannel wmChannel){
        return wmChannelService.saveChanel(wmChannel);
    }
    //分页查询
    @PostMapping("/list")
    public ResponseResult findList(@RequestBody WmFindDto dto){
        return wmChannelService.findList( dto);
    }
    /**
     * 修改频道
     */
    @PostMapping("/update")
    public ResponseResult update(@RequestBody WmChannel wmChannel){
        return wmChannelService.update(wmChannel);
    }
    //删除频道
    @GetMapping("/del/{id}")
    public ResponseResult remove(@PathVariable Integer id) {
        return wmChannelService.removeChanel(id);
    }
}
WmChannelService
package com.heima.wemedia.service;
import com.baomidou.mybatisplus.extension.service.IService;
import com.heima.model.common.dtos.ResponseResult;
import com.heima.model.wemedia.dtos.WmFindDto;
import com.heima.model.wemedia.pojos.WmChannel;
import org.springframework.web.bind.annotation.RequestBody;
public interface WmChannelService extends IService<WmChannel> {
    //查询所有频道
    public ResponseResult findAll();
    //查看文章详情
    public ResponseResult select(Integer id);
        //保存文章频道
    public ResponseResult saveChanel( WmChannel wmChannel);
    /**
     * 查询所有频道
     * @param dto
     * @return
     */
    ResponseResult findList(WmFindDto dto);
    //修改频道
     ResponseResult update(WmChannel wmChannel);
     //删除频道
    ResponseResult removeChanel(Integer id);
}
WmChannelServiceImpl
package com.heima.wemedia.service.impl;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.core.toolkit.Wrappers;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.heima.model.common.dtos.PageResponseResult;
import com.heima.model.common.dtos.ResponseResult;
import com.heima.model.common.enums.AppHttpCodeEnum;
import com.heima.model.wemedia.dtos.WmFindDto;
import com.heima.model.wemedia.pojos.WmChannel;
import com.heima.model.wemedia.pojos.WmNews;
import com.heima.wemedia.mapper.WmChannelMapper;
import com.heima.wemedia.mapper.WmNewsMapper;
import com.heima.wemedia.service.WmChannelService;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.lang3.StringUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;
import java.util.Date;
@Service
@Transactional
@Slf4j
public class WmChannelServiceImpl extends ServiceImpl<WmChannelMapper, WmChannel> implements WmChannelService {
    /**
     * @return
     */
    @Override
    public ResponseResult findAll() {
        return ResponseResult.okResult(list());
    }
    /**
     * 查看文章
     *
     * @param id
     * @return
     */
    @Override
    public ResponseResult select(Integer id) {
        WmChannel byId = super.getById(id);
        return ResponseResult.okResult(byId);
    }
    /**
     * 保存频道
     *
     * @param wmChannel
     * @return
     */
    @Override
    public ResponseResult saveChanel(WmChannel wmChannel) {
        if (wmChannel == null || StringUtils.isBlank(wmChannel.getName())) {
            return ResponseResult.errorResult(AppHttpCodeEnum.PARAM_INVALID);
        }
        String name = wmChannel.getName();
        WmChannel one = getOne(Wrappers.<WmChannel>lambdaQuery().eq(WmChannel::getName, name));
        if (one == null) {
            wmChannel.setIsDefault(true);
            wmChannel.setCreatedTime(new Date());
            save(wmChannel);
            return ResponseResult.okResult("保存成功");
        } else {
            return ResponseResult.errorResult(AppHttpCodeEnum.DATA_EXIST);
        }
    }
    /**
     * 查询所有频道
     *
     * @param dto
     * @return
     */
    @Override
    public ResponseResult findList(WmFindDto dto) {
        if (dto == null) {
            return ResponseResult.errorResult(AppHttpCodeEnum.PARAM_INVALID);
        }
        //如果当前页是空 那就给一个初始值 , 每页条数也是
        if (dto.getPage() == null || dto.getSize() == null) {
            dto.setPage(1);
            dto.setSize(10);
        }
        //开始分页查询
        Page page = new Page(dto.getPage(), dto.getSize());
        //构建查询
        LambdaQueryWrapper<WmChannel> wrapper = new LambdaQueryWrapper();
        //如果有名称就根据名称查询
        if (StringUtils.isNoneBlank(dto.getName())) {
            wrapper.like(WmChannel::getName, dto.getName());
        }
        //如果有状态根据状态查询
        if (dto.getStatus() != null) {
            wrapper.eq(WmChannel::getStatus, dto.getStatus());
        }
        //倒叙
        wrapper.orderByDesc(WmChannel::getCreatedTime);
        //开始分页
        page = page(page, wrapper);
        //结果返回
        ResponseResult responseResult = new PageResponseResult(dto.getPage(), dto.getSize(), (int) page.getTotal());
        responseResult.setData(page.getRecords());
        return responseResult;
    }
    @Autowired
    private WmNewsMapper wmNewsMapper;
    /**
     * 更新频道
     *
     * @param wmChannel
     * @return
     */
    @Override
    public ResponseResult update(WmChannel wmChannel) {
        if (wmChannel.getId() == null || wmChannel == null) {
            return ResponseResult.errorResult(AppHttpCodeEnum.PARAM_INVALID);
        }
        //设置缺少属性
        wmChannel.setCreatedTime(new Date());
        wmChannel.setIsDefault(true);
        //查看是否被引用
        if (wmChannel.getStatus() == false) {
            LambdaQueryWrapper<WmNews> query = new LambdaQueryWrapper();
            query.eq(WmNews::getChannelId, wmChannel.getId());
            //审核中的文章使用这个频道也不能删除
            //    List<WmNews> wmNews = wmNewsMapper.selectList(query);
            int count = wmNewsMapper.selectCount(query);
            if (count > 0) {
                return ResponseResult.errorResult(AppHttpCodeEnum.NO_OPERATOR_AUTH, "素材已被引用");
            }
        }
        updateById(wmChannel);
        return ResponseResult.okResult("更新成功");
    }
    /**
     * 删除频道
     * @param id
     * @return
     */
    @Override
    public ResponseResult removeChanel(Integer id) {
        if (id == null) {
            return ResponseResult.errorResult(AppHttpCodeEnum.PARAM_INVALID);
        }
        WmChannel channel = getById(id);
        if (channel.getStatus() != false){
            return ResponseResult.errorResult(AppHttpCodeEnum.NO_OPERATOR_AUTH, "素材已启用无法删除");
        }
        removeById(id);
        return ResponseResult.okResult("删除成功");
    }
}
4.敏感词管理
nacos 配置不用动 就是最基本增删改查 列出核心代码
 AdSensitiveController
package com.heima.wemedia.controller.v1;
import com.heima.model.common.dtos.ResponseResult;
import com.heima.model.common.enums.AppHttpCodeEnum;
import com.heima.model.wemedia.dtos.AdSentiveDto;
import com.heima.model.wemedia.pojos.WmSensitive;
import com.heima.wemedia.service.AdSensitiveService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.*;
@RestController
@RequestMapping("/api/v1/sensitive")
public class AdSensitiveController {
    @Autowired
    private AdSensitiveService adSensitiveService;
    //新增敏感词
    @PostMapping("/save")
    public ResponseResult save(@RequestBody WmSensitive wmSensitive) {
        return adSensitiveService.saveSensitive(wmSensitive);
    }
    @PostMapping("/list")
    public ResponseResult list(@RequestBody AdSentiveDto dto) {
        return adSensitiveService.selectList(dto);
    }
    @DeleteMapping("/del/{id}")
    public ResponseResult del(@PathVariable Integer id) {
        if ( adSensitiveService.removeById(id)){
            return ResponseResult.okResult("删除成功");
        }else{
            return ResponseResult.errorResult(AppHttpCodeEnum.PARAM_INVALID,"删除失败");
        }
    }
    @PostMapping("/update")
    public ResponseResult update(@RequestBody WmSensitive wmSensitive) {
        return adSensitiveService.updateSensitive(wmSensitive);
    }
}
AdSensitiveService
package com.heima.wemedia.service;
import com.baomidou.mybatisplus.extension.service.IService;
import com.heima.model.common.dtos.ResponseResult;
import com.heima.model.wemedia.dtos.AdSentiveDto;
import com.heima.model.wemedia.pojos.WmSensitive;
public interface AdSensitiveService extends IService<WmSensitive> {
    //新增敏感词
    ResponseResult saveSensitive(WmSensitive wmSensitive);
    //分页查询敏感词
    ResponseResult selectList(AdSentiveDto dto);
        //修改敏感词
    ResponseResult updateSensitive(WmSensitive wmSensitive);
}
AdSensitiveServiceImpl
package com.heima.wemedia.service.impl;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.core.injector.methods.SelectList;
import com.baomidou.mybatisplus.core.metadata.IPage;
import com.baomidou.mybatisplus.core.toolkit.Wrappers;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.heima.model.common.dtos.PageResponseResult;
import com.heima.model.common.dtos.ResponseResult;
import com.heima.model.common.enums.AppHttpCodeEnum;
import com.heima.model.wemedia.dtos.AdSentiveDto;
import com.heima.model.wemedia.pojos.WmSensitive;
import com.heima.wemedia.mapper.WmSensitiveMapper;
import com.heima.wemedia.service.AdSensitiveService;
import org.apache.commons.lang3.StringUtils;
import org.springframework.stereotype.Service;
import java.util.Date;
@Service
public class AdSensitiveServiceImpl extends ServiceImpl<WmSensitiveMapper , WmSensitive> implements AdSensitiveService {
    /**
     * 新增敏感词
     * @param wmSensitive
     */
    @Override
    public ResponseResult saveSensitive(WmSensitive wmSensitive) {
            if(StringUtils.isBlank(wmSensitive.getSensitives())){
                return ResponseResult.errorResult(AppHttpCodeEnum.PARAM_INVALID);
            }
        String sensitives = wmSensitive.getSensitives();
        WmSensitive sensitive = getOne(Wrappers.<WmSensitive>lambdaQuery()
                .eq(WmSensitive::getSensitives, sensitives));
        if (sensitive != null){
            return ResponseResult.errorResult(AppHttpCodeEnum.PARAM_INVALID,"敏感词已存在");
        }
        wmSensitive.setCreatedTime(new Date());
        save(wmSensitive);
        return ResponseResult.okResult("新增成功");
    }
    /**
     * 分页查询敏感词
     * @param dto
     * @return
     */
    @Override
    public ResponseResult selectList(AdSentiveDto dto) {
        //设置初始值
        if (dto.getPage() == null || dto.getSize() == null){
            dto.setPage(1);
            dto.setSize(10);
        }
        //开始分页
        IPage page = new Page(dto.getPage(), dto.getSize());
        LambdaQueryWrapper<WmSensitive> wrapper = new LambdaQueryWrapper();
        if (StringUtils.isNoneBlank(dto.getName())){
            wrapper.like(WmSensitive::getSensitives,dto.getName());
        }
        //返回结果
        page = page(page,wrapper);
        ResponseResult responseResult = new PageResponseResult(dto.getPage(), dto.getSize(), (int) page.getTotal());
        responseResult.setData(page.getRecords());
        return responseResult;
    }
    /**
     * @param wmSensitive
     * @return
     */
    @Override
    public ResponseResult updateSensitive(WmSensitive wmSensitive) {
        if (wmSensitive.getId() == null){
            return ResponseResult.errorResult(AppHttpCodeEnum.PARAM_INVALID);
        }
        wmSensitive.setCreatedTime(new Date());
        updateById(wmSensitive);
        return ResponseResult.okResult("修改成功");
    }
}
5.用户认证审核
http://localhost:8803/service_6001/user/api/v1/auth/list
 请求路径 , 发现需要经过nacos 设置 可以转发到user微服务 , 不转发自己配一套应该也可以 就是太麻烦 所以直接用
spring:
  cloud:
    gateway:
      globalcors:
        add-to-simple-url-handler-mapping: true
        corsConfigurations:
          '[/**]':
            allowedHeaders: "*"
            allowedOrigins: "*"
            allowedMethods:
              - GET
              - POST
              - DELETE
              - PUT
              - OPTION
      routes:
        # 平台管理登录
        - id: adminlogin
          uri: lb://leadnews-admin-web
          predicates:
            - Path=/admin/**
          filters:
            - StripPrefix= 1
                #自媒体服务
        - id: leadnews-wemedia
          uri: lb://leadnews-wemedia
          predicates:
            - Path=/wemedia/**
          filters:
            - StripPrefix= 1
             #用户服务
        - id: user
          uri: lb://leadnews-user
          predicates:
           - Path=/user/**
          filters:
           - StripPrefix= 1
测试后发现请求成功到达
主要代码如下
 AdAuthController
package com.heima.user.controller.v1;
import com.heima.model.admin.web.dto.AdUserDto;
import com.heima.model.admin.web.pojo.ApUserRealname;
import com.heima.model.common.dtos.ResponseResult;
import com.heima.user.service.AdUserService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.PostMapping;
import org.springframework.web.bind.annotation.RequestBody;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;
@RestController
@RequestMapping("/api/v1/auth")
public class AdAuthController {
    @Autowired
    private AdUserService adUserService;
    //分页查询
    @PostMapping("/list")
    public ResponseResult selectList(@RequestBody AdUserDto dto) {
        return  adUserService.selectList(dto);
    }
    @PostMapping("/authFail")
    public ResponseResult authErrot(@RequestBody ApUserRealname dto){
        dto.setStatus((short) 2);
        dto.setReason("审核不通过");
        return adUserService.authErrot(dto);
    }
    @PostMapping("/authPass")
    public ResponseResult authPass(@RequestBody ApUserRealname dto){
        dto.setStatus((short) 9);
        return adUserService.authErrot(dto);
    }
}
AdUserService
package com.heima.user.service;
import com.baomidou.mybatisplus.extension.service.IService;
import com.heima.model.admin.web.dto.AdUserDto;
import com.heima.model.admin.web.pojo.AdUser;
import com.heima.model.admin.web.pojo.ApUserRealname;
import com.heima.model.common.dtos.ResponseResult;
import com.heima.model.user.pojos.ApUser;
public interface AdUserService extends IService<ApUserRealname> {
 // 分页查询
    ResponseResult selectList(AdUserDto dto);
    //审核成功或失败通用
    ResponseResult authErrot(ApUserRealname dto);
}
impl
package com.heima.user.service.impl;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.core.metadata.IPage;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.baomidou.mybatisplus.extension.service.IService;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.heima.model.admin.web.dto.AdUserDto;
import com.heima.model.admin.web.pojo.AdUser;
import com.heima.model.admin.web.pojo.ApUserRealname;
import com.heima.model.common.dtos.PageResponseResult;
import com.heima.model.common.dtos.ResponseResult;
import com.heima.model.common.enums.AppHttpCodeEnum;
import com.heima.user.mapper.AdUserMapper;
import com.heima.user.mapper.ApUserRealnameMapper;
import com.heima.user.service.AdUserService;
import org.apache.commons.lang3.StringUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import java.util.Date;
@Service
public class AdUserServiceImpl extends ServiceImpl<ApUserRealnameMapper, ApUserRealname> implements AdUserService {
    /**
     * @param dto
     * @return
     */
    @Override
    public ResponseResult selectList(AdUserDto dto) {
        if (dto.getPage() == null || dto.getSize() == null)
        {
            dto.setPage(1);
            dto.setSize(10);
        }
        IPage page = new Page(dto.getPage(), dto.getSize());
        LambdaQueryWrapper<ApUserRealname> wrapper = new LambdaQueryWrapper();
        if (dto.getStatus() != null){
            wrapper.eq(ApUserRealname::getStatus,dto.getStatus());
            page = page(page ,wrapper);
        }else{
        page = page(page);
        }
        ResponseResult responseResult = new PageResponseResult(dto.getPage(), dto.getSize(), (int) page.getTotal());
        responseResult.setData(page.getRecords());
        return responseResult;
    }
    //审核失败逻辑
    /**
     * @param dto
     * @return
     */
    @Override
    public ResponseResult authErrot(ApUserRealname dto) {
        if (dto.getId()==null){
            return ResponseResult.errorResult(AppHttpCodeEnum.PARAM_INVALID);
        }
        ApUserRealname byId = getById(dto.getId());
        byId.setStatus(dto.getStatus());
        if (dto.getReason() != null) {
            byId.setReason(dto.getReason());
        }
        byId.setUpdatedTime(new Date());
        updateById(byId);
        return ResponseResult.okResult("修改成功");
    }
}
6.自媒体文章人工审核
主要类 如下
 WmNewsController
package com.heima.wemedia.controller.v1;
import com.heima.model.common.dtos.ResponseResult;
import com.heima.model.wemedia.dtos.AdNews;
import com.heima.model.wemedia.dtos.AuthDto;
import com.heima.model.wemedia.dtos.WmNewsDto;
import com.heima.model.wemedia.dtos.WmNewsPageReqDto;
import com.heima.model.wemedia.pojos.WmNews;
import com.heima.wemedia.service.WmChannelService;
import com.heima.wemedia.service.WmNewsService;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.*;
import javax.annotation.Resource;
@RestController
@RequestMapping("/api/v1/news")
@Slf4j
public class WmNewsController {
    @Autowired
    private WmNewsService wmNewsService;
    @PostMapping("/list")
    public ResponseResult findList(@RequestBody WmNewsPageReqDto dto) {
            return wmNewsService.findList(dto);
    }
    @PostMapping("/submit")
    public ResponseResult submitNews(@RequestBody WmNewsDto dto){
        return wmNewsService.submitNews(dto);
    }
    @GetMapping("/one/{id}")
    public ResponseResult viewDetails(@PathVariable Integer id) {
        log.info("查看频道详情id:{}" , id);
        return wmNewsService.viewDetail(id);
    }
    @GetMapping("/del_news/{id}")
    public ResponseResult delNews(@PathVariable Integer id) {
        return wmNewsService.delNews(id);
    }
    @PostMapping("/down_or_up")
    public ResponseResult News(@RequestBody WmNews dto) {
        return wmNewsService.downorup(dto);
    }
// 查询文章列表
    @PostMapping("/list_vo")
    public ResponseResult listVo(@RequestBody AdNews dto) {
        return wmNewsService.listVo(dto);
    }
    //查询文章详情
    @GetMapping("/one_vo/{id}")
    public ResponseResult one(@PathVariable Integer id){
        return wmNewsService.getOneVo(id);
    }
    //人工审核失败
    @PostMapping("/auth_fail")
    public ResponseResult authFail(@RequestBody AuthDto dto){
        dto.setStatus(2);
        return wmNewsService.auth(dto);
    }
    //人工审核成功
    @PostMapping("/auth_pass")
    public ResponseResult authPass(@RequestBody AuthDto dto){
        dto.setStatus(4);
        return wmNewsService.auth(dto);
    }
}
WmNewsService
package com.heima.wemedia.service;
import com.baomidou.mybatisplus.extension.service.IService;
import com.heima.model.common.dtos.ResponseResult;
import com.heima.model.wemedia.dtos.AdNews;
import com.heima.model.wemedia.dtos.AuthDto;
import com.heima.model.wemedia.dtos.WmNewsDto;
import com.heima.model.wemedia.dtos.WmNewsPageReqDto;
import com.heima.model.wemedia.pojos.WmNews;
import org.springframework.web.bind.annotation.RequestBody;
public interface WmNewsService extends IService<WmNews> {
    /**
     * 条件查询文章列表
     * @param dto
     * @return
     */
    public ResponseResult findList( WmNewsPageReqDto dto);
    /**
     * 发布修改文章/保存为草稿
     * @param dto
     * @return
     */
    public ResponseResult submitNews(WmNewsDto dto);
  public  ResponseResult viewDetail(Integer id);
   public  ResponseResult delNews(Integer id);
    //文章上下架
   public ResponseResult downorup(WmNews dto);
    //文章人工审核分页查询
    ResponseResult listVo(AdNews dto);
    //查询文章详情
    ResponseResult getOneVo(Integer id);
        //人工审核
    ResponseResult auth(AuthDto dto);
}
WmNewsServiceImpl
package com.heima.wemedia.service.impl;
import com.alibaba.fastjson.JSON;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.core.injector.methods.SelectCount;
import com.baomidou.mybatisplus.core.injector.methods.SelectList;
import com.baomidou.mybatisplus.core.metadata.IPage;
import com.baomidou.mybatisplus.core.toolkit.Wrappers;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.heima.common.constants.WmNewsMessageConstants;
import com.heima.common.exception.CustomException;
import com.heima.model.admin.web.pojo.AdUser;
import com.heima.model.common.dtos.PageResponseResult;
import com.heima.model.common.dtos.ResponseResult;
import com.heima.model.common.enums.AppHttpCodeEnum;
import com.heima.model.wemedia.dtos.AdNews;
import com.heima.model.wemedia.dtos.AuthDto;
import com.heima.model.wemedia.dtos.WmNewsDto;
import com.heima.model.wemedia.dtos.WmNewsPageReqDto;
import com.heima.model.wemedia.pojos.WmMaterial;
import com.heima.model.wemedia.pojos.WmNews;
import com.heima.model.wemedia.pojos.WmNewsMaterial;
import com.heima.model.wemedia.pojos.WmUser;
import com.heima.utils.thread.WmThreadLocalUtil;
import com.heima.wemedia.mapper.WmMaterialMapper;
import com.heima.wemedia.mapper.WmNewsMapper;
import com.heima.wemedia.mapper.WmNewsMaterialMapper;
import com.heima.wemedia.mapper.WmUserMapper;
import com.heima.wemedia.service.WmNewsAutoScanService;
import com.heima.wemedia.service.WmNewsService;
import com.heima.wemedia.service.WmNewsTaskService;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.lang3.StringUtils;
import org.springframework.beans.BeanUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.kafka.core.KafkaTemplate;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;
import javax.annotation.Resource;
import java.util.*;
import java.util.stream.Collectors;
import static com.heima.common.constants.WemediaConstants.*;
@Service
@Slf4j
@Transactional
public class WmNewsServiceImpl extends ServiceImpl<WmNewsMapper, WmNews> implements WmNewsService {
    /**
     * 条件查询文章列表
     *
     * @param dto
     * @return
     */
    @Override
    public ResponseResult findList(WmNewsPageReqDto dto) {
        //检查参数
        //分页检查
        dto.checkParam();
        //分页条件查询
        IPage page = new Page(dto.getPage(), dto.getSize());
        LambdaQueryWrapper<WmNews> wrapper = new LambdaQueryWrapper();
        //状态精确查询
        if (dto.getStatus() != null) {
            wrapper.eq(WmNews::getStatus, dto.getStatus());
        }
        //频道精确查询
        if (dto.getChannelId() != null) {
            wrapper.eq(WmNews::getChannelId, dto.getChannelId());
        }
        //时间范围查询
        if (dto.getBeginPubDate() != null && dto.getEndPubDate() != null) {
            wrapper.between(WmNews::getPublishTime, dto.getBeginPubDate(), dto.getEndPubDate());
        }
        //关键字模糊查询
        if (StringUtils.isNotBlank(dto.getKeyword())) {
            wrapper.like(WmNews::getTitle, dto.getKeyword());
        }
        //查询当前登陆人文章
        wrapper.eq(WmNews::getUserId, WmThreadLocalUtil.getUser().getId());
        //按照发布时间倒叙
        wrapper.orderByDesc(WmNews::getPublishTime);
        page = page(page, wrapper);
        //结果返回
        ResponseResult responseResult = new PageResponseResult(dto.getPage(), dto.getSize(), (int) page.getTotal());
        responseResult.setData(page.getRecords());
        return responseResult;
    }
    @Autowired
    private WmNewsAutoScanService wmsNewsAutoScanService;
    @Autowired
    private WmNewsTaskService wmNewsTaskService;
    /**
     * @param dto
     * @return
     */
    @Override
    public ResponseResult submitNews(WmNewsDto dto) {
        //条件判断
        if (dto == null || dto.getContent() == null) {
            return ResponseResult.errorResult(AppHttpCodeEnum.PARAM_INVALID);
        }
        //保存或修改文章
        WmNews wmNews = new WmNews();
        //属性拷贝
        BeanUtils.copyProperties(dto, wmNews);
        //封面图片 list --。> string
        if (dto.getImages() != null && dto.getImages().size() > 0) {
            String imageStr = StringUtils.join(dto.getImages(), ",");
            wmNews.setImages(imageStr);
        }
        //如果当前封面类型为自动 -1
        if (dto.getType().equals(WM_NEWS_TYPE_AUTO)) {
            wmNews.setType(null);
        }
        saveOrUpdateWmNews(wmNews);
        //判断是否为草稿 , 结束当前方法
        if (dto.getStatus().equals(WmNews.Status.NORMAL.getCode())) {
            return ResponseResult.okResult(AppHttpCodeEnum.SUCCESS);
        }
        //不是草稿,保存文章内容图片与素材关系
        //获取文章内容中图片的url
        List<String> materials = ectractUrlInfo(dto.getContent());
        saveRelativeInfoForContent(materials, wmNews.getId());
        //不是草稿保存文章封面与素材关系
        saveRelativeInfoForCover(dto, wmNews, materials);
        //审核文章
        //    wmsNewsAutoScanService.autoScanWmNews(wmNews.getId());
        wmNewsTaskService.addNewsToTask(wmNews.getId() , wmNews.getPublishTime());
        return ResponseResult.okResult(AppHttpCodeEnum.SUCCESS);
    }
    /**
     * 如果当前封面类型为自动 , 则设置封面类型的数据
     * 匹配规则
     * 1.如果内容图片大于等于1 ,小于等于3 单图 type 1
     * 2.如果内容图片大于等于3 多图 type 3
     * 3.如果内容图片为0  无图 type 0
     * <p>
     * 保存封面图面与素材的关系
     *
     * @param dto
     * @param wmNews
     * @param materials
     */
    private void saveRelativeInfoForCover(WmNewsDto dto, WmNews wmNews, List<String> materials) {
        List<String> images = dto.getImages();
        //  如果当前封面类型为自动 , 则设置封面类型的数据
        if (dto.getType().equals(WM_NEWS_TYPE_AUTO)) {
            //多图
            if (materials.size() >= 3) {
                wmNews.setType(WM_NEWS_MANY_IMAGE);
                images = materials.stream().limit(3).collect(Collectors.toList());
            } else if (materials.size() >= 1 && materials.size() < 3) {
                //单图
                wmNews.setType(WM_COVER_REFERENCE);
                images = materials.stream().limit(1).collect(Collectors.toList());
            } else {
                //无图
                wmNews.setType(WM_NEWS_NONE_IMAGE);
            }
//            修改文章
            if (images != null && images.size() > 0) {
                wmNews.setImages(StringUtils.join(images, ","));
            }
            updateById(wmNews);
//* 保存封面图面与素材的关系
            if (images != null && images.size() > 0) {
                saveRelativeInfo(images, wmNews.getId(), WM_COVER_REFERENCE);
            }
        }
    }
    /**
     * 处理文章内容图片与素材的关系
     *
     * @param materials
     * @param newsId
     */
    private void saveRelativeInfoForContent(List<String> materials, Integer newsId) {
        saveRelativeInfo(materials, newsId, WM_NEWS_NONE_IMAGE);
    }
    @Autowired
    private WmMaterialMapper wmMaterialMapper;
    /**
     * 保存文章图片与素材关系到数据库中
     *
     * @param materials
     * @param newsId
     * @param wmNewsNoneImage
     */
    private void saveRelativeInfo(List<String> materials, Integer newsId, Short wmNewsNoneImage) {
        if (materials != null && !materials.isEmpty()) {
            //通过图片url 查询素材id
            List<WmMaterial> dbMaterials = wmMaterialMapper.selectList(Wrappers.<WmMaterial>lambdaQuery().in(WmMaterial::getUrl, materials));
            //判断素材是否有效
            if (dbMaterials == null || dbMaterials.size() == 0) {
                //手动抛出异常 为了统一异常处理,回滚事务
                throw new CustomException(AppHttpCodeEnum.MATERIASL_REFERENCE_FAIL);
            }
            if (materials.size() != dbMaterials.size()) {
                //手动抛出异常 为了统一异常处理,回滚事务
                throw new CustomException(AppHttpCodeEnum.MATERIASL_REFERENCE_FAIL);
            }
            List<Integer> idList = dbMaterials.stream().map(WmMaterial::getId).collect(Collectors.toList());
            //批量保存
            wmNewsMaterialMapper.saveRelations(idList, newsId, wmNewsNoneImage);
        }
    }
    /**
     * 提取文章内容中图片信息
     *
     * @param content
     * @return
     */
    private List<String> ectractUrlInfo(String content) {
        List<String> material = new ArrayList<>();
        List<Map> maps = JSON.parseArray(content, Map.class);
        for (Map map : maps) {
            if (map.get("type").equals("image")) {
                String imUrl = (String) map.get("value");
                material.add(imUrl);
            }
        }
        return material;
    }
    @Autowired
    private WmNewsMaterialMapper wmNewsMaterialMapper;
    /**
     * 保存或修改文章
     *
     * @param wmNews
     */
    private void saveOrUpdateWmNews(WmNews wmNews) {
        //补全属性
        wmNews.setUserId(WmThreadLocalUtil.getUser().getId());
        wmNews.setCreatedTime(new Date());
        wmNews.setSubmitedTime(new Date());
        wmNews.setEnable((short) 1);//默认上架
        if (wmNews.getId() == null) {
            //保存
            save(wmNews);
        } else {
            //修改
            //删除文章图片与素材的关系
            wmNewsMaterialMapper.delete(Wrappers.<WmNewsMaterial>lambdaQuery().eq(WmNewsMaterial::getNewsId, wmNews.getId()));
            updateById(wmNews);
        }
    }
    /**
     * 查看文章详情
     *
     * @param id
     * @return
     */
    @Override
    public ResponseResult viewDetail(Integer id) {
        WmNews byId = getById(id);
        WmNewsDto wmNewsDto = new WmNewsDto();
        BeanUtils.copyProperties(byId, wmNewsDto);
        List<String> images = new ArrayList<>();
        String images1 = byId.getImages();
        if (StringUtils.isNotEmpty(images1)) {
            images = Arrays.asList(images1.split(","));
        }
        wmNewsDto.setImages(images);
        return ResponseResult.okResult(wmNewsDto);
    }
@Autowired
private KafkaTemplate<String, String> kafkaTemplate;
    /**
     * @param dto
     * @return
     */
    @Override
    public ResponseResult downorup(WmNews dto) {
        if (dto.getId() == null){
            return ResponseResult.errorResult(AppHttpCodeEnum.PARAM_INVALID);
        }
        WmNews byId = getById(dto.getId());
        if (byId == null){
            return ResponseResult.errorResult(AppHttpCodeEnum.PARAM_INVALID , "文章不存在");
        }
        //判断文章是否发布
        if (!byId.getStatus().equals(WmNews.Status.PUBLISHED.getCode())){
            return ResponseResult.errorResult(AppHttpCodeEnum.PARAM_INVALID , "文章不是发布状态,不能上下架");
        }
        //修改文章
        if (dto.getEnable() != null && dto.getEnable() > -1  && dto.getEnable() < 2 ){
            update(Wrappers.<WmNews>lambdaUpdate().set(WmNews::getEnable , dto.getEnable())
                    .eq(WmNews::getId , byId.getId()));
            if (byId.getArticleId() != null) {
                //发送消息通知article 修改 文章的配置
                Map<String , Object> map = new HashMap<>();
                map.put("articleId" , byId.getArticleId());
                map.put("enable" , dto.getEnable());
                kafkaTemplate.send(WmNewsMessageConstants.WM_NEWS_UP_OR_DOWN_TOPIC ,JSON.toJSONString(map) );
            }
        }
//            WmNews wmNews = new WmNews();
//
//            byId.setEnable(dto.getEnable());
//            super.updateById(byId);
        return ResponseResult.okResult(AppHttpCodeEnum.SUCCESS);
    }
    /**
     * @param id
     * @return
     */
    @Override
    public ResponseResult delNews(Integer id) {
        if (id != null && id != 0) {
            boolean b = super.removeById(id);
        }
        return ResponseResult.okResult(AppHttpCodeEnum.SUCCESS);
    }
            @Autowired
            private WmUserMapper wmUserMapper;
    /**
     * 文章人工审核分页查询
     * @param dto
     * @return
     */
    @Override
    public ResponseResult listVo(AdNews dto) {
            // 查询所有 查询构造器 和分页构造器
        IPage page = new Page(dto.getPage(), dto.getSize());
        LambdaQueryWrapper<WmNews> wrapper = new LambdaQueryWrapper<>();
        // 判断条件
        if (dto.getTitle() != null){
            wrapper.like(WmNews::getTitle,dto.getTitle());
        }
        if (dto.getStatus() != null){
            wrapper.eq(WmNews::getStatus,dto.getStatus());
        }
        wrapper.orderByDesc(WmNews::getCreatedTime);
        page = page(page, wrapper);
        long total = page.getTotal();
        List records = page.getRecords();
        //为文章添加作者
        List<AdNews> adNewsList = new ArrayList<>();
        for (Object record : records) {
            //创建一个adNews对象 用来存储包含作者名称的类
            //一会试试多态
            //
            AdNews adNews =  new AdNews();
            //不知道这样拷贝能否成功
            BeanUtils.copyProperties(record,adNews);
            //如果成功进行下一步
            if (adNews.getUserId() != null){
                //查询作者
                WmUser wmUser = wmUserMapper.selectById(adNews.getUserId());
                //设置作者名称
                adNews.setAuthorName(wmUser.getName());
                //添加到集合中
                adNewsList.add(adNews);
            }
        }
        //替换page
        page.setRecords(adNewsList);
        ResponseResult responseResult  = new PageResponseResult(dto.getPage() , dto.getSize() , (int)page.getTotal());
        responseResult.setData(page.getRecords());
        return responseResult;
    }
    /**
     * 查询文章详情
     * @param id
     * @return
     */
    @Override
    public ResponseResult getOneVo(Integer id) {
        if (id == null){
            return ResponseResult.errorResult(AppHttpCodeEnum.PARAM_INVALID);
        }
        WmNews byId = getById(id);
        //赋予作者
        AdNews adNews = new AdNews();
        BeanUtils.copyProperties(byId , adNews);
        LambdaQueryWrapper<WmUser> wrapper = new LambdaQueryWrapper<>();
        wrapper.eq(WmUser::getId , byId.getUserId());
        WmUser wmUser = wmUserMapper.selectOne(wrapper);
        adNews.setAuthorName(wmUser.getName());
        return ResponseResult.okResult(adNews);
    }
    /**
     * 人工审核
     * @param dto
     * @return
     */
    @Override
    public ResponseResult auth(AuthDto dto) {
        if (dto.getStatus().equals(2)){
            update(Wrappers.<WmNews>lambdaUpdate().set(WmNews::getStatus , dto.getStatus())
                    .set(WmNews::getReason , dto.getMsg())
                    .eq(WmNews::getId , dto.getId()));
            return ResponseResult.okResult(AppHttpCodeEnum.SUCCESS);
        }
        if (dto.getStatus().equals(4)){
            update(Wrappers.<WmNews>lambdaUpdate().set(WmNews::getStatus , dto.getStatus())
                    .eq(WmNews::getId , dto.getId()));
            return ResponseResult.okResult(AppHttpCodeEnum.SUCCESS);
        }
        return ResponseResult.errorResult(AppHttpCodeEnum.PARAM_INVALID);
    }
}
99. 最后开发中碰到的问题汇总
1.关于nacos 配置 问题
这个是正确的 nacos 关于登录的配置
spring:
  cloud:
    gateway:
      globalcors:
        add-to-simple-url-handler-mapping: true
        corsConfigurations:
          '[/**]':
            allowedHeaders: "*"
            allowedOrigins: "*"
            allowedMethods:
              - GET
              - POST
              - DELETE
              - PUT
              - OPTION
      routes:
        # 平台管理微服务
        - id: admin
          uri: lb://leadnews-admin      #这个lb 后面的是 登录微服务的微服务配置文件名称
          predicates:
routes 的 uri 路径 /service_6001/admin/login/** 我写成这个就无法访问到后端 而写/admin/** 就可以 虽然知道 /admin 匹配更宽泛 但是为什么 我写精准的就不行呢
 
 
答 :
 结合nginx 配置发现
 这里的正则表达式~/service_6001/(.*)会匹配以/service_6001/开头的任何URI,并捕获/service_6001/之后的部分作为变量$1。当您将前端请求发送到http://localhost:8803/service_6001/admin/login/in时,该请求会被这个location块捕获,并且$1将等于admin/login/in。
2.在开发频道管理新增频道后端无法接收到前端请求
!!不需要新建一个模块, 用leadnews-wemedia模块就能完成
 因为 请求url 根据nginx 配置 会发给 admin-web-gateway 的配置文件
 应在配置文件中配置这个路径转发到哪不然后端接收到
 http://localhost:8803/service_6001/wemedia/api/v1/channel/save
 正确配置
spring:
  cloud:
    gateway:
      globalcors:
        add-to-simple-url-handler-mapping: true
        corsConfigurations:
          '[/**]':
            allowedHeaders: "*"
            allowedOrigins: "*"
            allowedMethods:
              - GET
              - POST
              - DELETE
              - PUT
              - OPTION
      routes:
        # 平台管理登录
        - id: adminlogin
          uri: lb://leadnews-admin-web
          predicates:
            - Path=/admin/**
          filters:
            - StripPrefix= 1
               #自媒体服务
        - id: leadnews-wemedia   #名字自定义不重复即可
          uri: lb://leadnews-wemedia   #对应wemedia 的微服务配置文件名称
          predicates:
            - Path=/wemedia/**
          filters:
            - StripPrefix= 1
3.观察了两个方法
selectList
 

 selectCount
 
4.规范性 dto 和pojo类
pojo用于和数据库交互 dto 用于和前端交互 , 开发时应注意规范性
5.java中多态
父类型引用 指向子类型对象 如果父类中没有子类特有的方法 则多态无法调用子类型方法 (向下转型可以)









![[大模型开源]SecGPT 网络安全大模型](https://i-blog.csdnimg.cn/direct/121fd0226f0f48a5bc74c65cebde0b7b.png)









