using Microsoft.AspNetCore.Mvc; using Microsoft.EntityFrameworkCore; namespace DysonNetwork.Sphere.Connection.WebReader; [ApiController] [Route("/feeds/articles")] public class WebArticleController(AppDatabase db) : ControllerBase { /// /// Get a list of recent web articles /// /// Maximum number of articles to return /// Number of articles to skip /// Optional feed ID to filter by /// Optional publisher ID to filter by /// List of web articles [HttpGet] public async Task GetArticles( [FromQuery] int limit = 20, [FromQuery] int offset = 0, [FromQuery] Guid? feedId = null, [FromQuery] Guid? publisherId = null ) { var query = db.WebArticles .OrderByDescending(a => a.PublishedAt) .Include(a => a.Feed) .AsQueryable(); if (feedId.HasValue) query = query.Where(a => a.FeedId == feedId.Value); if (publisherId.HasValue) query = query.Where(a => a.Feed.PublisherId == publisherId.Value); var totalCount = await query.CountAsync(); var articles = await query .Skip(offset) .Take(limit) .ToListAsync(); Response.Headers["X-Total"] = totalCount.ToString(); return Ok(articles); } /// /// Get a specific web article by ID /// /// The article ID /// The web article [HttpGet("{id:guid}")] [ProducesResponseType(404)] public async Task GetArticle(Guid id) { var article = await db.WebArticles .Include(a => a.Feed) .FirstOrDefaultAsync(a => a.Id == id); if (article == null) return NotFound(); return Ok(article); } /// /// Get random web articles /// /// Maximum number of articles to return /// List of random web articles [HttpGet("random")] public async Task GetRandomArticles([FromQuery] int limit = 5) { var articles = await db.WebArticles .OrderBy(_ => EF.Functions.Random()) .Include(a => a.Feed) .Take(limit) .ToListAsync(); return Ok(articles); } }