SpringBoot+OSS+VUE+mybatis-plus 前后端 (前后端 · 素材管理)

本文介绍了使用SpringBoot、OSS和Vue实现前后端素材管理的过程,包括客户端WEB直传图片、OSS删除功能。首先创建数据库表,接着搭建SpringBoot项目,安装OSS SDK,讲解OSS服务及其优势。通过服务端签名直传,减少服务器压力,提高上传效率。详细阐述了后端OSS服务的实现以及前端Vue组件的编写。
摘要由CSDN通过智能技术生成

                                      SpringBoot+OSS+VUE(前后端 · 素材管理)


       功能:
            1. 实现客户端WEB直传(图片上传)
            2. 实现素材管理模块有图片上传(客户端直传)、OSS删除。
      实现步骤:
           1. 数据库创建两张表一张是分组素材表、一张素材详细表

2. 创建Springboot项目,此处就详细讲解了。。。。不在的小伙伴可以去网上查找

  •  创建Springboot项目:https://blog.csdn.net/qq_42539533/article/details/90607415

3. 安装SDK,在Maven项目中加入依赖项(推荐方式)

<dependency>
    <groupId>com.aliyun.oss</groupId>
    <artifactId>aliyun-sdk-oss</artifactId>
    <version>2.8.3</version>
</dependency

4. 介绍OSS是什么? 

流程介绍

  • 因为公司已经开通OSS配置好OSS所有这里我就不详细截图展示了,要开通才可以使用,我采用的是OSS最佳实践方式来实现文件上传。
  • 为什么要采用这种方式来实现呢?它的好处在那呢?为什么要这么做的原因呢?来着这些问题给你们讲解。
  • 采用这种方式是让系统服务不需要承受较大带宽,减少开发成本、易维护,想想用普通上传方式客户端都需要经过服务端处理,而用客户端直传方式(Web直传)不需要经过服务端处理,而是经过客户直接上传图片并让OSS返回回调接口,减轻服务器的压力,提高服务端处理图片效率、减轻IO流繁琐流程处理。
String accessId = "<yourAccessKeyId>"; // 请填写您的AccessKeyId。
        String accessKey = "<yourAccessKeySecret>"; // 请填写您的AccessKeySecret。
        String endpoint = "oss-cn-hangzhou.aliyuncs.com"; // 请填写您的 endpoint。
        String bucket = "bucket-name"; // 请填写您的 bucketname 。
        String host = "https://" + bucket + "." + endpoint; // host的格式为 bucketname.endpoint
        // callbackUrl为 上传回调服务器的URL,请将下面的IP和Port配置为您自己的真实信息。
        String callbackUrl = "http://88.88.88.88:8888";
        String dir = "user-dir-prefix/"; // 用户上传文件时指定的前缀。

流程如下图所示:

时序图

5. 进入主题

  1.文件上传是

Java后端

OssService:
package com.qlrsoft.smart_store.admin.system.service;

import com.qlrsoft.smart_store.admin.bean.ResultBean;
import javax.servlet.http.HttpServletRequest;

/**
 * oss上传及回调接口
 * @author Lwb
 */
public interface OssService {
    /**
     * 服务端生成签名
     * @return
     */
    ResultBean getPolicy(HttpServletRequest request);
    /**
     * 回调接口
     * @param request
     * @return
     */
    ResultBean callback(HttpServletRequest request);
}

  OssServiceImpl:

package com.qlrsoft.smart_store.admin.system.service.impl;

import cn.hutool.json.JSONUtil;
import cn.stylefeng.roses.core.util.ToolUtil;
import com.alibaba.fastjson.JSONObject;
import com.aliyun.oss.OSSClient;
import com.aliyun.oss.common.utils.BinaryUtil;
import com.aliyun.oss.model.MatchMode;
import com.aliyun.oss.model.PolicyConditions;
import com.qlrsoft.smart_store.admin.bean.Constants;
import com.qlrsoft.smart_store.admin.bean.OssCallbackParam;
import com.qlrsoft.smart_store.admin.bean.ResultBean;
import com.qlrsoft.smart_store.admin.core.storage.oss.OssFileOperator;
import com.qlrsoft.smart_store.admin.system.service.OssService;
import com.qlrsoft.smart_store.mall.entity.MaterialDetails;
import com.qlrsoft.smart_store.mall.service.MaterialDetailsService;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.stereotype.Service;

import javax.servlet.http.HttpServletRequest;
import java.util.Date;
import java.util.HashMap;
import java.util.Map;

@Service
@Slf4j
public class OssServiceImpl implements OssService {

    @Autowired
    private OSSClient ossClient;
    @Autowired
    private MaterialDetailsService materialDetailsService;

