55 "crypto/sha256"
66 "encoding/hex"
77 "net/url"
8+ "path"
89 "sort"
910 "strconv"
1011 "strings"
@@ -24,8 +25,6 @@ type PresignedInput struct {
2425 Timestamp time.Time
2526 ExtraHeaders map [string ]string
2627 ExpirySeconds int
27- Protocol string
28- Endpoint string
2928}
3029
3130// GeneratePresignedURL creates a Presigned URL that can be used
@@ -35,8 +34,9 @@ func (s3 *S3) GeneratePresignedURL(in PresignedInput) string {
3534 var (
3635 nowTime = nowTime ()
3736
38- protocol = defaultProtocol
39- endpoint = defaultPresignedHost
37+ protocol = defaultProtocol
38+ hostname = defaultPresignedHost
39+ path_prefix = ""
4040 )
4141 if ! in .Timestamp .IsZero () {
4242 nowTime = in .Timestamp .UTC ()
@@ -52,28 +52,30 @@ func (s3 *S3) GeneratePresignedURL(in PresignedInput) string {
5252 b .Reset ()
5353
5454 // Set the protocol as default if not provided.
55- if in .Protocol != "" {
56- protocol = in .Protocol
57- }
58- if in .Endpoint != "" {
59- endpoint = in .Endpoint
55+ if endpoint , _ := url .Parse (s3 .Endpoint ); endpoint .Host != "" {
56+ protocol = endpoint .Scheme + "://"
57+ hostname = endpoint .Host
58+ path_prefix = path .Join ("/" , endpoint .Path , in .Bucket )
59+ } else {
60+ host := bytes.Buffer {}
61+ host .WriteString (in .Bucket )
62+ host .WriteRune ('.' )
63+ host .WriteString (hostname )
64+ hostname = host .String ()
6065 }
6166
6267 // Add host to Headers
6368 signedHeaders := map [string ][]byte {}
6469 for k , v := range in .ExtraHeaders {
6570 signedHeaders [k ] = []byte (v )
6671 }
67- host := bytes.Buffer {}
68- host .WriteString (in .Bucket )
69- host .WriteRune ('.' )
70- host .WriteString (endpoint )
71- signedHeaders ["host" ] = host .Bytes ()
72+ signedHeaders ["host" ] = []byte (hostname )
7273
7374 // Start Canonical Request Formation
7475 h := sha256 .New () // We write the canonical request directly to the SHA256 hash.
7576 h .Write ([]byte (in .Method )) // HTTP Verb
7677 h .Write (newLine )
78+ h .Write ([]byte (path_prefix ))
7779 h .Write ([]byte {'/' })
7880 h .Write ([]byte (in .ObjectKey )) // CanonicalURL
7981 h .Write (newLine )
@@ -193,10 +195,14 @@ func (s3 *S3) GeneratePresignedURL(in PresignedInput) string {
193195 b .Reset ()
194196
195197 // Start Generating URL
196- b .WriteString (protocol )
197- b .WriteString (in .Bucket )
198- b .WriteRune ('.' )
199- b .WriteString (endpoint )
198+ if s3 .Endpoint != "" {
199+ b .WriteString (s3 .Endpoint )
200+ b .WriteRune ('/' )
201+ b .WriteString (in .Bucket )
202+ } else {
203+ b .WriteString (protocol )
204+ b .WriteString (hostname )
205+ }
200206 b .WriteRune ('/' )
201207 b .WriteString (in .ObjectKey )
202208 b .WriteRune ('?' )
0 commit comments