From b2f51225bc78212682fd087a4ef8a67c51a94188 Mon Sep 17 00:00:00 2001 From: Lukasz Rajewski Date: Fri, 15 Oct 2021 12:11:44 +0200 Subject: Expose Update Handlers Expose Update Handlers for Definition, Profile and Config Tmpl Issue-ID: MULTICLOUD-1410 Signed-off-by: Lukasz Rajewski Change-Id: Ibe6fe05458f2af28f3e1ca14a54492a4bae19362 --- src/k8splugin/api/api.go | 3 ++ src/k8splugin/api/configtemplatehandler.go | 53 ++++++++++++++++++++++++- src/k8splugin/api/defhandler.go | 52 ++++++++++++++++++++++-- src/k8splugin/api/profilehandler.go | 64 +++++++++++++++++++++++++++++- src/k8splugin/api/profilehandler_test.go | 2 +- 5 files changed, 167 insertions(+), 7 deletions(-) (limited to 'src/k8splugin/api') diff --git a/src/k8splugin/api/api.go b/src/k8splugin/api/api.go index ed23f392..a3e53dc8 100644 --- a/src/k8splugin/api/api.go +++ b/src/k8splugin/api/api.go @@ -104,6 +104,7 @@ func NewRouter(defClient rb.DefinitionManager, resRouter.HandleFunc("/definition/{rbname}", defHandler.listVersionsHandler).Methods("GET") resRouter.HandleFunc("/definition", defHandler.listAllHandler).Methods("GET") resRouter.HandleFunc("/definition/{rbname}/{rbversion}", defHandler.getHandler).Methods("GET") + resRouter.HandleFunc("/definition/{rbname}/{rbversion}", defHandler.updateHandler).Methods("PUT") resRouter.HandleFunc("/definition/{rbname}/{rbversion}", defHandler.deleteHandler).Methods("DELETE") //Setup resource bundle profile routes @@ -115,6 +116,7 @@ func NewRouter(defClient rb.DefinitionManager, resRouter.HandleFunc("/definition/{rbname}/{rbversion}/profile", profileHandler.listHandler).Methods("GET") resRouter.HandleFunc("/definition/{rbname}/{rbversion}/profile/{prname}/content", profileHandler.uploadHandler).Methods("POST") resRouter.HandleFunc("/definition/{rbname}/{rbversion}/profile/{prname}", profileHandler.getHandler).Methods("GET") + resRouter.HandleFunc("/definition/{rbname}/{rbversion}/profile/{prname}", profileHandler.updateHandler).Methods("PUT") resRouter.HandleFunc("/definition/{rbname}/{rbversion}/profile/{prname}", profileHandler.deleteHandler).Methods("DELETE") // Config Template @@ -126,6 +128,7 @@ func NewRouter(defClient rb.DefinitionManager, resRouter.HandleFunc("/definition/{rbname}/{rbversion}/config-template", templateHandler.listHandler).Methods("GET") resRouter.HandleFunc("/definition/{rbname}/{rbversion}/config-template/{tname}/content", templateHandler.uploadHandler).Methods("POST") resRouter.HandleFunc("/definition/{rbname}/{rbversion}/config-template/{tname}", templateHandler.getHandler).Methods("GET") + resRouter.HandleFunc("/definition/{rbname}/{rbversion}/config-template/{tname}", templateHandler.updateHandler).Methods("PUT") resRouter.HandleFunc("/definition/{rbname}/{rbversion}/config-template/{tname}", templateHandler.deleteHandler).Methods("DELETE") // Config value diff --git a/src/k8splugin/api/configtemplatehandler.go b/src/k8splugin/api/configtemplatehandler.go index 0560c7ea..e8750fd8 100644 --- a/src/k8splugin/api/configtemplatehandler.go +++ b/src/k8splugin/api/configtemplatehandler.go @@ -59,7 +59,7 @@ func (h rbTemplateHandler) createHandler(w http.ResponseWriter, r *http.Request) return } - err = h.client.Create(rbName, rbVersion, p) + err = h.client.CreateOrUpdate(rbName, rbVersion, p, false) if err != nil { http.Error(w, err.Error(), http.StatusInternalServerError) return @@ -123,6 +123,57 @@ func (h rbTemplateHandler) getHandler(w http.ResponseWriter, r *http.Request) { } } +// createHandler handles creation of the template entry in the database +func (h rbTemplateHandler) updateHandler(w http.ResponseWriter, r *http.Request) { + var p rb.ConfigTemplate + + vars := mux.Vars(r) + rbName := vars["rbname"] + rbVersion := vars["rbversion"] + templateName := vars["tname"] + + err := json.NewDecoder(r.Body).Decode(&p) + switch { + case err == io.EOF: + http.Error(w, "Empty body", http.StatusBadRequest) + return + case err != nil: + http.Error(w, err.Error(), http.StatusUnprocessableEntity) + return + } + + // Name is required. + if p.TemplateName == "" { + http.Error(w, "Missing name in POST request", http.StatusBadRequest) + return + } + + ret, err := h.client.Get(rbName, rbVersion, templateName) + if err != nil { + http.Error(w, err.Error(), http.StatusInternalServerError) + return + } + + if p.TemplateName != "" && p.TemplateName != ret.TemplateName { + http.Error(w, "Template name mismatch", http.StatusBadRequest) + return + } + + err = h.client.CreateOrUpdate(rbName, rbVersion, p, true) + if err != nil { + http.Error(w, err.Error(), http.StatusInternalServerError) + return + } + + w.Header().Set("Content-Type", "application/json") + w.WriteHeader(http.StatusCreated) + err = json.NewEncoder(w).Encode(p) + if err != nil { + http.Error(w, err.Error(), http.StatusInternalServerError) + return + } +} + // getHandler handles GET operations on a particular template func (h rbTemplateHandler) listHandler(w http.ResponseWriter, r *http.Request) { vars := mux.Vars(r) diff --git a/src/k8splugin/api/defhandler.go b/src/k8splugin/api/defhandler.go index 480d4be5..3dea8ade 100644 --- a/src/k8splugin/api/defhandler.go +++ b/src/k8splugin/api/defhandler.go @@ -35,7 +35,7 @@ type rbDefinitionHandler struct { client rb.DefinitionManager } -// createHandler handles creation of the definition entry in the database +// createOrUpdateHandler handles creation of the definition entry in the database func (h rbDefinitionHandler) createHandler(w http.ResponseWriter, r *http.Request) { var v rb.Definition @@ -48,20 +48,64 @@ func (h rbDefinitionHandler) createHandler(w http.ResponseWriter, r *http.Reques http.Error(w, err.Error(), http.StatusUnprocessableEntity) return } + h.createOrUpdateHandler(v, w, false) +} + +// createOrUpdateHandler handles creation of the definition entry in the database +func (h rbDefinitionHandler) updateHandler(w http.ResponseWriter, r *http.Request) { + vars := mux.Vars(r) + name := vars["rbname"] + version := vars["rbversion"] + + var v rb.Definition + err := json.NewDecoder(r.Body).Decode(&v) + switch { + case err == io.EOF: + http.Error(w, "Empty body", http.StatusBadRequest) + return + case err != nil: + http.Error(w, err.Error(), http.StatusUnprocessableEntity) + return + } + + if v.RBVersion != "" && v.RBVersion != version { + http.Error(w, "RB version mismatch", http.StatusBadRequest) + return + } + + if v.RBName != "" && v.RBName != name { + http.Error(w, "RB name mismatch", http.StatusBadRequest) + return + } + + v.RBVersion = version + v.RBName = name + + h.createOrUpdateHandler(v, w, true) +} + +// createOrUpdateHandler handles creation of the definition entry in the database +func (h rbDefinitionHandler) createOrUpdateHandler(v rb.Definition, w http.ResponseWriter, update bool) { // Name is required. if v.RBName == "" { - http.Error(w, "Missing name in POST request", http.StatusBadRequest) + http.Error(w, "Missing name in request", http.StatusBadRequest) return } // Version is required. if v.RBVersion == "" { - http.Error(w, "Missing version in POST request", http.StatusBadRequest) + http.Error(w, "Missing version in request", http.StatusBadRequest) return } - ret, err := h.client.Create(v) + var ret rb.Definition + var err error + if update { + ret, err = h.client.Update(v) + } else { + ret, err = h.client.Create(v) + } if err != nil { http.Error(w, err.Error(), http.StatusInternalServerError) return diff --git a/src/k8splugin/api/profilehandler.go b/src/k8splugin/api/profilehandler.go index acd23060..1babc4ae 100644 --- a/src/k8splugin/api/profilehandler.go +++ b/src/k8splugin/api/profilehandler.go @@ -56,7 +56,7 @@ func (h rbProfileHandler) createHandler(w http.ResponseWriter, r *http.Request) return } - ret, err := h.client.Create(p) + ret, err := h.client.CreateOrUpdate(p, false) if err != nil { http.Error(w, err.Error(), http.StatusInternalServerError) return @@ -127,6 +127,68 @@ func (h rbProfileHandler) getHandler(w http.ResponseWriter, r *http.Request) { } } +// updateHandler updates Profile Key in the database +// Returns an rb.Profile +func (h rbProfileHandler) updateHandler(w http.ResponseWriter, r *http.Request) { + vars := mux.Vars(r) + rbName := vars["rbname"] + rbVersion := vars["rbversion"] + prName := vars["prname"] + + ret, err := h.client.Get(rbName, rbVersion, prName) + if err != nil { + // Separate "Not found" from generic DB errors + if strings.Contains(err.Error(), "Error finding") { + http.Error(w, err.Error(), http.StatusNotFound) + return + } else { + http.Error(w, err.Error(), http.StatusInternalServerError) + return + } + } + + var p rb.Profile + + err = json.NewDecoder(r.Body).Decode(&p) + switch { + case err == io.EOF: + http.Error(w, "Empty body", http.StatusBadRequest) + return + case err != nil: + http.Error(w, err.Error(), http.StatusUnprocessableEntity) + return + } + + if p.ProfileName != "" && p.ProfileName != ret.ProfileName { + http.Error(w, "Profile name mismatch", http.StatusBadRequest) + return + } + + if p.RBVersion != "" && p.RBVersion != ret.RBVersion { + http.Error(w, "RB version mismatch", http.StatusBadRequest) + return + } + + if p.RBName != "" && p.RBName != ret.RBName { + http.Error(w, "RB name mismatch", http.StatusBadRequest) + return + } + + p.ProfileName = ret.ProfileName + p.RBVersion = ret.RBVersion + p.RBName = ret.RBName + + ret, err = h.client.CreateOrUpdate(p, true) + + w.Header().Set("Content-Type", "application/json") + w.WriteHeader(http.StatusOK) + err = json.NewEncoder(w).Encode(ret) + if err != nil { + http.Error(w, err.Error(), http.StatusInternalServerError) + return + } +} + // getHandler gets all profiles of a Resource Bundle Key in the database // Returns a list of rb.Profile func (h rbProfileHandler) listHandler(w http.ResponseWriter, r *http.Request) { diff --git a/src/k8splugin/api/profilehandler_test.go b/src/k8splugin/api/profilehandler_test.go index 32d0061f..181b775b 100644 --- a/src/k8splugin/api/profilehandler_test.go +++ b/src/k8splugin/api/profilehandler_test.go @@ -42,7 +42,7 @@ type mockRBProfile struct { Err error } -func (m *mockRBProfile) Create(inp rb.Profile) (rb.Profile, error) { +func (m *mockRBProfile) CreateOrUpdate(inp rb.Profile, update bool) (rb.Profile, error) { if m.Err != nil { return rb.Profile{}, m.Err } -- cgit 1.2.3-korg