簡體   English   中英

使用 AlamoFire 和 Presigned URL 將圖像上傳到 S3 存儲桶時出現問題

[英]Problem Uploading Images to S3 Bucket Using AlamoFire and Presigned URL

我為我的應用程序上傳到 S3 的方法是向我的 PHP 后端發送一個獲取請求,以生成一個預簽名的 URL。 我知道后端設置正確,因為運行以下命令成功地將圖像上傳到 S3 存儲桶:

curl -v -H "Content-Type: image/jpeg" -T./test.jpeg '<presignedURL>'

但是,嘗試在 Swift 中上傳圖像時遇到問題。 這是我當前的實現(請忽略垃圾,硬編碼,非錯誤檢查):

后端

<?php
require '../vendor/autoload.php';

use Aws\S3\S3Client;
use Aws\Exception\AwsException;

$response = array();

$client = S3Client::factory(array(
    'profile' => 'default',
    'version' => 'latest',
    'region' => 'us-east-2',
    'signature' => 'v4'
));

$command = $client->getCommand('PutObject', array(
    'Bucket'      => 'test',
    'Key'         => 'test.jpeg',
    'ContentType' => 'image/jpeg',
    'Body'        => ''
));

$signedUrl = $command->createPresignedUrl('+5 minutes');

$response['error'] = false;
$response['url'] = $signedUrl;

echo json_encode($response);

Swift代碼

import Foundation
import Alamofire

let getTokenURL = "http://192.168.1.59:8000/v1/upload.php"

func submitImage(image: UIImage, completion: @escaping (NSDictionary) -> Void) {
    
    AF.request(getTokenURL, method: .get).responseJSON { response in
        
        switch response.result {
        case.success(let value):
            let jsonData = value as! NSDictionary
            let url = jsonData.value(forKey: "url") as! String
            
            performUpload(image: image, postURL: url)
        
        case.failure(_):
            let error_msg: NSDictionary = [
                "error" : true,
                "message" : "Unknown error occurred. Please try again",
            ]
            
            //completion(error_msg)
        }
    }
                                
}

func performUpload(image: UIImage, postURL: String) {
    let imageData = image.jpegData(compressionQuality: 0.50)!
    
    AF.upload(imageData, to: postURL, headers: ["Content-Type":"image/jpeg"])    //likely the culprit line
}

目前 URL 從 submitImage() 中的 get 請求返回,並調用 performUpload(),這使得罪魁禍首(可能)成為我的 Swift 代碼段的最后一個問題。 我在閱讀文檔時無法弄清楚我應該做什么,並且大多數關於這個主題的指南都過時了,因為 AlamoFire 已經改變了它們的語法。 任何幫助將不勝感激。 謝謝!

編輯:我已經調整了 performUpload() function。 它現在將數據上傳到 s3 存儲桶,但是無法打開圖像。 我懷疑這是因為請求中的 header 不正確。 通過調試,我可以告訴 Content-Type header 無論如何都是“multipart/form-data”,所以我不確定這種方法是否可行:

struct HTTPBinResponse: Decodable { let url: String }

func performUpload(image: UIImage, postURL: String) {
    let imageData = image.jpegData(compressionQuality: 0.50)!
    
    AF.upload(multipartFormData: { multipartFormData in
        multipartFormData.append(imageData, withName: "file", mimeType: "image/jpeg")
    }, to: postURL, method: .put, headers: ["Content-Type":"image/jpeg"]).responseDecodable(of: HTTPBinResponse.self) { response in
            debugPrint(response)
    }  
}

對於未來的讀者,這里的關鍵是添加method: .put 這個問題的其他一切都很好。

我還發現您必須使用空的內容類型標頭。 S3很奇怪。

AF.upload(imageData, to: postURL, method: .put, headers: ["Content-Type": ""])

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM