Sindbad~EG File Manager
<?php
session_start();
require_once __DIR__ . '/../config/database.php';
require_once __DIR__ . '/../includes/functions.php';
if (!isset($_SESSION['user_id'])) {
header('Location: ../login.php');
exit();
}
// Check permission for user management
error_log("Checking permissions for user management");
if (!function_exists('checkPermission')) {
error_log("FATAL: checkPermission function does not exist");
die("Required function checkPermission not found");
}
if (!checkPermission('admin') && $_SESSION['user_level'] !== 'superuser') {
error_log("Access denied for user: " . $_SESSION['user_id']);
header('Location: ' . $_SESSION['user_level'] . '.php?error=access_denied');
exit();
}
error_log("Permission check passed");
$page_title = 'User Management';
$page_description = 'Manage system users and permissions';
$success_message = '';
$error_message = '';
// Handle success message from redirect
if (isset($_GET['success'])) {
$success_message = $_GET['success'];
}
// Test database connection
if (!$db) {
$error_message = 'Database connection failed. Please check your database configuration.';
error_log("Database connection is null in user-management.php");
}
// Handle user actions
if ($_POST) {
error_log("POST request received with data: " . json_encode($_POST));
error_log("Checking for create_user parameter...");
error_log("create_user isset: " . (isset($_POST['create_user']) ? 'YES' : 'NO'));
// Check if this is a user creation request (has the required fields)
if (isset($_POST['first_name']) && isset($_POST['last_name']) && isset($_POST['username']) && isset($_POST['email']) && isset($_POST['user_level']) && isset($_POST['user_role'])) {
error_log("User creation form detected (has all required fields)");
// Check if functions exist BEFORE using them
if (!function_exists('sanitizeInput')) {
error_log("FATAL: sanitizeInput function does not exist");
die("Required function sanitizeInput not found");
}
if (!function_exists('generateRandomPassword')) {
error_log("FATAL: generateRandomPassword function does not exist");
die("Required function generateRandomPassword not found");
}
error_log("All required functions exist - proceeding");
// Immediate database connection test
try {
if (!$db) {
error_log("FATAL: Database connection is NULL");
die("Database connection failed");
}
$test = $db->query("SELECT 1");
if ($test) {
error_log("Database connection test PASSED");
} else {
error_log("Database connection test FAILED");
}
} catch (Exception $e) {
error_log("Database connection exception: " . $e->getMessage());
die("Database error: " . $e->getMessage());
}
error_log("About to sanitize input data");
$username = sanitizeInput($_POST['username']);
$email = sanitizeInput($_POST['email']);
$first_name = sanitizeInput($_POST['first_name']);
$last_name = sanitizeInput($_POST['last_name']);
$user_level = sanitizeInput($_POST['user_level']);
$user_role = sanitizeInput($_POST['user_role']);
$area_id = !empty($_POST['area_id']) ? (int)$_POST['area_id'] : null;
$district_id = !empty($_POST['district_id']) ? (int)$_POST['district_id'] : null;
$assembly_id = !empty($_POST['assembly_id']) ? (int)$_POST['assembly_id'] : null;
// Check if required functions exist
error_log("Checking required functions...");
if (!function_exists('generateRandomPassword')) {
error_log("generateRandomPassword function does not exist");
$error_message = 'System error: Required function missing.';
} else {
error_log("generateRandomPassword function exists");
$password = generateRandomPassword();
error_log("Generated password: " . $password);
}
if (!function_exists('sanitizeInput')) {
error_log("sanitizeInput function does not exist");
$error_message = 'System error: sanitizeInput function missing.';
} else {
error_log("sanitizeInput function exists");
}
// Debug: Log the form data
error_log("Create user form submitted with data: " . json_encode($_POST));
error_log("Processed data - Username: $username, Email: $email, First: $first_name, Last: $last_name, Level: $user_level, Role: $user_role");
// Enhanced validation with better debugging (only if no function errors)
if (empty($error_message)) {
$validation_errors = [];
if (empty($username)) $validation_errors[] = "username is empty";
if (empty($email)) $validation_errors[] = "email is empty";
if (empty($first_name)) $validation_errors[] = "first_name is empty";
if (empty($last_name)) $validation_errors[] = "last_name is empty";
if (empty($user_level)) $validation_errors[] = "user_level is empty";
if (empty($user_role)) $validation_errors[] = "user_role is empty";
if (!empty($validation_errors)) {
$error_message = 'Please fill in all required fields: ' . implode(', ', $validation_errors);
error_log("Validation failed: " . implode(', ', $validation_errors));
error_log("Raw POST data: " . print_r($_POST, true));
}
}
if (empty($error_message)) {
error_log("Validation passed, proceeding with user creation");
// Skip complex checks for now - direct insertion test
if (!$db) {
error_log("CRITICAL: Database connection is null");
$error_message = 'Database connection failed';
} else {
error_log("Database connection is valid");
}
// Test database connection and table structure
try {
// Test basic connection
$test_connection = "SELECT 1 as test";
$test_conn_stmt = $db->prepare($test_connection);
$test_conn_stmt->execute();
$conn_result = $test_conn_stmt->fetch();
error_log("Database connection test result: " . json_encode($conn_result));
// Check current database
$current_db_query = "SELECT DATABASE() as current_db";
$current_db_stmt = $db->prepare($current_db_query);
$current_db_stmt->execute();
$current_db = $current_db_stmt->fetch();
error_log("Current database: " . json_encode($current_db));
// Check if users table exists
$table_exists_query = "SHOW TABLES LIKE 'users'";
$table_exists_stmt = $db->prepare($table_exists_query);
$table_exists_stmt->execute();
$table_exists = $table_exists_stmt->fetch();
error_log("Users table exists: " . ($table_exists ? 'YES' : 'NO'));
if ($table_exists) {
// Get table structure
$test_query = "DESCRIBE users";
$test_stmt = $db->prepare($test_query);
$test_stmt->execute();
$table_structure = $test_stmt->fetchAll(PDO::FETCH_ASSOC);
error_log("Users table structure: " . json_encode($table_structure));
// Count existing users
$count_query = "SELECT COUNT(*) as user_count FROM users";
$count_stmt = $db->prepare($count_query);
$count_stmt->execute();
$user_count = $count_stmt->fetch();
error_log("Current user count: " . json_encode($user_count));
} else {
error_log("ERROR: Users table does not exist!");
$error_message = 'Database error: Users table does not exist. Please run the <a href="../setup.php" class="text-blue-600 underline">setup script</a> first.';
}
} catch (Exception $e) {
error_log("Error checking database/table: " . $e->getMessage());
$error_message = 'Database connection error: ' . $e->getMessage();
}
// Only proceed if database connection and table checks passed
if (empty($error_message)) {
// Check if username or email already exists
$check_query = "SELECT id FROM users WHERE username = :username OR email = :email";
$check_stmt = $db->prepare($check_query);
$check_stmt->bindParam(':username', $username);
$check_stmt->bindParam(':email', $email);
$check_stmt->execute();
if ($check_stmt->rowCount() > 0) {
$error_message = 'Username or email already exists.';
error_log("User creation failed: Username or email already exists");
} else {
error_log("Username/email check passed - proceeding with insertion");
}
}
if (empty($error_message)) {
$password_hash = password_hash($password, PASSWORD_DEFAULT);
$insert_query = "INSERT INTO users (username, email, password_hash, first_name, last_name, user_level, user_role, area_id, district_id, assembly_id)
VALUES (:username, :email, :password_hash, :first_name, :last_name, :user_level, :user_role, :area_id, :district_id, :assembly_id)";
error_log("Attempting to insert user with query: $insert_query");
error_log("Values: username=$username, email=$email, first_name=$first_name, last_name=$last_name, user_level=$user_level, user_role=$user_role, area_id=$area_id, district_id=$district_id, assembly_id=$assembly_id");
$insert_stmt = $db->prepare($insert_query);
$insert_stmt->bindParam(':username', $username);
$insert_stmt->bindParam(':email', $email);
$insert_stmt->bindParam(':password_hash', $password_hash);
$insert_stmt->bindParam(':first_name', $first_name);
$insert_stmt->bindParam(':last_name', $last_name);
$insert_stmt->bindParam(':user_level', $user_level);
$insert_stmt->bindParam(':user_role', $user_role);
$insert_stmt->bindParam(':area_id', $area_id);
$insert_stmt->bindParam(':district_id', $district_id);
$insert_stmt->bindParam(':assembly_id', $assembly_id);
try {
error_log("About to execute INSERT statement");
$execution_result = $insert_stmt->execute();
error_log("INSERT execution result: " . ($execution_result ? 'TRUE' : 'FALSE'));
if ($execution_result) {
$user_id = $db->lastInsertId();
error_log("User created successfully with ID: $user_id");
// Verify the user was actually inserted
$verify_query = "SELECT id, username, email FROM users WHERE id = :user_id";
$verify_stmt = $db->prepare($verify_query);
$verify_stmt->bindParam(':user_id', $user_id);
$verify_stmt->execute();
$inserted_user = $verify_stmt->fetch(PDO::FETCH_ASSOC);
if ($inserted_user) {
error_log("User verification successful: " . json_encode($inserted_user));
// Create audit log entry
try {
logAudit('CREATE', 'users', $user_id, null, [
'username' => $username,
'email' => $email,
'user_level' => $user_level,
'user_role' => $user_role,
'area_id' => $area_id,
'district_id' => $district_id,
'assembly_id' => $assembly_id
]);
error_log("Audit log created successfully for user ID: $user_id");
} catch (Exception $audit_e) {
error_log("Audit log failed: " . $audit_e->getMessage());
}
// Create welcome notification for the new user
try {
createNotification($user_id, 'Welcome to COP Madina Reports',
"Your account has been created successfully. Your temporary password is: $password. Please change it after your first login for security.", 'info');
error_log("Welcome notification created successfully for user ID: $user_id");
} catch (Exception $notif_e) {
error_log("Notification creation failed: " . $notif_e->getMessage());
}
$success_message = "User created successfully. Temporary password: $password";
// Redirect to avoid form resubmission
header("Location: user-management.php?success=" . urlencode($success_message));
exit();
} else {
error_log("User verification failed - user not found in database after insert");
$error_message = 'User creation failed - database verification failed.';
}
} else {
$error_info = $insert_stmt->errorInfo();
error_log("Failed to create user. Error info: " . json_encode($error_info));
error_log("SQL State: " . $error_info[0] . ", Error Code: " . $error_info[1] . ", Error Message: " . $error_info[2]);
$error_message = 'Failed to create user. Database error: ' . $error_info[2];
}
} catch (Exception $e) {
error_log("Exception during user creation: " . $e->getMessage());
error_log("Exception trace: " . $e->getTraceAsString());
$error_message = 'Failed to create user: ' . $e->getMessage();
}
}
}
} elseif (isset($_POST['toggle_user_status'])) {
$user_id = (int)$_POST['user_id'];
$new_status = (int)$_POST['new_status'];
// Check if user is superuser (prevent deactivation)
$check_query = "SELECT user_level FROM users WHERE id = :user_id";
$check_stmt = $db->prepare($check_query);
$check_stmt->bindParam(':user_id', $user_id);
$check_stmt->execute();
$user_data = $check_stmt->fetch(PDO::FETCH_ASSOC);
if ($user_data['user_level'] === 'superuser' && $new_status == 0) {
$error_message = 'Superuser accounts cannot be deactivated.';
} else {
$update_query = "UPDATE users SET is_active = :status WHERE id = :user_id";
$update_stmt = $db->prepare($update_query);
$update_stmt->bindParam(':status', $new_status);
$update_stmt->bindParam(':user_id', $user_id);
if ($update_stmt->execute()) {
logAudit('UPDATE', 'users', $user_id, null, ['is_active' => $new_status]);
$success_message = $new_status ? 'User activated successfully.' : 'User deactivated successfully.';
} else {
$error_message = 'Failed to update user status.';
}
}
} elseif (isset($_POST['edit_user'])) {
$user_id = (int)$_POST['user_id'];
$first_name = sanitizeInput($_POST['first_name']);
$last_name = sanitizeInput($_POST['last_name']);
$email = sanitizeInput($_POST['email']);
$user_level = sanitizeInput($_POST['user_level']);
$user_role = sanitizeInput($_POST['user_role']);
$area_id = !empty($_POST['area_id']) ? (int)$_POST['area_id'] : null;
$district_id = !empty($_POST['district_id']) ? (int)$_POST['district_id'] : null;
$assembly_id = !empty($_POST['assembly_id']) ? (int)$_POST['assembly_id'] : null;
$update_query = "UPDATE users SET first_name = :first_name, last_name = :last_name, email = :email,
user_level = :user_level, user_role = :user_role, area_id = :area_id,
district_id = :district_id, assembly_id = :assembly_id WHERE id = :user_id";
$update_stmt = $db->prepare($update_query);
$update_stmt->bindParam(':first_name', $first_name);
$update_stmt->bindParam(':last_name', $last_name);
$update_stmt->bindParam(':email', $email);
$update_stmt->bindParam(':user_level', $user_level);
$update_stmt->bindParam(':user_role', $user_role);
$update_stmt->bindParam(':area_id', $area_id);
$update_stmt->bindParam(':district_id', $district_id);
$update_stmt->bindParam(':assembly_id', $assembly_id);
$update_stmt->bindParam(':user_id', $user_id);
if ($update_stmt->execute()) {
logAudit('UPDATE', 'users', $user_id, null, $_POST);
$success_message = 'User updated successfully.';
} else {
$error_message = 'Failed to update user.';
}
} elseif (isset($_POST['delete_user'])) {
$user_id = (int)$_POST['user_id'];
// Check if user is superuser (prevent deletion)
$check_query = "SELECT user_level FROM users WHERE id = :user_id";
$check_stmt = $db->prepare($check_query);
$check_stmt->bindParam(':user_id', $user_id);
$check_stmt->execute();
$user_data = $check_stmt->fetch(PDO::FETCH_ASSOC);
if ($user_data['user_level'] === 'superuser') {
$error_message = 'Superuser accounts cannot be deleted.';
} else {
$delete_query = "DELETE FROM users WHERE id = :user_id";
$delete_stmt = $db->prepare($delete_query);
$delete_stmt->bindParam(':user_id', $user_id);
if ($delete_stmt->execute()) {
logAudit('DELETE', 'users', $user_id, $user_data, null);
$success_message = 'User deleted successfully.';
} else {
$error_message = 'Failed to delete user.';
}
}
} elseif (isset($_POST['reset_password'])) {
$user_id = (int)$_POST['user_id'];
$new_password = generateRandomPassword();
$password_hash = password_hash($new_password, PASSWORD_DEFAULT);
$update_query = "UPDATE users SET password_hash = :password_hash WHERE id = :user_id";
$update_stmt = $db->prepare($update_query);
$update_stmt->bindParam(':password_hash', $password_hash);
$update_stmt->bindParam(':user_id', $user_id);
if ($update_stmt->execute()) {
logAudit('UPDATE', 'users', $user_id, null, ['password_reset' => true]);
createNotification($user_id, 'Password Reset', "Your password has been reset. New password: $new_password", 'info');
$success_message = "Password reset successfully. New password: $new_password";
} else {
$error_message = 'Failed to reset password.';
}
} elseif (isset($_POST['enable_user'])) {
$user_id = (int)$_POST['user_id'];
$update_query = "UPDATE users SET is_active = 1 WHERE id = :user_id";
$update_stmt = $db->prepare($update_query);
$update_stmt->bindParam(':user_id', $user_id);
if ($update_stmt->execute()) {
logAudit('UPDATE', 'users', $user_id, null, ['is_active' => 1, 'action' => 'enabled']);
createNotification($user_id, 'Account Enabled', 'Your account has been enabled and you can now access the system.', 'success');
$success_message = 'User account enabled successfully.';
} else {
$error_message = 'Failed to enable user account.';
}
} elseif (isset($_POST['disable_user'])) {
$user_id = (int)$_POST['user_id'];
// Check if user is superuser (prevent disabling)
$check_query = "SELECT user_level FROM users WHERE id = :user_id";
$check_stmt = $db->prepare($check_query);
$check_stmt->bindParam(':user_id', $user_id);
$check_stmt->execute();
$user_data = $check_stmt->fetch(PDO::FETCH_ASSOC);
if ($user_data['user_level'] === 'superuser') {
$error_message = 'Superuser accounts cannot be disabled.';
} else {
$update_query = "UPDATE users SET is_active = 0 WHERE id = :user_id";
$update_stmt = $db->prepare($update_query);
$update_stmt->bindParam(':user_id', $user_id);
if ($update_stmt->execute()) {
logAudit('UPDATE', 'users', $user_id, null, ['is_active' => 0, 'action' => 'disabled']);
createNotification($user_id, 'Account Disabled', 'Your account has been disabled. Please contact an administrator if you believe this is an error.', 'warning');
$success_message = 'User account disabled successfully.';
} else {
$error_message = 'Failed to disable user account.';
}
}
}
}
// Get users based on current user's level
$users_query = "SELECT u.*, a.name as area_name, d.name as district_name, ass.name as assembly_name
FROM users u
LEFT JOIN areas a ON u.area_id = a.id
LEFT JOIN districts d ON u.district_id = d.id
LEFT JOIN assemblies ass ON u.assembly_id = ass.id";
$where_conditions = [];
$params = [];
// Apply access restrictions based on user level
if ($_SESSION['user_level'] !== 'superuser') {
if ($_SESSION['user_level'] === 'area') {
$where_conditions[] = "u.area_id = :area_id";
$params[':area_id'] = $_SESSION['area_id'];
} elseif ($_SESSION['user_level'] === 'district') {
$where_conditions[] = "u.district_id = :district_id";
$params[':district_id'] = $_SESSION['district_id'];
} elseif ($_SESSION['user_level'] === 'assembly') {
$where_conditions[] = "u.assembly_id = :assembly_id";
$params[':assembly_id'] = $_SESSION['assembly_id'];
}
}
if (!empty($where_conditions)) {
$users_query .= " WHERE " . implode(' AND ', $where_conditions);
}
$users_query .= " ORDER BY u.created_at DESC";
$users_stmt = $db->prepare($users_query);
foreach ($params as $key => $value) {
$users_stmt->bindValue($key, $value);
}
$users_stmt->execute();
$users = $users_stmt->fetchAll(PDO::FETCH_ASSOC);
// Get areas for dropdowns (districts and assemblies will be loaded dynamically)
$areas = getAccessibleAreas($_SESSION['user_level'], $_SESSION['area_id']);
// Get all districts and assemblies for edit modal (these will be filtered by JavaScript)
$all_districts_query = "SELECT d.id, d.name, d.area_id FROM districts d
JOIN areas a ON d.area_id = a.id ORDER BY a.name, d.name";
$all_districts_stmt = $db->prepare($all_districts_query);
$all_districts_stmt->execute();
$all_districts = $all_districts_stmt->fetchAll(PDO::FETCH_ASSOC);
$all_assemblies_query = "SELECT ass.id, ass.name, ass.district_id, d.area_id
FROM assemblies ass
JOIN districts d ON ass.district_id = d.id
JOIN areas a ON d.area_id = a.id
ORDER BY a.name, d.name, ass.name";
$all_assemblies_stmt = $db->prepare($all_assemblies_query);
$all_assemblies_stmt->execute();
$all_assemblies = $all_assemblies_stmt->fetchAll(PDO::FETCH_ASSOC);
include '../includes/header.php';
?>
<?php if ($success_message): ?>
<div class="bg-green-100 border border-green-400 text-green-700 px-4 py-3 rounded-lg mb-6 alert-auto-hide">
<div class="flex items-center">
<i class="fas fa-check-circle mr-2"></i>
<span><?php echo htmlspecialchars($success_message); ?></span>
</div>
</div>
<?php endif; ?>
<?php if ($error_message): ?>
<div class="bg-red-100 border border-red-400 text-red-700 px-4 py-3 rounded-lg mb-6 alert-auto-hide">
<div class="flex items-center">
<i class="fas fa-exclamation-circle mr-2"></i>
<span><?php echo htmlspecialchars($error_message); ?></span>
</div>
</div>
<?php endif; ?>
<!-- Tab Navigation -->
<div class="mb-6">
<div class="border-b border-gray-200">
<nav class="-mb-px flex space-x-8">
<button onclick="showTab('users-list')" id="users-list-tab"
class="tab-button active py-2 px-1 border-b-2 border-cop-blue font-medium text-sm text-cop-blue">
<i class="fas fa-users mr-2"></i>Users List
</button>
<button onclick="showTab('new-user')" id="new-user-tab"
class="tab-button py-2 px-1 border-b-2 border-transparent font-medium text-sm text-gray-500 hover:text-gray-700 hover:border-gray-300">
<i class="fas fa-user-plus mr-2"></i>New User
</button>
</nav>
</div>
</div>
<!-- Users List Tab -->
<div id="users-list-content" class="tab-content">
<div class="bg-white rounded-lg shadow-sm">
<div class="p-6 border-b border-gray-200">
<div class="flex items-center justify-between">
<h3 class="text-lg font-semibold text-gray-800">System Users</h3>
<span class="px-3 py-1 bg-blue-100 text-blue-800 text-sm rounded-full">
<?php echo count($users); ?> users
</span>
</div>
</div>
<div class="overflow-x-auto">
<?php if (empty($users)): ?>
<div class="text-center py-12">
<i class="fas fa-users text-4xl text-gray-400 mb-4"></i>
<h3 class="text-lg font-medium text-gray-600 mb-2">No users found</h3>
<p class="text-gray-500">Create your first user using the form on the right.</p>
</div>
<?php else: ?>
<table class="min-w-full divide-y divide-gray-200">
<thead class="bg-gray-50">
<tr>
<th class="px-6 py-3 text-left text-xs font-medium text-gray-500 uppercase tracking-wider">User</th>
<th class="px-6 py-3 text-left text-xs font-medium text-gray-500 uppercase tracking-wider">Level & Role</th>
<th class="px-6 py-3 text-left text-xs font-medium text-gray-500 uppercase tracking-wider">Assignment</th>
<th class="px-6 py-3 text-left text-xs font-medium text-gray-500 uppercase tracking-wider">Status</th>
<th class="px-6 py-3 text-left text-xs font-medium text-gray-500 uppercase tracking-wider">Actions</th>
</tr>
</thead>
<tbody class="bg-white divide-y divide-gray-200">
<?php foreach ($users as $user): ?>
<tr class="hover:bg-gray-50">
<td class="px-6 py-4 whitespace-nowrap">
<div class="flex items-center">
<div class="w-10 h-10 bg-gray-200 rounded-full flex items-center justify-center mr-3">
<span class="text-sm font-medium text-gray-600">
<?php echo strtoupper(substr($user['first_name'], 0, 1) . substr($user['last_name'], 0, 1)); ?>
</span>
</div>
<div>
<div class="text-sm font-medium text-gray-900">
<?php echo htmlspecialchars($user['first_name'] . ' ' . $user['last_name']); ?>
</div>
<div class="text-sm text-gray-500"><?php echo htmlspecialchars($user['email']); ?></div>
<div class="text-xs text-gray-400">@<?php echo htmlspecialchars($user['username']); ?></div>
</div>
</div>
</td>
<td class="px-6 py-4 whitespace-nowrap">
<div class="text-sm text-gray-900 capitalize"><?php echo htmlspecialchars($user['user_level']); ?></div>
<div class="text-sm text-gray-500 capitalize"><?php echo htmlspecialchars($user['user_role']); ?></div>
</td>
<td class="px-6 py-4 whitespace-nowrap text-sm text-gray-500">
<?php if ($user['area_name']): ?>
<div>Area: <?php echo htmlspecialchars($user['area_name']); ?></div>
<?php endif; ?>
<?php if ($user['district_name']): ?>
<div>District: <?php echo htmlspecialchars($user['district_name']); ?></div>
<?php endif; ?>
<?php if ($user['assembly_name']): ?>
<div>Assembly: <?php echo htmlspecialchars($user['assembly_name']); ?></div>
<?php endif; ?>
</td>
<td class="px-6 py-4 whitespace-nowrap">
<span class="px-2 inline-flex text-xs leading-5 font-semibold rounded-full <?php echo $user['is_active'] ? 'bg-green-100 text-green-800' : 'bg-red-100 text-red-800'; ?>">
<?php echo $user['is_active'] ? 'Active' : 'Inactive'; ?>
</span>
</td>
<td class="px-6 py-4 whitespace-nowrap text-sm font-medium">
<div class="flex items-center space-x-2">
<!-- Edit Button -->
<button onclick="editUser(<?php echo htmlspecialchars(json_encode($user)); ?>)"
class="text-blue-600 hover:text-blue-900"
title="Edit User">
<i class="fas fa-edit"></i>
</button>
<!-- Reset Password Button -->
<form method="POST" class="inline">
<input type="hidden" name="user_id" value="<?php echo $user['id']; ?>">
<button type="submit"
name="reset_password"
onclick="return confirm('Reset password for this user?')"
class="text-yellow-600 hover:text-yellow-900"
title="Reset Password">
<i class="fas fa-key"></i>
</button>
</form>
<?php if ($user['id'] != $_SESSION['user_id']): ?>
<!-- Enable/Disable Buttons -->
<?php if ($user['is_active']): ?>
<!-- Disable Button (only show if user is active and not superuser) -->
<?php if ($user['user_level'] !== 'superuser'): ?>
<form method="POST" class="inline">
<input type="hidden" name="user_id" value="<?php echo $user['id']; ?>">
<button type="submit"
name="disable_user"
onclick="return confirm('Are you sure you want to disable this user account? They will not be able to access the system.')"
class="text-orange-600 hover:text-orange-900"
title="Disable User Account">
<i class="fas fa-user-slash"></i>
</button>
</form>
<?php endif; ?>
<?php else: ?>
<!-- Enable Button (show for inactive users) -->
<form method="POST" class="inline">
<input type="hidden" name="user_id" value="<?php echo $user['id']; ?>">
<button type="submit"
name="enable_user"
onclick="return confirm('Enable this user account? They will be able to access the system again.')"
class="text-green-600 hover:text-green-900"
title="Enable User Account">
<i class="fas fa-user-check"></i>
</button>
</form>
<?php endif; ?>
<!-- Delete Button -->
<?php if ($user['user_level'] !== 'superuser'): ?>
<form method="POST" class="inline">
<input type="hidden" name="user_id" value="<?php echo $user['id']; ?>">
<button type="submit"
name="delete_user"
onclick="return confirm('Are you sure you want to delete this user? This action cannot be undone.')"
class="text-red-600 hover:text-red-900"
title="Delete User">
<i class="fas fa-trash"></i>
</button>
</form>
<?php endif; ?>
<?php endif; ?>
</div>
</td>
</tr>
<?php endforeach; ?>
</tbody>
</table>
<?php endif; ?>
</div>
</div>
</div>
</div>
<!-- New User Tab -->
<div id="new-user-content" class="tab-content hidden">
<div class="bg-white rounded-lg shadow-sm">
<div class="p-6 border-b border-gray-200">
<h3 class="text-lg font-semibold text-gray-800">Create New User</h3>
<p class="text-gray-600 text-sm">Add a new user to the system with appropriate access levels</p>
</div>
<div class="p-6">
<form method="POST" action="" class="space-y-6">
<input type="hidden" name="create_user" value="1">
<!-- Personal Information Section -->
<div class="bg-gray-50 rounded-lg p-4">
<h4 class="text-md font-semibold text-gray-800 mb-4">
<i class="fas fa-user mr-2 text-cop-blue"></i>Personal Information
</h4>
<div class="grid grid-cols-1 md:grid-cols-2 gap-4">
<div>
<label for="new_first_name" class="block text-sm font-medium text-gray-700 mb-1">
First Name <span class="text-red-500">*</span>
</label>
<input type="text"
id="new_first_name"
name="first_name"
required
class="w-full px-3 py-2 border border-gray-300 rounded-lg focus:ring-2 focus:ring-cop-blue focus:border-transparent text-sm">
</div>
<div>
<label for="new_last_name" class="block text-sm font-medium text-gray-700 mb-1">
Last Name <span class="text-red-500">*</span>
</label>
<input type="text"
id="new_last_name"
name="last_name"
required
class="w-full px-3 py-2 border border-gray-300 rounded-lg focus:ring-2 focus:ring-cop-blue focus:border-transparent text-sm">
</div>
<div>
<label for="new_username" class="block text-sm font-medium text-gray-700 mb-1">
Username <span class="text-red-500">*</span>
</label>
<input type="text"
id="new_username"
name="username"
required
placeholder="Enter unique username"
class="w-full px-3 py-2 border border-gray-300 rounded-lg focus:ring-2 focus:ring-cop-blue focus:border-transparent text-sm">
</div>
<div>
<label for="new_email" class="block text-sm font-medium text-gray-700 mb-1">
Email Address <span class="text-red-500">*</span>
</label>
<input type="email"
id="new_email"
name="email"
required
placeholder="user@example.com"
class="w-full px-3 py-2 border border-gray-300 rounded-lg focus:ring-2 focus:ring-cop-blue focus:border-transparent text-sm">
</div>
</div>
</div>
<!-- Access Level Section -->
<div class="bg-blue-50 rounded-lg p-4">
<h4 class="text-md font-semibold text-gray-800 mb-4">
<i class="fas fa-shield-alt mr-2 text-cop-blue"></i>Access Level & Role
</h4>
<div class="grid grid-cols-1 md:grid-cols-2 gap-4">
<div>
<label for="new_user_level" class="block text-sm font-medium text-gray-700 mb-1">
User Level <span class="text-red-500">*</span>
</label>
<select id="new_user_level"
name="user_level"
required
onchange="updateNewUserAssignmentOptions()"
class="w-full px-3 py-2 border border-gray-300 rounded-lg focus:ring-2 focus:ring-cop-blue focus:border-transparent text-sm">
<option value="">Select User Level</option>
<?php if ($_SESSION['user_level'] === 'superuser'): ?>
<option value="area">Area Level</option>
<option value="district">District Level</option>
<option value="assembly">Assembly Level</option>
<?php elseif ($_SESSION['user_level'] === 'area'): ?>
<option value="district">District Level</option>
<option value="assembly">Assembly Level</option>
<?php elseif ($_SESSION['user_level'] === 'district'): ?>
<option value="assembly">Assembly Level</option>
<?php endif; ?>
</select>
<p class="text-xs text-gray-500 mt-1">Determines the scope of access</p>
</div>
<div>
<label for="new_user_role" class="block text-sm font-medium text-gray-700 mb-1">
User Role <span class="text-red-500">*</span>
</label>
<select id="new_user_role"
name="user_role"
required
class="w-full px-3 py-2 border border-gray-300 rounded-lg focus:ring-2 focus:ring-cop-blue focus:border-transparent text-sm">
<option value="">Select User Role</option>
<option value="admin">Administrator</option>
<option value="dataentry">Data Entry</option>
<option value="viewer">Viewer Only</option>
</select>
<p class="text-xs text-gray-500 mt-1">Determines permissions within the level</p>
</div>
</div>
</div>
<!-- Location Assignment Section -->
<div class="bg-green-50 rounded-lg p-4">
<h4 class="text-md font-semibold text-gray-800 mb-4">
<i class="fas fa-map-marker-alt mr-2 text-cop-blue"></i>Location Assignment
</h4>
<div class="grid grid-cols-1 md:grid-cols-3 gap-4">
<!-- Area Field -->
<div id="new_area_field" style="display: none;">
<label for="new_area_id" class="block text-sm font-medium text-gray-700 mb-1">
Area <span class="text-red-500">*</span>
</label>
<select id="new_area_id"
name="area_id"
onchange="loadNewUserDistricts()"
class="w-full px-3 py-2 border border-gray-300 rounded-lg focus:ring-2 focus:ring-cop-blue focus:border-transparent text-sm">
<option value="">Select Area</option>
<?php foreach ($areas as $area): ?>
<option value="<?php echo $area['id']; ?>"><?php echo htmlspecialchars($area['name']); ?></option>
<?php endforeach; ?>
</select>
</div>
<!-- District Field -->
<div id="new_district_field" style="display: none;">
<label for="new_district_id" class="block text-sm font-medium text-gray-700 mb-1">
District <span class="text-red-500">*</span>
</label>
<select id="new_district_id"
name="district_id"
onchange="loadNewUserAssemblies()"
class="w-full px-3 py-2 border border-gray-300 rounded-lg focus:ring-2 focus:ring-cop-blue focus:border-transparent text-sm">
<option value="">Select District</option>
</select>
</div>
<!-- Assembly Field -->
<div id="new_assembly_field" style="display: none;">
<label for="new_assembly_id" class="block text-sm font-medium text-gray-700 mb-1">
Assembly <span class="text-gray-400">(Optional)</span>
</label>
<select id="new_assembly_id"
name="assembly_id"
class="w-full px-3 py-2 border border-gray-300 rounded-lg focus:ring-2 focus:ring-cop-blue focus:border-transparent text-sm">
<option value="">Select Assembly (Optional)</option>
</select>
</div>
</div>
<div class="mt-4 p-3 bg-white border border-blue-200 rounded-lg">
<p class="text-sm text-blue-800">
<i class="fas fa-info-circle mr-1"></i>
<strong>Location Assignment Guide:</strong><br>
• <strong>Area Level:</strong> Select the area this user will manage<br>
• <strong>District Level:</strong> Select area and district this user will manage<br>
• <strong>Assembly Level:</strong> Select area, district, and specific assembly
</p>
</div>
</div>
<!-- Password Information -->
<div class="bg-yellow-50 border border-yellow-200 rounded-lg p-4">
<div class="flex items-start">
<i class="fas fa-key text-yellow-600 mr-3 mt-1"></i>
<div>
<h5 class="font-medium text-yellow-800">Password Information</h5>
<p class="text-sm text-yellow-700 mt-1">
A secure temporary password will be automatically generated and displayed after user creation.
The user should change this password on their first login.
</p>
</div>
</div>
</div>
<!-- Submit Button -->
<div class="flex justify-end space-x-4">
<button type="button"
onclick="showTab('users-list')"
class="px-6 py-2 bg-gray-300 text-gray-700 rounded-lg hover:bg-gray-400 transition duration-200">
<i class="fas fa-times mr-2"></i>Cancel
</button>
<button type="submit"
name="create_user"
id="create-user-btn"
class="px-6 py-2 bg-cop-blue text-white rounded-lg hover:bg-cop-light-blue transition duration-200">
<i class="fas fa-user-plus mr-2"></i>Create User
</button>
</div>
</form>
</div>
</div>
</div>
<!-- Edit User Modal -->
<div id="editUserModal" class="fixed inset-0 bg-gray-600 bg-opacity-50 overflow-y-auto h-full w-full hidden">
<div class="relative top-20 mx-auto p-5 border w-96 shadow-lg rounded-md bg-white">
<div class="mt-3">
<div class="flex items-center justify-between mb-4">
<h3 class="text-lg font-medium text-gray-900">Edit User</h3>
<button onclick="closeEditModal()" class="text-gray-400 hover:text-gray-600">
<i class="fas fa-times"></i>
</button>
</div>
<form method="POST" id="editUserForm" class="space-y-4">
<input type="hidden" name="user_id" id="edit_user_id">
<div class="grid grid-cols-2 gap-4">
<div>
<label for="edit_first_name" class="block text-sm font-medium text-gray-700 mb-1">First Name</label>
<input type="text" id="edit_first_name" name="first_name" required
class="w-full px-3 py-2 border border-gray-300 rounded-lg focus:ring-2 focus:ring-cop-blue focus:border-transparent text-sm">
</div>
<div>
<label for="edit_last_name" class="block text-sm font-medium text-gray-700 mb-1">Last Name</label>
<input type="text" id="edit_last_name" name="last_name" required
class="w-full px-3 py-2 border border-gray-300 rounded-lg focus:ring-2 focus:ring-cop-blue focus:border-transparent text-sm">
</div>
</div>
<div>
<label for="edit_email" class="block text-sm font-medium text-gray-700 mb-1">Email</label>
<input type="email" id="edit_email" name="email" required
class="w-full px-3 py-2 border border-gray-300 rounded-lg focus:ring-2 focus:ring-cop-blue focus:border-transparent text-sm">
</div>
<div>
<label for="edit_user_level" class="block text-sm font-medium text-gray-700 mb-1">User Level</label>
<select id="edit_user_level" name="user_level" required
class="w-full px-3 py-2 border border-gray-300 rounded-lg focus:ring-2 focus:ring-cop-blue focus:border-transparent text-sm">
<option value="area">Area</option>
<option value="district">District</option>
<option value="assembly">Assembly</option>
</select>
</div>
<div>
<label for="edit_user_role" class="block text-sm font-medium text-gray-700 mb-1">User Role</label>
<select id="edit_user_role" name="user_role" required
class="w-full px-3 py-2 border border-gray-300 rounded-lg focus:ring-2 focus:ring-cop-blue focus:border-transparent text-sm">
<option value="admin">Admin</option>
<option value="dataentry">Data Entry</option>
<option value="viewer">Viewer</option>
</select>
</div>
<div>
<label for="edit_area_id" class="block text-sm font-medium text-gray-700 mb-1">Area</label>
<select id="edit_area_id" name="area_id"
onchange="loadEditDistricts()"
class="w-full px-3 py-2 border border-gray-300 rounded-lg focus:ring-2 focus:ring-cop-blue focus:border-transparent text-sm">
<option value="">Select Area</option>
<?php foreach ($areas as $area): ?>
<option value="<?php echo $area['id']; ?>"><?php echo htmlspecialchars($area['name']); ?></option>
<?php endforeach; ?>
</select>
</div>
<div>
<label for="edit_district_id" class="block text-sm font-medium text-gray-700 mb-1">District</label>
<select id="edit_district_id" name="district_id"
onchange="loadEditAssemblies()"
class="w-full px-3 py-2 border border-gray-300 rounded-lg focus:ring-2 focus:ring-cop-blue focus:border-transparent text-sm">
<option value="">Select District</option>
<?php foreach ($all_districts as $district): ?>
<option value="<?php echo $district['id']; ?>" data-area-id="<?php echo $district['area_id']; ?>"><?php echo htmlspecialchars($district['name']); ?></option>
<?php endforeach; ?>
</select>
</div>
<div>
<label for="edit_assembly_id" class="block text-sm font-medium text-gray-700 mb-1">Assembly</label>
<select id="edit_assembly_id" name="assembly_id"
class="w-full px-3 py-2 border border-gray-300 rounded-lg focus:ring-2 focus:ring-cop-blue focus:border-transparent text-sm">
<option value="">Select Assembly</option>
<?php foreach ($all_assemblies as $assembly): ?>
<option value="<?php echo $assembly['id']; ?>" data-district-id="<?php echo $assembly['district_id']; ?>" data-area-id="<?php echo $assembly['area_id']; ?>"><?php echo htmlspecialchars($assembly['name']); ?></option>
<?php endforeach; ?>
</select>
</div>
<div class="flex justify-end space-x-3 pt-4">
<button type="button" onclick="closeEditModal()"
class="px-4 py-2 bg-gray-300 text-gray-700 rounded-lg hover:bg-gray-400 transition duration-200">
Cancel
</button>
<button type="submit" name="edit_user"
class="px-4 py-2 bg-cop-blue text-white rounded-lg hover:bg-cop-light-blue transition duration-200">
Update User
</button>
</div>
</form>
</div>
</div>
</div>
<script>
// Tab Management Functions
function showTab(tabName) {
// Hide all tab contents
const tabContents = document.querySelectorAll('.tab-content');
tabContents.forEach(content => content.classList.add('hidden'));
// Remove active class from all tab buttons
const tabButtons = document.querySelectorAll('.tab-button');
tabButtons.forEach(button => {
button.classList.remove('active', 'border-cop-blue', 'text-cop-blue');
button.classList.add('border-transparent', 'text-gray-500');
});
// Show selected tab content
const selectedContent = document.getElementById(tabName + '-content');
if (selectedContent) {
selectedContent.classList.remove('hidden');
}
// Add active class to selected tab button
const selectedButton = document.getElementById(tabName + '-tab');
if (selectedButton) {
selectedButton.classList.add('active', 'border-cop-blue', 'text-cop-blue');
selectedButton.classList.remove('border-transparent', 'text-gray-500');
}
}
// New User Form Functions
function updateNewUserAssignmentOptions() {
const userLevel = document.getElementById('new_user_level').value;
const areaField = document.getElementById('new_area_field');
const districtField = document.getElementById('new_district_field');
const assemblyField = document.getElementById('new_assembly_field');
// Show/hide fields based on user level
if (areaField) areaField.style.display = userLevel === 'area' ? 'block' : 'none';
if (districtField) districtField.style.display = ['area', 'district'].includes(userLevel) ? 'block' : 'none';
if (assemblyField) assemblyField.style.display = ['area', 'district', 'assembly'].includes(userLevel) ? 'block' : 'none';
// Clear dependent fields when user level changes
if (userLevel !== 'area') {
const areaSelect = document.getElementById('new_area_id');
if (areaSelect) areaSelect.value = '';
}
if (!['area', 'district'].includes(userLevel)) {
const districtSelect = document.getElementById('new_district_id');
if (districtSelect) districtSelect.value = '';
}
if (!['area', 'district', 'assembly'].includes(userLevel)) {
const assemblySelect = document.getElementById('new_assembly_id');
if (assemblySelect) assemblySelect.value = '';
}
}
function loadNewUserDistricts() {
const areaId = document.getElementById('new_area_id').value;
const districtSelect = document.getElementById('new_district_id');
const assemblySelect = document.getElementById('new_assembly_id');
console.log('Loading districts for new user form, area ID:', areaId);
// Clear districts and assemblies
if (districtSelect) {
districtSelect.innerHTML = '<option value="">Loading districts...</option>';
}
if (assemblySelect) {
assemblySelect.innerHTML = '<option value="">Select Assembly</option>';
}
if (areaId) {
fetch(`../api/get-districts.php?area_id=${areaId}`)
.then(response => {
console.log('Districts response status:', response.status);
if (!response.ok) {
throw new Error(`HTTP error! status: ${response.status}`);
}
return response.json();
})
.then(districts => {
console.log('Districts loaded for new user:', districts);
if (districtSelect) {
districtSelect.innerHTML = '<option value="">Select District</option>';
if (Array.isArray(districts) && districts.length > 0) {
districts.forEach(district => {
const option = document.createElement('option');
option.value = district.id;
option.textContent = district.name;
districtSelect.appendChild(option);
});
} else {
districtSelect.innerHTML = '<option value="">No districts found</option>';
}
}
})
.catch(error => {
console.error('Error loading districts for new user:', error);
if (districtSelect) {
districtSelect.innerHTML = '<option value="">Error loading districts</option>';
}
});
} else {
if (districtSelect) {
districtSelect.innerHTML = '<option value="">Select District</option>';
}
}
}
function loadNewUserAssemblies() {
const districtId = document.getElementById('new_district_id').value;
const assemblySelect = document.getElementById('new_assembly_id');
console.log('Loading assemblies for new user form, district ID:', districtId);
// Clear assemblies
if (assemblySelect) {
assemblySelect.innerHTML = '<option value="">Loading assemblies...</option>';
}
if (districtId) {
fetch(`../api/get-assemblies.php?district_id=${districtId}`)
.then(response => {
console.log('Assemblies response status:', response.status);
if (!response.ok) {
throw new Error(`HTTP error! status: ${response.status}`);
}
return response.json();
})
.then(assemblies => {
console.log('Assemblies loaded for new user:', assemblies);
if (assemblySelect) {
assemblySelect.innerHTML = '<option value="">Select Assembly</option>';
if (Array.isArray(assemblies) && assemblies.length > 0) {
assemblies.forEach(assembly => {
const option = document.createElement('option');
option.value = assembly.id;
option.textContent = assembly.name;
assemblySelect.appendChild(option);
});
} else {
assemblySelect.innerHTML = '<option value="">No assemblies found</option>';
}
}
})
.catch(error => {
console.error('Error loading assemblies for new user:', error);
if (assemblySelect) {
assemblySelect.innerHTML = '<option value="">Error loading assemblies</option>';
}
});
} else {
if (assemblySelect) {
assemblySelect.innerHTML = '<option value="">Select Assembly</option>';
}
}
}
// Form submission handling
document.addEventListener('DOMContentLoaded', function() {
const createUserForm = document.querySelector('#new-user-content form');
const createUserBtn = document.getElementById('create-user-btn');
if (createUserForm && createUserBtn) {
createUserForm.addEventListener('submit', function(e) {
// Show loading state
createUserBtn.disabled = true;
createUserBtn.innerHTML = '<i class="fas fa-spinner fa-spin mr-2"></i>Creating User...';
// Form will submit normally, loading state will be reset on page reload
});
}
});
function loadDistricts() {
const areaId = document.getElementById('area_id').value;
const districtSelect = document.getElementById('district_id');
const assemblySelect = document.getElementById('assembly_id');
console.log('Loading districts for area ID:', areaId);
// Clear districts and assemblies
if (districtSelect) {
districtSelect.innerHTML = '<option value="">Loading districts...</option>';
}
if (assemblySelect) {
assemblySelect.innerHTML = '<option value="">Select Assembly</option>';
}
if (areaId) {
fetch(`../api/get-districts.php?area_id=${areaId}`)
.then(response => {
console.log('Districts response status:', response.status);
if (!response.ok) {
throw new Error(`HTTP error! status: ${response.status}`);
}
return response.json();
})
.then(districts => {
console.log('Districts loaded:', districts);
if (districtSelect) {
districtSelect.innerHTML = '<option value="">Select District</option>';
if (Array.isArray(districts) && districts.length > 0) {
districts.forEach(district => {
const option = document.createElement('option');
option.value = district.id;
option.textContent = district.name;
districtSelect.appendChild(option);
});
} else {
districtSelect.innerHTML = '<option value="">No districts found</option>';
}
}
})
.catch(error => {
console.error('Error loading districts:', error);
if (districtSelect) {
districtSelect.innerHTML = '<option value="">Error loading districts</option>';
}
});
} else {
if (districtSelect) {
districtSelect.innerHTML = '<option value="">Select District</option>';
}
}
}
function loadAssemblies() {
const districtId = document.getElementById('district_id').value;
const assemblySelect = document.getElementById('assembly_id');
console.log('Loading assemblies for district ID:', districtId);
// Clear assemblies
if (assemblySelect) {
assemblySelect.innerHTML = '<option value="">Loading assemblies...</option>';
}
if (districtId) {
fetch(`../api/get-assemblies.php?district_id=${districtId}`)
.then(response => {
console.log('Assemblies response status:', response.status);
if (!response.ok) {
throw new Error(`HTTP error! status: ${response.status}`);
}
return response.json();
})
.then(assemblies => {
console.log('Assemblies loaded:', assemblies);
if (assemblySelect) {
assemblySelect.innerHTML = '<option value="">Select Assembly</option>';
if (Array.isArray(assemblies) && assemblies.length > 0) {
assemblies.forEach(assembly => {
const option = document.createElement('option');
option.value = assembly.id;
option.textContent = assembly.name;
assemblySelect.appendChild(option);
});
} else {
assemblySelect.innerHTML = '<option value="">No assemblies found</option>';
}
}
})
.catch(error => {
console.error('Error loading assemblies:', error);
if (assemblySelect) {
assemblySelect.innerHTML = '<option value="">Error loading assemblies</option>';
}
});
} else {
if (assemblySelect) {
assemblySelect.innerHTML = '<option value="">Select Assembly</option>';
}
}
}
function showLoading(button) {
button.disabled = true;
button.innerHTML = '<i class="fas fa-spinner fa-spin mr-2"></i>Creating...';
}
// Edit User Functions
function editUser(user) {
document.getElementById('edit_user_id').value = user.id;
document.getElementById('edit_first_name').value = user.first_name;
document.getElementById('edit_last_name').value = user.last_name;
document.getElementById('edit_email').value = user.email;
document.getElementById('edit_user_level').value = user.user_level;
document.getElementById('edit_user_role').value = user.user_role;
document.getElementById('edit_area_id').value = user.area_id || '';
// Filter and populate districts based on selected area
filterEditDistricts(user.area_id);
document.getElementById('edit_district_id').value = user.district_id || '';
// Filter and populate assemblies based on selected district
filterEditAssemblies(user.district_id);
document.getElementById('edit_assembly_id').value = user.assembly_id || '';
document.getElementById('editUserModal').classList.remove('hidden');
}
function filterEditDistricts(areaId) {
const districtSelect = document.getElementById('edit_district_id');
const assemblySelect = document.getElementById('edit_assembly_id');
// Clear districts and assemblies
districtSelect.innerHTML = '<option value="">Select District</option>';
assemblySelect.innerHTML = '<option value="">Select Assembly</option>';
if (areaId) {
// Show only districts that belong to the selected area
const allOptions = districtSelect.querySelectorAll('option[data-area-id]');
const allDistricts = <?php echo json_encode($all_districts); ?>;
allDistricts.forEach(district => {
if (district.area_id == areaId) {
const option = document.createElement('option');
option.value = district.id;
option.textContent = district.name;
option.setAttribute('data-area-id', district.area_id);
districtSelect.appendChild(option);
}
});
}
}
function filterEditAssemblies(districtId) {
const assemblySelect = document.getElementById('edit_assembly_id');
// Clear assemblies
assemblySelect.innerHTML = '<option value="">Select Assembly</option>';
if (districtId) {
// Show only assemblies that belong to the selected district
const allAssemblies = <?php echo json_encode($all_assemblies); ?>;
allAssemblies.forEach(assembly => {
if (assembly.district_id == districtId) {
const option = document.createElement('option');
option.value = assembly.id;
option.textContent = assembly.name;
option.setAttribute('data-district-id', assembly.district_id);
option.setAttribute('data-area-id', assembly.area_id);
assemblySelect.appendChild(option);
}
});
}
}
function loadEditDistricts() {
const areaId = document.getElementById('edit_area_id').value;
filterEditDistricts(areaId);
}
function loadEditAssemblies() {
const districtId = document.getElementById('edit_district_id').value;
filterEditAssemblies(districtId);
}
function closeEditModal() {
document.getElementById('editUserModal').classList.add('hidden');
}
// Close modal when clicking outside
document.getElementById('editUserModal').addEventListener('click', function(e) {
if (e.target === this) {
closeEditModal();
}
});
// Initialize page
document.addEventListener('DOMContentLoaded', function() {
// Show users list tab by default
showTab('users-list');
// Initialize new user form
updateNewUserAssignmentOptions();
});
// Handle successful form submission - switch back to users list
<?php if ($success_message && isset($_POST['create_user'])): ?>
document.addEventListener('DOMContentLoaded', function() {
showTab('users-list');
});
<?php endif; ?>
</script>
<style>
.tab-button.active {
border-color: #1e40af !important;
color: #1e40af !important;
}
.tab-content {
animation: fadeIn 0.3s ease-in-out;
}
@keyframes fadeIn {
from { opacity: 0; transform: translateY(10px); }
to { opacity: 1; transform: translateY(0); }
}
.tab-button:hover {
border-color: #9ca3af !important;
color: #374151 !important;
}
</style>
<?php include '../includes/footer.php'; ?>
Sindbad File Manager Version 1.0, Coded By Sindbad EG ~ The Terrorists