'desc']; protected string|array $orderGuarantee = ['id' => 'desc']; protected array $withJoinTable = ['admin', 'channel', 'reviewAdmin']; protected function initController(WebmanRequest $request): ?Response { $this->model = new \app\common\model\AdminWithdrawOrder(); return null; } protected function _index(): Response { if ($this->request && $this->request->get('select')) { return $this->select($this->request); } list($where, $alias, $limit, $order) = $this->queryBuilder(); $table = strtolower($this->model->getTable()); $mainShort = $alias[$table] ?? ''; $scopedAdminIds = $this->getManageableScopeAdminIds(); if ($mainShort !== '' && $scopedAdminIds !== []) { $where[] = [$mainShort . '.admin_id', 'in', $scopedAdminIds]; } $res = $this->model ->withJoin($this->withJoinTable, $this->withJoinType) ->with($this->withJoinTable) ->visible([ 'admin' => ['username'], 'channel' => ['name'], 'reviewAdmin' => ['username'], ]) ->alias($alias) ->where($where) ->order($order) ->paginate($limit); $listArr = []; foreach ($res->items() as $item) { $row = is_array($item) ? $item : $item->toArray(); $row['can_review'] = $this->canReviewOrder($row) ? 1 : 0; $listArr[] = $row; } return $this->success('', [ 'list' => $listArr, 'total' => $res->total(), 'remark' => get_route_remark(), ]); } protected function _edit(): Response { $pk = $this->model->getPk(); $id = $this->request ? ($this->request->post($pk) ?? $this->request->get($pk)) : null; if ($id === null || $id === '') { return $this->error(__('Parameter error')); } if ($this->request && $this->request->method() === 'POST') { return $this->error(__('Please use the review action to process this order')); } $row = $this->loadWithRelations(intval(strval($id))); if (!$row) { return $this->error(__('Record not found')); } if (!$this->canReviewOrder($row)) { return $this->error(__('You have no permission')); } return $this->success('', ['row' => $row]); } /** * 审核(通过 / 拒绝) */ public function review(WebmanRequest $request): Response { $response = $this->initializeBackend($request); if ($response !== null) { return $response; } if ($request->method() !== 'POST') { return $this->error(__('Parameter error')); } $id = intval(strval($request->post('id', 0))); $action = strtolower(trim((string) $request->post('action', ''))); if ($id <= 0 || !in_array($action, ['approve', 'reject'], true)) { return $this->error(__('Parameter error')); } $remark = trim((string) $request->post('remark', '')); if ($action === 'reject' && $remark === '') { return $this->error(__('Please provide reject reason')); } $order = Db::name('admin_withdraw_order')->where('id', $id)->find(); if (!is_array($order)) { return $this->error(__('Record not found')); } if (!$this->canReviewOrder($order)) { return $this->error(__('You have no permission')); } if (intval($order['status'] ?? 0) !== 0) { return $this->error(__('This withdraw order has already been reviewed')); } Db::startTrans(); try { if ($action === 'approve') { AdminWalletService::approveWithdraw($order, intval($this->auth->id), $remark); } else { AdminWalletService::rejectWithdraw($order, intval($this->auth->id), $remark); } Db::commit(); } catch (Throwable $e) { Db::rollback(); return $this->error($e->getMessage()); } return $this->success($action === 'approve' ? __('Approved') : __('Rejected')); } public function stats(WebmanRequest $request): Response { $response = $this->initializeBackend($request); if ($response !== null) { return $response; } $query = Db::name('admin_withdraw_order'); $scopedAdminIds = $this->getManageableScopeAdminIds(); if ($scopedAdminIds !== []) { $query->where('admin_id', 'in', $scopedAdminIds); } $rows = $query->field(['status', 'amount', 'actual_amount'])->select()->toArray(); $total = count($rows); $pending = 0; $approved = 0; $rejected = 0; $totalAmount = '0.00'; $pendingAmount = '0.00'; $approvedAmount = '0.00'; foreach ($rows as $row) { $status = intval($row['status'] ?? 0); $amount = bcadd(strval($row['amount'] ?? '0'), '0', 2); $actual = bcadd(strval($row['actual_amount'] ?? '0'), '0', 2); $totalAmount = bcadd($totalAmount, $amount, 2); if ($status === 0) { $pending++; $pendingAmount = bcadd($pendingAmount, $amount, 2); } elseif ($status === 1) { $approved++; $approvedAmount = bcadd($approvedAmount, $actual, 2); } elseif ($status === 2) { $rejected++; } } return $this->success('', [ 'total_count' => $total, 'pending_count' => $pending, 'approved_count' => $approved, 'rejected_count' => $rejected, 'total_amount' => $totalAmount, 'pending_amount' => $pendingAmount, 'approved_amount' => $approvedAmount, ]); } private function loadWithRelations(int $id): ?array { $row = $this->model ->withJoin($this->withJoinTable, $this->withJoinType) ->with($this->withJoinTable) ->visible([ 'admin' => ['username'], 'channel' => ['name'], 'reviewAdmin' => ['username'], ]) ->where($this->model->getTable() . '.id', $id) ->find(); return $row ? $row->toArray() : null; } private function canReviewOrder(array $order): bool { if (!$this->auth || intval($order['status'] ?? 0) !== 0) { return false; } if (!$this->hasAdminWithdrawReviewPermission()) { return false; } $adminId = intval($order['admin_id'] ?? 0); if ($adminId <= 0) { return false; } $scopedAdminIds = $this->getManageableScopeAdminIds(); if ($scopedAdminIds === []) { return true; } return in_array($adminId, $scopedAdminIds, true); } private function hasAdminWithdrawReviewPermission(): bool { if (!$this->auth) { return false; } if ($this->auth->isSuperAdmin()) { return true; } foreach ($this->buildPermissionRoutePaths('order/adminWithdrawOrder', 'review') as $routePath) { if ($this->auth->check($routePath)) { return true; } } return false; } }