【问题标题】:AWS S3 Upload - Using AccessKey, SecretKey and SessionToken - iOS SDKAWS S3 上传 - 使用 AccessKey、SecretKey 和 SessionToken - iOS 开发工具包
【发布时间】:2015-08-14 21:12:18
【问题描述】:

我正在开发 iOS 应用程序,我需要将图像上传到 AWS S3Bucket。我已经从服务器获取了临时凭证(accessKey、secretKey、sessionToken 和 bucketName)来上传图片。

我发现很难识别正确的 API 以使用此凭据上传图像。

AWS 示例程序是使用 AWSCognitoCredentialsProvider 提供的。

我已经获得了可以工作的 Android 版本的代码,可以将图像上传到 S3。但我在 iOS SDK 中找不到相应的 API。

 BasicSessionCredentials basiccredentials = new BasicSessionCredentials(
                            MY_ACCESS_KEY_ID, MY_SECRET_KEY,
                            MY_SESSION_TOKEN);
AmazonS3Client s3Client = new AmazonS3Client(
                            basiccredentials);
TransferManager manager = new TransferManager(s3Client);
PutObjectRequest por = new PutObjectRequest(Constants.getPictureBucket(), Constants.PICTURE_NAME,file name);
 manager.upload(por);

iOS SDK 有以下 CredentialsProvider 类

  1. AWSCognitoCredentialsProvider
  2. AWSStaticCredentialsProvider
  3. AWSWebIdentityCredentialsProvider

AWSStaticCredentialsProvider 类仅接受 accessKeysecretKey。其他 2 个类需要不同的参数。

当我使用 AWSStaticCredentialsProvider 和 accessKey 和 secretKey 上传图片时,我收到以下错误消息

