4665bbe6624452c2aeac8cffbc2a82ece893c9b4..51df6e262c2d625e700a8194cbe0ec1e40b80843
2025-06-03 xin
存储桶
51df6e diff | tree
2025-06-03 xin
Merge remote-tracking branch 'origin/master' into xin
95dc03 diff | tree
2025-06-03 xin
9fbd15 diff | tree
2025-06-03 xin
重命名
7e2117 diff | tree
2 files deleted
4 files renamed
10 files added
3 files modified
920 ■■■■ changed files
oying-system/src/main/java/com/oying/modules/system/domain/Merchant.java 18 ●●●● patch | view | raw | blame | history
oying-system/src/main/java/com/oying/modules/system/mapper/MerchantMapper.java 8 ●●●● patch | view | raw | blame | history
oying-system/src/main/java/com/oying/modules/system/rest/MerchantController.java 73 ●●●●● patch | view | raw | blame | history
oying-system/src/main/java/com/oying/modules/system/rest/MerchantsController.java 74 ●●●●● patch | view | raw | blame | history
oying-system/src/main/java/com/oying/modules/system/service/MerchantService.java 14 ●●●● patch | view | raw | blame | history
oying-system/src/main/java/com/oying/modules/system/service/impl/MerchantServiceImpl.java 86 ●●●●● patch | view | raw | blame | history
oying-system/src/main/java/com/oying/modules/system/service/impl/MerchantsServiceImpl.java 86 ●●●●● patch | view | raw | blame | history
oying-system/src/main/resources/config/application-dev.yml 6 ●●●●● patch | view | raw | blame | history
oying-system/src/main/resources/config/application-prod.yml 6 ●●●●● patch | view | raw | blame | history
oying-system/src/main/resources/mapper/system/MerchantMapper.xml 20 ●●●● patch | view | raw | blame | history
oying-tools/src/main/java/com/oying/domain/BucketStorage.java 58 ●●●●● patch | view | raw | blame | history
oying-tools/src/main/java/com/oying/domain/dto/BucketStorageQueryCriteria.java 25 ●●●●● patch | view | raw | blame | history
oying-tools/src/main/java/com/oying/mapper/BucketStorageMapper.java 22 ●●●●● patch | view | raw | blame | history
oying-tools/src/main/java/com/oying/rest/BucketStorageController.java 82 ●●●●● patch | view | raw | blame | history
oying-tools/src/main/java/com/oying/service/BucketStorageService.java 57 ●●●●● patch | view | raw | blame | history
oying-tools/src/main/java/com/oying/service/impl/BucketStorageServiceImpl.java 131 ●●●●● patch | view | raw | blame | history
oying-tools/src/main/java/com/oying/utils/ObsProperties.java 21 ●●●●● patch | view | raw | blame | history
oying-tools/src/main/java/com/oying/utils/ObsUtils.java 127 ●●●●● patch | view | raw | blame | history
pom.xml 6 ●●●●● patch | view | raw | blame | history
oying-system/src/main/java/com/oying/modules/system/domain/Merchant.java
File was renamed from oying-system/src/main/java/com/oying/modules/system/domain/Merchants.java
@@ -20,12 +20,12 @@
**/
@Getter
@Setter
@TableName("sys_merchants")
public class Merchants extends BaseEntity implements Serializable {
@TableName("sys_merchant")
public class Merchant extends BaseEntity implements Serializable {
    @TableId(value = "merchants_id", type = IdType.AUTO)
    @TableId(value = "merchant_id", type = IdType.AUTO)
    @ApiModelProperty(value = "ID")
    private Long merchantsId;
    private Long merchantId;
    @NotBlank
    @ApiModelProperty(value = "名称")
@@ -48,21 +48,21 @@
    private String contactMobile;
    @ApiModelProperty(value = "排序")
    private Integer merchantsSort;
    private Integer merchantSort;
    @ApiModelProperty(value = "状态")
    private String enabled = "1";
    @ApiModelProperty(value = "审核人")
    private String authUser;
    private String auditUser;
    @ApiModelProperty(value = "审核时间")
    private Timestamp authTime;
    private Timestamp auditTime;
    @ApiModelProperty(value = "审核信息")
    private String authMessage;
    private String auditMessage;
    public void copy(Merchants source){
    public void copy(Merchant source){
        BeanUtil.copyProperties(source,this, CopyOptions.create().setIgnoreNullValue(true));
    }
}
oying-system/src/main/java/com/oying/modules/system/mapper/MerchantMapper.java
File was renamed from oying-system/src/main/java/com/oying/modules/system/mapper/MerchantsMapper.java
@@ -1,6 +1,6 @@
package com.oying.modules.system.mapper;
import com.oying.modules.system.domain.Merchants;
import com.oying.modules.system.domain.Merchant;
import com.oying.modules.system.domain.dto.MerchantsQueryCriteria;
import java.util.List;
import org.apache.ibatis.annotations.Param;
@@ -14,9 +14,9 @@
* @date 2025-05-29
**/
@Mapper
public interface MerchantsMapper extends BaseMapper<Merchants> {
public interface MerchantMapper extends BaseMapper<Merchant> {
    IPage<Merchants> findAll(@Param("criteria") MerchantsQueryCriteria criteria, Page<Object> page);
    IPage<Merchant> findAll(@Param("criteria") MerchantsQueryCriteria criteria, Page<Object> page);
    List<Merchants> findAll(@Param("criteria") MerchantsQueryCriteria criteria);
    List<Merchant> findAll(@Param("criteria") MerchantsQueryCriteria criteria);
}
oying-system/src/main/java/com/oying/modules/system/rest/MerchantController.java
New file
@@ -0,0 +1,73 @@
package com.oying.modules.system.rest;
import com.oying.annotation.Log;
import com.oying.modules.system.domain.Merchant;
import com.oying.modules.system.service.MerchantService;
import com.oying.modules.system.domain.dto.MerchantsQueryCriteria;
import lombok.RequiredArgsConstructor;
import java.util.List;
import org.springframework.http.HttpStatus;
import org.springframework.http.ResponseEntity;
import org.springframework.security.access.prepost.PreAuthorize;
import org.springframework.validation.annotation.Validated;
import org.springframework.web.bind.annotation.*;
import io.swagger.annotations.*;
import java.io.IOException;
import javax.servlet.http.HttpServletResponse;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.oying.utils.PageResult;
/**
* @author lixin
* @date 2025-05-29
**/
@RestController
@RequiredArgsConstructor
@Api(tags = "系统:商户信息")
@RequestMapping("/api/merchant")
public class MerchantController {
    private final MerchantService merchantService;
    @ApiOperation("导出数据")
    @GetMapping(value = "/download")
    @PreAuthorize("@el.check('merchant:list')")
    public void exportMerchants(HttpServletResponse response, MerchantsQueryCriteria criteria) throws IOException {
        merchantService.download(merchantService.queryAll(criteria), response);
    }
    @GetMapping
    @ApiOperation("查询商户信息")
    @PreAuthorize("@el.check('merchant:list')")
    public ResponseEntity<PageResult<Merchant>> queryMerchants(MerchantsQueryCriteria criteria){
        Page<Object> page = new Page<>(criteria.getPage(), criteria.getSize());
        return new ResponseEntity<>(merchantService.queryAll(criteria,page),HttpStatus.OK);
    }
    @PostMapping
    @Log("新增商户信息")
    @ApiOperation("新增商户信息")
    @PreAuthorize("@el.check('merchant:add')")
    public ResponseEntity<Object> createMerchants(@Validated @RequestBody Merchant resources){
        merchantService.create(resources);
        return new ResponseEntity<>(HttpStatus.CREATED);
    }
    @PutMapping
    @Log("修改商户信息")
    @ApiOperation("修改商户信息")
    @PreAuthorize("@el.check('merchant:edit')")
    public ResponseEntity<Object> updateMerchants(@Validated @RequestBody Merchant resources){
        merchantService.update(resources);
        return new ResponseEntity<>(HttpStatus.NO_CONTENT);
    }
    @DeleteMapping
    @Log("删除商户信息")
    @ApiOperation("删除商户信息")
    @PreAuthorize("@el.check('merchant:del')")
    public ResponseEntity<Object> deleteMerchants(@ApiParam(value = "传ID数组[]") @RequestBody List<Long> ids) {
        merchantService.deleteAll(ids);
        return new ResponseEntity<>(HttpStatus.OK);
    }
}
oying-system/src/main/java/com/oying/modules/system/rest/MerchantsController.java
File was deleted
oying-system/src/main/java/com/oying/modules/system/service/MerchantService.java
File was renamed from oying-system/src/main/java/com/oying/modules/system/service/MerchantsService.java
@@ -1,6 +1,6 @@
package com.oying.modules.system.service;
import com.oying.modules.system.domain.Merchants;
import com.oying.modules.system.domain.Merchant;
import com.oying.modules.system.domain.dto.MerchantsQueryCriteria;
import java.util.List;
import java.io.IOException;
@@ -14,7 +14,7 @@
* @author lixin
* @date 2025-05-29
**/
public interface MerchantsService extends IService<Merchants> {
public interface MerchantService extends IService<Merchant> {
    /**
    * 查询数据分页
@@ -22,26 +22,26 @@
    * @param page 分页参数
    * @return PageResult
    */
    PageResult<Merchants> queryAll(MerchantsQueryCriteria criteria, Page<Object> page);
    PageResult<Merchant> queryAll(MerchantsQueryCriteria criteria, Page<Object> page);
    /**
    * 查询所有数据不分页
    * @param criteria 条件参数
    * @return List<MerchantsDto>
    */
    List<Merchants> queryAll(MerchantsQueryCriteria criteria);
    List<Merchant> queryAll(MerchantsQueryCriteria criteria);
    /**
    * 创建
    * @param resources /
    */
    void create(Merchants resources);
    void create(Merchant resources);
    /**
    * 编辑
    * @param resources /
    */
    void update(Merchants resources);
    void update(Merchant resources);
    /**
    * 多选删除
@@ -55,5 +55,5 @@
    * @param response /
    * @throws IOException /
    */
    void download(List<Merchants> all, HttpServletResponse response) throws IOException;
    void download(List<Merchant> all, HttpServletResponse response) throws IOException;
}
oying-system/src/main/java/com/oying/modules/system/service/impl/MerchantServiceImpl.java
New file
@@ -0,0 +1,86 @@
package com.oying.modules.system.service.impl;
import com.oying.modules.system.domain.Merchant;
import com.oying.modules.system.mapper.MerchantMapper;
import com.oying.utils.FileUtil;
import lombok.RequiredArgsConstructor;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.oying.modules.system.service.MerchantService;
import com.oying.modules.system.domain.dto.MerchantsQueryCriteria;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;
import com.oying.utils.PageUtil;
import java.util.List;
import java.util.Map;
import java.io.IOException;
import javax.servlet.http.HttpServletResponse;
import java.util.ArrayList;
import java.util.LinkedHashMap;
import com.oying.utils.PageResult;
/**
* @description 服务实现
* @author lixin
* @date 2025-05-29
**/
@Service
@RequiredArgsConstructor
public class MerchantServiceImpl extends ServiceImpl<MerchantMapper, Merchant> implements MerchantService {
    private final MerchantMapper merchantMapper;
    @Override
    public PageResult<Merchant> queryAll(MerchantsQueryCriteria criteria, Page<Object> page){
        return PageUtil.toPage(merchantMapper.findAll(criteria, page));
    }
    @Override
    public List<Merchant> queryAll(MerchantsQueryCriteria criteria){
        return merchantMapper.findAll(criteria);
    }
    @Override
    @Transactional(rollbackFor = Exception.class)
    public void create(Merchant resources) {
        merchantMapper.insert(resources);
    }
    @Override
    @Transactional(rollbackFor = Exception.class)
    public void update(Merchant resources) {
        Merchant merchant = getById(resources.getMerchantId());
        merchant.copy(resources);
        merchantMapper.updateById(merchant);
    }
    @Override
    @Transactional(rollbackFor = Exception.class)
    public void deleteAll(List<Long> ids) {
        merchantMapper.deleteBatchIds(ids);
    }
    @Override
    public void download(List<Merchant> all, HttpServletResponse response) throws IOException {
        List<Map<String, Object>> list = new ArrayList<>();
        for (Merchant merchant : all) {
            Map<String, Object> map = new LinkedHashMap<>();
            map.put("名称", merchant.getMerchantName());
            map.put("商户编码", merchant.getMerchantCode());
            map.put("营业执照号", merchant.getBusinessLicense());
            map.put("营业执照号路径", merchant.getBusinessLicensePath());
            map.put("联系手机", merchant.getContactMobile());
            map.put("排序", merchant.getMerchantSort());
            map.put("状态", merchant.getEnabled());
            map.put("审核人", merchant.getAuditUser());
            map.put("审核时间", merchant.getAuditTime());
            map.put("审核信息", merchant.getAuditMessage());
            map.put("创建者", merchant.getCreateBy());
            map.put("更新者", merchant.getUpdateBy());
            map.put("创建日期", merchant.getCreateTime());
            map.put("更新时间", merchant.getUpdateTime());
            list.add(map);
        }
        FileUtil.downloadExcel(list, response);
    }
}
oying-system/src/main/java/com/oying/modules/system/service/impl/MerchantsServiceImpl.java
File was deleted
oying-system/src/main/resources/config/application-dev.yml
@@ -170,3 +170,9 @@
  notify-url: https://localhost/oying/api/swiftPass/alipayCallback
  # 退款通知地址
  refund-url: https://localhost/oying/api/swiftPass/returnNotify
obs:
  access_key_id: RZ1UIOZDZ58DD4NWPD6Q
  access_key_secret: QpE58YEFtgoIwUoGNlN5JlNY7t6qVu7vMkix8gAI
  bucket: oying
  endpoint: https://obs.cn-southwest-2.myhuaweicloud.com
oying-system/src/main/resources/config/application-prod.yml
@@ -180,3 +180,9 @@
  notify-url: https://localhost/oying/api/swiftPass/alipayCallback
  # 退款通知地址
  refund-url: https://localhost/oying/api/swiftPass/returnNotify
obs:
  access_key_id: RZ1UIOZDZ58DD4NWPD6Q
  access_key_secret: QpE58YEFtgoIwUoGNlN5JlNY7t6qVu7vMkix8gAI
  bucket: oying
  endpoint: https://obs.cn-southwest-2.myhuaweicloud.com
oying-system/src/main/resources/mapper/system/MerchantMapper.xml
File was renamed from oying-system/src/main/resources/mapper/system/MerchantsMapper.xml
@@ -1,32 +1,32 @@
<?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.oying.modules.system.mapper.MerchantsMapper">
    <resultMap id="BaseResultMap" type="com.oying.modules.system.domain.Merchants">
        <id column="merchants_id" property="merchantsId"/>
<mapper namespace="com.oying.modules.system.mapper.MerchantMapper">
    <resultMap id="BaseResultMap" type="com.oying.modules.system.domain.Merchant">
        <id column="merchant_id" property="merchantId"/>
        <result column="merchant_name" property="merchantName"/>
        <result column="merchant_code" property="merchantCode"/>
        <result column="business_license" property="businessLicense"/>
        <result column="business_license_path" property="businessLicensePath"/>
        <result column="contact_mobile" property="contactMobile"/>
        <result column="merchants_sort" property="merchantsSort"/>
        <result column="merchant_sort" property="merchantSort"/>
        <result column="enabled" property="enabled"/>
        <result column="create_by" property="createBy"/>
        <result column="update_by" property="updateBy"/>
        <result column="create_time" property="createTime"/>
        <result column="update_time" property="updateTime"/>
        <result column="auth_user" property="authUser"/>
        <result column="auth_time" property="authTime"/>
        <result column="auth_message" property="authMessage"/>
        <result column="audit_user" property="auditUser"/>
        <result column="audit_time" property="auditTime"/>
        <result column="audit_message" property="auditMessage"/>
    </resultMap>
    <sql id="Base_Column_List">
        merchants_id, merchant_name, merchant_code, business_license, business_license_path, contact_mobile, merchants_sort, enabled, create_by, update_by, create_time, update_time, auth_user, auth_time, auth_message
        merchant_id, merchant_name, merchant_code, business_license, business_license_path, contact_mobile, merchant_sort, enabled, create_by, update_by, create_time, update_time, audit_user, audit_time, audit_message
    </sql>
    <select id="findAll" resultMap="BaseResultMap">
        select
        <include refid="Base_Column_List"/>
        from sys_merchants
        from sys_merchant
        <where>
            <if test="criteria.blurry != null and criteria.blurry != ''">
                and (
@@ -43,6 +43,6 @@
                AND create_time BETWEEN #{criteria.createTime[0]} AND #{criteria.createTime[1]}
            </if>
        </where>
        order by merchants_sort desc
        order by merchant_sort desc
    </select>
</mapper>
oying-tools/src/main/java/com/oying/domain/BucketStorage.java
New file
@@ -0,0 +1,58 @@
package com.oying.domain;
import com.oying.base.BaseEntity;
import cn.hutool.core.bean.BeanUtil;
import io.swagger.annotations.ApiModelProperty;
import cn.hutool.core.bean.copier.CopyOptions;
import java.io.Serializable;
import com.baomidou.mybatisplus.annotation.IdType;
import com.baomidou.mybatisplus.annotation.TableId;
import com.baomidou.mybatisplus.annotation.TableName;
import lombok.Getter;
import lombok.Setter;
/**
* @description /
* @author lixin
* @date 2025-06-03
**/
@Getter
@Setter
@TableName("tool_bucket_storage")
public class BucketStorage extends BaseEntity implements Serializable {
    @TableId(value = "bucket_id", type = IdType.AUTO)
    @ApiModelProperty(value = "主键")
    private Long bucketId;
    @ApiModelProperty(value = "文件真实的名称")
    private String realName;
    @ApiModelProperty(value = "文件名")
    private String name;
    @ApiModelProperty(value = "后缀")
    private String suffix;
    @ApiModelProperty(value = "路径")
    private String path;
    @ApiModelProperty(value = "类型")
    private String type;
    @ApiModelProperty(value = "大小")
    private String size;
    public void copy(BucketStorage source){
        BeanUtil.copyProperties(source,this, CopyOptions.create().setIgnoreNullValue(true));
    }
    public BucketStorage(String realName,String name, String suffix, String path, String type, String size) {
        this.realName = realName;
        this.name = name;
        this.suffix = suffix;
        this.path = path;
        this.type = type;
        this.size = size;
    }
}
oying-tools/src/main/java/com/oying/domain/dto/BucketStorageQueryCriteria.java
New file
@@ -0,0 +1,25 @@
package com.oying.domain.dto;
import lombok.Data;
import java.sql.Timestamp;
import java.util.List;
import io.swagger.annotations.ApiModelProperty;
/**
* @author lixin
* @date 2025-06-03
**/
@Data
public class BucketStorageQueryCriteria{
    @ApiModelProperty(value = "页码", example = "1")
    private Integer page = 1;
    @ApiModelProperty(value = "每页数据量", example = "10")
    private Integer size = 10;
    @ApiModelProperty(value = "模糊查询")
    private String blurry;
    private List<Timestamp> createTime;
}
oying-tools/src/main/java/com/oying/mapper/BucketStorageMapper.java
New file
@@ -0,0 +1,22 @@
package com.oying.mapper;
import com.oying.domain.BucketStorage;
import com.oying.domain.dto.BucketStorageQueryCriteria;
import java.util.List;
import org.apache.ibatis.annotations.Param;
import org.apache.ibatis.annotations.Mapper;
import com.baomidou.mybatisplus.core.mapper.BaseMapper;
import com.baomidou.mybatisplus.core.metadata.IPage;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
/**
* @author lixin
* @date 2025-06-03
**/
@Mapper
public interface BucketStorageMapper extends BaseMapper<BucketStorage> {
    IPage<BucketStorage> findAll(@Param("criteria") BucketStorageQueryCriteria criteria, Page<Object> page);
    List<BucketStorage> findAll(@Param("criteria") BucketStorageQueryCriteria criteria);
}
oying-tools/src/main/java/com/oying/rest/BucketStorageController.java
New file
@@ -0,0 +1,82 @@
package com.oying.rest;
import com.oying.annotation.Log;
import com.oying.domain.BucketStorage;
import com.oying.exception.BadRequestException;
import com.oying.service.BucketStorageService;
import com.oying.domain.dto.BucketStorageQueryCriteria;
import com.oying.utils.FileUtil;
import com.oying.utils.R;
import lombok.RequiredArgsConstructor;
import java.util.List;
import org.springframework.http.HttpStatus;
import org.springframework.http.ResponseEntity;
import org.springframework.security.access.prepost.PreAuthorize;
import org.springframework.web.bind.annotation.*;
import io.swagger.annotations.*;
import java.io.IOException;
import javax.servlet.http.HttpServletResponse;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import org.springframework.web.multipart.MultipartFile;
/**
 * @author lixin
 * @date 2025-06-03
 **/
@RestController
@RequiredArgsConstructor
@Api(tags = "工具:存储桶")
@RequestMapping("/api/bucketStorage")
public class BucketStorageController {
    private final BucketStorageService bucketStorageService;
    @ApiOperation("导出数据")
    @GetMapping(value = "/download")
    @PreAuthorize("@el.check('bucketStorage:list')")
    public void exportBucketStorage(HttpServletResponse response, BucketStorageQueryCriteria criteria) throws IOException {
        bucketStorageService.download(bucketStorageService.queryAll(criteria), response);
    }
    @GetMapping
    @ApiOperation("查询存储桶")
    @PreAuthorize("@el.check('bucketStorage:list')")
    public ResponseEntity<Object> queryBucketStorage(BucketStorageQueryCriteria criteria) {
        Page<Object> page = new Page<>(criteria.getPage(), criteria.getSize());
        return new ResponseEntity<>(R.success(bucketStorageService.queryAll(criteria, page)), HttpStatus.OK);
    }
    @PostMapping
    @Log("上传存储桶文件")
    @ApiOperation("上传存储桶文件")
    @PreAuthorize("@el.check('bucketStorage:add')")
    public ResponseEntity<Object> create(@RequestParam String name, @RequestParam("file") MultipartFile file) {
        return new ResponseEntity<>(R.success(bucketStorageService.create(name, file)), HttpStatus.CREATED);
    }
    @PostMapping("/pictures")
    @ApiOperation("上传图片")
    public ResponseEntity<Object> upload(@RequestParam MultipartFile file) {
        // 判断文件是否为图片
        String suffix = FileUtil.getExtensionName(file.getOriginalFilename());
        FileUtil.checkSize(5, file.getSize());
        if (!FileUtil.IMAGE.equals(FileUtil.getFileType(suffix))) {
            throw new BadRequestException("只能上传图片");
        }
        BucketStorage bucketStorage = bucketStorageService.create(null, file);
        return new ResponseEntity<>(R.success(bucketStorage), HttpStatus.OK);
    }
    @DeleteMapping
    @Log("删除存储桶")
    @ApiOperation("删除存储桶")
    @PreAuthorize("@el.check('bucketStorage:del')")
    public ResponseEntity<Object> deleteBucketStorage(@ApiParam(value = "传ID数组[]") @RequestBody List<Long> ids) {
        bucketStorageService.deleteAll(ids);
        return new ResponseEntity<>(R.success(), HttpStatus.OK);
    }
}
oying-tools/src/main/java/com/oying/service/BucketStorageService.java
New file
@@ -0,0 +1,57 @@
package com.oying.service;
import com.oying.domain.BucketStorage;
import com.oying.domain.dto.BucketStorageQueryCriteria;
import java.io.File;
import java.util.List;
import java.io.IOException;
import javax.servlet.http.HttpServletResponse;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.baomidou.mybatisplus.extension.service.IService;
import com.oying.utils.PageResult;
import org.springframework.web.multipart.MultipartFile;
/**
* @description 服务接口
* @author lixin
* @date 2025-06-03
**/
public interface BucketStorageService extends IService<BucketStorage> {
    /**
    * 查询数据分页
    * @param criteria 条件
    * @param page 分页参数
    * @return PageResult
    */
    PageResult<BucketStorage> queryAll(BucketStorageQueryCriteria criteria, Page<Object> page);
    /**
    * 查询所有数据不分页
    * @param criteria 条件参数
    * @return List<BucketStorageDto>
    */
    List<BucketStorage> queryAll(BucketStorageQueryCriteria criteria);
    /**
    * 创建
    */
    BucketStorage create(String name, MultipartFile file);
    BucketStorage createFile(String name, File file);
    /**
    * 多选删除
    * @param ids /
    */
    void deleteAll(List<Long> ids);
    /**
    * 导出数据
    * @param all 待导出的数据
    * @param response /
    * @throws IOException /
    */
    void download(List<BucketStorage> all, HttpServletResponse response) throws IOException;
}
oying-tools/src/main/java/com/oying/service/impl/BucketStorageServiceImpl.java
New file
@@ -0,0 +1,131 @@
package com.oying.service.impl;
import cn.hutool.core.util.ObjectUtil;
import com.obs.services.model.AccessControlList;
import com.obs.services.model.PutObjectResult;
import com.oying.config.properties.FileProperties;
import com.oying.domain.BucketStorage;
import com.oying.exception.BadRequestException;
import com.oying.utils.*;
import lombok.RequiredArgsConstructor;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.oying.service.BucketStorageService;
import com.oying.domain.dto.BucketStorageQueryCriteria;
import com.oying.mapper.BucketStorageMapper;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;
import java.io.File;
import java.util.List;
import java.util.Map;
import java.io.IOException;
import javax.servlet.http.HttpServletResponse;
import java.util.ArrayList;
import java.util.LinkedHashMap;
import org.springframework.web.multipart.MultipartFile;
/**
 * @author lixin
 * @description 服务实现
 * @date 2025-06-03
 **/
@Service
@RequiredArgsConstructor
public class BucketStorageServiceImpl extends ServiceImpl<BucketStorageMapper, BucketStorage> implements BucketStorageService {
    private final BucketStorageMapper bucketStorageMapper;
    private final ObsProperties properties;
    private final FileProperties fileProperties;
    @Override
    public PageResult<BucketStorage> queryAll(BucketStorageQueryCriteria criteria, Page<Object> page) {
        return PageUtil.toPage(bucketStorageMapper.findAll(criteria, page));
    }
    @Override
    public List<BucketStorage> queryAll(BucketStorageQueryCriteria criteria) {
        return bucketStorageMapper.findAll(criteria);
    }
    @Override
    @Transactional(rollbackFor = Exception.class)
    public BucketStorage createFile(String name, File file) {
        FileUtil.checkSize(fileProperties.getMaxSize(), file.length());
        String suffix = FileUtil.getExtensionName(file.getName());
        String type = FileUtil.getFileType(suffix);
        String reaName = System.currentTimeMillis() + "." + suffix;
        String objectKey = type + "/" + reaName;
        PutObjectResult result = ObsUtils.putObject(properties, file, objectKey, AccessControlList.REST_CANNED_PUBLIC_READ);
        if (ObjectUtil.isNull(result)) {
            throw new BadRequestException("上传失败");
        }
        name = StringUtils.isBlank(name) ? FileUtil.getFileNameNoEx(reaName) : name;
        BucketStorage bucketStorage = new BucketStorage(
                reaName,
                name,
                suffix,
                objectKey,
                type,
                FileUtil.getSize(file.length())
        );
        bucketStorageMapper.insert(bucketStorage);
        return bucketStorage;
    }
    @Override
    @Transactional(rollbackFor = Exception.class)
    public BucketStorage create(String name, MultipartFile file) {
        FileUtil.checkSize(fileProperties.getMaxSize(), file.getSize());
        String suffix = FileUtil.getExtensionName(file.getOriginalFilename());
        String type = FileUtil.getFileType(suffix);
        String reaName = System.currentTimeMillis() + "." + suffix;
        String objectKey = type + "/" + reaName;
        PutObjectResult result = ObsUtils.putObject(properties, FileUtil.toFile(file), objectKey, AccessControlList.REST_CANNED_PUBLIC_READ);
        if (ObjectUtil.isNull(result)) {
            throw new BadRequestException("上传失败");
        }
        name = StringUtils.isBlank(name) ? FileUtil.getFileNameNoEx(reaName) : name;
        BucketStorage bucketStorage = new BucketStorage(
                reaName,
                name,
                suffix,
                objectKey,
                type,
                FileUtil.getSize(file.getSize())
        );
        bucketStorageMapper.insert(bucketStorage);
        return bucketStorage;
    }
    @Override
    @Transactional(rollbackFor = Exception.class)
    public void deleteAll(List<Long> ids) {
        for(Long id : ids) {
            BucketStorage storage = bucketStorageMapper.selectById(id);
            ObsUtils.deleteObject(properties, storage.getPath());
        }
        bucketStorageMapper.deleteBatchIds(ids);
    }
    @Override
    public void download(List<BucketStorage> all, HttpServletResponse response) throws IOException {
        List<Map<String, Object>> list = new ArrayList<>();
        for (BucketStorage bucketStorage : all) {
            Map<String, Object> map = new LinkedHashMap<>();
            map.put("文件真实的名称", bucketStorage.getRealName());
            map.put("文件名", bucketStorage.getName());
            map.put("后缀", bucketStorage.getSuffix());
            map.put("路径", bucketStorage.getPath());
            map.put("类型", bucketStorage.getType());
            map.put("大小", bucketStorage.getSize());
            map.put("创建人", bucketStorage.getCreateBy());
            map.put("创建时间", bucketStorage.getCreateTime());
            map.put("修改者", bucketStorage.getUpdateBy());
            map.put("修改时间", bucketStorage.getUpdateTime());
            list.add(map);
        }
        FileUtil.downloadExcel(list, response);
    }
}
oying-tools/src/main/java/com/oying/utils/ObsProperties.java
New file
@@ -0,0 +1,21 @@
package com.oying.utils;
import lombok.Data;
import org.springframework.boot.context.properties.ConfigurationProperties;
import org.springframework.context.annotation.Configuration;
/**
 * @author xin
 * @description
 * @date 2025/6/3 01:54
 */
@Data
@Configuration
@ConfigurationProperties(prefix = "obs")
public class ObsProperties {
    private String accessKeyId;
    private String accessKeySecret;
    private String bucket;
    private String endpoint;
}
oying-tools/src/main/java/com/oying/utils/ObsUtils.java
New file
@@ -0,0 +1,127 @@
package com.oying.utils;
import com.obs.services.ObsClient;
import com.obs.services.model.AccessControlList;
import com.obs.services.model.ObsObject;
import com.obs.services.model.PutObjectRequest;
import com.obs.services.model.PutObjectResult;
import com.oying.exception.BadRequestException;
import java.io.File;
import java.io.FileOutputStream;
import java.io.InputStream;
public class ObsUtils {
    /**
     * 创建ObsClient实例
     *
     * @param properties obs配置
     * @return ObsClient实例
     */
    public static ObsClient getObsClient(ObsProperties properties) {
        // 创建ObsClient实例
        return new ObsClient(properties.getAccessKeyId(), properties.getAccessKeySecret(), properties.getEndpoint());
    }
    /**
     * 上传对象权限
     *
     * @param properties    obs配置
     * @param file      文件
     * @param objectKey 对象名
     * @param acl       对象权限
     * @return PutObjectResult
     */
    public static PutObjectResult putObject(ObsProperties properties, File file, String objectKey, AccessControlList acl) {
        try {
            // 创建ObsClient实例
            ObsClient obsClient = getObsClient(properties);
            PutObjectRequest request = new PutObjectRequest();
            request.setBucketName(properties.getBucket());
            request.setObjectKey(objectKey);
            request.setFile(file);
            // 对象权限
            request.setAcl(acl);
            // 为待上传的本地文件路径,需要指定到具体的文件名
            return obsClient.putObject(request);
        } catch (Exception e) {
            throw new BadRequestException("上传对象失败" + e.getMessage());
        } finally {
            FileUtil.del(file);
        }
    }
    /**
     * 上传对象
     *
     * @param properties    obs配置
     * @param file      文件
     * @param objectKey 对象名
     * @return PutObjectResult
     */
    public static PutObjectResult putObject(ObsProperties properties, File file, String objectKey) {
        try {
            // 创建ObsClient实例
            ObsClient obsClient = getObsClient(properties);
            // 为待上传的本地文件路径,需要指定到具体的文件名
            return obsClient.putObject(properties.getBucket(), objectKey, file);
        } catch (Exception e) {
            throw new BadRequestException("上传对象失败" + e.getMessage());
        } finally {
            FileUtil.del(file);
        }
    }
    /**
     * 下载对象
     *
     * @param properties    obs配置
     * @param objectKey 对象名
     * @param path      保存路径
     */
    public static String getObject(ObsProperties properties, String objectKey, String path) {
        // 创建ObsClient实例
        ObsClient obsClient = getObsClient(properties);
        ObsObject obsObject = obsClient.getObject(properties.getBucket(), objectKey);
        InputStream in = obsObject.getObjectContent();
        if (in != null) {
            FileOutputStream out = null;
            try {
                // getCanonicalFile 可解析正确各种路径
                File dest = new File(path).getCanonicalFile();
                // 检测是否存在目录
                if (!dest.getParentFile().exists()) {
                    dest.getParentFile().mkdirs();
                }
                out = new FileOutputStream(path);
                byte[] b = new byte[1024];
                int length;
                while ((length = in.read(b)) > 0) {
                    out.write(b, 0, length);
                }
            } catch (Exception e) {
                throw new BadRequestException("流输出异常");
            } finally {
                CloseUtil.close(in);
                CloseUtil.close(out);
            }
        }
        return path;
    }
    /**
     * 删除对象
     *
     * @param properties    obs配置
     * @param objectKey 对象名
     */
    public static void deleteObject(ObsProperties properties, String objectKey) {
        // 创建ObsClient实例
        ObsClient obsClient = getObsClient(properties);
        // 删除指定的对象
        obsClient.deleteObject(properties.getBucket(), objectKey);
    }
}
pom.xml
@@ -236,6 +236,12 @@
            <artifactId>commons-text</artifactId>
            <version>1.13.0</version>
        </dependency>
        <!-- 华为云对象存储服务 OBS-->
        <dependency>
            <groupId>com.huaweicloud</groupId>
            <artifactId>esdk-obs-java-bundle</artifactId>
            <version>3.22.12</version>
        </dependency>
    </dependencies>
    <build>