Files
FlashSaleSystem/src/main/webapp/WEB-INF/views/admin/flashsales.jsp

892 lines
35 KiB
Plaintext
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.
<%@ page contentType="text/html;charset=UTF-8" language="java" %>
<%@ taglib prefix="c" uri="http://java.sun.com/jsp/jstl/core" %>
<%@ taglib prefix="fn" uri="http://flashsale.org/functions" %>
<c:set var="pageTitle" value="秒杀管理"/>
<%@ include file="../common/header.jsp" %>
<div class="container-fluid">
<div class="row">
<!-- 侧边栏 -->
<nav class="col-md-3 col-lg-2 d-md-block bg-light sidebar">
<div class="position-sticky pt-3">
<h6 class="sidebar-heading d-flex justify-content-between align-items-center px-3 mt-4 mb-1 text-muted">
<span>管理功能</span>
</h6>
<ul class="nav flex-column">
<li class="nav-item">
<a class="nav-link" href="${pageContext.request.contextPath}/admin">
<i class="fas fa-tachometer-alt"></i> 仪表盘
</a>
</li>
<li class="nav-item">
<a class="nav-link" href="${pageContext.request.contextPath}/admin/products">
<i class="fas fa-box"></i> 商品管理
</a>
</li>
<li class="nav-item">
<a class="nav-link active" href="${pageContext.request.contextPath}/admin/flashsales">
<i class="fas fa-bolt"></i> 秒杀管理
</a>
</li>
<li class="nav-item">
<a class="nav-link" href="${pageContext.request.contextPath}/admin/orders">
<i class="fas fa-shopping-cart"></i> 订单管理
</a>
</li>
<li class="nav-item">
<a class="nav-link" href="${pageContext.request.contextPath}/admin/users">
<i class="fas fa-users"></i> 用户管理
</a>
</li>
<li class="nav-item">
<a class="nav-link" href="${pageContext.request.contextPath}/admin/monitor">
<i class="fas fa-chart-line"></i> 系统监控
</a>
</li>
</ul>
</div>
</nav>
<!-- 主内容区域 -->
<main class="col-md-9 ms-sm-auto col-lg-10 px-md-4">
<div class="d-flex justify-content-between flex-wrap flex-md-nowrap align-items-center pt-3 pb-2 mb-3 border-bottom">
<h1 class="h2">秒杀管理</h1>
<div class="btn-toolbar mb-2 mb-md-0">
<div class="btn-group me-2">
<button type="button" class="btn btn-sm btn-primary" data-bs-toggle="modal"
data-bs-target="#addFlashSaleModal">
<i class="fas fa-plus"></i> 创建秒杀
</button>
<button type="button" class="btn btn-sm btn-outline-secondary" onclick="refreshFlashSales()">
<i class="fas fa-sync-alt"></i> 刷新
</button>
</div>
</div>
</div>
<!-- 筛选和搜索 -->
<div class="row mb-3">
<div class="col-md-4">
<div class="input-group">
<input type="text" class="form-control" id="searchInput" placeholder="搜索秒杀活动...">
<button class="btn btn-outline-secondary" type="button" onclick="searchFlashSales()">
<i class="fas fa-search"></i>
</button>
</div>
</div>
<div class="col-md-2">
<select class="form-select" id="statusFilter" onchange="filterFlashSales()">
<option value="">全部状态</option>
<option value="pending">未开始</option>
<option value="active">进行中</option>
<option value="ended">已结束</option>
</select>
</div>
<div class="col-md-2">
<select class="form-select" id="sortBy" onchange="sortFlashSales()">
<option value="startTime">按开始时间</option>
<option value="endTime">按结束时间</option>
<option value="createdAt">按创建时间</option>
</select>
</div>
</div>
<!-- 秒杀活动列表 -->
<div class="card">
<div class="card-body">
<div class="table-responsive">
<table class="table table-striped table-hover">
<thead>
<tr>
<th>ID</th>
<th>活动名称</th>
<th>商品</th>
<th>原价/秒杀价</th>
<th>库存</th>
<th>开始时间</th>
<th>结束时间</th>
<th>状态</th>
<th>操作</th>
</tr>
</thead>
<tbody id="flashSalesTableBody">
<tr>
<td colspan="9" class="text-center">
<i class="fas fa-spinner fa-spin"></i> 加载中...
</td>
</tr>
</tbody>
</table>
</div>
<!-- 分页 -->
<nav aria-label="秒杀分页">
<ul class="pagination justify-content-center" id="pagination">
<!-- 分页按钮将通过JavaScript生成 -->
</ul>
</nav>
</div>
</div>
</main>
</div>
</div>
<!-- 创建秒杀模态框 -->
<div class="modal fade" id="addFlashSaleModal" tabindex="-1">
<div class="modal-dialog modal-lg">
<div class="modal-content">
<div class="modal-header">
<h5 class="modal-title">创建秒杀活动</h5>
<button type="button" class="btn-close" data-bs-dismiss="modal"></button>
</div>
<div class="modal-body">
<form id="addFlashSaleForm">
<div class="row">
<div class="col-md-12">
<div class="mb-3">
<label for="productSelect" class="form-label">选择商品 *</label>
<select class="form-select" id="productSelect" required>
<option value="">请选择商品</option>
</select>
</div>
</div>
</div>
<div class="row">
<div class="col-md-6">
<div class="mb-3">
<label for="flashSalePrice" class="form-label">秒杀价格 *</label>
<div class="input-group">
<span class="input-group-text">¥</span>
<input type="number" class="form-control" id="flashSalePrice" step="0.01" min="0"
required>
</div>
</div>
</div>
<div class="col-md-6">
<div class="mb-3">
<label for="flashSaleStock" class="form-label">秒杀库存 *</label>
<input type="number" class="form-control" id="flashSaleStock" min="1" required>
</div>
</div>
</div>
<div class="row">
<div class="col-md-6">
<div class="mb-3">
<label for="startTime" class="form-label">开始时间 *</label>
<input type="datetime-local" class="form-control" id="startTime" required>
</div>
</div>
<div class="col-md-6">
<div class="mb-3">
<label for="endTime" class="form-label">结束时间 *</label>
<input type="datetime-local" class="form-control" id="endTime" required>
</div>
</div>
</div>
</form>
</div>
<div class="modal-footer">
<button type="button" class="btn btn-secondary" data-bs-dismiss="modal">取消</button>
<button type="button" class="btn btn-primary" onclick="saveFlashSale()">创建活动</button>
</div>
</div>
</div>
</div>
<!-- 查看详情模态框 -->
<div class="modal fade" id="viewFlashSaleModal" tabindex="-1">
<div class="modal-dialog modal-lg">
<div class="modal-content">
<div class="modal-header">
<h5 class="modal-title">秒杀活动详情</h5>
<button type="button" class="btn-close" data-bs-dismiss="modal"></button>
</div>
<div class="modal-body">
<div class="row">
<div class="col-md-6">
<div class="mb-3">
<label class="form-label fw-bold">活动ID</label>
<p id="viewFlashSaleId" class="form-control-plaintext">-</p>
</div>
</div>
<div class="col-md-6">
<div class="mb-3">
<label class="form-label fw-bold">商品名称</label>
<p id="viewProductName" class="form-control-plaintext">-</p>
</div>
</div>
</div>
<div class="row">
<div class="col-md-6">
<div class="mb-3">
<label class="form-label fw-bold">原价</label>
<p id="viewOriginalPrice" class="form-control-plaintext">-</p>
</div>
</div>
<div class="col-md-6">
<div class="mb-3">
<label class="form-label fw-bold">秒杀价</label>
<p id="viewFlashPrice" class="form-control-plaintext text-danger fw-bold">-</p>
</div>
</div>
</div>
<div class="row">
<div class="col-md-6">
<div class="mb-3">
<label class="form-label fw-bold">总库存</label>
<p id="viewFlashStock" class="form-control-plaintext">-</p>
</div>
</div>
<div class="col-md-6">
<div class="mb-3">
<label class="form-label fw-bold">剩余库存</label>
<p id="viewRemainingStock" class="form-control-plaintext">-</p>
</div>
</div>
</div>
<div class="row">
<div class="col-md-6">
<div class="mb-3">
<label class="form-label fw-bold">开始时间</label>
<p id="viewStartTime" class="form-control-plaintext">-</p>
</div>
</div>
<div class="col-md-6">
<div class="mb-3">
<label class="form-label fw-bold">结束时间</label>
<p id="viewEndTime" class="form-control-plaintext">-</p>
</div>
</div>
</div>
<div class="row">
<div class="col-md-6">
<div class="mb-3">
<label class="form-label fw-bold">活动状态</label>
<p id="viewStatus" class="form-control-plaintext">-</p>
</div>
</div>
<div class="col-md-6">
<div class="mb-3">
<label class="form-label fw-bold">创建时间</label>
<p id="viewCreatedAt" class="form-control-plaintext">-</p>
</div>
</div>
</div>
</div>
<div class="modal-footer">
<button type="button" class="btn btn-secondary" data-bs-dismiss="modal">关闭</button>
</div>
</div>
</div>
</div>
<!-- 编辑秒杀模态框 -->
<div class="modal fade" id="editFlashSaleModal" tabindex="-1">
<div class="modal-dialog modal-lg">
<div class="modal-content">
<div class="modal-header">
<h5 class="modal-title">编辑秒杀活动</h5>
<button type="button" class="btn-close" data-bs-dismiss="modal"></button>
</div>
<div class="modal-body">
<form id="editFlashSaleForm">
<input type="hidden" id="editFlashSaleId">
<div class="row">
<div class="col-md-6">
<div class="mb-3">
<label for="editFlashPrice" class="form-label">秒杀价格 *</label>
<div class="input-group">
<span class="input-group-text">¥</span>
<input type="number" class="form-control" id="editFlashPrice" step="0.01" min="0"
required>
</div>
</div>
</div>
<div class="col-md-6">
<div class="mb-3">
<label for="editFlashStock" class="form-label">秒杀库存 *</label>
<input type="number" class="form-control" id="editFlashStock" min="1" required>
</div>
</div>
</div>
<div class="row">
<div class="col-md-6">
<div class="mb-3">
<label for="editStartTime" class="form-label">开始时间 *</label>
<input type="datetime-local" class="form-control" id="editStartTime" required>
</div>
</div>
<div class="col-md-6">
<div class="mb-3">
<label for="editEndTime" class="form-label">结束时间 *</label>
<input type="datetime-local" class="form-control" id="editEndTime" required>
</div>
</div>
</div>
</form>
</div>
<div class="modal-footer">
<button type="button" class="btn btn-secondary" data-bs-dismiss="modal">取消</button>
<button type="button" class="btn btn-primary" onclick="saveEditFlashSale()">保存修改</button>
</div>
</div>
</div>
</div>
<style>
.sidebar {
position: fixed;
top: 56px;
bottom: 0;
left: 0;
z-index: 100;
padding: 48px 0 0;
box-shadow: inset -1px 0 0 rgba(0, 0, 0, .1);
}
.sidebar .nav-link {
font-weight: 500;
color: #333;
}
.sidebar .nav-link.active {
color: #007bff;
}
main {
margin-left: 240px;
}
@media (max-width: 768px) {
main {
margin-left: 0;
}
.sidebar {
position: relative;
top: 0;
}
}
.status-pending {
color: #ffc107;
}
.status-active {
color: #28a745;
}
.status-ended {
color: #6c757d;
}
</style>
<script>
let currentPage = 1;
let pageSize = 10;
let totalPages = 1;
$(document).ready(function () {
loadFlashSales();
loadProducts();
// 设置默认时间
const now = new Date();
const tomorrow = new Date(now.getTime() + 24 * 60 * 60 * 1000);
$('#startTime').val(formatDateTime(now));
$('#endTime').val(formatDateTime(tomorrow));
});
function formatDateTime(date) {
const year = date.getFullYear();
const month = String(date.getMonth() + 1).padStart(2, '0');
const day = String(date.getDate()).padStart(2, '0');
const hours = String(date.getHours()).padStart(2, '0');
const minutes = String(date.getMinutes()).padStart(2, '0');
return year + '-' + month + '-' + day + 'T' + hours + ':' + minutes;
}
function loadProducts() {
// 获取商品列表用于下拉框
$.ajax({
url: '${pageContext.request.contextPath}/api/admin/products',
type: 'GET',
data: {
page: 1,
size: 100, // 获取足够多的商品
status: 1 // 只获取上架的商品
},
success: function (response) {
if (response.success && response.data) {
const products = response.data.content || response.data.products || [];
let options = '<option value="">请选择商品</option>';
products.forEach(product => {
options += `<option value="${product.id}">${product.name} - ¥${product.price}</option>`;
});
$('#productSelect').html(options);
} else {
console.error('获取商品列表失败:', response.message);
}
},
error: function (xhr, status, error) {
console.error('获取商品列表失败:', error);
}
});
}
function loadFlashSales(page = 1) {
currentPage = page;
// 显示加载状态
$('#flashSalesTableBody').html('<tr><td colspan="9" class="text-center"><i class="fas fa-spinner fa-spin"></i> 加载中...</td></tr>');
// 构建查询参数
const queryData = {
page: page - 1, // 后端使用0基索引
size: pageSize,
sortBy: $('#sortBy').val() || 'startTime',
sortDirection: 'desc'
};
// 添加状态筛选
const statusFilter = $('#statusFilter').val();
if (statusFilter) {
// 将前端状态值转换为后端状态值
switch (statusFilter) {
case 'pending':
queryData.status = 1; // 未开始
break;
case 'active':
queryData.status = 2; // 进行中
break;
case 'ended':
queryData.status = 3; // 已结束
break;
}
}
// 调用真实API
$.ajax({
url: '${pageContext.request.contextPath}/api/flashsale/list',
type: 'POST',
contentType: 'application/json',
data: JSON.stringify(queryData),
success: function (response) {
if (response.success) {
renderFlashSalesTable(response.data.content || response.data.flashSales || []);
renderPagination(response.data.totalElements || response.data.total || 0, pageSize);
} else {
$('#flashSalesTableBody').html('<tr><td colspan="9" class="text-center text-danger">获取秒杀数据失败: ' + response.message + '</td></tr>');
}
},
error: function (xhr, status, error) {
console.error('获取秒杀列表失败:', error);
$('#flashSalesTableBody').html('<tr><td colspan="9" class="text-center text-danger">网络请求失败,请稍后重试</td></tr>');
}
});
}
function renderFlashSalesTable(flashSales) {
let html = '';
if (flashSales.length === 0) {
html = '<tr><td colspan="9" class="text-center">暂无秒杀活动</td></tr>';
} else {
flashSales.forEach(flashSale => {
const statusText = getStatusText(flashSale.status);
const statusClass = getStatusClass(flashSale.status);
html += `
<tr>
<td>` + flashSale.id + `</td>
<td>
<div class="fw-bold">` + (flashSale.productName || '秒杀活动') + `</div>
<small class="text-muted">` + (flashSale.statusDescription || '') + `</small>
</td>
<td>` + (flashSale.productName || '-') + `</td>
<td>
<div>原价: ¥` + (flashSale.originalPrice ? flashSale.originalPrice.toFixed(2) : '0.00') + `</div>
<div class="text-danger fw-bold">秒杀: ¥` + (flashSale.flashPrice ? flashSale.flashPrice.toFixed(2) : '0.00') + `</div>
</td>
<td>
<span class="badge ` + (flashSale.remainingStock > 0 ? 'bg-success' : 'bg-danger') + `">
` + (flashSale.remainingStock || 0) + ` / ` + (flashSale.flashStock || 0) + `
</span>
</td>
<td>` + formatDateTime(flashSale.startTime) + `</td>
<td>` + formatDateTime(flashSale.endTime) + `</td>
<td>
<span class="badge ` + statusClass + `">
` + statusText + `
</span>
</td>
<td>
<div class="btn-group btn-group-sm">
<button class="btn btn-outline-primary" onclick="editFlashSale(` + flashSale.id + `)" title="编辑">
<i class="fas fa-edit"></i>
</button>
<button class="btn btn-outline-danger" onclick="deleteFlashSale(` + flashSale.id + `)" title="删除">
<i class="fas fa-trash"></i>
</button>
<button class="btn btn-outline-info" onclick="viewFlashSale(` + flashSale.id + `)" title="查看">
<i class="fas fa-eye"></i>
</button>
</div>
</td>
</tr>
`;
});
}
$('#flashSalesTableBody').html(html);
}
function getStatusText(status) {
switch (status) {
case 1:
return '未开始';
case 2:
return '进行中';
case 3:
return '已结束';
default:
return '未知';
}
}
function getStatusClass(status) {
switch (status) {
case 1:
return 'bg-warning'; // 未开始
case 2:
return 'bg-success'; // 进行中
case 3:
return 'bg-secondary'; // 已结束
default:
return 'bg-secondary';
}
}
function renderPagination(total, pageSize) {
totalPages = Math.ceil(total / pageSize);
let html = '';
if (totalPages <= 1) {
$('#pagination').html('');
return;
}
// 上一页
html += `
<li class="page-item ` + (currentPage === 1 ? 'disabled' : '') + `">
<a class="page-link" href="#" onclick="loadFlashSales(` + (currentPage - 1) + `)">上一页</a>
</li>
`;
// 页码
for (let i = 1; i <= totalPages; i++) {
html += `
<li class="page-item ` + (i === currentPage ? 'active' : '') + `">
<a class="page-link" href="#" onclick="loadFlashSales(` + i + `)">` + i + `</a>
</li>
`;
}
// 下一页
html += `
<li class="page-item ` + (currentPage === totalPages ? 'disabled' : '') + `">
<a class="page-link" href="#" onclick="loadFlashSales(` + (currentPage + 1) + `)">下一页</a>
</li>
`;
$('#pagination').html(html);
}
function refreshFlashSales() {
$('#flashSalesTableBody').html('<tr><td colspan="9" class="text-center"><i class="fas fa-spinner fa-spin"></i> 加载中...</td></tr>');
loadFlashSales(currentPage);
}
function searchFlashSales() {
const keyword = $('#searchInput').val();
console.log('搜索秒杀活动:', keyword);
// 重置到第一页并重新加载
loadFlashSales(1);
}
function filterFlashSales() {
const status = $('#statusFilter').val();
console.log('筛选状态:', status);
// 重置到第一页并重新加载
loadFlashSales(1);
}
function sortFlashSales() {
const sortBy = $('#sortBy').val();
console.log('排序方式:', sortBy);
// 重置到第一页并重新加载
loadFlashSales(1);
}
function saveFlashSale() {
// 验证表单
if (!$('#productSelect').val()) {
alert('请选择商品');
return;
}
if (!$('#flashSalePrice').val()) {
alert('请输入秒杀价格');
return;
}
if (!$('#flashSaleStock').val()) {
alert('请输入秒杀库存');
return;
}
if (!$('#startTime').val() || !$('#endTime').val()) {
alert('请选择开始和结束时间');
return;
}
const flashSaleData = {
productId: parseInt($('#productSelect').val()),
flashPrice: parseFloat($('#flashSalePrice').val()),
flashStock: parseInt($('#flashSaleStock').val()),
startTime: $('#startTime').val().replace('T', ' ') + ':00',
endTime: $('#endTime').val().replace('T', ' ') + ':00'
};
console.log('创建秒杀活动:', flashSaleData);
// 调用真实API
$.ajax({
url: '${pageContext.request.contextPath}/api/flashsale/create',
type: 'POST',
contentType: 'application/json',
data: JSON.stringify(flashSaleData),
success: function (response) {
if (response.success) {
$('#addFlashSaleModal').modal('hide');
$('#addFlashSaleForm')[0].reset();
alert('秒杀活动创建成功!');
refreshFlashSales();
} else {
alert('创建失败: ' + response.message);
}
},
error: function (xhr, status, error) {
console.error('创建秒杀活动失败:', error);
alert('创建失败,请稍后重试');
}
});
}
function editFlashSale(id) {
console.log('编辑秒杀活动:', id);
// 获取秒杀活动详情
$.ajax({
url: '${pageContext.request.contextPath}/api/flashsale/' + id,
type: 'GET',
success: function (response) {
if (response.success) {
const flashSale = response.data;
// 检查是否可以编辑(只有未开始的活动才能编辑)
if (flashSale.status !== 1) {
alert('只有未开始的秒杀活动才能编辑');
return;
}
// 填充编辑表单
$('#editFlashSaleId').val(flashSale.id);
$('#editFlashPrice').val(flashSale.flashPrice);
$('#editFlashStock').val(flashSale.flashStock);
$('#editStartTime').val(formatDateTimeForInput(flashSale.startTime));
$('#editEndTime').val(formatDateTimeForInput(flashSale.endTime));
// 显示编辑模态框
$('#editFlashSaleModal').modal('show');
} else {
alert('获取秒杀活动详情失败: ' + response.message);
}
},
error: function () {
alert('获取秒杀活动详情失败,请稍后重试');
}
});
}
function deleteFlashSale(id) {
if (confirm('确定要删除这个秒杀活动吗?此操作不可恢复。')) {
console.log('删除秒杀活动:', id);
$.ajax({
url: '${pageContext.request.contextPath}/api/flashsale/' + id,
type: 'DELETE',
success: function (response) {
if (response.success) {
alert('秒杀活动删除成功!');
refreshFlashSales();
} else {
alert('删除失败: ' + response.message);
}
},
error: function (xhr) {
let errorMessage = '删除失败,请稍后重试';
if (xhr.responseJSON && xhr.responseJSON.message) {
errorMessage = xhr.responseJSON.message;
}
alert(errorMessage);
}
});
}
}
function viewFlashSale(id) {
console.log('查看秒杀详情:', id);
// 获取秒杀活动详情
$.ajax({
url: '${pageContext.request.contextPath}/api/flashsale/' + id,
type: 'GET',
success: function (response) {
if (response.success) {
const flashSale = response.data;
// 填充详情模态框
$('#viewFlashSaleId').text(flashSale.id);
$('#viewProductName').text(flashSale.productName || '-');
$('#viewOriginalPrice').text(flashSale.originalPrice ? '¥' + flashSale.originalPrice.toFixed(2) : '-');
$('#viewFlashPrice').text(flashSale.flashPrice ? '¥' + flashSale.flashPrice.toFixed(2) : '-');
$('#viewFlashStock').text(flashSale.flashStock || '-');
$('#viewRemainingStock').text(flashSale.remainingStock || '-');
$('#viewStartTime').text(formatDateTime(flashSale.startTime));
$('#viewEndTime').text(formatDateTime(flashSale.endTime));
$('#viewStatus').html('<span class="badge ' + getStatusClass(flashSale.status) + '">' + getStatusText(flashSale.status) + '</span>');
$('#viewCreatedAt').text(formatDateTime(flashSale.createdAt));
// 显示详情模态框
$('#viewFlashSaleModal').modal('show');
} else {
alert('获取秒杀活动详情失败: ' + response.message);
}
},
error: function () {
alert('获取秒杀活动详情失败,请稍后重试');
}
});
}
// 保存编辑的秒杀活动
function saveEditFlashSale() {
// 验证表单
if (!$('#editFlashPrice').val()) {
alert('请输入秒杀价格');
return;
}
if (!$('#editFlashStock').val()) {
alert('请输入秒杀库存');
return;
}
if (!$('#editStartTime').val() || !$('#editEndTime').val()) {
alert('请选择开始和结束时间');
return;
}
const flashSaleId = $('#editFlashSaleId').val();
const updateData = {
flashPrice: parseFloat($('#editFlashPrice').val()),
flashStock: parseInt($('#editFlashStock').val()),
startTime: $('#editStartTime').val().replace('T', ' ') + ':00',
endTime: $('#editEndTime').val().replace('T', ' ') + ':00'
};
// 验证时间
const startTime = new Date($('#editStartTime').val());
const endTime = new Date($('#editEndTime').val());
const now = new Date();
if (startTime < now) {
alert('开始时间不能早于当前时间');
return;
}
if (startTime >= endTime) {
alert('开始时间不能晚于或等于结束时间');
return;
}
console.log('更新秒杀活动:', updateData);
// 调用更新API
$.ajax({
url: '${pageContext.request.contextPath}/api/flashsale/' + flashSaleId,
type: 'PUT',
contentType: 'application/json',
data: JSON.stringify(updateData),
success: function (response) {
if (response.success) {
$('#editFlashSaleModal').modal('hide');
alert('秒杀活动更新成功!');
refreshFlashSales();
} else {
alert('更新失败: ' + response.message);
}
},
error: function (xhr) {
let errorMessage = '更新失败,请稍后重试';
if (xhr.responseJSON && xhr.responseJSON.message) {
errorMessage = xhr.responseJSON.message;
}
alert(errorMessage);
}
});
}
// 工具函数
function formatDateTime(dateTimeStr) {
if (!dateTimeStr) return '-';
// 如果是ISO格式转换为本地时间显示
try {
const date = new Date(dateTimeStr);
return date.toLocaleString('zh-CN', {
year: 'numeric',
month: '2-digit',
day: '2-digit',
hour: '2-digit',
minute: '2-digit',
second: '2-digit'
});
} catch (e) {
return dateTimeStr; // 如果转换失败,返回原字符串
}
}
// 格式化日期时间用于input[type="datetime-local"]
function formatDateTimeForInput(dateTimeStr) {
if (!dateTimeStr) return '';
try {
const date = new Date(dateTimeStr);
const year = date.getFullYear();
const month = String(date.getMonth() + 1).padStart(2, '0');
const day = String(date.getDate()).padStart(2, '0');
const hours = String(date.getHours()).padStart(2, '0');
const minutes = String(date.getMinutes()).padStart(2, '0');
return year + '-' + month + '-' + day + 'T' + hours + ':' + minutes;
} catch (e) {
return '';
}
}
</script>
<%@ include file="../common/footer.jsp" %>