Добавить фильтр по title в GET /api/request-types/lists #24

Merged
gorbenko.pavel merged 1 commits from feature/request-types-lists-title-filter into main 2026-09-28 06:37:48 +00:00
3 changed files with 22 additions and 5 deletions
@@ -20,10 +20,14 @@ public sealed class RequestTypeListsController(ListPartitionService service) : C
/// заявкам сразу во всех партициях (архив + текущая) любого типа, не нужно
/// запрашивать серию по каждому типу отдельно.
/// </summary>
/// <param name="title">
/// Необязательный фильтр по заголовку партиции (Title списка SharePoint),
/// без учёта регистра, по вхождению подстроки.
/// </param>
[HttpGet("lists")]
[ProducesResponseType(typeof(ApiResponse<IReadOnlyList<RequestTypeListSeriesDto>>), StatusCodes.Status200OK)]
public async Task<IActionResult> ListAll(CancellationToken ct) =>
(await service.ListAllAsync(ct)).ToActionResult();
public async Task<IActionResult> ListAll([FromQuery] string? title, CancellationToken ct) =>
(await service.ListAllAsync(title, ct)).ToActionResult();
/// <summary>Вся серия партиций одного типа заявок (архив + текущая), от первой к последней.</summary>
[HttpGet("{requestTypeId:int}/lists")]
@@ -78,7 +78,12 @@ public sealed class ListPartitionService(
/// адресов один раз, а не по одному запросу на тип. Типы без настроенного
/// списка SharePoint в ответ не попадают — искать там всё равно нечего.
/// </summary>
public async Task<Result<IReadOnlyList<RequestTypeListSeriesDto>>> ListAllAsync(CancellationToken cancellationToken)
/// <param name="title">
/// Необязательный фильтр по заголовку партиции (Title списка SharePoint),
/// без учёта регистра, по вхождению подстроки. null — фильтр не применяется.
/// </param>
public async Task<Result<IReadOnlyList<RequestTypeListSeriesDto>>> ListAllAsync(
string? title, CancellationToken cancellationToken)
{
var requestTypes = await db.RequestTypes
.Where(x => x.ListId != null && x.SiteUrl != null)
@@ -88,6 +93,14 @@ public sealed class ListPartitionService(
foreach (var requestType in requestTypes)
{
var partitions = await BuildSeriesAsync(requestType, cancellationToken);
if (!string.IsNullOrWhiteSpace(title))
partitions = partitions
.Where(x => x.Title is not null && x.Title.Contains(title, StringComparison.OrdinalIgnoreCase))
.ToList();
if (partitions.Count == 0) continue;
result.Add(new RequestTypeListSeriesDto(requestType.Id, partitions));
}
@@ -72,8 +72,8 @@ export class ApprovalRouteApi {
// ListPartitionService.ListAllAsync) — для дашборда (счётчик партиций) и
// портала, которому нужен весь список адресов разом, а не по одному запросу
// на тип.
listsAll: (): Promise<RequestTypeListSeries[]> =>
this.http.get<RequestTypeListSeries[]>('/api/request-types/lists'),
listsAll: (title?: string): Promise<RequestTypeListSeries[]> =>
this.http.get<RequestTypeListSeries[]>('/api/request-types/lists', { title }),
// Вся серия партиций ОДНОГО типа заявки (архив + текущая) — нужна экрану
// редактирования заявок: заявка может лежать в любой из них, не только в