master
rong.liu 6 months ago
parent 9dcf313952
commit 934b732b50
  1. 2
      src/main/java/com/huoran/iasf/common/exception/code/BaseResponseCode.java
  2. 16
      src/main/java/com/huoran/iasf/common/utils/R.java
  3. 68
      src/main/java/com/huoran/iasf/controller/SeoController.java
  4. 12
      src/main/java/com/huoran/iasf/controller/SysColumnController.java
  5. 309
      src/main/java/com/huoran/iasf/controller/SysFloatingColumnSchemeController.java
  6. 45
      src/main/java/com/huoran/iasf/entity/Seo.java
  7. 76
      src/main/java/com/huoran/iasf/entity/SysFloatingColumnScheme.java
  8. 48
      src/main/java/com/huoran/iasf/entity/SysFloatingColumnSchemeModule.java
  9. 38
      src/main/java/com/huoran/iasf/entity/SysFloatingColumnSchemeScopeOfApplication.java
  10. 16
      src/main/java/com/huoran/iasf/mapper/SeoMapper.java
  11. 24
      src/main/java/com/huoran/iasf/mapper/SysFloatingColumnSchemeMapper.java
  12. 16
      src/main/java/com/huoran/iasf/mapper/SysFloatingColumnSchemeModuleMapper.java
  13. 19
      src/main/java/com/huoran/iasf/mapper/SysFloatingColumnSchemeScopeOfApplicationMapper.java
  14. 51
      src/main/java/com/huoran/iasf/mapper/xml/SysFloatingColumnSchemeMapper.xml
  15. 5
      src/main/java/com/huoran/iasf/mapper/xml/SysFloatingColumnSchemeModuleMapper.xml
  16. 16
      src/main/java/com/huoran/iasf/mapper/xml/SysFloatingColumnSchemeScopeOfApplicationMapper.xml
  17. 16
      src/main/java/com/huoran/iasf/service/SeoService.java
  18. 22
      src/main/java/com/huoran/iasf/service/SysFloatingColumnSchemeModuleService.java
  19. 23
      src/main/java/com/huoran/iasf/service/SysFloatingColumnSchemeScopeOfApplicationService.java
  20. 25
      src/main/java/com/huoran/iasf/service/SysFloatingColumnSchemeService.java
  21. 20
      src/main/java/com/huoran/iasf/service/impl/SeoServiceImpl.java
  22. 36
      src/main/java/com/huoran/iasf/service/impl/SysFloatingColumnSchemeModuleServiceImpl.java
  23. 36
      src/main/java/com/huoran/iasf/service/impl/SysFloatingColumnSchemeScopeOfApplicationServiceImpl.java
  24. 322
      src/main/java/com/huoran/iasf/service/impl/SysFloatingColumnSchemeServiceImpl.java
  25. 7
      src/main/java/com/huoran/iasf/util/ConflictException.java
  26. 59
      src/main/java/com/huoran/iasf/vo/SysFloatingColumnSchemeVO.java
  27. 31
      src/main/java/com/huoran/iasf/vo/req/SuspensionBarListPagingReq.java
  28. 2
      src/test/java/com/company/project/CodeGenerator.java

@ -54,6 +54,8 @@ public enum BaseResponseCode implements ResponseCodeInterface {
ROLE_ERROR(401017, "账号角色被删,请联系管理员添加角色后再试"),
EXCEL_FILE_NULL(40006, "导入失败,导入数据为空!"),
DATA_DUPLICATION(40007, "方案存在重复"),
DATA_DOES_NOT_EXIST(500, "当前数据不存在"),
;

@ -113,4 +113,20 @@ public class R {
}
/**
* 返回警告信息的R对象通常用于前端展示警告但不完全阻止操作的场景
*
* @param warnMsg 警告信息
* @return 包含警告信息的R对象实例
*/
public static R warn(String warnMsg) {
// 这里直接使用字符串信息作为警告,如果您有专门的警告响应码,可以使用如下形式:
// return new R(BaseResponseCode.WARNING_CODE, warnMsg);
// 或者,如果只想传递消息而不改变响应码(保持成功响应码,但附带警告信息):
return new R(300, warnMsg);
}
}

@ -0,0 +1,68 @@
package com.huoran.iasf.controller;
import cn.hutool.core.util.ObjectUtil;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.huoran.iasf.common.utils.R;
import com.huoran.iasf.entity.Seo;
import com.huoran.iasf.service.SeoService;
import io.swagger.annotations.Api;
import io.swagger.annotations.ApiOperation;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.*;
import java.util.List;
/**
* <p>
* 前端控制器
* </p>
*
* @author cheney
* @since 2023-08-24
*/
@Api(tags = "seo管理")
@RestController
@RequestMapping("/seo")
public class SeoController {
@Autowired
private SeoService seoService;
@PostMapping("/add")
@ApiOperation(value = "新增seo")
public R addUserGroup(@RequestBody Seo seo) {
Seo one = seoService.getOne(new QueryWrapper<Seo>().eq("title", seo.getTitle()));
if (ObjectUtil.isNotNull(one)) {
R.fail("seo已存在");
}
boolean save = seoService.save(seo);
return save ? R.success() : R.fail("添加失败");
}
@PostMapping("/delete")
@ApiOperation(value = "删除seo")
public R deleted(@RequestParam Integer id) {
boolean remove = seoService.removeById(id);
return remove ? R.success() : R.fail("删除失败");
}
@PostMapping("/update")
@ApiOperation(value = "更新seo")
public R update(@RequestBody Seo seo) {
boolean update = seoService.updateById(seo);
return update ? R.success() : R.fail("更新失败");
}
@GetMapping("/list")
@ApiOperation(value = "站点seo列表")
public R list(@RequestParam Integer siteId) {
QueryWrapper<Seo> queryWrapper = new QueryWrapper<>();
queryWrapper.eq("site_id", siteId);
List<Seo> list = seoService.list(queryWrapper);
return R.success(list);
}
}

