167 lines
6.3 KiB
C#
167 lines
6.3 KiB
C#
using Asp.Versioning;
|
||
using MediatR;
|
||
using Microsoft.AspNetCore.Mvc;
|
||
using Microsoft.Extensions.Options;
|
||
using Mirea.Api.DataAccess.Application.Cqrs.Schedule.Queries.GetScheduleList;
|
||
using Mirea.Api.Dto.Requests;
|
||
using Mirea.Api.Endpoint.Configuration.Model;
|
||
using OfficeOpenXml;
|
||
using System;
|
||
using System.Globalization;
|
||
using System.IO;
|
||
using System.Linq;
|
||
using System.Threading.Tasks;
|
||
|
||
namespace Mirea.Api.Endpoint.Controllers.V1;
|
||
|
||
[ApiVersion("1.0")]
|
||
public class ImportController(IMediator mediator, IOptionsSnapshot<GeneralConfig> config) : BaseController
|
||
{
|
||
// todo: transfer data to storage
|
||
private static string GetFaculty(char c) =>
|
||
c switch
|
||
{
|
||
'У' => "ИТУ",
|
||
'Б' => "ИКБ",
|
||
'Х' => "ИТХТ",
|
||
'Э' => "ИПТИП",
|
||
'Т' => "ИПТИП",
|
||
'Р' => "ИРИ",
|
||
'К' => "ИИИ",
|
||
'И' => "ИИТ",
|
||
'П' => "ИИТ",
|
||
_ => throw new ArgumentOutOfRangeException(nameof(c), c, null)
|
||
};
|
||
|
||
/// <summary>
|
||
/// Creates an Excel file based on a schedule filter
|
||
/// </summary>
|
||
/// <param name="request">The request object containing filter criteria.</param>
|
||
/// <returns>Excel file</returns>
|
||
[HttpPost("ImportToExcel")]
|
||
[Produces("application/vnd.ms-excel")]
|
||
public async Task<IActionResult> ImportToExcel([FromBody] ScheduleRequest request)
|
||
{
|
||
var result = (await mediator.Send(new GetScheduleListQuery
|
||
{
|
||
IsEven = request.IsEven,
|
||
DisciplineIds = request.Disciplines,
|
||
GroupIds = request.Groups,
|
||
LectureHallIds = request.LectureHalls,
|
||
ProfessorIds = request.Professors
|
||
})).Schedules;
|
||
|
||
if (result.Count == 0)
|
||
return NoContent();
|
||
|
||
ExcelPackage.LicenseContext = LicenseContext.NonCommercial;
|
||
using var package = new ExcelPackage();
|
||
var worksheet = package.Workbook.Worksheets.Add("Расписание");
|
||
|
||
int row = 1;
|
||
int col = 1;
|
||
|
||
worksheet.Cells[row, col++].Value = "День";
|
||
worksheet.Cells[row, col++].Value = "Пара";
|
||
worksheet.Cells[row, col++].Value = "Неделя";
|
||
worksheet.Cells[row, col++].Value = "Время";
|
||
worksheet.Cells[row, col++].Value = "Группа";
|
||
worksheet.Cells[row, col++].Value = "Институт";
|
||
worksheet.Cells[row, col++].Value = "Курс";
|
||
worksheet.Cells[row, col++].Value = "Дисциплина";
|
||
worksheet.Cells[row, col++].Value = "Преподаватель";
|
||
worksheet.Cells[row, col++].Value = "Вид";
|
||
worksheet.Cells[row, col++].Value = "Кампус";
|
||
worksheet.Cells[row, col].Value = "Ауд.";
|
||
|
||
row++;
|
||
col = 1;
|
||
|
||
var pairsDictionary = config.Value.ScheduleSettings!.PairPeriod;
|
||
|
||
var ruCulture = new CultureInfo("ru-RU");
|
||
|
||
foreach (var dto in result.GroupBy(s => new
|
||
{
|
||
s.DayOfWeek,
|
||
s.PairNumber,
|
||
s.IsEven,
|
||
s.DisciplineId,
|
||
TypeOfOccupations = string.Join(',', s.TypeOfOccupations.OrderBy(x => x)),
|
||
LectureHalls = string.Join(',', s.LectureHalls.OrderBy(x => x)),
|
||
Campus = string.Join(',', s.Campus.OrderBy(x => x)),
|
||
Professors = string.Join(',', s.Professors.OrderBy(x => x))
|
||
})
|
||
.Select(g => new
|
||
{
|
||
g.Key.DayOfWeek,
|
||
g.Key.PairNumber,
|
||
g.Key.IsEven,
|
||
g.First().Discipline,
|
||
g.First().LectureHalls,
|
||
g.First().Campus,
|
||
g.First().Professors,
|
||
Groups = string.Join('\n', g.Select(x => x.Group)),
|
||
|
||
IsExclude = g.First().IsExcludedWeeks,
|
||
g.First().TypeOfOccupations,
|
||
g.First().Weeks
|
||
})
|
||
.ToList())
|
||
{
|
||
// День
|
||
worksheet.Cells[row, col++].Value =
|
||
$"{(int)dto.DayOfWeek} [{ruCulture.DateTimeFormat.GetAbbreviatedDayName(dto.DayOfWeek).ToUpper()}]";
|
||
|
||
// Пара
|
||
worksheet.Cells[row, col++].Value = dto.PairNumber + " п";
|
||
|
||
// Неделя
|
||
worksheet.Cells[row, col++].Value = $"[{(dto.IsEven ? 2 : 1)}] {(dto.IsEven ? "Четная" : "Нечетная")}";
|
||
|
||
// Время
|
||
worksheet.Cells[row, col++].Value = pairsDictionary[dto.PairNumber].Start.ToString(ruCulture);
|
||
|
||
// Группа
|
||
worksheet.Cells[row, col].Style.WrapText = true;
|
||
worksheet.Cells[row, col++].Value = dto.Groups;
|
||
|
||
var groupTemplate = dto.Groups.Split('\n')[0];
|
||
|
||
// Институт
|
||
worksheet.Cells[row, col++].Value = GetFaculty(groupTemplate[0]);
|
||
// Курс
|
||
worksheet.Cells[row, col++].Value = groupTemplate[2] == 'М' ?
|
||
'М' :
|
||
(24 - int.Parse(groupTemplate.Split(' ')[0].Split('-').TakeLast(1).ElementAt(0)) + 1).ToString();
|
||
|
||
var disciplineAdditional = string.Empty;
|
||
|
||
if (dto.IsExclude.HasValue && dto.Weeks != null && dto.Weeks.Any())
|
||
disciplineAdditional += $"{(dto.IsExclude.Value ? "Кр. " : "")}{string.Join(", ", dto.Weeks.OrderBy(x => x))} н. ";
|
||
|
||
// Дисциплина
|
||
worksheet.Cells[row, col++].Value = disciplineAdditional + dto.Discipline;
|
||
|
||
// Преподаватель
|
||
worksheet.Cells[row, col++].Value = dto.Professors;
|
||
// Вид
|
||
worksheet.Cells[row, col++].Value = dto.TypeOfOccupations.FirstOrDefault();
|
||
// Кампус
|
||
worksheet.Cells[row, col++].Value = dto.Campus.FirstOrDefault()?.Replace("С-20", "С20").Replace("В-78", "В78");
|
||
// Ауд.
|
||
worksheet.Cells[row, col].Value = dto.LectureHalls;
|
||
|
||
col = 1;
|
||
row++;
|
||
}
|
||
|
||
worksheet.Cells[1, 1, 1, 12].AutoFilter = true;
|
||
worksheet.Cells[worksheet.Dimension.Address].AutoFitColumns();
|
||
|
||
var stream = new MemoryStream();
|
||
await package.SaveAsAsync(stream);
|
||
stream.Position = 0;
|
||
return File(stream, "application/vnd.ms-excel", "data.xlsx");
|
||
}
|
||
} |