- 所有账户页签在「店铺」右侧新增「总账备注」下拉:按(平台+账单项目)翻译成账单项目集合过滤,页面/列设置/导出同口径;淘系支付宝、淘系微信同页签混多平台时按店铺名前缀细分 - 每日账单脚本:胜算超出同步导出上限(url=null+taskId)时自动从「异步导出下载管理」取回本次任务全部分片并合并成一份 CSV,导入前按页面笔数核对(不一致则跳过导入) - 实测:京东 7 月异步导出两片 219158+235846=455004 笔 / 收入 17695094.84 / 支出 8035128.21,与已导入口径一致
144 lines
5.7 KiB
PHP
144 lines
5.7 KiB
PHP
<?php
|
|
|
|
namespace Tests\Feature\Business;
|
|
|
|
use App\Models\Auth\Permission;
|
|
use Mockery;
|
|
use Modules\EcommerceFinance\Repositories\PinduoduoSettlementBillRepository;
|
|
use RuntimeException;
|
|
use Tests\Feature\FeatureTestCase;
|
|
|
|
class PinduoduoReceivingBillsTest extends FeatureTestCase
|
|
{
|
|
public function test_endpoint_reads_pinduoduo_goods_account_mirror_with_all_filters(): void
|
|
{
|
|
$this->allowPage();
|
|
$filters = [
|
|
'store_name' => '拼多多-测试店',
|
|
'bill_item' => '交易收入',
|
|
'start' => '2026-08-12',
|
|
'end' => '2026-09-10',
|
|
'keyword' => '260909',
|
|
];
|
|
$repository = Mockery::mock(PinduoduoSettlementBillRepository::class);
|
|
$repository->shouldReceive('paginateAccountBills')->once()->with(
|
|
$filters, 'occurred_at', 'desc', 2, 20,
|
|
)->andReturn([
|
|
'current_page' => 2,
|
|
'last_page' => 3,
|
|
'per_page' => 20,
|
|
'total' => 41,
|
|
'data' => [[
|
|
'id' => '14424200',
|
|
'record_code' => '380425163199',
|
|
'store_name' => '拼多多-测试店',
|
|
'income' => 91.64,
|
|
'expense' => 0.0,
|
|
'payload' => [
|
|
'merchant_order_no' => '260909-047741735284017',
|
|
'finance_type' => '交易收入',
|
|
'type' => '拼多多货款账户',
|
|
],
|
|
]],
|
|
'summary' => ['income' => 91.64, 'expense' => 0.0, 'balance' => 91.64, 'count' => 41],
|
|
]);
|
|
$this->app->instance(PinduoduoSettlementBillRepository::class, $repository);
|
|
|
|
$this->withExceptionHandling()
|
|
->loginAs()
|
|
->getJson(route('ecommerce-finance.account-bills.index', [
|
|
'bill_type' => 'pinduoduo',
|
|
...$filters,
|
|
'page' => 2,
|
|
'limit' => 20,
|
|
]))
|
|
->assertOk()
|
|
->assertJsonPath('data.0.payload.type', '拼多多货款账户')
|
|
->assertJsonPath('columns.title', '拼多多账户')
|
|
->assertJsonPath('summary.count', 41);
|
|
}
|
|
|
|
public function test_filter_options_and_selected_column_export_use_the_same_mirror(): void
|
|
{
|
|
$this->allowPage();
|
|
$repository = Mockery::mock(PinduoduoSettlementBillRepository::class);
|
|
$repository->shouldReceive('accountBillFilterOptions')->once()->andReturn([
|
|
'shops' => ['拼多多-A店', '拼多多-B店'],
|
|
'bill_items' => ['交易收入', '技术服务费'],
|
|
]);
|
|
$repository->shouldReceive('exportAccountBills')->once()->with(
|
|
['store_name' => '拼多多-A店'], 'record_code', 'asc',
|
|
)->andReturn([[
|
|
'record_code' => '380425163199',
|
|
'store_name' => '拼多多-A店',
|
|
'payload' => ['finance_type' => '交易收入'],
|
|
]]);
|
|
$this->app->instance(PinduoduoSettlementBillRepository::class, $repository);
|
|
|
|
$this->loginAs()
|
|
->withHeader('X-Requested-With', 'XMLHttpRequest')
|
|
->get(route('ecommerce-finance.account-bills.filter-options', ['bill_type' => 'pinduoduo']))
|
|
->assertOk()
|
|
->assertExactJson([
|
|
'shops' => ['拼多多-A店', '拼多多-B店'],
|
|
'bill_items' => ['交易收入', '技术服务费'],
|
|
'ledger_remarks' => [],
|
|
]);
|
|
|
|
$response = $this->loginAs()->get(route('ecommerce-finance.account-bills.export', [
|
|
'bill_type' => 'pinduoduo',
|
|
'store_name' => '拼多多-A店',
|
|
'sort' => 'record_code',
|
|
'dir' => 'asc',
|
|
'columns' => 'payload.finance_type,record_code,store_name',
|
|
]));
|
|
|
|
$response->assertOk()
|
|
->assertHeader('content-type', 'text/csv; charset=UTF-8')
|
|
->assertDownload('pinduoduo_account_bills.csv');
|
|
$csv = $response->streamedContent();
|
|
$this->assertStringContainsString('财务类型,记录编码,店铺', $csv);
|
|
$this->assertStringContainsString('交易收入,"=""380425163199""",拼多多-A店', $csv);
|
|
}
|
|
|
|
public function test_unready_mirror_returns_a_clear_retryable_response(): void
|
|
{
|
|
$this->allowPage();
|
|
$repository = Mockery::mock(PinduoduoSettlementBillRepository::class);
|
|
$repository->shouldReceive('paginateAccountBills')->once()->andThrow(
|
|
new RuntimeException('pinduoduo_authoritative_bills_not_ready')
|
|
);
|
|
$this->app->instance(PinduoduoSettlementBillRepository::class, $repository);
|
|
|
|
$this->loginAs()
|
|
->withHeader('X-Requested-With', 'XMLHttpRequest')
|
|
->get(route('ecommerce-finance.account-bills.index', ['bill_type' => 'pinduoduo']))
|
|
->assertStatus(503)
|
|
->assertJsonPath('message', '拼多多完整货款账单尚未完成首次导入,当前不会回退到不完整的聚水潭辅助表。');
|
|
}
|
|
|
|
public function test_invalid_date_range_is_rejected_before_reading_the_mirror(): void
|
|
{
|
|
$this->allowPage();
|
|
$repository = Mockery::mock(PinduoduoSettlementBillRepository::class);
|
|
$repository->shouldNotReceive('paginateAccountBills');
|
|
$this->app->instance(PinduoduoSettlementBillRepository::class, $repository);
|
|
|
|
$this->withExceptionHandling()
|
|
->loginAs()
|
|
->getJson(route('ecommerce-finance.account-bills.index', [
|
|
'bill_type' => 'pinduoduo',
|
|
'start' => '2026-09-10',
|
|
'end' => '2026-08-12',
|
|
]))
|
|
->assertStatus(422);
|
|
}
|
|
|
|
private function allowPage(): void
|
|
{
|
|
$this->user->attachPermission(
|
|
Permission::where('name', 'read-admin-panel')->firstOrFail()
|
|
);
|
|
}
|
|
}
|