diff --git a/src/Oms.Application/Dtos/Finance/ReceivablePayablePaginatedInput.cs b/src/Oms.Application/Dtos/Finance/ReceivablePayablePaginatedInput.cs new file mode 100644 index 0000000..bb51370 --- /dev/null +++ b/src/Oms.Application/Dtos/Finance/ReceivablePayablePaginatedInput.cs @@ -0,0 +1,43 @@ +namespace Oms.Application.Dtos.Finance; + +/// +/// 应收应付分页查询入参。 +/// +public class ReceivablePayablePaginatedInput +{ + public int Page { get; set; } = 1; + + public int PageSize { get; set; } = 20; + + /// + /// 运单号 / 客户单号 / 跟踪号关键词。 + /// + public string? Keyword { get; set; } + + /// + /// 费用类型:receivable / payable,空或 all 表示全部。 + /// + public string? FeeType { get; set; } + + /// + /// 费用项关键词。 + /// + public string? CostItem { get; set; } + + /// + /// 计费阶段:forecast / inbound / outbound。 + /// + public string? ChargingStage { get; set; } + + public int? CustomerId { get; set; } + + /// + /// 订单创建时间起。 + /// + public DateTime? StartTime { get; set; } + + /// + /// 订单创建时间止。 + /// + public DateTime? EndTime { get; set; } +} diff --git a/src/Oms.Application/Dtos/Finance/ReceivablePayablePaginatedOutput.cs b/src/Oms.Application/Dtos/Finance/ReceivablePayablePaginatedOutput.cs new file mode 100644 index 0000000..fa832c3 --- /dev/null +++ b/src/Oms.Application/Dtos/Finance/ReceivablePayablePaginatedOutput.cs @@ -0,0 +1,53 @@ +namespace Oms.Application.Dtos.Finance; + +/// +/// 应收应付分页出参(不含主键与审计字段)。 +/// +public class ReceivablePayablePaginatedOutput +{ + public string ServiceNo { get; set; } = string.Empty; + + public string? ClientNo { get; set; } + + public string? TrackNo { get; set; } + + public string? CustomerCode { get; set; } + + public string OrderStatus { get; set; } = string.Empty; + + public string? OrderStatusName { get; set; } + + public byte IsPaid { get; set; } + + public DateTime? PayTime { get; set; } + + public DateTime? ReceiveTime { get; set; } + + public DateTime? ShipTime { get; set; } + + public string? ProductCode { get; set; } + + public string? ChannelCode { get; set; } + + public string? ConsigneeCountryName { get; set; } + + public string FeeType { get; set; } = string.Empty; + + public string? FeeTypeName { get; set; } + + public string CostItem { get; set; } = string.Empty; + + public decimal Amount { get; set; } + + public string Currency { get; set; } = string.Empty; + + public string? DownstreamProvider { get; set; } + + public string? PriceNo { get; set; } + + public DateTime? PriceEffectiveTime { get; set; } + + public string? ChargingStage { get; set; } + + public string? ChargingStageName { get; set; } +} diff --git a/src/Oms.Application/Services/Channels/AutoTriggerService.cs b/src/Oms.Application/Services/Channels/AutoTriggerService.cs index 7d7c359..c7914aa 100644 --- a/src/Oms.Application/Services/Channels/AutoTriggerService.cs +++ b/src/Oms.Application/Services/Channels/AutoTriggerService.cs @@ -22,12 +22,6 @@ public class AutoTriggerService : ApplicationService /// /// 入参:自动触发规则列表查询条件。 /// 自动触发规则分页结果,包含列表数据和总记录数。 - /// - /// 核心业务逻辑: - /// 1. 根据查询条件构造筛选规则。 - /// 2. 查询目标数据并补齐关联展示字段。 - /// 3. 按接口约定返回列表结果。 - /// [HttpGet("/channel/auto-trigger/list")] public async Task> GetListAsync([FromQuery] AutoTriggerListInput input) { @@ -49,12 +43,6 @@ public class AutoTriggerService : ApplicationService /// /// 入参:自动触发规则保存参数。 /// 无返回体,仅完成新增自动触发规则。 - /// - /// 核心业务逻辑: - /// 1. 校验入参与关联对象、唯一性等前置条件。 - /// 2. 组装目标实体及相关明细数据。 - /// 3. 写入审计字段并持久化结果。 - /// [HttpPost("/channel/auto-trigger/create")] public async Task CreateAsync(AutoTriggerSaveInput input) { @@ -75,12 +63,6 @@ public class AutoTriggerService : ApplicationService /// /// 入参:自动触发规则保存参数。 /// 无返回体,仅完成更新自动触发规则。 - /// - /// 核心业务逻辑: - /// 1. 查询并校验目标对象。 - /// 2. 按入参更新主体数据和关联配置。 - /// 3. 写入更新审计字段并保存结果。 - /// [HttpPost("/channel/auto-trigger/update")] public async Task UpdateAsync(AutoTriggerSaveInput input) { @@ -99,12 +81,6 @@ public class AutoTriggerService : ApplicationService /// /// 入参:目标主键。 /// 无返回体,仅完成删除自动触发规则。 - /// - /// 核心业务逻辑: - /// 1. 查询并校验目标对象。 - /// 2. 执行软删除或删除关联明细。 - /// 3. 持久化删除结果。 - /// [HttpPost("/channel/auto-trigger/delete")] public async Task DeleteAsync(IdInput input) { @@ -117,12 +93,6 @@ public class AutoTriggerService : ApplicationService /// /// 入参:目标主键和状态值。 /// 无返回体,仅完成切换自动触发规则状态。 - /// - /// 核心业务逻辑: - /// 1. 查询并校验目标对象。 - /// 2. 更新启停状态。 - /// 3. 保存状态变更结果。 - /// [HttpPost("/channel/auto-trigger/toggleStatus")] public async Task ToggleStatusAsync(ToggleStatusInput input) { diff --git a/src/Oms.Application/Services/Channels/KpiAreaService.cs b/src/Oms.Application/Services/Channels/KpiAreaService.cs index f391563..8313e88 100644 --- a/src/Oms.Application/Services/Channels/KpiAreaService.cs +++ b/src/Oms.Application/Services/Channels/KpiAreaService.cs @@ -26,12 +26,6 @@ public class KpiAreaService : ApplicationService /// /// 入参:KPI分区列表查询条件。 /// KPI分区分页结果,包含列表数据和总记录数。 - /// - /// 核心业务逻辑: - /// 1. 根据查询条件构造筛选规则。 - /// 2. 查询目标数据并补齐关联展示字段。 - /// 3. 按接口约定返回列表结果。 - /// [HttpPost("/channel/kpi-area/list")] public async Task> GetListAsync(KpiAreaListInput input) { @@ -56,12 +50,6 @@ public class KpiAreaService : ApplicationService /// /// 入参:KPI分区保存参数。 /// 无返回体,仅完成新增KPI分区。 - /// - /// 核心业务逻辑: - /// 1. 校验入参与关联对象、唯一性等前置条件。 - /// 2. 组装目标实体及相关明细数据。 - /// 3. 写入审计字段并持久化结果。 - /// [HttpPost("/channel/kpi-area/create")] public async Task CreateAsync(KpiAreaSaveInput input) { @@ -81,12 +69,6 @@ public class KpiAreaService : ApplicationService /// /// 入参:KPI分区保存参数。 /// 无返回体,仅完成更新KPI分区。 - /// - /// 核心业务逻辑: - /// 1. 查询并校验目标对象。 - /// 2. 按入参更新主体数据和关联配置。 - /// 3. 写入更新审计字段并保存结果。 - /// [HttpPost("/channel/kpi-area/update")] public async Task UpdateAsync(KpiAreaSaveInput input) { @@ -104,12 +86,6 @@ public class KpiAreaService : ApplicationService /// /// 入参:目标主键。 /// 无返回体,仅完成删除KPI分区。 - /// - /// 核心业务逻辑: - /// 1. 查询并校验目标对象。 - /// 2. 执行软删除或删除关联明细。 - /// 3. 持久化删除结果。 - /// [HttpPost("/channel/kpi-area/delete")] public async Task DeleteAsync(IdInput input) { @@ -122,12 +98,6 @@ public class KpiAreaService : ApplicationService /// /// 入参:KPI分区明细列表查询条件。 /// KPI分区明细分页结果,包含列表数据和总记录数。 - /// - /// 核心业务逻辑: - /// 1. 根据查询条件构造筛选规则。 - /// 2. 查询目标数据并补齐关联展示字段。 - /// 3. 按接口约定返回列表结果。 - /// [HttpPost("/channel/kpi-area/info/list")] public async Task> GetInfoListAsync(KpiAreaInfoListInput input) { @@ -148,12 +118,6 @@ public class KpiAreaService : ApplicationService /// /// 入参:KPI分区明细保存参数。 /// 无返回体,仅完成新增KPI分区明细。 - /// - /// 核心业务逻辑: - /// 1. 校验入参与关联对象、唯一性等前置条件。 - /// 2. 组装目标实体及相关明细数据。 - /// 3. 写入审计字段并持久化结果。 - /// [HttpPost("/channel/kpi-area/info/add")] public async Task AddInfoAsync(KpiAreaInfoSaveInput input) { @@ -175,12 +139,6 @@ public class KpiAreaService : ApplicationService /// /// 入参:KPI分区明细保存参数。 /// 无返回体,仅完成更新KPI分区明细。 - /// - /// 核心业务逻辑: - /// 1. 查询并校验目标对象。 - /// 2. 按入参更新主体数据和关联配置。 - /// 3. 写入更新审计字段并保存结果。 - /// [HttpPost("/channel/kpi-area/info/update")] public async Task UpdateInfoAsync(KpiAreaInfoSaveInput input) { @@ -201,12 +159,6 @@ public class KpiAreaService : ApplicationService /// /// 入参:目标主键。 /// 无返回体,仅完成删除KPI分区明细。 - /// - /// 核心业务逻辑: - /// 1. 查询并校验目标对象。 - /// 2. 执行软删除或删除关联明细。 - /// 3. 持久化删除结果。 - /// [HttpPost("/channel/kpi-area/info/delete")] public async Task DeleteInfoAsync(IdInput input) { diff --git a/src/Oms.Application/Services/Channels/LabelTemplateService.cs b/src/Oms.Application/Services/Channels/LabelTemplateService.cs index 71250b7..43995b5 100644 --- a/src/Oms.Application/Services/Channels/LabelTemplateService.cs +++ b/src/Oms.Application/Services/Channels/LabelTemplateService.cs @@ -20,12 +20,6 @@ public class LabelTemplateService : ApplicationService /// /// 入参:标签模板保存参数。 /// 标签模板保存结果。 - /// - /// 核心业务逻辑: - /// 1. 查询并校验目标对象。 - /// 2. 按入参更新主体数据和关联配置。 - /// 3. 写入更新审计字段并保存结果。 - /// [HttpPost("/channel/label-template/save")] public async Task SaveAsync(LabelTemplateSaveInput input) { diff --git a/src/Oms.Application/Services/Channels/SalesProductService.cs b/src/Oms.Application/Services/Channels/SalesProductService.cs index eb75bac..ec96d94 100644 --- a/src/Oms.Application/Services/Channels/SalesProductService.cs +++ b/src/Oms.Application/Services/Channels/SalesProductService.cs @@ -33,12 +33,6 @@ public partial class SalesProductService : ApplicationService /// /// 入参:销售产品列表查询条件。 /// 销售产品分页结果,包含列表数据和总记录数。 - /// - /// 核心业务逻辑: - /// 1. 根据查询条件构造筛选规则。 - /// 2. 查询目标数据并补齐关联展示字段。 - /// 3. 按接口约定返回列表结果。 - /// [HttpGet("/channel/sales-product/list")] public async Task> GetListAsync([FromQuery] SalesProductListInput input) { @@ -63,12 +57,6 @@ public partial class SalesProductService : ApplicationService /// /// 入参:目标主键。 /// 销售产品详情。 - /// - /// 核心业务逻辑: - /// 1. 根据标识查询目标对象。 - /// 2. 目标不存在时抛出业务异常。 - /// 3. 映射并返回详情结果。 - /// [HttpGet("/channel/sales-product/detail")] public async Task GetDetailAsync([FromQuery] int id) { @@ -83,12 +71,6 @@ public partial class SalesProductService : ApplicationService /// /// 入参:销售产品保存参数。 /// 无返回体,仅完成新增销售产品。 - /// - /// 核心业务逻辑: - /// 1. 校验入参与关联对象、唯一性等前置条件。 - /// 2. 组装目标实体及相关明细数据。 - /// 3. 写入审计字段并持久化结果。 - /// [HttpPost("/channel/sales-product/create")] public async Task CreateAsync(SalesProductSaveInput input) { @@ -103,12 +85,6 @@ public partial class SalesProductService : ApplicationService /// /// 入参:销售产品保存参数。 /// 无返回体,仅完成更新销售产品。 - /// - /// 核心业务逻辑: - /// 1. 查询并校验目标对象。 - /// 2. 按入参更新主体数据和关联配置。 - /// 3. 写入更新审计字段并保存结果。 - /// [HttpPost("/channel/sales-product/update")] public async Task UpdateAsync(SalesProductSaveInput input) { @@ -123,12 +99,6 @@ public partial class SalesProductService : ApplicationService /// /// 入参:目标主键。 /// 无返回体,仅完成删除销售产品。 - /// - /// 核心业务逻辑: - /// 1. 查询并校验目标对象。 - /// 2. 执行软删除或删除关联明细。 - /// 3. 持久化删除结果。 - /// [HttpPost("/channel/sales-product/delete")] public async Task DeleteAsync(IdInput input) { @@ -141,12 +111,6 @@ public partial class SalesProductService : ApplicationService /// /// 入参:销售产品保存参数。 /// 无返回体,仅完成保存销售产品配置。 - /// - /// 核心业务逻辑: - /// 1. 查询并校验目标对象。 - /// 2. 按入参更新主体数据和关联配置。 - /// 3. 写入更新审计字段并保存结果。 - /// [ApiExplorerSettings(IgnoreApi = true)] [HttpPost("/channel/sales-product/config/save")] public async Task SaveConfigAsync(SalesProductSaveInput input) @@ -162,12 +126,6 @@ public partial class SalesProductService : ApplicationService /// /// 入参:销售产品主键。 /// 销售产品价格项列表结果。 - /// - /// 核心业务逻辑: - /// 1. 根据查询条件构造筛选规则。 - /// 2. 查询目标数据并补齐关联展示字段。 - /// 3. 按接口约定返回列表结果。 - /// [HttpGet("/channel/sales-product/price/list")] public async Task> GetPriceListAsync([FromQuery] int salesProductId) { @@ -183,12 +141,6 @@ public partial class SalesProductService : ApplicationService /// /// 入参:销售产品价格项保存参数。 /// 无返回体,仅完成新增销售产品价格项。 - /// - /// 核心业务逻辑: - /// 1. 校验入参与关联对象、唯一性等前置条件。 - /// 2. 组装目标实体及相关明细数据。 - /// 3. 写入审计字段并持久化结果。 - /// [HttpPost("/channel/sales-product/price/create")] public async Task CreatePriceAsync(SalesProductPriceSaveInput input) { @@ -214,12 +166,6 @@ public partial class SalesProductService : ApplicationService /// /// 入参:销售产品价格项保存参数。 /// 无返回体,仅完成更新销售产品价格项。 - /// - /// 核心业务逻辑: - /// 1. 查询并校验目标对象。 - /// 2. 按入参更新主体数据和关联配置。 - /// 3. 写入更新审计字段并保存结果。 - /// [HttpPost("/channel/sales-product/price/update")] public async Task UpdatePriceAsync(SalesProductPriceSaveInput input) { @@ -247,12 +193,6 @@ public partial class SalesProductService : ApplicationService /// /// 入参:目标主键。 /// 无返回体,仅完成删除销售产品价格项。 - /// - /// 核心业务逻辑: - /// 1. 查询并校验目标对象。 - /// 2. 执行软删除或删除关联明细。 - /// 3. 持久化删除结果。 - /// [HttpPost("/channel/sales-product/price/delete")] public async Task DeletePriceAsync(IdInput input) { @@ -265,12 +205,6 @@ public partial class SalesProductService : ApplicationService /// /// 入参:目标主键和状态值。 /// 无返回体,仅完成切换销售产品价格项状态。 - /// - /// 核心业务逻辑: - /// 1. 查询并校验目标对象。 - /// 2. 更新启停状态。 - /// 3. 保存状态变更结果。 - /// [HttpPost("/channel/sales-product/price/toggleStatus")] public async Task TogglePriceStatusAsync(ToggleStatusInput input) { @@ -283,12 +217,6 @@ public partial class SalesProductService : ApplicationService /// /// 入参:销售产品价格项批量保存参数。 /// 无返回体,仅完成批量保存销售产品价格项。 - /// - /// 核心业务逻辑: - /// 1. 查询并校验目标对象。 - /// 2. 按入参更新主体数据和关联配置。 - /// 3. 写入更新审计字段并保存结果。 - /// [HttpPost("/channel/sales-product/price/save")] public async Task SavePriceAsync(SalesProductPriceSaveAllInput input) { @@ -330,12 +258,6 @@ public partial class SalesProductService : ApplicationService /// /// 入参:销售产品主键。 /// 销售产品分配配置。 - /// - /// 核心业务逻辑: - /// 1. 根据标识查询目标对象。 - /// 2. 目标不存在时抛出业务异常。 - /// 3. 映射并返回详情结果。 - /// [HttpGet("/channel/sales-product/allocation/get")] public Task GetAllocationAsync([FromQuery] int salesProductId) { @@ -347,12 +269,6 @@ public partial class SalesProductService : ApplicationService /// /// 入参:销售产品分配配置保存参数。 /// 无返回体,仅完成保存销售产品分配配置。 - /// - /// 核心业务逻辑: - /// 1. 查询并校验目标对象。 - /// 2. 按入参更新主体数据和关联配置。 - /// 3. 写入更新审计字段并保存结果。 - /// [HttpPost("/channel/sales-product/allocation/save")] public async Task SaveAllocationAsync(SalesProductAllocationSaveInput input) { @@ -382,12 +298,6 @@ public partial class SalesProductService : ApplicationService /// /// 入参:销售产品发布列表查询条件。 /// 销售产品发布价格分页结果,包含列表数据和总记录数。 - /// - /// 核心业务逻辑: - /// 1. 根据查询条件构造筛选规则。 - /// 2. 查询目标数据并补齐关联展示字段。 - /// 3. 按接口约定返回列表结果。 - /// [HttpGet("/channel/sales-product/publish/price/list")] public Task> GetPricePublishListAsync([FromQuery] SalesProductPublishListInput input) { @@ -399,12 +309,6 @@ public partial class SalesProductService : ApplicationService /// /// 入参:销售产品发布列表查询条件。 /// 销售产品发布规则分页结果,包含列表数据和总记录数。 - /// - /// 核心业务逻辑: - /// 1. 根据查询条件构造筛选规则。 - /// 2. 查询目标数据并补齐关联展示字段。 - /// 3. 按接口约定返回列表结果。 - /// [HttpGet("/channel/sales-product/publish/rules/list")] public Task> GetRulesPublishListAsync([FromQuery] SalesProductPublishListInput input) { @@ -428,12 +332,6 @@ public partial class SalesProductService : ApplicationService /// /// 入参:销售产品发布参数。 /// 无返回体,仅完成销售产品发布处理。 - /// - /// 核心业务逻辑: - /// 1. 校验目标对象和发布前提条件。 - /// 2. 生成、切换或回退发布版本数据。 - /// 3. 保存发布结果并返回处理信息。 - /// [HttpPost("/channel/sales-product/publish")] public async Task PublishAsync(SalesProductPublishInput input) { @@ -445,12 +343,6 @@ public partial class SalesProductService : ApplicationService /// /// 入参:销售产品发布回滚参数。 /// 无返回体,仅完成回滚销售产品发布版本。 - /// - /// 核心业务逻辑: - /// 1. 校验目标对象和发布前提条件。 - /// 2. 生成、切换或回退发布版本数据。 - /// 3. 保存发布结果并返回处理信息。 - /// [HttpPost("/channel/sales-product/publish/rollback")] public Task RollbackAsync(SalesProductRollbackInput input) { diff --git a/src/Oms.Application/Services/Channels/ServiceChannelService.cs b/src/Oms.Application/Services/Channels/ServiceChannelService.cs index 6fe41cd..9609f8b 100644 --- a/src/Oms.Application/Services/Channels/ServiceChannelService.cs +++ b/src/Oms.Application/Services/Channels/ServiceChannelService.cs @@ -28,12 +28,6 @@ public partial class ServiceChannelService : ApplicationService /// /// 入参:服务渠道列表查询条件。 /// 服务渠道分页结果,包含列表数据和总记录数。 - /// - /// 核心业务逻辑: - /// 1. 根据查询条件构造筛选规则。 - /// 2. 查询目标数据并补齐关联展示字段。 - /// 3. 按接口约定返回列表结果。 - /// [HttpGet("/channel/service-channel/list")] public async Task> GetListAsync([FromQuery] ServiceChannelListInput input) { @@ -59,12 +53,6 @@ public partial class ServiceChannelService : ApplicationService /// /// 入参:目标主键。 /// 服务渠道详情。 - /// - /// 核心业务逻辑: - /// 1. 根据标识查询目标对象。 - /// 2. 目标不存在时抛出业务异常。 - /// 3. 映射并返回详情结果。 - /// [HttpGet("/channel/service-channel/detail")] public async Task GetDetailAsync([FromQuery] int id) { @@ -79,12 +67,6 @@ public partial class ServiceChannelService : ApplicationService /// /// 入参:服务渠道保存参数。 /// 无返回体,仅完成新增服务渠道。 - /// - /// 核心业务逻辑: - /// 1. 校验入参与关联对象、唯一性等前置条件。 - /// 2. 组装目标实体及相关明细数据。 - /// 3. 写入审计字段并持久化结果。 - /// [HttpPost("/channel/service-channel/create")] public async Task CreateAsync(ServiceChannelSaveInput input) { @@ -99,12 +81,6 @@ public partial class ServiceChannelService : ApplicationService /// /// 入参:服务渠道保存参数。 /// 无返回体,仅完成更新服务渠道。 - /// - /// 核心业务逻辑: - /// 1. 查询并校验目标对象。 - /// 2. 按入参更新主体数据和关联配置。 - /// 3. 写入更新审计字段并保存结果。 - /// [HttpPost("/channel/service-channel/update")] public async Task UpdateAsync(ServiceChannelSaveInput input) { @@ -119,12 +95,6 @@ public partial class ServiceChannelService : ApplicationService /// /// 入参:目标主键。 /// 无返回体,仅完成删除服务渠道。 - /// - /// 核心业务逻辑: - /// 1. 查询并校验目标对象。 - /// 2. 执行软删除或删除关联明细。 - /// 3. 持久化删除结果。 - /// [HttpPost("/channel/service-channel/delete")] public async Task DeleteAsync(IdInput input) { @@ -137,12 +107,6 @@ public partial class ServiceChannelService : ApplicationService /// /// 入参:分组名称、应用 ID、API 服务商 ID 等筛选条件。 /// 服务渠道分组列表,供下拉与左侧树筛选使用。 - /// - /// 核心业务逻辑: - /// 1. 按 keyword、appId、apiServiceProviderId 构造筛选条件。 - /// 2. 查询未删除分组并按 id 倒序返回。 - /// 3. 无数据时返回空数组。 - /// [HttpGet("/channel/service-channel/group/list")] public async Task> GetGroupListAsync([FromQuery] ServiceChannelGroupListInput input) { @@ -158,12 +122,6 @@ public partial class ServiceChannelService : ApplicationService /// /// 入参:服务渠道分组保存参数。 /// 无返回体,仅完成新增服务渠道分组。 - /// - /// 核心业务逻辑: - /// 1. 校验分组名称、应用ID、API服务商ID等基础字段。 - /// 2. 检查分组名称唯一性,避免重复配置。 - /// 3. 保存分组主数据供服务渠道绑定。 - /// [HttpPost("/channel/service-channel/group/create")] public async Task CreateGroupAsync(ServiceChannelGroupSaveInput input) { @@ -181,12 +139,6 @@ public partial class ServiceChannelService : ApplicationService /// /// 入参:服务渠道分组保存参数。 /// 无返回体,仅完成更新服务渠道分组。 - /// - /// 核心业务逻辑: - /// 1. 查询并校验目标分组是否存在。 - /// 2. 检查名称唯一性并更新分组主数据。 - /// 3. 保留既有渠道关联,只更新分组属性。 - /// [HttpPost("/channel/service-channel/group/update")] public async Task UpdateGroupAsync(ServiceChannelGroupSaveInput input) { @@ -203,12 +155,6 @@ public partial class ServiceChannelService : ApplicationService /// /// 入参:目标分组主键。 /// 无返回体,仅完成删除服务渠道分组。 - /// - /// 核心业务逻辑: - /// 1. 查询并校验目标分组是否存在。 - /// 2. 检查分组下是否仍有关联渠道。 - /// 3. 无关联时执行删除,保留框架软删语义。 - /// [HttpPost("/channel/service-channel/group/delete")] public async Task DeleteGroupAsync(IdInput input) { @@ -226,12 +172,6 @@ public partial class ServiceChannelService : ApplicationService /// /// 入参:服务渠道保存参数。 /// 无返回体,仅完成保存服务渠道配置。 - /// - /// 核心业务逻辑: - /// 1. 查询并校验目标对象。 - /// 2. 按入参更新主体数据和关联配置。 - /// 3. 写入更新审计字段并保存结果。 - /// [ApiExplorerSettings(IgnoreApi = true)] [HttpPost("/channel/service-channel/config/save")] public async Task SaveConfigAsync(ServiceChannelSaveInput input) @@ -247,12 +187,6 @@ public partial class ServiceChannelService : ApplicationService /// /// 入参:serviceChannelId。 /// 服务渠道价格项列表结果。 - /// - /// 核心业务逻辑: - /// 1. 根据查询条件构造筛选规则。 - /// 2. 查询目标数据并补齐关联展示字段。 - /// 3. 按接口约定返回列表结果。 - /// [HttpGet("/channel/service-channel/price/list")] public async Task> GetPriceListAsync([FromQuery] int serviceChannelId) { @@ -268,12 +202,6 @@ public partial class ServiceChannelService : ApplicationService /// /// 入参:服务渠道价格项保存参数。 /// 无返回体,仅完成新增服务渠道价格项。 - /// - /// 核心业务逻辑: - /// 1. 校验入参与关联对象、唯一性等前置条件。 - /// 2. 组装目标实体及相关明细数据。 - /// 3. 写入审计字段并持久化结果。 - /// [HttpPost("/channel/service-channel/price/create")] public async Task CreatePriceAsync(ServiceChannelPriceSaveInput input) { @@ -299,12 +227,6 @@ public partial class ServiceChannelService : ApplicationService /// /// 入参:服务渠道价格项保存参数。 /// 无返回体,仅完成更新服务渠道价格项。 - /// - /// 核心业务逻辑: - /// 1. 查询并校验目标对象。 - /// 2. 按入参更新主体数据和关联配置。 - /// 3. 写入更新审计字段并保存结果。 - /// [HttpPost("/channel/service-channel/price/update")] public async Task UpdatePriceAsync(ServiceChannelPriceSaveInput input) { @@ -332,12 +254,6 @@ public partial class ServiceChannelService : ApplicationService /// /// 入参:目标主键。 /// 无返回体,仅完成删除服务渠道价格项。 - /// - /// 核心业务逻辑: - /// 1. 查询并校验目标对象。 - /// 2. 执行软删除或删除关联明细。 - /// 3. 持久化删除结果。 - /// [HttpPost("/channel/service-channel/price/delete")] public async Task DeletePriceAsync(IdInput input) { @@ -350,12 +266,6 @@ public partial class ServiceChannelService : ApplicationService /// /// 入参:目标主键和状态值。 /// 无返回体,仅完成切换服务渠道价格项状态。 - /// - /// 核心业务逻辑: - /// 1. 查询并校验目标对象。 - /// 2. 更新启停状态。 - /// 3. 保存状态变更结果。 - /// [HttpPost("/channel/service-channel/price/toggleStatus")] public async Task TogglePriceStatusAsync(ToggleStatusInput input) { @@ -368,12 +278,6 @@ public partial class ServiceChannelService : ApplicationService /// /// 入参:服务渠道价格项批量保存参数。 /// 无返回体,仅完成批量保存服务渠道价格项。 - /// - /// 核心业务逻辑: - /// 1. 查询并校验目标对象。 - /// 2. 按入参更新主体数据和关联配置。 - /// 3. 写入更新审计字段并保存结果。 - /// [HttpPost("/channel/service-channel/price/save")] public async Task SavePriceAsync(ServiceChannelPriceSaveAllInput input) { @@ -415,12 +319,6 @@ public partial class ServiceChannelService : ApplicationService /// /// 入参:服务渠道发布列表查询条件。 /// 服务渠道发布价格分页结果,包含列表数据和总记录数。 - /// - /// 核心业务逻辑: - /// 1. 根据查询条件构造筛选规则。 - /// 2. 查询目标数据并补齐关联展示字段。 - /// 3. 按接口约定返回列表结果。 - /// [HttpGet("/channel/service-channel/publish/price/list")] public Task> GetPricePublishListAsync([FromQuery] ServiceChannelPublishListInput input) { @@ -444,12 +342,6 @@ public partial class ServiceChannelService : ApplicationService /// /// 入参:服务渠道发布列表查询条件。 /// 服务渠道发布规则分页结果,包含列表数据和总记录数。 - /// - /// 核心业务逻辑: - /// 1. 根据查询条件构造筛选规则。 - /// 2. 查询目标数据并补齐关联展示字段。 - /// 3. 按接口约定返回列表结果。 - /// [HttpGet("/channel/service-channel/publish/rules/list")] public Task> GetRulesPublishListAsync([FromQuery] ServiceChannelPublishListInput input) { @@ -461,12 +353,6 @@ public partial class ServiceChannelService : ApplicationService /// /// 入参:服务渠道发布参数。 /// 无返回体,仅完成服务渠道发布处理。 - /// - /// 核心业务逻辑: - /// 1. 校验目标对象和发布前提条件。 - /// 2. 生成、切换或回退发布版本数据。 - /// 3. 保存发布结果并返回处理信息。 - /// [HttpPost("/channel/service-channel/publish")] public async Task PublishAsync(ServiceChannelPublishInput input) { @@ -478,12 +364,6 @@ public partial class ServiceChannelService : ApplicationService /// /// 入参:服务渠道发布回滚参数。 /// 无返回体,仅完成回滚服务渠道发布版本。 - /// - /// 核心业务逻辑: - /// 1. 校验目标对象和发布前提条件。 - /// 2. 生成、切换或回退发布版本数据。 - /// 3. 保存发布结果并返回处理信息。 - /// [HttpPost("/channel/service-channel/publish/rollback")] public Task RollbackAsync(ServiceChannelRollbackInput input) { diff --git a/src/Oms.Application/Services/Channels/WeightRoundingService.cs b/src/Oms.Application/Services/Channels/WeightRoundingService.cs index 6adc81e..c919d5b 100644 --- a/src/Oms.Application/Services/Channels/WeightRoundingService.cs +++ b/src/Oms.Application/Services/Channels/WeightRoundingService.cs @@ -22,12 +22,6 @@ public class WeightRoundingService : ApplicationService /// /// 入参:计重进位规则列表查询条件。 /// 计重进位规则分页结果,包含列表数据和总记录数。 - /// - /// 核心业务逻辑: - /// 1. 根据查询条件构造筛选规则。 - /// 2. 查询目标数据并补齐关联展示字段。 - /// 3. 按接口约定返回列表结果。 - /// [HttpPost("/channel/weight-rounding/list")] public async Task> GetListAsync(WeightRoundingListInput input) { @@ -52,12 +46,6 @@ public class WeightRoundingService : ApplicationService /// /// 入参:计重进位规则保存参数。 /// 无返回体,仅完成新增计重进位规则。 - /// - /// 核心业务逻辑: - /// 1. 校验入参与关联对象、唯一性等前置条件。 - /// 2. 组装目标实体及相关明细数据。 - /// 3. 写入审计字段并持久化结果。 - /// [HttpPost("/channel/weight-rounding/create")] public async Task CreateAsync(WeightRoundingSaveInput input) { @@ -74,12 +62,6 @@ public class WeightRoundingService : ApplicationService /// /// 入参:计重进位规则保存参数。 /// 无返回体,仅完成更新计重进位规则。 - /// - /// 核心业务逻辑: - /// 1. 查询并校验目标对象。 - /// 2. 按入参更新主体数据和关联配置。 - /// 3. 写入更新审计字段并保存结果。 - /// [HttpPost("/channel/weight-rounding/update")] public async Task UpdateAsync(WeightRoundingSaveInput input) { @@ -95,12 +77,6 @@ public class WeightRoundingService : ApplicationService /// /// 入参:目标主键。 /// 无返回体,仅完成删除计重进位规则。 - /// - /// 核心业务逻辑: - /// 1. 查询并校验目标对象。 - /// 2. 执行软删除或删除关联明细。 - /// 3. 持久化删除结果。 - /// [HttpPost("/channel/weight-rounding/delete")] public async Task DeleteAsync(IdInput input) { @@ -113,12 +89,6 @@ public class WeightRoundingService : ApplicationService /// /// 入参:计重进位规则明细列表查询条件。 /// 计重进位规则明细分页结果,包含列表数据和总记录数。 - /// - /// 核心业务逻辑: - /// 1. 根据查询条件构造筛选规则。 - /// 2. 查询目标数据并补齐关联展示字段。 - /// 3. 按接口约定返回列表结果。 - /// [HttpPost("/channel/weight-rounding/info/list")] public async Task> GetInfoListAsync(WeightRoundingInfoListInput input) { @@ -139,12 +109,6 @@ public class WeightRoundingService : ApplicationService /// /// 入参:计重进位规则明细保存参数。 /// 无返回体,仅完成新增计重进位规则明细。 - /// - /// 核心业务逻辑: - /// 1. 校验入参与关联对象、唯一性等前置条件。 - /// 2. 组装目标实体及相关明细数据。 - /// 3. 写入审计字段并持久化结果。 - /// [HttpPost("/channel/weight-rounding/info/add")] public async Task AddInfoAsync(WeightRoundingInfoSaveInput input) { @@ -165,12 +129,6 @@ public class WeightRoundingService : ApplicationService /// /// 入参:计重进位规则明细保存参数。 /// 无返回体,仅完成更新计重进位规则明细。 - /// - /// 核心业务逻辑: - /// 1. 查询并校验目标对象。 - /// 2. 按入参更新主体数据和关联配置。 - /// 3. 写入更新审计字段并保存结果。 - /// [HttpPost("/channel/weight-rounding/info/update")] public async Task UpdateInfoAsync(WeightRoundingInfoSaveInput input) { @@ -190,12 +148,6 @@ public class WeightRoundingService : ApplicationService /// /// 入参:目标主键。 /// 无返回体,仅完成删除计重进位规则明细。 - /// - /// 核心业务逻辑: - /// 1. 查询并校验目标对象。 - /// 2. 执行软删除或删除关联明细。 - /// 3. 持久化删除结果。 - /// [HttpPost("/channel/weight-rounding/info/delete")] public async Task DeleteInfoAsync(IdInput input) { diff --git a/src/Oms.Application/Services/Channels/WeightRuleService.cs b/src/Oms.Application/Services/Channels/WeightRuleService.cs index cbe93f5..e60acbb 100644 --- a/src/Oms.Application/Services/Channels/WeightRuleService.cs +++ b/src/Oms.Application/Services/Channels/WeightRuleService.cs @@ -22,12 +22,6 @@ public class WeightRuleService : ApplicationService /// /// 入参:计重规则列表查询条件。 /// 计重规则分页结果,包含列表数据和总记录数。 - /// - /// 核心业务逻辑: - /// 1. 根据查询条件构造筛选规则。 - /// 2. 查询目标数据并补齐关联展示字段。 - /// 3. 按接口约定返回列表结果。 - /// [HttpPost("/channel/weight-rule/list")] public async Task> GetListAsync(WeightRuleListInput input) { @@ -52,12 +46,6 @@ public class WeightRuleService : ApplicationService /// /// 入参:计重规则保存参数。 /// 无返回体,仅完成新增计重规则。 - /// - /// 核心业务逻辑: - /// 1. 校验入参与关联对象、唯一性等前置条件。 - /// 2. 组装目标实体及相关明细数据。 - /// 3. 写入审计字段并持久化结果。 - /// [HttpPost("/channel/weight-rule/create")] public async Task CreateAsync(WeightRuleSaveInput input) { @@ -74,12 +62,6 @@ public class WeightRuleService : ApplicationService /// /// 入参:计重规则保存参数。 /// 无返回体,仅完成更新计重规则。 - /// - /// 核心业务逻辑: - /// 1. 查询并校验目标对象。 - /// 2. 按入参更新主体数据和关联配置。 - /// 3. 写入更新审计字段并保存结果。 - /// [HttpPost("/channel/weight-rule/update")] public async Task UpdateAsync(WeightRuleSaveInput input) { @@ -95,12 +77,6 @@ public class WeightRuleService : ApplicationService /// /// 入参:目标主键。 /// 无返回体,仅完成删除计重规则。 - /// - /// 核心业务逻辑: - /// 1. 查询并校验目标对象。 - /// 2. 执行软删除或删除关联明细。 - /// 3. 持久化删除结果。 - /// [HttpPost("/channel/weight-rule/delete")] public async Task DeleteAsync(IdInput input) { @@ -113,12 +89,6 @@ public class WeightRuleService : ApplicationService /// /// 入参:计重规则明细列表查询条件。 /// 计重规则明细分页结果,包含列表数据和总记录数。 - /// - /// 核心业务逻辑: - /// 1. 根据查询条件构造筛选规则。 - /// 2. 查询目标数据并补齐关联展示字段。 - /// 3. 按接口约定返回列表结果。 - /// [HttpPost("/channel/weight-rule/info/list")] public async Task> GetInfoListAsync(WeightRuleInfoListInput input) { @@ -139,12 +109,6 @@ public class WeightRuleService : ApplicationService /// /// 入参:计重规则明细保存参数。 /// 无返回体,仅完成新增计重规则明细。 - /// - /// 核心业务逻辑: - /// 1. 校验入参与关联对象、唯一性等前置条件。 - /// 2. 组装目标实体及相关明细数据。 - /// 3. 写入审计字段并持久化结果。 - /// [HttpPost("/channel/weight-rule/info/add")] public async Task AddInfoAsync(WeightRuleInfoSaveInput input) { @@ -164,12 +128,6 @@ public class WeightRuleService : ApplicationService /// /// 入参:计重规则明细保存参数。 /// 无返回体,仅完成更新计重规则明细。 - /// - /// 核心业务逻辑: - /// 1. 查询并校验目标对象。 - /// 2. 按入参更新主体数据和关联配置。 - /// 3. 写入更新审计字段并保存结果。 - /// [HttpPost("/channel/weight-rule/info/update")] public async Task UpdateInfoAsync(WeightRuleInfoSaveInput input) { @@ -188,12 +146,6 @@ public class WeightRuleService : ApplicationService /// /// 入参:目标主键。 /// 无返回体,仅完成删除计重规则明细。 - /// - /// 核心业务逻辑: - /// 1. 查询并校验目标对象。 - /// 2. 执行软删除或删除关联明细。 - /// 3. 持久化删除结果。 - /// [HttpPost("/channel/weight-rule/info/delete")] public async Task DeleteInfoAsync(IdInput input) { diff --git a/src/Oms.Application/Services/Customers/CustomerService.cs b/src/Oms.Application/Services/Customers/CustomerService.cs index 960df8d..4ca749a 100644 --- a/src/Oms.Application/Services/Customers/CustomerService.cs +++ b/src/Oms.Application/Services/Customers/CustomerService.cs @@ -40,12 +40,6 @@ public class CustomerService : ApplicationService /// /// 入参:客户分页查询条件。 /// 客户分页结果,包含列表数据和总记录数。 - /// - /// 核心业务逻辑: - /// 1. 根据查询条件构造筛选规则。 - /// 2. 查询目标数据并补齐关联展示字段。 - /// 3. 按接口约定返回列表结果。 - /// [HttpGet("/customer/list")] public async Task> GetPaginatedListAsync([FromQuery] CustomerPaginatedInput input) { @@ -83,12 +77,6 @@ public class CustomerService : ApplicationService /// /// 入参:目标主键。 /// 客户详情。 - /// - /// 核心业务逻辑: - /// 1. 根据标识查询目标对象。 - /// 2. 目标不存在时抛出业务异常。 - /// 3. 映射并返回详情结果。 - /// [HttpGet("/customer/get")] public async Task GetByIdAsync([FromQuery] int id) { @@ -107,12 +95,6 @@ public class CustomerService : ApplicationService /// /// 入参:客户创建参数。 /// 无返回体,仅完成新增客户。 - /// - /// 核心业务逻辑: - /// 1. 校验入参与关联对象、唯一性等前置条件。 - /// 2. 组装目标实体及相关明细数据。 - /// 3. 写入审计字段并持久化结果。 - /// [HttpPost("/customer/create")] public async Task CreateAsync(CreateCustomerInput input) { @@ -181,12 +163,6 @@ public class CustomerService : ApplicationService /// /// 入参:客户更新参数。 /// 无返回体,仅完成更新客户。 - /// - /// 核心业务逻辑: - /// 1. 查询并校验目标对象。 - /// 2. 按入参更新主体数据和关联配置。 - /// 3. 写入更新审计字段并保存结果。 - /// [HttpPost("/customer/update")] public async Task UpdateAsync(UpdateCustomerInput input) { @@ -221,12 +197,6 @@ public class CustomerService : ApplicationService /// /// 入参:目标主键。 /// 无返回体,仅完成删除客户。 - /// - /// 核心业务逻辑: - /// 1. 查询并校验目标对象。 - /// 2. 执行软删除或删除关联明细。 - /// 3. 持久化删除结果。 - /// [HttpPost("/customer/delete")] public async Task DeleteAsync(IdInput input) { @@ -239,12 +209,6 @@ public class CustomerService : ApplicationService /// /// 入参:客户密码重置参数。 /// 无返回体,仅完成重置客户密码。 - /// - /// 核心业务逻辑: - /// 1. 查询并校验目标对象及当前状态。 - /// 2. 执行业务状态流转或敏感字段更新。 - /// 3. 写入审计字段并保存结果。 - /// [HttpPost("/customer/reset-password")] public async Task ResetPasswordAsync(ResetCustomerPasswordInput input) { diff --git a/src/Oms.Application/Services/DataPerm/DataPermService.Template.cs b/src/Oms.Application/Services/DataPerm/DataPermService.Template.cs index 088af50..286e931 100644 --- a/src/Oms.Application/Services/DataPerm/DataPermService.Template.cs +++ b/src/Oms.Application/Services/DataPerm/DataPermService.Template.cs @@ -10,6 +10,9 @@ namespace Oms.Application.Services.DataPerm; public partial class DataPermService { + /// + /// 分页查询数据权限模板 + /// [HttpGet("/rbac/data-perm/template/list")] public Task> GetTemplateListAsync( [FromQuery] string? keyword, @@ -22,12 +25,18 @@ public partial class DataPermService OmsDocHelper.NormalizePageSize(pageSize), cancellationToken); + /// + /// 查询数据权限模板详情 + /// [HttpGet("/rbac/data-perm/template/get")] public Task GetTemplateDetailAsync( [FromQuery] string id, CancellationToken cancellationToken = default) => Store.GetTemplateDetailAsync(ParseGuid(id, "id"), cancellationToken); + /// + /// 创建数据权限模板 + /// [HttpPost("/rbac/data-perm/template/create")] public Task CreateTemplateAsync( [FromBody] DataPermTemplateSaveInput input, @@ -37,6 +46,9 @@ public partial class DataPermService return Store.CreateTemplateAsync(input, GetCurrentMapId(), cancellationToken); } + /// + /// 更新数据权限模板 + /// [HttpPut("/rbac/data-perm/template/update")] public Task UpdateTemplateAsync( [FromQuery] string id, @@ -47,10 +59,16 @@ public partial class DataPermService return Store.UpdateTemplateAsync(ParseGuid(id, "id"), input, GetCurrentMapId(), cancellationToken); } + /// + /// 删除数据权限模板 + /// [HttpDelete("/rbac/data-perm/template/delete")] public Task DeleteTemplateAsync([FromQuery] string id, CancellationToken cancellationToken = default) => Store.DeleteTemplateAsync(ParseGuid(id, "id"), cancellationToken); + /// + /// 应用数据权限模板 + /// [HttpPost("/rbac/data-perm/template/apply")] public async Task ApplyTemplateAsync( [FromBody] TemplateApplyInput input, diff --git a/src/Oms.Application/Services/DataPerm/DataPermService.cs b/src/Oms.Application/Services/DataPerm/DataPermService.cs index 448a964..cb9c7f2 100644 --- a/src/Oms.Application/Services/DataPerm/DataPermService.cs +++ b/src/Oms.Application/Services/DataPerm/DataPermService.cs @@ -14,6 +14,9 @@ using Oms.Domain.SystemAggregate.Repositories; namespace Oms.Application.Services.DataPerm; +/// +/// 数据权限服务 +/// [Authorize] [ApiExplorerSettings(GroupName = "RBAC-DataPerm")] public partial class DataPermService : ApplicationService @@ -26,6 +29,9 @@ public partial class DataPermService : ApplicationService private IKpiAreaRepository KpiAreaRepository => LazyServiceProvider.GetRequiredService(); private IWarehouseAddressRepository WarehouseRepository => LazyServiceProvider.GetRequiredService(); + /// + /// 获取数据权限元数据 + /// [HttpGet("/rbac/data-perm/meta")] public async Task GetMetaAsync(CancellationToken cancellationToken = default) { @@ -45,6 +51,9 @@ public partial class DataPermService : ApplicationService }; } + /// + /// 分页查询业务选项 + /// [HttpGet("/rbac/data-perm/biz-options")] public async Task> GetBizOptionsAsync( [FromQuery] string bizType, @@ -72,6 +81,9 @@ public partial class DataPermService : ApplicationService }; } + /// + /// 查询用户数据权限 + /// [HttpGet("/rbac/data-perm/get-by-user")] public async Task GetByUserAsync([FromQuery] string userId, CancellationToken cancellationToken = default) { @@ -84,6 +96,9 @@ public partial class DataPermService : ApplicationService return await Store.GetUserDataPermAsync(id, cancellationToken); } + /// + /// 查询用户生效数据范围 + /// [HttpGet("/rbac/data-perm/get-effective-by-user")] public async Task GetEffectiveByUserAsync( [FromQuery] string userId, @@ -122,6 +137,9 @@ public partial class DataPermService : ApplicationService }; } + /// + /// 保存用户数据权限 + /// [HttpPut("/rbac/data-perm/save-user")] public async Task SaveUserAsync( [FromQuery] string userId, @@ -153,12 +171,18 @@ public partial class DataPermService : ApplicationService return await Store.GetUserDataPermAsync(targetUserId, cancellationToken); } + /// + /// 查询角色数据权限 + /// [HttpGet("/rbac/data-perm/get-by-role")] public Task GetByRoleAsync([FromQuery] string roleId, CancellationToken cancellationToken = default) { return Store.GetRoleDataPermAsync(ParseGuid(roleId, "roleId"), cancellationToken); } + /// + /// 保存角色数据权限 + /// [HttpPut("/rbac/data-perm/save-role")] public async Task SaveRoleAsync( [FromQuery] string roleId, @@ -180,6 +204,9 @@ public partial class DataPermService : ApplicationService return await Store.GetRoleDataPermAsync(targetRoleId, cancellationToken); } + /// + /// 查询字段脱敏配置 + /// [HttpGet("/rbac/data-perm/field-mask/list")] public async Task GetFieldMaskListAsync([FromQuery] string dataResourceCode, CancellationToken cancellationToken = default) { @@ -188,6 +215,9 @@ public partial class DataPermService : ApplicationService return new { items }; } + /// + /// 保存字段脱敏配置 + /// [HttpPut("/rbac/data-perm/field-mask/save")] public Task SaveFieldMaskAsync([FromBody] FieldMaskSaveInput input, CancellationToken cancellationToken = default) { @@ -195,6 +225,9 @@ public partial class DataPermService : ApplicationService return Store.SaveFieldMasksAsync(code, input.Items, cancellationToken); } + /// + /// 分页查询变更日志 + /// [HttpGet("/rbac/data-perm/change-log/list")] public Task> GetChangeLogListAsync( [FromQuery] string? targetType, @@ -211,6 +244,9 @@ public partial class DataPermService : ApplicationService cancellationToken); } + /// + /// 分页查询访问日志 + /// [HttpGet("/rbac/data-perm/access-log/list")] public Task> GetAccessLogListAsync( [FromQuery] int page = 1, @@ -223,6 +259,9 @@ public partial class DataPermService : ApplicationService cancellationToken); } + /// + /// 清除用户权限缓存 + /// [HttpPost("/rbac/data-perm/invalidate-cache")] public async Task InvalidateCacheAsync([FromQuery] string userId, CancellationToken cancellationToken = default) { diff --git a/src/Oms.Application/Services/Finance/FinanceService.cs b/src/Oms.Application/Services/Finance/FinanceService.cs new file mode 100644 index 0000000..5cce6f0 --- /dev/null +++ b/src/Oms.Application/Services/Finance/FinanceService.cs @@ -0,0 +1,153 @@ +using Fake.Application; +using Fake.Users; +using Microsoft.AspNetCore.Mvc; +using Oms.Application.DataPerm; +using Oms.Application.Dtos.Finance; +using Oms.Application.Dtos.Shared; +using Oms.Application.Shared; +using Oms.Domain.CustomersAggregate.Repositories; +using Oms.Domain.OrdersAggregate; +using Oms.Domain.OrdersAggregate.Consts; +using Oms.Domain.OrdersAggregate.Repositories; + +namespace Oms.Application.Services.Finance; + +/// +/// 财务相关 API�。 + /// +[ApiExplorerSettings(GroupName = "OMS-Finance")] +public class FinanceService : ApplicationService +{ + private IOrderRepository OrderRepository => + LazyServiceProvider.GetRequiredService(); + + private ICustomerRepository CustomerRepository => + LazyServiceProvider.GetRequiredService(); + + private EffectiveScopeBuilder DataScopeBuilder => + LazyServiceProvider.GetRequiredService(); + + /// + /// 分页查询应收应付(订单费用联查订单)�。 + /// + [HttpGet("/finance/receivable-payable/list")] + public async Task> GetReceivablePayableListAsync( + [FromQuery] ReceivablePayablePaginatedInput input) + { + var customerId = await OmsSessionHelper.ResolveListCustomerIdAsync( + CustomerRepository, + CurrentUser, + input.CustomerId); + var filter = BuildFilter(input, customerId); + await ApplyInternalOrderDataScopeAsync(filter); + + var pageIndex = OmsDocHelper.NormalizePage(input.Page); + var pageSize = OmsDocHelper.NormalizePageSize(input.PageSize); + var (rows, total) = await OrderRepository.GetReceivablePayablePagedListAsync( + pageIndex, + pageSize, + filter); + + var customerIds = rows + .Select(x => x.Order.CustomerId) + .Where(x => x.HasValue) + .Select(x => x!.Value) + .Distinct() + .ToArray(); + var customers = customerIds.Length == 0 + ? [] + : await CustomerRepository.GetListAsync(x => customerIds.Contains(x.Id)); + var customerMap = customers.ToDictionary(x => x.Id); + + var items = rows.Select(row => + { + string? customerCode = null; + if (row.Order.CustomerId.HasValue + && customerMap.TryGetValue(row.Order.CustomerId.Value, out var customer)) + { + customerCode = customer.CustomerCode; + } + + return new ReceivablePayablePaginatedOutput + { + ServiceNo = row.Order.ServiceNo, + ClientNo = row.Order.ClientNo, + TrackNo = row.Order.TrackNo, + CustomerCode = customerCode, + OrderStatus = row.Order.OrderStatus, + OrderStatusName = OmsDocHelper.GetOrderStatusName(row.Order.OrderStatus), + IsPaid = row.Order.IsPaid, + PayTime = row.Order.PayTime, + ReceiveTime = row.Order.ReceiveTime, + ShipTime = row.Order.ShipTime, + ProductCode = row.Order.ProductCode, + ChannelCode = row.Order.ChannelCode, + ConsigneeCountryName = row.Order.ConsigneeCountryName, + FeeType = row.Fee.Type, + FeeTypeName = GetFeeTypeName(row.Fee.Type), + CostItem = row.Fee.CostItem, + Amount = row.Fee.Amount, + Currency = row.Fee.Currency, + DownstreamProvider = row.Fee.DownstreamProvider, + PriceNo = row.Fee.PriceNo, + PriceEffectiveTime = row.Fee.PriceEffectiveTime, + ChargingStage = row.Fee.ChargingStage, + ChargingStageName = GetChargingStageName(row.Fee.ChargingStage) + }; + }).ToList(); + + return new OmsPageResult + { + Items = items, + Total = total + }; + } + + private static OrderReceivablePayableFilter BuildFilter( + ReceivablePayablePaginatedInput input, + int? customerId) => + new() + { + Keyword = input.Keyword, + CustomerId = customerId, + CreateTimeStart = input.StartTime, + CreateTimeEnd = input.EndTime, + FeeType = input.FeeType, + CostItem = input.CostItem, + ChargingStage = input.ChargingStage + }; + + private async Task ApplyInternalOrderDataScopeAsync(OrderReceivablePayableFilter filter) + { + if (OmsSessionHelper.IsCustomerLogin(CurrentUser)) + { + return; + } + + var userGuidRaw = CurrentUser.FindClaimValueOrNull(global::System.Security.Claims.ClaimTypes.NameIdentifier); + if (string.IsNullOrWhiteSpace(userGuidRaw) || !Guid.TryParse(userGuidRaw, out var userGuid)) + { + return; + } + + var context = await DataScopeBuilder.BuildAsync(userGuid, DataScopeApplier.OrderResourceCode); + DataScopeApplier.ApplyToOrderListFilter(filter, context); + } + + private static string GetFeeTypeName(string feeType) => + feeType switch + { + OrderFeeTypeCodes.Receivable => "应收", + OrderFeeTypeCodes.Payable => "应付", + _ => feeType + }; + + private static string? GetChargingStageName(string? chargingStage) => + chargingStage switch + { + OrderFeeChargingStageCodes.Forecast => "预报", + OrderFeeChargingStageCodes.Inbound => "入库", + OrderFeeChargingStageCodes.Outbound => "出库", + _ => chargingStage + }; +} diff --git a/src/Oms.Application/Services/Operations/InboundRecordService.cs b/src/Oms.Application/Services/Operations/InboundRecordService.cs index b039cb3..e5b1d50 100644 --- a/src/Oms.Application/Services/Operations/InboundRecordService.cs +++ b/src/Oms.Application/Services/Operations/InboundRecordService.cs @@ -78,12 +78,6 @@ public class InboundRecordService : ApplicationService /// /// 入参:入库记录创建参数。 /// 入库记录结果。 - /// - /// 核心业务逻辑: - /// 1. 校验入参与关联对象、唯一性等前置条件。 - /// 2. 组装目标实体及相关明细数据。 - /// 3. 写入审计字段并持久化结果。 - /// [HttpPost("/operation/inbound/create")] public async Task CreateAsync(CreateInboundRecordInput input) { @@ -145,12 +139,6 @@ public class InboundRecordService : ApplicationService /// 入参:返回记录条数上限。 /// 入参:warehouseId。 /// 入库记录列表结果。 - /// - /// 核心业务逻辑: - /// 1. 根据查询条件构造筛选规则。 - /// 2. 查询目标数据并补齐关联展示字段。 - /// 3. 按接口约定返回列表结果。 - /// [HttpGet("/operation/inbound/recent-list")] public async Task> GetRecentListAsync([FromQuery] int limit = 20, [FromQuery] int? warehouseId = null) { diff --git a/src/Oms.Application/Services/Operations/LabelPrintService.cs b/src/Oms.Application/Services/Operations/LabelPrintService.cs index 4f0fdd3..95442ef 100644 --- a/src/Oms.Application/Services/Operations/LabelPrintService.cs +++ b/src/Oms.Application/Services/Operations/LabelPrintService.cs @@ -24,12 +24,6 @@ public class LabelPrintService : ApplicationService /// /// 入参:面单打印参数。 /// 面单打印记录。 - /// - /// 核心业务逻辑: - /// 1. 校验模板、目标单据等前置依赖数据。 - /// 2. 执行打印逻辑并记录打印结果。 - /// 3. 返回打印结果信息。 - /// [HttpPost("/operation/print-label/print")] public async Task PrintAsync(PrintLabelInput input) { @@ -98,12 +92,6 @@ public class LabelPrintService : ApplicationService /// 入参:返回记录条数上限。 /// 入参:标签模板主键,可选。 /// 面单打印记录列表结果。 - /// - /// 核心业务逻辑: - /// 1. 根据查询条件构造筛选规则。 - /// 2. 查询目标数据并补齐关联展示字段。 - /// 3. 按接口约定返回列表结果。 - /// [HttpGet("/operation/print-label/recent-list")] public async Task> GetRecentListAsync([FromQuery] int limit = 20, [FromQuery] int? labelTemplateId = null) { @@ -141,12 +129,6 @@ public class LabelPrintService : ApplicationService /// /// 入参:模板类型,可选。 /// 标签模板列表结果。 - /// - /// 核心业务逻辑: - /// 1. 根据查询条件构造筛选规则。 - /// 2. 查询目标数据并补齐关联展示字段。 - /// 3. 按接口约定返回列表结果。 - /// [HttpGet("/operation/print-label/template-list")] public async Task> GetTemplateDropdownListAsync([FromQuery] string? templateType = null) { diff --git a/src/Oms.Application/Services/Orders/OrderService.cs b/src/Oms.Application/Services/Orders/OrderService.cs index 5a9f177..f6d41bf 100644 --- a/src/Oms.Application/Services/Orders/OrderService.cs +++ b/src/Oms.Application/Services/Orders/OrderService.cs @@ -40,12 +40,6 @@ public partial class OrderService : ApplicationService /// /// 入参:订单分页查询条件。 /// 订单分页结果,包含列表数据和总记录数。 - /// - /// 核心业务逻辑: - /// 1. 根据查询条件构造筛选规则。 - /// 2. 查询目标数据并补齐关联展示字段。 - /// 3. 按接口约定返回列表结果。 - /// [HttpPost("/order/list")] public async Task> GetPaginatedListAsync([FromBody] OrderPaginatedInput input) { @@ -91,12 +85,6 @@ public partial class OrderService : ApplicationService /// /// 入参:目标主键。 /// 订单详情。 - /// - /// 核心业务逻辑: - /// 1. 根据标识查询目标对象。 - /// 2. 目标不存在时抛出业务异常。 - /// 3. 映射并返回详情结果。 - /// [HttpGet("/order/detail")] public async Task GetDetailAsync([FromQuery] int id) { @@ -109,12 +97,6 @@ public partial class OrderService : ApplicationService /// /// 入参:订单操作参数。 /// 无返回体,仅完成订单支付处理。 - /// - /// 核心业务逻辑: - /// 1. 查询并校验目标对象及当前状态。 - /// 2. 执行业务状态流转或敏感字段更新。 - /// 3. 写入审计字段并保存结果。 - /// [HttpPost("/order/pay")] public async Task PayAsync(OrderActionInput input) { @@ -168,12 +150,6 @@ public partial class OrderService : ApplicationService /// /// 入参:订单操作参数。 /// 无返回体,仅完成订单预报处理。 - /// - /// 核心业务逻辑: - /// 1. 查询并校验目标对象及当前状态。 - /// 2. 执行业务状态流转或敏感字段更新。 - /// 3. 写入审计字段并保存结果。 - /// [HttpPost("/order/pre-declare")] public async Task PreDeclareAsync(OrderActionInput input) { @@ -187,12 +163,6 @@ public partial class OrderService : ApplicationService /// /// 入参:订单操作参数。 /// 无返回体,仅完成订单拦截处理。 - /// - /// 核心业务逻辑: - /// 1. 查询并校验目标对象及当前状态。 - /// 2. 执行业务状态流转或敏感字段更新。 - /// 3. 写入审计字段并保存结果。 - /// [HttpPost("/order/intercept")] public async Task InterceptAsync(OrderActionInput input) { @@ -206,12 +176,6 @@ public partial class OrderService : ApplicationService /// /// 入参:订单操作参数。 /// 无返回体,仅完成取消订单拦截。 - /// - /// 核心业务逻辑: - /// 1. 查询并校验目标对象及当前状态。 - /// 2. 执行业务状态流转或敏感字段更新。 - /// 3. 写入审计字段并保存结果。 - /// [HttpPost("/order/cancel-intercept")] public async Task CancelInterceptAsync(OrderActionInput input) { @@ -225,12 +189,6 @@ public partial class OrderService : ApplicationService /// /// 入参:订单操作参数。 /// 无返回体,仅完成删除订单。 - /// - /// 核心业务逻辑: - /// 1. 查询并校验目标对象。 - /// 2. 执行软删除或删除关联明细。 - /// 3. 持久化删除结果。 - /// [HttpPost("/order/delete")] public async Task DeleteAsync(OrderActionInput input) { @@ -250,12 +208,6 @@ public partial class OrderService : ApplicationService /// /// 入参:订单操作参数。 /// 订单打印结果。 - /// - /// 核心业务逻辑: - /// 1. 校验模板、目标单据等前置依赖数据。 - /// 2. 执行打印逻辑并记录打印结果。 - /// 3. 返回打印结果信息。 - /// [HttpPost("/order/print")] public async Task PrintAsync(OrderActionInput input) { @@ -269,12 +221,6 @@ public partial class OrderService : ApplicationService /// /// 入参:订单导出筛选条件。 /// 订单导出结果。 - /// - /// 核心业务逻辑: - /// 1. 根据筛选条件查询待导出数据或定位模板资源。 - /// 2. 生成文件内容或组装下载响应。 - /// 3. 以文件形式返回结果。 - /// [HttpPost("/order/export")] public async Task ExportAsync([FromBody] OrderExportInput input) { @@ -302,12 +248,6 @@ public partial class OrderService : ApplicationService /// /// 入参:订单运费试算参数。 /// 订单运费试算列表结果。 - /// - /// 核心业务逻辑: - /// 1. 按 bindTime 解析销售产品最新生效卖价/规则快照(与 parcel/create 同源)。 - /// 2. 计重、分区匹配后基于卖价快照计算预报阶段应收费用。 - /// 3. 返回试算金额及 rulesVersion、priceVersion。 - /// [HttpPost("/order/price-check")] public async Task PriceCheckAsync(OrderPriceCheckInput input) { @@ -319,12 +259,6 @@ public partial class OrderService : ApplicationService /// /// 入参:订单模板列表查询条件。 /// 订单模板分页结果,包含列表数据和总记录数。 - /// - /// 核心业务逻辑: - /// 1. 根据查询条件构造筛选规则。 - /// 2. 查询目标数据并补齐关联展示字段。 - /// 3. 按接口约定返回列表结果。 - /// [HttpGet("/order/template/list")] public async Task> GetTemplateListAsync([FromQuery] OrderTemplateListInput input) { @@ -337,12 +271,6 @@ public partial class OrderService : ApplicationService /// /// 入参:模板主键。 /// 文件流响应。 - /// - /// 核心业务逻辑: - /// 1. 根据筛选条件查询待导出数据或定位模板资源。 - /// 2. 生成文件内容或组装下载响应。 - /// 3. 以文件形式返回结果。 - /// [HttpGet("/order/template/download")] public async Task DownloadTemplateAsync([FromQuery] int templateId) { @@ -354,12 +282,6 @@ public partial class OrderService : ApplicationService /// /// 入参:订单导入参数。 /// 订单导入结果。 - /// - /// 核心业务逻辑: - /// 1. 校验上传文件及导入参数。 - /// 2. 解析文件内容并执行导入流程。 - /// 3. 汇总成功失败结果后返回。 - /// [HttpPost("/order/upload")] public async Task UploadAsync([FromForm] OrderUploadInput input) { @@ -371,12 +293,6 @@ public partial class OrderService : ApplicationService /// /// 入参:订单任务列表查询条件。 /// 订单任务分页结果,包含列表数据和总记录数。 - /// - /// 核心业务逻辑: - /// 1. 根据查询条件构造筛选规则。 - /// 2. 查询目标数据并补齐关联展示字段。 - /// 3. 按接口约定返回列表结果。 - /// [HttpGet("/order/task/list")] public async Task> GetTaskListAsync([FromQuery] OrderTaskListInput input) { @@ -388,12 +304,6 @@ public partial class OrderService : ApplicationService /// /// 入参:任务主键。 /// 订单任务详情。 - /// - /// 核心业务逻辑: - /// 1. 根据标识查询目标对象。 - /// 2. 目标不存在时抛出业务异常。 - /// 3. 映射并返回详情结果。 - /// [HttpGet("/order/task/detail")] public async Task GetTaskDetailAsync([FromQuery] int taskId) { @@ -405,12 +315,6 @@ public partial class OrderService : ApplicationService /// /// 入参:订单包裹创建参数。 /// 订单包裹创建结果。 - /// - /// 核心业务逻辑: - /// 1. 校验入参与关联对象、唯一性等前置条件。 - /// 2. 组装目标实体及相关明细数据。 - /// 3. 写入审计字段并持久化结果。 - /// [HttpPost("/order/parcel/create")] public async Task CreateParcelAsync(OrderParcelCreateInput input) { @@ -422,12 +326,6 @@ public partial class OrderService : ApplicationService /// /// 入参:批量创建小包请求集合,每条记录沿用单票创建结构。 /// 批量处理结果,包含批次号、成功失败数量与逐条执行明细。 - /// - /// 核心业务逻辑: - /// 1. 校验批量请求非空后逐条复用单票创建逻辑。 - /// 2. 单条失败不会中断整批处理,允许部分成功部分失败。 - /// 3. 返回逐条执行结果,方便调用方定位失败原因并重试。 - /// [HttpPost("/order/parcel/batch-create")] public async Task BatchCreateParcelAsync(OrderParcelBatchCreateInput input) { diff --git a/src/Oms.Application/Services/Recharge/RechargeService.cs b/src/Oms.Application/Services/Recharge/RechargeService.cs index d624f5f..1e52a0d 100644 --- a/src/Oms.Application/Services/Recharge/RechargeService.cs +++ b/src/Oms.Application/Services/Recharge/RechargeService.cs @@ -68,12 +68,6 @@ public class RechargeService : ApplicationService /// /// 入参:充值审核通过参数。 /// 无返回体,仅完成审核通过充值记录。 - /// - /// 核心业务逻辑: - /// 1. 查询并校验目标对象及当前状态。 - /// 2. 执行业务状态流转或敏感字段更新。 - /// 3. 写入审计字段并保存结果。 - /// [HttpPost("/recharge/recharge-record/approve")] public async Task ApproveAsync(ApproveRechargeInput input) { @@ -112,12 +106,6 @@ public class RechargeService : ApplicationService /// /// 入参:充值审核驳回参数。 /// 无返回体,仅完成驳回充值记录。 - /// - /// 核心业务逻辑: - /// 1. 查询并校验目标对象及当前状态。 - /// 2. 执行业务状态流转或敏感字段更新。 - /// 3. 写入审计字段并保存结果。 - /// [HttpPost("/recharge/recharge-record/reject")] public async Task RejectAsync(RejectRechargeInput input) { @@ -140,12 +128,6 @@ public class RechargeService : ApplicationService /// /// 入参:充值记录分页查询条件。 /// 充值记录分页结果,包含列表数据和总记录数。 - /// - /// 核心业务逻辑: - /// 1. 根据查询条件构造筛选规则。 - /// 2. 查询目标数据并补齐关联展示字段。 - /// 3. 按接口约定返回列表结果。 - /// [HttpGet("/recharge/recharge-record/list")] public async Task> GetPaginatedListAsync([FromQuery] RechargeRecordPaginatedInput input) { @@ -199,12 +181,6 @@ public class RechargeService : ApplicationService /// /// 入参:充值记录导出筛选条件。 /// 文件流响应。 - /// - /// 核心业务逻辑: - /// 1. 根据筛选条件查询待导出数据或定位模板资源。 - /// 2. 生成文件内容或组装下载响应。 - /// 3. 以文件形式返回结果。 - /// [HttpGet("/recharge/export")] public async Task ExportAsync([FromQuery] RechargeExportInput input) { @@ -329,12 +305,6 @@ public class RechargeService : ApplicationService /// 入参:充值时间开始值。 /// 入参:充值时间结束值。 /// 出参:可直接交给 SqlSugar 仓储执行的充值记录筛选表达式。 - /// - /// 核心业务逻辑: - /// 1. 将可选筛选条件先转换成布尔开关和值; - /// 2. 根据时间区间是否存在拆分表达式; - /// 3. 避免在 SQL 翻译阶段混用 Nullable 时间判空和比较,降低生成异常 SQL 的风险。 - /// private static Expression> BuildRechargePredicate( int? customerId, RechargeStatus? rechargeStatus, diff --git a/src/Oms.Application/Services/System/CountryService.cs b/src/Oms.Application/Services/System/CountryService.cs index 8174c0e..51c93d6 100644 --- a/src/Oms.Application/Services/System/CountryService.cs +++ b/src/Oms.Application/Services/System/CountryService.cs @@ -17,12 +17,6 @@ public class CountryService : ApplicationService /// 查询国家列表。 /// /// 国家列表,返回全部有效国家主数据。 - /// - /// 核心业务逻辑: - /// 1. 查询全部国家主数据。 - /// 2. 按国家代码和英文名稳定排序。 - /// 3. 返回页面选择器可直接消费的静态结果集。 - /// [HttpGet("/system/country/list")] public async Task> GetListAsync() { diff --git a/src/Oms.Application/Services/System/DictService.cs b/src/Oms.Application/Services/System/DictService.cs index c9be9cb..d1bad20 100644 --- a/src/Oms.Application/Services/System/DictService.cs +++ b/src/Oms.Application/Services/System/DictService.cs @@ -22,12 +22,6 @@ public class DictService : ApplicationService /// /// 入参:字典分页查询条件。 /// 字典分页结果,包含字典列表与总记录数。 - /// - /// 核心业务逻辑: - /// 1. 根据字典类型和关键词拼装筛选条件。 - /// 2. 按排序值升序、主键降序返回分页结果。 - /// 3. 供系统配置页直接展示和编辑。 - /// [HttpGet("/system/dict/list")] public async Task> GetListAsync([FromQuery] DictListInput input) { @@ -53,12 +47,6 @@ public class DictService : ApplicationService /// /// 入参:字典新增参数。 /// 无返回体,仅完成新增字典。 - /// - /// 核心业务逻辑: - /// 1. 校验类型、编码、名称等基础字段。 - /// 2. 检查同类型下编码唯一性。 - /// 3. 写入字典主数据供系统配置复用。 - /// [HttpPost("/system/dict/create")] public async Task CreateAsync(DictCreateInput input) { @@ -77,12 +65,6 @@ public class DictService : ApplicationService /// /// 入参:字典更新参数。 /// 无返回体,仅完成更新字典。 - /// - /// 核心业务逻辑: - /// 1. 查询并校验目标字典是否存在。 - /// 2. 检查更新后的类型与编码组合唯一性。 - /// 3. 保存排序、编码和名称等最新配置。 - /// [HttpPost("/system/dict/update")] public async Task UpdateAsync(DictUpdateInput input) { @@ -100,12 +82,6 @@ public class DictService : ApplicationService /// /// 入参:目标主键。 /// 无返回体,仅完成删除字典。 - /// - /// 核心业务逻辑: - /// 1. 查询并校验目标字典是否存在。 - /// 2. 走框架删除通道保留软删语义。 - /// 3. 让下游列表自动隐藏已删除记录。 - /// [HttpPost("/system/dict/delete")] public async Task DeleteAsync(IdInput input) { diff --git a/src/Oms.Application/Services/System/NoticeService.cs b/src/Oms.Application/Services/System/NoticeService.cs index a455746..faa8933 100644 --- a/src/Oms.Application/Services/System/NoticeService.cs +++ b/src/Oms.Application/Services/System/NoticeService.cs @@ -32,12 +32,6 @@ public class NoticeService : ApplicationService /// /// 入参:通知分页查询条件。 /// 通知分页结果,包含通知主体、接收范围与已读统计。 - /// - /// 核心业务逻辑: - /// 1. 根据通知类型、接收对象和关键词过滤通知。 - /// 2. 聚合已读明细,计算每条通知的已读数。 - /// 3. 返回接收范围、弹窗标记与统计字段供管理端展示。 - /// [HttpGet("/system/notice/list")] public async Task> GetListAsync([FromQuery] NoticeListInput input) { @@ -75,12 +69,6 @@ public class NoticeService : ApplicationService /// /// 入参:通知新增参数。 /// 无返回体,仅完成新增通知。 - /// - /// 核心业务逻辑: - /// 1. 校验通知类型、接收对象和接收范围。 - /// 2. 验证用户或客户接收主体真实存在。 - /// 3. 保存公告或站内信主体,已读状态由确认接口单独落库。 - /// [HttpPost("/system/notice/create")] public async Task CreateAsync(NoticeCreateInput input) { @@ -102,12 +90,6 @@ public class NoticeService : ApplicationService /// /// 入参:通知更新参数。 /// 无返回体,仅完成更新通知。 - /// - /// 核心业务逻辑: - /// 1. 查询并校验目标通知是否存在。 - /// 2. 更新主体内容与接收范围。 - /// 3. 清理不在新接收范围内的历史已读明细。 - /// [HttpPost("/system/notice/update")] public async Task UpdateAsync(NoticeUpdateInput input) { @@ -135,12 +117,6 @@ public class NoticeService : ApplicationService /// /// 入参:目标主键。 /// 无返回体,仅完成删除通知。 - /// - /// 核心业务逻辑: - /// 1. 查询并校验目标通知是否存在。 - /// 2. 走框架删除通道保留软删语义。 - /// 3. 让通知与已读统计在常规查询中自动不可见。 - /// [HttpPost("/system/notice/delete")] public async Task DeleteAsync(IdInput input) { @@ -153,12 +129,6 @@ public class NoticeService : ApplicationService /// /// 入参:目标通知主键。 /// 无返回体,仅完成当前主体的已读确认。 - /// - /// 核心业务逻辑: - /// 1. 根据当前登录主体解析 user/customer 接收身份。 - /// 2. 校验当前主体在通知接收范围内。 - /// 3. 按通知、接收类型、接收ID 幂等写入已读明细。 - /// [HttpPost("/system/notice/read-confirm")] public async Task ReadConfirmAsync(IdInput input) { diff --git a/src/Oms.Application/Services/System/SystemBatchEmailService.cs b/src/Oms.Application/Services/System/SystemBatchEmailService.cs index f7eac04..d0b8dd0 100644 --- a/src/Oms.Application/Services/System/SystemBatchEmailService.cs +++ b/src/Oms.Application/Services/System/SystemBatchEmailService.cs @@ -42,6 +42,9 @@ public class SystemBatchEmailService : ApplicationService Total = total }; } + /// + /// 查询邮件模板列表 + /// [HttpGet("/system/batch-email/templates/list")] public async Task> GetTemplateListAsync() { diff --git a/src/Oms.Application/Services/System/WarehouseService.cs b/src/Oms.Application/Services/System/WarehouseService.cs index 969501b..0ce5d66 100644 --- a/src/Oms.Application/Services/System/WarehouseService.cs +++ b/src/Oms.Application/Services/System/WarehouseService.cs @@ -26,12 +26,6 @@ public class WarehouseService : ApplicationService /// /// 入参:仓库分页查询条件。 /// 仓库分页结果,包含列表数据和总记录数。 - /// - /// 核心业务逻辑: - /// 1. 根据查询条件构造筛选规则。 - /// 2. 查询目标数据并补齐关联展示字段。 - /// 3. 按接口约定返回列表结果。 - /// [HttpGet("/system/warehouse/list")] public async Task> GetPaginatedListAsync([FromQuery] WarehousePaginatedInput input) { @@ -66,12 +60,6 @@ public class WarehouseService : ApplicationService /// /// 入参:目标主键。 /// 仓库详情。 - /// - /// 核心业务逻辑: - /// 1. 根据标识查询目标对象。 - /// 2. 目标不存在时抛出业务异常。 - /// 3. 映射并返回详情结果。 - /// [HttpGet("/system/warehouse/detail")] public async Task GetByIdAsync([FromQuery] int id) { @@ -90,12 +78,6 @@ public class WarehouseService : ApplicationService /// /// 入参:仓库创建参数。 /// 无返回体,仅完成新增仓库。 - /// - /// 核心业务逻辑: - /// 1. 校验入参与关联对象、唯一性等前置条件。 - /// 2. 组装目标实体及相关明细数据。 - /// 3. 写入审计字段并持久化结果。 - /// [HttpPost("/system/warehouse/create")] public async Task CreateAsync(CreateWarehouseInput input) { @@ -125,12 +107,6 @@ public class WarehouseService : ApplicationService /// /// 入参:仓库更新参数。 /// 无返回体,仅完成更新仓库。 - /// - /// 核心业务逻辑: - /// 1. 查询并校验目标对象。 - /// 2. 按入参更新主体数据和关联配置。 - /// 3. 写入更新审计字段并保存结果。 - /// [HttpPost("/system/warehouse/update")] public async Task UpdateAsync(UpdateWarehouseInput input) { @@ -158,12 +134,6 @@ public class WarehouseService : ApplicationService /// /// 入参:目标主键。 /// 无返回体,仅完成删除仓库。 - /// - /// 核心业务逻辑: - /// 1. 查询并校验目标对象。 - /// 2. 执行软删除或删除关联明细。 - /// 3. 持久化删除结果。 - /// [HttpPost("/system/warehouse/delete")] public async Task DeleteAsync(IdInput input) { diff --git a/src/Oms.Application/Services/Xhs/XhsAgentService.cs b/src/Oms.Application/Services/Xhs/XhsAgentService.cs index a7ef6fc..fcb59bb 100644 --- a/src/Oms.Application/Services/Xhs/XhsAgentService.cs +++ b/src/Oms.Application/Services/Xhs/XhsAgentService.cs @@ -19,6 +19,9 @@ public class XhsAgentService : ApplicationService private IXhsHumanConfigRepository HumanConfigRepository => LazyServiceProvider.GetRequiredService(); private ICustomerRepository CustomerRepository => LazyServiceProvider.GetRequiredService(); + /// + /// 注册小红书Agent + /// [HttpPost("/xhs/agent/register")] public async Task RegisterAsync(XhsAgentRegisterInput input) { @@ -69,6 +72,9 @@ public class XhsAgentService : ApplicationService }; } + /// + /// Agent心跳上报 + /// [HttpPost("/xhs/agent/heartbeat")] public async Task HeartbeatAsync(XhsAgentHeartbeatInput input) { @@ -91,6 +97,9 @@ public class XhsAgentService : ApplicationService }; } + /// + /// 分页查询Agent列表 + /// [HttpPost("/xhs/agent/list")] public async Task> ListAsync(XhsAgentListInput input) { @@ -116,6 +125,9 @@ public class XhsAgentService : ApplicationService }; } + /// + /// 控制Agent设备 + /// [HttpPost("/xhs/agent/control")] public async Task ControlAsync(XhsAgentControlInput input) { diff --git a/src/Oms.Application/Services/Xhs/XhsAiService.cs b/src/Oms.Application/Services/Xhs/XhsAiService.cs index 99c7433..4ef37a6 100644 --- a/src/Oms.Application/Services/Xhs/XhsAiService.cs +++ b/src/Oms.Application/Services/Xhs/XhsAiService.cs @@ -17,6 +17,9 @@ public class XhsAiService : ApplicationService private IXhsAiProviderRepository AiProviderRepository => LazyServiceProvider.GetRequiredService(); private ICustomerRepository CustomerRepository => LazyServiceProvider.GetRequiredService(); + /// + /// 查询AI服务商列表 + /// [HttpPost("/xhs/ai/provider/list")] public async Task> ListProvidersAsync() { @@ -28,6 +31,9 @@ public class XhsAiService : ApplicationService }; } + /// + /// 保存AI服务商配置 + /// [HttpPost("/xhs/ai/provider/save")] public async Task SaveProviderAsync(XhsAiProviderSaveInput input) { @@ -78,6 +84,9 @@ public class XhsAiService : ApplicationService return MapProvider(entity, maskSecret: true); } + /// + /// AI对话 + /// [HttpPost("/xhs/ai/chat")] public async Task ChatAsync(XhsAiChatInput input) { diff --git a/src/Oms.Application/Services/Xhs/XhsAnalysisService.cs b/src/Oms.Application/Services/Xhs/XhsAnalysisService.cs index e27f64b..2d34d44 100644 --- a/src/Oms.Application/Services/Xhs/XhsAnalysisService.cs +++ b/src/Oms.Application/Services/Xhs/XhsAnalysisService.cs @@ -21,6 +21,9 @@ public class XhsAnalysisService : ApplicationService private IXhsAgentRepository AgentRepository => LazyServiceProvider.GetRequiredService(); private ICustomerRepository CustomerRepository => LazyServiceProvider.GetRequiredService(); + /// + /// 启动分析会话 + /// [HttpPost("/xhs/analysis/start")] public async Task StartAsync(XhsAnalysisStartInput input) { @@ -28,6 +31,9 @@ public class XhsAnalysisService : ApplicationService return await StartSessionAsync(customerId, input); } + /// + /// 分页查询分析会话 + /// [HttpPost("/xhs/analysis/list")] public async Task> ListAsync(XhsAnalysisListInput input) { @@ -52,6 +58,9 @@ public class XhsAnalysisService : ApplicationService }; } + /// + /// 查询分析会话详情 + /// [HttpPost("/xhs/analysis/detail")] public async Task DetailAsync(XhsAnalysisDetailInput input) { @@ -83,6 +92,9 @@ public class XhsAnalysisService : ApplicationService }; } + /// + /// 执行AI分析 + /// [HttpPost("/xhs/analysis/run-ai")] public async Task RunAiAsync(XhsAnalysisRunAiInput input) { @@ -130,6 +142,9 @@ public class XhsAnalysisService : ApplicationService return new XhsAnalysisRunAiOutput { Markdown = markdown }; } + /// + /// 创建互动任务 + /// [HttpPost("/xhs/analysis/interact")] public async Task InteractAsync(XhsAnalysisInteractInput input) { diff --git a/src/Oms.Application/Services/Xhs/XhsCreationService.cs b/src/Oms.Application/Services/Xhs/XhsCreationService.cs index c9e06dc..a556482 100644 --- a/src/Oms.Application/Services/Xhs/XhsCreationService.cs +++ b/src/Oms.Application/Services/Xhs/XhsCreationService.cs @@ -15,6 +15,9 @@ public class XhsCreationService : ApplicationService private IXhsPublishRecordRepository PublishRecordRepository => LazyServiceProvider.GetRequiredService(); private ICustomerRepository CustomerRepository => LazyServiceProvider.GetRequiredService(); + /// + /// 发布创作内容 + /// [HttpPost("/xhs/creation/publish")] public async Task PublishAsync(XhsCreationPublishInput input) { @@ -56,6 +59,9 @@ public class XhsCreationService : ApplicationService }; } + /// + /// AI生成创作内容 + /// [HttpPost("/xhs/creation/generate")] public async Task GenerateAsync(XhsCreationGenerateInput input) { diff --git a/src/Oms.Application/Services/Xhs/XhsHumanConfigService.cs b/src/Oms.Application/Services/Xhs/XhsHumanConfigService.cs index 985cb40..92f31b7 100644 --- a/src/Oms.Application/Services/Xhs/XhsHumanConfigService.cs +++ b/src/Oms.Application/Services/Xhs/XhsHumanConfigService.cs @@ -15,6 +15,9 @@ public class XhsHumanConfigService : ApplicationService private IXhsAgentRepository AgentRepository => LazyServiceProvider.GetRequiredService(); private ICustomerRepository CustomerRepository => LazyServiceProvider.GetRequiredService(); + /// + /// 查询人机行为配置 + /// [HttpPost("/xhs/human-config/get")] public async Task GetAsync() { @@ -23,6 +26,9 @@ public class XhsHumanConfigService : ApplicationService return MapOutput(config); } + /// + /// 保存人机行为配置 + /// [HttpPost("/xhs/human-config/save")] public async Task SaveAsync(XhsHumanConfigSaveInput input) { @@ -35,6 +41,9 @@ public class XhsHumanConfigService : ApplicationService return MapOutput(config); } + /// + /// 拉取人机行为配置 + /// [HttpPost("/xhs/human-config/pull")] public async Task PullAsync(XhsHumanConfigPullInput input) { diff --git a/src/Oms.Application/Services/Xhs/XhsMediaService.cs b/src/Oms.Application/Services/Xhs/XhsMediaService.cs index cff7799..389fdaf 100644 --- a/src/Oms.Application/Services/Xhs/XhsMediaService.cs +++ b/src/Oms.Application/Services/Xhs/XhsMediaService.cs @@ -17,6 +17,9 @@ public class XhsMediaService : ApplicationService private ICustomerRepository CustomerRepository => LazyServiceProvider.GetRequiredService(); private IWebHostEnvironment WebHostEnvironment => LazyServiceProvider.GetRequiredService(); + /// + /// 上传媒体文件 + /// [HttpPost("/xhs/media/upload")] public async Task UploadAsync(IFormFile file) { diff --git a/src/Oms.Application/Services/Xhs/XhsPublishService.cs b/src/Oms.Application/Services/Xhs/XhsPublishService.cs index e10fd31..e6ebaea 100644 --- a/src/Oms.Application/Services/Xhs/XhsPublishService.cs +++ b/src/Oms.Application/Services/Xhs/XhsPublishService.cs @@ -17,6 +17,9 @@ public class XhsPublishService : ApplicationService private IXhsTaskRepository TaskRepository => LazyServiceProvider.GetRequiredService(); private ICustomerRepository CustomerRepository => LazyServiceProvider.GetRequiredService(); + /// + /// 分页查询发布记录 + /// [HttpPost("/xhs/publish/list")] public async Task> ListAsync(XhsPublishListInput input) { @@ -37,6 +40,9 @@ public class XhsPublishService : ApplicationService }; } + /// + /// 取消定时发布 + /// [HttpPost("/xhs/publish/cancel")] public async Task CancelAsync(XhsPublishCancelInput input) { @@ -62,6 +68,9 @@ public class XhsPublishService : ApplicationService } } + /// + /// 重试失败发布 + /// [HttpPost("/xhs/publish/retry")] public async Task RetryAsync(XhsPublishRetryInput input) { diff --git a/src/Oms.Application/Services/Xhs/XhsSkillService.cs b/src/Oms.Application/Services/Xhs/XhsSkillService.cs index 6f4065c..5f35366 100644 --- a/src/Oms.Application/Services/Xhs/XhsSkillService.cs +++ b/src/Oms.Application/Services/Xhs/XhsSkillService.cs @@ -16,6 +16,9 @@ public class XhsSkillService : ApplicationService private IXhsSkillRepository SkillRepository => LazyServiceProvider.GetRequiredService(); private ICustomerRepository CustomerRepository => LazyServiceProvider.GetRequiredService(); + /// + /// 查询技能列表 + /// [HttpPost("/xhs/skill/list")] public async Task> ListAsync(XhsSkillListInput input) { @@ -31,6 +34,9 @@ public class XhsSkillService : ApplicationService }; } + /// + /// 保存技能 + /// [HttpPost("/xhs/skill/save")] public async Task SaveAsync(XhsSkillSaveInput input) { @@ -71,6 +77,9 @@ public class XhsSkillService : ApplicationService return MapSkill(entity); } + /// + /// 删除技能 + /// [HttpPost("/xhs/skill/delete")] public async Task DeleteAsync(IdInput input) { @@ -84,6 +93,9 @@ public class XhsSkillService : ApplicationService await SkillRepository.DeleteAsync(entity); } + /// + /// 运行技能 + /// [HttpPost("/xhs/skill/run")] public async Task RunAsync(XhsSkillRunInput input) { diff --git a/src/Oms.Application/Services/Xhs/XhsTaskService.cs b/src/Oms.Application/Services/Xhs/XhsTaskService.cs index 49f11ac..2281bfe 100644 --- a/src/Oms.Application/Services/Xhs/XhsTaskService.cs +++ b/src/Oms.Application/Services/Xhs/XhsTaskService.cs @@ -20,6 +20,9 @@ public class XhsTaskService : ApplicationService private IXhsAnalysisSessionRepository AnalysisSessionRepository => LazyServiceProvider.GetRequiredService(); private ICustomerRepository CustomerRepository => LazyServiceProvider.GetRequiredService(); + /// + /// 领取待执行任务 + /// [HttpPost("/xhs/task/claim")] public async Task ClaimAsync(XhsTaskClaimInput input) { @@ -42,6 +45,9 @@ public class XhsTaskService : ApplicationService }; } + /// + /// 上报任务执行结果 + /// [HttpPost("/xhs/task/report")] public async Task ReportAsync(XhsTaskReportInput input) { @@ -83,6 +89,9 @@ public class XhsTaskService : ApplicationService return new XhsTaskReportOutput(); } + /// + /// 分页查询任务列表 + /// [HttpPost("/xhs/task/list")] public async Task> ListAsync(XhsTaskListInput input) { @@ -104,6 +113,9 @@ public class XhsTaskService : ApplicationService }; } + /// + /// 取消任务 + /// [HttpPost("/xhs/task/cancel")] public async Task CancelAsync(XhsTaskCancelInput input) { diff --git a/src/Oms.Domain/OrdersAggregate/OrderReceivablePayableFilter.cs b/src/Oms.Domain/OrdersAggregate/OrderReceivablePayableFilter.cs new file mode 100644 index 0000000..9d72a6f --- /dev/null +++ b/src/Oms.Domain/OrdersAggregate/OrderReceivablePayableFilter.cs @@ -0,0 +1,22 @@ +namespace Oms.Domain.OrdersAggregate; + +/// +/// 应收应付(订单费用)列表筛选条件。 +/// +public class OrderReceivablePayableFilter : OrderListFilter +{ + /// + /// 费用类型:receivable / payable,空或 all 表示全部。 + /// + public string? FeeType { get; set; } + + /// + /// 费用项关键词。 + /// + public string? CostItem { get; set; } + + /// + /// 计费阶段:forecast / inbound / outbound。 + /// + public string? ChargingStage { get; set; } +} diff --git a/src/Oms.Domain/OrdersAggregate/OrderReceivablePayableRow.cs b/src/Oms.Domain/OrdersAggregate/OrderReceivablePayableRow.cs new file mode 100644 index 0000000..d9ec623 --- /dev/null +++ b/src/Oms.Domain/OrdersAggregate/OrderReceivablePayableRow.cs @@ -0,0 +1,13 @@ +using Oms.Domain.OrdersAggregate.Entities; + +namespace Oms.Domain.OrdersAggregate; + +/// +/// 订单费用与订单联查行。 +/// +public class OrderReceivablePayableRow +{ + public OrderFee Fee { get; set; } = null!; + + public Order Order { get; set; } = null!; +} diff --git a/src/Oms.Domain/OrdersAggregate/Repositories/IOrderRepository.cs b/src/Oms.Domain/OrdersAggregate/Repositories/IOrderRepository.cs index 8e6ce8b..f79403c 100644 --- a/src/Oms.Domain/OrdersAggregate/Repositories/IOrderRepository.cs +++ b/src/Oms.Domain/OrdersAggregate/Repositories/IOrderRepository.cs @@ -63,5 +63,11 @@ public interface IOrderRepository : IRepository Task> GetFeesByOrderIdsAsync(IEnumerable orderIds, CancellationToken cancellationToken = default); + Task<(List Items, int Total)> GetReceivablePayablePagedListAsync( + int pageIndex, + int pageSize, + OrderReceivablePayableFilter filter, + CancellationToken cancellationToken = default); + Task> GetStatusCountsAsync(int? customerId, CancellationToken cancellationToken = default); } diff --git a/src/Oms.SqlSugarCore/Orders/OrderRepository.cs b/src/Oms.SqlSugarCore/Orders/OrderRepository.cs index 61e5931..23f426e 100644 --- a/src/Oms.SqlSugarCore/Orders/OrderRepository.cs +++ b/src/Oms.SqlSugarCore/Orders/OrderRepository.cs @@ -340,6 +340,68 @@ public class OrderRepository : OmsSqlSugarRepository, IOrderRepository, I .ToListAsync(cancellationToken); } + public async Task<(List Items, int Total)> GetReceivablePayablePagedListAsync( + int pageIndex, + int pageSize, + OrderReceivablePayableFilter filter, + CancellationToken cancellationToken = default) + { + var db = await GetDbContextAsync(cancellationToken); + var orderIdsQuery = ApplyListFilter(db.Queryable(), filter).Select(x => x.Id); + + var feeQuery = db.Queryable() + .Where(fee => !fee.IsDeleted) + .In(fee => fee.OrderId, orderIdsQuery); + + var feeType = filter.FeeType?.Trim(); + if (!string.IsNullOrWhiteSpace(feeType) + && !string.Equals(feeType, "all", StringComparison.OrdinalIgnoreCase)) + { + feeQuery = feeQuery.Where(fee => fee.Type == feeType); + } + + var costItem = filter.CostItem?.Trim(); + if (!string.IsNullOrWhiteSpace(costItem)) + { + feeQuery = feeQuery.Where(fee => fee.CostItem.Contains(costItem)); + } + + var chargingStage = filter.ChargingStage?.Trim(); + if (!string.IsNullOrWhiteSpace(chargingStage) + && !string.Equals(chargingStage, "all", StringComparison.OrdinalIgnoreCase)) + { + feeQuery = feeQuery.Where(fee => fee.ChargingStage == chargingStage); + } + + var total = await feeQuery.CountAsync(cancellationToken); + var fees = await feeQuery + .OrderBy(fee => fee.CreateTime, OrderByType.Desc) + .OrderBy(fee => fee.Id, OrderByType.Desc) + .ToPageListAsync(pageIndex, pageSize, cancellationToken); + + if (fees.Count == 0) + { + return ([], total); + } + + var orderIds = fees.Select(x => x.OrderId).Distinct().ToArray(); + var orders = await db.Queryable() + .Where(x => orderIds.Contains(x.Id)) + .ToListAsync(cancellationToken); + var orderMap = orders.ToDictionary(x => x.Id); + + var items = fees + .Where(fee => orderMap.ContainsKey(fee.OrderId)) + .Select(fee => new OrderReceivablePayableRow + { + Fee = fee, + Order = orderMap[fee.OrderId] + }) + .ToList(); + + return (items, total); + } + public async Task> GetStatusCountsAsync(int? customerId, CancellationToken cancellationToken = default) { var db = await GetDbContextAsync(cancellationToken); diff --git a/src/SimpleAdmin.Api.IntegrationTests/Support/SimpleAdminApiTestHost.cs b/src/SimpleAdmin.Api.IntegrationTests/Support/SimpleAdminApiTestHost.cs index de62f5d..49bf56d 100644 --- a/src/SimpleAdmin.Api.IntegrationTests/Support/SimpleAdminApiTestHost.cs +++ b/src/SimpleAdmin.Api.IntegrationTests/Support/SimpleAdminApiTestHost.cs @@ -33,6 +33,16 @@ internal sealed class SimpleAdminApiTestHost : IAsyncDisposable .OrderBy(x => x) .ToList(); + public IReadOnlyList GetHttpMethods(string routePatternContains) => + _app.Services.GetRequiredService() + .Endpoints + .OfType() + .Where(x => (x.RoutePattern.RawText ?? string.Empty).Contains(routePatternContains, StringComparison.OrdinalIgnoreCase)) + .SelectMany(x => x.Metadata.GetMetadata()?.HttpMethods ?? []) + .Distinct(StringComparer.OrdinalIgnoreCase) + .OrderBy(x => x) + .ToList(); + public static async Task CreateAsync( ICountryRepository? countryRepository = null, IDictRepository? dictRepository = null, diff --git a/src/SimpleAdmin.Api.IntegrationTests/WeChatRouteIntegrationTests.cs b/src/SimpleAdmin.Api.IntegrationTests/WeChatRouteIntegrationTests.cs index 122347f..8d0ba6e 100644 --- a/src/SimpleAdmin.Api.IntegrationTests/WeChatRouteIntegrationTests.cs +++ b/src/SimpleAdmin.Api.IntegrationTests/WeChatRouteIntegrationTests.cs @@ -15,6 +15,16 @@ namespace SimpleAdmin.Api.IntegrationTests; public class WeChatRouteIntegrationTests { + [Fact] + public async Task WeChatLegacyVerification_ShouldRegisterGetAndPostMethods() + { + await using var host = await SimpleAdminApiTestHost.CreateAsync(configureServices: ConfigureWeChatFallback); + + var methods = host.GetHttpMethods("apiwechat/verification"); + methods.Should().Contain("GET"); + methods.Should().Contain("POST"); + } + [Fact] public async Task WeChatRoutes_ShouldBeRegisteredOnAuthService() { diff --git a/src/SimpleAdmin.Api/Auth/AuthService.WeChatMp.cs b/src/SimpleAdmin.Api/Auth/AuthService.WeChatMp.cs index da17f66..ca1ec56 100644 --- a/src/SimpleAdmin.Api/Auth/AuthService.WeChatMp.cs +++ b/src/SimpleAdmin.Api/Auth/AuthService.WeChatMp.cs @@ -23,7 +23,7 @@ public partial class AuthService LazyServiceProvider.GetRequiredService>(); /// - /// 微信服务器接入验签(兼容 WMS:/api/apiwechat/verification)。 + /// 微信公众号接入验签(GET) /// [AllowAnonymous] [HttpGet("/apiwechat/verification")] @@ -88,7 +88,7 @@ public partial class AuthService } /// - /// 微信消息/事件回调(兼容 WMS:/api/apiwechat/verification)。 + /// 微信公众号消息/事件回调(POST) /// [AllowAnonymous] [HttpPost("/apiwechat/verification")] diff --git a/src/SimpleAdmin.Api/SimpleAdmin.Api.csproj b/src/SimpleAdmin.Api/SimpleAdmin.Api.csproj index 3ba3514..18db10c 100644 --- a/src/SimpleAdmin.Api/SimpleAdmin.Api.csproj +++ b/src/SimpleAdmin.Api/SimpleAdmin.Api.csproj @@ -5,6 +5,8 @@ enable enable Linux + True + $(NoWarn);CS1591 diff --git a/src/SimpleAdmin.Api/SimpleAdminApiBootstrap.cs b/src/SimpleAdmin.Api/SimpleAdminApiBootstrap.cs index 1131c4b..4078a30 100644 --- a/src/SimpleAdmin.Api/SimpleAdminApiBootstrap.cs +++ b/src/SimpleAdmin.Api/SimpleAdminApiBootstrap.cs @@ -4,7 +4,7 @@ namespace SimpleAdmin.Api; /// /// 为正式启动与集成测试提供统一的应用构建入口。 -/// + /// public static class SimpleAdminApiBootstrap { ///