OSS(一):OSS工具类

本文涉及的产品
对象存储 OSS,20GB 3个月
对象存储 OSS,恶意文件检测 1000次 1年
对象存储 OSS,内容安全 1000次 1年
简介: OSS(一):OSS工具类

强烈推荐一个大神的人工智能的教程:http://www.captainai.net/zhanghan


【前言】


      我们上家公司的存储系统用的是FastDFS(智能一代云平台(二十八):对前后端分离和FastDFS的使用的再理解);现在在职的公司用的是阿里云的OSS(OSS的官方文档),在工作的时候整理一个上传OSS文件的工具类,现在与大家分享一下。


【工具类】


      1、工具类的代码:


package zhanghan.oss.utils;
import com.aliyun.oss.ClientException;
import com.aliyun.oss.OSSClient;
import com.aliyun.oss.OSSException;
import com.aliyun.oss.model.ObjectMetadata;
import com.aliyun.oss.model.PutObjectResult;
import com.fasterxml.jackson.annotation.JsonValue;
import org.apache.commons.io.FilenameUtils;
import org.apache.commons.lang3.time.DateUtils;
import org.springframework.util.StringUtils;
import org.springframework.web.multipart.MultipartFile;
import zhanghan.oss.exception.OSSCreateBucketRuntimeException;
import zhanghan.oss.exception.OSSGeneratePresignedUrlRuntimeException;
import zhanghan.oss.exception.OssPutObjectRuntimeException;
import java.io.InputStream;
import java.net.URL;
import java.util.Date;
import java.util.UUID;
/**
 * OSS上传工具类-张晗-2017/10/10
 */
