264 lines
12 KiB
PHP
264 lines
12 KiB
PHP
<?php
|
|
session_start();
|
|
require_once 'includes/auth_helpers.php';
|
|
require_once 'db/config.php';
|
|
|
|
redirect_if_not_authenticated();
|
|
redirect_if_no_permission('manage_users');
|
|
|
|
$pdo = db();
|
|
$user = $_SESSION['user'];
|
|
|
|
// Handle POST requests for Create, Update, Delete
|
|
if ($_SERVER['REQUEST_METHOD'] === 'POST') {
|
|
$action = $_POST['action'] ?? '';
|
|
|
|
try {
|
|
if ($action === 'create_user') {
|
|
$username = $_POST['username'];
|
|
$password = $_POST['password'];
|
|
$role_id = $_POST['role_id'];
|
|
$hashed_password = password_hash($password, PASSWORD_DEFAULT);
|
|
|
|
$stmt = $pdo->prepare("INSERT INTO users (username, password, role_id) VALUES (?, ?, ?)");
|
|
$stmt->execute([$username, $hashed_password, $role_id]);
|
|
$_SESSION['flash_message'] = ['type' => 'success', 'message' => 'User created successfully.'];
|
|
}
|
|
|
|
if ($action === 'update_role') {
|
|
$user_id = $_POST['user_id'];
|
|
$role_id = $_POST['role_id'];
|
|
|
|
$stmt = $pdo->prepare("UPDATE users SET role_id = ? WHERE id = ?");
|
|
$stmt->execute([$role_id, $user_id]);
|
|
$_SESSION['flash_message'] = ['type' => 'success', 'message' => 'User role updated successfully.'];
|
|
}
|
|
|
|
if ($action === 'delete_user') {
|
|
$user_id = $_POST['user_id'];
|
|
|
|
// Prevent admin from deleting themselves
|
|
if ($user_id == get_user_id()) {
|
|
$_SESSION['flash_message'] = ['type' => 'danger', 'message' => 'You cannot delete your own account.'];
|
|
} else {
|
|
$stmt = $pdo->prepare("DELETE FROM users WHERE id = ?");
|
|
$stmt->execute([$user_id]);
|
|
$_SESSION['flash_message'] = ['type' => 'success', 'message' => 'User deleted successfully.'];
|
|
}
|
|
}
|
|
} catch (PDOException $e) {
|
|
$_SESSION['flash_message'] = ['type' => 'danger', 'message' => 'Database error: ' . $e->getMessage()];
|
|
}
|
|
|
|
header('Location: manage_users.php');
|
|
exit();
|
|
}
|
|
|
|
// Fetch all users and roles
|
|
$stmt_users = $pdo->query("SELECT u.id, u.username, r.name as role_name, u.created_at FROM users u JOIN roles r ON u.role_id = r.id ORDER BY u.created_at DESC");
|
|
$users_list = $stmt_users->fetchAll();
|
|
|
|
$stmt_roles = $pdo->query("SELECT id, name FROM roles ORDER BY name");
|
|
$roles = $stmt_roles->fetchAll();
|
|
|
|
?>
|
|
<!DOCTYPE html>
|
|
<html lang="en">
|
|
<head>
|
|
<meta charset="UTF-8">
|
|
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
|
<title>Manage Users</title>
|
|
<link href="https://cdn.jsdelivr.net/npm/bootstrap@5.3.2/dist/css/bootstrap.min.css" rel="stylesheet">
|
|
<link href="https://cdn.jsdelivr.net/npm/bootstrap-icons@1.11.3/font/bootstrap-icons.min.css" rel="stylesheet">
|
|
</head>
|
|
<body>
|
|
<nav class="navbar navbar-expand-lg navbar-dark bg-dark">
|
|
<div class="container-fluid">
|
|
<a class="navbar-brand" href="index.php"><i class="bi bi-person-vcard"></i> Customer Master</a>
|
|
<div class="collapse navbar-collapse">
|
|
<ul class="navbar-nav me-auto">
|
|
<li class="nav-item"><a class="nav-link" href="index.php">Dashboard</a></li>
|
|
<li class="nav-item"><a class="nav-link active" href="manage_users.php">Manage Users</a></li>
|
|
</ul>
|
|
<ul class="navbar-nav">
|
|
<li class="nav-item dropdown">
|
|
<a class="nav-link dropdown-toggle" href="#" data-bs-toggle="dropdown"><i class="bi bi-person-circle"></i> <?= htmlspecialchars($user['username']) ?></a>
|
|
<ul class="dropdown-menu dropdown-menu-end">
|
|
<li><a class="dropdown-item" href="logout.php">Logout</a></li>
|
|
</ul>
|
|
</li>
|
|
</ul>
|
|
</div>
|
|
</div>
|
|
</nav>
|
|
|
|
<main class="container mt-4">
|
|
<?php if (isset($_SESSION['flash_message'])): ?>
|
|
<div class="alert alert-<?= $_SESSION['flash_message']['type'] ?> alert-dismissible fade show" role="alert">
|
|
<?= $_SESSION['flash_message']['message'] ?>
|
|
<button type="button" class="btn-close" data-bs-dismiss="alert" aria-label="Close"></button>
|
|
</div>
|
|
<?php unset($_SESSION['flash_message']); ?>
|
|
<?php endif; ?>
|
|
|
|
<div class="d-flex justify-content-between align-items-center mb-3">
|
|
<h1 class="h3">Manage Users</h1>
|
|
<button class="btn btn-primary" data-bs-toggle="modal" data-bs-target="#createUserModal"><i class="bi bi-plus-circle"></i> Create User</button>
|
|
</div>
|
|
|
|
<div class="card">
|
|
<div class="card-body">
|
|
<table class="table table-striped">
|
|
<thead>
|
|
<tr>
|
|
<th>Username</th>
|
|
<th>Role</th>
|
|
<th>Created At</th>
|
|
<th>Actions</th>
|
|
</tr>
|
|
</thead>
|
|
<tbody>
|
|
<?php foreach ($users_list as $u): ?>
|
|
<tr>
|
|
<td><?= htmlspecialchars($u['username']) ?></td>
|
|
<td><?= htmlspecialchars($u['role_name']) ?></td>
|
|
<td><?= date('Y-m-d H:i', strtotime($u['created_at'])) ?></td>
|
|
<td>
|
|
<button class="btn btn-sm btn-outline-primary" data-bs-toggle="modal" data-bs-target="#editRoleModal" data-user-id="<?= $u['id'] ?>" data-user-role="<?= $u['role_name'] ?>">
|
|
<i class="bi bi-pencil-square"></i> Edit Role
|
|
</button>
|
|
<button class="btn btn-sm btn-outline-danger" data-bs-toggle="modal" data-bs-target="#deleteUserModal" data-user-id="<?= $u['id'] ?>">
|
|
<i class="bi bi-trash"></i> Delete
|
|
</button>
|
|
</td>
|
|
</tr>
|
|
<?php endforeach; ?>
|
|
</tbody>
|
|
</table>
|
|
</div>
|
|
</div>
|
|
</main>
|
|
|
|
<!-- Create User Modal -->
|
|
<div class="modal fade" id="createUserModal" tabindex="-1">
|
|
<div class="modal-dialog">
|
|
<div class="modal-content">
|
|
<form action="manage_users.php" method="POST">
|
|
<input type="hidden" name="action" value="create_user">
|
|
<div class="modal-header">
|
|
<h5 class="modal-title">Create New User</h5>
|
|
<button type="button" class="btn-close" data-bs-dismiss="modal"></button>
|
|
</div>
|
|
<div class="modal-body">
|
|
<div class="mb-3">
|
|
<label for="username" class="form-label">Username</label>
|
|
<input type="text" class="form-control" id="username" name="username" required>
|
|
</div>
|
|
<div class="mb-3">
|
|
<label for="password" class="form-label">Password</label>
|
|
<input type="password" class="form-control" id="password" name="password" required>
|
|
</div>
|
|
<div class="mb-3">
|
|
<label for="role_id" class="form-label">Role</label>
|
|
<select class="form-select" id="role_id" name="role_id" required>
|
|
<?php foreach ($roles as $role): ?>
|
|
<option value="<?= $role['id'] ?>"><?= htmlspecialchars($role['name']) ?></option>
|
|
<?php endforeach; ?>
|
|
</select>
|
|
</div>
|
|
</div>
|
|
<div class="modal-footer">
|
|
<button type="button" class="btn btn-secondary" data-bs-dismiss="modal">Close</button>
|
|
<button type="submit" class="btn btn-primary">Create User</button>
|
|
</div>
|
|
</form>
|
|
</div>
|
|
</div>
|
|
</div>
|
|
|
|
<!-- Edit Role Modal -->
|
|
<div class="modal fade" id="editRoleModal" tabindex="-1">
|
|
<div class="modal-dialog">
|
|
<div class="modal-content">
|
|
<form action="manage_users.php" method="POST">
|
|
<input type="hidden" name="action" value="update_role">
|
|
<input type="hidden" name="user_id" id="editUserId">
|
|
<div class="modal-header">
|
|
<h5 class="modal-title">Edit User Role</h5>
|
|
<button type="button" class="btn-close" data-bs-dismiss="modal"></button>
|
|
</div>
|
|
<div class="modal-body">
|
|
<div class="mb-3">
|
|
<label for="edit_role_id" class="form-label">Role</label>
|
|
<select class="form-select" id="edit_role_id" name="role_id" required>
|
|
<?php foreach ($roles as $role): ?>
|
|
<option value="<?= $role['id'] ?>"><?= htmlspecialchars($role['name']) ?></option>
|
|
<?php endforeach; ?>
|
|
</select>
|
|
</div>
|
|
</div>
|
|
<div class="modal-footer">
|
|
<button type="button" class="btn btn-secondary" data-bs-dismiss="modal">Close</button>
|
|
<button type="submit" class="btn btn-primary">Save Changes</button>
|
|
</div>
|
|
</form>
|
|
</div>
|
|
</div>
|
|
</div>
|
|
|
|
<!-- Delete User Modal -->
|
|
<div class="modal fade" id="deleteUserModal" tabindex="-1">
|
|
<div class="modal-dialog">
|
|
<div class="modal-content">
|
|
<form action="manage_users.php" method="POST">
|
|
<input type="hidden" name="action" value="delete_user">
|
|
<input type="hidden" name="user_id" id="deleteUserId">
|
|
<div class="modal-header">
|
|
<h5 class="modal-title">Confirm Deletion</h5>
|
|
<button type="button" class="btn-close" data-bs-dismiss="modal"></button>
|
|
</div>
|
|
<div class="modal-body">
|
|
<p>Are you sure you want to delete this user? This action cannot be undone.</p>
|
|
</div>
|
|
<div class="modal-footer">
|
|
<button type="button" class="btn btn-secondary" data-bs-dismiss="modal">Cancel</button>
|
|
<button type="submit" class="btn btn-danger">Delete User</button>
|
|
</div>
|
|
</form>
|
|
</div>
|
|
</div>
|
|
</div>
|
|
|
|
<script src="https://cdn.jsdelivr.net/npm/bootstrap@5.3.2/dist/js/bootstrap.bundle.min.js"></script>
|
|
<script>
|
|
// Script to handle modal data population
|
|
const editRoleModal = document.getElementById('editRoleModal');
|
|
editRoleModal.addEventListener('show.bs.modal', event => {
|
|
const button = event.relatedTarget;
|
|
const userId = button.getAttribute('data-user-id');
|
|
const userRole = button.getAttribute('data-user-role');
|
|
|
|
const modalUserIdInput = editRoleModal.querySelector('#editUserId');
|
|
const modalRoleSelect = editRoleModal.querySelector('#edit_role_id');
|
|
|
|
modalUserIdInput.value = userId;
|
|
|
|
// Select the correct role in the dropdown
|
|
for (let i = 0; i < modalRoleSelect.options.length; i++) {
|
|
if (modalRoleSelect.options[i].text === userRole) {
|
|
modalRoleSelect.selectedIndex = i;
|
|
break;
|
|
}
|
|
}
|
|
});
|
|
|
|
const deleteUserModal = document.getElementById('deleteUserModal');
|
|
deleteUserModal.addEventListener('show.bs.modal', event => {
|
|
const button = event.relatedTarget;
|
|
const userId = button.getAttribute('data-user-id');
|
|
const modalUserIdInput = deleteUserModal.querySelector('#deleteUserId');
|
|
modalUserIdInput.value = userId;
|
|
});
|
|
</script>
|
|
</body>
|
|
</html>
|