HEX
Server: Apache/2.4.65 (Debian)
System: Linux kubikelcreative 5.10.0-35-amd64 #1 SMP Debian 5.10.237-1 (2025-05-19) x86_64
User: www-data (33)
PHP: 8.4.13
Disabled: NONE
Upload Files
File: /var/www/indoadvisory_new/webapp/src/routes/inquiries.js
import { Hono } from 'hono';
import { formatDate } from '../utils/database';
const inquiries = new Hono();
// Inquiries List
inquiries.get('/', async (c) => {
    try {
        const inquiriesList = await c.env.DB.prepare('SELECT * FROM contact_inquiries ORDER BY created_at DESC').all();
        const user = c.get('user');
        return c.html(`
      <!DOCTYPE html>
      <html lang="id">
      <head>
          <meta charset="UTF-8">
          <meta name="viewport" content="width=device-width, initial-scale=1.0">
          <title>Kelola Inquiry - Admin IndoAdvisory</title>
          <script src="https://cdn.tailwindcss.com"></script>
          <link href="https://cdnjs.cloudflare.com/ajax/libs/font-awesome/6.4.0/css/all.min.css" rel="stylesheet">
      </head>
      <body class="bg-gray-100">
          ${adminNavbar(user)}
          
          <div class="max-w-7xl mx-auto px-4 sm:px-6 lg:px-8 py-8">
              <div class="flex justify-between items-center mb-8">
                  <h1 class="text-3xl font-bold text-gray-800">Kelola Inquiry</h1>
                  <div class="flex space-x-4">
                      <select id="statusFilter" class="px-4 py-2 border border-gray-300 rounded-lg">
                          <option value="">Semua Status</option>
                          <option value="new">Baru</option>
                          <option value="contacted">Dihubungi</option>
                          <option value="closed">Ditutup</option>
                      </select>
                  </div>
              </div>
              
              <div class="bg-white rounded-xl shadow-lg overflow-hidden">
                  <div class="overflow-x-auto">
                      <table class="w-full">
                          <thead class="bg-gray-50">
                              <tr>
                                  <th class="px-6 py-3 text-left text-xs font-medium text-gray-500 uppercase tracking-wider">Nama & Email</th>
                                  <th class="px-6 py-3 text-left text-xs font-medium text-gray-500 uppercase tracking-wider">Perusahaan</th>
                                  <th class="px-6 py-3 text-left text-xs font-medium text-gray-500 uppercase tracking-wider">Layanan</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">Tanggal</th>
                                  <th class="px-6 py-3 text-left text-xs font-medium text-gray-500 uppercase tracking-wider">Aksi</th>
                              </tr>
                          </thead>
                          <tbody class="bg-white divide-y divide-gray-200">
                              ${inquiriesList.results.map(inquiry => `
                                  <tr class="hover:bg-gray-50">
                                      <td class="px-6 py-4">
                                          <div>
                                              <div class="text-sm font-medium text-gray-900">${inquiry.name}</div>
                                              <div class="text-sm text-gray-500">${inquiry.email}</div>
                                          </div>
                                      </td>
                                      <td class="px-6 py-4 whitespace-nowrap text-sm text-gray-900">
                                          ${inquiry.company || '-'}
                                      </td>
                                      <td class="px-6 py-4 whitespace-nowrap">
                                          <span class="px-2 py-1 text-xs font-semibold rounded-full bg-blue-100 text-blue-800">
                                              ${inquiry.service || 'Umum'}
                                          </span>
                                      </td>
                                      <td class="px-6 py-4 whitespace-nowrap">
                                          <select onchange="updateStatus(${inquiry.id}, this.value)" class="text-xs font-semibold rounded-full border-0 ${inquiry.status === 'new' ? 'bg-orange-100 text-orange-800' : inquiry.status === 'contacted' ? 'bg-blue-100 text-blue-800' : 'bg-green-100 text-green-800'}">
                                              <option value="new" ${inquiry.status === 'new' ? 'selected' : ''}>Baru</option>
                                              <option value="contacted" ${inquiry.status === 'contacted' ? 'selected' : ''}>Dihubungi</option>
                                              <option value="closed" ${inquiry.status === 'closed' ? 'selected' : ''}>Ditutup</option>
                                          </select>
                                      </td>
                                      <td class="px-6 py-4 whitespace-nowrap text-sm text-gray-500">
                                          ${formatDate(inquiry.created_at)}
                                      </td>
                                      <td class="px-6 py-4 whitespace-nowrap text-sm font-medium space-x-2">
                                          <button onclick="viewMessage(${inquiry.id}, '${inquiry.message.replace(/'/g, "\\'")}', '${inquiry.name}')" class="text-blue-600 hover:text-blue-900">
                                              <i class="fas fa-eye mr-1"></i>Lihat
                                          </button>
                                          <a href="mailto:${inquiry.email}?subject=Re: Inquiry dari ${inquiry.name}&body=Halo ${inquiry.name},%0A%0ATerima kasih atas inquiry Anda." class="text-green-600 hover:text-green-900">
                                              <i class="fas fa-envelope mr-1"></i>Email
                                          </a>
                                          <button onclick="deleteInquiry(${inquiry.id})" class="text-red-600 hover:text-red-900">
                                              <i class="fas fa-trash mr-1"></i>Hapus
                                          </button>
                                      </td>
                                  </tr>
                              `).join('')}
                          </tbody>
                      </table>
                  </div>
              </div>
          </div>
          
          <!-- Message Modal -->
          <div id="messageModal" class="hidden fixed inset-0 bg-gray-600 bg-opacity-50 overflow-y-auto h-full w-full z-50">
              <div class="relative top-20 mx-auto p-5 border w-11/12 md:w-3/4 lg:w-1/2 shadow-lg rounded-md bg-white">
                  <div class="mt-3">
                      <div class="flex justify-between items-center mb-4">
                          <h3 class="text-lg font-medium text-gray-900" id="modalTitle">Pesan Inquiry</h3>
                          <button onclick="closeModal()" class="text-gray-400 hover:text-gray-600">
                              <i class="fas fa-times"></i>
                          </button>
                      </div>
                      <div class="mt-2 px-7 py-3">
                          <p class="text-sm text-gray-500" id="modalMessage"></p>
                      </div>
                      <div class="items-center px-4 py-3">
                          <button onclick="closeModal()" class="px-4 py-2 bg-blue-500 text-white text-base font-medium rounded-md w-full shadow-sm hover:bg-blue-700 focus:outline-none focus:ring-2 focus:ring-blue-300">
                              Tutup
                          </button>
                      </div>
                  </div>
              </div>
          </div>
          
          <script>
              function updateStatus(id, status) {
                  fetch('/admin/inquiries/' + id + '/status', {
                      method: 'POST',
                      headers: { 'Content-Type': 'application/json' },
                      body: JSON.stringify({ status: status })
                  }).then(() => window.location.reload());
              }
              
              function deleteInquiry(id) {
                  if (confirm('Apakah Anda yakin ingin menghapus inquiry ini?')) {
                      fetch('/admin/inquiries/' + id + '/delete', { method: 'POST' })
                          .then(() => window.location.reload());
                  }
              }
              
              function viewMessage(id, message, name) {
                  document.getElementById('modalTitle').textContent = 'Pesan dari ' + name;
                  document.getElementById('modalMessage').textContent = message;
                  document.getElementById('messageModal').classList.remove('hidden');
              }
              
              function closeModal() {
                  document.getElementById('messageModal').classList.add('hidden');
              }
              
              // Filter functionality
              document.getElementById('statusFilter').addEventListener('change', function() {
                  const filterValue = this.value;
                  const rows = document.querySelectorAll('tbody tr');
                  
                  rows.forEach(row => {
                      const statusSelect = row.querySelector('select');
                      const currentStatus = statusSelect.value;
                      
                      if (filterValue === '' || currentStatus === filterValue) {
                          row.style.display = '';
                      } else {
                          row.style.display = 'none';
                      }
                  });
              });
          </script>
      </body>
      </html>
    `);
    }
    catch (error) {
        return c.html(`<div>Error: ${error.message}</div>`);
    }
});
// Update inquiry status
inquiries.post('/:id/status', async (c) => {
    try {
        const id = c.req.param('id');
        const { status } = await c.req.json();
        await c.env.DB.prepare('UPDATE contact_inquiries SET status = ? WHERE id = ?').bind(status, id).run();
        return c.json({ success: true });
    }
    catch (error) {
        return c.json({ error: error.message }, 500);
    }
});
// Delete inquiry
inquiries.post('/:id/delete', async (c) => {
    try {
        const id = c.req.param('id');
        await c.env.DB.prepare('DELETE FROM contact_inquiries WHERE id = ?').bind(id).run();
        return c.json({ success: true });
    }
    catch (error) {
        return c.json({ error: error.message }, 500);
    }
});
// Admin Navbar Component
function adminNavbar(user) {
    return `
    <nav class="bg-white shadow-lg border-b">
        <div class="max-w-7xl mx-auto px-4 sm:px-6 lg:px-8">
            <div class="flex justify-between items-center h-16">
                <div class="flex items-center">
                    <h1 class="text-xl font-bold text-gray-800">
                        <i class="fas fa-chart-line text-blue-600 mr-2"></i>
                        IndoAdvisory Admin
                    </h1>
                </div>
                
                <div class="hidden md:flex items-center space-x-6">
                    <a href="/admin/dashboard" class="text-gray-700 hover:text-blue-600 px-3 py-2 rounded-md text-sm font-medium">
                        <i class="fas fa-tachometer-alt mr-1"></i>
                        Dashboard
                    </a>
                    <a href="/admin/articles" class="text-gray-700 hover:text-blue-600 px-3 py-2 rounded-md text-sm font-medium">
                        <i class="fas fa-newspaper mr-1"></i>
                        Artikel
                    </a>
                    <a href="/admin/inquiries" class="text-blue-600 font-semibold px-3 py-2 rounded-md text-sm font-medium">
                        <i class="fas fa-envelope mr-1"></i>
                        Inquiry
                    </a>
                    <a href="/admin/team" class="text-gray-700 hover:text-blue-600 px-3 py-2 rounded-md text-sm font-medium">
                        <i class="fas fa-users mr-1"></i>
                        Tim
                    </a>
                    <a href="/admin/settings" class="text-gray-700 hover:text-blue-600 px-3 py-2 rounded-md text-sm font-medium">
                        <i class="fas fa-cog mr-1"></i>
                        Settings
                    </a>
                    <a href="/" target="_blank" class="text-gray-700 hover:text-blue-600 px-3 py-2 rounded-md text-sm font-medium">
                        <i class="fas fa-external-link-alt mr-1"></i>
                        Lihat Website
                    </a>
                </div>
                
                <div class="flex items-center">
                    <span class="text-gray-700 mr-4">
                        <i class="fas fa-user mr-1"></i>
                        ${user.name}
                    </span>
                    <a href="/admin/logout" class="text-red-600 hover:text-red-700 px-3 py-2 rounded-md text-sm font-medium">
                        <i class="fas fa-sign-out-alt mr-1"></i>
                        Logout
                    </a>
                </div>
            </div>
        </div>
    </nav>
  `;
}
export default inquiries;