新手如何使用JavaSDK,轻松上手腾讯云COS?Java内调用对象存储桶

本文最后更新于:2021年12月16日 上午

COS对象存储是什么?对象存储COS(英文Cloud Object Storage)是腾讯云提供的一种存储海量文件的分布式存储服务,用户可通过网络随时存储和查看数据。
说白话,就是用来存储文件的,并且提供分布式存储,确保文件资源高可用。
虽然都说COS存储好,但是实际开发,怎么使用呢?快来看看Java开发,如何使用COS存储。

本教程和图文,腾讯云存储平台评估为三等奖,如果你需要更专业,建议看看他们评估的一等奖

虽然我感觉他们一等奖、二等奖专业性都不高,不清楚他们 怎么评定的:-)

高级腾讯云COS使用,不会安排了,安排也不用腾讯云COS◡ ヽ(`Д´)ノ ┻━┻

样例-图床

最近想搭建了一个图片交流和展示的网站,也可以理解为图床,存储大量的图片并生成缩略图方便后台管理。

本次就以图床系统的图片存储为例,对比传统存储在服务器内和存储在COS内的特点。

存储至服务器

最开始,我设置的是存储在服务器内,所以流程应该是:

单服务器结构
图片的存储,就是存储到服务器磁盘内:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
private boolean saveOriginal(String originalImage, MultipartFile imageFile) {
File originalImageFile = new File(originalImage);
// 判断路径是否存在,如果不存在则创建
if (!originalImageFile.getParentFile().exists()) {
originalImageFile.getParentFile().mkdirs();
}
try {
// 保存到服务器中
imageFile.transferTo(originalImageFile);
} catch (Exception e) {
e.printStackTrace();
return false;
}
return true;
}

同时使用Google thumbnailator进行缩略图生成(并存储在磁盘内):

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
private boolean saveThumbnail(String originalImage, String imageThumbnailPath) {
File thumbnailImageFile = new File(imageThumbnailPath);
if (!thumbnailImageFile.getParentFile().exists()) {
thumbnailImageFile.getParentFile().mkdirs();
}
try {
Thumbnails.of(originalImage)
.imageType(ThumbnailParameter.DEFAULT_IMAGE_TYPE)
.scale(1.0f)
.outputQuality(0.35f)
.outputFormat("webp")
.toFile(imageThumbnailPath);
return true;
} catch (IOException e) {
e.printStackTrace();
}
return false;
}

这样的效果也很不错:
系统投入使用的效果

但是,我使用的是腾讯云轻量应用服务器,会有这样有三个问题(使用CVM其实也差不多):

  • 单一服务器存储,服务器集群负载时候,如果服务器宕机,则图床无法使用。
  • 服务器空间有限,迁移数据复杂。
  • 服务器带宽有限,高并发读取图片,带宽肯定不够。

芜湖

所以,还是引入COS比较好。

存储至COS

为了解决上诉问题,我使用腾讯云的COS存储桶,进行图片存储,后续项目流程结构:
使用COS
可以看到,基本解决我们使用服务器存储的痛点(就是比较贵,但是可以买资源包╮( ̄▽ ̄””)╭)。
这个也是本文的重头戏,所以分为三大点:

  • 创建存储桶:创建一个新的COS存储桶,用于项目文件(本文指图片)的存储。
  • 获取API密钥:Java在发送资源至COS存储桶时,进行鉴权。
  • Java工具包编写:后台请求处理以及Java项目如何和COS存储桶交互。

本文的思路是:用户上传的图片(MultipartFile),转Inputstream输入流,最后上传到存储桶内。使用的方法是0PUT Object,好处是上传简单,坏处是:

  • 文件大小上限5GB
  • 无法分片上传

考虑到 图床里图片普遍10MB以下,不需要分片和“大附件”,所以我没选择其他复杂上传。大家如果有需求,记得参考官方文档 嗷。

或者联系客服姐姐也不错,比如我碰到无法签名验证时,客服帮我排查问题:
客服很Nice!

现在,上机正式开始。以下操作,部分参考:对象存储-指南

创建存储桶

既然要上传到COS存储桶,肯定事先需要有一个存储桶吧,所以我们现在来创建。
首先进入COS页面,点击立即使用,选择存储桶列表,创建存储桶:
购买存储桶01
购买存储桶02

其中:

  • image-test-1302972711:存储桶的唯一标识,重要!(后续需要使用)。
  • ap-nanjing:这里我买的是南京地区的存储桶,所以所属地域是:ap-nanjing(后续需要使用)

当然,我的需求是将其作为图床,所以上传的文件应该是:公有读私有写
设置访问权限

获取API密钥

存储桶已经创建完成,现在我们需要获取API密钥,其实就是需要:

  • SecretId:密钥代号
  • SecretKey:密钥具体内容

获取方法也很简单,访问API密钥管理,添加即可(建议创建子账号):
获取API
这里就是我们需要的SecretIdSecretKey
密钥
到此,前期的准备工作就完成了。接下来就是Java工具包编写问题了。

Java工具包编写

这里编写一个工具包,工具包不需要实例化,用其静态方法进行图片上传就可以了,比如:

1
2
3
4
public class TencentCOSUtil {
public static String UploadIMG(MultipartFile imgFile, String imgName){
}
}

添加依赖

之后,我们在业务层或者服务层就可以直接使用了。为了能连接腾讯云COS,我们需要用配套SDK(Software development kit),很简单,如果你有使用Maven骨架,只需要添加:

1
2
3
4
5
6
7
<!--        腾讯云对象存储-->
<dependency>
<groupId>com.qcloud</groupId>
<artifactId>cos_api</artifactId>
<version>5.6.54</version>
</dependency>
<dependency>

添加依赖

创建COSClient

我们需要创建一个COSClient,其中的属性需要的基本参数:

  • SecretId:密钥代号
  • SecretKey:密钥具体内容
  • region:COS存储桶所在地区

比如,这里我使用一个私有的静态方法进行COSClient创建:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
// 上文获得的SecretId
private static String secretId = "AKIDH************************UFv9cao";
// 上文获得的SecretKey
private static String secretKey = "wdp************************fKvLV";

private static COSClient getCosClient(){
// 1 初始化用户身份信息(secretId, secretKey)。
COSCredentials cred = new BasicCOSCredentials(secretId, secretKey);
// 2.1 设置存储桶的地域(上文获得)
Region region = new Region("ap-nanjing");
ClientConfig clientConfig = new ClientConfig(region);
// 2.2 使用https协议传输
clientConfig.setHttpProtocol(HttpProtocol.https);
// 3 生成 cos 客户端。
COSClient cosClient = new COSClient(cred, clientConfig);
// 返回COS客户端
return cosClient;
}

需要注意,这里的存储桶地域就是上文创建存储桶所设置的,如果你不知道填什么,可以到控制台内查看:
查看地域

这样调取getCosClient()方法就会获得COSClient实例了。

上传方法

现在,我们编写一个上传方法,也就是上传到存储桶:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
public static String UploadIMG(MultipartFile imgFile, String imgName) {
try {
InputStream inputStream = imgFile.getInputStream();
// 创建上传Object的Metadata
ObjectMetadata objectMetadata = new ObjectMetadata();
// - 使用输入流存储,需要设置请求长度
objectMetadata.setContentLength(inputStream.available());
// - 设置缓存
objectMetadata.setCacheControl("no-cache");
// - 设置Content-Type
objectMetadata.setContentType(getcontentType(imgName.substring(imgNam.lastIndexOf("."))));
// 指定文件将要存放的存储桶
String bucketName = "image-test-1302972711";
// 指定文件上传到 COS 上的路径,即对象键。
String key = "imageHost/" + imgName;
PutObjectResult putResult = getCosClient().putObject(bucketName, key,inputStream, objectMetadata);
// 成功存储后,返回图片MD5
return putResult.getContentMd5();
} catch (Exception e) {
e.printStackTrace();
// 发生IO异常、COS连接异常等,返回空
return null;
}
}

这里我采用输入流并重命名文件的方式,进行上传。需要注意:

  • 对象键:其实就是虚拟目录了,这里imageHost/开头,就是在存储桶的根目录下,创建一个imageHost文件夹。若后面接着文件名,顾名思义,就是创建imageHost文件夹后,并将文件放入其内。

我们编辑一个Controller进行测试:

1
2
3
4
5
6
7
8
9
10
// 测试
@PostMapping(
value = "/img/test",
produces = { "application/json;charset=UTF-8" }
)
public ResponseEntity test(@RequestParam(value = "IMG_Raw") MultipartFile IMG_Raw,
@RequestParam(value = "IMG_Name") String IMG_Name){
return ResponseEntity.ok("返回值为:"+TencentCOSUtil.UploadIMG(IMG_Raw,IMG_Name));

}

使用Postman发送Post请求进行测试:
postman发送请求
页面成功响应,返回的结果:
postman查看响应结果
其实返回的结果,就是我们上传文件的MD5的值(这些内容应该存到数据库里……)

访问腾讯云的COS控制台,就可以看到我们刚刚上传的文件了:
虚拟文件夹
上传的图片

到此,我们的图片“变对象“就完成了,当然还有一些后续优化操作,这里介绍一下嗷。

自定义域名

我们上传的对象,默认域名访问是:
域名访问
访问成功

这样,确实可以使用,就是……有点不优雅,如何绑定自己的域名呢?其实,也很简单,进入控制台设置即可:
设置CDN

需要注意:

  • 域名需要解析CNAME地址
  • 域名的管理,需要到CDN控制台,包括:强制HTTPS等。

图片处理

图片处理,其实更多是使用数据万象的服务了,可以将图片裁切、压缩等等,甚至是图片审核(是否涉黄、涉及政治等)。比如对 刚刚上传的小鸟鉴黄:

代码实现

1
2
3
4
5
6
7
8
9
10
11
12
13
14
public static String judgeIMG() {
//1.创建任务请求对象
ImageAuditingRequest request = new ImageAuditingRequest();
//2.添加请求参数 参数详情请见api接口文档
//2.1设置请求bucket
request.setBucketName("image-test-1302972711");
//2.2设置审核类型
request.setDetectType("porn");
//2.3设置bucket中的图片位置
request.setObjectKey("imageHost/动物-鸟.jpg");
//3.调用接口,获取任务响应对象
ImageAuditingResponse response = getCosClient().imageAuditing(request);
return response.getPornInfo().getHitFlag();
}

返回结果为0,也就是图片不涉黄。

可以看到,用腾讯云的 Java SDK处理还是很方便的。但是我发现图片标签识别等,还没有配套SDK方法,希望腾讯云 后期可以补上,不然……自己写Http请求,挺麻烦的。

END

嘿嘿,有多少人看到最后了呢?

其实,使用COS很简单,如果你以前觉得COS存储很麻烦,或者认为项目小,而没有使用COS…… 还是建议尝试。并且真正用了COS,感觉也不麻烦,甚至还很方便。

并且文件资源更加安全了,实在出现不可读取情况,还可以甩锅给腾讯╮( ̄▽ ̄””)╭,避免自己被打~~比存储在我们自己服务器好多了。

大家对此感兴趣,强烈建议试试嗷。不过大型项目,记得购买资源包哟。

加油嗷

推荐腾讯云COS嗷 。COS都差不多,用千牛、阿里都差不多。


若对文章很感兴趣,可以B站关注我ヾ(≧▽≦*)o

点击跳转“爱发电”页面(○` 3′○)

本博客所有文章除特别声明外,均采用 CC BY-SA 4.0 协议 ,转载请注明出处!