|
|
|
|
@ -6,6 +6,8 @@ import (
|
|
|
|
|
"fmt"
|
|
|
|
|
"log"
|
|
|
|
|
"net/url"
|
|
|
|
|
"regexp"
|
|
|
|
|
"strings"
|
|
|
|
|
"time"
|
|
|
|
|
|
|
|
|
|
"github.com/aws/aws-sdk-go/aws"
|
|
|
|
|
@ -408,6 +410,10 @@ func resourceAwsS3BucketCreate(d *schema.ResourceData, meta interface{}) error {
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
if err := validateS3BucketName(bucket, awsRegion); err != nil {
|
|
|
|
|
return fmt.Errorf("Error validating S3 bucket name: %s", err)
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
err := resource.Retry(5*time.Minute, func() *resource.RetryError {
|
|
|
|
|
log.Printf("[DEBUG] Trying to create new S3 bucket: %q", bucket)
|
|
|
|
|
_, err := s3conn.CreateBucket(req)
|
|
|
|
|
@ -1728,6 +1734,40 @@ func validateS3BucketRequestPayerType(v interface{}, k string) (ws []string, err
|
|
|
|
|
return
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
// validateS3BucketName validates any S3 bucket name that is not inside the us-east-1 region.
|
|
|
|
|
// Buckets outside of this region have to be DNS-compliant. After the same restrictions are
|
|
|
|
|
// applied to buckets in the us-east-1 region, this function can be refactored as a SchemaValidateFunc
|
|
|
|
|
func validateS3BucketName(value string, region string) error {
|
|
|
|
|
if region != "us-east-1" {
|
|
|
|
|
if (len(value) < 3) || (len(value) > 63) {
|
|
|
|
|
return fmt.Errorf("%q must contain from 3 to 63 characters", value)
|
|
|
|
|
}
|
|
|
|
|
if !regexp.MustCompile(`^[0-9a-z-.]+$`).MatchString(value) {
|
|
|
|
|
return fmt.Errorf("only lowercase alphanumeric characters and hyphens allowed in %q", value)
|
|
|
|
|
}
|
|
|
|
|
if regexp.MustCompile(`^(?:[0-9]{1,3}\.){3}[0-9]{1,3}$`).MatchString(value) {
|
|
|
|
|
return fmt.Errorf("%q must not be formatted as an IP address", value)
|
|
|
|
|
}
|
|
|
|
|
if strings.HasPrefix(value, `.`) {
|
|
|
|
|
return fmt.Errorf("%q cannot start with a period", value)
|
|
|
|
|
}
|
|
|
|
|
if strings.HasSuffix(value, `.`) {
|
|
|
|
|
return fmt.Errorf("%q cannot end with a period", value)
|
|
|
|
|
}
|
|
|
|
|
if strings.Contains(value, `..`) {
|
|
|
|
|
return fmt.Errorf("%q can be only one period between labels", value)
|
|
|
|
|
}
|
|
|
|
|
} else {
|
|
|
|
|
if len(value) > 255 {
|
|
|
|
|
return fmt.Errorf("%q must contain less than 256 characters", value)
|
|
|
|
|
}
|
|
|
|
|
if !regexp.MustCompile(`^[0-9a-zA-Z-._]+$`).MatchString(value) {
|
|
|
|
|
return fmt.Errorf("only alphanumeric characters, hyphens, periods, and underscores allowed in %q", value)
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
return nil
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
func expirationHash(v interface{}) int {
|
|
|
|
|
var buf bytes.Buffer
|
|
|
|
|
m := v.(map[string]interface{})
|
|
|
|
|
|