@ -112,6 +112,18 @@ public class SysColumnController {
return updateState ? R.success() : R.fail("编辑失败");
}
@PostMapping("/controlDisplayNavigationMenu")
@ApiOperation(value = "控制显示导航菜单", response = SysColumn.class)
public R controlDisplayNavigationMenu(@ApiParam(name = "id", value = "主键", required = true) @RequestParam Integer id,
@ApiParam(name = "menuVisible", value = "菜单是否可见(默认0可见 1不可见)", required = true) @RequestParam Integer menuVisible) {
SysColumn column = new SysColumn();
column.setId(id);
column.setMenuVisible(menuVisible);//菜单是否可见(默认0可见 1不可见)
boolean updateState = service.updateById(column);
return updateState ? R.success() : R.fail("编辑失败");
}
/*@NoRepeatSubmit
@PostMapping("/delete")
@ApiOperation(value = "删除", response = SysContent.class)

@ -0,0 +1,309 @@
package com.huoran.iasf.controller;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.baomidou.mybatisplus.core.conditions.update.UpdateWrapper;
import com.huoran.iasf.common.exception.BusinessException;
import com.huoran.iasf.common.exception.code.BaseResponseCode;
import com.huoran.iasf.common.utils.R;
import com.huoran.iasf.entity.SysFloatingColumnScheme;
import com.huoran.iasf.entity.SysFloatingColumnSchemeModule;
import com.huoran.iasf.entity.SysFloatingColumnSchemeScopeOfApplication;
import com.huoran.iasf.service.SysFloatingColumnSchemeModuleService;
import com.huoran.iasf.service.SysFloatingColumnSchemeScopeOfApplicationService;
import com.huoran.iasf.service.SysFloatingColumnSchemeService;
import com.huoran.iasf.vo.SysFloatingColumnSchemeVO;
import com.huoran.iasf.vo.req.SuspensionBarListPagingReq;
import io.swagger.annotations.Api;
import io.swagger.annotations.ApiOperation;
import io.swagger.annotations.ApiParam;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.*;
import java.util.HashSet;
import java.util.List;
import java.util.Set;
/**
* @描述悬浮栏方案控制类
* @作者: Rong
* @日期: 2024-06-04
*/
@RestController
@RequestMapping("/SysFloatingColumnSchemeService/SysFloatingColumnScheme")
@Api(value = "悬浮栏相关接口:SysFloatingColumnSchemeController", tags = "悬浮栏方案:悬浮栏相关接口")
public class SysFloatingColumnSchemeController {
@Autowired
public SysFloatingColumnSchemeService service;
@Autowired
public SysFloatingColumnSchemeScopeOfApplicationService floatingColumnSchemeScopeOfApplicationService;
@Autowired
public SysFloatingColumnSchemeModuleService floatingColumnSchemeModuleService;
/**
* 保存或更新悬浮栏方案记录
* 如果ID为空则执行保存操作如果ID有值则视为更新操作
*
* @param sysFloatingColumnScheme 要保存或更新的悬浮栏方案对象
* @return R 结果对象包含操作状态信息
*/
@PostMapping("/saveOrUpdate")
@ApiOperation(value = "保存或更新悬浮栏方案记录", response = SysFloatingColumnScheme.class)
public R saveOrUpdate(@RequestBody @ApiParam(name = "悬浮栏方案对象", value = "包含悬浮栏方案详细信息,若id不存在则新建,否则视为更新", required = true) SysFloatingColumnScheme sysFloatingColumnScheme) {
// 校验集合内是否有重复的schemeTitle
Set<String> schemeTitles = new HashSet<>();
for (SysFloatingColumnSchemeModule module : sysFloatingColumnScheme.getFloatingColumnSchemeModules()) {
if (!schemeTitles.add(module.getSchemeTitle())) {
// throw new IllegalArgumentException(module.getSchemeTitle() + " 标题已存在");
String msg = module.getSchemeTitle() + " 标题已存在";
/*throw new RuntimeException(msg);*/
return R.fail(msg);
}
}
// 新增场景下直接进行校验
if (sysFloatingColumnScheme.getId() == null) {
if (checkSchemeName(sysFloatingColumnScheme.getSchemeName(), sysFloatingColumnScheme.getSiteId())) {
return R.fail("该站点下已存在相同的悬浮栏方案名称");
}
}
// 编辑场景下,只有当名称发生改变时才进行校验,并排除当前记录自身
else if (!sysFloatingColumnScheme.getSchemeName().equals(service.getById(sysFloatingColumnScheme.getId()).getSchemeName())) {
if (checkSchemeNameExceptSelf(sysFloatingColumnScheme.getSchemeName(), sysFloatingColumnScheme.getSiteId(), sysFloatingColumnScheme.getId())) {
return R.fail("该站点下已存在相同的悬浮栏方案名称");
}
}
//获取floatingColumnSchemeScopeOfApplications中的范围判断是不是0,如果包含为0
List<SysFloatingColumnSchemeScopeOfApplication> floatingColumnSchemeScopeOfApplications = sysFloatingColumnScheme.getFloatingColumnSchemeScopeOfApplications();
for (SysFloatingColumnSchemeScopeOfApplication floatingColumnSchemeScopeOfApplication : floatingColumnSchemeScopeOfApplications) {
if (floatingColumnSchemeScopeOfApplication.getApplicationScopeId().equals("0")) {
sysFloatingColumnScheme.setIsGlobal(1);
} else {
sysFloatingColumnScheme.setIsGlobal(0);
}
}
// 处理全局悬浮栏逻辑
if (sysFloatingColumnScheme.getIsGlobal() == 1) {
// 确保没有其他全局悬浮栏同时启用
long globalCount = service.count(new QueryWrapper<SysFloatingColumnScheme>().eq("is_global", true).eq("is_disable", 0).ne("id", sysFloatingColumnScheme.getId()));
if (globalCount > 0) {
return R.fail("已经有全局悬浮栏启用,请先禁用后再尝试设置");
}
}
boolean result = false;
try {
if (sysFloatingColumnScheme.getId() == null) {
// 保存操作
result = service.save(sysFloatingColumnScheme);
} else {
// 更新操作
result = service.updateById(sysFloatingColumnScheme);
}
} catch (Exception e) {
return R.fail("操作失败");
}
if (!result) {
return R.fail("操作失败");
}
//删除原有的方案和范围关系
floatingColumnSchemeModuleService.deleteByFloatingBarSchemeId(sysFloatingColumnScheme.getId());
floatingColumnSchemeScopeOfApplicationService.deleteByFloatingBarSchemeId(sysFloatingColumnScheme.getId());
// 保持原有的模块和范围处理逻辑
handleFloatingColumnSchemeModules(sysFloatingColumnScheme);
handleFloatingColumnSchemeScopeOfApplications(sysFloatingColumnScheme);
return R.success();
}
@PostMapping("/columnDisplayFloatingBar")
@ApiOperation(value = "根据栏目展示悬浮栏", response = SysFloatingColumnSchemeVO.class)
public R columnDisplayFloatingBar(@ApiParam(name = "columnId", value = "栏目id", required = true) @RequestParam String columnId) {
return service.columnDisplayFloatingBar(columnId);
}
@PostMapping("/floatingBarList")
@ApiOperation(value = "悬浮栏列表", response = SysFloatingColumnSchemeVO.class)
public R floatingBarList(@RequestBody SuspensionBarListPagingReq sysFloatingColumnScheme) {
return service.floatingBarList(sysFloatingColumnScheme);
}
/**
* * 1.应用全部权限最高只要是启用应用全部的除了一开始没有启用悬浮栏的都弹窗提示当前已启用了的悬浮栏方案将会被取消
* 2.启用了应用全部的后面要启用部分的提示先禁用应用全部的
* 3.部分启用vs部分启用且有重合的提示移除重合的
*/
@PostMapping("/enableOrDisableScheme")
@ApiOperation(value = "启用或禁用", response = SysFloatingColumnSchemeVO.class)
public R enableOrDisableScheme(@ApiParam(name = "id", value = "主键", required = true) @RequestParam Integer id, @ApiParam(name = "isDisable", value = "是否禁用(0启用 1禁用)", required = true) @RequestParam Integer isDisable) {
/* return service.enableOrDisableScheme(id, isDisable);*/
//禁启用操作
SysFloatingColumnScheme sysFloatingColumnScheme = service.getById(id);
sysFloatingColumnScheme.setIsDisable(isDisable);
boolean operation = service.updateById(sysFloatingColumnScheme);
//增加判断如果当前的应用权限如果为全部,需要将当前站点下其余已经启用的给禁用了
if (sysFloatingColumnScheme.getIsDisable() == 0 && sysFloatingColumnScheme.getIsGlobal() == 1) {
UpdateWrapper<SysFloatingColumnScheme> updateWrapper = new UpdateWrapper<>();
updateWrapper.set("is_disable", 1);
updateWrapper.eq("is_disable", 0);
updateWrapper.eq("site_id", sysFloatingColumnScheme.getSiteId());
updateWrapper.ne("id", id);
service.update(updateWrapper);
}
return operation ? R.success() : R.fail("操作失败");
}
@PostMapping("/checkEnableOrDisable")
@ApiOperation(value = "检查“启用”或“禁用”()", response = SysFloatingColumnSchemeVO.class)
public R checkEnableOrDisable(@ApiParam(name = "id", value = "主键", required = true) @RequestParam Integer id, @ApiParam(name = "isDisable", value = "是否禁用(0启用 1禁用)", required = true) @RequestParam Integer isDisable) {
return service.checkEnableOrDisable(id, isDisable);
}
@PostMapping("/findById")
@ApiOperation(value = "查询详情", response = SysFloatingColumnScheme.class)
public R findById(@ApiParam(name = "id", value = "主键", required = true) @RequestParam Integer id) {
SysFloatingColumnScheme sysFloatingColumnScheme = service.getById(id);
List<SysFloatingColumnSchemeScopeOfApplication> sysFloatingColumnSchemeScopeOfApplications = floatingColumnSchemeScopeOfApplicationService.getScopeOfApplicationByFloatingBarSchemeId(id);
List<SysFloatingColumnSchemeModule> getModuleByFloatingBarSchemeId = floatingColumnSchemeModuleService.getModuleByFloatingBarSchemeId(id);
sysFloatingColumnScheme.setFloatingColumnSchemeScopeOfApplications(sysFloatingColumnSchemeScopeOfApplications);
sysFloatingColumnScheme.setFloatingColumnSchemeModules(getModuleByFloatingBarSchemeId);
return R.success(sysFloatingColumnScheme);
}
@PostMapping("/batchDeletion")
@ApiOperation(value = "批量删除悬浮栏数据", response = SysFloatingColumnScheme.class)
public R batchDeletion(@ApiParam(name = "id", value = "主键", required = true) @RequestParam List<Integer> id) {
boolean delState = service.removeByIds(id);
//删除的同时将悬浮栏方案以及悬浮栏应用范围
if (delState) {
for (Integer removeId : id) {
LambdaQueryWrapper<SysFloatingColumnSchemeModule> queryWrapper = new LambdaQueryWrapper<>();
queryWrapper.eq(SysFloatingColumnSchemeModule::getFloatingBarSchemeId, removeId);
floatingColumnSchemeModuleService.remove(queryWrapper);
LambdaQueryWrapper<SysFloatingColumnSchemeScopeOfApplication> queryWrapper1 = new LambdaQueryWrapper<>();
queryWrapper1.eq(SysFloatingColumnSchemeScopeOfApplication::getFloatingBarSchemeId, removeId);
floatingColumnSchemeScopeOfApplicationService.remove(queryWrapper1);
}
}
return R.success();
}
@PostMapping("/batchDeletionScheme")
@ApiOperation(value = "批量删除方案", response = SysFloatingColumnSchemeModule.class)
public R batchDeletionScheme(@ApiParam(name = "id", value = "主键", required = true) @RequestParam List<Integer> id) {
boolean delState = floatingColumnSchemeModuleService.removeByIds(id);
return delState ? R.success() : R.fail("删除失败");
}
@PostMapping("/batchDeleteRange")
@ApiOperation(value = "批量删除应用范围", response = SysFloatingColumnSchemeScopeOfApplication.class)
public R batchDeleteRange(@ApiParam(name = "id", value = "主键", required = true) @RequestParam List<Integer> id) {
boolean delState = floatingColumnSchemeScopeOfApplicationService.removeByIds(id);
return delState ? R.success() : R.fail("删除失败");
}
private void handleFloatingColumnSchemeModules(SysFloatingColumnScheme sysFloatingColumnScheme) {
/*// 校验集合内是否有重复的schemeTitle
Set<String> schemeTitles = new HashSet<>();
for (SysFloatingColumnSchemeModule module : sysFloatingColumnScheme.getFloatingColumnSchemeModules()) {
if (!schemeTitles.add(module.getSchemeTitle())) {
// throw new IllegalArgumentException(module.getSchemeTitle() + " 标题已存在");
String msg = module.getSchemeTitle() + " 标题已存在";
throw new RuntimeException(msg);
}
}*/
if (sysFloatingColumnScheme.getFloatingColumnSchemeModules() != null && !sysFloatingColumnScheme.getFloatingColumnSchemeModules().isEmpty()) {
for (SysFloatingColumnSchemeModule module : sysFloatingColumnScheme.getFloatingColumnSchemeModules()) {
module.setFloatingBarSchemeId(sysFloatingColumnScheme.getId()); // 确保模块关联到当前方案
if (sysFloatingColumnScheme.getId() == null) {
// 如果悬浮栏方案是新建的,直接保存模块(假设模块没有独立的ID生成策略)
floatingColumnSchemeModuleService.save(module);
} else {
// 如果悬浮栏方案是更新的,根据情况更新或保存模块
floatingColumnSchemeModuleService.saveOrUpdate(module);
}
}
}
}
private void handleFloatingColumnSchemeScopeOfApplications(SysFloatingColumnScheme sysFloatingColumnScheme) {
if (sysFloatingColumnScheme.getFloatingColumnSchemeScopeOfApplications() != null && !sysFloatingColumnScheme.getFloatingColumnSchemeScopeOfApplications().isEmpty()) {
for (SysFloatingColumnSchemeScopeOfApplication scope : sysFloatingColumnScheme.getFloatingColumnSchemeScopeOfApplications()) {
scope.setFloatingBarSchemeId(sysFloatingColumnScheme.getId());
if (sysFloatingColumnScheme.getId() == null) {
// 如果悬浮栏方案是新建的,直接保存范围
floatingColumnSchemeScopeOfApplicationService.save(scope);
} else {
// 如果悬浮栏方案是更新的,根据情况更新或保存范围
floatingColumnSchemeScopeOfApplicationService.saveOrUpdate(scope);
}
}
}
}
// 根据站点校验方案名称,排除当前ID记录
private boolean checkSchemeNameExceptSelf(String schemeName, Integer siteId, Integer id) {
QueryWrapper<SysFloatingColumnScheme> queryWrapper = new QueryWrapper<>();
queryWrapper.eq("scheme_name", schemeName);
queryWrapper.eq("site_id", siteId);
// 添加条件,排除当前ID的记录
if (id != null) {
queryWrapper.ne("id", id);
}
return service.count(queryWrapper) > 0;
}
// 现在仅用于新增场景或编辑时名称变更的校验,不需排除自身ID
private boolean checkSchemeName(String schemeName, Integer siteId) {
QueryWrapper<SysFloatingColumnScheme> queryWrapper = new QueryWrapper<>();
queryWrapper.eq("scheme_name", schemeName);
queryWrapper.eq("site_id", siteId);
return service.count(queryWrapper) > 0;
}
}

