Updating updateMovieHandler to be able to update only some fields (patch instead of put). Update routes with the correct verb.
All checks were successful
Deploy Greenlight API / deploy (push) Successful in 1m20s

This commit is contained in:
Maxime Delporte
2025-11-07 11:57:04 +01:00
parent 1270a3bda6
commit b76496e096
2 changed files with 21 additions and 10 deletions

View File

@@ -109,11 +109,12 @@ func (app *application) updateMovieHandler(w http.ResponseWriter, r *http.Reques
} }
// Declare an input struct to hold the expected data from the client // Declare an input struct to hold the expected data from the client
// Use pointers for the Title, Year and Runtime fields : so we can see if a client has provided a particular key/value pair in the JSON.
var input struct { var input struct {
Title string `json:"title"` Title *string `json:"title"`
Year int32 `json:"year"` Year *int32 `json:"year"`
Runtime data.Runtime `json:"runtime"` Runtime *data.Runtime `json:"runtime"`
Genres []string `json:"genres"` Genres []string `json:"genres"`
} }
// Read the JSON request body data into the input struct // Read the JSON request body data into the input struct
@@ -123,11 +124,21 @@ func (app *application) updateMovieHandler(w http.ResponseWriter, r *http.Reques
return return
} }
// Copy the values from the request body to the appropriate fields of the movie record. // If the input.Title value is nil, then we know that no corresponding "title" key/value pair was provided in the JSON request body. So we move on and leave the movie record unchanged. Otherwise, we update the movie record with the new title value. Importantly, because input.Title is now a pointer to a string, we need to dereference the pointer using the * operator to get the underlying value before assigning it to our movie record.
movie.Title = input.Title if input.Title != nil {
movie.Year = input.Year movie.Title = *input.Title
movie.Runtime = input.Runtime }
movie.Genres = input.Genres
// We also do the same for the other fields in the input struct.
if input.Year != nil {
movie.Year = *input.Year
}
if input.Runtime != nil {
movie.Runtime = *input.Runtime
}
if input.Genres != nil {
movie.Genres = input.Genres // We don't need to dereference a slice.
}
// Validate the updated movie record, sending the client a 422 Unprocessable Entity response if any checks fail. // Validate the updated movie record, sending the client a 422 Unprocessable Entity response if any checks fail.
v := validator.New() v := validator.New()

View File

@@ -24,7 +24,7 @@ func (app *application) routes() http.Handler {
router.HandlerFunc(http.MethodGet, "/v1/healthcheck", app.healthcheckHandler) router.HandlerFunc(http.MethodGet, "/v1/healthcheck", app.healthcheckHandler)
router.HandlerFunc(http.MethodPost, "/v1/movies", app.createMovieHandler) router.HandlerFunc(http.MethodPost, "/v1/movies", app.createMovieHandler)
router.HandlerFunc(http.MethodGet, "/v1/movies/:id", app.showMovieHandler) router.HandlerFunc(http.MethodGet, "/v1/movies/:id", app.showMovieHandler)
router.HandlerFunc(http.MethodPut, "/v1/movies/:id", app.updateMovieHandler) router.HandlerFunc(http.MethodPatch, "/v1/movies/:id", app.updateMovieHandler)
router.HandlerFunc(http.MethodDelete, "/v1/movies/:id", app.deleteMovieHandler) router.HandlerFunc(http.MethodDelete, "/v1/movies/:id", app.deleteMovieHandler)
// Return the httprouter instance. // Return the httprouter instance.