2021-04-19 03:41:13 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								// Copyright (c) 2015-2021 MinIO, Inc.
  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								//
  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								// This file is part of MinIO Object Storage stack
  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								//
  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								// This program is free software: you can redistribute it and/or modify
  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								// it under the terms of the GNU Affero General Public License as published by
  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								// the Free Software Foundation, either version 3 of the License, or
  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								// (at your option) any later version.
  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								//
  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								// This program is distributed in the hope that it will be useful
  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								// but WITHOUT ANY WARRANTY; without even the implied warranty of
  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								// GNU Affero General Public License for more details.
  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								//
  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								// You should have received a copy of the GNU Affero General Public License
  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								// along with this program.  If not, see <http://www.gnu.org/licenses/>.
  
						 
					
						
							
								
									
										
										
										
											2016-09-14 10:00:01 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								package  cmd  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								import  (  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									"bytes" 
							 
						 
					
						
							
								
									
										
										
										
											2018-03-16 04:27:16 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									"context" 
							 
						 
					
						
							
								
									
										
										
										
											2016-09-14 10:00:01 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									"encoding/base64" 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									"fmt" 
							 
						 
					
						
							
								
									
										
										
										
											2022-09-20 02:05:16 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									"io" 
							 
						 
					
						
							
								
									
										
										
										
											2016-09-14 10:00:01 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									"mime/multipart" 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									"net/http" 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									"net/http/httptest" 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-14 05:41:13 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									"net/url" 
							 
						 
					
						
							
								
									
										
										
										
											2023-03-20 16:06:45 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									"strings" 
							 
						 
					
						
							
								
									
										
										
										
											2016-09-14 10:00:01 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									"testing" 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									"time" 
							 
						 
					
						
							
								
									
										
										
										
											2016-11-23 10:18:22 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2021-10-28 22:35:28 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									"github.com/dustin/go-humanize" 
							 
						 
					
						
							
								
									
										
										
										
											2016-09-14 10:00:01 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								)  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								const  (  
						 
					
						
							
								
									
										
										
										
											2020-05-26 07:51:32 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									iso8601DateFormat  =  "20060102T150405Z" 
							 
						 
					
						
							
								
									
										
										
										
											2016-09-14 10:00:01 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								)  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2016-11-21 20:15:26 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								func  newPostPolicyBytesV4WithContentRange ( credential ,  bucketName ,  objectKey  string ,  expiration  time . Time )  [ ] byte  {  
						 
					
						
							
								
									
										
										
										
											2017-03-19 02:28:41 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									t  :=  UTCNow ( ) 
							 
						 
					
						
							
								
									
										
										
										
											2016-11-21 20:15:26 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									// Add the expiration date.
 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-26 07:51:32 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									expirationStr  :=  fmt . Sprintf ( ` "expiration": "%s" ` ,  expiration . Format ( iso8601TimeFormat ) ) 
							 
						 
					
						
							
								
									
										
										
										
											2016-11-21 20:15:26 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									// Add the bucket condition, only accept buckets equal to the one passed.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									bucketConditionStr  :=  fmt . Sprintf ( ` ["eq", "$bucket", "%s"] ` ,  bucketName ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// Add the key condition, only accept keys equal to the one passed.
 
							 
						 
					
						
							
								
									
										
										
										
											2016-12-05 04:23:19 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									keyConditionStr  :=  fmt . Sprintf ( ` ["eq", "$key", "%s/upload.txt"] ` ,  objectKey ) 
							 
						 
					
						
							
								
									
										
										
										
											2016-11-21 20:15:26 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									// Add content length condition, only accept content sizes of a given length.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									contentLengthCondStr  :=  ` ["content-length-range", 1024, 1048576] ` 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// Add the algorithm condition, only accept AWS SignV4 Sha256.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									algorithmConditionStr  :=  ` ["eq", "$x-amz-algorithm", "AWS4-HMAC-SHA256"] ` 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// Add the date condition, only accept the current date.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									dateConditionStr  :=  fmt . Sprintf ( ` ["eq", "$x-amz-date", "%s"] ` ,  t . Format ( iso8601DateFormat ) ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// Add the credential string, only accept the credential passed.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									credentialConditionStr  :=  fmt . Sprintf ( ` ["eq", "$x-amz-credential", "%s"] ` ,  credential ) 
							 
						 
					
						
							
								
									
										
										
										
											2019-04-02 14:45:32 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									// Add the meta-uuid string, set to 1234
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									uuidConditionStr  :=  fmt . Sprintf ( ` ["eq", "$x-amz-meta-uuid", "%s"] ` ,  "1234" ) 
							 
						 
					
						
							
								
									
										
										
										
											2016-11-21 20:15:26 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// Combine all conditions into one string.
 
							 
						 
					
						
							
								
									
										
										
										
											2019-04-02 14:45:32 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									conditionStr  :=  fmt . Sprintf ( ` "conditions":[%s, %s, %s, %s, %s, %s, %s] ` ,  bucketConditionStr , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										keyConditionStr ,  contentLengthCondStr ,  algorithmConditionStr ,  dateConditionStr ,  credentialConditionStr ,  uuidConditionStr ) 
							 
						 
					
						
							
								
									
										
										
										
											2016-11-21 20:15:26 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									retStr  :=  "{" 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									retStr  =  retStr  +  expirationStr  +  "," 
							 
						 
					
						
							
								
									
										
										
										
											2021-11-17 01:28:29 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									retStr  +=  conditionStr 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									retStr  +=  "}" 
							 
						 
					
						
							
								
									
										
										
										
											2016-11-21 20:15:26 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  [ ] byte ( retStr ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2016-10-22 23:57:12 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								// newPostPolicyBytesV4 - creates a bare bones postpolicy string with key and bucket matches.
  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								func  newPostPolicyBytesV4 ( credential ,  bucketName ,  objectKey  string ,  expiration  time . Time )  [ ] byte  {  
						 
					
						
							
								
									
										
										
										
											2017-03-19 02:28:41 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									t  :=  UTCNow ( ) 
							 
						 
					
						
							
								
									
										
										
										
											2016-09-14 10:00:01 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									// Add the expiration date.
 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-26 07:51:32 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									expirationStr  :=  fmt . Sprintf ( ` "expiration": "%s" ` ,  expiration . Format ( iso8601TimeFormat ) ) 
							 
						 
					
						
							
								
									
										
										
										
											2016-09-14 10:00:01 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									// Add the bucket condition, only accept buckets equal to the one passed.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									bucketConditionStr  :=  fmt . Sprintf ( ` ["eq", "$bucket", "%s"] ` ,  bucketName ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// Add the key condition, only accept keys equal to the one passed.
 
							 
						 
					
						
							
								
									
										
										
										
											2016-12-05 04:23:19 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									keyConditionStr  :=  fmt . Sprintf ( ` ["eq", "$key", "%s/upload.txt"] ` ,  objectKey ) 
							 
						 
					
						
							
								
									
										
										
										
											2016-09-14 10:00:01 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									// Add the algorithm condition, only accept AWS SignV4 Sha256.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									algorithmConditionStr  :=  ` ["eq", "$x-amz-algorithm", "AWS4-HMAC-SHA256"] ` 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// Add the date condition, only accept the current date.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									dateConditionStr  :=  fmt . Sprintf ( ` ["eq", "$x-amz-date", "%s"] ` ,  t . Format ( iso8601DateFormat ) ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// Add the credential string, only accept the credential passed.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									credentialConditionStr  :=  fmt . Sprintf ( ` ["eq", "$x-amz-credential", "%s"] ` ,  credential ) 
							 
						 
					
						
							
								
									
										
										
										
											2019-04-02 14:45:32 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									// Add the meta-uuid string, set to 1234
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									uuidConditionStr  :=  fmt . Sprintf ( ` ["eq", "$x-amz-meta-uuid", "%s"] ` ,  "1234" ) 
							 
						 
					
						
							
								
									
										
										
										
											2016-09-14 10:00:01 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// Combine all conditions into one string.
 
							 
						 
					
						
							
								
									
										
										
										
											2019-04-02 14:45:32 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									conditionStr  :=  fmt . Sprintf ( ` "conditions":[%s, %s, %s, %s, %s, %s] ` ,  bucketConditionStr ,  keyConditionStr ,  algorithmConditionStr ,  dateConditionStr ,  credentialConditionStr ,  uuidConditionStr ) 
							 
						 
					
						
							
								
									
										
										
										
											2016-09-14 10:00:01 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									retStr  :=  "{" 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									retStr  =  retStr  +  expirationStr  +  "," 
							 
						 
					
						
							
								
									
										
										
										
											2021-11-17 01:28:29 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									retStr  +=  conditionStr 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									retStr  +=  "}" 
							 
						 
					
						
							
								
									
										
										
										
											2016-09-14 10:00:01 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  [ ] byte ( retStr ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2016-10-22 23:57:12 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								// newPostPolicyBytesV2 - creates a bare bones postpolicy string with key and bucket matches.
  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								func  newPostPolicyBytesV2 ( bucketName ,  objectKey  string ,  expiration  time . Time )  [ ] byte  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// Add the expiration date.
 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-26 07:51:32 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									expirationStr  :=  fmt . Sprintf ( ` "expiration": "%s" ` ,  expiration . Format ( iso8601TimeFormat ) ) 
							 
						 
					
						
							
								
									
										
										
										
											2016-10-22 23:57:12 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									// Add the bucket condition, only accept buckets equal to the one passed.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									bucketConditionStr  :=  fmt . Sprintf ( ` ["eq", "$bucket", "%s"] ` ,  bucketName ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// Add the key condition, only accept keys equal to the one passed.
 
							 
						 
					
						
							
								
									
										
										
										
											2016-12-05 04:23:19 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									keyConditionStr  :=  fmt . Sprintf ( ` ["starts-with", "$key", "%s/upload.txt"] ` ,  objectKey ) 
							 
						 
					
						
							
								
									
										
										
										
											2016-10-22 23:57:12 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// Combine all conditions into one string.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									conditionStr  :=  fmt . Sprintf ( ` "conditions":[%s, %s] ` ,  bucketConditionStr ,  keyConditionStr ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									retStr  :=  "{" 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									retStr  =  retStr  +  expirationStr  +  "," 
							 
						 
					
						
							
								
									
										
										
										
											2021-11-17 01:28:29 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									retStr  +=  conditionStr 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									retStr  +=  "}" 
							 
						 
					
						
							
								
									
										
										
										
											2016-10-22 23:57:12 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  [ ] byte ( retStr ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2023-03-20 16:06:45 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								// Wrapper
  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								func  TestPostPolicyReservedBucketExploit ( t  * testing . T )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ExecObjectLayerTestWithDirs ( t ,  testPostPolicyReservedBucketExploit ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								// testPostPolicyReservedBucketExploit is a test for the exploit fixed in PR
  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								// #16849
  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								func  testPostPolicyReservedBucketExploit ( obj  ObjectLayer ,  instanceType  string ,  dirs  [ ] string ,  t  TestErrHandler )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  err  :=  newTestConfig ( globalMinioDefaultRegion ,  obj ) ;  err  !=  nil  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										t . Fatalf ( "Initializing config.json failed" ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// Register the API end points with Erasure/FS object layer.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									apiRouter  :=  initTestAPIEndPoints ( obj ,  [ ] string { "PostPolicy" } ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									credentials  :=  globalActiveCred 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									bucketName  :=  minioMetaBucket 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									objectName  :=  "config/x" 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// This exploit needs browser to be enabled.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ! globalBrowserEnabled  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										globalBrowserEnabled  =  true 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										defer  func ( )  {  globalBrowserEnabled  =  false  } ( ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// initialize HTTP NewRecorder, this records any mutations to response writer inside the handler.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									rec  :=  httptest . NewRecorder ( ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									req ,  perr  :=  newPostRequestV4 ( "" ,  bucketName ,  objectName ,  [ ] byte ( "pwned" ) ,  credentials . AccessKey ,  credentials . SecretKey ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  perr  !=  nil  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										t . Fatalf ( "Test %s: Failed to create HTTP request for PostPolicyHandler: <ERROR> %v" ,  instanceType ,  perr ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									contentTypeHdr  :=  req . Header . Get ( "Content-Type" ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									contentTypeHdr  =  strings . Replace ( contentTypeHdr ,  "multipart/form-data" ,  "multipart/form-datA" ,  1 ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									req . Header . Set ( "Content-Type" ,  contentTypeHdr ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									req . Header . Set ( "User-Agent" ,  "Mozilla" ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2024-01-18 15:03:17 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									// Since `apiRouter` satisfies `http.Handler` it has a ServeHTTP to execute the logic of the handler.
 
							 
						 
					
						
							
								
									
										
										
										
											2023-03-20 16:06:45 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									// Call the ServeHTTP to execute the handler.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									apiRouter . ServeHTTP ( rec ,  req ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ctx ,  cancel  :=  context . WithCancel ( GlobalContext ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									defer  cancel ( ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// Now check if we actually wrote to backend (regardless of the response
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// returned by the server).
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									z  :=  obj . ( * erasureServerPools ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									xl  :=  z . serverPools [ 0 ] . sets [ 0 ] 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									erasureDisks  :=  xl . getDisks ( ) 
							 
						 
					
						
							
								
									
										
										
										
											2024-01-31 04:43:25 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									parts ,  errs  :=  readAllFileInfo ( ctx ,  erasureDisks ,  "" ,  bucketName ,  objectName + "/upload.txt" ,  "" ,  false ,  false ) 
							 
						 
					
						
							
								
									
										
										
										
											2023-03-20 16:06:45 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									for  i  :=  range  parts  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  errs [ i ]  ==  nil  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											if  parts [ i ] . Name  ==  objectName + "/upload.txt"  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												t . Errorf ( "Test %s: Failed to stop post policy handler from writing to minioMetaBucket" ,  instanceType ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-06-13 11:04:01 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								// Wrapper for calling TestPostPolicyBucketHandler tests for both Erasure multiple disks and single node setup.
  
						 
					
						
							
								
									
										
										
										
											2016-12-05 04:23:19 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								func  TestPostPolicyBucketHandler ( t  * testing . T )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ExecObjectLayerTest ( t ,  testPostPolicyBucketHandler ) 
							 
						 
					
						
							
								
									
										
										
										
											2016-09-14 10:00:01 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2016-12-05 04:23:19 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								// testPostPolicyBucketHandler - Tests validate post policy handler uploading objects.
  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								func  testPostPolicyBucketHandler ( obj  ObjectLayer ,  instanceType  string ,  t  TestErrHandler )  {  
						 
					
						
							
								
									
										
										
										
											2018-08-15 12:41:47 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  err  :=  newTestConfig ( globalMinioDefaultRegion ,  obj ) ;  err  !=  nil  { 
							 
						 
					
						
							
								
									
										
										
										
											2016-10-06 03:48:07 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										t . Fatalf ( "Initializing config.json failed" ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2016-09-14 10:00:01 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									// get random bucket name.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									bucketName  :=  getRandomBucketName ( ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2018-09-11 00:42:43 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									var  opts  ObjectOptions 
							 
						 
					
						
							
								
									
										
										
										
											2020-06-13 11:04:01 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									// Register the API end points with Erasure/FS object layer.
 
							 
						 
					
						
							
								
									
										
										
										
											2016-09-14 10:00:01 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									apiRouter  :=  initTestAPIEndPoints ( obj ,  [ ] string { "PostPolicy" } ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2019-10-23 13:59:13 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									credentials  :=  globalActiveCred 
							 
						 
					
						
							
								
									
										
										
										
											2016-09-15 14:53:42 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-03-19 02:28:41 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									curTime  :=  UTCNow ( ) 
							 
						 
					
						
							
								
									
										
										
										
											2016-12-05 04:23:19 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									curTimePlus5Min  :=  curTime . Add ( time . Minute  *  5 ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2016-09-14 10:00:01 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									// bucketnames[0].
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// objectNames[0].
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// uploadIds [0].
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// Create bucket before initiating NewMultipartUpload.
 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-23 23:46:00 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									err  :=  obj . MakeBucket ( context . Background ( ) ,  bucketName ,  MakeBucketOptions { } ) 
							 
						 
					
						
							
								
									
										
										
										
											2016-09-14 10:00:01 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									if  err  !=  nil  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										// Failed to create newbucket, abort.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										t . Fatalf ( "%s : %s" ,  instanceType ,  err . Error ( ) ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2016-10-22 23:57:12 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									// Test cases for signature-V2.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									testCasesV2  :=  [ ] struct  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										expectedStatus  int 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										secretKey       string 
							 
						 
					
						
							
								
									
										
										
										
											2024-05-06 18:52:41 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										formData        map [ string ] string 
							 
						 
					
						
							
								
									
										
										
										
											2016-10-22 23:57:12 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} { 
							 
						 
					
						
							
								
									
										
										
										
											2024-05-06 18:52:41 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										{ http . StatusForbidden ,  credentials . SecretKey ,  map [ string ] string { "AWSAccessKeyId" :  "invalidaccesskey" } } , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										{ http . StatusForbidden ,  "invalidsecretkey" ,  map [ string ] string { "AWSAccessKeyId" :  credentials . AccessKey } } , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										{ http . StatusNoContent ,  credentials . SecretKey ,  map [ string ] string { "AWSAccessKeyId" :  credentials . AccessKey } } , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										{ http . StatusForbidden ,  credentials . SecretKey ,  map [ string ] string { "Awsaccesskeyid" :  "invalidaccesskey" } } , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										{ http . StatusForbidden ,  "invalidsecretkey" ,  map [ string ] string { "Awsaccesskeyid" :  credentials . AccessKey } } , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										{ http . StatusNoContent ,  credentials . SecretKey ,  map [ string ] string { "Awsaccesskeyid" :  credentials . AccessKey } } , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										// Forbidden with key not in policy.conditions for signed requests V2.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										{ http . StatusForbidden ,  credentials . SecretKey ,  map [ string ] string { "Awsaccesskeyid" :  credentials . AccessKey ,  "AnotherKey" :  "AnotherContent" } } , 
							 
						 
					
						
							
								
									
										
										
										
											2016-10-22 23:57:12 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									for  i ,  test  :=  range  testCasesV2  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										// initialize HTTP NewRecorder, this records any mutations to response writer inside the handler.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										rec  :=  httptest . NewRecorder ( ) 
							 
						 
					
						
							
								
									
										
										
										
											2024-05-06 18:52:41 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										req ,  perr  :=  newPostRequestV2 ( "" ,  bucketName ,  "testobject" ,  test . secretKey ,  test . formData ) 
							 
						 
					
						
							
								
									
										
										
										
											2016-10-22 23:57:12 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										if  perr  !=  nil  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											t . Fatalf ( "Test %d: %s: Failed to create HTTP request for PostPolicyHandler: <ERROR> %v" ,  i + 1 ,  instanceType ,  perr ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2024-01-18 15:03:17 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										// Since `apiRouter` satisfies `http.Handler` it has a ServeHTTP to execute the logic of the handler.
 
							 
						 
					
						
							
								
									
										
										
										
											2016-10-22 23:57:12 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										// Call the ServeHTTP to execute the handler.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										apiRouter . ServeHTTP ( rec ,  req ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  rec . Code  !=  test . expectedStatus  { 
							 
						 
					
						
							
								
									
										
										
										
											2024-05-23 07:07:14 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											t . Fatalf ( "Test %d: %s: Expected the response status to be `%d`, but instead found `%d`, Resp: %s" ,  i + 1 ,  instanceType ,  test . expectedStatus ,  rec . Code ,  rec . Body ) 
							 
						 
					
						
							
								
									
										
										
										
											2016-10-22 23:57:12 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// Test cases for signature-V4.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									testCasesV4  :=  [ ] struct  { 
							 
						 
					
						
							
								
									
										
										
										
											2016-09-14 10:00:01 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										objectName          string 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										data                [ ] byte 
							 
						 
					
						
							
								
									
										
										
										
											2016-12-20 08:14:04 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										expectedHeaders     map [ string ] string 
							 
						 
					
						
							
								
									
										
										
										
											2016-09-14 10:00:01 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										expectedRespStatus  int 
							 
						 
					
						
							
								
									
										
										
										
											2016-09-15 14:53:42 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										accessKey           string 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										secretKey           string 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										malformedBody       bool 
							 
						 
					
						
							
								
									
										
										
										
											2016-09-14 10:00:01 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									} { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										// Success case.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										{ 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											objectName :          "test" , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											data :                [ ] byte ( "Hello, World" ) , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											expectedRespStatus :  http . StatusNoContent , 
							 
						 
					
						
							
								
									
										
										
										
											2016-12-20 08:14:04 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											expectedHeaders :     map [ string ] string { "X-Amz-Meta-Uuid" :  "1234" } , 
							 
						 
					
						
							
								
									
										
										
										
											2016-12-27 02:21:23 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											accessKey :           credentials . AccessKey , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											secretKey :           credentials . SecretKey , 
							 
						 
					
						
							
								
									
										
										
										
											2016-09-15 14:53:42 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											malformedBody :       false , 
							 
						 
					
						
							
								
									
										
										
										
											2016-09-14 10:00:01 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										} , 
							 
						 
					
						
							
								
									
										
										
										
											2016-09-15 14:53:42 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										// Bad case invalid request.
 
							 
						 
					
						
							
								
									
										
										
										
											2016-09-14 10:00:01 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										{ 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											objectName :          "test" , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											data :                [ ] byte ( "Hello, World" ) , 
							 
						 
					
						
							
								
									
										
										
										
											2020-08-24 13:06:22 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											expectedRespStatus :  http . StatusForbidden , 
							 
						 
					
						
							
								
									
										
										
										
											2016-09-15 14:53:42 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											accessKey :           "" , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											secretKey :           "" , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											malformedBody :       false , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										// Bad case malformed input.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										{ 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											objectName :          "test" , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											data :                [ ] byte ( "Hello, World" ) , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											expectedRespStatus :  http . StatusBadRequest , 
							 
						 
					
						
							
								
									
										
										
										
											2016-12-27 02:21:23 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											accessKey :           credentials . AccessKey , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											secretKey :           credentials . SecretKey , 
							 
						 
					
						
							
								
									
										
										
										
											2016-09-15 14:53:42 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											malformedBody :       true , 
							 
						 
					
						
							
								
									
										
										
										
											2016-09-14 10:00:01 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										} , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2016-10-22 23:57:12 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									for  i ,  testCase  :=  range  testCasesV4  { 
							 
						 
					
						
							
								
									
										
										
										
											2016-09-14 10:00:01 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										// initialize HTTP NewRecorder, this records any mutations to response writer inside the handler.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										rec  :=  httptest . NewRecorder ( ) 
							 
						 
					
						
							
								
									
										
										
										
											2016-10-22 23:57:12 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										req ,  perr  :=  newPostRequestV4 ( "" ,  bucketName ,  testCase . objectName ,  testCase . data ,  testCase . accessKey ,  testCase . secretKey ) 
							 
						 
					
						
							
								
									
										
										
										
											2016-09-14 10:00:01 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										if  perr  !=  nil  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											t . Fatalf ( "Test %d: %s: Failed to create HTTP request for PostPolicyHandler: <ERROR> %v" ,  i + 1 ,  instanceType ,  perr ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2016-09-15 14:53:42 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										if  testCase . malformedBody  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											// Change the request body.
 
							 
						 
					
						
							
								
									
										
										
										
											2022-09-20 02:05:16 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											req . Body  =  io . NopCloser ( bytes . NewReader ( [ ] byte ( "Hello," ) ) ) 
							 
						 
					
						
							
								
									
										
										
										
											2016-09-15 14:53:42 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2024-01-18 15:03:17 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										// Since `apiRouter` satisfies `http.Handler` it has a ServeHTTP to execute the logic of the handler.
 
							 
						 
					
						
							
								
									
										
										
										
											2016-09-14 10:00:01 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										// Call the ServeHTTP to execute the handler.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										apiRouter . ServeHTTP ( rec ,  req ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  rec . Code  !=  testCase . expectedRespStatus  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											t . Errorf ( "Test %d: %s: Expected the response status to be `%d`, but instead found `%d`" ,  i + 1 ,  instanceType ,  testCase . expectedRespStatus ,  rec . Code ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2016-12-20 08:14:04 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										// When the operation is successful, check if sending metadata is successful too
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  rec . Code  ==  http . StatusNoContent  { 
							 
						 
					
						
							
								
									
										
										
										
											2018-09-11 00:42:43 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											objInfo ,  err  :=  obj . GetObjectInfo ( context . Background ( ) ,  bucketName ,  testCase . objectName + "/upload.txt" ,  opts ) 
							 
						 
					
						
							
								
									
										
										
										
											2016-12-20 08:14:04 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											if  err  !=  nil  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												t . Error ( "Unexpected error: " ,  err ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											for  k ,  v  :=  range  testCase . expectedHeaders  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												if  objInfo . UserDefined [ k ]  !=  v  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													t . Errorf ( "Expected to have header %s with value %s, but found value `%s` instead" ,  k ,  v ,  objInfo . UserDefined [ k ] ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2016-09-14 10:00:01 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2016-11-21 20:15:26 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-05-16 09:17:02 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									region  :=  "us-east-1" 
							 
						 
					
						
							
								
									
										
										
										
											2016-12-05 04:23:19 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									// Test cases for signature-V4.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									testCasesV4BadData  :=  [ ] struct  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										objectName          string 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										data                [ ] byte 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										expectedRespStatus  int 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										accessKey           string 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										secretKey           string 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										dates               [ ] interface { } 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										policy              string 
							 
						 
					
						
							
								
									
										
										
										
											2023-10-31 12:06:32 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										noFilename          bool 
							 
						 
					
						
							
								
									
										
										
										
											2016-12-05 04:23:19 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										corruptedBase64     bool 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										corruptedMultipart  bool 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										// Success case.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										{ 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											objectName :          "test" , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											data :                [ ] byte ( "Hello, World" ) , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											expectedRespStatus :  http . StatusNoContent , 
							 
						 
					
						
							
								
									
										
										
										
											2016-12-27 02:21:23 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											accessKey :           credentials . AccessKey , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											secretKey :           credentials . SecretKey , 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-26 07:51:32 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											dates :               [ ] interface { } { curTimePlus5Min . Format ( iso8601TimeFormat ) ,  curTime . Format ( iso8601DateFormat ) ,  curTime . Format ( yyyymmdd ) } , 
							 
						 
					
						
							
								
									
										
										
										
											2019-04-02 14:45:32 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											policy :              ` { "expiration": "%s","conditions":[["eq", "$bucket", " `  +  bucketName  +  ` "], ["starts-with", "$key", "test/"], ["eq", "$x-amz-algorithm", "AWS4-HMAC-SHA256"], ["eq", "$x-amz-date", "%s"], ["eq", "$x-amz-credential", " `  +  credentials . AccessKey  +  ` /%s/us-east-1/s3/aws4_request"],["eq", "$x-amz-meta-uuid", "1234"]]} ` , 
							 
						 
					
						
							
								
									
										
										
										
											2021-10-28 22:35:28 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										} , 
							 
						 
					
						
							
								
									
										
										
										
											2023-10-31 12:06:32 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										// Success case, no multipart filename.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										{ 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											objectName :          "test" , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											data :                [ ] byte ( "Hello, World" ) , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											expectedRespStatus :  http . StatusNoContent , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											accessKey :           credentials . AccessKey , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											secretKey :           credentials . SecretKey , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											dates :               [ ] interface { } { curTimePlus5Min . Format ( iso8601TimeFormat ) ,  curTime . Format ( iso8601DateFormat ) ,  curTime . Format ( yyyymmdd ) } , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											policy :              ` { "expiration": "%s","conditions":[["eq", "$bucket", " `  +  bucketName  +  ` "], ["starts-with", "$key", "test/"], ["eq", "$x-amz-algorithm", "AWS4-HMAC-SHA256"], ["eq", "$x-amz-date", "%s"], ["eq", "$x-amz-credential", " `  +  credentials . AccessKey  +  ` /%s/us-east-1/s3/aws4_request"],["eq", "$x-amz-meta-uuid", "1234"]]} ` , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											noFilename :          true , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} , 
							 
						 
					
						
							
								
									
										
										
										
											2021-10-28 22:35:28 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										// Success case, big body.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										{ 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											objectName :          "test" , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											data :                bytes . Repeat ( [ ] byte ( "a" ) ,  10 << 20 ) , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											expectedRespStatus :  http . StatusNoContent , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											accessKey :           credentials . AccessKey , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											secretKey :           credentials . SecretKey , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											dates :               [ ] interface { } { curTimePlus5Min . Format ( iso8601TimeFormat ) ,  curTime . Format ( iso8601DateFormat ) ,  curTime . Format ( yyyymmdd ) } , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											policy :              ` { "expiration": "%s","conditions":[["eq", "$bucket", " `  +  bucketName  +  ` "], ["starts-with", "$key", "test/"], ["eq", "$x-amz-algorithm", "AWS4-HMAC-SHA256"], ["eq", "$x-amz-date", "%s"], ["eq", "$x-amz-credential", " `  +  credentials . AccessKey  +  ` /%s/us-east-1/s3/aws4_request"],["eq", "$x-amz-meta-uuid", "1234"]]} ` , 
							 
						 
					
						
							
								
									
										
										
										
											2016-12-05 04:23:19 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										} , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										// Corrupted Base 64 result
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										{ 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											objectName :          "test" , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											data :                [ ] byte ( "Hello, World" ) , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											expectedRespStatus :  http . StatusBadRequest , 
							 
						 
					
						
							
								
									
										
										
										
											2016-12-27 02:21:23 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											accessKey :           credentials . AccessKey , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											secretKey :           credentials . SecretKey , 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-26 07:51:32 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											dates :               [ ] interface { } { curTimePlus5Min . Format ( iso8601TimeFormat ) ,  curTime . Format ( iso8601DateFormat ) ,  curTime . Format ( yyyymmdd ) } , 
							 
						 
					
						
							
								
									
										
										
										
											2016-12-27 02:21:23 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											policy :              ` { "expiration": "%s","conditions":[["eq", "$bucket", " `  +  bucketName  +  ` "], ["starts-with", "$key", "test/"], ["eq", "$x-amz-algorithm", "AWS4-HMAC-SHA256"], ["eq", "$x-amz-date", "%s"], ["eq", "$x-amz-credential", " `  +  credentials . AccessKey  +  ` /%s/us-east-1/s3/aws4_request"]]} ` , 
							 
						 
					
						
							
								
									
										
										
										
											2016-12-05 04:23:19 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											corruptedBase64 :     true , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										// Corrupted Multipart body
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										{ 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											objectName :          "test" , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											data :                [ ] byte ( "Hello, World" ) , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											expectedRespStatus :  http . StatusBadRequest , 
							 
						 
					
						
							
								
									
										
										
										
											2016-12-27 02:21:23 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											accessKey :           credentials . AccessKey , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											secretKey :           credentials . SecretKey , 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-26 07:51:32 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											dates :               [ ] interface { } { curTimePlus5Min . Format ( iso8601TimeFormat ) ,  curTime . Format ( iso8601DateFormat ) ,  curTime . Format ( yyyymmdd ) } , 
							 
						 
					
						
							
								
									
										
										
										
											2016-12-27 02:21:23 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											policy :              ` { "expiration": "%s","conditions":[["eq", "$bucket", " `  +  bucketName  +  ` "], ["starts-with", "$key", "test/"], ["eq", "$x-amz-algorithm", "AWS4-HMAC-SHA256"], ["eq", "$x-amz-date", "%s"], ["eq", "$x-amz-credential", " `  +  credentials . AccessKey  +  ` /%s/us-east-1/s3/aws4_request"]]} ` , 
							 
						 
					
						
							
								
									
										
										
										
											2016-12-05 04:23:19 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											corruptedMultipart :  true , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										// Bad case invalid request.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										{ 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											objectName :          "test" , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											data :                [ ] byte ( "Hello, World" ) , 
							 
						 
					
						
							
								
									
										
										
										
											2020-08-24 13:06:22 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											expectedRespStatus :  http . StatusForbidden , 
							 
						 
					
						
							
								
									
										
										
										
											2016-12-05 04:23:19 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											accessKey :           "" , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											secretKey :           "" , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											dates :               [ ] interface { } { } , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											policy :              ` ` , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										// Expired document
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										{ 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											objectName :          "test" , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											data :                [ ] byte ( "Hello, World" ) , 
							 
						 
					
						
							
								
									
										
										
										
											2019-03-06 04:10:47 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											expectedRespStatus :  http . StatusForbidden , 
							 
						 
					
						
							
								
									
										
										
										
											2016-12-27 02:21:23 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											accessKey :           credentials . AccessKey , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											secretKey :           credentials . SecretKey , 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-26 07:51:32 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											dates :               [ ] interface { } { curTime . Add ( - 1  *  time . Minute  *  5 ) . Format ( iso8601TimeFormat ) ,  curTime . Format ( iso8601DateFormat ) ,  curTime . Format ( yyyymmdd ) } , 
							 
						 
					
						
							
								
									
										
										
										
											2016-12-27 02:21:23 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											policy :              ` { "expiration": "%s","conditions":[["eq", "$bucket", " `  +  bucketName  +  ` "], ["starts-with", "$key", "test/"], ["eq", "$x-amz-algorithm", "AWS4-HMAC-SHA256"], ["eq", "$x-amz-date", "%s"], ["eq", "$x-amz-credential", " `  +  credentials . AccessKey  +  ` /%s/us-east-1/s3/aws4_request"]]} ` , 
							 
						 
					
						
							
								
									
										
										
										
											2016-12-05 04:23:19 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										} , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										// Corrupted policy document
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										{ 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											objectName :          "test" , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											data :                [ ] byte ( "Hello, World" ) , 
							 
						 
					
						
							
								
									
										
										
										
											2019-09-23 05:20:49 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											expectedRespStatus :  http . StatusForbidden , 
							 
						 
					
						
							
								
									
										
										
										
											2016-12-27 02:21:23 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											accessKey :           credentials . AccessKey , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											secretKey :           credentials . SecretKey , 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-26 07:51:32 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											dates :               [ ] interface { } { curTimePlus5Min . Format ( iso8601TimeFormat ) ,  curTime . Format ( iso8601DateFormat ) ,  curTime . Format ( yyyymmdd ) } , 
							 
						 
					
						
							
								
									
										
										
										
											2016-12-05 04:23:19 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											policy :              ` { "3/aws4_request"]]} ` , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									for  i ,  testCase  :=  range  testCasesV4BadData  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										// initialize HTTP NewRecorder, this records any mutations to response writer inside the handler.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										rec  :=  httptest . NewRecorder ( ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										testCase . policy  =  fmt . Sprintf ( testCase . policy ,  testCase . dates ... ) 
							 
						 
					
						
							
								
									
										
										
										
											2016-12-21 01:32:17 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2016-12-05 04:23:19 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										req ,  perr  :=  newPostRequestV4Generic ( "" ,  bucketName ,  testCase . objectName ,  testCase . data ,  testCase . accessKey , 
							 
						 
					
						
							
								
									
										
										
										
											2023-10-31 12:06:32 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											testCase . secretKey ,  region ,  curTime ,  [ ] byte ( testCase . policy ) ,  nil ,  testCase . noFilename ,  testCase . corruptedBase64 ,  testCase . corruptedMultipart ) 
							 
						 
					
						
							
								
									
										
										
										
											2016-12-05 04:23:19 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										if  perr  !=  nil  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											t . Fatalf ( "Test %d: %s: Failed to create HTTP request for PostPolicyHandler: <ERROR> %v" ,  i + 1 ,  instanceType ,  perr ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2024-01-18 15:03:17 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										// Since `apiRouter` satisfies `http.Handler` it has a ServeHTTP to execute the logic of the handler.
 
							 
						 
					
						
							
								
									
										
										
										
											2016-12-05 04:23:19 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										// Call the ServeHTTP to execute the handler.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										apiRouter . ServeHTTP ( rec ,  req ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  rec . Code  !=  testCase . expectedRespStatus  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											t . Errorf ( "Test %d: %s: Expected the response status to be `%d`, but instead found `%d`" ,  i + 1 ,  instanceType ,  testCase . expectedRespStatus ,  rec . Code ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2016-11-21 20:15:26 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									testCases2  :=  [ ] struct  { 
							 
						 
					
						
							
								
									
										
										
										
											2017-02-03 02:45:00 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										objectName           string 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										data                 [ ] byte 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										expectedRespStatus   int 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										accessKey            string 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										secretKey            string 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										malformedBody        bool 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										ignoreContentLength  bool 
							 
						 
					
						
							
								
									
										
										
										
											2016-11-21 20:15:26 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										// Success case.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										{ 
							 
						 
					
						
							
								
									
										
										
										
											2017-02-03 02:45:00 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											objectName :           "test" , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											data :                 bytes . Repeat ( [ ] byte ( "a" ) ,  1025 ) , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											expectedRespStatus :   http . StatusNoContent , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											accessKey :            credentials . AccessKey , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											secretKey :            credentials . SecretKey , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											malformedBody :        false , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											ignoreContentLength :  false , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										// Failed with Content-Length not specified.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										{ 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											objectName :           "test" , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											data :                 bytes . Repeat ( [ ] byte ( "a" ) ,  1025 ) , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											expectedRespStatus :   http . StatusNoContent , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											accessKey :            credentials . AccessKey , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											secretKey :            credentials . SecretKey , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											malformedBody :        false , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											ignoreContentLength :  true , 
							 
						 
					
						
							
								
									
										
										
										
											2016-11-21 20:15:26 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										} , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										// Failed with entity too small.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										{ 
							 
						 
					
						
							
								
									
										
										
										
											2017-02-03 02:45:00 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											objectName :           "test" , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											data :                 bytes . Repeat ( [ ] byte ( "a" ) ,  1023 ) , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											expectedRespStatus :   http . StatusBadRequest , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											accessKey :            credentials . AccessKey , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											secretKey :            credentials . SecretKey , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											malformedBody :        false , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											ignoreContentLength :  false , 
							 
						 
					
						
							
								
									
										
										
										
											2016-11-21 20:15:26 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										} , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										// Failed with entity too large.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										{ 
							 
						 
					
						
							
								
									
										
										
										
											2017-02-03 02:45:00 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											objectName :           "test" , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											data :                 bytes . Repeat ( [ ] byte ( "a" ) ,  ( 1 * humanize . MiByte ) + 1 ) , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											expectedRespStatus :   http . StatusBadRequest , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											accessKey :            credentials . AccessKey , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											secretKey :            credentials . SecretKey , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											malformedBody :        false , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											ignoreContentLength :  false , 
							 
						 
					
						
							
								
									
										
										
										
											2016-11-21 20:15:26 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										} , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									for  i ,  testCase  :=  range  testCases2  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										// initialize HTTP NewRecorder, this records any mutations to response writer inside the handler.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										rec  :=  httptest . NewRecorder ( ) 
							 
						 
					
						
							
								
									
										
										
										
											2017-02-03 02:45:00 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										var  req  * http . Request 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										var  perr  error 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  testCase . ignoreContentLength  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											req ,  perr  =  newPostRequestV4 ( "" ,  bucketName ,  testCase . objectName ,  testCase . data ,  testCase . accessKey ,  testCase . secretKey ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										}  else  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											req ,  perr  =  newPostRequestV4WithContentLength ( "" ,  bucketName ,  testCase . objectName ,  testCase . data ,  testCase . accessKey ,  testCase . secretKey ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2016-11-21 20:15:26 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										if  perr  !=  nil  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											t . Fatalf ( "Test %d: %s: Failed to create HTTP request for PostPolicyHandler: <ERROR> %v" ,  i + 1 ,  instanceType ,  perr ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2024-01-18 15:03:17 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										// Since `apiRouter` satisfies `http.Handler` it has a ServeHTTP to execute the logic of the handler.
 
							 
						 
					
						
							
								
									
										
										
										
											2016-11-21 20:15:26 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										// Call the ServeHTTP to execute the handler.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										apiRouter . ServeHTTP ( rec ,  req ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  rec . Code  !=  testCase . expectedRespStatus  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											t . Errorf ( "Test %d: %s: Expected the response status to be `%d`, but instead found `%d`" ,  i + 1 ,  instanceType ,  testCase . expectedRespStatus ,  rec . Code ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2016-09-14 10:00:01 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-06-13 11:04:01 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								// Wrapper for calling TestPostPolicyBucketHandlerRedirect tests for both Erasure multiple disks and single node setup.
  
						 
					
						
							
								
									
										
										
										
											2016-12-21 01:32:17 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								func  TestPostPolicyBucketHandlerRedirect ( t  * testing . T )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ExecObjectLayerTest ( t ,  testPostPolicyBucketHandlerRedirect ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								// testPostPolicyBucketHandlerRedirect tests POST Object when success_action_redirect is specified
  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								func  testPostPolicyBucketHandlerRedirect ( obj  ObjectLayer ,  instanceType  string ,  t  TestErrHandler )  {  
						 
					
						
							
								
									
										
										
										
											2018-08-15 12:41:47 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  err  :=  newTestConfig ( globalMinioDefaultRegion ,  obj ) ;  err  !=  nil  { 
							 
						 
					
						
							
								
									
										
										
										
											2016-12-21 01:32:17 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										t . Fatalf ( "Initializing config.json failed" ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// get random bucket name.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									bucketName  :=  getRandomBucketName ( ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// Key specified in Form data
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									keyName  :=  "test/object" 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2018-09-11 00:42:43 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									var  opts  ObjectOptions 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2016-12-21 01:32:17 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									// The final name of the upload object
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									targetObj  :=  keyName  +  "/upload.txt" 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// The url of success_action_redirect field
 
							 
						 
					
						
							
								
									
										
										
										
											2022-07-13 22:46:44 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									redirectURL ,  err  :=  url . Parse ( "http://www.google.com?query=value" ) 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-14 05:41:13 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  err  !=  nil  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										t . Fatal ( err ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2016-12-21 01:32:17 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-06-13 11:04:01 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									// Register the API end points with Erasure/FS object layer.
 
							 
						 
					
						
							
								
									
										
										
										
											2016-12-21 01:32:17 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									apiRouter  :=  initTestAPIEndPoints ( obj ,  [ ] string { "PostPolicy" } ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2019-10-23 13:59:13 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									credentials  :=  globalActiveCred 
							 
						 
					
						
							
								
									
										
										
										
											2016-12-21 01:32:17 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-03-19 02:28:41 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									curTime  :=  UTCNow ( ) 
							 
						 
					
						
							
								
									
										
										
										
											2016-12-21 01:32:17 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									curTimePlus5Min  :=  curTime . Add ( time . Minute  *  5 ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-23 23:46:00 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									err  =  obj . MakeBucket ( context . Background ( ) ,  bucketName ,  MakeBucketOptions { } ) 
							 
						 
					
						
							
								
									
										
										
										
											2016-12-21 01:32:17 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  err  !=  nil  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										// Failed to create newbucket, abort.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										t . Fatalf ( "%s : %s" ,  instanceType ,  err . Error ( ) ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// initialize HTTP NewRecorder, this records any mutations to response writer inside the handler.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									rec  :=  httptest . NewRecorder ( ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-05-26 07:51:32 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									dates  :=  [ ] interface { } { curTimePlus5Min . Format ( iso8601TimeFormat ) ,  curTime . Format ( iso8601DateFormat ) ,  curTime . Format ( yyyymmdd ) } 
							 
						 
					
						
							
								
									
										
										
										
											2019-04-02 14:45:32 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									policy  :=  ` { "expiration": "%s","conditions":[["eq", "$bucket", " `  +  bucketName  +  ` "],  { "success_action_redirect":" `  +  redirectURL . String ( )  +  ` "},["starts-with", "$key", "test/"], ["eq", "$x-amz-meta-uuid", "1234"], ["eq", "$x-amz-algorithm", "AWS4-HMAC-SHA256"], ["eq", "$x-amz-date", "%s"], ["eq", "$x-amz-credential", " `  +  credentials . AccessKey  +  ` /%s/us-east-1/s3/aws4_request"]]} ` 
							 
						 
					
						
							
								
									
										
										
										
											2016-12-21 01:32:17 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// Generate the final policy document
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									policy  =  fmt . Sprintf ( policy ,  dates ... ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-05-16 09:17:02 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									region  :=  "us-east-1" 
							 
						 
					
						
							
								
									
										
										
										
											2016-12-21 01:32:17 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									// Create a new POST request with success_action_redirect field specified
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									req ,  perr  :=  newPostRequestV4Generic ( "" ,  bucketName ,  keyName ,  [ ] byte ( "objData" ) , 
							 
						 
					
						
							
								
									
										
										
										
											2017-05-16 09:17:02 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										credentials . AccessKey ,  credentials . SecretKey ,  region ,  curTime , 
							 
						 
					
						
							
								
									
										
										
										
											2023-10-31 12:06:32 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										[ ] byte ( policy ) ,  map [ string ] string { "success_action_redirect" :  redirectURL . String ( ) } ,  false ,  false ,  false ) 
							 
						 
					
						
							
								
									
										
										
										
											2016-12-21 01:32:17 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  perr  !=  nil  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										t . Fatalf ( "%s: Failed to create HTTP request for PostPolicyHandler: <ERROR> %v" ,  instanceType ,  perr ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2024-01-18 15:03:17 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									// Since `apiRouter` satisfies `http.Handler` it has a ServeHTTP to execute the logic of the handler.
 
							 
						 
					
						
							
								
									
										
										
										
											2016-12-21 01:32:17 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									// Call the ServeHTTP to execute the handler.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									apiRouter . ServeHTTP ( rec ,  req ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// Check the status code, which must be 303 because success_action_redirect is specified
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  rec . Code  !=  http . StatusSeeOther  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										t . Errorf ( "%s: Expected the response status to be `%d`, but instead found `%d`" ,  instanceType ,  http . StatusSeeOther ,  rec . Code ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// Get the uploaded object info
 
							 
						 
					
						
							
								
									
										
										
										
											2018-09-11 00:42:43 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									info ,  err  :=  obj . GetObjectInfo ( context . Background ( ) ,  bucketName ,  targetObj ,  opts ) 
							 
						 
					
						
							
								
									
										
										
										
											2016-12-21 01:32:17 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  err  !=  nil  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										t . Error ( "Unexpected error: " ,  err ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-07-16 06:04:48 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									v  :=  redirectURL . Query ( ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									v . Add ( "bucket" ,  info . Bucket ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									v . Add ( "key" ,  info . Name ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									v . Add ( "etag" ,  "\"" + info . ETag + "\"" ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									redirectURL . RawQuery  =  v . Encode ( ) 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-14 05:41:13 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									expectedLocation  :=  redirectURL . String ( ) 
							 
						 
					
						
							
								
									
										
										
										
											2016-12-21 01:32:17 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// Check the new location url
 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-19 00:59:45 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  rec . Header ( ) . Get ( "Location" )  !=  expectedLocation  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										t . Errorf ( "Unexpected location, expected = %s, found = `%s`" ,  rec . Header ( ) . Get ( "Location" ) ,  expectedLocation ) 
							 
						 
					
						
							
								
									
										
										
										
											2016-12-21 01:32:17 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2016-09-14 10:00:01 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								// postPresignSignatureV4 - presigned signature for PostPolicy requests.
  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								func  postPresignSignatureV4 ( policyBase64  string ,  t  time . Time ,  secretAccessKey ,  location  string )  string  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// Get signining key.
 
							 
						 
					
						
							
								
									
										
										
										
											2019-02-28 09:46:55 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									signingkey  :=  getSigningKey ( secretAccessKey ,  t ,  location ,  "s3" ) 
							 
						 
					
						
							
								
									
										
										
										
											2016-09-14 10:00:01 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									// Calculate signature.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									signature  :=  getSignature ( signingkey ,  policyBase64 ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  signature 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2024-05-06 18:52:41 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								func  newPostRequestV2 ( endPoint ,  bucketName ,  objectName  string ,  secretKey  string ,  formInputData  map [ string ] string )  ( * http . Request ,  error )  {  
						 
					
						
							
								
									
										
										
										
											2016-10-22 23:57:12 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									// Expire the request five minutes from now.
 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-19 02:28:41 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									expirationTime  :=  UTCNow ( ) . Add ( time . Minute  *  5 ) 
							 
						 
					
						
							
								
									
										
										
										
											2016-10-22 23:57:12 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									// Create a new post policy.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									policy  :=  newPostPolicyBytesV2 ( bucketName ,  objectName ,  expirationTime ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// Only need the encoding.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									encodedPolicy  :=  base64 . StdEncoding . EncodeToString ( policy ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// Presign with V4 signature based on the policy.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									signature  :=  calculateSignatureV2 ( encodedPolicy ,  secretKey ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									formData  :=  map [ string ] string { 
							 
						 
					
						
							
								
									
										
										
										
											2024-05-06 18:52:41 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										"bucket" :     bucketName , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										"key" :        objectName  +  "/${filename}" , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										"policy" :     encodedPolicy , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										"signature" :  signature , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									for  key ,  value  :=  range  formInputData  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										formData [ key ]  =  value 
							 
						 
					
						
							
								
									
										
										
										
											2016-10-22 23:57:12 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// Create the multipart form.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									var  buf  bytes . Buffer 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									w  :=  multipart . NewWriter ( & buf ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// Set the normal formData
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									for  k ,  v  :=  range  formData  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										w . WriteField ( k ,  v ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// Set the File formData
 
							 
						 
					
						
							
								
									
										
										
										
											2016-12-05 04:23:19 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									writer ,  err  :=  w . CreateFormFile ( "file" ,  "upload.txt" ) 
							 
						 
					
						
							
								
									
										
										
										
											2016-10-22 23:57:12 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  err  !=  nil  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										// return nil, err
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										return  nil ,  err 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									writer . Write ( [ ] byte ( "hello world" ) ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// Close before creating the new request.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									w . Close ( ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// Set the body equal to the created policy.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									reader  :=  bytes . NewReader ( buf . Bytes ( ) ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-07-21 03:52:49 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									req ,  err  :=  http . NewRequest ( http . MethodPost ,  makeTestTargetURL ( endPoint ,  bucketName ,  "" ,  nil ) ,  reader ) 
							 
						 
					
						
							
								
									
										
										
										
											2016-10-22 23:57:12 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  err  !=  nil  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										return  nil ,  err 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// Set form content-type.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									req . Header . Set ( "Content-Type" ,  w . FormDataContentType ( ) ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  req ,  nil 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-05-16 09:17:02 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								func  buildGenericPolicy ( t  time . Time ,  accessKey ,  region ,  bucketName ,  objectName  string ,  contentLengthRange  bool )  [ ] byte  {  
						 
					
						
							
								
									
										
										
										
											2016-09-14 10:00:01 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									// Expire the request five minutes from now.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									expirationTime  :=  t . Add ( time . Minute  *  5 ) 
							 
						 
					
						
							
								
									
										
										
										
											2016-12-05 04:23:19 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-05-16 09:17:02 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									credStr  :=  getCredentialString ( accessKey ,  region ,  t ) 
							 
						 
					
						
							
								
									
										
										
										
											2016-09-14 10:00:01 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									// Create a new post policy.
 
							 
						 
					
						
							
								
									
										
										
										
											2016-10-22 23:57:12 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									policy  :=  newPostPolicyBytesV4 ( credStr ,  bucketName ,  objectName ,  expirationTime ) 
							 
						 
					
						
							
								
									
										
										
										
											2016-11-21 20:15:26 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  contentLengthRange  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										policy  =  newPostPolicyBytesV4WithContentRange ( credStr ,  bucketName ,  objectName ,  expirationTime ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2016-12-05 04:23:19 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									return  policy 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-05-16 09:17:02 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								func  newPostRequestV4Generic ( endPoint ,  bucketName ,  objectName  string ,  objData  [ ] byte ,  accessKey ,  secretKey  string ,  region  string ,  
						 
					
						
							
								
									
										
										
										
											2023-10-31 12:06:32 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									t  time . Time ,  policy  [ ] byte ,  addFormData  map [ string ] string ,  noFilename  bool ,  corruptedB64  bool ,  corruptedMultipart  bool , 
							 
						 
					
						
							
								
									
										
										
										
											2022-04-14 03:00:11 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								)  ( * http . Request ,  error )  {  
						 
					
						
							
								
									
										
										
										
											2016-12-05 04:23:19 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									// Get the user credential.
 
							 
						 
					
						
							
								
									
										
										
										
											2017-05-16 09:17:02 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									credStr  :=  getCredentialString ( accessKey ,  region ,  t ) 
							 
						 
					
						
							
								
									
										
										
										
											2016-12-05 04:23:19 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2016-09-14 10:00:01 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									// Only need the encoding.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									encodedPolicy  :=  base64 . StdEncoding . EncodeToString ( policy ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2016-12-05 04:23:19 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  corruptedB64  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										encodedPolicy  =  "%!~&"  +  encodedPolicy 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2016-09-15 14:53:42 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									// Presign with V4 signature based on the policy.
 
							 
						 
					
						
							
								
									
										
										
										
											2017-05-16 09:17:02 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									signature  :=  postPresignSignatureV4 ( encodedPolicy ,  t ,  secretKey ,  region ) 
							 
						 
					
						
							
								
									
										
										
										
											2016-09-15 14:53:42 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2023-10-31 12:06:32 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									// If there is no filename on multipart, get the filename from the key.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									key  :=  objectName 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  noFilename  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										key  +=  "/upload.txt" 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									}  else  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										key  +=  "/${filename}" 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2016-09-15 14:53:42 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									formData  :=  map [ string ] string { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										"bucket" :            bucketName , 
							 
						 
					
						
							
								
									
										
										
										
											2023-10-31 12:06:32 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										"key" :               key , 
							 
						 
					
						
							
								
									
										
										
										
											2016-09-15 14:53:42 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										"x-amz-credential" :  credStr , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										"policy" :            encodedPolicy , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										"x-amz-signature" :   signature , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										"x-amz-date" :        t . Format ( iso8601DateFormat ) , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										"x-amz-algorithm" :   "AWS4-HMAC-SHA256" , 
							 
						 
					
						
							
								
									
										
										
										
											2016-12-20 08:14:04 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										"x-amz-meta-uuid" :   "1234" , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										"Content-Encoding" :  "gzip" , 
							 
						 
					
						
							
								
									
										
										
										
											2016-09-14 10:00:01 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2016-12-21 01:32:17 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									// Add form data
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									for  k ,  v  :=  range  addFormData  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										formData [ k ]  =  v 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2016-09-14 10:00:01 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									// Create the multipart form.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									var  buf  bytes . Buffer 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									w  :=  multipart . NewWriter ( & buf ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// Set the normal formData
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									for  k ,  v  :=  range  formData  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										w . WriteField ( k ,  v ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2016-12-05 04:23:19 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									// Set the File formData but don't if we want send an incomplete multipart request
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ! corruptedMultipart  { 
							 
						 
					
						
							
								
									
										
										
										
											2023-10-31 12:06:32 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										var  writer  io . Writer 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										var  err  error 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  noFilename  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											writer ,  err  =  w . CreateFormField ( "file" ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										}  else  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											writer ,  err  =  w . CreateFormFile ( "file" ,  "upload.txt" ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2016-12-05 04:23:19 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										if  err  !=  nil  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											// return nil, err
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											return  nil ,  err 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										writer . Write ( objData ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										// Close before creating the new request.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										w . Close ( ) 
							 
						 
					
						
							
								
									
										
										
										
											2016-09-14 10:00:01 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// Set the body equal to the created policy.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									reader  :=  bytes . NewReader ( buf . Bytes ( ) ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-07-21 03:52:49 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									req ,  err  :=  http . NewRequest ( http . MethodPost ,  makeTestTargetURL ( endPoint ,  bucketName ,  "" ,  nil ) ,  reader ) 
							 
						 
					
						
							
								
									
										
										
										
											2016-09-14 10:00:01 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									if  err  !=  nil  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										return  nil ,  err 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// Set form content-type.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									req . Header . Set ( "Content-Type" ,  w . FormDataContentType ( ) ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  req ,  nil 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
									
										
										
										
											2016-11-21 20:15:26 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								func  newPostRequestV4WithContentLength ( endPoint ,  bucketName ,  objectName  string ,  objData  [ ] byte ,  accessKey ,  secretKey  string )  ( * http . Request ,  error )  {  
						 
					
						
							
								
									
										
										
										
											2017-03-19 02:28:41 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									t  :=  UTCNow ( ) 
							 
						 
					
						
							
								
									
										
										
										
											2017-05-16 09:17:02 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									region  :=  "us-east-1" 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									policy  :=  buildGenericPolicy ( t ,  accessKey ,  region ,  bucketName ,  objectName ,  true ) 
							 
						 
					
						
							
								
									
										
										
										
											2023-10-31 12:06:32 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									return  newPostRequestV4Generic ( endPoint ,  bucketName ,  objectName ,  objData ,  accessKey ,  secretKey ,  region ,  t ,  policy ,  nil ,  false ,  false ,  false ) 
							 
						 
					
						
							
								
									
										
										
										
											2016-11-21 20:15:26 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								func  newPostRequestV4 ( endPoint ,  bucketName ,  objectName  string ,  objData  [ ] byte ,  accessKey ,  secretKey  string )  ( * http . Request ,  error )  {  
						 
					
						
							
								
									
										
										
										
											2017-03-19 02:28:41 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									t  :=  UTCNow ( ) 
							 
						 
					
						
							
								
									
										
										
										
											2017-05-16 09:17:02 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									region  :=  "us-east-1" 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									policy  :=  buildGenericPolicy ( t ,  accessKey ,  region ,  bucketName ,  objectName ,  false ) 
							 
						 
					
						
							
								
									
										
										
										
											2023-10-31 12:06:32 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									return  newPostRequestV4Generic ( endPoint ,  bucketName ,  objectName ,  objData ,  accessKey ,  secretKey ,  region ,  t ,  policy ,  nil ,  false ,  false ,  false ) 
							 
						 
					
						
							
								
									
										
										
										
											2016-11-21 20:15:26 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								}