PaymentCenter/front/templates/payPage.html

403 lines
14 KiB
HTML
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

{{define "payPage.html"}}
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>收银台页面</title>
<style>
/* 基础样式 */
body {
font-family: Arial, sans-serif;
max-width: 800px;
margin: 0 auto;
padding: 20px;
}
/* 段落样式 */
p {
color: #666666;
margin-bottom: 10px;
}
/* 无序列表样式 */
ul {
list-style: none;
padding: 0;
}
/* 列表项样式 */
li {
margin: 10px 0;
display: flex;
align-items: center;
}
/* 按钮样式 */
button {
background-color: #007BFF;
color: #fff;
border: none;
padding: 10px 20px;
cursor: pointer;
transition: background-color 0.3s ease;
border-radius: 4px;
font-size: 16px;
margin-top: 20px;
}
/* 按钮悬停样式 */
button:hover {
background-color: #0056b3;
}
/* loading样式 */
.loading-container {
display: flex;
flex-direction: column;
align-items: center;
justify-content: center;
height: 200px;
}
.loading-spinner {
border: 5px solid #f3f3f3;
border-top: 5px solid #007BFF;
border-radius: 50%;
width: 50px;
height: 50px;
animation: spin 1s linear infinite;
margin-bottom: 20px;
}
@keyframes spin {
0% { transform: rotate(0deg); }
100% { transform: rotate(360deg); }
}
.loading-text {
color: #666;
font-size: 18px;
}
/* 支付信息卡片 */
.payment-info {
background: #f9f9f9;
padding: 20px;
border-radius: 8px;
margin-bottom: 20px;
}
.payment-info h2 {
margin-top: 0;
color: #333;
}
/* 支付方式选项 */
.payment-option {
padding: 15px;
border: 1px solid #ddd;
border-radius: 8px;
margin-bottom: 10px;
cursor: pointer;
transition: all 0.3s ease;
}
.payment-option:hover {
border-color: #007BFF;
background-color: #f0f7ff;
}
.payment-option input[type="radio"] {
margin-right: 15px;
}
/* 选中状态样式 */
.payment-option.selected {
border-color: #007BFF;
background-color: #f0f7ff;
}
</style>
</head>
{{if eq .code 200 }}
<body>
<!-- 页面内容 -->
<div class="payment-info">
<h2>订单支付</h2>
<p>{{.desc}}</p>
<p>交易号:{{ .id }}</p>
<p>交易金额:<strong style="color: #ff5500; font-size: 24px;">{{ .amount }}</strong></p>
</div>
<!-- 支付方式选择区域 -->
<div id="pay-container">
<div id="pay"></div>
<!-- 支付方式列表 -->
<ul id="payment-list"></ul>
<!-- Loading状态 -->
<div id="loading" class="loading-container" style="display: none;">
<div class="loading-spinner"></div>
<p class="loading-text">支付处理中,请稍候...</p>
</div>
</div>
</body>
<script>
// 从 URL 中提取参数
function getQueryParam(param) {
const queryString = window.location.search.substring(1);
const params = queryString.split('&');
for (let i = 0; i < params.length; i++) {
const [key, value] = params[i].split('=');
if (key === param) {
return decodeURIComponent(value);
}
}
return null;
}
// 检查是否是支付回调
function isPaymentCallback() {
return getQueryParam('callback') === 'true';
}
// 获取预设的支付方式
function getPresetPaymentMethod() {
return getQueryParam('preset_method') || null;
}
// 检查订单状态
function checkOrderStatus(orderNo) {
return fetch(`/pay/front/api/v1/payPage/status?no=${orderNo}`, {
method: 'GET',
})
.then(response => {
if (!response.ok) {
throw new Error('网络响应不正常');
}
return response.json();
})
.then(data => {
if (data.code !== 200) {
throw new Error(data.message || '获取订单状态失败');
}
return data;
});
}
// 显示Loading状态
function showLoading() {
document.getElementById('pay-container').style.display = 'none';
document.getElementById('loading').style.display = 'flex';
}
// 隐藏Loading状态
function hideLoading() {
document.getElementById('pay-container').style.display = 'block';
document.getElementById('loading').style.display = 'none';
}
// 处理支付回调
function handlePaymentCallback() {
const orderNo = getQueryParam('no');
if (!orderNo) {
console.error('订单号不存在');
return;
}
showLoading();
// 检查订单状态
checkOrderStatus(orderNo)
.then(data => {
if (data.data.status === 'SUCCESS') {
// 支付成功,跳转到指定链接
if (data.data.redirectUrl) {
setTimeout(() => {
window.location.href = data.data.redirectUrl;
}, 1000);
} else {
hideLoading();
alert('支付成功!');
}
} else if (data.data.status === 'PENDING') {
// 支付处理中1秒后再次检查
setTimeout(() => {
handlePaymentCallback();
}, 1000);
} else {
// 支付失败或其他状态
hideLoading();
alert('支付未完成: ' + (data.data.message || '未知错误'));
}
})
.catch(error => {
hideLoading();
console.error('检查订单状态失败:', error);
alert('检查订单状态失败: ' + error.message);
});
}
// 获取支付方式列表
function fetchPaymentMethods() {
const id = getQueryParam('no');
const presetMethod = getPresetPaymentMethod();
console.log('Order no:', id, 'Preset method:', presetMethod);
if (id) {
fetch(`/pay/front/api/v1/payPage/list?id=${id}`, {
method: 'POST',
})
.then(async response => {
if (response.ok) {
const data = await response.json()
console.log(data)
if (data.code !== 200) {
throw new Error('无效');
} else {
return data;
}
} else {
throw new Error('无效');
}
})
.then(data => {
// 处理返回的数据,例如渲染支付方式列表
if (data === null || data.data.length === 0) {
const pay = document.getElementById('pay');
pay.innerHTML = '<h3>支付环境异常,请检查</h3>';
} else if (data.data.length === 1) {
// 只有一个支付方式时,显示支付中状态并直接跳转
showLoading();
window.location.href = `/pay/front/api/v1/payPage/submit?pay_channel_id=${data.data[0].pay_channel_id}&no=${id}`;
} else {
renderPaymentMethods(data.data, presetMethod);
}
})
.catch(error => {
console.error('获取支付方式失败:', error);
const pay = document.getElementById('pay');
pay.innerHTML = '<h3 style="color: red;">获取支付方式失败,请刷新重试</h3>';
});
} else {
console.error('Order no not found in URL');
}
}
// 渲染支付方式列表
function renderPaymentMethods(paymentMethods, presetMethod) {
const pay = document.getElementById('pay');
pay.innerHTML = '<h3>请选择支付方式</h3>';
const paymentList = document.getElementById('payment-list');
paymentList.innerHTML = '';
let hasPresetMethod = false;
paymentMethods.forEach(method => {
const listItem = document.createElement('li');
listItem.className = 'payment-option';
const radioInput = document.createElement('input');
radioInput.type = 'radio';
radioInput.name = 'paymentMethod';
radioInput.value = method.pay_channel_id;
radioInput.id = `method-${method.pay_channel_id}`;
// 检查是否是预设的支付方式
if (presetMethod && (method.pay_channel_id === presetMethod || method.pay_name.includes(presetMethod))) {
radioInput.checked = true;
listItem.classList.add('selected');
hasPresetMethod = true;
}
const label = document.createElement('label');
label.htmlFor = `method-${method.pay_channel_id}`;
label.textContent = method.pay_name;
if (method.icon_url) {
const icon = document.createElement('img');
icon.src = method.icon_url;
icon.style.height = '24px';
icon.style.marginRight = '10px';
label.prepend(icon);
}
listItem.appendChild(radioInput);
listItem.appendChild(label);
paymentList.appendChild(listItem);
// 点击整个区域也可以选择
listItem.addEventListener('click', () => {
// 移除所有选中样式
document.querySelectorAll('.payment-option').forEach(item => {
item.classList.remove('selected');
});
// 添加当前选中样式
listItem.classList.add('selected');
radioInput.checked = true;
});
});
// 如果没有匹配的预设支付方式,默认选中第一个
if (!hasPresetMethod && paymentMethods.length > 0) {
const firstItem = document.querySelector('.payment-option');
if (firstItem) {
firstItem.classList.add('selected');
firstItem.querySelector('input[type="radio"]').checked = true;
}
}
// 添加提交按钮
const submitButton = document.createElement('button');
submitButton.type = 'button';
submitButton.textContent = '立即支付';
submitButton.onclick = function () {
const no = getQueryParam('no');
const selectedMethod = document.querySelector('input[name="paymentMethod"]:checked');
if (selectedMethod) {
showLoading();
window.location.href = `/pay/front/api/v1/payPage/submit?pay_channel_id=${selectedMethod.value}&no=${no}`;
} else {
alert('请选择支付方式');
}
};
const buttonContainer = document.createElement('div');
buttonContainer.style.textAlign = 'center';
buttonContainer.appendChild(submitButton);
paymentList.appendChild(buttonContainer);
}
// 页面加载时执行
window.onload = function() {
if (isPaymentCallback()) {
// 如果是支付回调,处理支付结果
handlePaymentCallback();
} else {
// 否则获取支付方式
fetchPaymentMethods();
}
};
</script>
{{ else}}
<body>
<div class="payment-info" style="text-align: center;">
<h2 style="color: #ff0000;">支付异常</h2>
<p>{{.message}}</p>
<button onclick="window.location.href='/'">返回首页</button>
</div>
</body>
{{end}}
</html>
{{end}}