Details
-
Type:
Bug
-
Status:
Resolved
-
Priority:
Major
-
Resolution: Fixed
-
Affects Version/s: 1.8.0
-
Fix Version/s: 1.8.2
-
Component/s: Zend_Service_Amazon
-
Labels:None
Description
When you try to put an object into a bucket located in EU, you get an error from amazon, that this bucket must be accessed using the specific endpoint (bucketname.s3.amazonaws.com).
I have changed the function _makeRequest as follows. It seems to work so far with these changes. Haven't tested intensively.
/**
* Make a request to Amazon S3
*
* TODO: support bucket.s3.amazon.com style
*
* @param string $method
* @param string $path
* @param array $params
* @param array $headers
* @param string $data
* @return Zend_Http_Response
*/
public function _makeRequest($method, $path='', $params=null, $headers=array(), $data=null)
{
$retry_count = 0;
if (!is_array($headers)) {
$headers = array($headers);
}
$headers['Date'] = gmdate(DATE_RFC1123, time());
$parts = explode('/', $path);
self::addSignature($method, $path, $headers);
$client = self::getHttpClient();
$client->resetParameters();
// Work around buglet in HTTP client - it doesn't clean headers
// Remove when ZHC is fixed
$client->setHeaders(array('Content-MD5' => null, 'Expect' => null, 'Range' => null));
$endpoint = self::S3_ENDPOINT;
if (count($parts) > 1){
$endpoint = str_replace('http://', 'http://' . $parts[0] . '.', $endpoint);
array_shift($parts);
$client->setUri($endpoint.'/'.implode('/', $parts));
} else {
$client->setUri(self::S3_ENDPOINT.'/'.$path);
}
$client->setHeaders($headers);
if (is_array($params)) {
foreach ($params as $name=>$value) {
$client->setParameterGet($name, $value);
}
}
if (($method == 'PUT') && ($data !== null)) {
if (!isset($headers['Content-type'])) {
$headers['Content-type'] = self::getMimeType($path);
}
$client->setRawData($data, $headers['Content-type']);
}
do {
$retry = false;
$response = $client->request($method);
$response_code = $response->getStatus();
// Some 5xx errors are expected, so retry automatically
if ($response_code >= 500 && $response_code < 600 && $retry_count <= 5) {
$retry = true;
$retry_count++;
sleep($retry_count / 4 * $retry_count);
}
else if ($response_code == 307) {
// Need to redirect, new S3 endpoint given
// This should never happen as Zend_Http_Client will redirect automatically
}
else if ($response_code == 100) {
//echo 'OK to Continue';
}
} while ($retry);
return $response;
}
Attachments
1. |
Objects are never removed from S3 | |
|
Stanislav Malyshev |
Assigning to Jon