improvement: 메시지 발송 상태 집계 규칙 고정 (#178) #228
|
|
@ -32,7 +32,7 @@ public class MessageController : ControllerBase
|
||||||
}
|
}
|
||||||
|
|
||||||
[HttpPost("list")]
|
[HttpPost("list")]
|
||||||
[SwaggerOperation(Summary = "메시지 목록 조회", Description = "메시지 목록을 페이지 단위로 조회합니다. X-Service-Code 헤더가 있으면 해당 서비스만, 없으면 전체 서비스 메시지를 반환합니다. send_status 필터(complete/pending/failed)를 지원합니다.")]
|
[SwaggerOperation(Summary = "메시지 목록 조회", Description = "메시지 목록을 페이지 단위로 조회합니다. X-Service-Code 헤더가 있으면 해당 서비스만, 없으면 전체 서비스 메시지를 반환합니다. send_status 필터(complete/pending/failed)를 지원합니다. 발송 상태는 통일된 SendStatus 규칙(pending=미발송, complete=1건 이상 성공, failed=전건 실패)으로 판정됩니다.")]
|
||||||
public async Task<IActionResult> GetListAsync([FromBody] MessageListRequestDto request)
|
public async Task<IActionResult> GetListAsync([FromBody] MessageListRequestDto request)
|
||||||
{
|
{
|
||||||
var serviceId = GetServiceIdOrNull();
|
var serviceId = GetServiceIdOrNull();
|
||||||
|
|
@ -41,7 +41,7 @@ public class MessageController : ControllerBase
|
||||||
}
|
}
|
||||||
|
|
||||||
[HttpPost("info")]
|
[HttpPost("info")]
|
||||||
[SwaggerOperation(Summary = "메시지 상세 조회", Description = "메시지 코드로 상세 정보를 조회합니다. 서비스 정보(service_name, service_code), 작성자(created_by_name), 발송 상태(latest_send_status), 템플릿 변수 목록을 포함합니다.")]
|
[SwaggerOperation(Summary = "메시지 상세 조회", Description = "메시지 코드로 상세 정보를 조회합니다. 서비스 정보(service_name, service_code), 작성자(created_by_name), 발송 상태(latest_send_status), 템플릿 변수 목록을 포함합니다. 발송 상태는 통일된 SendStatus 규칙(pending=미발송, complete=1건 이상 성공, failed=전건 실패)으로 판정됩니다.")]
|
||||||
public async Task<IActionResult> GetInfoAsync([FromBody] MessageInfoRequestDto request)
|
public async Task<IActionResult> GetInfoAsync([FromBody] MessageInfoRequestDto request)
|
||||||
{
|
{
|
||||||
var serviceId = GetServiceId();
|
var serviceId = GetServiceId();
|
||||||
|
|
|
||||||
|
|
@ -4,6 +4,7 @@ using SPMS.Application.DTOs.Message;
|
||||||
using SPMS.Application.DTOs.Notice;
|
using SPMS.Application.DTOs.Notice;
|
||||||
using SPMS.Application.Interfaces;
|
using SPMS.Application.Interfaces;
|
||||||
using SPMS.Domain.Common;
|
using SPMS.Domain.Common;
|
||||||
|
using SPMS.Domain.Enums;
|
||||||
using SPMS.Domain.Exceptions;
|
using SPMS.Domain.Exceptions;
|
||||||
using SPMS.Domain.Interfaces;
|
using SPMS.Domain.Interfaces;
|
||||||
|
|
||||||
|
|
@ -84,7 +85,7 @@ public class MessageService : IMessageService
|
||||||
CreatedAt = p.CreatedAt,
|
CreatedAt = p.CreatedAt,
|
||||||
ServiceName = p.ServiceName,
|
ServiceName = p.ServiceName,
|
||||||
ServiceCode = p.ServiceCode,
|
ServiceCode = p.ServiceCode,
|
||||||
LatestSendStatus = DetermineSendStatus(p.TotalSendCount, p.SuccessCount)
|
LatestSendStatus = SendStatus.Determine(p.TotalSendCount, p.SuccessCount)
|
||||||
}).ToList(),
|
}).ToList(),
|
||||||
Pagination = new PaginationDto
|
Pagination = new PaginationDto
|
||||||
{
|
{
|
||||||
|
|
@ -96,12 +97,6 @@ public class MessageService : IMessageService
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
private static string DetermineSendStatus(int totalSend, int successCount)
|
|
||||||
{
|
|
||||||
if (totalSend == 0) return "pending";
|
|
||||||
return successCount > 0 ? "complete" : "failed";
|
|
||||||
}
|
|
||||||
|
|
||||||
public async Task<MessageInfoResponseDto> GetInfoAsync(long serviceId, MessageInfoRequestDto request)
|
public async Task<MessageInfoResponseDto> GetInfoAsync(long serviceId, MessageInfoRequestDto request)
|
||||||
{
|
{
|
||||||
if (string.IsNullOrWhiteSpace(request.MessageCode))
|
if (string.IsNullOrWhiteSpace(request.MessageCode))
|
||||||
|
|
@ -135,7 +130,7 @@ public class MessageService : IMessageService
|
||||||
ServiceName = message.Service.ServiceName,
|
ServiceName = message.Service.ServiceName,
|
||||||
ServiceCode = message.Service.ServiceCode,
|
ServiceCode = message.Service.ServiceCode,
|
||||||
CreatedByName = message.CreatedByAdmin.Name,
|
CreatedByName = message.CreatedByAdmin.Name,
|
||||||
LatestSendStatus = DetermineSendStatus(totalSend, successCount),
|
LatestSendStatus = SendStatus.Determine(totalSend, successCount),
|
||||||
CreatedAt = message.CreatedAt
|
CreatedAt = message.CreatedAt
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
|
||||||
18
SPMS.Domain/Enums/SendStatus.cs
Normal file
18
SPMS.Domain/Enums/SendStatus.cs
Normal file
|
|
@ -0,0 +1,18 @@
|
||||||
|
namespace SPMS.Domain.Enums;
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// 메시지 발송 상태 판정 규칙 (PRD FR-MSG-006)
|
||||||
|
/// 목록/상세/통계 API에서 동일 규칙을 적용해야 함
|
||||||
|
/// </summary>
|
||||||
|
public static class SendStatus
|
||||||
|
{
|
||||||
|
public const string Pending = "pending";
|
||||||
|
public const string Complete = "complete";
|
||||||
|
public const string Failed = "failed";
|
||||||
|
|
||||||
|
public static string Determine(int totalSendCount, int successCount)
|
||||||
|
{
|
||||||
|
if (totalSendCount == 0) return Pending;
|
||||||
|
return successCount > 0 ? Complete : Failed;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
@ -104,12 +104,12 @@ public class MessageRepository : Repository<Message>, IMessageRepository
|
||||||
SuccessCount = _context.PushSendLogs.Count(l => l.MessageId == m.Id && l.Status == PushResult.Success)
|
SuccessCount = _context.PushSendLogs.Count(l => l.MessageId == m.Id && l.Status == PushResult.Success)
|
||||||
});
|
});
|
||||||
|
|
||||||
// 발송 상태 필터
|
// 발송 상태 필터 (SendStatus 상수 사용 — PRD FR-MSG-006)
|
||||||
if (sendStatus == "complete")
|
if (sendStatus == SendStatus.Complete)
|
||||||
projected = projected.Where(p => p.SuccessCount > 0);
|
projected = projected.Where(p => p.SuccessCount > 0);
|
||||||
else if (sendStatus == "failed")
|
else if (sendStatus == SendStatus.Failed)
|
||||||
projected = projected.Where(p => p.TotalSendCount > 0 && p.SuccessCount == 0);
|
projected = projected.Where(p => p.TotalSendCount > 0 && p.SuccessCount == 0);
|
||||||
else if (sendStatus == "pending")
|
else if (sendStatus == SendStatus.Pending)
|
||||||
projected = projected.Where(p => p.TotalSendCount == 0);
|
projected = projected.Where(p => p.TotalSendCount == 0);
|
||||||
|
|
||||||
var totalCount = await projected.CountAsync();
|
var totalCount = await projected.CountAsync();
|
||||||
|
|
|
||||||
Loading…
Reference in New Issue
Block a user