上传失败:[Error Domain=NSURLErrorDomain Code=-1017“无法解析 响应“用户信息=0x7f8773f70ee0 {NSUnderlyingError=0x7f8773f4bbb0 “操作无法完成。(kCFErrorDomainCFNetwork 错误 -1017.)", NSErrorFailingURLStringKey=https://s3.amazonaws.com/playfiksprofilepictures/429bfd812ea08e706bab868f3cd8b9c6.jpg, NSErrorFailingURLKey=https://s3.amazonaws.com/playfiksprofilepictures/429bfd812ea08e706bab868f3cd8b9c6.jpg, _kCFStreamErrorDomainKey=4, _kCFStreamErrorCodeKey=-1, NSLocalizedDescription=无法解析响应}]

此错误消息不清楚是凭据提供程序问题还是其他问题

非常感谢任何帮助解决此问题

谢谢

编辑

我用过@user3467204提供的示例程序

这是带有错误消息的输出(您提供的 AWS 访问密钥 ID 在我们的记录中不存在)。但是使用相同的键,android java 代码可以正常工作。

Android 代码使用 accessKey、secrectKey 和 sessionToken,而 iOS 代码只使用 accessKey 和 secrectKey。

2015-06-01 19:42:55.747 AWSV2Test[2191:170157] 图片位于 /Users/jpsasi/Library/Developer/CoreSimulator/Devices/E846AC10-82BE-40AA-BB7E-29796A8FAD2B/data/Containers/Bundle /Application/B59E9032-306D-4609-97D6-6C516638463A/AWSV2Test.app/testimage.png 2015-06-01 19:42:56.841 AWSV2Test[2191:170157] 上传 32677 / 35516 字节 2015-06-01 19:42:56.842 AWSV2Test[2191:170157] 上传 35516 / 35516 字节 2015-06-01 19:42:56.843 AWSV2Test[2191:170157] 上传 35516 / 35516 字节 2015-06-01 19:43:00.249 AWSV2Test[2191:170157] 上传 32677 / 35516 字节 2015-06-01 19:43:00.250 AWSV2Test[2191:170157] 上传 35516 / 35516 字节 2015-06-01 19:43:00.251 AWSV2Test[2191:170157] 上传 35516 / 35516 字节 2015-06-01 19:43:02.848 AWSV2Test[2191:170157] 上传 32677 / 35516 字节 2015-06-01 19:43:02.849 AWSV2Test[2191:170157] 上传 35516 / 35516 字节 2015-06-01 19:43:02.850 AWSV2Test[2191:170157] 上传 35516 / 35516 字节 2015-06-01 19:43:05.285 AWSV2Test[2191:170157] 上传 32677 / 35516 字节 2015-06-01 19:43:05.286 AWSV2Test[2191:170157] 上传 35516 / 35516 字节 2015-06-01 19:43:05.287 AWSV2Test[2191:170157] 上传 35516 / 35516 字节 2015-06-01 19:43:06.681 AWSV2Test[2191:170157] 错误 => 错误域 = com.amazonaws.AWSS3ErrorDomain 代码 = 3“操作无法完成。(com.amazonaws.AWSS3ErrorDomain 错误 3。)” UserInfo=0x7faea40171d0 {HostId=GeMapgMjrv43TZ4yFKmTjIw6EsZafbgk3GH9ATtbgIj1VpNNv6EjhmZhobHVm+/2, Message=您提供的 AWS 访问密钥 ID 在我们的记录中不存在。AWSAccessKeyId=ASIAIFYM7NXH3CSNXY3Q, Code=InvalidAccessKeyId, RequestId=48}}3

【问题讨论】:

  • 您能否发布您的代码,您是如何使用 AWSStaticCredentialsProvider 的?
  • 我从这里对 AWSStaticCredentialsProvider 做了同样的事情:dropbox.com/s/87ngdsnsgshovzt/awsv2test.tar.gz?dl=0,它工作正常。
  • @user3467204 感谢您提供示例程序。我用您提供的示例程序的输出更新了帖子。至少我得到了意义错误,但我仍然不确定我是否使用了正确的 API。因为我有 3 个键,而 iOS 程序只使用 2 个键。
  • IAM 用户凭证有两部分:访问密钥和秘密密钥。临时 STS 凭证有 3 个部分:访问密钥、秘密密钥和会话令牌。您似乎正在使用 STS 凭据中的访问密钥和密钥,但未提供会话令牌,因此 InvalidAccessKeyId 失败。另请参阅aws.amazon.com/articles/4617974389850313,了解使用 STS/WIF 凭据的 iOS 示例。
  • @jarmod 感谢您澄清我有临时 STS(3 部分凭据)。您提供的链接指向使用旧 AWS API 的代码 sn-p。我发现很难识别正确的 API 以使用 STS 3 Part 凭据。

标签: ios amazon-web-services amazon-s3


【解决方案1】:

如果您想使用在您的服务器上生成的临时凭证,您需要实现自己的凭证提供程序。我推荐以下方法:

  1. 在您的服务器上生成访问密钥、秘密密钥和会话令牌。您有多种语言选择,包括 Java、.NET、PHP、Ruby、Python 和 Node.js。
  2. 通过遵循AWSCredentialsProvider 来实现您的凭据提供程序。以AWSWebIdentityCredentialsProviderAWSCognitoCredentialsProvider 的实现为例。此凭据提供程序应:
    • 从您的服务器检索访问密钥、秘密密钥和会话密钥。
    • 在本地保留它们直到它们过期。
    • 在请求时返回凭据。
    • 如果它们已过期,请从您的服务器重新检索它们。
    • 在调用- refresh 时启动凭据刷新过程。

我鼓励你看看Amazon Cognito Identity。借助 Amazon Cognito,您可以使用公共登录提供商(例如 Amazon、Facebook、Google 和任何 OpenID Connect 兼容提供商)或使用您自己的用户身份系统来创建唯一的最终用户标识符,以访问 AWS 云服务。它涵盖了许多自定义凭据提供程序用例,并且更易于使用和管理。

【讨论】:

  • 感谢您提供的详细信息。让我尝试实现我自己的 CredentialProvider。
  • @jpsasi 实施 CredentialProvider 将是一项很好的技术练习,但除非您确实需要这样做,因为您有自定义要求,否则 Cognito 可能会是更好的方法。
  • @jarmod 这是一个客户端项目,我无法控制选择 cognito。他们通过 REST API 提供临时凭证来上传图片。
  • @jpsasi 您是否最终实现了自己的 AWSCredentialProvider?由于 AWSStaticCredentialsProvider 上缺少“刷新”实施,是否需要这样做?我使用 AWSStaticCredentialsProvider 遇到了同样的错误,密钥是在我的 API 服务器上生成的。
  • 没有。我尝试过实现自己的提供程序。但它没有用。所以我说服了我的客户使用 Congnito 并实施了同样的方法。现在可以了。
猜你喜欢
  • 1970-01-01
  • 2023-03-15
  • 1970-01-01
  • 2017-09-06
  • 1970-01-01
  • 2011-11-10
  • 1970-01-01
  • 2020-10-29
  • 2021-07-13
相关资源
最近更新 更多