public class OSSUtil {
    private volatile static OSSClient instance;
    private OSSUtil() {
    }
    /**
     * 单例
     * @return  OSS工具类实例
     */
    private static OSSClient getOSSClient() {
        if (instance == null) {
            synchronized (OSSUtil.class) {
                if (instance == null) {
                    instance = new OSSClient(OSS_END_POINT, OSS_ACCESS_KEY_ID, OSS_ACCESS_KEY_SECRET);
                }
            }
        }
        return instance;
    }
    //定义日志
    private final static LogUtils logger = LogUtils.getLogger(OSSUtil.class);
    //OSS 的地址
    private final static String OSS_END_POINT = "http://oss-cn-qingdao.aliyuncs.com";
    //OSS 的key值
    private final static String OSS_ACCESS_KEY_ID = "OSSKEY";
    //OSS 的secret值
    private final static String OSS_ACCESS_KEY_SECRET = "OSSSECRET";
    //OSS 的bucket名字
    private final static String OSS_BUCKET_NAME = "zhanghan-test";
    //设置URL过期时间为10年
    private final static Date OSS_URL_EXPIRATION = DateUtils.addDays(new Date(), 365 * 10);
    //文件路径的枚举
    public enum FileDirType {
        ZHANGHAN_TEST("test");
        private String dir;
        FileDirType(String dir) {
            this.dir = dir;
        }
        @JsonValue
        public String getDir() {
            return dir;
        }
    }
    /**
     * 上传文件---去除URL中的?后的时间戳
     * @param file 文件
     * @param fileDir 上传到OSS上文件的路径
     * @return 文件的访问地址
     */
    public static String upload(MultipartFile file, FileDirType fileDir) {
        OSSUtil.createBucket();
        String fileName = OSSUtil.uploadFile(file, fileDir);
        String fileOssURL = OSSUtil.getImgUrl(fileName, fileDir);
        int firstChar = fileOssURL.indexOf("?");
        if (firstChar > 0) {
            fileOssURL = fileOssURL.substring(0, firstChar);
        }
        return fileOssURL;
    }
    /**
     * 当Bucket不存在时创建Bucket
     *
     * @throws OSSException 异常
     * @throws ClientException Bucket命名规则:
     *                         1.只能包含小写字母、数字和短横线,
     *                         2.必须以小写字母和数字开头和结尾
     *                         3.长度在3-63之间
     */
    private static void createBucket() {
        try {
            if (!OSSUtil.getOSSClient().doesBucketExist(OSS_BUCKET_NAME)) {//判断是否存在该Bucket,不存在时再重新创建
                OSSUtil.getOSSClient().createBucket(OSS_BUCKET_NAME);
            }
        } catch (Exception e) {
            logger.error("{}", "创建Bucket失败,请核对Bucket名称(规则:只能包含小写字母、数字和短横线,必须以小写字母和数字开头和结尾,长度在3-63之间)");
            throw new OSSCreateBucketRuntimeException("创建Bucket失败,请核对Bucket名称(规则:只能包含小写字母、数字和短横线,必须以小写字母和数字开头和结尾,长度在3-63之间)");
        }
    }
    /**
     * 上传到OSS服务器  如果同名文件会覆盖服务器上的
     * @param file 文件
     * @param fileDir  上传到OSS上文件的路径
     * @return 文件的访问地址
     */
    private static String uploadFile(MultipartFile file, FileDirType fileDir) {
        String fileName = String.format(
                "%s.%s",
                UUID.randomUUID().toString(),
                FilenameUtils.getExtension(file.getOriginalFilename()));
        try (InputStream inputStream = file.getInputStream()) {
            //创建上传Object的Metadata
            ObjectMetadata objectMetadata = new ObjectMetadata();
            objectMetadata.setContentLength(inputStream.available());
            objectMetadata.setCacheControl("no-cache");
            objectMetadata.setHeader("Pragma", "no-cache");
            objectMetadata.setContentType(getContentType(FilenameUtils.getExtension("." + file.getOriginalFilename())));
            objectMetadata.setContentDisposition("inline;filename=" + fileName);
            //上传文件
            PutObjectResult putResult = OSSUtil.getOSSClient().putObject(OSS_BUCKET_NAME, fileDir.getDir() + fileName, inputStream, objectMetadata);
            return fileName;
        } catch (Exception e) {
            logger.error("{}", "上传文件失败");
            throw new OssPutObjectRuntimeException("上传文件失败");
        }
    }
    /**
     * 获得文件路径
     * @param fileUrl  文件的URL
     * @param fileDir  文件在OSS上的路径
     * @return 文件的路径
     */
    private static String getImgUrl(String fileUrl, FileDirType fileDir) {
        if (StringUtils.isEmpty(fileUrl)) {
            logger.error("{}", "文件地址为空");
            throw new RuntimeException("文件地址为空");
        }
        String[] split = fileUrl.split("/");
        //获取oss图片URL失败
        URL url = OSSUtil.getOSSClient().generatePresignedUrl(OSS_BUCKET_NAME, fileDir.getDir() + split[split.length - 1], OSS_URL_EXPIRATION);
        if (url == null) {
            logger.error("{}", "获取oss文件URL失败");
            throw new OSSGeneratePresignedUrlRuntimeException("获取oss文件URL失败");
        }
        return url.toString();
    }
    /**
     * 判断OSS服务文件上传时文件的contentType
     *
     * @param FilenameExtension 文件后缀
     * @return 后缀
     */
    private static String getContentType(String FilenameExtension) {
        if (FilenameExtension.equalsIgnoreCase("bmp")) {
            return "image/bmp";
        }
        if (FilenameExtension.equalsIgnoreCase("gif")) {
            return "image/gif";
        }
        if (FilenameExtension.equalsIgnoreCase("jpeg") ||
                FilenameExtension.equalsIgnoreCase("jpg") ||
                FilenameExtension.equalsIgnoreCase("png")) {
            return "image/jpeg";
        }
        if (FilenameExtension.equalsIgnoreCase("html")) {
            return "text/html";
        }
        if (FilenameExtension.equalsIgnoreCase("txt")) {
            return "text/plain";
        }
        if (FilenameExtension.equalsIgnoreCase("vsd")) {
            return "application/vnd.visio";
        }
        if (FilenameExtension.equalsIgnoreCase("pptx") ||
                FilenameExtension.equalsIgnoreCase("ppt")) {
            return "application/vnd.ms-powerpoint";
        }
        if (FilenameExtension.equalsIgnoreCase("docx") ||
                FilenameExtension.equalsIgnoreCase("doc")) {
            return "application/msword";
        }
        if (FilenameExtension.equalsIgnoreCase("xml")) {
            return "text/xml";
        }
        return "image/jpeg";
    }
}

      2、调用工具类的代码:


