diff --git a/internal/api/handlers.go b/internal/api/handlers.go index 7ed4767..8b6cc70 100644 --- a/internal/api/handlers.go +++ b/internal/api/handlers.go @@ -36,6 +36,7 @@ func NewGoCertRouter(env *Environment) http.Handler { apiV1Router.HandleFunc("GET /accounts/{id}", GetUserAccount(env)) apiV1Router.HandleFunc("GET /accounts", GetUserAccounts(env)) apiV1Router.HandleFunc("POST /accounts", PostUserAccount(env)) + apiV1Router.HandleFunc("DELETE /accounts/{id}", DeleteUserAccount(env)) apiV1Router.HandleFunc("POST /accounts/{id}/change_password", ChangeUserAccountPassword(env)) m := metrics.NewMetricsSubsystem(env.DB) @@ -371,6 +372,27 @@ func PostUserAccount(env *Environment) http.HandlerFunc { } } +// DeleteUserAccount handler receives an id as a path parameter, +// deletes the corresponding User Account, and returns a http.StatusNoContent on success +func DeleteUserAccount(env *Environment) http.HandlerFunc { + return func(w http.ResponseWriter, r *http.Request) { + id := r.PathValue("id") + insertId, err := env.DB.DeleteUser(id) + if err != nil { + if errors.Is(err, certdb.ErrIdNotFound) { + logErrorAndWriteResponse(err.Error(), http.StatusNotFound, w) + return + } + logErrorAndWriteResponse(err.Error(), http.StatusInternalServerError, w) + return + } + w.WriteHeader(http.StatusAccepted) + if _, err := w.Write([]byte(strconv.FormatInt(insertId, 10))); err != nil { + logErrorAndWriteResponse(err.Error(), http.StatusInternalServerError, w) + } + } +} + func ChangeUserAccountPassword(env *Environment) http.HandlerFunc { return func(w http.ResponseWriter, r *http.Request) { id := r.PathValue("id") diff --git a/internal/api/handlers_test.go b/internal/api/handlers_test.go index a5e68cf..961e3d6 100644 --- a/internal/api/handlers_test.go +++ b/internal/api/handlers_test.go @@ -475,6 +475,22 @@ func TestGoCertUsersHandlers(t *testing.T) { response: "Password does not meet requirements. It must include at least one capital letter, one lowercase letter, and either a number or a symbol.", status: http.StatusBadRequest, }, + { + desc: "Delete user success", + method: "DELETE", + path: "/api/v1/accounts/2", + data: invalidUser, + response: "1", + status: http.StatusAccepted, + }, + { + desc: "Delete user failure", + method: "DELETE", + path: "/api/v1/accounts/2", + data: invalidUser, + response: "error: id not found", + status: http.StatusNotFound, + }, } for _, tC := range testCases { t.Run(tC.desc, func(t *testing.T) {