<%- include('partials/sidebar', { activePage: 'customers', company }) %>
<%= t('admin.customers.manage_title', 'Manajemen Pelanggan') %>
<%= (typeof session !== 'undefined' && session && session.isCashier) ? t('admin.role.cashier', 'Kasir') : t('admin.role.admin', 'Admin') %>
<% if (msg) { %>
<%= msg.text %>
<% } %>
<%= t('admin.customers.stats.total', 'Total') %>
<%= stats.total %>
<% if (!filterStatus) { %>
<%= t('admin.cust.filter_active','Filter Aktif') %>
<% } %>
<%= t('admin.customers.stats.active', 'Aktif') %>
<%= stats.active %>
<% if (filterStatus === 'active') { %>
<%= t('admin.cust.filter_active','Filter Aktif') %>
<% } %>
<%= t('admin.customers.stats.suspended', 'Disuspend') %>
<%= stats.suspended %>
<% if (filterStatus === 'suspended') { %>
<%= t('admin.cust.filter_active','Filter Aktif') %>
<% } %>
<%= t('admin.customers.stats.inactive', 'Pendaftar Baru (Nonaktif)') %>
<%= stats.inactive %>
<% if (filterStatus === 'inactive') { %>
<%= t('admin.cust.filter_active','Filter Aktif') %>
<% } %>
<%= t('admin.customers.list', 'Daftar Pelanggan') %> (<%= customers.length %>)
Stiker ONU <%= t('admin.customers.export_excel', 'Export Excel') %>
<% if (typeof routers !== 'undefined' && routers && routers.length > 0) { %> <% } %> <% if (search || filterStatus || selectedRouterId || filterPackage || filterCollector || filterOlt || filterConn || filterBilling || filterAuto) { %> <%= t('common.reset', 'Reset') %><% } %>
<% if (customers.length === 0) { %> <% } %> <% customers.forEach((c, i) => { %> <% }) %>
# <%= t('admin.customers.table.name', 'Nama') %> <%= t('admin.customers.table.phone_tag', 'Telepon / Tag ONU') %> <%= t('admin.customers.table.package', 'Paket') %> <%= t('admin.cust.f_mikrotik_conn','Koneksi MikroTik') %> <%= t('admin.customers.table.address', 'Alamat') %> <%= t('admin.customers.table.status', 'Status') %> <%= t('admin.customers.table.unpaid', 'Tagihan Belum Bayar') %> <%= t('admin.customers.table.actions', 'Aksi') %>
<%= t('admin.customers.empty', 'Belum ada pelanggan') %>
<%= i+1 %> <%= c.name %><% var _miss=[]; if(!c.phone)_miss.push('HP'); if(!c.lat||!c.lng)_miss.push('koordinat'); if(!c.genieacs_tag)_miss.push('ACS'); %><% if(_miss.length===0){ %><% } else { %><% } %> <% if (c.customer_code) { %>
<%= c.customer_code %>
<% } %>
<%= c.phone || '-' %>
<% if (c.genieacs_tag) { %>
<%= c.genieacs_tag %>
<% } %>
<% if (c.package_name) { %>
<%= c.package_name %>
<%= (c.speed_down/1000).toFixed(0) %>/<%= (c.speed_up/1000).toFixed(0) %> Mbps • Rp <%= c.package_price ? c.package_price.toLocaleString('id-ID') : '-' %>
<% if (c.package_billing_type === 'prepaid' || c.expired_at) { %> <% const expDateStr = c.expired_at ? String(c.expired_at).slice(0, 10) : '-'; const isExpired = c.expired_at ? (new Date(c.expired_at) < new Date()) : false; %>
Exp: <%= expDateStr %>
<% } %> <% } else { %>-<% } %>
<% const username = String(c.pppoe_username || c.hotspot_username || '').trim().toLowerCase(); const session = username && typeof activeSessionsMap !== 'undefined' && activeSessionsMap && activeSessionsMap.get ? activeSessionsMap.get(username) : null; const isOnline = !!session; const rxBytes = session && session.bytesIn ? session.bytesIn : (c.bytes_in || 0); const txBytes = session && session.bytesOut ? session.bytesOut : (c.bytes_out || 0); function fmtB(b) { const num = Number(b) || 0; if (num <= 0) return '0 B'; const k = 1024; const sizes = ['B', 'KB', 'MB', 'GB', 'TB']; const i = Math.floor(Math.log(num) / Math.log(k)); return (num / Math.pow(k, i)).toFixed(1) + ' ' + sizes[i]; } %> <% if (isOnline) { %> ONLINE
<%= session.uptime %>
<%= session.ip %><% if (session.type) { %> (<%= session.type.toUpperCase() %>)<% } %>
<% } else { %> OFFLINE
Tidak Terhubung
<% } %>
RX: <%= fmtB(rxBytes) %> TX: <%= fmtB(txBytes) %>
<%= c.address || '-' %>
<% if (c.area) { %>
<%= c.area %>
<% } %>
<% if (c.status==='active') { %><%= t('admin.customers.filter.active', 'Aktif') %> <% } else if (c.status==='suspended') { %><% if (c.deactivate_cause==='auto_unpaid') { %> <%= t('admin.cust.inactive','Nonaktif') %> (auto)<% } else { %><%= t('admin.customers.filter.suspended', 'Suspend') %><% } %> <% } else { %><%= t('admin.customers.filter.inactive', 'Nonaktif') %><% } %> <% if (c.status === 'inactive' && (c.reg_total || c.reg_due_date || c.reg_voucher_code)) { %>
Est: Rp <%= Number(c.reg_total||0).toLocaleString('id-ID') %> <% if (c.reg_due_date) { %> • JT <%= c.reg_due_date %><% } %> <% if (c.reg_voucher_code) { %> • <%= c.reg_voucher_code %><% } %>
<% } %>
<%= t('admin.customers.auto_isolate.label', 'Auto Isolir') %>: <%= c.auto_isolate === 0 ? t('admin.customers.auto_isolate.off', 'OFF') : t('admin.customers.auto_isolate.date_prefix', 'Tgl ') + (c.isolate_day || 10) %>
<% if (c.unpaid_count > 0) { %> <%= c.unpaid_count %> <%= t('admin.customers.unpaid_suffix', 'tagihan') %> <% } else { %><%= t('admin.customers.paid_label', 'Lunas') %><% } %> <% if (c.status === 'inactive') { %> <% } %> <% if (typeof session !== 'undefined' && session && !session.isCashier) { %> <% if (c.package_id && (c.package_promo_cycles || 0) > 0) { %> <% } %> <% if (c.package_id && c.install_date && c.package_prorate_first_invoice) { %> <% } %> <% } %> <% if (!c.pppoe_username) { %> <% } %>
<% if (c.status === 'inactive') { %>
<% } %>
Cetak Stiker ONU <% if (typeof session !== 'undefined' && session && !session.isCashier) { %> <% if (c.package_id && (c.package_promo_cycles || 0) > 0) { %> <% } %> <% if (c.package_id && c.install_date && c.package_prorate_first_invoice) { %> <% } %> <% } %> <% if (!c.pppoe_username) { %> <% } %>
<%= t('admin.cust.add_customer','Tambah Pelanggan Baru') %>
<% const isRadiusActive = (typeof settings !== 'undefined' && settings && String(settings.radius_enabled) === '1'); %> <% if (isRadiusActive) { %>
<%= t('admin.cust.auth_mode','Mode Autentikasi Pelanggan (Utama)') %> <%= t('admin.cust.f_mikrotik_api','Diutamakan MikroTik API') %>
Mode MikroTik API mengelola kredensial PPP langsung di menu /ppp secret RouterOS MikroTik.
<% } else { %> <% } %>
<%= t('admin.cust.sec_personal','Informasi Pribadi Pelanggan') %>
Paket & Akses Jaringan (MikroTik / RADIUS)
<% if (isRadiusActive) { %>
<% } else { %> <% } %>
<%= isRadiusActive ? t('admin.cust.modem_hint','Kredensial login modem pelanggan untuk RADIUS & PPPoE.') : t('admin.cust.modem_hint_mt','Kredensial login modem pelanggan untuk PPPoE MikroTik API.') %>
Penagihan, Kolektor, & <%= t('admin.cust.status','Status Akun') %>
Infrastruktur (OLT, ODP, & Peta)
<%= t('admin.cust.btn_import','Import Pelanggan') %>