/**
     * 上传文件测试
     * @param multipartFile 待上传的文件
     * @return  上传在OSS文件的访问路径
     * @throws BusinessException  上传异常
     */
    public String uploadTest(MultipartFile multipartFile) throws BusinessException{
        try {
            uploadResult = OSSUtil.upload(multipartFile, OSSUtil.FileDirType.ZHANGHAN_TEST);
        } catch (Exception e) {
            LoggerUtil.logService(LoggerUtil.spManualLoan, "SPManualLoanServiceImpl-submitLoan", "call OSSUtil.upload; Exception:" + e.getMessage());
            throw new BusinessException(WrongMessageEnum.EXCEPTION_STORE);
        }
        return uploadResult;
    }

      3、问题&解决:


         (1) 问题:通过URL在浏览器中访问时报如下错:


 2a8ed165ba09d1cd96df16c9a8ec7bf8_Center.jpg


         (2)解决方案:在阿里云的控制台上,进入OSS的设置界面,将Bucket的访问权限由 私有 设置为 公共读


1e496b538e0ed4fb79ca87695837cf13_Center.jpg


【总结】


      阿里云现在很多公司都在用,阿里云稳定,安全,相对来说成本更低;给自己更多思考的是如何让项目减少成本,以及阿里云等带来的商业模式。


相关实践学习
借助OSS搭建在线教育视频课程分享网站
本教程介绍如何基于云服务器ECS和对象存储OSS,搭建一个在线教育视频课程分享网站。
相关文章
|
7月前
|
C# 对象存储
C#上传阿里云OSS工具类AliOSSTool
C#上传阿里云OSS工具类AliOSSTool
258 0
|
弹性计算 安全 Java
使用 OSS 的 bucket 进行文件上传下载|学习笔记
快速学习使用 OSS 的 bucket 进行文件上传下载
1075 0
|
3天前
|
存储 API 开发工具
OSS工作原理
OSS工作原理
24 6
|
4天前
|
存储 弹性计算 API
OSS使用方式
OSS使用方式
36 2
|
4天前
|
存储 容灾 API
OSS重要特性
OSS重要特性
20 1
|
4天前
|
存储 安全 Java
全面了解阿里云OSS使用方法
本文介绍了阿里云对象存储(OSS)的准备工作、服务开通、优势、使用步骤以及代码实现。首先,用户需要注册阿里云账号并进行实名认证,然后开通OSS服务,创建存储空间。阿里云OSS提供高可靠、安全、低成本的云存储,适合各种数据存储和分发场景。接着,通过官方SDK学习如何上传文件,并提供了Java代码示例。最后,展示了如何在Spring Boot项目中集成阿里云OSS,实现文件上传功能。
|
4天前
|
开发工具 对象存储 Android开发
对象存储oss使用问题之C++使用OSS SDK时遍历OSS上的文件时崩溃如何解决
《对象存储OSS操作报错合集》精选了用户在使用阿里云对象存储服务(OSS)过程中出现的各种常见及疑难报错情况,包括但不限于权限问题、上传下载异常、Bucket配置错误、网络连接问题、跨域资源共享(CORS)设定错误、数据一致性问题以及API调用失败等场景。为用户降低故障排查时间,确保OSS服务的稳定运行与高效利用。
31 0
|
4天前
|
JSON 前端开发 开发工具
对象存储oss使用问题之OSS文件下载中CRC64校验如何解决
《对象存储OSS操作报错合集》精选了用户在使用阿里云对象存储服务(OSS)过程中出现的各种常见及疑难报错情况,包括但不限于权限问题、上传下载异常、Bucket配置错误、网络连接问题、跨域资源共享(CORS)设定错误、数据一致性问题以及API调用失败等场景。为用户降低故障排查时间,确保OSS服务的稳定运行与高效利用。
64 0
|
4天前
|
安全 Java 网络安全
对象存储oss使用问题之使用oss上服务器后显示服务异常如何解决
《对象存储OSS操作报错合集》精选了用户在使用阿里云对象存储服务(OSS)过程中出现的各种常见及疑难报错情况,包括但不限于权限问题、上传下载异常、Bucket配置错误、网络连接问题、跨域资源共享(CORS)设定错误、数据一致性问题以及API调用失败等场景。为用户降低故障排查时间,确保OSS服务的稳定运行与高效利用。
40 0
|
4天前
|
存储 弹性计算 安全
oss配置Bucket属性
oss配置Bucket属性
101 1