github.com/StarfishStorage/goofys@v0.23.2-0.20200415030923-535558486b34/api/common/conf_s3.go (about) 1 // Copyright 2019 Databricks 2 // 3 // Licensed under the Apache License, Version 2.0 (the "License"); 4 // you may not use this file except in compliance with the License. 5 // You may obtain a copy of the License at 6 // 7 // http://www.apache.org/licenses/LICENSE-2.0 8 // 9 // Unless required by applicable law or agreed to in writing, software 10 // distributed under the License is distributed on an "AS IS" BASIS, 11 // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 12 // See the License for the specific language governing permissions and 13 // limitations under the License. 14 15 package common 16 17 import ( 18 "crypto/md5" 19 "encoding/base64" 20 "fmt" 21 "net/http" 22 23 "github.com/aws/aws-sdk-go/aws" 24 "github.com/aws/aws-sdk-go/aws/client" 25 "github.com/aws/aws-sdk-go/aws/credentials" 26 "github.com/aws/aws-sdk-go/aws/credentials/stscreds" 27 "github.com/aws/aws-sdk-go/aws/session" 28 ) 29 30 type S3Config struct { 31 Profile string 32 AccessKey string 33 SecretKey string 34 RoleArn string 35 RoleExternalId string 36 RoleSessionName string 37 StsEndpoint string 38 39 RequesterPays bool 40 Region string 41 RegionSet bool 42 43 StorageClass string 44 45 UseSSE bool 46 UseKMS bool 47 KMSKeyID string 48 SseC string 49 SseCDigest string 50 ACL string 51 52 Subdomain bool 53 54 Credentials *credentials.Credentials 55 Session *session.Session 56 } 57 58 var s3Session *session.Session 59 60 func (c *S3Config) Init() *S3Config { 61 if c.Region == "" { 62 c.Region = "us-east-1" 63 } 64 if c.StorageClass == "" { 65 c.StorageClass = "STANDARD" 66 } 67 return c 68 } 69 70 func (c *S3Config) ToAwsConfig(flags *FlagStorage) (*aws.Config, error) { 71 awsConfig := (&aws.Config{ 72 Region: &c.Region, 73 Logger: GetLogger("s3"), 74 }).WithHTTPClient(&http.Client{ 75 Transport: &defaultHTTPTransport, 76 Timeout: flags.HTTPTimeout, 77 }) 78 if flags.DebugS3 { 79 awsConfig.LogLevel = aws.LogLevel(aws.LogDebug | aws.LogDebugWithRequestErrors) 80 } 81 82 if c.Credentials == nil { 83 if c.AccessKey != "" { 84 c.Credentials = credentials.NewStaticCredentials(c.AccessKey, c.SecretKey, "") 85 } 86 } 87 if flags.Endpoint != "" { 88 awsConfig.Endpoint = &flags.Endpoint 89 } 90 91 awsConfig.S3ForcePathStyle = aws.Bool(!c.Subdomain) 92 93 if c.Session == nil { 94 if s3Session == nil { 95 var err error 96 s3Session, err = session.NewSessionWithOptions(session.Options{ 97 Profile: c.Profile, 98 SharedConfigState: session.SharedConfigEnable, 99 }) 100 if err != nil { 101 return nil, err 102 } 103 } 104 c.Session = s3Session 105 } 106 107 if c.RoleArn != "" { 108 c.Credentials = stscreds.NewCredentials(stsConfigProvider{c}, c.RoleArn, 109 func(p *stscreds.AssumeRoleProvider) { 110 if c.RoleExternalId != "" { 111 p.ExternalID = &c.RoleExternalId 112 } 113 p.RoleSessionName = c.RoleSessionName 114 }) 115 } 116 117 if c.Credentials != nil { 118 awsConfig.Credentials = c.Credentials 119 } 120 121 if c.SseC != "" { 122 key, err := base64.StdEncoding.DecodeString(c.SseC) 123 if err != nil { 124 return nil, fmt.Errorf("sse-c is not base64-encoded: %v", err) 125 } 126 127 c.SseC = string(key) 128 m := md5.Sum(key) 129 c.SseCDigest = base64.StdEncoding.EncodeToString(m[:]) 130 } 131 132 return awsConfig, nil 133 } 134 135 type stsConfigProvider struct { 136 *S3Config 137 } 138 139 func (c stsConfigProvider) ClientConfig(serviceName string, cfgs ...*aws.Config) client.Config { 140 config := c.Session.ClientConfig(serviceName, cfgs...) 141 if c.Credentials != nil { 142 config.Config.Credentials = c.Credentials 143 } 144 if c.StsEndpoint != "" { 145 config.Endpoint = c.StsEndpoint 146 } 147 148 return config 149 }