    @Value("${aliyun.oss.policy.expire}")
    private int ALIYUN_OSS_EXPIRE;
    @Value("${aliyun.oss.maxSize}")
    private int ALIYUN_OSS_MAX_SIZE;
    @Value("${aliyun.oss.callback}")
    private String ALIYUN_OSS_CALLBACK;
    @Value("${aliyun.oss.endpoint}")
    private String ALIYUN_OSS_ENDPOINT;
    @Value("${aliyun.oss.internet-file-url}")
    private String INTERNET_FILE_URL;

    /**
     * 服务端生成签名
     *
     * @return
     */
    @Override
    public ResultBean getPolicy(HttpServletRequest request) {
        JSONObject resultBean = new JSONObject();
        String pic_location = String.valueOf(System.currentTimeMillis());
        // 存储目录
        String dir = pic_location+"/";
        // 签名有效期
        long expireEndTime = System.currentTimeMillis() + ALIYUN_OSS_EXPIRE * 1000;
        Date expiration = new Date(expireEndTime);
        // 文件大小
        long maxSize = ALIYUN_OSS_MAX_SIZE * 1024 * 1024;
        Map<String,String> map=new HashMap<>();
        map.put("Cookie",request.getHeader("Cookie"));
        // 回调
        OssCallbackParam callback = new OssCallbackParam();
        callback.setCallbackUrl(ALIYUN_OSS_CALLBACK);
        callback.setSignatureVersion("2.0");
        callback.setAdditionalHeaders(map);
        callback.setCallbackBody("filename=${object}&size=${size}&mimeType=${mimeType}&height=${imageInfo.height}&width=${imageInfo.width}");
        callback.setCallbackBodyType("application/x-www-form-urlencoded");
        // 提交节点
        String action = INTERNET_FILE_URL;
        try {
            PolicyConditions policyConds = new PolicyConditions();
            policyConds.addConditionItem(PolicyConditions.COND_CONTENT_LENGTH_RANGE, 0, maxSize);
            policyConds.addConditionItem(MatchMode.StartWith, PolicyConditions.COND_KEY, dir);
            String postPolicy = ossClient.generatePostPolicy(expiration, policyConds);
            byte[] binaryData = postPolicy.getBytes("utf-8");
            String policy = BinaryUtil.toBase64String(binaryData);
            String signature = ossClient.calculatePostSignature(postPolicy);
            String callbackData = BinaryUtil.toBase64String(JSONUtil.parse(callback).toString().getBytes("utf-8"));
            resultBean.put("accessid",ossClient.getCredentialsProvider().getCredentials().getAccessKeyId());
            resultBean.put("policy",policy);
            resultBean.put("signature",signature);
            resultBean.put("dir",dir);
            resultBean.put("expire",String.valueOf(expireEndTime / 1000));
            resultBean.put("callback",callbackData);
            resultBean.put("host",action);

            // 返回结果
        } catch (Exception e) {
            log.error("签名生成失败", e);
            return new ResultBean(Constants.RESCODE_SIGNATION_FAILED,Constants.RESMSG_SIGNATION_FAILED);
        }
        return new ResultBean(Constants.RESCODE_SUCCESS,Constants.RESMSG_SUCCESS,resultBean);
    }

    /**
     * 回调接口
     *
     * @param request
     * @return
     */
    @Override
    public ResultBean callback(HttpServletRequest request) {
        MaterialDetails materialDetails=new MaterialDetails();
        JSONObject resultBean = new JSONObject();
        String filename = String.valueOf(request.getParameter("filename"));
        materialDetails.setFileName(filename);
         String substring = filename.substring(filename.lastIndexOf("/") + 1);
        //截取图片类别
        String groupingId = filename.substring(filename.lastIndexOf("."));
        //获取图片名称
        materialDetails.setDetailsName(substring);
        filename = INTERNET_FILE_URL.concat("/").concat(filename);
        //获取图片地址
        materialDetails.setDetailsAddress(filename);
        //获取分组Id
        materialDetails.setGroupingId(Long.valueOf(OssFileOperator.getGroupingId(groupingId)));
        //图片文件大小
        materialDetails.setDetailsSize(String.valueOf(OssFileOperator.bytes2kb(Long.valueOf(request.getParameter("size")))+"KB"));
        //获取文件后缀
        String fileSuffix = ToolUtil.getFileSuffix(filename);
        //图片类别
        materialDetails.setDetailsCategory(fileSuffix);
        resultBean.put("filename",filename);
        resultBean.put("size",request.getParameter("size"));
        resultBean.put("mimeType",request.getParameter("mimeType"));
        resultBean.put("width",request.getParameter("width"));
        resultBean.put("height",request.getParameter("height"));
        //素材信息保存
        materialDetailsService.save(materialDetails);

        return new ResultBean(Constants.RESCODE_SUCCESS,Constants.RESMSG_SUCCESS,resultBean);
    }
}

OssController :

package com.javaboy.aliyun_oss_upload.controller;


