2015-06-30 17:42:29 -04:00
|
|
|
/*
|
2016-03-05 19:43:48 -05:00
|
|
|
* Minio Cloud Storage, (C) 2015, 2016 Minio, Inc.
|
2015-06-30 17:42:29 -04:00
|
|
|
*
|
|
|
|
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
|
|
* you may not use this file except in compliance with the License.
|
|
|
|
* You may obtain a copy of the License at
|
|
|
|
*
|
|
|
|
* http://www.apache.org/licenses/LICENSE-2.0
|
|
|
|
*
|
|
|
|
* Unless required by applicable law or agreed to in writing, software
|
|
|
|
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
|
|
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
|
|
* See the License for the specific language governing permissions and
|
|
|
|
* limitations under the License.
|
|
|
|
*/
|
|
|
|
|
2015-09-19 03:52:01 -04:00
|
|
|
package main
|
2015-06-30 17:42:29 -04:00
|
|
|
|
|
|
|
import (
|
2016-02-15 20:42:39 -05:00
|
|
|
"bytes"
|
2016-03-05 19:43:48 -05:00
|
|
|
"crypto/md5"
|
|
|
|
"encoding/base64"
|
2015-10-16 14:26:01 -04:00
|
|
|
"encoding/hex"
|
2016-03-05 19:43:48 -05:00
|
|
|
"encoding/xml"
|
2016-02-15 20:42:39 -05:00
|
|
|
"io"
|
2015-10-16 14:26:01 -04:00
|
|
|
"io/ioutil"
|
2016-02-15 20:42:39 -05:00
|
|
|
"mime/multipart"
|
2015-06-30 17:42:29 -04:00
|
|
|
"net/http"
|
accessPolicy: Implement Put, Get, Delete access policy.
This patch implements Get,Put,Delete bucket policies
Supporting - http://docs.aws.amazon.com/AmazonS3/latest/dev/access-policy-language-overview.html
Currently supports following actions.
"*": true,
"s3:*": true,
"s3:GetObject": true,
"s3:ListBucket": true,
"s3:PutObject": true,
"s3:CreateBucket": true,
"s3:GetBucketLocation": true,
"s3:DeleteBucket": true,
"s3:DeleteObject": true,
"s3:AbortMultipartUpload": true,
"s3:ListBucketMultipartUploads": true,
"s3:ListMultipartUploadParts": true,
following conditions for "StringEquals" and "StringNotEquals"
"s3:prefix", "s3:max-keys"
2016-02-03 19:46:56 -05:00
|
|
|
"net/url"
|
|
|
|
"strings"
|
2015-06-30 17:42:29 -04:00
|
|
|
|
2016-02-21 20:57:05 -05:00
|
|
|
mux "github.com/gorilla/mux"
|
2016-02-10 19:40:09 -05:00
|
|
|
"github.com/minio/minio/pkg/crypto/sha256"
|
2015-10-16 16:47:44 -04:00
|
|
|
"github.com/minio/minio/pkg/fs"
|
2016-02-10 19:40:09 -05:00
|
|
|
"github.com/minio/minio/pkg/probe"
|
2016-02-21 20:57:05 -05:00
|
|
|
"github.com/minio/minio/pkg/s3/signature4"
|
2015-06-30 17:42:29 -04:00
|
|
|
)
|
|
|
|
|
accessPolicy: Implement Put, Get, Delete access policy.
This patch implements Get,Put,Delete bucket policies
Supporting - http://docs.aws.amazon.com/AmazonS3/latest/dev/access-policy-language-overview.html
Currently supports following actions.
"*": true,
"s3:*": true,
"s3:GetObject": true,
"s3:ListBucket": true,
"s3:PutObject": true,
"s3:CreateBucket": true,
"s3:GetBucketLocation": true,
"s3:DeleteBucket": true,
"s3:DeleteObject": true,
"s3:AbortMultipartUpload": true,
"s3:ListBucketMultipartUploads": true,
"s3:ListMultipartUploadParts": true,
following conditions for "StringEquals" and "StringNotEquals"
"s3:prefix", "s3:max-keys"
2016-02-03 19:46:56 -05:00
|
|
|
// http://docs.aws.amazon.com/AmazonS3/latest/dev/mpuAndPermissions.html
|
2016-03-10 05:24:52 -05:00
|
|
|
func enforceBucketPolicy(action string, bucket string, reqURL *url.URL) (s3Error APIErrorCode) {
|
accessPolicy: Implement Put, Get, Delete access policy.
This patch implements Get,Put,Delete bucket policies
Supporting - http://docs.aws.amazon.com/AmazonS3/latest/dev/access-policy-language-overview.html
Currently supports following actions.
"*": true,
"s3:*": true,
"s3:GetObject": true,
"s3:ListBucket": true,
"s3:PutObject": true,
"s3:CreateBucket": true,
"s3:GetBucketLocation": true,
"s3:DeleteBucket": true,
"s3:DeleteObject": true,
"s3:AbortMultipartUpload": true,
"s3:ListBucketMultipartUploads": true,
"s3:ListMultipartUploadParts": true,
following conditions for "StringEquals" and "StringNotEquals"
"s3:prefix", "s3:max-keys"
2016-02-03 19:46:56 -05:00
|
|
|
// Read saved bucket policy.
|
|
|
|
policy, err := readBucketPolicy(bucket)
|
|
|
|
if err != nil {
|
|
|
|
errorIf(err.Trace(bucket), "GetBucketPolicy failed.", nil)
|
|
|
|
switch err.ToGoError().(type) {
|
|
|
|
case fs.BucketNotFound:
|
2016-03-10 05:24:52 -05:00
|
|
|
return ErrNoSuchBucket
|
accessPolicy: Implement Put, Get, Delete access policy.
This patch implements Get,Put,Delete bucket policies
Supporting - http://docs.aws.amazon.com/AmazonS3/latest/dev/access-policy-language-overview.html
Currently supports following actions.
"*": true,
"s3:*": true,
"s3:GetObject": true,
"s3:ListBucket": true,
"s3:PutObject": true,
"s3:CreateBucket": true,
"s3:GetBucketLocation": true,
"s3:DeleteBucket": true,
"s3:DeleteObject": true,
"s3:AbortMultipartUpload": true,
"s3:ListBucketMultipartUploads": true,
"s3:ListMultipartUploadParts": true,
following conditions for "StringEquals" and "StringNotEquals"
"s3:prefix", "s3:max-keys"
2016-02-03 19:46:56 -05:00
|
|
|
case fs.BucketNameInvalid:
|
2016-03-10 05:24:52 -05:00
|
|
|
return ErrInvalidBucketName
|
accessPolicy: Implement Put, Get, Delete access policy.
This patch implements Get,Put,Delete bucket policies
Supporting - http://docs.aws.amazon.com/AmazonS3/latest/dev/access-policy-language-overview.html
Currently supports following actions.
"*": true,
"s3:*": true,
"s3:GetObject": true,
"s3:ListBucket": true,
"s3:PutObject": true,
"s3:CreateBucket": true,
"s3:GetBucketLocation": true,
"s3:DeleteBucket": true,
"s3:DeleteObject": true,
"s3:AbortMultipartUpload": true,
"s3:ListBucketMultipartUploads": true,
"s3:ListMultipartUploadParts": true,
following conditions for "StringEquals" and "StringNotEquals"
"s3:prefix", "s3:max-keys"
2016-02-03 19:46:56 -05:00
|
|
|
default:
|
|
|
|
// For any other error just return AccessDenied.
|
2016-03-10 05:24:52 -05:00
|
|
|
return ErrAccessDenied
|
accessPolicy: Implement Put, Get, Delete access policy.
This patch implements Get,Put,Delete bucket policies
Supporting - http://docs.aws.amazon.com/AmazonS3/latest/dev/access-policy-language-overview.html
Currently supports following actions.
"*": true,
"s3:*": true,
"s3:GetObject": true,
"s3:ListBucket": true,
"s3:PutObject": true,
"s3:CreateBucket": true,
"s3:GetBucketLocation": true,
"s3:DeleteBucket": true,
"s3:DeleteObject": true,
"s3:AbortMultipartUpload": true,
"s3:ListBucketMultipartUploads": true,
"s3:ListMultipartUploadParts": true,
following conditions for "StringEquals" and "StringNotEquals"
"s3:prefix", "s3:max-keys"
2016-02-03 19:46:56 -05:00
|
|
|
}
|
|
|
|
}
|
|
|
|
// Parse the saved policy.
|
bucketpolicy: Improve bucket policy validation, avoid nested rules.
Bucket policy validation is more stricter now, to avoid nested
rules. The reason to do this is keep the rules simpler and more
meaningful avoiding conflicts.
This patch implements stricter checks.
Example policy to be generally avoided.
```
{
"Version": "2012-10-17",
"Statement": [
{
"Action": [
"s3:GetObject",
"s3:DeleteObject"
],
"Effect": "Allow",
"Principal": {
"AWS": [
"*"
]
},
"Resource": [
"arn:aws:s3:::jarjarbing/*"
]
},
{
"Action": [
"s3:GetObject",
"s3:DeleteObject"
],
"Effect": "Deny",
"Principal": {
"AWS": [
"*"
]
},
"Resource": [
"arn:aws:s3:::jarjarbing/restic/key/*"
]
}
]
}
```
2016-03-15 13:38:04 -04:00
|
|
|
bucketPolicy, e := parseBucketPolicy(policy)
|
accessPolicy: Implement Put, Get, Delete access policy.
This patch implements Get,Put,Delete bucket policies
Supporting - http://docs.aws.amazon.com/AmazonS3/latest/dev/access-policy-language-overview.html
Currently supports following actions.
"*": true,
"s3:*": true,
"s3:GetObject": true,
"s3:ListBucket": true,
"s3:PutObject": true,
"s3:CreateBucket": true,
"s3:GetBucketLocation": true,
"s3:DeleteBucket": true,
"s3:DeleteObject": true,
"s3:AbortMultipartUpload": true,
"s3:ListBucketMultipartUploads": true,
"s3:ListMultipartUploadParts": true,
following conditions for "StringEquals" and "StringNotEquals"
"s3:prefix", "s3:max-keys"
2016-02-03 19:46:56 -05:00
|
|
|
if e != nil {
|
|
|
|
errorIf(probe.NewError(e), "Parse policy failed.", nil)
|
2016-03-10 05:24:52 -05:00
|
|
|
return ErrAccessDenied
|
accessPolicy: Implement Put, Get, Delete access policy.
This patch implements Get,Put,Delete bucket policies
Supporting - http://docs.aws.amazon.com/AmazonS3/latest/dev/access-policy-language-overview.html
Currently supports following actions.
"*": true,
"s3:*": true,
"s3:GetObject": true,
"s3:ListBucket": true,
"s3:PutObject": true,
"s3:CreateBucket": true,
"s3:GetBucketLocation": true,
"s3:DeleteBucket": true,
"s3:DeleteObject": true,
"s3:AbortMultipartUpload": true,
"s3:ListBucketMultipartUploads": true,
"s3:ListMultipartUploadParts": true,
following conditions for "StringEquals" and "StringNotEquals"
"s3:prefix", "s3:max-keys"
2016-02-03 19:46:56 -05:00
|
|
|
}
|
|
|
|
|
|
|
|
// Construct resource in 'arn:aws:s3:::examplebucket' format.
|
bucketpolicy: Improve bucket policy validation, avoid nested rules.
Bucket policy validation is more stricter now, to avoid nested
rules. The reason to do this is keep the rules simpler and more
meaningful avoiding conflicts.
This patch implements stricter checks.
Example policy to be generally avoided.
```
{
"Version": "2012-10-17",
"Statement": [
{
"Action": [
"s3:GetObject",
"s3:DeleteObject"
],
"Effect": "Allow",
"Principal": {
"AWS": [
"*"
]
},
"Resource": [
"arn:aws:s3:::jarjarbing/*"
]
},
{
"Action": [
"s3:GetObject",
"s3:DeleteObject"
],
"Effect": "Deny",
"Principal": {
"AWS": [
"*"
]
},
"Resource": [
"arn:aws:s3:::jarjarbing/restic/key/*"
]
}
]
}
```
2016-03-15 13:38:04 -04:00
|
|
|
resource := AWSResourcePrefix + strings.TrimPrefix(reqURL.Path, "/")
|
accessPolicy: Implement Put, Get, Delete access policy.
This patch implements Get,Put,Delete bucket policies
Supporting - http://docs.aws.amazon.com/AmazonS3/latest/dev/access-policy-language-overview.html
Currently supports following actions.
"*": true,
"s3:*": true,
"s3:GetObject": true,
"s3:ListBucket": true,
"s3:PutObject": true,
"s3:CreateBucket": true,
"s3:GetBucketLocation": true,
"s3:DeleteBucket": true,
"s3:DeleteObject": true,
"s3:AbortMultipartUpload": true,
"s3:ListBucketMultipartUploads": true,
"s3:ListMultipartUploadParts": true,
following conditions for "StringEquals" and "StringNotEquals"
"s3:prefix", "s3:max-keys"
2016-02-03 19:46:56 -05:00
|
|
|
|
|
|
|
// Get conditions for policy verification.
|
|
|
|
conditions := make(map[string]string)
|
|
|
|
for queryParam := range reqURL.Query() {
|
|
|
|
conditions[queryParam] = reqURL.Query().Get("queryParam")
|
|
|
|
}
|
|
|
|
|
|
|
|
// Validate action, resource and conditions with current policy statements.
|
bucketpolicy: Improve bucket policy validation, avoid nested rules.
Bucket policy validation is more stricter now, to avoid nested
rules. The reason to do this is keep the rules simpler and more
meaningful avoiding conflicts.
This patch implements stricter checks.
Example policy to be generally avoided.
```
{
"Version": "2012-10-17",
"Statement": [
{
"Action": [
"s3:GetObject",
"s3:DeleteObject"
],
"Effect": "Allow",
"Principal": {
"AWS": [
"*"
]
},
"Resource": [
"arn:aws:s3:::jarjarbing/*"
]
},
{
"Action": [
"s3:GetObject",
"s3:DeleteObject"
],
"Effect": "Deny",
"Principal": {
"AWS": [
"*"
]
},
"Resource": [
"arn:aws:s3:::jarjarbing/restic/key/*"
]
}
]
}
```
2016-03-15 13:38:04 -04:00
|
|
|
if !bucketPolicyEvalStatements(action, resource, conditions, bucketPolicy.Statements) {
|
2016-03-10 05:24:52 -05:00
|
|
|
return ErrAccessDenied
|
accessPolicy: Implement Put, Get, Delete access policy.
This patch implements Get,Put,Delete bucket policies
Supporting - http://docs.aws.amazon.com/AmazonS3/latest/dev/access-policy-language-overview.html
Currently supports following actions.
"*": true,
"s3:*": true,
"s3:GetObject": true,
"s3:ListBucket": true,
"s3:PutObject": true,
"s3:CreateBucket": true,
"s3:GetBucketLocation": true,
"s3:DeleteBucket": true,
"s3:DeleteObject": true,
"s3:AbortMultipartUpload": true,
"s3:ListBucketMultipartUploads": true,
"s3:ListMultipartUploadParts": true,
following conditions for "StringEquals" and "StringNotEquals"
"s3:prefix", "s3:max-keys"
2016-02-03 19:46:56 -05:00
|
|
|
}
|
2016-03-10 05:24:52 -05:00
|
|
|
return ErrNone
|
accessPolicy: Implement Put, Get, Delete access policy.
This patch implements Get,Put,Delete bucket policies
Supporting - http://docs.aws.amazon.com/AmazonS3/latest/dev/access-policy-language-overview.html
Currently supports following actions.
"*": true,
"s3:*": true,
"s3:GetObject": true,
"s3:ListBucket": true,
"s3:PutObject": true,
"s3:CreateBucket": true,
"s3:GetBucketLocation": true,
"s3:DeleteBucket": true,
"s3:DeleteObject": true,
"s3:AbortMultipartUpload": true,
"s3:ListBucketMultipartUploads": true,
"s3:ListMultipartUploadParts": true,
following conditions for "StringEquals" and "StringNotEquals"
"s3:prefix", "s3:max-keys"
2016-02-03 19:46:56 -05:00
|
|
|
}
|
|
|
|
|
2015-12-27 02:38:38 -05:00
|
|
|
// GetBucketLocationHandler - GET Bucket location.
|
|
|
|
// -------------------------
|
|
|
|
// This operation returns bucket location.
|
2016-02-18 05:13:52 -05:00
|
|
|
func (api storageAPI) GetBucketLocationHandler(w http.ResponseWriter, r *http.Request) {
|
2016-02-15 20:42:39 -05:00
|
|
|
vars := mux.Vars(r)
|
2015-12-27 02:38:38 -05:00
|
|
|
bucket := vars["bucket"]
|
|
|
|
|
accessPolicy: Implement Put, Get, Delete access policy.
This patch implements Get,Put,Delete bucket policies
Supporting - http://docs.aws.amazon.com/AmazonS3/latest/dev/access-policy-language-overview.html
Currently supports following actions.
"*": true,
"s3:*": true,
"s3:GetObject": true,
"s3:ListBucket": true,
"s3:PutObject": true,
"s3:CreateBucket": true,
"s3:GetBucketLocation": true,
"s3:DeleteBucket": true,
"s3:DeleteObject": true,
"s3:AbortMultipartUpload": true,
"s3:ListBucketMultipartUploads": true,
"s3:ListMultipartUploadParts": true,
following conditions for "StringEquals" and "StringNotEquals"
"s3:prefix", "s3:max-keys"
2016-02-03 19:46:56 -05:00
|
|
|
switch getRequestAuthType(r) {
|
|
|
|
default:
|
|
|
|
// For all unknown auth types return error.
|
2016-03-10 05:24:52 -05:00
|
|
|
writeErrorResponse(w, r, ErrAccessDenied, r.URL.Path)
|
2016-02-15 20:42:39 -05:00
|
|
|
return
|
accessPolicy: Implement Put, Get, Delete access policy.
This patch implements Get,Put,Delete bucket policies
Supporting - http://docs.aws.amazon.com/AmazonS3/latest/dev/access-policy-language-overview.html
Currently supports following actions.
"*": true,
"s3:*": true,
"s3:GetObject": true,
"s3:ListBucket": true,
"s3:PutObject": true,
"s3:CreateBucket": true,
"s3:GetBucketLocation": true,
"s3:DeleteBucket": true,
"s3:DeleteObject": true,
"s3:AbortMultipartUpload": true,
"s3:ListBucketMultipartUploads": true,
"s3:ListMultipartUploadParts": true,
following conditions for "StringEquals" and "StringNotEquals"
"s3:prefix", "s3:max-keys"
2016-02-03 19:46:56 -05:00
|
|
|
case authTypeAnonymous:
|
|
|
|
// http://docs.aws.amazon.com/AmazonS3/latest/dev/mpuAndPermissions.html
|
2016-03-10 05:24:52 -05:00
|
|
|
if s3Error := enforceBucketPolicy("s3:GetBucketLocation", bucket, r.URL); s3Error != ErrNone {
|
accessPolicy: Implement Put, Get, Delete access policy.
This patch implements Get,Put,Delete bucket policies
Supporting - http://docs.aws.amazon.com/AmazonS3/latest/dev/access-policy-language-overview.html
Currently supports following actions.
"*": true,
"s3:*": true,
"s3:GetObject": true,
"s3:ListBucket": true,
"s3:PutObject": true,
"s3:CreateBucket": true,
"s3:GetBucketLocation": true,
"s3:DeleteBucket": true,
"s3:DeleteObject": true,
"s3:AbortMultipartUpload": true,
"s3:ListBucketMultipartUploads": true,
"s3:ListMultipartUploadParts": true,
following conditions for "StringEquals" and "StringNotEquals"
"s3:prefix", "s3:max-keys"
2016-02-03 19:46:56 -05:00
|
|
|
writeErrorResponse(w, r, s3Error, r.URL.Path)
|
|
|
|
return
|
|
|
|
}
|
|
|
|
case authTypeSigned, authTypePresigned:
|
2016-03-10 05:24:52 -05:00
|
|
|
if s3Error := isReqAuthenticated(api.Signature, r); s3Error != ErrNone {
|
accessPolicy: Implement Put, Get, Delete access policy.
This patch implements Get,Put,Delete bucket policies
Supporting - http://docs.aws.amazon.com/AmazonS3/latest/dev/access-policy-language-overview.html
Currently supports following actions.
"*": true,
"s3:*": true,
"s3:GetObject": true,
"s3:ListBucket": true,
"s3:PutObject": true,
"s3:CreateBucket": true,
"s3:GetBucketLocation": true,
"s3:DeleteBucket": true,
"s3:DeleteObject": true,
"s3:AbortMultipartUpload": true,
"s3:ListBucketMultipartUploads": true,
"s3:ListMultipartUploadParts": true,
following conditions for "StringEquals" and "StringNotEquals"
"s3:prefix", "s3:max-keys"
2016-02-03 19:46:56 -05:00
|
|
|
writeErrorResponse(w, r, s3Error, r.URL.Path)
|
|
|
|
return
|
|
|
|
}
|
2016-02-04 15:52:25 -05:00
|
|
|
}
|
|
|
|
|
2016-03-11 19:31:24 -05:00
|
|
|
_, err := api.Filesystem.GetBucketInfo(bucket)
|
2015-12-27 02:38:38 -05:00
|
|
|
if err != nil {
|
2016-03-11 19:31:24 -05:00
|
|
|
errorIf(err.Trace(), "GetBucketInfo failed.", nil)
|
2015-12-27 02:38:38 -05:00
|
|
|
switch err.ToGoError().(type) {
|
|
|
|
case fs.BucketNotFound:
|
2016-03-10 05:24:52 -05:00
|
|
|
writeErrorResponse(w, r, ErrNoSuchBucket, r.URL.Path)
|
2015-12-27 02:38:38 -05:00
|
|
|
case fs.BucketNameInvalid:
|
2016-03-10 05:24:52 -05:00
|
|
|
writeErrorResponse(w, r, ErrInvalidBucketName, r.URL.Path)
|
2015-12-27 02:38:38 -05:00
|
|
|
default:
|
2016-03-10 05:24:52 -05:00
|
|
|
writeErrorResponse(w, r, ErrInternalError, r.URL.Path)
|
2015-12-27 02:38:38 -05:00
|
|
|
}
|
2016-01-19 20:49:48 -05:00
|
|
|
return
|
2015-12-27 02:38:38 -05:00
|
|
|
}
|
|
|
|
|
2016-02-15 20:42:39 -05:00
|
|
|
// Generate response.
|
2016-03-06 15:16:22 -05:00
|
|
|
encodedSuccessResponse := encodeResponse(LocationResponse{})
|
config/main: Re-write config files - add to new config v3
- New config format.
```
{
"version": "3",
"address": ":9000",
"backend": {
"type": "fs",
"disk": "/path"
},
"credential": {
"accessKey": "WLGDGYAQYIGI833EV05A",
"secretKey": "BYvgJM101sHngl2uzjXS/OBF/aMxAN06JrJ3qJlF"
},
"region": "us-east-1",
"logger": {
"file": {
"enable": false,
"fileName": "",
"level": "error"
},
"syslog": {
"enable": false,
"address": "",
"level": "debug"
},
"console": {
"enable": true,
"level": "fatal"
}
}
}
```
New command lines in lieu of supporting XL.
Minio initialize filesystem backend.
~~~
$ minio init fs <path>
~~~
Minio initialize XL backend.
~~~
$ minio init xl <url1>...<url16>
~~~
For 'fs' backend it starts the server.
~~~
$ minio server
~~~
For 'xl' backend it waits for servers to join.
~~~
$ minio server
... [PROGRESS BAR] of servers connecting
~~~
Now on other servers execute 'join' and they connect.
~~~
....
minio join <url1> -- from <url2> && minio server
minio join <url1> -- from <url3> && minio server
...
...
minio join <url1> -- from <url16> && minio server
~~~
2016-02-12 18:27:10 -05:00
|
|
|
// Get current region.
|
|
|
|
region := serverConfig.GetRegion()
|
|
|
|
if region != "us-east-1" {
|
2016-03-06 15:16:22 -05:00
|
|
|
encodedSuccessResponse = encodeResponse(LocationResponse{
|
config/main: Re-write config files - add to new config v3
- New config format.
```
{
"version": "3",
"address": ":9000",
"backend": {
"type": "fs",
"disk": "/path"
},
"credential": {
"accessKey": "WLGDGYAQYIGI833EV05A",
"secretKey": "BYvgJM101sHngl2uzjXS/OBF/aMxAN06JrJ3qJlF"
},
"region": "us-east-1",
"logger": {
"file": {
"enable": false,
"fileName": "",
"level": "error"
},
"syslog": {
"enable": false,
"address": "",
"level": "debug"
},
"console": {
"enable": true,
"level": "fatal"
}
}
}
```
New command lines in lieu of supporting XL.
Minio initialize filesystem backend.
~~~
$ minio init fs <path>
~~~
Minio initialize XL backend.
~~~
$ minio init xl <url1>...<url16>
~~~
For 'fs' backend it starts the server.
~~~
$ minio server
~~~
For 'xl' backend it waits for servers to join.
~~~
$ minio server
... [PROGRESS BAR] of servers connecting
~~~
Now on other servers execute 'join' and they connect.
~~~
....
minio join <url1> -- from <url2> && minio server
minio join <url1> -- from <url3> && minio server
...
...
minio join <url1> -- from <url16> && minio server
~~~
2016-02-12 18:27:10 -05:00
|
|
|
Location: region,
|
2016-02-15 20:42:39 -05:00
|
|
|
})
|
|
|
|
}
|
|
|
|
setCommonHeaders(w) // write headers.
|
2016-01-08 03:40:06 -05:00
|
|
|
writeSuccessResponse(w, encodedSuccessResponse)
|
2015-12-27 02:38:38 -05:00
|
|
|
}
|
|
|
|
|
2015-06-30 23:15:48 -04:00
|
|
|
// ListMultipartUploadsHandler - GET Bucket (List Multipart uploads)
|
2015-06-30 17:42:29 -04:00
|
|
|
// -------------------------
|
|
|
|
// This operation lists in-progress multipart uploads. An in-progress
|
|
|
|
// multipart upload is a multipart upload that has been initiated,
|
2015-10-16 22:09:35 -04:00
|
|
|
// using the Initiate Multipart Upload request, but has not yet been
|
|
|
|
// completed or aborted. This operation returns at most 1,000 multipart
|
|
|
|
// uploads in the response.
|
2015-06-30 17:42:29 -04:00
|
|
|
//
|
2016-02-18 05:13:52 -05:00
|
|
|
func (api storageAPI) ListMultipartUploadsHandler(w http.ResponseWriter, r *http.Request) {
|
2016-02-15 20:42:39 -05:00
|
|
|
vars := mux.Vars(r)
|
2015-10-16 22:09:35 -04:00
|
|
|
bucket := vars["bucket"]
|
|
|
|
|
accessPolicy: Implement Put, Get, Delete access policy.
This patch implements Get,Put,Delete bucket policies
Supporting - http://docs.aws.amazon.com/AmazonS3/latest/dev/access-policy-language-overview.html
Currently supports following actions.
"*": true,
"s3:*": true,
"s3:GetObject": true,
"s3:ListBucket": true,
"s3:PutObject": true,
"s3:CreateBucket": true,
"s3:GetBucketLocation": true,
"s3:DeleteBucket": true,
"s3:DeleteObject": true,
"s3:AbortMultipartUpload": true,
"s3:ListBucketMultipartUploads": true,
"s3:ListMultipartUploadParts": true,
following conditions for "StringEquals" and "StringNotEquals"
"s3:prefix", "s3:max-keys"
2016-02-03 19:46:56 -05:00
|
|
|
switch getRequestAuthType(r) {
|
|
|
|
default:
|
|
|
|
// For all unknown auth types return error.
|
2016-03-10 05:24:52 -05:00
|
|
|
writeErrorResponse(w, r, ErrAccessDenied, r.URL.Path)
|
2016-02-15 20:42:39 -05:00
|
|
|
return
|
accessPolicy: Implement Put, Get, Delete access policy.
This patch implements Get,Put,Delete bucket policies
Supporting - http://docs.aws.amazon.com/AmazonS3/latest/dev/access-policy-language-overview.html
Currently supports following actions.
"*": true,
"s3:*": true,
"s3:GetObject": true,
"s3:ListBucket": true,
"s3:PutObject": true,
"s3:CreateBucket": true,
"s3:GetBucketLocation": true,
"s3:DeleteBucket": true,
"s3:DeleteObject": true,
"s3:AbortMultipartUpload": true,
"s3:ListBucketMultipartUploads": true,
"s3:ListMultipartUploadParts": true,
following conditions for "StringEquals" and "StringNotEquals"
"s3:prefix", "s3:max-keys"
2016-02-03 19:46:56 -05:00
|
|
|
case authTypeAnonymous:
|
|
|
|
// http://docs.aws.amazon.com/AmazonS3/latest/dev/mpuAndPermissions.html
|
2016-03-10 05:24:52 -05:00
|
|
|
if s3Error := enforceBucketPolicy("s3:ListBucketMultipartUploads", bucket, r.URL); s3Error != ErrNone {
|
accessPolicy: Implement Put, Get, Delete access policy.
This patch implements Get,Put,Delete bucket policies
Supporting - http://docs.aws.amazon.com/AmazonS3/latest/dev/access-policy-language-overview.html
Currently supports following actions.
"*": true,
"s3:*": true,
"s3:GetObject": true,
"s3:ListBucket": true,
"s3:PutObject": true,
"s3:CreateBucket": true,
"s3:GetBucketLocation": true,
"s3:DeleteBucket": true,
"s3:DeleteObject": true,
"s3:AbortMultipartUpload": true,
"s3:ListBucketMultipartUploads": true,
"s3:ListMultipartUploadParts": true,
following conditions for "StringEquals" and "StringNotEquals"
"s3:prefix", "s3:max-keys"
2016-02-03 19:46:56 -05:00
|
|
|
writeErrorResponse(w, r, s3Error, r.URL.Path)
|
|
|
|
return
|
|
|
|
}
|
|
|
|
case authTypePresigned, authTypeSigned:
|
2016-03-10 05:24:52 -05:00
|
|
|
if s3Error := isReqAuthenticated(api.Signature, r); s3Error != ErrNone {
|
accessPolicy: Implement Put, Get, Delete access policy.
This patch implements Get,Put,Delete bucket policies
Supporting - http://docs.aws.amazon.com/AmazonS3/latest/dev/access-policy-language-overview.html
Currently supports following actions.
"*": true,
"s3:*": true,
"s3:GetObject": true,
"s3:ListBucket": true,
"s3:PutObject": true,
"s3:CreateBucket": true,
"s3:GetBucketLocation": true,
"s3:DeleteBucket": true,
"s3:DeleteObject": true,
"s3:AbortMultipartUpload": true,
"s3:ListBucketMultipartUploads": true,
"s3:ListMultipartUploadParts": true,
following conditions for "StringEquals" and "StringNotEquals"
"s3:prefix", "s3:max-keys"
2016-02-03 19:46:56 -05:00
|
|
|
writeErrorResponse(w, r, s3Error, r.URL.Path)
|
|
|
|
return
|
|
|
|
}
|
2016-02-04 15:52:25 -05:00
|
|
|
}
|
|
|
|
|
2016-02-15 20:42:39 -05:00
|
|
|
resources := getBucketMultipartResources(r.URL.Query())
|
2015-07-16 20:22:45 -04:00
|
|
|
if resources.MaxUploads < 0 {
|
2016-03-10 05:24:52 -05:00
|
|
|
writeErrorResponse(w, r, ErrInvalidMaxUploads, r.URL.Path)
|
2015-07-16 20:22:45 -04:00
|
|
|
return
|
|
|
|
}
|
2015-06-30 17:42:29 -04:00
|
|
|
if resources.MaxUploads == 0 {
|
|
|
|
resources.MaxUploads = maxObjectList
|
|
|
|
}
|
|
|
|
|
2015-10-16 14:26:01 -04:00
|
|
|
resources, err := api.Filesystem.ListMultipartUploads(bucket, resources)
|
2015-09-19 06:20:07 -04:00
|
|
|
if err != nil {
|
|
|
|
errorIf(err.Trace(), "ListMultipartUploads failed.", nil)
|
|
|
|
switch err.ToGoError().(type) {
|
2015-10-16 14:26:01 -04:00
|
|
|
case fs.BucketNotFound:
|
2016-03-10 05:24:52 -05:00
|
|
|
writeErrorResponse(w, r, ErrNoSuchBucket, r.URL.Path)
|
2015-09-19 06:20:07 -04:00
|
|
|
default:
|
2016-03-10 05:24:52 -05:00
|
|
|
writeErrorResponse(w, r, ErrInternalError, r.URL.Path)
|
2015-09-19 06:20:07 -04:00
|
|
|
}
|
2015-08-03 19:17:21 -04:00
|
|
|
return
|
|
|
|
}
|
2015-09-19 06:20:07 -04:00
|
|
|
// generate response
|
|
|
|
response := generateListMultipartUploadsResponse(bucket, resources)
|
2016-03-06 15:16:22 -05:00
|
|
|
encodedSuccessResponse := encodeResponse(response)
|
2016-01-08 03:40:06 -05:00
|
|
|
// write headers.
|
|
|
|
setCommonHeaders(w)
|
|
|
|
// write success response.
|
|
|
|
writeSuccessResponse(w, encodedSuccessResponse)
|
2015-06-30 17:42:29 -04:00
|
|
|
}
|
|
|
|
|
2015-06-30 23:15:48 -04:00
|
|
|
// ListObjectsHandler - GET Bucket (List Objects)
|
2016-02-15 20:42:39 -05:00
|
|
|
// -- -----------------------
|
2015-06-30 17:42:29 -04:00
|
|
|
// This implementation of the GET operation returns some or all (up to 1000)
|
|
|
|
// of the objects in a bucket. You can use the request parameters as selection
|
|
|
|
// criteria to return a subset of the objects in a bucket.
|
|
|
|
//
|
2016-02-18 05:13:52 -05:00
|
|
|
func (api storageAPI) ListObjectsHandler(w http.ResponseWriter, r *http.Request) {
|
2016-02-15 20:42:39 -05:00
|
|
|
vars := mux.Vars(r)
|
2015-10-16 22:09:35 -04:00
|
|
|
bucket := vars["bucket"]
|
2015-06-30 17:42:29 -04:00
|
|
|
|
accessPolicy: Implement Put, Get, Delete access policy.
This patch implements Get,Put,Delete bucket policies
Supporting - http://docs.aws.amazon.com/AmazonS3/latest/dev/access-policy-language-overview.html
Currently supports following actions.
"*": true,
"s3:*": true,
"s3:GetObject": true,
"s3:ListBucket": true,
"s3:PutObject": true,
"s3:CreateBucket": true,
"s3:GetBucketLocation": true,
"s3:DeleteBucket": true,
"s3:DeleteObject": true,
"s3:AbortMultipartUpload": true,
"s3:ListBucketMultipartUploads": true,
"s3:ListMultipartUploadParts": true,
following conditions for "StringEquals" and "StringNotEquals"
"s3:prefix", "s3:max-keys"
2016-02-03 19:46:56 -05:00
|
|
|
switch getRequestAuthType(r) {
|
|
|
|
default:
|
|
|
|
// For all unknown auth types return error.
|
2016-03-10 05:24:52 -05:00
|
|
|
writeErrorResponse(w, r, ErrAccessDenied, r.URL.Path)
|
accessPolicy: Implement Put, Get, Delete access policy.
This patch implements Get,Put,Delete bucket policies
Supporting - http://docs.aws.amazon.com/AmazonS3/latest/dev/access-policy-language-overview.html
Currently supports following actions.
"*": true,
"s3:*": true,
"s3:GetObject": true,
"s3:ListBucket": true,
"s3:PutObject": true,
"s3:CreateBucket": true,
"s3:GetBucketLocation": true,
"s3:DeleteBucket": true,
"s3:DeleteObject": true,
"s3:AbortMultipartUpload": true,
"s3:ListBucketMultipartUploads": true,
"s3:ListMultipartUploadParts": true,
following conditions for "StringEquals" and "StringNotEquals"
"s3:prefix", "s3:max-keys"
2016-02-03 19:46:56 -05:00
|
|
|
return
|
|
|
|
case authTypeAnonymous:
|
|
|
|
// http://docs.aws.amazon.com/AmazonS3/latest/dev/mpuAndPermissions.html
|
2016-03-10 05:24:52 -05:00
|
|
|
if s3Error := enforceBucketPolicy("s3:ListBucket", bucket, r.URL); s3Error != ErrNone {
|
accessPolicy: Implement Put, Get, Delete access policy.
This patch implements Get,Put,Delete bucket policies
Supporting - http://docs.aws.amazon.com/AmazonS3/latest/dev/access-policy-language-overview.html
Currently supports following actions.
"*": true,
"s3:*": true,
"s3:GetObject": true,
"s3:ListBucket": true,
"s3:PutObject": true,
"s3:CreateBucket": true,
"s3:GetBucketLocation": true,
"s3:DeleteBucket": true,
"s3:DeleteObject": true,
"s3:AbortMultipartUpload": true,
"s3:ListBucketMultipartUploads": true,
"s3:ListMultipartUploadParts": true,
following conditions for "StringEquals" and "StringNotEquals"
"s3:prefix", "s3:max-keys"
2016-02-03 19:46:56 -05:00
|
|
|
writeErrorResponse(w, r, s3Error, r.URL.Path)
|
|
|
|
return
|
|
|
|
}
|
|
|
|
case authTypeSigned, authTypePresigned:
|
2016-03-10 05:24:52 -05:00
|
|
|
if s3Error := isReqAuthenticated(api.Signature, r); s3Error != ErrNone {
|
accessPolicy: Implement Put, Get, Delete access policy.
This patch implements Get,Put,Delete bucket policies
Supporting - http://docs.aws.amazon.com/AmazonS3/latest/dev/access-policy-language-overview.html
Currently supports following actions.
"*": true,
"s3:*": true,
"s3:GetObject": true,
"s3:ListBucket": true,
"s3:PutObject": true,
"s3:CreateBucket": true,
"s3:GetBucketLocation": true,
"s3:DeleteBucket": true,
"s3:DeleteObject": true,
"s3:AbortMultipartUpload": true,
"s3:ListBucketMultipartUploads": true,
"s3:ListMultipartUploadParts": true,
following conditions for "StringEquals" and "StringNotEquals"
"s3:prefix", "s3:max-keys"
2016-02-03 19:46:56 -05:00
|
|
|
writeErrorResponse(w, r, s3Error, r.URL.Path)
|
2016-02-04 15:52:25 -05:00
|
|
|
return
|
|
|
|
}
|
2016-02-15 20:42:39 -05:00
|
|
|
}
|
|
|
|
|
2016-01-19 20:49:48 -05:00
|
|
|
// TODO handle encoding type.
|
2016-02-15 20:42:39 -05:00
|
|
|
prefix, marker, delimiter, maxkeys, _ := getBucketResources(r.URL.Query())
|
2016-01-19 20:49:48 -05:00
|
|
|
if maxkeys < 0 {
|
2016-03-10 05:24:52 -05:00
|
|
|
writeErrorResponse(w, r, ErrInvalidMaxKeys, r.URL.Path)
|
2015-07-16 20:22:45 -04:00
|
|
|
return
|
|
|
|
}
|
2016-01-19 20:49:48 -05:00
|
|
|
if maxkeys == 0 {
|
|
|
|
maxkeys = maxObjectList
|
2015-06-30 17:42:29 -04:00
|
|
|
}
|
|
|
|
|
2016-01-19 20:49:48 -05:00
|
|
|
listResp, err := api.Filesystem.ListObjects(bucket, prefix, marker, delimiter, maxkeys)
|
2015-08-03 19:17:21 -04:00
|
|
|
if err == nil {
|
2015-11-10 06:10:11 -05:00
|
|
|
// generate response
|
2016-01-19 20:49:48 -05:00
|
|
|
response := generateListObjectsResponse(bucket, prefix, marker, delimiter, maxkeys, listResp)
|
2016-03-06 15:16:22 -05:00
|
|
|
encodedSuccessResponse := encodeResponse(response)
|
2016-01-08 03:40:06 -05:00
|
|
|
// Write headers
|
|
|
|
setCommonHeaders(w)
|
|
|
|
// Write success response.
|
|
|
|
writeSuccessResponse(w, encodedSuccessResponse)
|
2015-08-03 19:17:21 -04:00
|
|
|
return
|
|
|
|
}
|
2015-08-18 22:30:17 -04:00
|
|
|
switch err.ToGoError().(type) {
|
2015-10-16 14:26:01 -04:00
|
|
|
case fs.BucketNameInvalid:
|
2016-03-10 05:24:52 -05:00
|
|
|
writeErrorResponse(w, r, ErrInvalidBucketName, r.URL.Path)
|
2015-10-16 14:26:01 -04:00
|
|
|
case fs.BucketNotFound:
|
2016-03-10 05:24:52 -05:00
|
|
|
writeErrorResponse(w, r, ErrNoSuchBucket, r.URL.Path)
|
2015-10-16 14:26:01 -04:00
|
|
|
case fs.ObjectNotFound:
|
2016-03-10 05:24:52 -05:00
|
|
|
writeErrorResponse(w, r, ErrNoSuchKey, r.URL.Path)
|
2015-10-16 14:26:01 -04:00
|
|
|
case fs.ObjectNameInvalid:
|
2016-03-10 05:24:52 -05:00
|
|
|
writeErrorResponse(w, r, ErrNoSuchKey, r.URL.Path)
|
2015-07-02 23:31:22 -04:00
|
|
|
default:
|
2015-09-19 06:20:07 -04:00
|
|
|
errorIf(err.Trace(), "ListObjects failed.", nil)
|
2016-03-10 05:24:52 -05:00
|
|
|
writeErrorResponse(w, r, ErrInternalError, r.URL.Path)
|
2015-07-02 23:31:22 -04:00
|
|
|
}
|
2015-06-30 17:42:29 -04:00
|
|
|
}
|
|
|
|
|
2015-06-30 23:15:48 -04:00
|
|
|
// ListBucketsHandler - GET Service
|
2015-06-30 17:42:29 -04:00
|
|
|
// -----------
|
|
|
|
// This implementation of the GET operation returns a list of all buckets
|
|
|
|
// owned by the authenticated sender of the request.
|
2016-02-18 05:13:52 -05:00
|
|
|
func (api storageAPI) ListBucketsHandler(w http.ResponseWriter, r *http.Request) {
|
accessPolicy: Implement Put, Get, Delete access policy.
This patch implements Get,Put,Delete bucket policies
Supporting - http://docs.aws.amazon.com/AmazonS3/latest/dev/access-policy-language-overview.html
Currently supports following actions.
"*": true,
"s3:*": true,
"s3:GetObject": true,
"s3:ListBucket": true,
"s3:PutObject": true,
"s3:CreateBucket": true,
"s3:GetBucketLocation": true,
"s3:DeleteBucket": true,
"s3:DeleteObject": true,
"s3:AbortMultipartUpload": true,
"s3:ListBucketMultipartUploads": true,
"s3:ListMultipartUploadParts": true,
following conditions for "StringEquals" and "StringNotEquals"
"s3:prefix", "s3:max-keys"
2016-02-03 19:46:56 -05:00
|
|
|
// List buckets does not support bucket policies.
|
|
|
|
switch getRequestAuthType(r) {
|
|
|
|
default:
|
|
|
|
// For all unknown auth types return error.
|
2016-03-10 05:24:52 -05:00
|
|
|
writeErrorResponse(w, r, ErrAccessDenied, r.URL.Path)
|
2016-02-15 20:42:39 -05:00
|
|
|
return
|
accessPolicy: Implement Put, Get, Delete access policy.
This patch implements Get,Put,Delete bucket policies
Supporting - http://docs.aws.amazon.com/AmazonS3/latest/dev/access-policy-language-overview.html
Currently supports following actions.
"*": true,
"s3:*": true,
"s3:GetObject": true,
"s3:ListBucket": true,
"s3:PutObject": true,
"s3:CreateBucket": true,
"s3:GetBucketLocation": true,
"s3:DeleteBucket": true,
"s3:DeleteObject": true,
"s3:AbortMultipartUpload": true,
"s3:ListBucketMultipartUploads": true,
"s3:ListMultipartUploadParts": true,
following conditions for "StringEquals" and "StringNotEquals"
"s3:prefix", "s3:max-keys"
2016-02-03 19:46:56 -05:00
|
|
|
case authTypeSigned, authTypePresigned:
|
2016-03-10 05:24:52 -05:00
|
|
|
if s3Error := isReqAuthenticated(api.Signature, r); s3Error != ErrNone {
|
accessPolicy: Implement Put, Get, Delete access policy.
This patch implements Get,Put,Delete bucket policies
Supporting - http://docs.aws.amazon.com/AmazonS3/latest/dev/access-policy-language-overview.html
Currently supports following actions.
"*": true,
"s3:*": true,
"s3:GetObject": true,
"s3:ListBucket": true,
"s3:PutObject": true,
"s3:CreateBucket": true,
"s3:GetBucketLocation": true,
"s3:DeleteBucket": true,
"s3:DeleteObject": true,
"s3:AbortMultipartUpload": true,
"s3:ListBucketMultipartUploads": true,
"s3:ListMultipartUploadParts": true,
following conditions for "StringEquals" and "StringNotEquals"
"s3:prefix", "s3:max-keys"
2016-02-03 19:46:56 -05:00
|
|
|
writeErrorResponse(w, r, s3Error, r.URL.Path)
|
|
|
|
return
|
|
|
|
}
|
2016-02-04 15:52:25 -05:00
|
|
|
}
|
|
|
|
|
2015-10-16 14:26:01 -04:00
|
|
|
buckets, err := api.Filesystem.ListBuckets()
|
2015-08-03 19:17:21 -04:00
|
|
|
if err == nil {
|
2015-07-02 23:31:22 -04:00
|
|
|
// generate response
|
|
|
|
response := generateListBucketsResponse(buckets)
|
2016-03-06 15:16:22 -05:00
|
|
|
encodedSuccessResponse := encodeResponse(response)
|
2015-07-02 23:31:22 -04:00
|
|
|
// write headers
|
2016-01-08 03:40:06 -05:00
|
|
|
setCommonHeaders(w)
|
2015-07-02 23:31:22 -04:00
|
|
|
// write response
|
2016-01-08 03:40:06 -05:00
|
|
|
writeSuccessResponse(w, encodedSuccessResponse)
|
2015-08-03 19:17:21 -04:00
|
|
|
return
|
|
|
|
}
|
2015-10-04 15:06:14 -04:00
|
|
|
errorIf(err.Trace(), "ListBuckets failed.", nil)
|
2016-03-10 05:24:52 -05:00
|
|
|
writeErrorResponse(w, r, ErrInternalError, r.URL.Path)
|
2015-06-30 17:42:29 -04:00
|
|
|
}
|
|
|
|
|
2016-03-05 19:43:48 -05:00
|
|
|
// DeleteMultipleObjectsHandler - deletes multiple objects.
|
|
|
|
func (api storageAPI) DeleteMultipleObjectsHandler(w http.ResponseWriter, r *http.Request) {
|
|
|
|
vars := mux.Vars(r)
|
|
|
|
bucket := vars["bucket"]
|
|
|
|
|
|
|
|
// Content-Length is required and should be non-zero
|
|
|
|
// http://docs.aws.amazon.com/AmazonS3/latest/API/multiobjectdeleteapi.html
|
|
|
|
if r.ContentLength <= 0 {
|
2016-03-10 05:24:52 -05:00
|
|
|
writeErrorResponse(w, r, ErrMissingContentLength, r.URL.Path)
|
2016-03-05 19:43:48 -05:00
|
|
|
return
|
|
|
|
}
|
|
|
|
|
|
|
|
// Content-Md5 is requied should be set
|
|
|
|
// http://docs.aws.amazon.com/AmazonS3/latest/API/multiobjectdeleteapi.html
|
|
|
|
if _, ok := r.Header["Content-Md5"]; !ok {
|
2016-03-10 05:24:52 -05:00
|
|
|
writeErrorResponse(w, r, ErrMissingContentMD5, r.URL.Path)
|
2016-03-05 19:43:48 -05:00
|
|
|
return
|
|
|
|
}
|
|
|
|
|
|
|
|
// Set http request for signature.
|
|
|
|
auth := api.Signature.SetHTTPRequestToVerify(r)
|
|
|
|
|
|
|
|
// Allocate incoming content length bytes.
|
|
|
|
deleteXMLBytes := make([]byte, r.ContentLength)
|
|
|
|
|
|
|
|
// Read incoming body XML bytes.
|
|
|
|
_, e := io.ReadFull(r.Body, deleteXMLBytes)
|
|
|
|
if e != nil {
|
|
|
|
errorIf(probe.NewError(e), "DeleteMultipleObjects failed.", nil)
|
2016-03-10 05:24:52 -05:00
|
|
|
writeErrorResponse(w, r, ErrInternalError, r.URL.Path)
|
2016-03-05 19:43:48 -05:00
|
|
|
return
|
|
|
|
}
|
|
|
|
|
accessPolicy: Implement Put, Get, Delete access policy.
This patch implements Get,Put,Delete bucket policies
Supporting - http://docs.aws.amazon.com/AmazonS3/latest/dev/access-policy-language-overview.html
Currently supports following actions.
"*": true,
"s3:*": true,
"s3:GetObject": true,
"s3:ListBucket": true,
"s3:PutObject": true,
"s3:CreateBucket": true,
"s3:GetBucketLocation": true,
"s3:DeleteBucket": true,
"s3:DeleteObject": true,
"s3:AbortMultipartUpload": true,
"s3:ListBucketMultipartUploads": true,
"s3:ListMultipartUploadParts": true,
following conditions for "StringEquals" and "StringNotEquals"
"s3:prefix", "s3:max-keys"
2016-02-03 19:46:56 -05:00
|
|
|
switch getRequestAuthType(r) {
|
|
|
|
default:
|
|
|
|
// For all unknown auth types return error.
|
2016-03-10 05:24:52 -05:00
|
|
|
writeErrorResponse(w, r, ErrAccessDenied, r.URL.Path)
|
accessPolicy: Implement Put, Get, Delete access policy.
This patch implements Get,Put,Delete bucket policies
Supporting - http://docs.aws.amazon.com/AmazonS3/latest/dev/access-policy-language-overview.html
Currently supports following actions.
"*": true,
"s3:*": true,
"s3:GetObject": true,
"s3:ListBucket": true,
"s3:PutObject": true,
"s3:CreateBucket": true,
"s3:GetBucketLocation": true,
"s3:DeleteBucket": true,
"s3:DeleteObject": true,
"s3:AbortMultipartUpload": true,
"s3:ListBucketMultipartUploads": true,
"s3:ListMultipartUploadParts": true,
following conditions for "StringEquals" and "StringNotEquals"
"s3:prefix", "s3:max-keys"
2016-02-03 19:46:56 -05:00
|
|
|
return
|
|
|
|
case authTypeAnonymous:
|
|
|
|
// http://docs.aws.amazon.com/AmazonS3/latest/dev/mpuAndPermissions.html
|
2016-03-10 05:24:52 -05:00
|
|
|
if s3Error := enforceBucketPolicy("s3:DeleteObject", bucket, r.URL); s3Error != ErrNone {
|
accessPolicy: Implement Put, Get, Delete access policy.
This patch implements Get,Put,Delete bucket policies
Supporting - http://docs.aws.amazon.com/AmazonS3/latest/dev/access-policy-language-overview.html
Currently supports following actions.
"*": true,
"s3:*": true,
"s3:GetObject": true,
"s3:ListBucket": true,
"s3:PutObject": true,
"s3:CreateBucket": true,
"s3:GetBucketLocation": true,
"s3:DeleteBucket": true,
"s3:DeleteObject": true,
"s3:AbortMultipartUpload": true,
"s3:ListBucketMultipartUploads": true,
"s3:ListMultipartUploadParts": true,
following conditions for "StringEquals" and "StringNotEquals"
"s3:prefix", "s3:max-keys"
2016-02-03 19:46:56 -05:00
|
|
|
writeErrorResponse(w, r, s3Error, r.URL.Path)
|
|
|
|
return
|
|
|
|
}
|
|
|
|
case authTypePresigned:
|
|
|
|
// Check if request is presigned.
|
2016-03-05 19:43:48 -05:00
|
|
|
ok, err := auth.DoesPresignedSignatureMatch()
|
|
|
|
if err != nil {
|
|
|
|
errorIf(err.Trace(r.URL.String()), "Presigned signature verification failed.", nil)
|
2016-03-10 05:24:52 -05:00
|
|
|
writeErrorResponse(w, r, ErrSignatureDoesNotMatch, r.URL.Path)
|
2016-03-05 19:43:48 -05:00
|
|
|
return
|
|
|
|
}
|
|
|
|
if !ok {
|
2016-03-10 05:24:52 -05:00
|
|
|
writeErrorResponse(w, r, ErrSignatureDoesNotMatch, r.URL.Path)
|
2016-03-05 19:43:48 -05:00
|
|
|
return
|
|
|
|
}
|
accessPolicy: Implement Put, Get, Delete access policy.
This patch implements Get,Put,Delete bucket policies
Supporting - http://docs.aws.amazon.com/AmazonS3/latest/dev/access-policy-language-overview.html
Currently supports following actions.
"*": true,
"s3:*": true,
"s3:GetObject": true,
"s3:ListBucket": true,
"s3:PutObject": true,
"s3:CreateBucket": true,
"s3:GetBucketLocation": true,
"s3:DeleteBucket": true,
"s3:DeleteObject": true,
"s3:AbortMultipartUpload": true,
"s3:ListBucketMultipartUploads": true,
"s3:ListMultipartUploadParts": true,
following conditions for "StringEquals" and "StringNotEquals"
"s3:prefix", "s3:max-keys"
2016-02-03 19:46:56 -05:00
|
|
|
case authTypeSigned:
|
2016-03-05 19:43:48 -05:00
|
|
|
// Check if request is signed.
|
|
|
|
sha := sha256.New()
|
|
|
|
mdSh := md5.New()
|
|
|
|
sha.Write(deleteXMLBytes)
|
|
|
|
mdSh.Write(deleteXMLBytes)
|
|
|
|
ok, err := auth.DoesSignatureMatch(hex.EncodeToString(sha.Sum(nil)))
|
|
|
|
if err != nil {
|
|
|
|
errorIf(err.Trace(), "DeleteMultipleObjects failed.", nil)
|
2016-03-10 05:24:52 -05:00
|
|
|
writeErrorResponse(w, r, ErrInternalError, r.URL.Path)
|
2016-03-05 19:43:48 -05:00
|
|
|
return
|
|
|
|
}
|
|
|
|
if !ok {
|
2016-03-10 05:24:52 -05:00
|
|
|
writeErrorResponse(w, r, ErrSignatureDoesNotMatch, r.URL.Path)
|
2016-03-05 19:43:48 -05:00
|
|
|
return
|
|
|
|
}
|
|
|
|
// Verify content md5.
|
|
|
|
if r.Header.Get("Content-Md5") != base64.StdEncoding.EncodeToString(mdSh.Sum(nil)) {
|
2016-03-10 05:24:52 -05:00
|
|
|
writeErrorResponse(w, r, ErrBadDigest, r.URL.Path)
|
2016-03-05 19:43:48 -05:00
|
|
|
return
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
// Unmarshal list of keys to be deleted.
|
|
|
|
deleteObjects := &DeleteObjectsRequest{}
|
|
|
|
if e := xml.Unmarshal(deleteXMLBytes, deleteObjects); e != nil {
|
2016-03-10 05:24:52 -05:00
|
|
|
writeErrorResponse(w, r, ErrMalformedXML, r.URL.Path)
|
2016-03-05 19:43:48 -05:00
|
|
|
return
|
|
|
|
}
|
|
|
|
|
|
|
|
var deleteErrors []DeleteError
|
|
|
|
var deletedObjects []ObjectIdentifier
|
|
|
|
// Loop through all the objects and delete them sequentially.
|
|
|
|
for _, object := range deleteObjects.Objects {
|
|
|
|
err := api.Filesystem.DeleteObject(bucket, object.ObjectName)
|
|
|
|
if err == nil {
|
|
|
|
deletedObjects = append(deletedObjects, ObjectIdentifier{
|
|
|
|
ObjectName: object.ObjectName,
|
|
|
|
})
|
|
|
|
} else {
|
|
|
|
errorIf(err.Trace(object.ObjectName), "DeleteObject failed.", nil)
|
|
|
|
switch err.ToGoError().(type) {
|
|
|
|
case fs.BucketNameInvalid:
|
|
|
|
deleteErrors = append(deleteErrors, DeleteError{
|
2016-03-10 05:24:52 -05:00
|
|
|
Code: errorCodeResponse[ErrInvalidBucketName].Code,
|
|
|
|
Message: errorCodeResponse[ErrInvalidBucketName].Description,
|
2016-03-05 19:43:48 -05:00
|
|
|
Key: object.ObjectName,
|
|
|
|
})
|
|
|
|
case fs.BucketNotFound:
|
|
|
|
deleteErrors = append(deleteErrors, DeleteError{
|
2016-03-10 05:24:52 -05:00
|
|
|
Code: errorCodeResponse[ErrNoSuchBucket].Code,
|
|
|
|
Message: errorCodeResponse[ErrNoSuchBucket].Description,
|
2016-03-05 19:43:48 -05:00
|
|
|
Key: object.ObjectName,
|
|
|
|
})
|
|
|
|
case fs.ObjectNotFound:
|
|
|
|
deleteErrors = append(deleteErrors, DeleteError{
|
2016-03-10 05:24:52 -05:00
|
|
|
Code: errorCodeResponse[ErrNoSuchKey].Code,
|
|
|
|
Message: errorCodeResponse[ErrNoSuchKey].Description,
|
2016-03-05 19:43:48 -05:00
|
|
|
Key: object.ObjectName,
|
|
|
|
})
|
|
|
|
case fs.ObjectNameInvalid:
|
|
|
|
deleteErrors = append(deleteErrors, DeleteError{
|
2016-03-10 05:24:52 -05:00
|
|
|
Code: errorCodeResponse[ErrNoSuchKey].Code,
|
|
|
|
Message: errorCodeResponse[ErrNoSuchKey].Description,
|
2016-03-05 19:43:48 -05:00
|
|
|
Key: object.ObjectName,
|
|
|
|
})
|
|
|
|
default:
|
|
|
|
deleteErrors = append(deleteErrors, DeleteError{
|
2016-03-10 05:24:52 -05:00
|
|
|
Code: errorCodeResponse[ErrInternalError].Code,
|
|
|
|
Message: errorCodeResponse[ErrInternalError].Description,
|
2016-03-05 19:43:48 -05:00
|
|
|
Key: object.ObjectName,
|
|
|
|
})
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
// Generate response
|
|
|
|
response := generateMultiDeleteResponse(deleteObjects.Quiet, deletedObjects, deleteErrors)
|
|
|
|
encodedSuccessResponse := encodeResponse(response)
|
|
|
|
// Write headers
|
|
|
|
setCommonHeaders(w)
|
|
|
|
// Write success response.
|
|
|
|
writeSuccessResponse(w, encodedSuccessResponse)
|
|
|
|
}
|
|
|
|
|
2015-06-30 23:15:48 -04:00
|
|
|
// PutBucketHandler - PUT Bucket
|
2015-06-30 17:42:29 -04:00
|
|
|
// ----------
|
|
|
|
// This implementation of the PUT operation creates a new bucket for authenticated request
|
2016-02-18 05:13:52 -05:00
|
|
|
func (api storageAPI) PutBucketHandler(w http.ResponseWriter, r *http.Request) {
|
2016-02-15 20:42:39 -05:00
|
|
|
vars := mux.Vars(r)
|
2015-10-16 22:09:35 -04:00
|
|
|
bucket := vars["bucket"]
|
|
|
|
|
accessPolicy: Implement Put, Get, Delete access policy.
This patch implements Get,Put,Delete bucket policies
Supporting - http://docs.aws.amazon.com/AmazonS3/latest/dev/access-policy-language-overview.html
Currently supports following actions.
"*": true,
"s3:*": true,
"s3:GetObject": true,
"s3:ListBucket": true,
"s3:PutObject": true,
"s3:CreateBucket": true,
"s3:GetBucketLocation": true,
"s3:DeleteBucket": true,
"s3:DeleteObject": true,
"s3:AbortMultipartUpload": true,
"s3:ListBucketMultipartUploads": true,
"s3:ListMultipartUploadParts": true,
following conditions for "StringEquals" and "StringNotEquals"
"s3:prefix", "s3:max-keys"
2016-02-03 19:46:56 -05:00
|
|
|
// Set http request for signature.
|
|
|
|
auth := api.Signature.SetHTTPRequestToVerify(r)
|
|
|
|
switch getRequestAuthType(r) {
|
|
|
|
default:
|
|
|
|
// For all unknown auth types return error.
|
2016-03-10 05:24:52 -05:00
|
|
|
writeErrorResponse(w, r, ErrAccessDenied, r.URL.Path)
|
2016-02-04 15:52:25 -05:00
|
|
|
return
|
accessPolicy: Implement Put, Get, Delete access policy.
This patch implements Get,Put,Delete bucket policies
Supporting - http://docs.aws.amazon.com/AmazonS3/latest/dev/access-policy-language-overview.html
Currently supports following actions.
"*": true,
"s3:*": true,
"s3:GetObject": true,
"s3:ListBucket": true,
"s3:PutObject": true,
"s3:CreateBucket": true,
"s3:GetBucketLocation": true,
"s3:DeleteBucket": true,
"s3:DeleteObject": true,
"s3:AbortMultipartUpload": true,
"s3:ListBucketMultipartUploads": true,
"s3:ListMultipartUploadParts": true,
following conditions for "StringEquals" and "StringNotEquals"
"s3:prefix", "s3:max-keys"
2016-02-03 19:46:56 -05:00
|
|
|
case authTypePresigned:
|
2016-02-16 21:50:36 -05:00
|
|
|
ok, err := auth.DoesPresignedSignatureMatch()
|
|
|
|
if err != nil {
|
|
|
|
errorIf(err.Trace(r.URL.String()), "Presigned signature verification failed.", nil)
|
2016-03-10 05:24:52 -05:00
|
|
|
writeErrorResponse(w, r, ErrSignatureDoesNotMatch, r.URL.Path)
|
2016-02-16 21:50:36 -05:00
|
|
|
return
|
|
|
|
}
|
|
|
|
if !ok {
|
2016-03-10 05:24:52 -05:00
|
|
|
writeErrorResponse(w, r, ErrSignatureDoesNotMatch, r.URL.Path)
|
2016-02-16 21:50:36 -05:00
|
|
|
return
|
|
|
|
}
|
accessPolicy: Implement Put, Get, Delete access policy.
This patch implements Get,Put,Delete bucket policies
Supporting - http://docs.aws.amazon.com/AmazonS3/latest/dev/access-policy-language-overview.html
Currently supports following actions.
"*": true,
"s3:*": true,
"s3:GetObject": true,
"s3:ListBucket": true,
"s3:PutObject": true,
"s3:CreateBucket": true,
"s3:GetBucketLocation": true,
"s3:DeleteBucket": true,
"s3:DeleteObject": true,
"s3:AbortMultipartUpload": true,
"s3:ListBucketMultipartUploads": true,
"s3:ListMultipartUploadParts": true,
following conditions for "StringEquals" and "StringNotEquals"
"s3:prefix", "s3:max-keys"
2016-02-03 19:46:56 -05:00
|
|
|
case authTypeSigned:
|
2016-02-16 21:50:36 -05:00
|
|
|
// Verify signature for the incoming body if any.
|
2016-02-15 20:42:39 -05:00
|
|
|
locationBytes, e := ioutil.ReadAll(r.Body)
|
|
|
|
if e != nil {
|
|
|
|
errorIf(probe.NewError(e), "MakeBucket failed.", nil)
|
2016-03-10 05:24:52 -05:00
|
|
|
writeErrorResponse(w, r, ErrInternalError, r.URL.Path)
|
2015-07-14 12:17:30 -04:00
|
|
|
return
|
|
|
|
}
|
2016-02-15 20:42:39 -05:00
|
|
|
sh := sha256.New()
|
|
|
|
sh.Write(locationBytes)
|
2016-02-16 21:50:36 -05:00
|
|
|
ok, err := auth.DoesSignatureMatch(hex.EncodeToString(sh.Sum(nil)))
|
2016-02-15 20:42:39 -05:00
|
|
|
if err != nil {
|
|
|
|
errorIf(err.Trace(), "MakeBucket failed.", nil)
|
2016-03-10 05:24:52 -05:00
|
|
|
writeErrorResponse(w, r, ErrInternalError, r.URL.Path)
|
2016-02-15 20:42:39 -05:00
|
|
|
return
|
|
|
|
}
|
|
|
|
if !ok {
|
2016-03-10 05:24:52 -05:00
|
|
|
writeErrorResponse(w, r, ErrSignatureDoesNotMatch, r.URL.Path)
|
2016-02-15 20:42:39 -05:00
|
|
|
return
|
2015-10-16 14:26:01 -04:00
|
|
|
}
|
2015-07-14 12:17:30 -04:00
|
|
|
}
|
|
|
|
|
2016-02-15 20:42:39 -05:00
|
|
|
// Make bucket.
|
accessPolicy: Implement Put, Get, Delete access policy.
This patch implements Get,Put,Delete bucket policies
Supporting - http://docs.aws.amazon.com/AmazonS3/latest/dev/access-policy-language-overview.html
Currently supports following actions.
"*": true,
"s3:*": true,
"s3:GetObject": true,
"s3:ListBucket": true,
"s3:PutObject": true,
"s3:CreateBucket": true,
"s3:GetBucketLocation": true,
"s3:DeleteBucket": true,
"s3:DeleteObject": true,
"s3:AbortMultipartUpload": true,
"s3:ListBucketMultipartUploads": true,
"s3:ListMultipartUploadParts": true,
following conditions for "StringEquals" and "StringNotEquals"
"s3:prefix", "s3:max-keys"
2016-02-03 19:46:56 -05:00
|
|
|
err := api.Filesystem.MakeBucket(bucket)
|
2015-09-19 06:20:07 -04:00
|
|
|
if err != nil {
|
|
|
|
errorIf(err.Trace(), "MakeBucket failed.", nil)
|
|
|
|
switch err.ToGoError().(type) {
|
2015-10-16 14:26:01 -04:00
|
|
|
case fs.BucketNameInvalid:
|
2016-03-10 05:24:52 -05:00
|
|
|
writeErrorResponse(w, r, ErrInvalidBucketName, r.URL.Path)
|
2015-10-16 14:26:01 -04:00
|
|
|
case fs.BucketExists:
|
2016-03-10 05:24:52 -05:00
|
|
|
writeErrorResponse(w, r, ErrBucketAlreadyExists, r.URL.Path)
|
2015-09-19 06:20:07 -04:00
|
|
|
default:
|
2016-03-10 05:24:52 -05:00
|
|
|
writeErrorResponse(w, r, ErrInternalError, r.URL.Path)
|
2015-09-19 06:20:07 -04:00
|
|
|
}
|
2015-08-03 19:17:21 -04:00
|
|
|
return
|
|
|
|
}
|
2015-09-19 06:20:07 -04:00
|
|
|
// Make sure to add Location information here only for bucket
|
2016-03-01 23:01:40 -05:00
|
|
|
w.Header().Set("Location", getLocation(r))
|
2016-01-08 03:40:06 -05:00
|
|
|
writeSuccessResponse(w, nil)
|
2015-06-30 17:42:29 -04:00
|
|
|
}
|
|
|
|
|
2016-02-15 20:42:39 -05:00
|
|
|
func extractHTTPFormValues(reader *multipart.Reader) (io.Reader, map[string]string, *probe.Error) {
|
|
|
|
/// HTML Form values
|
|
|
|
formValues := make(map[string]string)
|
|
|
|
filePart := new(bytes.Buffer)
|
|
|
|
var e error
|
|
|
|
for e == nil {
|
|
|
|
var part *multipart.Part
|
|
|
|
part, e = reader.NextPart()
|
|
|
|
if part != nil {
|
|
|
|
if part.FileName() == "" {
|
|
|
|
buffer, e := ioutil.ReadAll(part)
|
|
|
|
if e != nil {
|
|
|
|
return nil, nil, probe.NewError(e)
|
|
|
|
}
|
|
|
|
formValues[http.CanonicalHeaderKey(part.FormName())] = string(buffer)
|
|
|
|
} else {
|
|
|
|
if _, e := io.Copy(filePart, part); e != nil {
|
|
|
|
return nil, nil, probe.NewError(e)
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
return filePart, formValues, nil
|
|
|
|
}
|
|
|
|
|
2015-10-02 02:51:17 -04:00
|
|
|
// PostPolicyBucketHandler - POST policy
|
|
|
|
// ----------
|
|
|
|
// This implementation of the POST operation handles object creation with a specified
|
|
|
|
// signature policy in multipart/form-data
|
2016-02-18 05:13:52 -05:00
|
|
|
func (api storageAPI) PostPolicyBucketHandler(w http.ResponseWriter, r *http.Request) {
|
2015-10-02 02:51:17 -04:00
|
|
|
// Here the parameter is the size of the form data that should
|
2016-03-22 20:54:31 -04:00
|
|
|
// be loaded in memory, the remaining being put in temporary files.
|
2016-02-15 20:42:39 -05:00
|
|
|
reader, e := r.MultipartReader()
|
2016-02-04 15:52:25 -05:00
|
|
|
if e != nil {
|
|
|
|
errorIf(probe.NewError(e), "Unable to initialize multipart reader.", nil)
|
2016-03-10 05:24:52 -05:00
|
|
|
writeErrorResponse(w, r, ErrMalformedPOSTRequest, r.URL.Path)
|
2015-10-02 02:51:17 -04:00
|
|
|
return
|
|
|
|
}
|
|
|
|
|
2016-02-04 15:52:25 -05:00
|
|
|
fileBody, formValues, err := extractHTTPFormValues(reader)
|
|
|
|
if err != nil {
|
|
|
|
errorIf(err.Trace(), "Unable to parse form values.", nil)
|
2016-03-10 05:24:52 -05:00
|
|
|
writeErrorResponse(w, r, ErrMalformedPOSTRequest, r.URL.Path)
|
2015-10-02 02:51:17 -04:00
|
|
|
return
|
|
|
|
}
|
2016-02-15 20:42:39 -05:00
|
|
|
bucket := mux.Vars(r)["bucket"]
|
2015-10-02 02:51:17 -04:00
|
|
|
formValues["Bucket"] = bucket
|
2015-10-06 13:12:06 -04:00
|
|
|
object := formValues["Key"]
|
2015-10-02 02:51:17 -04:00
|
|
|
var ok bool
|
2016-02-15 20:42:39 -05:00
|
|
|
|
|
|
|
// Set http request for signature.
|
2016-03-02 14:22:58 -05:00
|
|
|
auth := api.Signature.SetHTTPRequestToVerify(r)
|
2016-02-15 20:42:39 -05:00
|
|
|
|
|
|
|
// Verify policy signature.
|
2016-03-02 14:22:58 -05:00
|
|
|
ok, err = auth.DoesPolicySignatureMatch(formValues)
|
2016-02-15 20:42:39 -05:00
|
|
|
if err != nil {
|
2016-02-04 15:52:25 -05:00
|
|
|
errorIf(err.Trace(), "Unable to verify signature.", nil)
|
2016-03-10 05:24:52 -05:00
|
|
|
writeErrorResponse(w, r, ErrSignatureDoesNotMatch, r.URL.Path)
|
2015-10-02 02:51:17 -04:00
|
|
|
return
|
|
|
|
}
|
2016-02-15 20:42:39 -05:00
|
|
|
if !ok {
|
2016-03-10 05:24:52 -05:00
|
|
|
writeErrorResponse(w, r, ErrSignatureDoesNotMatch, r.URL.Path)
|
2015-10-02 02:51:17 -04:00
|
|
|
return
|
|
|
|
}
|
2016-02-21 20:57:05 -05:00
|
|
|
if err = signature4.ApplyPolicyCond(formValues); err != nil {
|
2016-02-04 15:52:25 -05:00
|
|
|
errorIf(err.Trace(), "Invalid request, policy doesn't match with the endpoint.", nil)
|
2016-03-10 05:24:52 -05:00
|
|
|
writeErrorResponse(w, r, ErrMalformedPOSTRequest, r.URL.Path)
|
2015-10-06 13:12:06 -04:00
|
|
|
return
|
|
|
|
}
|
2016-03-11 19:31:24 -05:00
|
|
|
objectInfo, err := api.Filesystem.CreateObject(bucket, object, "", -1, fileBody, nil)
|
2016-02-04 15:52:25 -05:00
|
|
|
if err != nil {
|
|
|
|
errorIf(err.Trace(), "CreateObject failed.", nil)
|
|
|
|
switch err.ToGoError().(type) {
|
2015-10-17 22:17:33 -04:00
|
|
|
case fs.RootPathFull:
|
2016-03-10 05:24:52 -05:00
|
|
|
writeErrorResponse(w, r, ErrRootPathFull, r.URL.Path)
|
2015-10-16 14:26:01 -04:00
|
|
|
case fs.BucketNotFound:
|
2016-03-10 05:24:52 -05:00
|
|
|
writeErrorResponse(w, r, ErrNoSuchBucket, r.URL.Path)
|
2015-10-16 14:26:01 -04:00
|
|
|
case fs.BucketNameInvalid:
|
2016-03-10 05:24:52 -05:00
|
|
|
writeErrorResponse(w, r, ErrInvalidBucketName, r.URL.Path)
|
2015-10-16 14:26:01 -04:00
|
|
|
case fs.BadDigest:
|
2016-03-10 05:24:52 -05:00
|
|
|
writeErrorResponse(w, r, ErrBadDigest, r.URL.Path)
|
2015-10-16 14:26:01 -04:00
|
|
|
case fs.IncompleteBody:
|
2016-03-10 05:24:52 -05:00
|
|
|
writeErrorResponse(w, r, ErrIncompleteBody, r.URL.Path)
|
2015-10-16 14:26:01 -04:00
|
|
|
case fs.InvalidDigest:
|
2016-03-10 05:24:52 -05:00
|
|
|
writeErrorResponse(w, r, ErrInvalidDigest, r.URL.Path)
|
2015-10-02 02:51:17 -04:00
|
|
|
default:
|
2016-03-10 05:24:52 -05:00
|
|
|
writeErrorResponse(w, r, ErrInternalError, r.URL.Path)
|
2015-10-02 02:51:17 -04:00
|
|
|
}
|
|
|
|
return
|
|
|
|
}
|
2016-03-11 19:31:24 -05:00
|
|
|
if objectInfo.MD5Sum != "" {
|
|
|
|
w.Header().Set("ETag", "\""+objectInfo.MD5Sum+"\"")
|
2016-02-01 15:19:54 -05:00
|
|
|
}
|
2016-01-08 03:40:06 -05:00
|
|
|
writeSuccessResponse(w, nil)
|
2015-10-02 02:51:17 -04:00
|
|
|
}
|
|
|
|
|
2015-06-30 23:15:48 -04:00
|
|
|
// HeadBucketHandler - HEAD Bucket
|
2015-06-30 17:42:29 -04:00
|
|
|
// ----------
|
|
|
|
// This operation is useful to determine if a bucket exists.
|
|
|
|
// The operation returns a 200 OK if the bucket exists and you
|
|
|
|
// have permission to access it. Otherwise, the operation might
|
|
|
|
// return responses such as 404 Not Found and 403 Forbidden.
|
2016-02-18 05:13:52 -05:00
|
|
|
func (api storageAPI) HeadBucketHandler(w http.ResponseWriter, r *http.Request) {
|
2016-02-15 20:42:39 -05:00
|
|
|
vars := mux.Vars(r)
|
2015-06-30 17:42:29 -04:00
|
|
|
bucket := vars["bucket"]
|
2015-07-02 23:31:22 -04:00
|
|
|
|
accessPolicy: Implement Put, Get, Delete access policy.
This patch implements Get,Put,Delete bucket policies
Supporting - http://docs.aws.amazon.com/AmazonS3/latest/dev/access-policy-language-overview.html
Currently supports following actions.
"*": true,
"s3:*": true,
"s3:GetObject": true,
"s3:ListBucket": true,
"s3:PutObject": true,
"s3:CreateBucket": true,
"s3:GetBucketLocation": true,
"s3:DeleteBucket": true,
"s3:DeleteObject": true,
"s3:AbortMultipartUpload": true,
"s3:ListBucketMultipartUploads": true,
"s3:ListMultipartUploadParts": true,
following conditions for "StringEquals" and "StringNotEquals"
"s3:prefix", "s3:max-keys"
2016-02-03 19:46:56 -05:00
|
|
|
switch getRequestAuthType(r) {
|
|
|
|
default:
|
|
|
|
// For all unknown auth types return error.
|
2016-03-10 05:24:52 -05:00
|
|
|
writeErrorResponse(w, r, ErrAccessDenied, r.URL.Path)
|
accessPolicy: Implement Put, Get, Delete access policy.
This patch implements Get,Put,Delete bucket policies
Supporting - http://docs.aws.amazon.com/AmazonS3/latest/dev/access-policy-language-overview.html
Currently supports following actions.
"*": true,
"s3:*": true,
"s3:GetObject": true,
"s3:ListBucket": true,
"s3:PutObject": true,
"s3:CreateBucket": true,
"s3:GetBucketLocation": true,
"s3:DeleteBucket": true,
"s3:DeleteObject": true,
"s3:AbortMultipartUpload": true,
"s3:ListBucketMultipartUploads": true,
"s3:ListMultipartUploadParts": true,
following conditions for "StringEquals" and "StringNotEquals"
"s3:prefix", "s3:max-keys"
2016-02-03 19:46:56 -05:00
|
|
|
return
|
|
|
|
case authTypePresigned, authTypeSigned:
|
2016-03-10 05:24:52 -05:00
|
|
|
if s3Error := isReqAuthenticated(api.Signature, r); s3Error != ErrNone {
|
accessPolicy: Implement Put, Get, Delete access policy.
This patch implements Get,Put,Delete bucket policies
Supporting - http://docs.aws.amazon.com/AmazonS3/latest/dev/access-policy-language-overview.html
Currently supports following actions.
"*": true,
"s3:*": true,
"s3:GetObject": true,
"s3:ListBucket": true,
"s3:PutObject": true,
"s3:CreateBucket": true,
"s3:GetBucketLocation": true,
"s3:DeleteBucket": true,
"s3:DeleteObject": true,
"s3:AbortMultipartUpload": true,
"s3:ListBucketMultipartUploads": true,
"s3:ListMultipartUploadParts": true,
following conditions for "StringEquals" and "StringNotEquals"
"s3:prefix", "s3:max-keys"
2016-02-03 19:46:56 -05:00
|
|
|
writeErrorResponse(w, r, s3Error, r.URL.Path)
|
2016-02-04 15:52:25 -05:00
|
|
|
return
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2016-03-11 19:31:24 -05:00
|
|
|
_, err := api.Filesystem.GetBucketInfo(bucket)
|
2015-09-19 06:20:07 -04:00
|
|
|
if err != nil {
|
2016-03-11 19:31:24 -05:00
|
|
|
errorIf(err.Trace(), "GetBucketInfo failed.", nil)
|
2015-09-19 06:20:07 -04:00
|
|
|
switch err.ToGoError().(type) {
|
2015-10-16 14:26:01 -04:00
|
|
|
case fs.BucketNotFound:
|
2016-03-10 05:24:52 -05:00
|
|
|
writeErrorResponse(w, r, ErrNoSuchBucket, r.URL.Path)
|
2015-10-16 14:26:01 -04:00
|
|
|
case fs.BucketNameInvalid:
|
2016-03-10 05:24:52 -05:00
|
|
|
writeErrorResponse(w, r, ErrInvalidBucketName, r.URL.Path)
|
2015-09-19 06:20:07 -04:00
|
|
|
default:
|
2016-03-10 05:24:52 -05:00
|
|
|
writeErrorResponse(w, r, ErrInternalError, r.URL.Path)
|
2015-09-19 06:20:07 -04:00
|
|
|
}
|
2015-08-03 19:17:21 -04:00
|
|
|
return
|
|
|
|
}
|
2016-01-08 03:40:06 -05:00
|
|
|
writeSuccessResponse(w, nil)
|
2015-06-30 17:42:29 -04:00
|
|
|
}
|
2015-10-16 14:26:01 -04:00
|
|
|
|
|
|
|
// DeleteBucketHandler - Delete bucket
|
2016-02-18 05:13:52 -05:00
|
|
|
func (api storageAPI) DeleteBucketHandler(w http.ResponseWriter, r *http.Request) {
|
2016-02-15 20:42:39 -05:00
|
|
|
vars := mux.Vars(r)
|
2015-10-16 14:26:01 -04:00
|
|
|
bucket := vars["bucket"]
|
|
|
|
|
accessPolicy: Implement Put, Get, Delete access policy.
This patch implements Get,Put,Delete bucket policies
Supporting - http://docs.aws.amazon.com/AmazonS3/latest/dev/access-policy-language-overview.html
Currently supports following actions.
"*": true,
"s3:*": true,
"s3:GetObject": true,
"s3:ListBucket": true,
"s3:PutObject": true,
"s3:CreateBucket": true,
"s3:GetBucketLocation": true,
"s3:DeleteBucket": true,
"s3:DeleteObject": true,
"s3:AbortMultipartUpload": true,
"s3:ListBucketMultipartUploads": true,
"s3:ListMultipartUploadParts": true,
following conditions for "StringEquals" and "StringNotEquals"
"s3:prefix", "s3:max-keys"
2016-02-03 19:46:56 -05:00
|
|
|
switch getRequestAuthType(r) {
|
|
|
|
default:
|
|
|
|
// For all unknown auth types return error.
|
2016-03-10 05:24:52 -05:00
|
|
|
writeErrorResponse(w, r, ErrAccessDenied, r.URL.Path)
|
2016-02-15 20:42:39 -05:00
|
|
|
return
|
accessPolicy: Implement Put, Get, Delete access policy.
This patch implements Get,Put,Delete bucket policies
Supporting - http://docs.aws.amazon.com/AmazonS3/latest/dev/access-policy-language-overview.html
Currently supports following actions.
"*": true,
"s3:*": true,
"s3:GetObject": true,
"s3:ListBucket": true,
"s3:PutObject": true,
"s3:CreateBucket": true,
"s3:GetBucketLocation": true,
"s3:DeleteBucket": true,
"s3:DeleteObject": true,
"s3:AbortMultipartUpload": true,
"s3:ListBucketMultipartUploads": true,
"s3:ListMultipartUploadParts": true,
following conditions for "StringEquals" and "StringNotEquals"
"s3:prefix", "s3:max-keys"
2016-02-03 19:46:56 -05:00
|
|
|
case authTypePresigned, authTypeSigned:
|
2016-03-10 05:24:52 -05:00
|
|
|
if s3Error := isReqAuthenticated(api.Signature, r); s3Error != ErrNone {
|
accessPolicy: Implement Put, Get, Delete access policy.
This patch implements Get,Put,Delete bucket policies
Supporting - http://docs.aws.amazon.com/AmazonS3/latest/dev/access-policy-language-overview.html
Currently supports following actions.
"*": true,
"s3:*": true,
"s3:GetObject": true,
"s3:ListBucket": true,
"s3:PutObject": true,
"s3:CreateBucket": true,
"s3:GetBucketLocation": true,
"s3:DeleteBucket": true,
"s3:DeleteObject": true,
"s3:AbortMultipartUpload": true,
"s3:ListBucketMultipartUploads": true,
"s3:ListMultipartUploadParts": true,
following conditions for "StringEquals" and "StringNotEquals"
"s3:prefix", "s3:max-keys"
2016-02-03 19:46:56 -05:00
|
|
|
writeErrorResponse(w, r, s3Error, r.URL.Path)
|
|
|
|
return
|
|
|
|
}
|
2016-02-04 15:52:25 -05:00
|
|
|
}
|
|
|
|
|
2015-10-16 14:26:01 -04:00
|
|
|
err := api.Filesystem.DeleteBucket(bucket)
|
|
|
|
if err != nil {
|
|
|
|
errorIf(err.Trace(), "DeleteBucket failed.", nil)
|
|
|
|
switch err.ToGoError().(type) {
|
|
|
|
case fs.BucketNotFound:
|
2016-03-10 05:24:52 -05:00
|
|
|
writeErrorResponse(w, r, ErrNoSuchBucket, r.URL.Path)
|
2015-10-16 14:26:01 -04:00
|
|
|
case fs.BucketNotEmpty:
|
2016-03-10 05:24:52 -05:00
|
|
|
writeErrorResponse(w, r, ErrBucketNotEmpty, r.URL.Path)
|
2015-10-16 14:26:01 -04:00
|
|
|
default:
|
2016-03-10 05:24:52 -05:00
|
|
|
writeErrorResponse(w, r, ErrInternalError, r.URL.Path)
|
2015-10-16 14:26:01 -04:00
|
|
|
}
|
|
|
|
return
|
|
|
|
}
|
accessPolicy: Implement Put, Get, Delete access policy.
This patch implements Get,Put,Delete bucket policies
Supporting - http://docs.aws.amazon.com/AmazonS3/latest/dev/access-policy-language-overview.html
Currently supports following actions.
"*": true,
"s3:*": true,
"s3:GetObject": true,
"s3:ListBucket": true,
"s3:PutObject": true,
"s3:CreateBucket": true,
"s3:GetBucketLocation": true,
"s3:DeleteBucket": true,
"s3:DeleteObject": true,
"s3:AbortMultipartUpload": true,
"s3:ListBucketMultipartUploads": true,
"s3:ListMultipartUploadParts": true,
following conditions for "StringEquals" and "StringNotEquals"
"s3:prefix", "s3:max-keys"
2016-02-03 19:46:56 -05:00
|
|
|
|
|
|
|
// Delete bucket access policy, if present - ignore any errors.
|
|
|
|
removeBucketPolicy(bucket)
|
|
|
|
|
|
|
|
// Write success response.
|
2015-10-16 23:02:37 -04:00
|
|
|
writeSuccessNoContent(w)
|
2015-10-16 14:26:01 -04:00
|
|
|
}
|