@ -0,0 +1,45 @@
package com.huoran.iasf.entity;
import com.baomidou.mybatisplus.annotation.IdType;
import com.baomidou.mybatisplus.annotation.TableId;
import com.baomidou.mybatisplus.annotation.TableName;
import io.swagger.annotations.ApiModel;
import io.swagger.annotations.ApiModelProperty;
import lombok.Data;
import lombok.EqualsAndHashCode;
import java.io.Serializable;
/**
* <p>
*
* </p>
*
* @author cheney
* @since 2023-08-24
*/
@Data
@EqualsAndHashCode(callSuper = false)
@TableName("sys_seo")
@ApiModel(value = "Seo对象", description = "")
public class Seo implements Serializable {
private static final long serialVersionUID = 1L;
@ApiModelProperty(value = "主键")
@TableId(value = "id", type = IdType.AUTO)
private Integer id;
@ApiModelProperty(value = "标题")
private String title;
@ApiModelProperty(value = "关键词")
private String keyword;
@ApiModelProperty(value = "描述")
private String description;
@ApiModelProperty(value = "站点")
private Integer siteId;
}

@ -0,0 +1,76 @@
package com.huoran.iasf.entity;
import com.baomidou.mybatisplus.annotation.FieldFill;
import com.baomidou.mybatisplus.annotation.IdType;
import com.baomidou.mybatisplus.annotation.TableField;
import com.baomidou.mybatisplus.annotation.TableId;
import io.swagger.annotations.ApiModel;
import io.swagger.annotations.ApiModelProperty;
import lombok.Data;
import lombok.EqualsAndHashCode;
import java.io.Serializable;
import java.util.Date;
import java.util.List;
/**
* <p>
* 悬浮栏方案
* </p>
*
* @author cheney
* @since 2024-06-04
*/
@Data
@EqualsAndHashCode(callSuper = false)
@ApiModel(value = "SysFloatingColumnScheme对象", description = "悬浮栏方案")
public class SysFloatingColumnScheme implements Serializable {
private static final long serialVersionUID = 1L;
@ApiModelProperty(value = "主键")
@TableId(value = "id", type = IdType.AUTO)
private Integer id;
@ApiModelProperty(value = "悬浮栏方案名称")
private String schemeName;
@ApiModelProperty(value = "状态(0默认草稿箱 1为已发布)")
private Integer status;
@ApiModelProperty(value = "悬浮栏样式id(关联样式表id)")
private Integer floatingBarStyle;
@ApiModelProperty(value = "是否禁用(默认1不启用,0启用 1禁用)")
private Integer isDisable;
@ApiModelProperty(value = "站点id")
private Integer siteId;
@ApiModelProperty(value = "创建人id")
private Integer founderId;
@ApiModelProperty(value = "编辑人id")
private Integer editorId;
@ApiModelProperty(value = "创建时间")
@TableField(fill = FieldFill.INSERT)
private Date createTime;
@ApiModelProperty(value = "更新时间")
@TableField(fill = FieldFill.INSERT_UPDATE)
private Date updateTime;
@ApiModelProperty(value = "表示是否为全局应用,便于快速判断是否存在全局悬浮栏,0表示不是全局悬浮栏,1表示是全局悬浮栏")
private Integer isGlobal;
@ApiModelProperty(value = "悬浮栏方案模块")
@TableField(exist = false)
private List<SysFloatingColumnSchemeModule> floatingColumnSchemeModules;
@ApiModelProperty(value = "悬浮栏方案范围")
@TableField(exist = false)
private List<SysFloatingColumnSchemeScopeOfApplication> floatingColumnSchemeScopeOfApplications;
}

