From 65f71ce0c57865630c83a5a8ecb6fa5ce9b0ba78 Mon Sep 17 00:00:00 2001 From: Harshavardhana Date: Wed, 27 Jul 2016 21:11:15 -0700 Subject: [PATCH] browser: Object upload should save metadata and notify. (#2309) Object upload from browser should save additional incoming metadata. Additionally should also notify through bucket notifications once they are set. Fixes #2292 --- bucket-handlers.go | 2 +- bucket-notification-handlers.go | 6 +++--- object-handlers.go | 8 ++++---- web-handlers.go | 30 ++++++++++++++++++++++++++++-- 4 files changed, 36 insertions(+), 10 deletions(-) diff --git a/bucket-handlers.go b/bucket-handlers.go index 650612b80..a1fc27e47 100644 --- a/bucket-handlers.go +++ b/bucket-handlers.go @@ -397,7 +397,7 @@ func (api objectAPIHandlers) PostPolicyBucketHandler(w http.ResponseWriter, r *h writeSuccessResponse(w, encodedSuccessResponse) // Load notification config if any. - nConfig, err := api.loadNotificationConfig(bucket) + nConfig, err := loadNotificationConfig(api.ObjectAPI, bucket) // Notifications not set, return. if err == errNoSuchNotifications { return diff --git a/bucket-notification-handlers.go b/bucket-notification-handlers.go index 1a24b8d4d..645df4b9b 100644 --- a/bucket-notification-handlers.go +++ b/bucket-notification-handlers.go @@ -32,10 +32,10 @@ const ( ) // loads notifcation config if any for a given bucket, returns back structured notification config. -func (api objectAPIHandlers) loadNotificationConfig(bucket string) (nConfig notificationConfig, err error) { +func loadNotificationConfig(objAPI ObjectLayer, bucket string) (nConfig notificationConfig, err error) { notificationConfigPath := path.Join(bucketConfigPrefix, bucket, bucketNotificationConfig) var objInfo ObjectInfo - objInfo, err = api.ObjectAPI.GetObjectInfo(minioMetaBucket, notificationConfigPath) + objInfo, err = objAPI.GetObjectInfo(minioMetaBucket, notificationConfigPath) if err != nil { switch err.(type) { case ObjectNotFound: @@ -44,7 +44,7 @@ func (api objectAPIHandlers) loadNotificationConfig(bucket string) (nConfig noti return notificationConfig{}, err } var buffer bytes.Buffer - err = api.ObjectAPI.GetObject(minioMetaBucket, notificationConfigPath, 0, objInfo.Size, &buffer) + err = objAPI.GetObject(minioMetaBucket, notificationConfigPath, 0, objInfo.Size, &buffer) if err != nil { switch err.(type) { case ObjectNotFound: diff --git a/object-handlers.go b/object-handlers.go index ee9d84eed..147c63a44 100644 --- a/object-handlers.go +++ b/object-handlers.go @@ -357,7 +357,7 @@ func (api objectAPIHandlers) CopyObjectHandler(w http.ResponseWriter, r *http.Re pipeReader.Close() // Load notification config if any. - nConfig, err := api.loadNotificationConfig(bucket) + nConfig, err := loadNotificationConfig(api.ObjectAPI, bucket) // Notifications not set, return. if err == errNoSuchNotifications { return @@ -441,7 +441,7 @@ func (api objectAPIHandlers) PutObjectHandler(w http.ResponseWriter, r *http.Req writeSuccessResponse(w, nil) // Load notification config if any. - nConfig, err := api.loadNotificationConfig(bucket) + nConfig, err := loadNotificationConfig(api.ObjectAPI, bucket) // Notifications not set, return. if err == errNoSuchNotifications { return @@ -778,7 +778,7 @@ func (api objectAPIHandlers) CompleteMultipartUploadHandler(w http.ResponseWrite w.(http.Flusher).Flush() // Load notification config if any. - nConfig, err := api.loadNotificationConfig(bucket) + nConfig, err := loadNotificationConfig(api.ObjectAPI, bucket) // Notifications not set, return. if err == errNoSuchNotifications { return @@ -835,7 +835,7 @@ func (api objectAPIHandlers) DeleteObjectHandler(w http.ResponseWriter, r *http. writeSuccessNoContent(w) // Load notification config if any. - nConfig, err := api.loadNotificationConfig(bucket) + nConfig, err := loadNotificationConfig(api.ObjectAPI, bucket) // Notifications not set, return. if err == errNoSuchNotifications { return diff --git a/web-handlers.go b/web-handlers.go index 4b1c85ba0..87658a200 100644 --- a/web-handlers.go +++ b/web-handlers.go @@ -374,10 +374,36 @@ func (web *webAPIHandlers) Upload(w http.ResponseWriter, r *http.Request) { vars := mux.Vars(r) bucket := vars["bucket"] object := vars["object"] - // FIXME: Allow file upload handler to set content-type, content-encoding. - if _, err := web.ObjectAPI.PutObject(bucket, object, -1, r.Body, nil); err != nil { + + // Extract incoming metadata if any. + metadata := extractMetadataFromHeader(r.Header) + + if _, err := web.ObjectAPI.PutObject(bucket, object, -1, r.Body, metadata); err != nil { writeWebErrorResponse(w, err) + return + } + + // Load notification config if any. + nConfig, err := loadNotificationConfig(web.ObjectAPI, bucket) + // Notifications not set, return. + if err == errNoSuchNotifications { + return } + // For all other errors, return. + if err != nil { + errorIf(err, "Unable to load notification config for bucket: \"%s\"", bucket) + return + } + + // Fetch object info for notifications. + objInfo, err := web.ObjectAPI.GetObjectInfo(bucket, object) + if err != nil { + errorIf(err, "Unable to fetch object info for \"%s\"", path.Join(bucket, object)) + return + } + + // Notify object created event. + notifyObjectCreatedEvent(nConfig, ObjectCreatedPut, bucket, objInfo) } // Download - file download handler.