Excon::Errors::Forbidden(预期(200)<=> 实际(403 禁止)
Excon::Errors::Forbidden (Expected(200) <=> Actual(403 Forbidden)
当我尝试将图片上传到 "Car" 对象时,我被拒绝访问 S3。但是自从我添加 S3 以来,资产文件夹中的站点图像显示得很好。我得到的具体错误是:
2015-02-17T14:40:48.459629+00:00 app[web.1]: Excon::Errors::Forbidden (Expected(200) <=> Actual(403 Forbidden)
2015-02-17T14:40:48.459630+00:00 app[web.1]: excon.error.response
2015-02-17T14:40:48.459635+00:00 app[web.1]: "Connection" => "close"
2015-02-17T14:40:48.459637+00:00 app[web.1]: "Content-Type" => "application/xml"
2015-02-17T14:40:48.459639+00:00 app[web.1]: "Date" => "Tue, 17 Feb 2015 14:40:48 GMT"
2015-02-17T14:40:48.459640+00:00 app[web.1]: "Server" => "AmazonS3"
2015-02-17T14:40:48.459632+00:00 app[web.1]: :body => "<?xml version=\"1.0\" encoding=\"UTF-8\"?>\n<Error><Code>AccessDenied</Code><Message>Access Denied</Message><RequestId>2CE306ACD51F02A1</RequestId><HostId>tKLXUAKxyDFTMExl7kE+AuVVsEJOFqXh983li6N7R2UlYDXv1Z3GJRvW5zy1XIXVs2zArp310vg=</HostId></Error>"
2015-02-17T14:40:48.459642+00:00 app[web.1]: "x-amz-id-2" => ""part of secret key"="
"part of secret key" 明显被删节了。我试过创建不同的用户并使用新密钥,但这没有用。不知道从这里去哪里。
app/uploaders/picture_uploader
class PictureUploader < CarrierWave::Uploader::Base
include CarrierWave::MiniMagick
process resize_to_limit: [400, 400]
if Rails.env.production?
storage :fog
else
storage :file
end
# Override the directory where uploaded files will be stored.
# This is a sensible default for uploaders that are meant to be mounted:
def store_dir
"uploads/#{model.class.to_s.underscore}/#{mounted_as}/#{model.id}"
end
# Add a white list of extensions which are allowed to be uploaded.
def extension_white_list
%w(jpg jpeg gif png)
end
end
carrier_wave.rb
if Rails.env.production?
CarrierWave.configure do |config|
config.fog_credentials = {
# Configuration for Amazon S3
:provider => 'AWS',
:aws_access_key_id => ENV['S3_ACCESS_KEY'],
:aws_secret_access_key => ENV['S3_SECRET_KEY']
}
config.fog_directory = ENV['S3_BUCKET']
end
end
我相信这就是所有相关文件,如果还有更多要查看,请告诉我。不确定指定区域或高级用户是否有帮助,似乎没有帮助。
[编辑:此时我默认使用其他答案,尤其是当您处于生产环境中时。几年前,当我在构建一个易碎玩具时,这是一个对我有用的变通方法,但我同意在考虑到安全性时授予最小权限。]
我遇到了同样的错误,解决方案是从 AWS 管理控制台附加管理访问策略:
1) 在 http://aws.amazon.com/iam/
登录 AWS 管理控制台
2) 单击左侧导航窗格中的 "Policies"
3) Select "AdministratorAccess" 政策
4) 单击页面顶部的策略操作 > 附加
5) Select 与我的 S3_ACCESS_KEY、S3_SECRET_KEY 和 S3_BUCKET
关联的用户
6) 点击"Attach Policy"
仅授予我在 https://console.aws.amazon.com/s3/home 的存储桶的所有权限是不够的。
另一个告诉您授予 IAM 用户 AdministratorAccess 权限的答案从安全角度来看是个坏主意 - 它会允许任何有权访问这些密钥的人在您的帐户中执行任何操作,包括删除所有基础设施。
我还没有计算出 Carrierwave / Fog 需要的确切的最小权限集,但我得到的一个较小的权限集看起来像:
使用如下策略文档创建 AWS IAM 策略:
{
"Version": "2012-10-17",
"Statement": [
{
"Effect": "Allow",
"Action": "s3:*",
"Resource": "arn:aws:s3:::BUCKETNAME/*"
},
{
"Effect": "Allow",
"Action": "s3:*",
"Resource": "arn:aws:s3:::BUCKETNAME"
},
{
"Effect": "Allow",
"Action": [
"s3:ListAllMyBuckets"
],
"Resource": [
"*"
]
}
]
}
请注意,在 BUCKETNAME
和 BUCKETNAME/*
上指定 S3 操作不是错误 - 第一个与在存储桶上执行的 API 操作有关,而其次,存储桶中的存储对象。
设置完成后,我可以通过软件 (DragonDisk) 添加或删除存储桶中的文件。但是我在 assets:precompile 上遇到了同样的错误。我刚刚在权限 > Public 存储桶设置中的访问设置页面上删除了 ACL 的复选框:
此外,我使用的是主帐户,没有 IAM,所以 Rob Mulholand 的回答与我无关。
一种更简单的权限方法是:
{
"Version": "2012-10-17",
"Statement": [
{
"Effect": "Allow",
"Principal": {
"AWS": "<IAM user with programatic access>"
},
"Action": "s3:ListBucket",
"Resource": "arn:aws:s3:::BUCKETNAME"
},
{
"Effect": "Allow",
"Principal": {
"AWS": "<IAM user with programatic access>"
},
"Action": [
"s3:PutObjectAcl",
"s3:PutObject",
"s3:GetObject",
"s3:DeleteObject"
],
"Resource": "arn:aws:s3:::BUCKETNAME/*"
}
]
}
tl;dr:您还需要 s3:PutObjectAcl 权限。
(我没有检查它是否可以在没有 GetObject、DeleteObject 权限的情况下工作,因为在我的情况下我无论如何都想授予它们。)
如果您的存储桶不是 public,请确保 carrierwave.rb
中的 config.fog_public = false
。
当我尝试将图片上传到 "Car" 对象时,我被拒绝访问 S3。但是自从我添加 S3 以来,资产文件夹中的站点图像显示得很好。我得到的具体错误是:
2015-02-17T14:40:48.459629+00:00 app[web.1]: Excon::Errors::Forbidden (Expected(200) <=> Actual(403 Forbidden)
2015-02-17T14:40:48.459630+00:00 app[web.1]: excon.error.response
2015-02-17T14:40:48.459635+00:00 app[web.1]: "Connection" => "close"
2015-02-17T14:40:48.459637+00:00 app[web.1]: "Content-Type" => "application/xml"
2015-02-17T14:40:48.459639+00:00 app[web.1]: "Date" => "Tue, 17 Feb 2015 14:40:48 GMT"
2015-02-17T14:40:48.459640+00:00 app[web.1]: "Server" => "AmazonS3"
2015-02-17T14:40:48.459632+00:00 app[web.1]: :body => "<?xml version=\"1.0\" encoding=\"UTF-8\"?>\n<Error><Code>AccessDenied</Code><Message>Access Denied</Message><RequestId>2CE306ACD51F02A1</RequestId><HostId>tKLXUAKxyDFTMExl7kE+AuVVsEJOFqXh983li6N7R2UlYDXv1Z3GJRvW5zy1XIXVs2zArp310vg=</HostId></Error>"
2015-02-17T14:40:48.459642+00:00 app[web.1]: "x-amz-id-2" => ""part of secret key"="
"part of secret key" 明显被删节了。我试过创建不同的用户并使用新密钥,但这没有用。不知道从这里去哪里。
app/uploaders/picture_uploader
class PictureUploader < CarrierWave::Uploader::Base
include CarrierWave::MiniMagick
process resize_to_limit: [400, 400]
if Rails.env.production?
storage :fog
else
storage :file
end
# Override the directory where uploaded files will be stored.
# This is a sensible default for uploaders that are meant to be mounted:
def store_dir
"uploads/#{model.class.to_s.underscore}/#{mounted_as}/#{model.id}"
end
# Add a white list of extensions which are allowed to be uploaded.
def extension_white_list
%w(jpg jpeg gif png)
end
end
carrier_wave.rb
if Rails.env.production?
CarrierWave.configure do |config|
config.fog_credentials = {
# Configuration for Amazon S3
:provider => 'AWS',
:aws_access_key_id => ENV['S3_ACCESS_KEY'],
:aws_secret_access_key => ENV['S3_SECRET_KEY']
}
config.fog_directory = ENV['S3_BUCKET']
end
end
我相信这就是所有相关文件,如果还有更多要查看,请告诉我。不确定指定区域或高级用户是否有帮助,似乎没有帮助。
[编辑:此时我默认使用其他答案,尤其是当您处于生产环境中时。几年前,当我在构建一个易碎玩具时,这是一个对我有用的变通方法,但我同意在考虑到安全性时授予最小权限。]
我遇到了同样的错误,解决方案是从 AWS 管理控制台附加管理访问策略:
1) 在 http://aws.amazon.com/iam/
登录 AWS 管理控制台2) 单击左侧导航窗格中的 "Policies"
3) Select "AdministratorAccess" 政策
4) 单击页面顶部的策略操作 > 附加
5) Select 与我的 S3_ACCESS_KEY、S3_SECRET_KEY 和 S3_BUCKET
关联的用户6) 点击"Attach Policy"
仅授予我在 https://console.aws.amazon.com/s3/home 的存储桶的所有权限是不够的。
另一个告诉您授予 IAM 用户 AdministratorAccess 权限的答案从安全角度来看是个坏主意 - 它会允许任何有权访问这些密钥的人在您的帐户中执行任何操作,包括删除所有基础设施。
我还没有计算出 Carrierwave / Fog 需要的确切的最小权限集,但我得到的一个较小的权限集看起来像:
使用如下策略文档创建 AWS IAM 策略:
{
"Version": "2012-10-17",
"Statement": [
{
"Effect": "Allow",
"Action": "s3:*",
"Resource": "arn:aws:s3:::BUCKETNAME/*"
},
{
"Effect": "Allow",
"Action": "s3:*",
"Resource": "arn:aws:s3:::BUCKETNAME"
},
{
"Effect": "Allow",
"Action": [
"s3:ListAllMyBuckets"
],
"Resource": [
"*"
]
}
]
}
请注意,在 BUCKETNAME
和 BUCKETNAME/*
上指定 S3 操作不是错误 - 第一个与在存储桶上执行的 API 操作有关,而其次,存储桶中的存储对象。
设置完成后,我可以通过软件 (DragonDisk) 添加或删除存储桶中的文件。但是我在 assets:precompile 上遇到了同样的错误。我刚刚在权限 > Public 存储桶设置中的访问设置页面上删除了 ACL 的复选框:
此外,我使用的是主帐户,没有 IAM,所以 Rob Mulholand 的回答与我无关。
一种更简单的权限方法是:
{
"Version": "2012-10-17",
"Statement": [
{
"Effect": "Allow",
"Principal": {
"AWS": "<IAM user with programatic access>"
},
"Action": "s3:ListBucket",
"Resource": "arn:aws:s3:::BUCKETNAME"
},
{
"Effect": "Allow",
"Principal": {
"AWS": "<IAM user with programatic access>"
},
"Action": [
"s3:PutObjectAcl",
"s3:PutObject",
"s3:GetObject",
"s3:DeleteObject"
],
"Resource": "arn:aws:s3:::BUCKETNAME/*"
}
]
}
tl;dr:您还需要 s3:PutObjectAcl 权限。
(我没有检查它是否可以在没有 GetObject、DeleteObject 权限的情况下工作,因为在我的情况下我无论如何都想授予它们。)
如果您的存储桶不是 public,请确保 carrierwave.rb
中的 config.fog_public = false
。