2012-12-08 62 views
2

我想知道後處理文件到谷歌雲存儲,如果任何人都可以告訴我正確的語法&格式化服務帳戶的POST對象發送到水桶請求時?我試圖以編程方式使用它the HttpComponents library。我設法從我GoogleCredential獲得令牌,但我每次構造POST請求的時候,我得到:獲得403(禁止)試圖從服務帳戶

HTTP/1.1 403禁止

<?xml version='1.0' encoding='UTF-8'?><Error><Code>AccessDenied</Code><Message>Access denied.</Message><Details>鬥名</Details></Error>

該谷歌documentation描述請求方法,提到使用HTML表單張貼,但我希望這是不是暗示只有這樣,才能把工作做好。我知道HttpComponents有辦法通過使用UrlEncodedFormEntity明確創建表單數據,但它不支持多數據。這就是我使用MultipartEntity類的原因。我的代碼如下:

MultipartEntity entity = new MultipartEntity(HttpMultipartMode.BROWSER_COMPATIBLE); 
String token = credential.getAccessToken(); 
entity.addPart("Authorization", new StringBody("OAuth " + token)); 
String date = formatDate(new Date()); 
entity.addPart("Date", new StringBody(date)); 
entity.addPart("Content-Type", new StringBody("multipart/form-data")); 
entity.addPart("bucket", new StringBody(bucket)); 
entity.addPart("key", new StringBody("fileName")); 
entity.addPart("success_action_redirect", new StringBody("/storage")); 
File uploadFile = new File("pathToFile"); 
FileBody fileBody = new FileBody(uploadFile, "text/xml"); 
entity.addPart("file", fileBody); 
httppost.setEntity(entity); 
System.out.println("Posting URI = "+httppost.toString()); 
HttpResponse response = client.execute(httppost); 
HttpEntity resp_entity = response.getEntity(); 

正如我所說,我能得到一個實際的道理,所以我敢肯定,問題是如何我已經形成,而不是沒有正確驗證的請求。

請記住:

  1. 這是由服務帳戶進行。
  2. 這意味着它有讀/寫訪問

感謝您的閱讀,我感謝所有幫助!

+0

你可以發佈''bucket''和''httppost.toString()''的內容嗎?此外,我不知道你是否應該內容編碼被設置爲UTF-8這樣的。 – jterrace

+0

順便說一下,我不是太肯定它的任何=)...但我認爲你是對有關內容的編碼。我只是把它扔在那裏,因爲它沒有它也沒有工作。只是測試不同的領域。我會編輯它。 – klactose

+0

你是如何決定POST和PUT的? – fejta

回答

2

由於您使用的OAuth訪問令牌只能與PUT一起使用,並且只能使用POST的表單字段,因此您似乎正在將PUTPOST方法混淆。

載對象將使用類似的最簡單方法如下:

HttpPut put = new HttpPut("https://storage.googleapis.com/" + BUCKET + "/" + OBJECT); 
put.addHeader("Authorization", "Bearer " + credential.getAccessToken()); 
put.setEntity(new StringEntity("object data")); 
client.execute(put); 

也是可能的,但更復雜的不僅僅是使用PUT,創建一個簽名的HTML表單用戶能用於使用POST上傳對象。你的表格要求類似如下的signed policy document

PolicyDocument = {"expiration": "2010-06-16T11:11:11Z", 
"conditions": [ 
    ["starts-with", "$key", "" ], 
    {"acl": "bucket-owner-read" }, 
    {"bucket": "travel-maps"}, 
    {"success_action_redirect": "http://www.example.com/success_notification.html" }, 
    ["eq", "$Content-Type", "image/jpeg" ], 
    ["content-length-range", 0, 1000000] 
    ] 
} 
Policy = Base_64_Encoding_Of(PolicyDocument) 
MessageDigest = Sha256_With_RSA(SecretKey, Policy) 
Signature = Base64_Encoding_Of(MessageDigest) 

導致下面的HTML:

<form action="http://travel-maps.storage.googleapis.com" method="post" enctype="multipart/form-data"> 
<input type="text" name="key" value=""> 
<input type="hidden" name="bucket" value="travel-maps"> 
<input type="hidden" name="Content-Type" value="image/jpeg"> 
<input type="hidden" name="GoogleAccessId" value="[email protected]"> 
<input type="hidden" name="acl" value="bucket-owner-read"> 
<input type="hidden" name="success_action_redirect" value="http://www.example.com/success_notification.html"> 
<input type="hidden" name="policy" value="ajUJTm9jAHADNmF0aW9uIjogIjIwMTAtMDYtMTZUMTSAMPLEE6MTE6MTFaIiwNCSAMPLEiAgWyJzdGFydSAMPLEAiaHR0cDovL3maWNhSAMPLEIiB9LASAMPLEWN0aW9uX3JlZGlyZW"> 
<input type="hidden" name="signature" value="BSAMPLEaASAMPLE6SAMPLE+SAMPPLEqSAMPLEPSAMPLE+SAMPLEgSAMPLEzCPlgWREeF7oPGowkeKk7J4WApzkzxERdOQmAdrvshKSzUHg8Jqp1lw9tbiJfE2ExdOOIoJVmGLoDeAGnfzCd4fTsWcLbal9sFpqXsQI8IQi1493mw="> 

<input name="file" type="file"> 
<input type="submit" value="Upload"> 
</form> 

注意政策和簽名領域以及其他的隱藏字段,符合規定的條件,在政策文件中。具體bucket == travel-maps,acl == bucket-owner-read

+0

感謝您的反饋!今晚晚些時候我會嘗試拍攝這張照片。絕對感謝指導 – klactose

+0

你展示的例子工作出色!謝謝! – klactose