diff --git a/CHANGELOG-client.md b/CHANGELOG-client.md index 30c9410..b958e73 100644 --- a/CHANGELOG-client.md +++ b/CHANGELOG-client.md @@ -5,6 +5,12 @@ All notable changes to this project will be documented in this file. The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/), and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.html). +## [1.0.63] - 2026-06-20 + +### 修复 +- 修复入库单 / 出库单「全部状态」筛选遗漏未审核单据的问题,状态下拉新增「待审核」选项,且筛选真正生效 +- 修复「入库审核 / 出库审核」标签页只显示部分待审核单、漏掉早期单号的问题:筛选改为服务端驱动,跨分页结果完整可靠 + ## [1.0.62] - 2026-06-20 ### 改进 diff --git a/client/lib/providers/stock_in_provider.dart b/client/lib/providers/stock_in_provider.dart index f1e994b..2d08713 100644 --- a/client/lib/providers/stock_in_provider.dart +++ b/client/lib/providers/stock_in_provider.dart @@ -60,6 +60,9 @@ class StockInListNotifier extends AsyncNotifier> { reload(); } + /// 当前服务端状态过滤值(供页面进入时对齐标签/下拉,避免重复拉取) + String get currentStatus => _status; + void setStatus(String status) { _status = status; _page = 1; diff --git a/client/lib/providers/stock_out_provider.dart b/client/lib/providers/stock_out_provider.dart index ef7b667..a062001 100644 --- a/client/lib/providers/stock_out_provider.dart +++ b/client/lib/providers/stock_out_provider.dart @@ -60,6 +60,9 @@ class StockOutListNotifier extends AsyncNotifier> { reload(); } + /// 当前服务端状态过滤值(供页面进入时对齐标签/下拉,避免重复拉取) + String get currentStatus => _status; + void setStatus(String status) { _status = status; _page = 1; diff --git a/client/lib/screens/stock_in/stock_in_list_screen.dart b/client/lib/screens/stock_in/stock_in_list_screen.dart index 741f65d..d69cba3 100644 --- a/client/lib/screens/stock_in/stock_in_list_screen.dart +++ b/client/lib/screens/stock_in/stock_in_list_screen.dart @@ -61,6 +61,14 @@ class _StockInListScreenState extends ConsumerState { ColumnPrefs.load(_screenId).then((saved) { if (saved != null && mounted) setState(() => _hiddenCols = saved); }); + // 进入页面时把服务端状态过滤对齐到当前标签/下拉(provider 持久化,State 会重建) + WidgetsBinding.instance.addPostFrameCallback((_) { + if (!mounted) return; + final tab = ref.read(stockInTabProvider); + final want = tab == 1 ? 'pending,draft' : _statusFilter; + final notifier = ref.read(stockInListProvider.notifier); + if (notifier.currentStatus != want) notifier.setStatus(want); + }); } String? get _startDate => _dateRange != null @@ -89,7 +97,13 @@ class _StockInListScreenState extends ConsumerState { return PageScaffold( title: '入库管理', initialTab: ref.read(stockInTabProvider), - onTabChanged: (i) => ref.read(stockInTabProvider.notifier).state = i, + onTabChanged: (i) { + ref.read(stockInTabProvider.notifier).state = i; + // 审核标签页按 pending+draft 服务端拉取;入库单页沿用下拉状态('' 为全部) + ref + .read(stockInListProvider.notifier) + .setStatus(i == 1 ? 'pending,draft' : _statusFilter); + }, tabs: const [ Tab(text: '入库单'), Tab(text: '入库审核'), @@ -124,15 +138,19 @@ class _StockInListScreenState extends ConsumerState { ), data: (result) { final allOrders = result.data; + // 状态过滤已改为服务端驱动(setStatus)。这里仅按标签做轻量显示守卫, + // 避免共用 provider 在标签切换、refetch 在途时短暂闪现他状态数据。 final List statusFiltered; if (filterStatus == 'pending') { + // 入库审核:服务端按 pending,draft 拉取 statusFiltered = allOrders .where((o) => o.status == 'draft' || o.status == 'pending') .toList(); } else if (filterStatus == 'exclude_pending') { - statusFiltered = allOrders - .where((o) => o.status != 'draft' && o.status != 'pending') - .toList(); + // 入库单:服务端按下拉状态拉取;'全部状态' 显示全部(含未审核) + statusFiltered = _statusFilter.isEmpty + ? allOrders + : allOrders.where((o) => o.status == _statusFilter).toList(); } else { statusFiltered = allOrders; } @@ -1041,6 +1059,7 @@ class _StatusFilterDropdown extends StatelessWidget { items: [ const DropdownMenuItem(value: '', child: Text('全部状态', style: TextStyle(fontSize: 13))), const DropdownMenuItem(value: 'draft', child: Text('草稿', style: TextStyle(fontSize: 13))), + const DropdownMenuItem(value: 'pending', child: Text('待审核', style: TextStyle(fontSize: 13))), const DropdownMenuItem(value: 'approved', child: Text('已审核', style: TextStyle(fontSize: 13))), const DropdownMenuItem(value: 'rejected', child: Text('已拒绝', style: TextStyle(fontSize: 13))), ], diff --git a/client/lib/screens/stock_out/stock_out_list_screen.dart b/client/lib/screens/stock_out/stock_out_list_screen.dart index b8bd232..5df1f71 100644 --- a/client/lib/screens/stock_out/stock_out_list_screen.dart +++ b/client/lib/screens/stock_out/stock_out_list_screen.dart @@ -47,6 +47,14 @@ class _StockOutListScreenState extends ConsumerState { ColumnPrefs.load(_screenId).then((saved) { if (saved != null && mounted) setState(() => _hiddenCols = saved); }); + // 进入页面时把服务端状态过滤对齐到当前标签/下拉(provider 持久化,State 会重建) + WidgetsBinding.instance.addPostFrameCallback((_) { + if (!mounted) return; + final tab = ref.read(stockOutTabProvider); + final want = tab == 1 ? 'pending,draft' : _statusFilter; + final notifier = ref.read(stockOutListProvider.notifier); + if (notifier.currentStatus != want) notifier.setStatus(want); + }); } static const _colDefs = [ @@ -89,7 +97,13 @@ class _StockOutListScreenState extends ConsumerState { return PageScaffold( title: '出库管理', initialTab: ref.read(stockOutTabProvider), - onTabChanged: (i) => ref.read(stockOutTabProvider.notifier).state = i, + onTabChanged: (i) { + ref.read(stockOutTabProvider.notifier).state = i; + // 审核标签页按 pending+draft 服务端拉取;出库单页沿用下拉状态('' 为全部) + ref + .read(stockOutListProvider.notifier) + .setStatus(i == 1 ? 'pending,draft' : _statusFilter); + }, tabs: const [ Tab(text: '出库单'), Tab(text: '出库审核'), @@ -124,15 +138,19 @@ class _StockOutListScreenState extends ConsumerState { ), data: (result) { final allOrders = result.data; + // 状态过滤已改为服务端驱动(setStatus)。这里仅按标签做轻量显示守卫, + // 避免共用 provider 在标签切换、refetch 在途时短暂闪现他状态数据。 final List statusFiltered; if (filterStatus == 'pending') { + // 出库审核:服务端按 pending,draft 拉取 statusFiltered = allOrders .where((o) => o.status == 'draft' || o.status == 'pending') .toList(); } else if (filterStatus == 'exclude_pending') { - statusFiltered = allOrders - .where((o) => o.status != 'draft' && o.status != 'pending') - .toList(); + // 出库单:服务端按下拉状态拉取;'全部状态' 显示全部(含未审核) + statusFiltered = _statusFilter.isEmpty + ? allOrders + : allOrders.where((o) => o.status == _statusFilter).toList(); } else { statusFiltered = allOrders; } @@ -950,6 +968,7 @@ class _StatusFilterDropdown extends StatelessWidget { items: const [ DropdownMenuItem(value: '', child: Text('全部状态', style: TextStyle(fontSize: 13))), DropdownMenuItem(value: 'draft', child: Text('草稿', style: TextStyle(fontSize: 13))), + DropdownMenuItem(value: 'pending', child: Text('待审核', style: TextStyle(fontSize: 13))), DropdownMenuItem(value: 'approved', child: Text('已审核', style: TextStyle(fontSize: 13))), DropdownMenuItem(value: 'rejected', child: Text('已拒绝', style: TextStyle(fontSize: 13))), ],