import com.javaboy.aliyun_oss_upload.bean.ResultBean;
import com.javaboy.aliyun_oss_upload.service.OssService;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.PostMapping;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;

import javax.servlet.http.HttpServletRequest;

@RestController
@RequestMapping("/aliyun/oss")
public class OssController {

    private static Logger log = LoggerFactory.getLogger(OssController.class);
    @Autowired
    private OssService ossService;

    @GetMapping("/policy")
    public ResultBean policy() {
        ResultBean result = ossService.getPolicy();
        log.info("服务端生成签名:{}",result);
        return result;
    }


    @PostMapping("/callback")
    public ResultBean callback(HttpServletRequest request) {
        ResultBean ossCallbackResult = ossService.callback(request);
        log.info("oss成功的回调:{}",ossCallbackResult);
        return ossCallbackResult;
    }

}

bean

package com.qlrsoft.smart_store.admin.bean;

public class Constants {

    public final static String RESCODE_SUCCESS = "0000";
    public final static String RESMSG_SUCCESS = "成功";

    public final static String RESCODE_SIGNATION_FAILED = "9999";
    public final static String RESMSG_SIGNATION_FAILED = "生成签名失败";

}
package com.qlrsoft.smart_store.admin.bean;

import lombok.Data;

import java.util.Map;

/**
 * oss上传成功后的回调参数
 */
@Data
public class OssCallbackParam {
    /**
     * 请求的回调地址
     */
    private String callbackUrl;
    /**
     * 回调是传入request中的参数
     */
    private String callbackBody;
    /**
     * 回调时传入参数的格式,比如表单提交形式
     */
    private String callbackBodyType;

    private String signatureVersion;
    private Map<String, String> additionalHeaders;

}

package com.qlrsoft.smart_store.admin.bean;

public class ResultBean {

    private String resCode;
    private String resMsg;
    private Object resultContent;

    public ResultBean(String resCode, String resMsg){
        this.resCode = resCode;
        this.resMsg = resMsg;
    }

    public ResultBean(String resCode, String resMsg, Object resultContent){
        this.resCode = resCode;
        this.resMsg = resMsg;
        this.resultContent = resultContent;
    }
    public ResultBean(){}

    public String getResCode() {
        return resCode;
    }
    public void setResCode(String resCode) {
        this.resCode = resCode;
    }
    public String getResMsg() {
        return resMsg;
    }
    public void setResMsg(String resMsg) {
        this.resMsg = resMsg;
    }
    public Object getResultContent() {
        return resultContent;
    }
    public void setResultContent(Object resultContent) {
        this.resultContent = resultContent;
    }

    @Override
    public String toString() {
        return "ResultBean{" +
                "resCode='" + resCode + '\'' +
                ", resMsg='" + resMsg + '\'' +
                ", resultContent=" + resultContent +
                '}';
    }
}

前端:

formImgUpload.vue

<template>
    <el-upload
            v-if="show"
            class="upload-demo"
            :drag="drag"
            :accept="'image/png, image/jpg, image/jpeg'"
            :action="fileUploadUrl"
            :http-request="getPolicy"
            :on-remove="handleRemove"
            :before-remove="beforeRemove"
            :multiple="multiple"
            :limit="limit"
            :disabled="disabled"
            :on-exceed="handleExceed"
            :file-list="fileList"
            :on-success="handleSuccess&#
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
SpringBootVue都是非常流行的开发框架,可以用来构建各种类型的应用程序。在这里,SpringBoot用于后端开发,提供了许多功能和库来简化开发过程,包括SpringSecurity用于安全管理MyBatisPlus用于数据库操作,Redis用于缓存,RabbitMQ用于消息队列等等。 而Vue作为前端开发框架,提供了一种组件化的方式来构建用户界面。它可以与vuex、vue-router、axios等配合使用,实现状态管理、路由导航和数据请求等功能。此外,还可以使用vuetify和element来创建美观的UI界面,使用echarts来展示数据图表等等。 根据您提供的信息,springboot vue个人博客系统是一个基于SpringBootVue开发的在线预览系统。该系统包括了前端部分和后端部分,前端代码可以通过提供的链接进行下载,而后端部分则使用了SpringBoot作为框架,并结合了各种技术和库来实现不同的功能。您可以通过访问提供的在线地址来预览该系统的功能和界面。<span class="em">1</span><span class="em">2</span><span class="em">3</span> #### 引用[.reference_title] - *1* *2* *3* [基于springboot+vue个人博客搭建](https://blog.csdn.net/m0_54853465/article/details/126351754)[target="_blank" data-report-click={"spm":"1018.2226.3001.9630","extra":{"utm_source":"vip_chatgpt_common_search_pc_result","utm_medium":"distribute.pc_search_result.none-task-cask-2~all~insert_cask~default-1-null.142^v93^chatsearchT3_2"}}] [.reference_item style="max-width: 100%"] [ .reference_list ]

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值