CaiWuXiTong/modules/EcommerceFinance/Services/PayablesFinalRegistry.php
renshen 7fbcd061af 应付款终版货款对账:新增「入库单号/采购单号/对账人」列 (#351)
「月份」后补入库单号、采购单号,末尾「未发出」后补对账人;导入模板/表格/导入/编辑/导出同一套字段,只作用于终版目录。
2026-10-16 20:58:42 +08:00

104 lines
3.7 KiB
PHP

<?php
namespace Modules\EcommerceFinance\Services;
use Illuminate\Validation\ValidationException;
/**
* 「终版」目录的按表数据登记:确定每个页签的字段(决定导入模板与表格列)
* 以及数据标题;数据本身独立存放,与基础目录互不影响。
*/
class PayablesFinalRegistry
{
public const SECTION_SUPPLIER = 'supplier-payables-final';
public const SECTION_COURIER = 'courier-payables-final';
/** @var array<string,string> 供应商应付(终版)页签 */
private const SUPPLIER_TITLES = [
'product-prices' => '商品价格',
'payment-reconciliation' => '货款对账',
'return-reconciliation' => '退货对账',
'invoice-deductions' => '发票扣款',
'board-deductions' => '板材扣款',
'compensation-details' => '赔偿明细',
'advance-details' => '借支明细',
'sample-deductions' => '样品扣款',
'other-adjustments' => '其他扣款补款',
'delivery-unpriced' => '送货未定价',
'return-unpriced' => '退货未定价',
'dropshipping-express' => '代发快递',
'supplier-payables-report' => '供应商应付表',
];
/** 所有终版导入模板都带“月份”列,方便按月导入和查看。 */
private const MONTH_FIELD = ['summary_month' => ['label' => '月份', 'type' => 'month']];
/**
* 供应商应付(终版)在基础字段前后追加的列(只影响终版目录,基础目录对应列另有口径):
* 货款对账在「月份」后补入库单号、采购单号,在末尾补未发出、对账人。
*/
private const SUPPLIER_EXTRA_FIELDS = [
'payment-reconciliation' => [
'before' => [
'stockNo' => ['label' => '入库单号', 'type' => 'text'],
'purchaseNo' => ['label' => '采购单号', 'type' => 'text'],
],
'after' => [
'unsent' => ['label' => '未发出', 'type' => 'text'],
'reconciler' => ['label' => '对账人', 'type' => 'text'],
],
],
];
public function __construct(
private readonly SupplierPayableMaintenanceRegistry $supplier,
private readonly ProductPriceWorkbookImporter $productPrices,
private readonly CourierPayableFinalRegistry $courier,
) {
}
public function supports(string $section, string $dataset): bool
{
return array_key_exists($dataset, $this->titles($section));
}
/** @return array<string,string> */
public function titles(string $section): array
{
return match ($section) {
self::SECTION_SUPPLIER => self::SUPPLIER_TITLES,
self::SECTION_COURIER => $this->courier->titles(),
default => [],
};
}
public function title(string $section, string $dataset): string
{
$titles = $this->titles($section);
if (! array_key_exists($dataset, $titles)) {
throw ValidationException::withMessages(['dataset' => '不支持该终版目录页面。']);
}
return $titles[$dataset];
}
/** @return array<string,array{label:string,type:string}> */
public function fields(string $section, string $dataset): array
{
$this->title($section, $dataset);
if ($section === self::SECTION_COURIER) {
return self::MONTH_FIELD + $this->courier->fields($dataset);
}
$fields = $dataset === 'product-prices'
? $this->productPrices->templateFields()
: $this->supplier->fields($dataset);
$extra = self::SUPPLIER_EXTRA_FIELDS[$dataset] ?? [];
return self::MONTH_FIELD + ($extra['before'] ?? []) + $fields + ($extra['after'] ?? []);
}
}