提现管理

This commit is contained in:
Leo_Ding 2026-01-13 17:24:29 +08:00
parent 3655207bfa
commit 0f00347a00
8 changed files with 223 additions and 459 deletions

View File

@ -28,3 +28,9 @@ export const CodeAuth=(params:any)=>request.put("/v1/auth/update_password_auth",
//提现
export const tixian=(params:any)=>request.put("/v1/balance/withdraw",params)
//充值记录
export const getUpList=(params:any)=>request.get("/v1/balance/top_up_list",{params})
//提现记录
export const getWithdrawList=(params:any)=>request.get("/v1/balance/withdraw_list",{params})

View File

@ -1,5 +1,5 @@
<template>
<div>
<div style="margin: 20px;">
<a-row :gutter="[16, 16]">
<a-col :span="24">
<a-card title="基本设置">

View File

@ -1,17 +1,17 @@
<template>
<div class="recharge-page">
<!-- 面包屑导航 -->
<a-breadcrumb class="breadcrumb">
<!-- <a-breadcrumb class="breadcrumb">
<a-breadcrumb-item>
<router-link to="/">首页</router-link>
</a-breadcrumb-item>
<a-breadcrumb-item>我的余额</a-breadcrumb-item>
</a-breadcrumb>
</a-breadcrumb> -->
<!-- 页面标题 -->
<div class="page-header">
<!-- <div class="page-header">
<h1 class="page-title">我的余额</h1>
</div>
</div> -->
<div class="main-content">
<!-- 余额和充值部分 -->
@ -22,40 +22,28 @@
<div class="balance-info">
<div class="balance-amount">
<div class="amount-label">账户余额</div>
<div class="amount-value">¥{{ formatCurrency(balance) }}</div>
<div class="amount-value">¥{{ formatCurrency(userInfo.balance || 0) }}</div>
</div>
</div>
</div>
<div class="recharge-content">
<!-- 充值金额选择 -->
<div class="recharge-section">
<h3 class="section-title">充值金额¥</h3>
<div class="amount-options">
<div
v-for="option in amountOptions"
:key="option.value"
<div v-for="option in amountOptions" :key="option.value"
:class="['amount-option', { 'selected': selectedAmount === option.value }]"
@click="selectAmount(option.value)"
>
@click="selectAmount(option.value)">
<div class="amount-number">¥{{ option.value }}</div>
</div>
</div>
</div>
<!-- 自定义金额输入 -->
<div class="recharge-section">
<h3 class="section-title">自定义充值金额</h3>
<div class="custom-amount">
<a-input
v-model:value="customAmount"
placeholder="请输入金额"
size="large"
:disabled="loading"
@change="handleCustomAmountChange"
>
<a-input v-model:value="customAmount" placeholder="请输入金额" size="large" :disabled="loading"
@change="handleCustomAmountChange">
<template #prefix>
<span class="input-prefix">¥</span>
</template>
@ -70,12 +58,9 @@
<div class="payment-methods-container">
<div class="payment-methods-title">充值方式</div>
<div class="payment-methods-row">
<div
v-for="method in paymentMethods"
:key="method.value"
<div v-for="method in paymentMethods" :key="method.value"
:class="['payment-method-item', { 'selected': selectedPaymentMethod === method.value }]"
@click="selectPaymentMethod(method.value)"
>
@click="selectPaymentMethod(method.value)">
<div class="method-icon">
<component :is="method.icon" />
</div>
@ -92,14 +77,8 @@
<!-- 操作按钮 -->
<div class="action-section">
<a-button
type="primary"
size="large"
:loading="loading"
:disabled="!canRecharge"
@click="handleRecharge"
class="recharge-btn"
>
<a-button type="primary" size="large" :loading="loading" :disabled="!canRecharge" @click="handleRecharge"
class="recharge-btn">
立即充值
</a-button>
</div>
@ -111,14 +90,12 @@
<a-card class="records-card" title="充值记录">
<!-- 筛选条件 -->
<div class="filter-section">
<a-range-picker
v-model:value="dateRange"
format="YYYY-MM-DD"
placeholder="开始时间 - 结束时间"
style="width: 300px; margin-right: 16px;"
/>
<a-range-picker v-model:value="dateRange" format="YYYY-MM-DD" placeholder="开始时间 - 结束时间"
style="width: 300px; margin-right: 16px;" />
<a-button type="primary" @click="handleSearch" :loading="searchLoading">
<template #icon><SearchOutlined /></template>
<template #icon>
<SearchOutlined />
</template>
查询
</a-button>
<a-button style="margin-left: 8px" @click="handleReset">
@ -128,15 +105,8 @@
<!-- 记录表格 -->
<div class="records-table">
<a-table
:columns="columns"
:data-source="rechargeRecords"
:pagination="pagination"
:loading="tableLoading"
@change="handleTableChange"
size="middle"
bordered
>
<a-table :columns="columns" :data-source="rechargeRecords" :pagination="pagination" :loading="tableLoading"
@change="handleTableChange" size="middle" bordered>
<template #bodyCell="{ column, record }">
<template v-if="column.key === 'amount'">
<span class="amount-cell">¥{{ record.amount }}</span>
@ -173,14 +143,8 @@
</div>
<!-- 充值确认模态框 -->
<a-modal
v-model:visible="rechargeModalVisible"
title="确认充值"
:confirm-loading="modalLoading"
@ok="handleRechargeConfirm"
@cancel="handleRechargeCancel"
centered
>
<a-modal v-model:visible="rechargeModalVisible" title="确认充值" :confirm-loading="modalLoading"
@ok="handleRechargeConfirm" @cancel="handleRechargeCancel" centered>
<div class="recharge-confirm">
<div class="confirm-item">
<span class="confirm-label">充值金额</span>
@ -192,11 +156,11 @@
</div>
<div class="confirm-item">
<span class="confirm-label">当前余额</span>
<span class="confirm-value">¥{{ formatCurrency(balance) }}</span>
<span class="confirm-value">¥{{ formatCurrency(userInfo.balance) }}</span>
</div>
<div class="confirm-item">
<span class="confirm-label">充值后余额</span>
<span class="confirm-value highlight">¥{{ formatCurrency(balance + selectedRechargeAmount) }}</span>
<span class="confirm-value highlight">¥{{ formatCurrency(userInfo.balance + selectedRechargeAmount) }}</span>
</div>
<div class="confirm-tips">
<InfoCircleOutlined />
@ -208,7 +172,7 @@
</template>
<script setup>
import { ref, reactive, computed, onMounted } from 'vue'
import { ref, reactive, computed, onMounted, } from 'vue'
import {
SearchOutlined,
CheckCircleFilled,
@ -219,9 +183,10 @@ import {
} from '@ant-design/icons-vue'
import { message } from 'ant-design-vue'
import dayjs from 'dayjs'
import { getUpList } from "@/apis/home"
//
const balance = ref(5.00)
const balance = ref(0)
//
const amountOptions = ref([
@ -248,7 +213,7 @@ const loading = ref(false)
const tableLoading = ref(false)
const searchLoading = ref(false)
const modalLoading = ref(false)
const userInfo = ref({})
//
const rechargeModalVisible = ref(false)
@ -362,6 +327,7 @@ const handleRecharge = () => {
//
const handleRechargeConfirm = () => {
modalLoading.value = true
setTimeout(() => {
balance.value += selectedRechargeAmount.value
const now = new Date()
@ -375,12 +341,10 @@ const handleRechargeConfirm = () => {
}
rechargeRecords.value.unshift(newRecord)
pagination.total += 1
//
selectedAmount.value = 0
customAmount.value = ''
customAmountError.value = ''
modalLoading.value = false
rechargeModalVisible.value = false
message.success(`充值成功!¥${selectedRechargeAmount.value} 已到账`)
@ -411,61 +375,33 @@ const viewDetail = (record) => {
message.info(`充值¥${record.amount},时间:${formatDateTime(record.rechargeTime)}`)
}
//
const loadRechargeRecords = () => {
tableLoading.value = true
setTimeout(() => {
const mockData = generateMockData(35)
let filtered = [...mockData]
if (dateRange.value?.length === 2) {
const start = dayjs(dateRange.value[0]).startOf('day')
const end = dayjs(dateRange.value[1]).endOf('day')
filtered = filtered.filter(r => {
const d = dayjs(r.rechargeTime)
return d.isAfter(start) && d.isBefore(end)
})
}
const startIdx = (pagination.current - 1) * pagination.pageSize
rechargeRecords.value = filtered.slice(startIdx, startIdx + pagination.pageSize)
pagination.total = filtered.length
tableLoading.value = false
searchLoading.value = false
}, 500)
}
//
const generateMockData = (count) => {
const methods = ['alipay', 'wechat', 'bank']
const statuses = ['success', 'processing', 'failed', 'pending']
let currentBalance = 5.00
const data = []
for (let i = 1; i <= count; i++) {
const amount = [100, 500, 1000, 5000][Math.floor(Math.random() * 4)]
const method = methods[Math.floor(Math.random() * methods.length)]
const status = statuses[Math.floor(Math.random() * statuses.length)]
if (status === 'success') currentBalance += amount
data.push({
key: i,
amount: amount,
rechargeTime: dayjs().subtract(Math.floor(Math.random() * 30), 'day').toDate(),
paymentMethod: method,
accountBalance: currentBalance,
status: status
})
const loadRechargeRecords = async () => {
try {
tableLoading.value = true
const params = {
start_at: dateRange.value[0],
end_at: dateRange.value[1],
page_num: pagination.current,
page_size: pagination.pageSize
}
const res = await getUpList(params)
rechargeRecords.value = res.data
pagination.total = res.total
tableLoading.value = false
} catch (error) {
tableLoading.value = false
}
return data.sort((a, b) => new Date(b.rechargeTime) - new Date(a.rechargeTime))
}
onMounted(() => {
rechargeRecords.value = generateMockData(15)
pagination.total = rechargeRecords.value.length
const userInfoStr = localStorage.getItem('userInfo');
if (userInfoStr) {
userInfo.value = JSON.parse(userInfoStr);
}
loadRechargeRecords()
})
</script>
@ -492,7 +428,7 @@ onMounted(() => {
}
.main-content {
max-width: 1200px;
/* max-width: 1200px; */
margin: 0 auto;
}
@ -609,9 +545,17 @@ onMounted(() => {
font-size: 18px;
}
.payment-method-item:nth-child(1) .method-icon { color: #1677ff; }
.payment-method-item:nth-child(2) .method-icon { color: #07c160; }
.payment-method-item:nth-child(3) .method-icon { color: #722ed1; }
.payment-method-item:nth-child(1) .method-icon {
color: #1677ff;
}
.payment-method-item:nth-child(2) .method-icon {
color: #07c160;
}
.payment-method-item:nth-child(3) .method-icon {
color: #722ed1;
}
.method-info {
flex: 1;

View File

@ -13,13 +13,8 @@
<div class="balance-desc">
当前可提现金额提现将在1-3个工作日内到账
</div>
<a-button
type="primary"
size="small"
class="w-full mt-4"
@click="showWithdrawalModal"
:disabled="accountInfo.availableBalance <= 0"
>
<a-button type="primary" class="w-full mt-4" @click="showWithdrawalModal"
:disabled="accountInfo.availableBalance <= 0">
去提现
</a-button>
</div>
@ -30,49 +25,17 @@
<!-- 提现记录查询 -->
<a-card title="提现记录" class="mb-6">
<template #extra>
<a-range-picker
v-model:value="searchParams.dateRange"
:format="dateFormat"
@change="handleDateChange"
/>
</template>
<!-- 查询条件 -->
<a-form layout="inline" :model="searchParams" class="mb-4">
<a-form-item label="提现单号">
<a-input
v-model:value="searchParams.orderNo"
placeholder="请输入提现单号"
@pressEnter="handleSearch"
/>
<a-input v-model:value="searchParams.orderNo" placeholder="请输入提现单号" @pressEnter="handleSearch" />
</a-form-item>
<a-form-item label="账户">
<a-select
v-model:value="searchParams.account"
placeholder="请选择账户"
style="width: 150px"
allowClear
>
<a-select-option v-for="account in accountOptions" :key="account.value">
{{ account.label }}
</a-select-option>
</a-select>
<a-form-item label="时间">
<a-range-picker v-model:value="searchParams.dateRange" :format="dateFormat" @change="handleDateChange" />
</a-form-item>
<a-form-item label="状态">
<a-select
v-model:value="searchParams.status"
placeholder="请选择状态"
style="width: 150px"
allowClear
>
<a-select-option value="pending">处理中</a-select-option>
<a-select-option value="success">成功</a-select-option>
<a-select-option value="failed">失败</a-select-option>
</a-select>
</a-form-item>
<a-form-item>
<a-button type="primary" @click="handleSearch">查询</a-button>
<a-button @click="handleReset" class="ml-2">重置</a-button>
@ -80,14 +43,8 @@
</a-form>
<!-- 提现记录表格 -->
<a-table
:columns="columns"
:data-source="withdrawalRecords"
:pagination="pagination"
@change="handleTableChange"
:loading="loading"
rowKey="id"
>
<a-table :columns="columns" :data-source="withdrawalRecords" :pagination="pagination" @change="handleTableChange"
:loading="loading" rowKey="id">
<template #bodyCell="{ column, record }">
<template v-if="column.key === 'amount'">
<span class="amount-cell">{{ formatCurrency(record.amount) }}</span>
@ -115,29 +72,14 @@
</a-card>
<!-- 提现弹窗 -->
<a-modal
v-model:visible="withdrawalModal.visible"
title="提现申请"
@ok="handleWithdrawalSubmit"
@cancel="handleWithdrawalCancel"
:confirm-loading="withdrawalModal.confirming"
>
<a-form
ref="withdrawalFormRef"
:model="withdrawalForm"
:rules="withdrawalRules"
layout="vertical"
>
<a-modal v-model:visible="withdrawalModal.visible" title="提现申请" @ok="handleWithdrawalSubmit"
@cancel="handleWithdrawalCancel" :confirm-loading="withdrawalModal.confirming">
<a-form ref="withdrawalFormRef" :model="withdrawalForm" :rules="withdrawalRules" layout="vertical">
<a-form-item label="提现金额" name="amount">
<a-input-number
v-model:value="withdrawalForm.amount"
placeholder="请输入提现金额"
:min="1"
:max="accountInfo.availableBalance"
style="width: 100%"
<a-input-number v-model:value="withdrawalForm.amount" placeholder="请输入提现金额" :min="1"
:max="accountInfo.availableBalance" style="width: 100%"
:formatter="value => `¥ ${value}`.replace(/\B(?=(\d{3})+(?!\d))/g, ',')"
:parser="value => value.replace(/¥\s?|(,*)/g, '')"
/>
:parser="value => value.replace(/¥\s?|(,*)/g, '')" />
<div class="amount-hint mt-2">
<div>可提现金额: {{ formatCurrency(accountInfo.availableBalance) }}</div>
<div>单笔最低提现: 1</div>
@ -145,23 +87,16 @@
</a-form-item>
<a-form-item label="提现到账账户" name="accountId">
<a-select
v-model:value="withdrawalForm.accountId"
placeholder="请选择提现账户"
>
<a-select v-model:value="withdrawalForm.accountId" placeholder="请选择提现账户">
<a-select-option :value="accountInfo.id">
{{ accountInfo.bank }} ({{ accountInfo.number }})
</a-select-option>
</a-select>
</a-form-item>
<a-alert
v-if="withdrawalForm.amount"
:message="`预计到账金额: ${formatCurrency(calculateActualAmount(withdrawalForm.amount))}元`"
type="info"
show-icon
class="mb-4"
/>
<a-alert v-if="withdrawalForm.amount"
:message="`预计到账金额: ${formatCurrency(calculateActualAmount(withdrawalForm.amount))}元`" type="info" show-icon
class="mb-4" />
</a-form>
</a-modal>
</div>
@ -171,7 +106,7 @@
import { ref, reactive, onMounted } from 'vue'
import { message } from 'ant-design-vue'
import dayjs from 'dayjs'
import { getWithdrawList } from "@/apis/home"
//
const accountInfo = reactive({
id: '1',
@ -294,51 +229,19 @@ onMounted(() => {
//
const fetchWithdrawalRecords = async () => {
loading.value = true
console.log(searchParams)
try {
// API
await new Promise(resolve => setTimeout(resolve, 500))
//
const mockData = Array.from({ length: 35 }, (_, index) => ({
id: index + 1,
orderNo: `TX${Date.now()}${index}`,
bank: ['工商银行', '建设银行', '农业银行'][index % 3],
accountNumber: `6228 **** **** ${1000 + index}`,
amount: Math.floor(Math.random() * 10000) + 100,
fee: Math.floor(Math.random() * 10),
status: ['pending', 'success', 'failed'][index % 3],
createdAt: dayjs().subtract(index, 'day').format('YYYY-MM-DD HH:mm:ss'),
completedAt: index % 3 !== 0 ? dayjs().subtract(index, 'day').add(1, 'hour').format('YYYY-MM-DD HH:mm:ss') : null
}))
//
let filteredData = mockData
if (searchParams.orderNo) {
filteredData = filteredData.filter(item => item.orderNo.includes(searchParams.orderNo))
let params = {
withdraw_number: searchParams.orderNo,
page_num: pagination.current,
page_size: pagination.pageSize,
start_at: formatDate(searchParams.dateRange[0]),
end_at: formatDate(searchParams.dateRange[1]),
}
if (searchParams.account) {
filteredData = filteredData.filter(item => item.accountNumber.endsWith(searchParams.account))
}
if (searchParams.status) {
filteredData = filteredData.filter(item => item.status === searchParams.status)
}
//
if (searchParams.dateRange && searchParams.dateRange[0] && searchParams.dateRange[1]) {
const start = searchParams.dateRange[0]
const end = searchParams.dateRange[1]
filteredData = filteredData.filter(item => {
const date = dayjs(item.createdAt)
return date.isAfter(start) && date.isBefore(end)
})
}
//
const start = (pagination.current - 1) * pagination.pageSize
const end = start + pagination.pageSize
withdrawalRecords.value = filteredData.slice(start, end)
pagination.total = filteredData.length
const res = await getWithdrawList(params)
console.log(res)
} catch (error) {
console.log(error)
message.error('获取提现记录失败')
} finally {
loading.value = false
@ -428,7 +331,7 @@ const formatCurrency = (amount) => {
//
const formatDate = (dateString) => {
return dayjs(dateString).format('YYYY-MM-DD HH:mm:ss')
return dayjs(dateString).format('YYYY-MM-DD')
}
//

View File

@ -10,7 +10,7 @@
<div class="money">¥ {{ formatAmount(userInfo.balance || 0) }}</div>
<div class="money-btn">
<div><a-button type="primary" size="small" @click="goToRecharge">充值</a-button></div>
<div><a-button size="small" @click="dialogWithDrawal = true">提现</a-button></div>
<div><a-button size="small" @click="router.push('/layout/admin/deposit')">提现</a-button></div>
</div>
</a-card>
</a-col>
@ -21,7 +21,8 @@
<a-card title="算力点" :bordered="false" class="card computing-card">
<div class="computing-content">
<div class="computing-amount">
<span class="amount-value">{{ '¥' + formatAmount(userInfo.computingPowerPoint || 0) }}</span>
<span class="amount-value">{{ '¥' + formatAmount(userInfo.computingPowerPoint || 0)
}}</span>
<!-- <span class="amount-unit"></span> -->
</div>
<div class="computing-actions">
@ -45,28 +46,25 @@
</a-col>
</a-row>
<!-- 底部账单区域 -->
<div class="bill-section">
<div class="bill-header">
<h3 class="bill-title">消费明细</h3>
</div>
<!-- 账单表格 -->
<a-table :columns="columns" :data-source="billData" :pagination="pagination" @change="handleTableChange"
:loading="loading" class="bill-table" :scroll="{ x: 1200 }">
<!-- 流水号列 -->
<!-- <div class="bill-section">
<a-tabs v-model:activeKey="activeKey">
<a-tab-pane key="1" tab="充值记录">
<a-table :columns="columns" :data-source="billData" :pagination="pagination"
@change="handleTableChange" :loading="loading" class="bill-table" :scroll="{ x: 1200 }">
<template #bodyCell="{ column, record }">
<template v-if="column.key === 'serialNumber'">
<span class="serial-number">{{ record.serialNumber }}</span>
</template>
<!-- 交易类型列 -->
<template v-else-if="column.key === 'transactionType'">
<a-tag :color="getTransactionTypeColor(record.transactionType)">
{{ record.transactionType }}
</a-tag>
</template>
<!-- 金额相关列 -->
<template
v-else-if="['transactionAmount', 'originalPrice', 'discountAmount', 'balancePayment', 'voucherDeduction'].includes(column.key)">
<span :class="{
@ -78,13 +76,17 @@
</template>
</template>
</a-table>
</div>
</a-tab-pane>
<a-tab-pane key="2" tab="提现记录">Content of Tab Pane 2</a-tab-pane>
</a-tabs>
</div> -->
</div>
<a-modal v-model:open="dialogWithDrawal" title="提现" @ok="handleOk">
<a-card>
<div style="display: flex;justify-content: flex-start;align-items: center;">
<span style="width: 120px;">提现金额</span>
<a-input-number id="inputNumber" v-model:value="withDrawalCount" placeholder="请输入提现金额" style="width: 100%;"/>
<a-input-number id="inputNumber" v-model:value="withDrawalCount" placeholder="请输入提现金额"
style="width: 100%;" />
<a-button type="link" @click="withDrawalCount = userInfo.balance" :loading="btnLoading">全部提现</a-button>
</div>
</a-card>
@ -99,6 +101,7 @@ import type { Dayjs } from 'dayjs'
import { tixian } from "@/apis/home"
import { fetchUserInfo } from '@/apis/modules/login';
const router = useRouter()
const activeKey = ref('1')
//
const btnLoading = ref(false)
const dialogWithDrawal = ref(false)
@ -132,66 +135,40 @@ const pagination = ref({
//
const columns = computed(() => [
{
title: '流水号',
dataIndex: 'serialNumber',
key: 'serialNumber',
title: '账户',
dataIndex: 'account',
key: 'account',
width: 180,
ellipsis: true
},
{
title: '交易时间',
dataIndex: 'transactionTime',
key: 'transactionTime',
title: '充值时间',
dataIndex: 'CreatedAt',
key: 'CreatedAt',
width: 170,
sorter: true
},
{
title: '交易类型',
dataIndex: 'transactionType',
key: 'transactionType',
title: '余额',
dataIndex: 'balance',
key: 'balance',
width: 120,
filters: [
{ text: '充值', value: '充值' },
{ text: '消费', value: '消费' },
{ text: '提现', value: '提现' },
{ text: '退款', value: '退款' }
]
},
{
title: '收支类型',
dataIndex: 'productName',
key: 'productName',
title: '支付方式',
dataIndex: 'payMethod',
key: 'payMethod',
width: 150,
ellipsis: true
},
{
title: '交易渠道',
dataIndex: 'transactionAmount',
key: 'transactionAmount',
title: '充值金额',
dataIndex: 'topUpAmount',
key: 'topUpAmount',
width: 120,
align: 'right'
align: 'left'
},
{
title: '交易金额',
dataIndex: 'transactionAmount',
key: 'transactionAmount',
width: 120,
align: 'right'
},
{
title: '账户余额',
dataIndex: 'balancePayment',
key: 'balancePayment',
width: 120,
align: 'right'
},
{
title: '备注',
dataIndex: 'voucherDeduction',
key: 'voucherDeduction',
width: 120,
align: 'right'
}
])
//
@ -245,94 +222,13 @@ const handleTableChange: TableProps['onChange'] = (pag, filters, sorter) => {
//
const fetchBillData = () => {
loading.value = true
// API
setTimeout(() => {
//
const mockData: BillRecord[] = [
{
key: '1',
serialNumber: 'TX202401010001',
transactionTime: '2024-01-01 10:30:25',
transactionType: '充值',
productName: '账户充值',
transactionAmount: 100.00,
originalPrice: 100.00,
discountAmount: 0.00,
balancePayment: 0.00,
voucherDeduction: 0.00
},
{
key: '2',
serialNumber: 'TX202401010002',
transactionTime: '2024-01-01 14:20:15',
transactionType: '消费',
productName: 'GPU算力服务',
transactionAmount: -50.00,
originalPrice: 60.00,
discountAmount: 10.00,
balancePayment: 40.00,
voucherDeduction: 10.00
},
{
key: '3',
serialNumber: 'TX202401020001',
transactionTime: '2024-01-02 09:15:30',
transactionType: '充值',
productName: '账户充值',
transactionAmount: 200.00,
originalPrice: 200.00,
discountAmount: 0.00,
balancePayment: 0.00,
voucherDeduction: 0.00
},
{
key: '4',
serialNumber: 'TX202401030001',
transactionTime: '2024-01-03 16:45:20',
transactionType: '消费',
productName: '存储空间',
transactionAmount: -30.00,
originalPrice: 30.00,
discountAmount: 0.00,
balancePayment: 30.00,
voucherDeduction: 0.00
},
{
key: '5',
serialNumber: 'TX202401040001',
transactionTime: '2024-01-04 11:10:05',
transactionType: '提现',
productName: '余额提现',
transactionAmount: -100.00,
originalPrice: 100.00,
discountAmount: 0.00,
balancePayment: 100.00,
voucherDeduction: 0.00
},
{
key: '6',
serialNumber: 'TX202401050001',
transactionTime: '2024-01-05 15:30:40',
transactionType: '退款',
productName: 'GPU算力服务',
transactionAmount: 25.00,
originalPrice: 25.00,
discountAmount: 0.00,
balancePayment: 0.00,
voucherDeduction: 0.00
}
]
billData.value = mockData
pagination.value.total = mockData.length
loading.value = false
}, 500)
}
//
const goToRecharge = () => {
router.push('/recharge')
router.push('/layout/admin/balance')
}
const goToBills = () => {

View File

@ -18,14 +18,14 @@
<div>
<p><span>认证类型</span>&nbsp;&nbsp;&nbsp;&nbsp;<span>{{ certificationInfo.certificationType }}</span></p>
<p><span>证件类型</span>&nbsp;&nbsp;&nbsp;&nbsp;<span></span><span>{{ certificationInfo.documentType }}</span></p>
<p><span>认证人</span>&nbsp;&nbsp;&nbsp;&nbsp;<span></span><span>{{ certificationInfo.name }}</span></p>
<p><span>认证人</span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<span></span><span>{{ certificationInfo.name }}</span></p>
<p>
<a-button type="primary" v-if="certificationInfo.certificationType==='个人认证'" @click="transOpen=true">变更为企业认证</a-button>
</p>
</div>
<div>
<p><span>认证时间</span><span>{{ certificationInfo.certificationTime }}</span></p>
<p><span>身份证号</span><span>{{ certificationInfo.idCard }}</span></p>
<p><span>认证时间</span>&nbsp;&nbsp;&nbsp;&nbsp;<span>{{ certificationInfo.certificationTime }}</span></p>
<p><span>身份证号</span>&nbsp;&nbsp;&nbsp;&nbsp;<span>{{ certificationInfo.idCard }}</span></p>
<!-- <p><span>认证人</span><span>用户名</span></p> -->
</div>
<div>

View File

@ -5,7 +5,7 @@
<!-- 左侧栏实例数据邀请好友 -->
<a-col :span="16">
<!-- 实例卡片 -->
<a-card title="GPU容器实例" :bordered="false" class="card">
<a-card title="GPU容器实例" class="card">
<a-row :gutter="32" align="middle">
<!-- 第一栏容器实例和运行中 -->
<a-col :span="18">
@ -43,7 +43,7 @@
<!-- 邀请好友卡片 -->
<a-card title="邀请好友得算力券" :bordered="false" class="card margin-top">
<a-card title="邀请好友得算力券" class="card margin-top">
<a-row :gutter="24" class="invite-container">
<!-- 左侧邀请信息和链接 -->
<a-col :span="24">
@ -95,7 +95,7 @@
<!-- 右侧栏用户信息 + 费用信息 -->
<a-col :span="8">
<!-- 费用信息卡片 -->
<a-card :bordered="false" class="card ">
<a-card class="card ">
<div class="fee-header">
<div class="fee-title">我的账号</div>
</div>
@ -174,10 +174,10 @@
</div>
</div>
</div>
<a-button type="link" class="view-coupons-btn" @click="goToCoupons">
<!-- <a-button type="link" class="view-coupons-btn" @click="goToCoupons">
查看全部权益
<RightOutlined style="font-size: 10px; margin-left: 2px;" />
</a-button>
</a-button> -->
</div>
</div>
@ -276,7 +276,7 @@ const goToRules = () => {
//
const goToRecharge = () => {
router.push('/recharge')
router.push('/layout/admin/balance')
}
//
@ -302,16 +302,11 @@ const goToInvoice = () => {
<style lang="scss" scoped>
.home-page {
padding: 15px;
margin: 20px;
background: #fff;
}
.card {
border-radius: 8px;
box-shadow: 0 2px 8px rgba(0, 0, 0, 0.1);
background: #fff;
margin-bottom: 20px;
}
.margin-top {
margin-top: 20px;

View File

@ -25,7 +25,7 @@
</template>
<script lang="ts" setup>
import { h, reactive, computed } from 'vue';
import { h, reactive, computed,watch } from 'vue';
import { useRouter } from 'vue-router';
import {
HomeOutlined,
@ -57,8 +57,8 @@ const menuItems: MenuItem[] = [
// { path: '/layout/admin/home', name: '', icon: HomeOutlined, visible: true },
{
path: '',
name: '费用',
path: '/fee',
name: '费用中心',
icon: MoneyCollectOutlined,
visible: true,
children: [
@ -78,13 +78,13 @@ const menuItems: MenuItem[] = [
],
},
{
path: '',
name: '账号',
path: '/account',
name: '我的账号',
icon: TeamOutlined,
visible: true,
children: [
{ path: '/layout/admin/security', name: '账号安全', visible: true },
{ path: '/layout/admin/history', name: '访问记录', visible: true },
// { path: '/layout/admin/security', name: '', visible: true },
// { path: '/layout/admin/history', name: '访', visible: true },
{ path: '/layout/admin/accountSet', name: '账户设置', visible: true },
{ path: '/layout/admin/realnameAuth', name: '实名认证', visible: true },
{ path: '/layout/admin/myCertificate', name: '我的算力券', visible: true },
@ -184,8 +184,28 @@ const items = computed(() => {
})
.filter(Boolean) as MenuItemType[];
});
watch(
() => router.currentRoute.value.path,
(currentPath) => {
//
state.selectedKeys = [currentPath];
//
const openKeys: string[] = [];
menuItems.forEach((item) => {
if (item.children && item.children.some(child => child.path === currentPath)) {
openKeys.push(item.path || ''); // key path key
}
});
state.openKeys = openKeys;
},
{ immediate: true } //
);
const handleMenuSelect = ({ key }: { key: string }) => {
//
if (key === '/fee' || key === '/account') {
return;
}
//
const allItems = flattenMenuItems(menuItems);
const targetItem = allItems.find(item => item.path === key);
@ -239,8 +259,8 @@ const changeTheme = (checked: boolean) => {
.admin-contain {
flex: 1;
padding: 20px;
/* padding: 20px; */
overflow-y: auto;
background-color: #f0f2f5;
background-color: #ffffff;
}
</style>