In ASP.NET Core, controller-based APIs organize related endpoints into classes that inherit from ControllerBase. This class provides essential HTTP functionality including status code responses, model binding, and request handling.
public class ProductsController : ControllerBase{[HttpGet]public ActionResult<IEnumerable<Product>> GetAll() => _products;[HttpGet("{id}")]public ActionResult<Product> GetById(int id) => _products.FirstOrDefault(p => p.Id == id);}
[ApiController] in ASP.NETIn ASP.NET Core, the [ApiController] attribute enhances controller classes with API-specific behaviors that reduce boilerplate code. This attribute automatically performs model validation, infers parameter binding sources, and returns standardized problem details for errors without requiring manual implementation.
[ApiController][Route("api/products")]public class ProductsController : ControllerBase{// Model validation happens automatically// Parameter binding sources are inferred}
[Route] in ASP.NETIn ASP.NET Core, the [Route] attribute defines the URL patterns for controller endpoints with the route template passed as a string parameter.
[Route("api/[controller]")] // Resolves to "api/products"public class ProductsController : ControllerBase{[HttpGet]public ActionResult<Product> Get() => _products;}
In ASP.NET Core, HTTP verb attributes ([HttpGet], [HttpPost], [HttpPut], [HttpDelete]) map controller action methods to specific HTTP operations:
public class ProductsController : ControllerBase{[HttpGet] // Handles GET requestspublic ActionResult<Product[]> GetAll() => _products;[HttpPost] // Handles POST requestspublic ActionResult<Product> Create(Product product) => CreatedAtAction(nameof(GetById), new { id = product.Id }, product);[HttpPut("{id}")] // Handles PUT requestspublic IActionResult Update(int id, Product product) => NoContent();[HttpDelete("{id}")] // Handles DELETE requestspublic IActionResult Delete(int id) => NoContent();}
In ASP.NET Core, route parameters capture dynamic values from URLs using curly brace syntax {id} in route patterns and corresponding method parameters.
[HttpGet("{id}")] // Captures dynamic value from URLpublic ActionResult<Product> GetById(int id) // Parameter name matches route parameter{var product = _products.FirstOrDefault(p => p.Id == id);return product == null ? NotFound() : product;}
ActionResult in ASP.NETIn ASP.NET Core, ActionResult<T> provides flexibility to return either data (200 OK) or status code responses (404 Not Found, 400 Bad Request) from controller actions.
public ActionResult<Product> GetById(int id){var product = _products.FirstOrDefault(p => p.Id == id);if (product == null)return NotFound(); // Returns 404 status codereturn product; // Returns 200 OK with product data}
In ASP.NET Core, model binding automatically maps request data to action method parameters with optional source binding attributes ([FromQuery], [FromBody], [FromRoute]).
// Automatic binding based on parameter names[HttpGet("{id}")]public ActionResult<Product> GetById(int id) // id from route{return _products.FirstOrDefault(p => p.Id == id);}// Explicit binding with source attributes[HttpGet("search")]public ActionResult<IEnumerable<Product>> Search([FromQuery] string name, // From query string[FromQuery] decimal? maxPrice, // From query string[FromRoute] string category) // From route{return _products.Where(p => p.Name.Contains(name) && p.Price <= maxPrice);}
In ASP.NET Core, data annotations like [Required] and [StringLength] enable declarative validation that is automatically enforced by the framework.
public class Product{public int Id { get; set; }[Required][StringLength(100, MinimumLength = 3)]public string Name { get; set; } = string.Empty;}