PeaceSheep's blog PeaceSheep's blog
首页
  • 分类
  • 标签
  • 归档
相关链接
提建议&咨询&赞赏
GitHub (opens new window)

PeaceSheep

以最简洁、易懂的话解决问题
首页
  • 分类
  • 标签
  • 归档
相关链接
提建议&咨询&赞赏
GitHub (opens new window)
  • web

    • element-plus滚动条滚动到底部
    • mac使用docker部署nextcloud-aio并为本地域名添加https支持(未成功)
    • 前端处理POST类型的sse请求
    • 网站域名迁移的百度和谷歌SEO优化
    • 使用腾讯云OSS作为个人网站文件处理的存储库
      • 整体介绍
      • 预签名URL生成
      • 下载文件名问题
    • 使用cloudflare-r2搭建webdav
  • 物联网与路由器

  • 操作系统

  • 错误解决

  • 使用技巧

  • 教程
  • web
PeaceSheep
2025-02-18
目录

使用腾讯云OSS作为个人网站文件处理的存储库

在我之前的网站中,文件存储是自己写的,文件保存到服务端本地。这样的弊端很多,占用服务器空间、占用服务器流量、服务器带宽较低且不保证全球访问、难以很想拓展等。为了解决这个问题,我决定把存储单独抽离出来,由腾讯云oss完成。

# 整体介绍

下载文件:

上传文件:

核心就是一个腾讯云的预签名URL。

# 预签名URL生成

初始化客户端:

func NewCosClient(conf *config.Config) *cos.Client {
	u, _ := url.Parse(conf.CosConfig.Endpoint)
	b := &cos.BaseURL{BucketURL: u}
	client := cos.NewClient(b, &http.Client{
		Transport: &cos.AuthorizationTransport{
			SecretID:  conf.CosConfig.Ak, // 用户的 SecretId,建议使用子账号密钥,授权遵循最小权限指引,降低使用风险。子账号密钥获取可参见 https://cloud.tencent.com/document/product/598/37140
			SecretKey: conf.CosConfig.Sk, // 用户的 SecretKey,建议使用子账号密钥,授权遵循最小权限指引,降低使用风险。子账号密钥获取可参见 https://cloud.tencent.com/document/product/598/37140
		},
	})
	return client
}

1
2
3
4
5
6
7
8
9
10
11
12

其中endpoint我使用了全球加速域名,没有用自定义域名,缺点是不能下载部分特殊格式(例如apk)的文件。 ak和sk建议用子账号的,仅给这个子账号oss的读写权限。

生成预签名url:

func (s *FileService) GetSignedUrl(ctx context.Context, method, name string) (string, error) {
	signedURL, err := s.CosClient.Object.GetPresignedURL(ctx, method, name, s.Config.CosConfig.Ak, s.Config.CosConfig.Sk, time.Hour, nil)
	if err != nil {
		return "", err
	}
	return signedURL.String(), err
}
1
2
3
4
5
6
7

其中,如果是上传文件,则method使用PUT(不可以是POST),下载则是GET。这里的签名过期时间用了一小时,因为我的文件都是很小的文件,一小时足够了。如果你的文件较大,需要调大一些,不然下载到一半就会断开连接了。

name是文件的名称,可以带有""表示文件夹,例如"2025\2\18\xxx.jpg"

# 下载文件名问题

由于后端保存的时候不是按照实际文件名保存的,而是用的uuid,所以前端直接访问url会出现文件名是uuid的情况。

解决方法有一个就是前端使用blob,先把文件下载到一个blob对象,在用实际文件名下载到本地。不过这样有一个问题就是占用内存,而且看不到实际的下载进度。

另外一个办法是查阅腾讯云OSS文档 (opens new window)看到的。可以通过response-content-disposition请求参数来设置响应中的 Content-Disposition 头部的值。因此对签名函数进行了改进:

func (s *FileService) GetSignedUrl(ctx context.Context, method, ossPath, name string) (string, error) {

	opt := &cos.PresignedURLOptions{
		Query: &url.Values{},
		Header: &http.Header{},
	}
	if method == http.MethodGet {
		opt.Query.Add("response-content-disposition", fmt.Sprintf("attachment; filename=%s", name))
		// 重点是这一行,通过设置返回的Content-Disposition响应头来达到修改下载的文件名的目的。

	}

	signedURL, err := s.CosClient.Object.GetPresignedURL(ctx, method, ossPath, s.Config.CosConfig.Ak, s.Config.CosConfig.Sk, time.Hour, opt)
	if err != nil {
		return "", err
	}
	return signedURL.String(), err
}

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
编辑 (opens new window)
上次更新: 2025/04/15, 10:52:45
网站域名迁移的百度和谷歌SEO优化
使用cloudflare-r2搭建webdav

← 网站域名迁移的百度和谷歌SEO优化 使用cloudflare-r2搭建webdav→

最近更新
01
ubuntu安装g++显示已有但是输入g++又找不到命令
04-15
02
使用cloudflare-r2搭建webdav
04-08
03
LLM聚合平台客户端对比
03-29
更多文章>
Theme by Vdoing | Copyright © 2022-2025 PeaceSheep
冀ICP备2022004632号-1
  • 跟随系统
  • 浅色模式
  • 深色模式
  • 阅读模式