DEV Community

loading...

DELETE and PATCH

Brandon Weaver
Software Engineer
・3 min read

In this, possibly the final part of the series, we'll focus on implementing DELETE and PATCH actions within our users controller.

We'll start by implementing the DELETE action as it's very simple and easy to do. We'll start by opening up 'AppRepo.cs' and adding a new method called DeleteUser.

public void DeleteUser(User user)
{
    this._context.Users.Remove(user);
}
Enter fullscreen mode Exit fullscreen mode

Now, we'll open up 'UsersController.cs' and create our DELETE action.

[HttpDelete("{id}")]
public ActionResult Delete(int id)
{
    User user = this._repo.GetUserById(id);

    if (user != null)
    {
        this._repo.DeleteUser(user);
        this._repo.SaveChanges();

        return NoContent();
    }
    return NotFound();
}
Enter fullscreen mode Exit fullscreen mode

That's it. Now, assuming there is a user with the ID of 1 within our database, we can remove them with the following JavaScript.

fetch("https://localhost:5001/api/users/1", {
    method: "DELETE"
})
.then(r => console.log(r));
Enter fullscreen mode Exit fullscreen mode

Unfortunately creating our PATCH action isn't quite so simple. We'll rely on a few more NuGet packages to help us out. In your terminal, run the following two commands to install the packages we'll be using.

dotnet add package Microsoft.AspNetCore.JsonPatch
dotnet add package Microsoft.AspNetCore.Mvc.NewtonsoftJson
Enter fullscreen mode Exit fullscreen mode

Now, within 'Startup.cs' we'll need to make some changes to get Newtonsoft JSON serlialization working within our controllers.

First, add the following using statement at the top of the file to reference our newly installed package.

using Newtonsoft.Json.Serialization;
Enter fullscreen mode Exit fullscreen mode

Now we need to locate the following line within the ConfigureServices method.

services.AddControllers();
Enter fullscreen mode Exit fullscreen mode

This line will need to be changed as follows.

services.AddControllers().AddNewtonsoftJson(s => {
    s.SerializerSettings.ContractResolver = new CamelCasePropertyNamesContractResolver();
});
Enter fullscreen mode Exit fullscreen mode

Next, we'll create a new DTO and map for handling the transfer of updated properties from the DTO to our user within the database context and vice-versa.

Within the 'Data' folder, create a new file named 'UserUpdateDto.cs', and add the following code.

using System.ComponentModel.DataAnnotations;

namespace AspNetCoreWebApiIntro.Dtos
{
    public class UserUpdateDto
    {
        [Key]
        public int Id { get; set; }

        [Required]
        public string FirstName { get; set; }

        [Required]
        public string LastName { get; set; }
    }
}
Enter fullscreen mode Exit fullscreen mode

Open up 'UserProfile.cs', and add the following code.

using AutoMapper;

using AspNetCoreWebApiIntro.Dtos;
using AspNetCoreWebApiIntro.Models;

namespace AspNetCoreWebApiIntro.Profiles
{
    public class UsersProfile : Profile
    {
        public UsersProfile()
        {
            CreateMap<User, UserReadDto>();
            CreateMap<User, UserUpdateDto>(); // New
            CreateMap<UserUpdateDto, User>(); // New
        }
    }
}
Enter fullscreen mode Exit fullscreen mode

Finally, we're able to create our PATCH action. Open 'UsersController.cs' and add the following using statement to the top of the file.

using Microsoft.AspNetCore.JsonPatch;
Enter fullscreen mode Exit fullscreen mode

Next, add the following action.

[HttpPatch("{id}")]
public ActionResult Update(int id, JsonPatchDocument<UserUpdateDto> patchDoc)
{
    User user = this._repo.GetUserById(id);

    if (user != null)
    {
        UserUpdateDto userToUpdate = this._mapper.Map<UserUpdateDto>(user);
        patchDoc.ApplyTo(userToUpdate, ModelState);

        if (!TryValidateModel(userToUpdate))
        {
            return ValidationProblem(ModelState);
        }

        this._mapper.Map(userToUpdate, user);
        this._repo.SaveChanges();

        return NoContent();
    }
    return NotFound();
}
Enter fullscreen mode Exit fullscreen mode

Here, we're grabbing the user from our repository as usual, creating a DTO from that user using our mapper, and applying our patch operations using the JSON patch document provided by the Microsoft.AspNetCore.JsonPatch package to the DTO before mapping it back to our user. Traditionally, you'd want to have an UpdateUser method within your repository to call prior to SaveChanges, however, mapping the user from our edited DTO applies all of the logic needed to update the user.

Again, assuming that there is a user with the ID of 1, we can now change their last name with the following JavaScript.

fetch("https://localhost:5001/api/users/5", {
    method: "PATCH",
    headers: {
        "Content-Type": "application/json"
    },
    body: JSON.stringify([
        {
            op: "replace",
            path: "/lastName",
            value: "Doe"
        }
    ])
})
.then(r => console.log(r));
Enter fullscreen mode Exit fullscreen mode

I hope that a few people were able to find this series helpful. I may decide to add additional sections in the future, but this should suffice to cover the fundamentals and I'd be glad to answer any questions (if I'm able) in the meantime.

Thanks for reading.

Discussion (0)