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

Salesforce Apex类调用AWS API时遭遇文件格式无效错误求助

问题分析与解决思路

核心问题原因

你遇到的错误本质是请求体格式不符合AWS API的预期,具体问题出在这几点:

  1. 你将VersionData(Blob类型)转成Base64字符串后直接放入multipart请求体,AWS会把这当成普通文本内容,而非原始文件的二进制数据,自然无法识别为PDF格式。
  2. 硬编码Content-Type: application/octet-stream没有匹配实际文件的MIME类型,AWS可能依赖这个头部辅助识别文件格式。
  3. 手动拼接字符串形式的multipart请求容易出现换行符、边界符的格式错误,导致AWS解析文件内容失败。

解决步骤

1. 直接传输二进制数据,避免Base64编码

不要将Blob转成Base64字符串,而是直接将二进制内容嵌入multipart请求体。Apex的HttpRequest支持setBodyAsBlob方法,可以正确处理二进制数据。

2. 设置正确的文件MIME类型

根据ContentVersion的FileType字段动态设置Content-Type,比如PDF对应application/pdf,JPG对应image/jpeg等。

3. 正确构造multipart/form-data请求体

使用Blob拼接的方式构造请求体,确保边界符、换行符和内容格式完全符合HTTP规范。

修改后的代码示例

public class InvoiceUpload {
    // ... (原有代码省略)

    public static void uploadFileToAWS(Id contentVersionId) {
        try {
            // 查询ContentVersion,确保获取到VersionData和FileType
            ContentVersion cv = [SELECT Id, Title, VersionData, FileType FROM ContentVersion WHERE Id = :contentVersionId LIMIT 1];

            // 定义multipart边界
            String boundary = 'Boundary-' + String.valueOf(System.currentTimeMillis());
            String contentTypeHeader = 'multipart/form-data; boundary=' + boundary;

            // 构造请求体的各个部分:边界、头部、文件内容、结束边界
            Blob bodyBlob = Blob.valueOf('--' + boundary + '\r\n');
            bodyBlob = bodyBlob + Blob.valueOf('Content-Disposition: form-data; name="document"; filename="' + cv.Title + '"\r\n');
            
            // 根据FileType设置正确的Content-Type
            String fileContentType = getContentTypeByFileType(cv.FileType);
            bodyBlob = bodyBlob + Blob.valueOf('Content-Type: ' + fileContentType + '\r\n\r\n');
            
            // 添加原始文件二进制数据
            bodyBlob = bodyBlob + cv.VersionData;
            bodyBlob = bodyBlob + Blob.valueOf('\r\n--' + boundary + '--');

            // 创建HTTP请求
            HttpRequest req = new HttpRequest();
            req.setEndpoint('你的AWS API端点');
            req.setMethod('POST');
            req.setHeader('Content-Type', contentTypeHeader);
            // 添加授权令牌等其他头部
            // req.setHeader('Authorization', 'Bearer ' + 你的令牌);
            
            req.setBodyAsBlob(bodyBlob);

            // 发送请求并处理响应
            Http http = new Http();
            HTTPResponse res = http.send(req);
            System.debug('AWS响应状态码: ' + res.getStatusCode());
            System.debug('AWS响应内容: ' + res.getBody());

        } catch (Exception ex) {
            System.debug('异常信息: ' + ex.getMessage());
        }
    }

    // 辅助方法:根据Salesforce的FileType返回对应的MIME类型
    private static String getContentTypeByFileType(String fileType) {
        Map<String, String> typeMap = new Map<String, String>{
            'PDF' => 'application/pdf',
            'JPG' => 'image/jpeg',
            'JPEG' => 'image/jpeg',
            'PNG' => 'image/png',
            'JFIF' => 'image/jfif',
            'BMP' => 'image/bmp',
            'TIFF' => 'image/tiff'
        };
        return typeMap.getOrDefault(fileType.toUpperCase(), 'application/octet-stream');
    }
}

额外验证点

  • 确认ContentVersion的FileType字段值正确(比如PDF文件对应的FileType是'PDF')。
  • 检查AWS API的multipart/form-data参数名是否确实是document(代码中name="document"要和API要求一致)。
  • 发送请求前可以打印请求体的Blob大小,确认和原始文件大小一致,避免数据丢失。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.06.25 01:10:24