@ -0,0 +1,48 @@
package com.huoran.iasf.entity;
import com.baomidou.mybatisplus.annotation.IdType;
import com.baomidou.mybatisplus.annotation.TableId;
import java.io.Serializable;
import io.swagger.annotations.ApiModel;
import io.swagger.annotations.ApiModelProperty;
import lombok.Data;
import lombok.EqualsAndHashCode;
/**
* <p>
* 悬浮栏方案设置
* </p>
*
* @author cheney
* @since 2024-06-04
*/
@Data
@EqualsAndHashCode(callSuper = false)
@ApiModel(value = "SysFloatingColumnSchemeModule对象", description = "悬浮栏方案设置")
public class SysFloatingColumnSchemeModule implements Serializable {
private static final long serialVersionUID = 1L;
@ApiModelProperty(value = "主键")
@TableId(value = "id", type = IdType.AUTO)
private Integer id;
@ApiModelProperty(value = "悬浮栏方案id")
private Integer floatingBarSchemeId;
@ApiModelProperty(value = "图片地址")
private String pictureAddress;
@ApiModelProperty(value = "方案标题")
private String schemeTitle;
@ApiModelProperty(value = "方案内容(json)")
private String schemeContentJson;
@ApiModelProperty(value = "是否禁用(0默认,0启用 1禁用)")
private Integer isDisable;
}

@ -0,0 +1,38 @@
package com.huoran.iasf.entity;
import com.baomidou.mybatisplus.annotation.IdType;
import com.baomidou.mybatisplus.annotation.TableId;
import io.swagger.annotations.ApiModel;
import io.swagger.annotations.ApiModelProperty;
import lombok.Data;
import lombok.EqualsAndHashCode;
import java.io.Serializable;
/**
* <p>
* 悬浮栏应用范围
* </p>
*
* @author cheney
* @since 2024-06-04
*/
@Data
@EqualsAndHashCode(callSuper = false)
@ApiModel(value = "SysFloatingColumnSchemeScopeOfApplication对象", description = "悬浮栏应用范围")
public class SysFloatingColumnSchemeScopeOfApplication implements Serializable {
private static final long serialVersionUID = 1L;
@ApiModelProperty(value = "主键")
@TableId(value = "id", type = IdType.AUTO)
private Integer id;
@ApiModelProperty(value = "悬浮栏方案id")
private Integer floatingBarSchemeId;
@ApiModelProperty(value = "应用范围id(为0表示网站全局,其余为栏目表主键),如果为父级子级栏目一起选中,则显示为多个,以逗号隔开:1,3,45,49")
private String applicationScopeId;
}

@ -0,0 +1,16 @@
package com.huoran.iasf.mapper;
import com.baomidou.mybatisplus.core.mapper.BaseMapper;
import com.huoran.iasf.entity.Seo;
/**
* <p>
* Mapper 接口
* </p>
*
* @author cheney
* @since 2023-08-24
*/
public interface SeoMapper extends BaseMapper<Seo> {
}

@ -0,0 +1,24 @@
package com.huoran.iasf.mapper;
import com.baomidou.mybatisplus.core.metadata.IPage;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.huoran.iasf.entity.SysFloatingColumnScheme;
import com.baomidou.mybatisplus.core.mapper.BaseMapper;
import com.huoran.iasf.vo.SysFloatingColumnSchemeVO;
import com.huoran.iasf.vo.req.PageContentReqVO;
import com.huoran.iasf.vo.req.SuspensionBarListPagingReq;
import com.huoran.iasf.vo.resp.PageContentRespVO;
import org.apache.ibatis.annotations.Param;
/**
* <p>
* 悬浮栏方案 Mapper 接口
* </p>
*
* @author cheney
* @since 2024-06-04
*/
public interface SysFloatingColumnSchemeMapper extends BaseMapper<SysFloatingColumnScheme> {
IPage<SysFloatingColumnSchemeVO> floatingBarList(Page<SysFloatingColumnSchemeVO> page, @Param("req") SuspensionBarListPagingReq req);
}

@ -0,0 +1,16 @@
package com.huoran.iasf.mapper;
import com.huoran.iasf.entity.SysFloatingColumnSchemeModule;
import com.baomidou.mybatisplus.core.mapper.BaseMapper;
/**
* <p>
* 悬浮栏方案设置 Mapper 接口
* </p>
*
* @author cheney
* @since 2024-06-04
*/
public interface SysFloatingColumnSchemeModuleMapper extends BaseMapper<SysFloatingColumnSchemeModule> {
}

