Asp.NET Core Simple CRUD Web API

When building data-driven applications, or may be an admin panel to manage database tables, we usually use CRUD (Create, Read, Update, Delete) operations to manipulate data. But when application grows, it’ll be hard and boring process when creating CRUD operation contracts.

In this tutorial, we’ll end up with this kind of controllers for our CRUD operations on entities:

Create folder for our project:

mkdir SimpleCrudApi
dotnet new webapi

Open the SimpleCrudApi folder with your preferred IDE or code editor. I’ve updated my .csproj with Entity Framework Core and MySql libraries:


I’ve created User and Announcement entities for now, but you can extend later:

After adding ApplicationDbContext, we have to add it to Startup:

When we run the app, we should see our tables created in database by EF Core:

Repository Pattern

I will use Repository pattern on entities to reduce complexity and increase readability.

The repository pattern is an abstraction and its purpose is to reduce complexity, with benefits of allowing us writing tests.

First create Repository.cs file under folder named Entities:

As you see we created a few methods for our repositories:

Task<DbSet<T>> List();
Task<T> Get(TKey id);
Task Create(T entity);
Task Update(T entity);
Task Delete(T entity);
Task Delete(TKey id);

T type represents entity type and TKey will be the primary key of entity.

I’m implementing IRepository interface with async/await:

Now I’m creating a SimpleCrudService with same signature of our IRepository:

Right now we are ready to setup our SimpleCrudController. CRUD controllers we want will extend this class instead of Controller because we already extend Controller:

I’ve implemented SimpleCrudController methods with HttpGet, HttpPost and HttpDelete verbs. Right now we can create our CRUD controllers that will extend this class:

As you see, we don’t have duplicated code anymore. This approach save lots of keystrokes and speeds up you when creating boring CRUD controllers.


List our users by sending a GET request to /User/List:

curl -X GET http://localhost:5000/User/List

Create a user:

curl -X POST \
 http://localhost:5000/User/Create \
 -H ‘content-type: application/json’ \
 -d ‘{
 “Name”: “Ozgur”,
 “Surname”: “GUL”,
 “Email”: “

After creating, ifwe list again, it’ll give us correct result:


And so on…


As I mention this is a ‘SimpleCrudController’ and doesn’t support pagination, filtering and sorting.

Also right now, when creating or updating entities, it expects an entity object from client. Instead of entities, they should communicate with DTO’s (Data Transfer Object) but then we have to implement some Entity => Dto or Dto => Entity mapper magics. I’m leaving them to you.

As always, if you don’t want to re-invent wheel with in your current application, you should use OData.

Also source code can be found here:

One clap, two clap, three clap, forty?

By clapping more or less, you can signal to us which stories really stand out.