Implement rejection reason modal instead of prompt, and fix SQL syntax error for column creation in MySQL 8.0

This commit is contained in:
ilham_gmail
2026-06-11 22:03:18 +07:00
parent da9796755a
commit 56bad098a3
2 changed files with 73 additions and 16 deletions
+69 -15
View File
@@ -241,6 +241,20 @@
</div>
</div>
<div id="admin-reject-modal" class="modal hidden" role="dialog" aria-hidden="true" style="z-index:11000">
<div class="modal-content" style="max-width:480px;width:min(480px,90vw)">
<h3>Alasan Penolakan</h3>
<div style="font-size:13px;color:#475569;margin-bottom:12px">Silakan masukkan alasan penolakan untuk pengelola ini. Alasan akan dikirimkan ke email pendaftar.</div>
<div style="margin-bottom:16px">
<textarea id="admin-reject-reason-input" style="width:100%;height:100px;padding:8px;border:1px solid #cbd5e1;border-radius:6px;box-sizing:border-box" placeholder="Tulis alasan di sini..."></textarea>
</div>
<div class="modal-actions" style="display:flex;justify-content:flex-end;gap:8px">
<button type="button" id="admin-reject-cancel" class="btn-secondary">Batal</button>
<button type="button" id="admin-reject-submit" class="btn-destructive">Tolak Pendaftaran</button>
</div>
</div>
</div>
<!-- Email Verification Modal -->
<!-- Image viewer modal (separate from form modal) -->
@@ -918,22 +932,61 @@ async function approvePendingUser(id){
}catch(e){ console.error(e); showToast('Gagal menyetujui user', 'error', 4000); }
}
async function rejectPendingUser(id){
const reason = prompt("Masukkan alasan penolakan:");
if (reason === null) return; // user cancelled
const trimmedReason = reason.trim();
if (!trimmedReason) {
showToast("Alasan penolakan wajib diisi!", "error", 4000);
return;
function closeRejectModal(){
const modal = document.getElementById('admin-reject-modal');
if(modal) {
modal.classList.add('hidden');
modal.setAttribute('aria-hidden','true');
}
try{
const resp = await fetch('src/api/admin/reject_user.php', { method: 'POST', headers: buildHeaders(), body: JSON.stringify({ id: id, reason: trimmedReason }), credentials: 'same-origin' });
const jr = await resp.json().catch(()=>null);
if(!resp.ok || !jr || !jr.success){ showToast('Gagal menolak user', 'error', 4000); return; }
showToast('User ditolak', 'success', 3000);
closePendingManagerDetail();
openAdminDashboard();
}catch(e){ console.error(e); showToast('Gagal menolak user', 'error', 4000); }
}
function rejectPendingUser(id){
const modal = document.getElementById('admin-reject-modal');
const input = document.getElementById('admin-reject-reason-input');
const submitBtn = document.getElementById('admin-reject-submit');
const cancelBtn = document.getElementById('admin-reject-cancel');
if(!modal || !input || !submitBtn || !cancelBtn) return;
input.value = '';
submitBtn.disabled = false;
submitBtn.textContent = 'Tolak Pendaftaran';
cancelBtn.onclick = function(){
closeRejectModal();
};
submitBtn.onclick = async function(){
const reason = input.value.trim();
if(!reason){
showToast('Alasan penolakan wajib diisi!', 'error', 4000);
return;
}
submitBtn.disabled = true;
submitBtn.textContent = 'Memproses...';
try{
const resp = await fetch('src/api/admin/reject_user.php', { method: 'POST', headers: buildHeaders(), body: JSON.stringify({ id: id, reason: reason }), credentials: 'same-origin' });
const jr = await resp.json().catch(()=>null);
if(!resp.ok || !jr || !jr.success){
showToast('Gagal menolak user', 'error', 4000);
submitBtn.disabled = false;
submitBtn.textContent = 'Tolak Pendaftaran';
return;
}
showToast('User ditolak', 'success', 3000);
closeRejectModal();
closePendingManagerDetail();
openAdminDashboard();
}catch(e){
console.error(e);
showToast('Gagal menolak user', 'error', 4000);
submitBtn.disabled = false;
submitBtn.textContent = 'Tolak Pendaftaran';
}
};
modal.classList.remove('hidden');
modal.setAttribute('aria-hidden','false');
}
function closeAdminDashboard(){
@@ -2411,6 +2464,7 @@ try{
document.getElementById('auth-modal').addEventListener('click', function(ev){ if(ev.target === this) closeAuthModal(); });
document.getElementById('admin-modal').addEventListener('click', function(ev){ if(ev.target === this) closeAdminDashboard(); });
document.getElementById('admin-detail-modal').addEventListener('click', function(ev){ if(ev.target === this) closePendingManagerDetail(); });
document.getElementById('admin-reject-modal').addEventListener('click', function(ev){ if(ev.target === this) closeRejectModal(); });
// Admin dashboard wiring is handled by openAdminDashboard() above.
}catch(e){}
@@ -8,7 +8,10 @@ require_role('admin');
// Ensure column exists
try {
$conn->query("ALTER TABLE users ADD COLUMN IF NOT EXISTS rejection_reason TEXT NULL");
$check = $conn->query("SHOW COLUMNS FROM users LIKE 'rejection_reason'");
if($check && $check->num_rows === 0){
$conn->query("ALTER TABLE users ADD COLUMN rejection_reason TEXT NULL");
}
} catch(Exception $e){}
$data = json_decode(file_get_contents('php://input'), true);