@ -0,0 +1,19 @@
package com.huoran.iasf.mapper;
import com.baomidou.mybatisplus.core.mapper.BaseMapper;
import com.huoran.iasf.entity.SysFloatingColumnSchemeScopeOfApplication;
import org.apache.ibatis.annotations.Param;
import java.util.List;
/**
* <p>
* 悬浮栏应用范围 Mapper 接口
* </p>
*
* @author cheney
* @since 2024-06-04
*/
public interface SysFloatingColumnSchemeScopeOfApplicationMapper extends BaseMapper<SysFloatingColumnSchemeScopeOfApplication> {
List<Integer> checkBoundByColumnId(@Param("columnId") String columnId);
}

@ -0,0 +1,51 @@
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE mapper PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN" "http://mybatis.org/dtd/mybatis-3-mapper.dtd">
<mapper namespace="com.huoran.iasf.mapper.SysFloatingColumnSchemeMapper">
<select id="floatingBarList" resultType="com.huoran.iasf.vo.SysFloatingColumnSchemeVO">
SELECT
s.id AS floatingBarSchemeId,
s.*,
GROUP_CONCAT(
DISTINCT
CASE
WHEN scsa.application_scope_id = '0' THEN '应用至全部'
ELSE (
SELECT GROUP_CONCAT(column_name SEPARATOR ', ')
FROM sys_column
WHERE FIND_IN_SET(id, REPLACE(scsa.application_scope_id, ',', ',')) > 0
)
END
ORDER BY
scsa.application_scope_id ASC
SEPARATOR ', '
) AS scopeOfApplication,
CONCAT(
COALESCE(
(SELECT COUNT(*) FROM sys_floating_column_scheme_module WHERE floating_bar_scheme_id = s.id),
0
),
'个'
) AS numberOfContentModules,
u.username AS editorSName
FROM
sys_floating_column_scheme s
INNER JOIN
sys_user u ON u.id = s.editor_id
LEFT JOIN
sys_floating_column_scheme_scope_of_application scsa ON s.id = scsa.floating_bar_scheme_id
WHERE
1=1
<if test="req.siteId != null">
AND s.site_id = #{req.siteId}
</if>
<if test="req.search != null and req.search != ''">
AND s.scheme_name LIKE CONCAT('%', #{req.search}, '%')
</if>
GROUP BY
s.id
ORDER BY
s.id DESC
</select>
</mapper>

@ -0,0 +1,5 @@
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE mapper PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN" "http://mybatis.org/dtd/mybatis-3-mapper.dtd">
<mapper namespace="com.huoran.iasf.mapper.SysFloatingColumnSchemeModuleMapper">
</mapper>

@ -0,0 +1,16 @@
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE mapper PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN" "http://mybatis.org/dtd/mybatis-3-mapper.dtd">
<mapper namespace="com.huoran.iasf.mapper.SysFloatingColumnSchemeScopeOfApplicationMapper">
<select id="checkBoundByColumnId" resultType="java.lang.Integer">
SELECT
floating_bar_scheme_id
FROM
sys_floating_column_scheme_scope_of_application
WHERE
FIND_IN_SET( application_scope_id, #{columnId} )
group by
floating_bar_scheme_id
</select>
</mapper>

@ -0,0 +1,16 @@
package com.huoran.iasf.service;
import com.baomidou.mybatisplus.extension.service.IService;
import com.huoran.iasf.entity.Seo;
/**
* <p>
* 服务类
* </p>
*
* @author cheney
* @since 2023-08-24
*/
public interface SeoService extends IService<Seo> {
}

@ -0,0 +1,22 @@
package com.huoran.iasf.service;
import com.baomidou.mybatisplus.extension.service.IService;
import com.huoran.iasf.entity.SysFloatingColumnSchemeModule;
import java.util.List;
/**
* <p>
* 悬浮栏方案设置 服务类
* </p>
*
* @author cheney
* @since 2024-06-04
*/
public interface SysFloatingColumnSchemeModuleService extends IService<SysFloatingColumnSchemeModule> {
//根据floatingBarSchemeId查询方案列表
List<SysFloatingColumnSchemeModule> getModuleByFloatingBarSchemeId(Integer floatingBarSchemeId);
//删除
void deleteByFloatingBarSchemeId(Integer floatingBarSchemeId);
}

@ -0,0 +1,23 @@
package com.huoran.iasf.service;
import com.huoran.iasf.entity.SysFloatingColumnSchemeScopeOfApplication;
import com.baomidou.mybatisplus.extension.service.IService;
import java.util.List;
/**
* <p>
* 悬浮栏应用范围 服务类
* </p>
*
* @author cheney
* @since 2024-06-04
*/
public interface SysFloatingColumnSchemeScopeOfApplicationService extends IService<SysFloatingColumnSchemeScopeOfApplication> {
//根据floatingBarSchemeId获取应用范围列表
List<SysFloatingColumnSchemeScopeOfApplication> getScopeOfApplicationByFloatingBarSchemeId(Integer floatingBarSchemeId);
//删除
void deleteByFloatingBarSchemeId(Integer floatingBarSchemeId);
}

@ -0,0 +1,25 @@
package com.huoran.iasf.service;
import com.huoran.iasf.common.utils.R;
import com.huoran.iasf.entity.SysFloatingColumnScheme;
import com.baomidou.mybatisplus.extension.service.IService;
import com.huoran.iasf.vo.req.SuspensionBarListPagingReq;
/**
* <p>
* 悬浮栏方案 服务类
* </p>
*
* @author cheney
* @since 2024-06-04
*/
public interface SysFloatingColumnSchemeService extends IService<SysFloatingColumnScheme> {
R floatingBarList(SuspensionBarListPagingReq req);
R enableOrDisableScheme(Integer schemeId, Integer enable);
R checkEnableOrDisable(Integer schemeId, Integer enable);
R columnDisplayFloatingBar(String columnId);
}

@ -0,0 +1,20 @@
package com.huoran.iasf.service.impl;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.huoran.iasf.entity.Seo;
import com.huoran.iasf.mapper.SeoMapper;
import com.huoran.iasf.service.SeoService;
import org.springframework.stereotype.Service;
/**
* <p>
* 服务实现类
* </p>
*
* @author cheney
* @since 2023-08-24
*/
@Service
public class SeoServiceImpl extends ServiceImpl<SeoMapper, Seo> implements SeoService {
}

@ -0,0 +1,36 @@
package com.huoran.iasf.service.impl;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.huoran.iasf.entity.SysFloatingColumnSchemeModule;
import com.huoran.iasf.mapper.SysFloatingColumnSchemeModuleMapper;
import com.huoran.iasf.service.SysFloatingColumnSchemeModuleService;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import org.springframework.stereotype.Service;
import java.util.List;
/**
* <p>
* 悬浮栏方案设置 服务实现类
* </p>
*
* @author cheney
* @since 2024-06-04
*/
@Service
public class SysFloatingColumnSchemeModuleServiceImpl extends ServiceImpl<SysFloatingColumnSchemeModuleMapper, SysFloatingColumnSchemeModule> implements SysFloatingColumnSchemeModuleService {
@Override
public List<SysFloatingColumnSchemeModule> getModuleByFloatingBarSchemeId(Integer floatingBarSchemeId) {
QueryWrapper<SysFloatingColumnSchemeModule> queryWrapper = new QueryWrapper<>();
queryWrapper.lambda().eq(SysFloatingColumnSchemeModule::getFloatingBarSchemeId, floatingBarSchemeId);
return list(queryWrapper);
}
@Override
public void deleteByFloatingBarSchemeId(Integer floatingBarSchemeId) {
QueryWrapper<SysFloatingColumnSchemeModule> queryWrapper = new QueryWrapper<>();
queryWrapper.lambda().eq(SysFloatingColumnSchemeModule::getFloatingBarSchemeId, floatingBarSchemeId);
remove(queryWrapper);
}
}

@ -0,0 +1,36 @@
package com.huoran.iasf.service.impl;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.huoran.iasf.entity.SysFloatingColumnSchemeScopeOfApplication;
import com.huoran.iasf.mapper.SysFloatingColumnSchemeScopeOfApplicationMapper;
import com.huoran.iasf.service.SysFloatingColumnSchemeScopeOfApplicationService;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import org.springframework.stereotype.Service;
import java.util.List;
/**
* <p>
* 悬浮栏应用范围 服务实现类
* </p>
*
* @author cheney
* @since 2024-06-04
*/
@Service
public class SysFloatingColumnSchemeScopeOfApplicationServiceImpl extends ServiceImpl<SysFloatingColumnSchemeScopeOfApplicationMapper, SysFloatingColumnSchemeScopeOfApplication> implements SysFloatingColumnSchemeScopeOfApplicationService {
@Override
public List<SysFloatingColumnSchemeScopeOfApplication> getScopeOfApplicationByFloatingBarSchemeId(Integer floatingBarSchemeId) {
QueryWrapper<SysFloatingColumnSchemeScopeOfApplication> queryWrapper = new QueryWrapper<>();
queryWrapper.eq("floating_bar_scheme_id", floatingBarSchemeId);
return this.list(queryWrapper);
}
@Override
public void deleteByFloatingBarSchemeId(Integer floatingBarSchemeId) {
QueryWrapper<SysFloatingColumnSchemeScopeOfApplication> queryWrapper = new QueryWrapper<>();
queryWrapper.eq("floating_bar_scheme_id", floatingBarSchemeId);
this.remove(queryWrapper);
}
}

@ -0,0 +1,322 @@
package com.huoran.iasf.service.impl;
import cn.hutool.core.util.ObjectUtil;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.baomidou.mybatisplus.core.metadata.IPage;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.huoran.iasf.common.utils.R;
import com.huoran.iasf.entity.SysColumn;
import com.huoran.iasf.entity.SysFloatingColumnScheme;
import com.huoran.iasf.entity.SysFloatingColumnSchemeModule;
import com.huoran.iasf.entity.SysFloatingColumnSchemeScopeOfApplication;
import com.huoran.iasf.mapper.SysColumnMapper;
import com.huoran.iasf.mapper.SysFloatingColumnSchemeMapper;
import com.huoran.iasf.mapper.SysFloatingColumnSchemeModuleMapper;
import com.huoran.iasf.mapper.SysFloatingColumnSchemeScopeOfApplicationMapper;
import com.huoran.iasf.service.SysFloatingColumnSchemeService;
import com.huoran.iasf.vo.SysFloatingColumnSchemeVO;
import com.huoran.iasf.vo.req.SuspensionBarListPagingReq;
import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;
import javax.annotation.Resource;
import java.util.*;
import java.util.stream.Collectors;
/**
* <p>
* 悬浮栏方案 服务实现类
* </p>
*
* @author cheney
* @since 2024-06-04
*/
@Service
public class SysFloatingColumnSchemeServiceImpl extends ServiceImpl<SysFloatingColumnSchemeMapper, SysFloatingColumnScheme> implements SysFloatingColumnSchemeService {
@Resource
private SysFloatingColumnSchemeMapper floatingColumnSchemeMapper;
@Autowired
public SysFloatingColumnSchemeScopeOfApplicationMapper scopeOfApplicationMapper;
@Autowired
public SysFloatingColumnSchemeModuleMapper floatingColumnSchemeModuleMapper;
@Autowired
public SysColumnMapper columnMapper;
private Log logger = LogFactory.getLog(getClass());
@Override
public R floatingBarList(SuspensionBarListPagingReq reqVO) {
Page<SysFloatingColumnSchemeVO> page = new Page<SysFloatingColumnSchemeVO>(reqVO.getPageNum(), reqVO.getPageSize());
IPage<SysFloatingColumnSchemeVO> pageList = baseMapper.floatingBarList(page, reqVO);
return R.success(pageList);
}
/**
* isGlobal为1表示应用全部的意思为1表示部分应用(表示是否为全局应用便于快速判断是否存在全局悬浮栏,0表示不是全局悬浮栏1表示是全局悬浮栏)
* <p>
* <p>
* <p>
* 应用全部权限最高
* 1.只要是启用应用全部的除了没有启用的悬浮栏,包含全部不论是应用全部还是部分应用的情况下,都会弹窗提示:"当前已启用了的悬浮栏方案将会被取消!"
* 2.如果当前操作的悬浮栏是要为启用状态且当前的悬浮栏应用类型为为部分应用的情况下下需要判断当前站点下是否存在已经启用了应用全部的如果存在则弹窗提示:"当前已启用全局悬浮栏,无法启用部分应用的悬浮栏,请先禁用全局悬浮栏!"
* 3.部分启用vs部分启用且有重合的提示"当前选择的栏目范围与已启用的悬浮栏方案有冲突,请移除冲突的栏目后再试:{后边展示的是冲突的栏目名称}"
*
* @param schemeId 悬浮栏目id
* @param enable 是否禁用(0默认0启用 1禁用)
* @return
*/
@Transactional
@Override
public R enableOrDisableScheme(Integer schemeId, Integer enable) {
/* SysFloatingColumnScheme scheme = floatingColumnSchemeMapper.selectById(schemeId);
scheme.setFloatingColumnSchemeScopeOfApplications(scopeOfApplicationMapper.selectList(new QueryWrapper<SysFloatingColumnSchemeScopeOfApplication>().lambda().eq(SysFloatingColumnSchemeScopeOfApplication::getFloatingBarSchemeId, schemeId)));
if (ObjectUtil.isEmpty(scheme)) {
return R.fail("悬浮窗方案不存在");
}
// 获取当前悬浮栏是否为全局应用(1表示全局,0表示非全局)
Integer isGlobal = scheme.getIsGlobal();
// 首先处理启用全局悬浮栏逻辑
if (enable == 0 && isGlobal.equals(1)) {
// 确保没有其他全局悬浮栏已启用
SysFloatingColumnScheme existingGlobal = floatingColumnSchemeMapper.selectOne(new LambdaQueryWrapper<SysFloatingColumnScheme>().eq(SysFloatingColumnScheme::getIsGlobal, 1).eq(SysFloatingColumnScheme::getIsDisable, 0));
if (existingGlobal != null && !Objects.equals(existingGlobal.getId(), schemeId)) {
System.err.println("已有其他全局悬浮栏方案启用,请先禁用它!");
}
}
// 2. 当尝试启用非全局悬浮栏,检查是否与已启用的全局悬浮栏冲突
if (enable == 0) {
SysFloatingColumnScheme globalEnabled = floatingColumnSchemeMapper.selectOne(new LambdaQueryWrapper<SysFloatingColumnScheme>().eq(SysFloatingColumnScheme::getIsGlobal, 1).eq(SysFloatingColumnScheme::getIsDisable, 0));
if (globalEnabled != null) {
System.err.println("当前已启用全局悬浮栏,无法启用部分应用的悬浮栏,请先禁用全局悬浮栏");
}
}
// 3. 部分启用vs部分启用的冲突检查
if (enable == 0) {
List<SysFloatingColumnScheme> activeSchemes = floatingColumnSchemeMapper.selectList(new LambdaQueryWrapper<SysFloatingColumnScheme>().ne(SysFloatingColumnScheme::getId, schemeId).eq(SysFloatingColumnScheme::getIsDisable, 0));
if (!activeSchemes.isEmpty()) {
Set<String> currentScopeIdsSet = new HashSet<>();
for (SysFloatingColumnSchemeScopeOfApplication scope : scheme.getFloatingColumnSchemeScopeOfApplications()) {
currentScopeIdsSet.addAll(Arrays.asList(scope.getApplicationScopeId().split(",")));
}
List<SysFloatingColumnSchemeScopeOfApplication> activeScopes = scopeOfApplicationMapper.selectList(new LambdaQueryWrapper<SysFloatingColumnSchemeScopeOfApplication>().in(SysFloatingColumnSchemeScopeOfApplication::getFloatingBarSchemeId, activeSchemes.stream().map(SysFloatingColumnScheme::getId).collect(Collectors.toList())));
List<String> conflictingScopeIds = activeScopes.stream().flatMap(scope -> Arrays.stream(scope.getApplicationScopeId().split(","))).distinct().filter(currentScopeIdsSet::contains).collect(Collectors.toList());
if (!conflictingScopeIds.isEmpty()) {
//根据获取到的栏目id 通过in查询栏目的名称
List<String> conflictingScopeNames = columnMapper.selectList(new LambdaQueryWrapper<SysColumn>().in(SysColumn::getId, conflictingScopeIds)).stream().map(SysColumn::getColumnName).collect(Collectors.toList());
String columnName = String.join(",", conflictingScopeNames);
System.err.println("当前选择的栏目范围与已启用的悬浮栏方案有冲突,请移除冲突的栏目后再试:" + columnName);
}
}
}
// 更新悬浮栏方案的状态
scheme.setIsDisable(enable);
floatingColumnSchemeMapper.updateById(scheme);
// 如果启用的是全局悬浮栏,需要禁用其他已启用的非全局悬浮栏
if (isGlobal.equals(1) && enable == 0) {
getNonGlobal(schemeId);
}*/
return R.success("操作成功");
}
/**
* 这个方法用来检查是否可以启用或禁用指定悬浮栏方案
* isGlobal为1表示应用全部的意思为1表示部分应用(表示是否为全局应用便于快速判断是否存在全局悬浮栏,0表示不是全局悬浮栏1表示是全局悬浮栏)
* <p>
* --所有操作里面应用全部权限最高
* 1.只要是启用应用全部的除了没有启用的悬浮栏,包含全部不论是应用全部还是部分应用的情况下,都会弹窗提示:"当前已启用了的悬浮栏方案将会被取消!"
* 2.如果当前操作的悬浮栏是要为启用状态且当前的悬浮栏应用类型为为部分应用的情况下下需要判断当前站点下是否存在已经启用了应用全部的如果存在则弹窗提示:"当前已启用全局悬浮栏,无法启用部分应用的悬浮栏,请先禁用全局悬浮栏!"
* 3.部分启用vs部分启用且有重合的提示"当前选择的栏目范围与已启用的悬浮栏方案有冲突,请移除冲突的栏目后再试:{后边展示的是冲突的栏目名称}"
*
* @param schemeId 悬浮栏目id
* @param enable 是否禁用(0启用 1禁用)
* @return 包含操作结果或警告信息的对象
*/
public R checkEnableOrDisable(Integer schemeId, Integer enable) {
SysFloatingColumnScheme scheme = floatingColumnSchemeMapper.selectById(schemeId);
if (scheme == null) {
return R.fail("悬浮窗方案不存在");
}
Integer siteId = scheme.getSiteId();
// 1. 当前操作为启用时,检查逻辑
if (enable == 0) {
// 全局悬浮栏启用逻辑
// 对于启用操作,先检查是否是全局应用
if (scheme.getIsGlobal() == 1) {
// 检查站点下是否存在任何已启用的悬浮栏方案,不论全局还是部分应用
long enabledCount = floatingColumnSchemeMapper.selectCount(new LambdaQueryWrapper<SysFloatingColumnScheme>().eq(SysFloatingColumnScheme::getSiteId, siteId).eq(SysFloatingColumnScheme::getIsDisable, 0));
if (enabledCount > 0) {
// 弹窗提示,表明启用新的全局悬浮栏会覆盖当前已启用的悬浮栏
return R.warn("当前站点已存在启用的悬浮栏方案,启用新方案将会覆盖原有设置,请确认是否继续?");
}
} else { // 非全局悬浮栏启用逻辑
// 检查是否存在启用的全局悬浮栏
if (existsEnabledGlobal(siteId)) {
return R.fail("当前已启用全局悬浮栏,无法直接启用部分应用的悬浮栏,请先禁用全局悬浮栏!");
}
// 检查与其它部分应用悬浮栏的冲突
if (hasOverlapWithOtherEnabled(schemeId, siteId)) {
return R.fail(generateConflictMessage(schemeId, siteId, enable));
}
}
} else if (enable == 1) { // 禁用操作逻辑
// 禁用操作直接允许,无需特殊检查
} else {
return R.fail("无效的操作类型");
}
// 如果没有冲突,直接返回成功提示
return R.success("操作可执行");
}
@Override
public R columnDisplayFloatingBar(String columnId) {
//获取站点
SysColumn column = columnMapper.selectById(columnId);
if (ObjectUtil.isEmpty(column)) {
return R.fail("未找到该栏目");
}
//查询范围应用为栏目的
/* List<SysFloatingColumnSchemeScopeOfApplication> sysFloatingColumnSchemeScopeOfApplications = scopeOfApplicationMapper.selectList(new LambdaQueryWrapper<SysFloatingColumnSchemeScopeOfApplication>()
.eq(SysFloatingColumnSchemeScopeOfApplication::getFloatingBarSchemeId, columnId)
);
*/
//查询栏目绑定过的悬浮栏
List<Integer> sysFloatingColumnSchemeScopeOfApplications = scopeOfApplicationMapper.checkBoundByColumnId(columnId);
List<SysFloatingColumnSchemeModule> columnSchemeModuleList = new ArrayList<>();
for (Integer floatingBarId : sysFloatingColumnSchemeScopeOfApplications) {
//查询启用的悬浮栏
SysFloatingColumnScheme scheme = floatingColumnSchemeMapper.selectById(floatingBarId);
if (!ObjectUtil.isEmpty(scheme)) {
//且为启用状态下才查询绑定的方案
if (scheme.getIsDisable() == 0) {
//查询悬浮栏当前绑定的方案
List<SysFloatingColumnSchemeModule> columnSchemeModule = floatingColumnSchemeModuleMapper.selectList(new LambdaQueryWrapper<SysFloatingColumnSchemeModule>()
.eq(SysFloatingColumnSchemeModule::getFloatingBarSchemeId, scheme.getId()).eq(SysFloatingColumnSchemeModule::getIsDisable, 0));;
if (!ObjectUtil.isEmpty(columnSchemeModule)) {
columnSchemeModuleList.addAll(columnSchemeModule);
}
}
}
}
return R.success(columnSchemeModuleList);
}
// 辅助方法检查站点下是否存在启用的全局悬浮栏
private boolean existsEnabledGlobal(Integer siteId) {
QueryWrapper<SysFloatingColumnScheme> queryWrapper = new QueryWrapper<>();
queryWrapper.eq("is_global", 1);
queryWrapper.eq("is_disable", 0);
queryWrapper.eq("site_id", siteId);
return !floatingColumnSchemeMapper.selectList(queryWrapper).isEmpty();
}
/**
* 检查当前悬浮栏方案与已启用方案是否有重叠
*
* @param schemeId 悬浮栏方案ID
* @return 是否有重叠
*/
private boolean hasOverlapWithOtherEnabled(Integer schemeId, Integer siteId) {
// 获取当前要检查的方案的应用范围
List<SysFloatingColumnSchemeScopeOfApplication> currentScopes = scopeOfApplicationMapper.selectList(new LambdaQueryWrapper<SysFloatingColumnSchemeScopeOfApplication>().eq(SysFloatingColumnSchemeScopeOfApplication::getFloatingBarSchemeId, schemeId));
if (currentScopes.isEmpty()) {
return false; // 当前方案无应用范围,自然无重叠
}
Set<Integer> currentScopeIds = currentScopes.stream().flatMap(scope -> Arrays.stream(scope.getApplicationScopeId().split(","))).map(Integer::parseInt).collect(Collectors.toSet());
// 构造查询条件,确保比较的方案属于同一个站点
String sqlInCondition = "SELECT id FROM sys_floating_column_scheme WHERE is_disable = 0 AND site_id = " + siteId;
// 查询所有启用且ID不等于当前schemeId且属于相同站点的悬浮栏方案的应用范围
List<SysFloatingColumnSchemeScopeOfApplication> enabledScopes = scopeOfApplicationMapper.selectList(new LambdaQueryWrapper<SysFloatingColumnSchemeScopeOfApplication>().ne(SysFloatingColumnSchemeScopeOfApplication::getFloatingBarSchemeId, schemeId).inSql(SysFloatingColumnSchemeScopeOfApplication::getFloatingBarSchemeId, sqlInCondition));
// 检查是否有重叠
for (SysFloatingColumnSchemeScopeOfApplication enabledScope : enabledScopes) {
Set<Integer> enabledScopeIds = Arrays.stream(enabledScope.getApplicationScopeId().split(",")).map(Integer::parseInt).collect(Collectors.toSet());
if (!Collections.disjoint(currentScopeIds, enabledScopeIds)) {
return true; // 存在重叠
}
}
return false; // 无重叠
}
/**
* 生成冲突提示信息展示冲突的栏目名称
*
* @param schemeId 悬浮栏方案ID
* @return 冲突提示信息
*/
private String generateConflictMessage(Integer schemeId, Integer siteId, Integer enableAction) {
// 调用 hasOverlapWithOtherEnabled 确认是否有重叠
if (!hasOverlapWithOtherEnabled(schemeId, siteId)) {
return ""; // 无冲突则返回空字符串
}
// 获取当前方案冲突的范围ID
List<SysFloatingColumnSchemeScopeOfApplication> conflictingScopes = scopeOfApplicationMapper.selectList(new LambdaQueryWrapper<SysFloatingColumnSchemeScopeOfApplication>().eq(SysFloatingColumnSchemeScopeOfApplication::getFloatingBarSchemeId, schemeId));
Set<Integer> conflictScopeIds = conflictingScopes.stream().flatMap(scope -> Arrays.stream(scope.getApplicationScopeId().split(","))).map(Integer::parseInt).collect(Collectors.toSet());
// 查询冲突范围对应的栏目名称
List<String> conflictingScopeNames = columnMapper.selectList(new LambdaQueryWrapper<SysColumn>().in(SysColumn::getId, conflictScopeIds)).stream().map(SysColumn::getColumnName).collect(Collectors.toList());
// 根据操作类型调整提示信息()
if (enableAction == 0) { // 启用操作
return "“" + String.join("”, “", conflictingScopeNames) + "”栏目已设置有悬浮栏,请移除后再试。。";
} else if (enableAction == 1) { // 禁用操作
return "“" + String.join("”, “", conflictingScopeNames) + "”存在悬浮栏配置冲突,请注意操作可能影响这些栏目的现有悬浮栏设置。";
} else {
return "未知的操作类型";
}
}
// 新增方法:统计当前站点下已启用的全局悬浮栏数量
public Integer countGlobalEnabled(Integer siteId) {
return baseMapper.selectCount(new LambdaQueryWrapper<SysFloatingColumnScheme>().eq(SysFloatingColumnScheme::getSiteId, siteId).eq(SysFloatingColumnScheme::getIsGlobal, 1).eq(SysFloatingColumnScheme::getIsDisable, false));
}
}

@ -0,0 +1,7 @@
package com.huoran.iasf.util;
public class ConflictException extends RuntimeException {
public ConflictException(String message) {
super(message);
}
}

@ -0,0 +1,59 @@
package com.huoran.iasf.vo;
import com.baomidou.mybatisplus.annotation.FieldFill;
import com.baomidou.mybatisplus.annotation.TableField;
import io.swagger.annotations.ApiModel;
import io.swagger.annotations.ApiModelProperty;
import lombok.Data;
import lombok.EqualsAndHashCode;
import java.util.Date;
/**
* <p>
* 悬浮栏方案
* </p>
*
* @author cheney
* @since 2024-06-04
*/
@Data
@EqualsAndHashCode(callSuper = false)
@ApiModel(value = "SysFloatingColumnScheme对象", description = "悬浮栏方案")
public class SysFloatingColumnSchemeVO {
@ApiModelProperty(value = "悬浮栏方案id")
private Integer floatingBarSchemeId;
@ApiModelProperty(value = "悬浮栏方案名称")
private String schemeName;
@ApiModelProperty(value = "应用范围")
private String scopeOfApplication;
@ApiModelProperty(value = "内容模块数量")
private String numberOfContentModules;
@ApiModelProperty(value = "是否禁用(0默认,0启用 1禁用)")
private Integer isDisable;
@ApiModelProperty(value = "编辑人id", hidden = true)
private Integer editorId;
@ApiModelProperty(value = "编辑人名称")
private String editorSName;
@ApiModelProperty(value = "创建时间")
@TableField(fill = FieldFill.INSERT)
private Date createTime;
@ApiModelProperty(value = "更新时间")
@TableField(fill = FieldFill.INSERT_UPDATE)
private Date updateTime;
}

@ -0,0 +1,31 @@
package com.huoran.iasf.vo.req;
import io.swagger.annotations.ApiModel;
import io.swagger.annotations.ApiModelProperty;
import lombok.Data;
import lombok.EqualsAndHashCode;
/**
* <p>
* 悬浮栏方案
* </p>
*
* @author cheney
* @since 2024-06-04
*/
@Data
@EqualsAndHashCode(callSuper = false)
@ApiModel(value = "SuspensionBarListPagingReq对象", description = "悬浮栏列表请求参数")
public class SuspensionBarListPagingReq extends PageReqVO {
@ApiModelProperty(value = "搜索参数")
private String search;
@ApiModelProperty(value = "站点id")
private Integer siteId;
/* @ApiModelProperty(value = "是否为前台(用于区分前台和后台,1为前台,0为后台)")
private Integer isForeground;*/
}

@ -61,7 +61,7 @@ public class CodeGenerator {
// 5、策略配置
StrategyConfig strategy = new StrategyConfig();
strategy.setInclude("sys_floating_column_scheme_scope_of_application");
strategy.setInclude("sys_floating_column_scheme","sys_floating_column_scheme_module","sys_floating_column_scheme_scope_of_application");
strategy.setNaming(NamingStrategy.underline_to_camel);//数据库表映射到实体的命名策略
// strategy.setTablePrefix("sys_"); //生成实体时去掉表前缀

Loading…
Cancel
Save