Implement orders tab aligned with Android, including scan verify flows.

Add role-based order/deposit lists, AVFoundation QR scanning, verify dialogs, and ViewModel tests so photographers, scenic admins, and store admins match Android behavior.

Co-authored-by: Cursor <cursoragent@cursor.com>
This commit is contained in:
2026-07-06 16:59:53 +08:00
parent 6492f80ef0
commit 31d2b6094b
27 changed files with 4226 additions and 17 deletions

View File

@ -0,0 +1,64 @@
//
// DepositOrderListViewModelTests.swift
// suixinkanTests
//
import XCTest
@testable import suixinkan
@MainActor
final class DepositOrderListViewModelTests: XCTestCase {
override func tearDown() {
AppStore.shared.currentStoreId = 0
AppStore.shared.currentScenicId = 0
super.tearDown()
}
func testStoreFilterMapsPaidStatusToAPI20() {
XCTAssertEqual(DepositOrderListViewModel.apiOrderStatus(forTabIndex: 18), 20)
XCTAssertEqual(DepositOrderListViewModel.apiOrderStatus(forTabIndex: 30), 30)
XCTAssertNil(DepositOrderListViewModel.apiOrderStatus(forTabIndex: 0))
}
func testStoreFilterLabelUsesPaidText() {
let viewModel = DepositOrderListViewModel()
viewModel.onFilterChange(tab: 18)
XCTAssertEqual(viewModel.filterLabel, "已支付")
}
func testPhoneValidation() {
XCTAssertTrue(DepositOrderListViewModel.isValidPhone("13800138000"))
XCTAssertFalse(DepositOrderListViewModel.isValidPhone("12345"))
XCTAssertFalse(DepositOrderListViewModel.isValidPhone("23800138000"))
}
func testStoreIdZeroAbortsWithMessage() async {
AppStore.shared.currentStoreId = 0
let viewModel = DepositOrderListViewModel()
var message: String?
viewModel.onShowMessage = { message = $0 }
let session = MockURLSession(responses: [])
let api = OrderAPI(client: APIClient(environment: .testing, session: session))
await viewModel.refreshOrderList(api: api)
XCTAssertTrue(viewModel.orderList.isEmpty)
XCTAssertEqual(message, "店铺信息异常,请先选择店铺")
}
func testCanOpenDetailOnlyForType19() throws {
let viewModel = DepositOrderListViewModel()
let json = """
{"order_number":"A","order_type":19,"order_status":20}
""".data(using: .utf8)!
let item = try JSONDecoder().decode(StoreOrderItem.self, from: json)
XCTAssertTrue(viewModel.canOpenDetail(for: item))
let otherJSON = """
{"order_number":"B","order_type":4,"order_status":20}
""".data(using: .utf8)!
let other = try JSONDecoder().decode(StoreOrderItem.self, from: otherJSON)
XCTAssertFalse(viewModel.canOpenDetail(for: other))
}
}