@@ -93,6 +93,15 @@ class S3
9393 */
9494 public static $ endpoint = 's3.amazonaws.com ' ;
9595
96+ /**
97+ * AWS Region
98+ *
99+ * @var string
100+ * @acess public
101+ * @static
102+ */
103+ public static $ region = '' ;
104+
96105 /**
97106 * Proxy information
98107 *
@@ -217,12 +226,13 @@ class S3
217226 * @param string $endpoint Amazon URI
218227 * @return void
219228 */
220- public function __construct ($ accessKey = null , $ secretKey = null , $ useSSL = false , $ endpoint = 's3.amazonaws.com ' )
229+ public function __construct ($ accessKey = null , $ secretKey = null , $ useSSL = false , $ endpoint = 's3.amazonaws.com ' , $ region = '' )
221230 {
222231 if ($ accessKey !== null && $ secretKey !== null )
223232 self ::setAuth ($ accessKey , $ secretKey );
224233 self ::$ useSSL = $ useSSL ;
225234 self ::$ endpoint = $ endpoint ;
235+ self ::$ region = $ region ;
226236 }
227237
228238
@@ -238,6 +248,39 @@ public function setEndpoint($host)
238248 }
239249
240250
251+ /**
252+ * Set the service region
253+ *
254+ * @param string $region
255+ * @return void
256+ */
257+ public function setRegion ($ region )
258+ {
259+ self ::$ region = $ region ;
260+ }
261+
262+
263+ /**
264+ * Get the service region
265+ *
266+ * @return string $region
267+ * @static
268+ */
269+ public static function getRegion ()
270+ {
271+ $ region = self ::$ region ;
272+
273+ // parse region from endpoint if not specific
274+ if (empty ($ region )) {
275+ if (preg_match ("/s3[.-](?:website-|dualstack\.)?(.+)\.amazonaws\.com/i " ,self ::$ endpoint ,$ match ) !== 0 && strtolower ($ match [1 ]) !== "external-1 " ) {
276+ $ region = $ match [1 ];
277+ }
278+ }
279+
280+ return empty ($ region ) ? 'us-east-1 ' : $ region ;
281+ }
282+
283+
241284 /**
242285 * Set AWS access key and secret key
243286 *
@@ -560,6 +603,8 @@ public static function putBucket($bucket, $acl = self::ACL_PRIVATE, $location =
560603 $ rest = new S3Request ('PUT ' , $ bucket , '' , self ::$ endpoint );
561604 $ rest ->setAmzHeader ('x-amz-acl ' , $ acl );
562605
606+ if ($ location === false ) $ location = self ::getRegion ();
607+
563608 if ($ location !== false )
564609 {
565610 $ dom = new DOMDocument ;
@@ -1958,13 +2003,14 @@ private static function __getHash($string)
19582003 * @param array $headers
19592004 * @param string $method
19602005 * @param string $uri
2006+ * @param string $data
19612007 * @param array $parameters
19622008 * @return array $headers
19632009 */
1964- public static function __getSignatureV4 ($ aHeaders , $ headers , $ method ='GET ' , $ uri ='' , $ parameters =array ())
1965- {
1966- // calculate the service name and region from the endpoint hostname: dynamodb.us-east-1.amazonaws.com
1967- list ( $ service , $ region, $ junk ) = explode ( ' . ' , self :: $ endpoint );
2010+ public static function __getSignatureV4 ($ aHeaders , $ headers , $ method ='GET ' , $ uri ='' , $ data = '' , $ parameters =array ())
2011+ {
2012+ $ service = ' s3 ' ;
2013+ $ region = S3 :: getRegion ( );
19682014
19692015 $ algorithm = 'AWS4-HMAC-SHA256 ' ;
19702016 $ amzHeaders = array ();
@@ -1986,7 +2032,7 @@ public static function __getSignatureV4($aHeaders, $headers, $method='GET', $uri
19862032 uksort ( $ amzHeaders , 'strcmp ' );
19872033
19882034 // payload
1989- $ payloadHash = isset ($ amzHeaders ['x-amz-content-sha256 ' ]) ? $ amzHeaders ['x-amz-content-sha256 ' ] : hash ('sha256 ' , '' );
2035+ $ payloadHash = isset ($ amzHeaders ['x-amz-content-sha256 ' ]) ? $ amzHeaders ['x-amz-content-sha256 ' ] : hash ('sha256 ' , $ data );
19902036
19912037 // CanonicalRequests
19922038 $ amzRequests [] = $ method ;
@@ -2346,6 +2392,7 @@ public function getResponse()
23462392 $ this ->headers ,
23472393 $ this ->verb ,
23482394 $ this ->uri ,
2395+ $ this ->data ,
23492396 $ this ->parameters
23502397 );
23512398 foreach ($ amzHeaders as $ k => $ v ) {
0 commit comments