前言
默认大家已经看完前面章节并实现功能。这章完结所有功能,写完之后写MVC模式。
页面
创建templates/uesr_center.html
<!DOCTYPE html>
<html lang="zh">
<head>
<meta charset="UTF-8">
<title>个人中心</title>
<link rel="stylesheet" href="/public/css/user_center.css">
</head>
<body>
<h1>欢迎来到个人中心</h1>
<div id="user-info">
<h2>个人信息</h2>
<p>用户名:<span id="username"></span></p>
<p>最近登录时间:<span id="last_login_time"></span></p>
<p>最近登录IP:<span id="last_login_ip"></span></p>
<input type="text" id="new_username" placeholder="修改用户名">
<button onclick="updateUsername()">提交修改</button>
</div>
<div id="password-change">
<h2>修改密码</h2>
<input type="password" id="old_password" placeholder="旧密码"><br>
<input type="password" id="new_password" placeholder="新密码"><br>
<input type="password" id="confirm_password" placeholder="确认新密码"><br>
<button onclick="changePassword()">修改密码</button>
</div>
<div id="login-history">
<h2>登录记录</h2>
<table border="1">
<thead>
<tr>
<th>时间</th>
<th>IP</th>
</tr>
</thead>
<tbody id="history-table"></tbody>
</table>
</div>
<button onclick="logout()">退出登录</button>
<script src="/public/js/user_center.js"></script>
</body>
</html>
创建css文件public/css/user_center.css
body {
font-family: 'Segoe UI', Tahoma, Geneva, Verdana, sans-serif;
margin: 40px;
background-color: #f4f4f4;
color: #333;
}
h1 {
font-size: 28px;
margin-bottom: 20px;
}
h2 {
font-size: 22px;
margin-top: 30px;
margin-bottom: 10px;
border-bottom: 2px solid #ccc;
padding-bottom: 5px;
}
#user-info, #password-change, #login-history {
background: #fff;
padding: 20px;
margin-bottom: 30px;
border-radius: 8px;
box-shadow: 0 2px 8px rgba(0,0,0,0.1);
}
input[type="text"],
input[type="password"] {
padding: 10px;
width: 100%;
margin-bottom: 10px;
border-radius: 4px;
border: 1px solid #ccc;
box-sizing: border-box;
}
button {
padding: 10px 16px;
background-color: #007BFF;
color: white;
border: none;
border-radius: 4px;
cursor: pointer;
}
button:hover {
background-color: #0056b3;
}
table {
width: 100%;
border-collapse: collapse;
background-color: #fff;
}
table th, table td {
padding: 10px;
border: 1px solid #ccc;
text-align: left;
}
table th {
background-color: #f0f0f0;
}
创建js文件public/js/user_center.js
document.addEventListener('DOMContentLoaded', () => {
fetch('/api/user.php')
.then(res => res.json())
.then(data => {
if (!data.success) {
alert(data.message);
window.location.href = '/login';
return;
}
const { user, history } = data;
document.getElementById('username').textContent = user.username;
document.getElementById('last_login_time').textContent = user.last_login_time;
document.getElementById('last_login_ip').textContent = user.last_login_ip;
const tbody = document.getElementById('history-table');
history.forEach(entry => {
const row = document.createElement('tr');
row.innerHTML = `<td>${entry.login_time}</td><td>${entry.ip_address}</td>`;
tbody.appendChild(row);
});
});
});
function updateUsername() {
const newUsername = document.getElementById('new_username').value;
if (!newUsername) return alert('请输入新用户名');
fetch('/api/user.php', {
method: 'POST',
headers: {'Content-Type': 'application/json'},
body: JSON.stringify({ action: 'update_username', username: newUsername })
})
.then(res => res.json())
.then(data => {
alert(data.message);
if (data.success) location.reload();
});
}
function changePassword() {
const oldPwd = document.getElementById('old_password').value;
const newPwd = document.getElementById('new_password').value;
const confirmPwd = document.getElementById('confirm_password').value;
if (!oldPwd || !newPwd || newPwd !== confirmPwd) {
alert('请正确填写所有密码字段');
return;
}
fetch('/api/change_password.php', {
method: 'POST',
headers: { 'Content-Type': 'application/json' },
body: JSON.stringify({ old_password: oldPwd, new_password: newPwd })
})
.then(res => res.json())
.then(data => {
alert(data.message);
if (data.success) window.location.href = '/logout';
});
}
function logout() {
fetch('/api/logout.php')
.then(() => window.location.href = '/login');
}
后端php
创建文件api/user.php
<?php
require_once '../func/db.class.php';
require_once '../func/auth.php';
require_once '../func/utils.php';
session_start();
header('Content-Type: application/json');
if (!isAuthenticated()) {
echo json_encode(['success' => false, 'message' => '未登录']);
exit;
}
$db = new Db();
$userId = getCurrentUserId();
// 修改用户名
if ($_SERVER['REQUEST_METHOD'] === 'POST') {
$input = json_decode(file_get_contents("php://input"), true);
if (isset($input['action']) && $input['action'] === 'update_username') {
$newUsername = trim($input['username']);
if (!$newUsername) {
echo json_encode(['success' => false, 'message' => '用户名不能为空']);
exit;
}
$exists = $db->query("SELECT id FROM users WHERE username = ? AND id != ?", [$newUsername, $userId]);
if ($exists) {
echo json_encode(['success' => false, 'message' => '用户名已存在']);
exit;
}
$db->update('users', ['username' => $newUsername], ['id' => $userId]);
$_SESSION['username'] = $newUsername;
echo json_encode(['success' => true, 'message' => '用户名更新成功']);
exit;
}
}
// 获取用户信息
$user = $db->query("SELECT username, last_login_ip, last_login_time FROM users WHERE id = ?", [$userId])[0];
$history = $db->query("SELECT login_time, ip_address FROM login_history WHERE user_id = ? ORDER BY login_time DESC LIMIT 10", [$userId]);
echo json_encode([
'success' => true,
'user' => $user,
'history' => $history
]);
到这里用户中心OK。先测试一下。测试的时候可以删除seesion直接登录这个页面看看能不能访问。
我这里是直接返回json。其实我这里少写了功能。404页面和错误跳转,我都是alert来直接替代了。
这些个功能到MVC模式的时候再来添加了。
言归正传,修改用户名已经写在了uesr.php
。补上两个功能,退出登录和修改密码
创建api/change_passsword.php
<?php
require_once '../func/db.class.php';
require_once '../func/auth.php';
require_once '../func/utils.php';
session_start();
header('Content-Type: application/json');
// 检查是否登录
if (!isAuthenticated()) {
echo json_encode(['success' => false, 'message' => '未登录']);
exit;
}
$input = json_decode(file_get_contents("php://input"), true);
$oldPwd = $input['old_password'] ?? '';
$newPwd = $input['new_password'] ?? '';
if (!$oldPwd || !$newPwd) {
echo json_encode(['success' => false, 'message' => '密码不能为空']);
exit;
}
if (strlen($newPwd) < 6) {
echo json_encode(['success' => false, 'message' => '密码长度不足6位']);
exit;
}
$db = new Db();
$userId = getCurrentUserId();
// 获取当前用户的密码哈希
$user = $db->query("SELECT password FROM users WHERE id = ?", [$userId]);
if (!$user) {
echo json_encode(['success' => false, 'message' => '用户不存在']);
exit;
}
$hash = $user[0]['password'];
if (!password_verify($oldPwd, $hash)) {
echo json_encode(['success' => false, 'message' => '原密码错误']);
exit;
}
// 更新密码(使用 password_hash 重新加密)
$newHash = password_hash($newPwd, PASSWORD_DEFAULT);
$db->update('users', ['password' => $newHash], ['id' => $userId]);
echo json_encode(['success' => true, 'message' => '密码修改成功']);
创建api/logout.php
<?php
require_once '../func/auth.php';
session_start();
logoutUser();
echo json_encode(['success' => true, 'message' => '退出登录成功']);
OKK!完结咯。下一个项目大家再见咯。