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

Rails 6本地传Amazon S3正常,Railway生产环境报422错误求助

问题

本地环境将图片上传至Amazon S3完全正常,但部署到railway.app生产服务器时,出现不明原因的422错误,且已确认S3存储桶权限配置正确。

尝试两种上传方式均触发错误:

  • 将图片附加到记录并保存时
  • 调用ActiveStorage::Blob.create_before_direct_upload!创建Blob时,代码如下:
blob = ActiveStorage::Blob.create_before_direct_upload!(filename: blob_args[:filename],
                                                    byte_size: blob_args[:byte_size], 
                                                    checksum: blob_args[:checksum], 
                                                    content_type: blob_args[:content_type])

补充说明:该关联记录无任何验证规则。

自定义DirectUploadsController代码如下:

class DirectUploadsController < ActiveStorage::DirectUploadsController
  include ActionController::HttpAuthentication::Basic::ControllerMethods
  skip_before_action :verify_authenticity_token

  def create
    blob = ActiveStorage::Blob.create_before_direct_upload!(filename: blob_args[:filename],
                                                            byte_size: blob_args[:byte_size], 
                                                            checksum: blob_args[:checksum], 
                                                            content_type: blob_args[:content_type])
    render json: direct_upload_json(blob)
  end

  private

  def direct_upload_json(blob)
    blob.as_json(root: false, methods: :signed_id).merge(service_url: url_for(blob)).merge(direct_upload: {
                                                                                             url: blob.service_url_for_direct_upload,
                                                                                             headers: blob.service_headers_for_direct_upload
                                                                                           })
  end
end

前端使用Angular 2向Rails API发送图片,本地正常,生产环境创建Blob或附加图片时均返回422,前端代码:

uploadFile = (name:any, the_attachment:any) => { // name is a string, the_attachment is a File object

  const upload = new DirectUpload(
    the_attachment,
    'https://some-api.railway.app/rails/active_storage/direct_uploads', // This url is exposed by default in your app
  );
  upload.create((error, blob) => {
    if (error) {
      console.log(error)
    } else {
      let signed_id = blob.signed_id;
      let request_body = {
        logo: signed_id
      }
      this.http.put("https://some-api.railway.app/api/v1/upload_logo/38", request_body).subscribe((resp)=>{
        console.log(resp)
      })
    }
  });

AWS CORS策略配置:

[
    {
        "AllowedHeaders": [
            "*"
        ],
        "AllowedMethods": [
            "PUT",
            "POST",
            "DELETE",
            "GET"
        ],
        "AllowedOrigins": [
            "https://some-app.up.railway.app/",
            "https://some-admin.netlify.app/",
        ],
        "ExposeHeaders": []
    }
]

前端错误日志:

POST https://some-app.up.railway.app/rails/active_storage/direct_uploads 422
...
main.a7200f0b44d7afc6.js:1 Error creating Blob for "386-3863556_ruby-clipart-vector-ruby-programming-language-png-transparent.png". Status: 422

可能的解决方向

1. 检查生产环境ActiveStorage配置

  • 确认railway.app上的环境变量AWS_ACCESS_KEY_ID、AWS_SECRET_ACCESS_KEY、AWS_REGION、AWS_BUCKET是否正确设置,无拼写错误或值缺失。
  • 验证生产环境storage.yml配置是否指向正确的S3服务,比如是否按需开启public: true,无多余配置项干扰。

2. 排查Blob创建的参数合法性

422错误多由参数不合法导致,可从以下几点排查:

  • 查看Rails生产日志(railway.app控制台可获取),日志会明确标注422错误的具体触发原因,比如哪个参数未通过验证。
  • 验证前端传递的checksum是否为文件的SHA-256哈希Base64编码,确保生产环境中前端生成的checksum与后端计算一致。
  • 确认content_type是否符合S3允许的类型,无生产环境Rails额外限制的情况。

3. 修正CORS配置的域名格式

当前CORS配置中AllowedOrigins的域名末尾带斜杠,会导致匹配失败,修正为:

"AllowedOrigins": [
    "https://some-app.up.railway.app",
    "https://some-admin.netlify.app"
],

S3对域名匹配严格,带斜杠与不带斜杠会被视为不同域名,修正后重新保存CORS配置。

4. 确认自定义控制器的参数获取逻辑

自定义DirectUploadsController需确保blob_args正确提取前端参数,添加强参数处理:

def blob_args
  params.require(:blob).permit(:filename, :byte_size, :checksum, :content_type)
end

若参数未正确提取,会导致参数缺失触发422错误。

5. 验证railway.app与S3的网络连通性

在railway.app控制台执行curl命令测试S3连通性,比如:

curl https://your-bucket-name.s3.your-region.amazonaws.com

确认服务器无网络策略或防火墙限制S3访问。


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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.08.19 16:46:37