You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何无需签名为公共文件URL设置自定义下载文件名?

解决方案:无需签名URL为公共S3/GCS文件设置自定义下载文件名

针对你的需求,分两种场景给出可行方案:

一、你拥有S3/GCS桶的控制权(可修改对象元数据)

这是最直接的方案,通过给公共对象配置Content-Disposition元数据,让浏览器自动使用自定义文件名下载。

AWS S3 实现(Java SDK 2.x)

S3不支持直接修改对象元数据,需通过复制对象到自身的方式更新元数据:

import software.amazon.awssdk.services.s3.S3Client;
import software.amazon.awssdk.services.s3.model.CopyObjectRequest;
import software.amazon.awssdk.services.s3.model.MetadataDirective;

public class S3UpdateMetadata {
    public static void setCustomDownloadFilename(String bucketName, String objectKey, String customFilename) {
        try (S3Client s3Client = S3Client.create()) {
            CopyObjectRequest copyRequest = CopyObjectRequest.builder()
                    .sourceBucket(bucketName)
                    .sourceKey(objectKey)
                    .destinationBucket(bucketName)
                    .destinationKey(objectKey)
                    .metadataDirective(MetadataDirective.REPLACE)
                    .contentDisposition("attachment; filename=\"" + customFilename + "\"")
                    .build();
            s3Client.copyObject(copyRequest);
        }
    }
}

配置完成后,直接访问该对象的公共URL,浏览器下载时会自动使用你设置的customFilename。

Google Cloud Storage 实现(Java SDK)

GCS支持直接更新对象元数据,无需复制:

import com.google.cloud.storage.Blob;
import com.google.cloud.storage.BlobId;
import com.google.cloud.storage.Storage;
import com.google.cloud.storage.StorageOptions;

public class GCSUpdateMetadata {
    public static void setCustomDownloadFilename(String bucketName, String objectName, String customFilename) {
        Storage storage = StorageOptions.getDefaultInstance().getService();
        BlobId blobId = BlobId.of(bucketName, objectName);
        Blob blob = storage.get(blobId);
        
        blob.toBuilder()
                .setContentDisposition("attachment; filename=\"" + customFilename + "\"")
                .build()
                .update();
    }
}

更新后,公共URL访问时浏览器会自动应用自定义文件名。

二、无法修改对象元数据(第三方公共文件)

如果是他人的公共S3/GCS文件,你无法修改其元数据,可通过以下两种方式实现:

方案1:Java后端中转下载

后端请求公共文件,在返回给前端的响应中设置Content-Disposition头:

import org.springframework.http.HttpHeaders;
import org.springframework.http.HttpStatus;
import org.springframework.http.ResponseEntity;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.RequestParam;
import org.springframework.web.client.RestTemplate;

import java.io.InputStream;
import java.nio.file.Files;
import java.nio.file.Path;
import java.nio.file.StandardCopyOption;

@GetMapping("/download-custom")
public ResponseEntity<byte[]> downloadWithCustomName(@RequestParam String publicUrl, @RequestParam String customFilename) throws Exception {
    RestTemplate restTemplate = new RestTemplate();
    InputStream inputStream = restTemplate.getForObject(publicUrl, InputStream.class);
    
    // 临时保存文件流(也可直接写入响应输出流)
    Path tempFile = Files.createTempFile("temp", null);
    Files.copy(inputStream, tempFile, StandardCopyOption.REPLACE_EXISTING);
    byte[] fileBytes = Files.readAllBytes(tempFile);
    
    HttpHeaders headers = new HttpHeaders();
    headers.add(HttpHeaders.CONTENT_DISPOSITION, "attachment; filename=\"" + customFilename + "\"");
    
    return new ResponseEntity<>(fileBytes, headers, HttpStatus.OK);
}

前端访问这个后端接口,即可下载带有自定义文件名的文件。

方案2:前端JS处理(注意CORS限制)

通过前端Fetch API获取文件Blob,再触发下载:

async function downloadWithCustomName(publicUrl, customFilename) {
    try {
        const response = await fetch(publicUrl);
        const blob = await response.blob();
        const blobUrl = URL.createObjectURL(blob);
        
        const link = document.createElement('a');
        link.href = blobUrl;
        link.download = customFilename;
        document.body.appendChild(link);
        link.click();
        
        document.body.removeChild(link);
        URL.revokeObjectURL(blobUrl);
    } catch (error) {
        console.error('下载失败:', error);
    }
}

注意:此方案要求公共文件所在的S3/GCS桶已配置CORS,允许你的前端域名发起跨域请求,否则会出现权限错误。

内容的提问来源于stack exchange,提问作者Sudhanshu Bansal

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.06.13 10:03:30