using Microsoft.AspNetCore.Authorization; using Microsoft.AspNetCore.Mvc; using eprintServer.DTOs; using eprintServer.Entities; using eprintServer.Responses; using eprintServer.Services; using eprintServer.Interfaces; namespace eprintServer.Controllers; [Authorize] [ApiController] [Route("api/v1/product-categories")] [Authorize(Roles = "ADMIN,SUB_ADMIN")] public class ProductCategoryController : ControllerBase { private readonly ProductCategoryService _categoryService; private readonly IFileStorageService _fileStorageService; public ProductCategoryController(ProductCategoryService categoryService, IFileStorageService fileStorageService) { _categoryService = categoryService; _fileStorageService = fileStorageService; } [HttpPost("add")] [ProducesResponseType(StatusCodes.Status201Created)] [ProducesResponseType(StatusCodes.Status400BadRequest)] public async Task> AddCategory([FromBody] ProductCategoryDto categoryDto) { try { var newCategory = await _categoryService.AddCategoryAsync(categoryDto); return CreatedAtAction(nameof(GetCategoryById), new { id = newCategory.Id }, newCategory); } catch (Exception e) { return StatusCode(StatusCodes.Status500InternalServerError, $"Error creating category: {e.Message}"); } } [HttpGet("get-category-by-id/{id}")] [ProducesResponseType(StatusCodes.Status200OK)] [ProducesResponseType(StatusCodes.Status404NotFound)] public async Task> GetCategoryById(long id) { try { var category = await _categoryService.GetCategoryByIdAsync(id); if (category == null) { return NotFound($"Category with ID {id} not found."); } return Ok(category); } catch (Exception e) { return StatusCode(StatusCodes.Status500InternalServerError, $"Error fetching category: {e.Message}"); } } [HttpPut("update-category/{id}")] [ProducesResponseType(StatusCodes.Status200OK)] [ProducesResponseType(StatusCodes.Status404NotFound)] [ProducesResponseType(StatusCodes.Status400BadRequest)] public async Task> UpdateCategory(long id, [FromBody] UpdateProductCategoryRequest categoryDto) { try { var updatedCategory = await _categoryService.UpdateCategoryAsync(id, categoryDto); return Ok(updatedCategory); } catch (KeyNotFoundException knf) { return NotFound(knf.Message); } catch (Exception e) { return StatusCode(StatusCodes.Status500InternalServerError, $"Error updating category: {e.Message}"); } } [HttpPut("toggle-archive/{id}")] [ProducesResponseType(StatusCodes.Status200OK)] [ProducesResponseType(StatusCodes.Status404NotFound)] public async Task> UpdateArchiveCategory(long id) { try { var updatedCategory = await _categoryService.UpdateArchiveStatusAsync(id); return Ok(updatedCategory); } catch (KeyNotFoundException knf) { return NotFound(knf.Message); } catch (Exception e) { return StatusCode(StatusCodes.Status500InternalServerError, $"Error updating archive status: {e.Message}"); } } [HttpGet("get-all-cateogies-list")] [ProducesResponseType(StatusCodes.Status200OK)] public async Task>> GetAllCategoriesList( [FromQuery] string? search, [FromQuery] bool? archive) { try { var categories = await _categoryService.GetAllCategoriesListAsync(search, archive); return Ok(categories); } catch (Exception e) { return StatusCode(StatusCodes.Status500InternalServerError, $"Error fetching categories: {e.Message}"); } } [HttpGet("get-all-cateogies-paginated")] [ProducesResponseType(StatusCodes.Status200OK)] public async Task>> GetAllCategoriesPaged( [FromQuery] string? search, [FromQuery] bool? archive, [FromQuery] int page = 0, [FromQuery] int size = 5) { try { var pagedResult = await _categoryService.GetAllCategoriesPagedAsync(search, archive, page, size); return Ok(pagedResult); } catch (Exception e) { return StatusCode(StatusCodes.Status500InternalServerError, $"Error fetching paged categories: {e.Message}"); } } [HttpPost("upload-category-image/{categoryId:long}")] public async Task> UploadCategoryImage(long categoryId, IFormFile image) { if (image == null || image.Length == 0) { return BadRequest("An image file is required."); } try { const string SubDirectory = "categoryImages"; // Use a distinct directory // 1. Save the file to storage var fileModel = await _fileStorageService.SaveFileAsync(image, SubDirectory); // 2. Update the category entity with the new FileModel var updatedCategory = await _categoryService.UpdateCategoryImageAsync(categoryId, fileModel); if (updatedCategory == null) { // If category is not found, delete the saved file and return 404 await _fileStorageService.DeleteFileAsync(fileModel.Id); return NotFound($"Product Category with ID {categoryId} not found. Image upload failed."); } // Reuse the existing image upload response DTO var response = new ProductImageUploadResponse(fileModel); return Ok(response); } catch (Exception ex) { return StatusCode(500, $"Something went wrong during category image upload: {ex.Message}"); } } }