ensure_cap(); $this->render_header(__('创作分成', 'aksrt')); if (!class_exists('\AKSRT\Payment\Revenue')) { echo '

' . esc_html__('分成模块未初始化。', 'aksrt') . '

'; $this->render_footer(); return; } $status = isset($_GET['status']) ? sanitize_key((string) wp_unslash($_GET['status'])) : ''; $order_status = isset($_GET['order_status']) ? sanitize_key((string) wp_unslash($_GET['order_status'])) : ''; $user_id = isset($_GET['user_id']) ? max(0, (int) $_GET['user_id']) : 0; $post_id = isset($_GET['post_id']) ? max(0, (int) $_GET['post_id']) : 0; $currency = isset($_GET['currency']) ? strtolower(sanitize_key((string) wp_unslash($_GET['currency']))) : ''; if ($currency === 'cny') { $currency = 'CNY'; } $order_number = isset($_GET['order_number']) ? sanitize_text_field((string) wp_unslash($_GET['order_number'])) : ''; $date_from = isset($_GET['date_from']) ? sanitize_text_field((string) wp_unslash($_GET['date_from'])) : ''; $date_to = isset($_GET['date_to']) ? sanitize_text_field((string) wp_unslash($_GET['date_to'])) : ''; $page_num = max(1, (int) ($_GET['paged'] ?? 1)); $per_page = 20; $order_statuses = class_exists('\\AKSRT\\Payment\\Order') ? \AKSRT\Payment\Order::get_valid_statuses() : []; $svc = \AKSRT\Payment\Revenue::get_instance(); $stats = $user_id > 0 ? $svc->get_stats($user_id) : $svc->get_stats(); $cash_stats = (array) ($stats['cash'] ?? []); $points_stats = (array) ($stats['points'] ?? []); $cash_amount = static function ($value): string { try { return \AKSRT\Ledger\AssetAmount::balance(is_string($value) ? $value : '')->formatted(); } catch (\InvalidArgumentException $e) { return '0.00'; } }; echo '

' . esc_html(sprintf( __('现金:合计 ¥%1$s · 待结算 ¥%2$s · 已结算 ¥%3$s;积分:合计 %4$s · 待结算 %5$s · 已结算 %6$s', 'aksrt'), $cash_amount($cash_stats['total'] ?? '0'), $cash_amount($cash_stats['pending'] ?? '0'), $cash_amount($cash_stats['settled'] ?? '0'), number_format_i18n(max(0, (int) ($points_stats['total'] ?? 0))), number_format_i18n(max(0, (int) ($points_stats['pending'] ?? 0))), number_format_i18n(max(0, (int) ($points_stats['settled'] ?? 0))) )) . '

'; echo '
'; echo ''; echo ''; wp_nonce_field('aksrt_pay_batch_settle_income'); submit_button(__('批量结算选中记录', 'aksrt'), 'secondary', '', false); echo '
'; echo '
'; echo ''; echo ' '; echo ' '; echo ' '; echo ' '; echo ' '; echo ' '; echo ' — '; submit_button(__('筛选', 'aksrt'), 'secondary', '', false); if ($user_id > 0) { echo ' ' . esc_html__('清除用户过滤', 'aksrt') . ''; } echo '
'; $list_args = [ 'status' => $status, 'order_status' => $order_status, 'limit' => $per_page, 'offset' => ($page_num - 1) * $per_page, 'post_id' => $post_id, 'currency' => $currency, 'order_number' => $order_number, 'date_from' => $date_from, 'date_to' => $date_to, ]; if ($user_id > 0) { $list_args['user_id'] = $user_id; } $result = $svc->get_list($list_args); $items = $result['items'] ?? []; $total = (int) ($result['total'] ?? 0); $pages = max(1, (int) ($result['max_pages'] ?? 1)); echo ''; echo ''; echo ''; if (!$items) { echo ''; } foreach ($items as $row) { $id = (int) ($row['id'] ?? 0); $user_id = (int) ($row['author_id'] ?? 0); $user = $user_id > 0 ? get_userdata($user_id) : null; $st = (string) ($row['status'] ?? ''); echo ''; echo ''; echo ''; echo ''; $is_points = (string) ($row['currency'] ?? 'CNY') === 'points'; $row_currency = $is_points ? __('积分', 'aksrt') : '¥'; $row_amount = $is_points ? number_format_i18n(max(0, (int) ($row['amount'] ?? 0))) : $cash_amount($row['amount'] ?? '0'); echo ''; echo ''; echo ''; echo ''; } echo '
ID' . esc_html__('用户', 'aksrt') . '' . esc_html__('订单号', 'aksrt') . '' . esc_html__('金额', 'aksrt') . '' . esc_html__('状态', 'aksrt') . '' . esc_html__('时间', 'aksrt') . '' . esc_html__('操作', 'aksrt') . '
' . esc_html__('暂无分成记录', 'aksrt') . '
' . ($st === 'pending' ? '' : '') . '' . esc_html((string) $id) . '' . ($user ? esc_html($user->display_name) : esc_html((string) $user_id)) . '' . esc_html((string) ($row['order_number'] ?? '')) . '' . esc_html($row_amount . ' ' . $row_currency) . '' . esc_html($st) . '' . esc_html((string) ($row['created_at'] ?? '')) . ''; if ($st === 'pending') { echo '
'; echo ''; echo ''; echo ''; wp_nonce_field('aksrt_pay_settle_income_' . $id); submit_button(__('结算', 'aksrt'), 'small', '', false); echo '
'; } else { echo '—'; } echo '
'; $this->render_pagination($pages, $page_num); $this->render_footer(); } public function handle_settle_income(): void { if (!current_user_can(self::CAPABILITY)) { wp_die(esc_html__('权限不足', 'aksrt')); } $id = isset($_POST['revenue_id']) ? (int) $_POST['revenue_id'] : 0; check_admin_referer('aksrt_pay_settle_income_' . $id); $request_key = sanitize_text_field((string) wp_unslash($_POST['operation_key'] ?? '')); $operation_key = wp_is_uuid($request_key) ? \AKSRT\Ledger\OperationKey::deterministic('admin-revenue-settle', [get_current_user_id(), strtolower($request_key)]) : ''; $ok = $id > 0 && $operation_key !== '' && class_exists('\AKSRT\Payment\Revenue') && \AKSRT\Payment\Revenue::get_instance()->settle($id, get_current_user_id(), $operation_key); wp_safe_redirect($this->page_url('aksrt_income', ['aksrt_pay_msg' => $ok ? 'income_settled' : 'income_failed'])); exit; } public function handle_batch_settle_income(): void { if (!current_user_can(self::CAPABILITY)) { wp_die(esc_html__('权限不足', 'aksrt')); } check_admin_referer('aksrt_pay_batch_settle_income'); $raw_ids = isset($_POST['revenue_ids']) ? wp_unslash($_POST['revenue_ids']) : []; $ids = []; if (is_array($raw_ids)) { foreach ($raw_ids as $raw_id) { $id = (int) $raw_id; if ($id > 0) { $ids[] = $id; } } } $ids = array_values(array_unique($ids)); $request_key = sanitize_text_field((string) wp_unslash($_POST['operation_key'] ?? '')); $operation_key = wp_is_uuid($request_key) ? \AKSRT\Ledger\OperationKey::deterministic('admin-revenue-settle-batch', [get_current_user_id(), strtolower($request_key)]) : ''; $batch_result = !empty($ids) && $operation_key !== '' && class_exists('\\AKSRT\\Payment\\Revenue') ? \AKSRT\Payment\Revenue::get_instance()->settle_batch($ids, get_current_user_id(), $operation_key) : ['settled' => [], 'failed' => $ids]; $message = empty($batch_result['settled']) ? 'income_failed' : (!empty($batch_result['failed']) ? 'income_batch_partial' : 'income_batch_settled'); wp_safe_redirect($this->page_url('aksrt_income', ['aksrt_pay_msg' => $message])); exit; } private function ensure_cap(): void { if (!current_user_can(self::CAPABILITY)) { wp_die(esc_html__('您没有权限访问此页面。', 'aksrt')); } } private function render_header(string $title): void { echo '
'; echo '

' . esc_html($title) . '

'; $this->render_flash(); } private function render_footer(): void { echo '
'; } private function render_flash(): void { if (empty($_GET['aksrt_pay_msg'])) { return; } $code = sanitize_key((string) wp_unslash($_GET['aksrt_pay_msg'])); $map = [ 'income_settled' => __('分成已结算。', 'aksrt'), 'income_batch_settled' => __('选中分成已批量结算。', 'aksrt'), 'income_batch_partial' => __('部分分成已结算,失败记录可稍后重试。', 'aksrt'), 'income_failed' => __('分成结算失败。', 'aksrt'), ]; if (!isset($map[$code])) { return; } $class = $code === 'income_batch_partial' ? 'notice-warning' : (str_contains($code, 'failed') ? 'notice-error' : 'notice-success'); echo '

' . esc_html($map[$code]) . '

'; } private function page_url(string $slug, array $args = []): string { return add_query_arg(array_merge(['page' => $slug], $args), admin_url('admin.php')); } private function render_pagination(int $pages, int $page_num): void { if ($pages <= 1) { return; } echo '
'; echo paginate_links([ 'base' => add_query_arg('paged', '%#%'), 'format' => '', 'prev_text' => '«', 'next_text' => '»', 'total' => $pages, 'current' => $page_num, ]); echo '
'; } }