Skip to content

Repository files navigation

PaletteCoreAPI

PaletteCoreAPI is an authenticated ASP.NET Core REST API for a palette-oriented social platform. It models users, profiles, posts, colours, tags, comments, favourites, following relationships, and API-key records in SQL Server.

Engineering highlights

  • .NET 10 and ASP.NET Core controllers
  • Entity Framework Core with SQL Server and a committed initial migration
  • JWT bearer authentication with a secure fallback policy
  • role- or scope-based protection for user and API-key administration
  • validated request and response DTOs that prevent entity over-posting
  • password hashing with ASP.NET Core Identity's PasswordHasher
  • API keys returned once on creation and omitted from later reads
  • OpenAPI/Swagger documentation, Problem Details, and a public health endpoint
  • integration tests with an in-memory database
  • GitHub Actions build and test workflow

Technology stack

AreaTechnology
LanguageC#
Runtime.NET 10
Web frameworkASP.NET Core Web API
Data accessEntity Framework Core 10
DatabaseMicrosoft SQL Server
AuthenticationJWT bearer / OpenID Connect authority
API documentationSwashbuckle OpenAPI and Swagger UI
TestingxUnit, WebApplicationFactory, EF Core InMemory
AutomationGitHub Actions

Architecture

The API uses a focused controller-to-database design. Controllers accept validated contracts, map them to the existing domain entities, and use PaletteContext for persistence. Authentication is applied globally; only /health is anonymous.

flowchart LR
Client["HTTP client"] --> Auth["JWT bearer authentication"]
Auth --> Controllers["API controllers"]
Controllers --> DTOs["Validated request/response DTOs"]
Controllers --> Context["PaletteContext"]
Context --> EF["Entity Framework Core"]
EF --> SQL[("SQL Server")]
Swagger["Swagger UI"] -. documents .-> Controllers
Health["/health"] --> Checks["Health checks"]
Loading

Request flow

sequenceDiagram
participant Client
participant Auth as JWT middleware
participant Posts as PostsController
participant DB as PaletteContext
Client->>Auth: GET /api/Posts/{id} + bearer token
Auth->>Posts: Authenticated request
Posts->>DB: Read post without tracking
alt Post exists
DB-->>Posts: Posts entity
Posts-->>Client: 200 OK + PostDto
else Post is missing
DB-->>Posts: null
Posts-->>Client: 404 Not Found
end
Loading

Domain model

erDiagram
USERS ||--o{ APIKEYS : owns
USERS ||--o{ POSTS : publishes
USERS ||--o{ USER_PROFILE : has
USERS ||--o{ COMMENTS : writes
POSTS ||--o{ COMMENTS : receives
USERS ||--o{ FAVOURITES : creates
POSTS ||--o{ FAVOURITES : receives
USERS ||--o{ FOLLOWINGS : follows
POSTS ||--o{ POST_COLORS : contains
POSTS ||--o{ POST_TAGS : categorised_by
TAGS ||--o{ POST_TAGS : assigned_through
Loading

API surface

All domain routes require an authenticated user.

ResourceBase routeOperations
Posts/api/PostsGET, GET by ID, POST, PUT, DELETE
Post colours/api/PostColorsGET, GET by ID, POST, PUT, DELETE
Tags/api/TagsGET, GET by ID, POST, PUT, DELETE
Post tags/api/PostTagsGET, GET by ID, POST, PUT, DELETE
Comments/api/CommentsGET, GET by ID, POST, PUT, DELETE
Favourites/api/FavouritesGET, GET by ID, POST, PUT, DELETE
Followings/api/FollowingsGET, GET by ID, POST, PUT, DELETE
User profiles/api/UserProfilesGET, GET by ID, POST, PUT, DELETE
Users/api/UsersAdmin policy; GET, POST, PUT, DELETE
API keys/api/ApikeysAdmin policy; GET, POST, PUT, DELETE
Health/healthAnonymous GET

The admin policy accepts either the admin role or a scope claim containing palette.admin. User responses never include password hashes. API-key list and detail responses never include the stored key; the generated value is returned only by the create operation.

Project structure

PaletteCoreAPI/
├── .github/workflows/ci.yml Build and test automation
├── PaletteCoreAPI/
│ ├── Contracts/ Validated public API contracts
│ ├── Controllers/ Authenticated HTTP endpoints
│ ├── Migrations/ EF Core database migration
│ ├── Models/ Entities and PaletteContext
│ └── Program.cs Services and HTTP pipeline
├── PaletteCoreAPI.Tests/ Integration and contract tests
├── PaletteCoreAPI.sln
└── global.json

Getting started

Prerequisites

  • .NET SDK 10.0.302 or a compatible .NET 10 SDK
  • SQL Server
  • an OpenID Connect or OAuth 2.0 authority that issues JWT access tokens

Configure local settings

The repository contains no database password, identity-provider secret, or production endpoint. Use .NET user secrets from the API project:

dotnet user-secrets --project PaletteCoreAPI/PaletteCoreAPI.csproj set \
"ConnectionStrings:Database" \
"Server=localhost;Database=Palette;Integrated Security=True;TrustServerCertificate=True"
dotnet user-secrets --project PaletteCoreAPI/PaletteCoreAPI.csproj set \
"Authentication:Authority" \
"https://identity.example.com"
dotnet user-secrets --project PaletteCoreAPI/PaletteCoreAPI.csproj set \
"Authentication:Audience" \
"palette-api"

Use a connection string and authority appropriate for your environment. Production configuration should come from the deployment platform's secret store or environment variables.

Create the database

dotnet tool restore
export ConnectionStrings__Database='Server=localhost;Database=Palette;Integrated Security=True;TrustServerCertificate=True'
dotnet tool run dotnet-ef database update --project PaletteCoreAPI/PaletteCoreAPI.csproj

Build, test, and run

dotnet restore PaletteCoreAPI.sln
dotnet build PaletteCoreAPI.sln --configuration Release --no-restore
dotnet test PaletteCoreAPI.sln --configuration Release --no-build
dotnet run --project PaletteCoreAPI/PaletteCoreAPI.csproj

The development launch profile opens Swagger UI at https://localhost:7042/swagger. The public health probe is available at https://localhost:7042/health.

Verification

The modernized solution builds with zero warnings and zero errors. The automated suite verifies that:

  • the health endpoint remains public;
  • representative domain routes reject anonymous access;
  • public contracts do not expose password or stored API-key fields.

Security notes

This repository no longer contains a fallback database connection string. Authentication configuration is external, entity types are not accepted as public request bodies, passwords are hashed before persistence, and administrative resources require an explicit policy.

The API delegates token issuance, account recovery, key rotation, rate limiting, and operational monitoring to surrounding infrastructure. Those production concerns must be configured by the deploying environment.

Author

Serkan Seker

About

Authenticated .NET 10 REST API with EF Core, SQL Server, JWT authorization, migrations, and integration tests.

Topics

Resources

Stars

0 stars

Watchers

1 watching

Forks

Releases

Packages

Contributors

Languages