Unggah file Excel (.xlsx). Pastikan format kolom sesuai dengan hasil Export.

Unduh format excel

<%= t('admin.cust.btn_edit','Edit Pelanggan') %>
<% if (isRadiusActive) { %>
<%= t('admin.cust.auth_mode','Mode Autentikasi Pelanggan (Utama)') %> <%= t('admin.cust.f_mikrotik_api','Diutamakan MikroTik API') %>
Mode MikroTik API mengelola kredensial PPP langsung di menu /ppp secret RouterOS MikroTik.
<% } else { %> <% } %>
<%= t('admin.cust.sec_personal','Informasi Pribadi Pelanggan') %>
Paket & Akses Jaringan (MikroTik / RADIUS)
<%= t('admin.cust.modem_hint','Kredensial login modem pelanggan untuk RADIUS & PPPoE.') %>
Penagihan, Kolektor, & <%= t('admin.cust.status','Status Akun') %>
<%= t('admin.cust.reg_hint','Otomatis dihitung saat pasang/bayar. Bisa disesuaikan manual jika perlu.') %>
Infrastruktur (OLT, ODP, & Peta)
<%= t('admin.customers.generate_invoice_title', 'Generate Tagihan (Pelanggan)') %>
<%= t('admin.customers.generate_invoice_hint', 'Tagihan hanya dibuat untuk pelanggan yang dipilih. Jika sudah ada, tidak akan dibuat ulang.') %>
<%= t('admin.customers.pay_invoice_title', 'Bayar Tagihan (Pelanggan)') %>
<%= t('admin.customers.pay_invoice_hint', 'Untuk pembayaran di muka: pilih periode. Jika tagihan belum ada, sistem akan membuat tagihan lalu langsung menandai Lunas.') %>
<% const payMns = (lang === 'en') ? ['January','February','March','April','May','June','July','August','September','October','November','December'] : ['Januari','Februari','Maret','April','Mei','Juni','Juli','Agustus','September','Oktober','November','Desember']; for(let m=1;m<=12;m++){%> <% } %>
<% const payByDefault = (typeof session !== 'undefined' && session && session.isCashier) ? (`Kasir ${(session.cashierName || '').trim()}` + ((session.cashierUsername || '').trim() ? ` (@${String(session.cashierUsername).trim()})` : '')).trim() : 'Admin'; %>
<%= t('admin.cust.pick_location','Pilih Lokasi Pelanggan') %>
<%= t('admin.cust.map_hint','Geser penanda (marker) atau klik pada peta untuk menentukan lokasi yang akurat.') %>
<%= t('admin.cust.modal_title','Detail & Informasi Koneksi Pelanggan') %>
-
<%= t('admin.cust.lbl_cust_id','ID Pelanggan:') %> -
<%= t('admin.cust.sec_mikrotik','Informasi Koneksi MikroTik') %>
Username PPPoE / Hotspot-
Password PPPoE / Hotspot-
IP Address (Sesi / Static)-
MAC Address / Caller-ID-
<%= t('admin.cust.router_target','Router Target') %>-
<%= t('admin.cust.conn_type','Tipe Koneksi') %>-
<%= t('admin.cust.uptime_session','Uptime Sesi Active') %>-
<%= t('admin.cust.traffic_stats','Statistik Trafik Data') %>
RX (Download)
-
0 Bytes
TX (Upload)
-
0 Bytes
<%= t('admin.cust.fup_total','Total Kuota Terpakai (FUP):') %> 0 GB
<%= t('admin.cust.sec_info','Informasi Pelanggan') %>
<%= t('admin.cust.nik','No. Identitas (KTP/SIM/Paspor)') %>-
<%= t('admin.cust.phone','No. Telepon / WhatsApp') %>-
<%= t('admin.cust.sec_addr_area','Alamat & Area') %>-
<%= t('admin.cust.pkg','Paket Internet') %>-
<%= t('admin.cust.validity','Masa Aktif (Prabayar)') %>-
<%= t('admin.cust.onu_tag','Tag ONU (GenieACS)') %>-
<%- t('admin.cust.status_auto','Status Akun & Auto-Isolir') %>-
<%- t('admin.cust.calc_reg','Kalkulator Prorata — Setujui Pendaftar') %>
Prorata PaketRp 0
<%= t('admin.cust.f_install_fee','Biaya Pasang') %>Rp 0
<%= t('admin.cust.f_voucher_disc','Diskon Voucher') %>- Rp 0
Total Bayar AwalRp 0