CaiWuXiTong/modules/EcommerceFinance/Services/SupplierReturnConfirmation.php
renshen 2848c81a5e 供应商对账:退货明细改为「退货扣减确认」面板 (#369)
退货扣减确认:顶部汇总、逐行确认/异议、全部确认(不覆盖异议)、金额空按预估金额扣减,展示金额最高 15 行。
2026-10-17 09:40:54 +08:00

76 lines
2.5 KiB
PHP
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

<?php
namespace Modules\EcommerceFinance\Services;
/**
* 退货扣减确认:厂家逐行「确认 / 异议」,或一键全部确认。
* 状态存在按表数据表里(数据集 return-confirmation:<厂家>,记录键沿用退货行的 _action_key)。
*/
class SupplierReturnConfirmation
{
public const PREFIX = 'return-confirmation:';
public const STATUS_CONFIRMED = 'confirmed';
public const STATUS_DISPUTED = 'disputed';
public function __construct(
private readonly SupplierPayableOverrideStore $store,
) {
}
/** @return array<string,string> 记录键 => 状态 */
public function statuses(string $supplier, int $companyId): array
{
$statuses = [];
foreach ($this->store->listRows(self::PREFIX . $supplier, $companyId) as $row) {
$key = (string) ($row['_action_key'] ?? '');
$status = (string) ($row['status'] ?? '');
if ($key !== '' && in_array($status, [self::STATUS_CONFIRMED, self::STATUS_DISPUTED], true)) {
$statuses[$key] = $status;
}
}
return $statuses;
}
public function mark(string $supplier, string $recordKey, string $status, int $companyId, ?int $userId): void
{
if (! in_array($status, [self::STATUS_CONFIRMED, self::STATUS_DISPUTED], true)) {
return;
}
$this->store->save(self::PREFIX . $supplier, $recordKey, [
'status' => $status,
'marked_at' => now()->toDateTimeString(),
], $companyId, $userId, 'manual');
}
/** @param list<string> $recordKeys 一键确认全部(已异议的行保持异议,不覆盖) */
public function confirmAll(string $supplier, array $recordKeys, int $companyId, ?int $userId): int
{
$statuses = $this->statuses($supplier, $companyId);
$confirmed = 0;
$this->store->transaction(function () use ($supplier, $recordKeys, $statuses, $companyId, $userId, &$confirmed): void {
foreach ($recordKeys as $key) {
if ($key === '') {
continue;
}
$status = $statuses[$key] ?? '';
if ($status === self::STATUS_DISPUTED) {
continue;
}
if ($status !== self::STATUS_CONFIRMED) {
$this->mark($supplier, $key, self::STATUS_CONFIRMED, $companyId, $userId);
}
$confirmed++;
}
});
return $confirmed;
}
}