diff --git a/.gitignore b/.gitignore index 9b1ee42..a6b017f 100755 --- a/.gitignore +++ b/.gitignore @@ -58,6 +58,7 @@ build/Release node_modules/ jspm_packages/ +tokens/ # Snowpack dependency directory (https://snowpack.dev/) diff --git a/assets/admin.js b/assets/admin.js new file mode 100644 index 0000000..3a41ee0 --- /dev/null +++ b/assets/admin.js @@ -0,0 +1,79 @@ +const socket = io(socket_server); // Connects to your server + +function reloadTheTable() { + if (document.getElementById('tb-paket')) { + // If tb-paket is a DataTable instance + $('#tb-paket').DataTable().destroy(); + reloadTable(); + } +} + + +socket.on('connect', () => { + console.log('Connected to server:', socket.id); +}); + + + +// notifikasi pengiriman baru oleh user +socket.on('pengiriman_baru_client', (data) => { + const sound = new Audio('/sound/notif.mp3'); + sound.play().catch(() => {}); + toastr.info("Ada Pengiriman Baru"); + // check if tb-paket is available , if available destroy then reloadTable() + reloadTheTable(); + + // console.log(data); +}); + +// notifikasi pembatalan paket dilakukan oleh kurir +socket.on('pembatalan_paket_kurir', (data) => { + const sound = new Audio('/sound/notif.mp3'); + sound.play().catch(() => {}); + toastr.warning("Kurir Membatalkan Pengambilan Paket No Resi " + data._id + "\nAlasan: " + data.alasan + "\nAdmin dapat menugaskan Kurir Baru atau Membatalkan Pengiriman."); + // check if tb-paket is available , if available destroy then reloadTable() + reloadTheTable(); +}); + +// notifikasi kurir dalam perjalanan mengambil paket +socket.on('kurir_mengambil_pengiriman_admin', (data) => { + const sound = new Audio('/sound/notif.mp3'); + sound.play().catch(() => {}); + toastr.info("Kurir Menyetujui Pengambilan Paket No Resi " + data._id + " dan Dalam Perjalanan Mengambil Paket di Alamat Pengirim : " + data.alamat_pengirim + ""); + // check if tb-paket is available , if available destroy then reloadTable() + reloadTheTable(); +}); + + +// notifikasi kurir mengambil paket dari pengirim dan mengantarkan ke penerima +socket.on('kurir_menghantar_ke_penerima_admin', (data) => { + const sound = new Audio('/sound/notif.mp3'); + sound.play().catch(() => {}); + // console.log(data); + if(data.status == 'Mengirim Paket Ke Alamat Penerima') { + toastr.info("Kurir Telah Mengambil Paket No Resi " + data._id + " dari Pengirim dan Dalam Perjalanan Mengantarkan ke Penerima di Alamat Penerima : " + data.alamat_penerima + ""); + }else { + toastr.success("Kurir Telah Mengantarkan Paket No Resi " + data._id + " ke Penerima di Alamat Penerima : " + data.alamat_penerima + ""); + } + + // check if tb-paket is available , if available destroy then reloadTable() + reloadTheTable(); +}); + +// notifikasi verifikasi paket diterima oleh user +socket.on('diterima_terverifikasi_admin', (data) => { + console.log(data); + const sound = new Audio('/sound/notif.mp3'); + sound.play().catch(() => {}); + toastr.success("Paket No Resi " + data._id + " Telah Diterima dan diverifikasi oleh Pengirim"); + // check if tb-paket is available , if available destroy then reloadTable() + reloadTheTable(); +}); + + +// tiada notifikasi sebab pengirim yang membatalkan pengiriman +socket.on('delete_kiriman_admin', (data) => { + console.log(data); + + reloadTheTable(); +}); diff --git a/assets/kurir.js b/assets/kurir.js new file mode 100644 index 0000000..c980af2 --- /dev/null +++ b/assets/kurir.js @@ -0,0 +1,40 @@ +const url = new URL(window.location.href); // or use your URL string instead +const pathSegments = url.pathname.split('/').filter(Boolean); + +// Check if 'kurir' is present and if there's something after it +const index = pathSegments.indexOf('kurir'); +const hasParamAfterKurir = index !== -1 && index < pathSegments.length - 1; + +console.log(hasParamAfterKurir); // true or false + +const socket = io(socket_server); // Connects to your server + + +socket.on('connect', () => { + console.log('Connected to server:', socket.id); +}); + +function reloadTheTable() { + if (document.getElementById('tb-paket')) { + // If tb-paket is a DataTable instance + $('#tb-paket').DataTable().destroy(); + reloadTable(); + } +} +console.log(global_data._id); +socket.on('kurir_ditugaskan_' + global_data._id, (data) => { + const sound = new Audio('/sound/notif.mp3'); + sound.play().catch(() => {}); + toastr.info("Ada Pengiriman Baru Ditugaskan Untuk Anda"); + // check if tb-paket is available , if available destroy then reloadTable() + reloadTheTable(); + + // console.log(data); +}); + +document.getElementById('h5-title').innerHTML = global_data.nama; + +$("#img-avatar").attr("src", hasParamAfterKurir? 'kurir/' + global_data.gambar_kurir : 'kurir/kurir/' + global_data.gambar_kurir); +$("#img-avatar").css("width", "65px"); +$("#img-avatar").css("height", "65px"); + diff --git a/assets/my-js.js b/assets/my-js.js index 5e113f8..7b4891c 100755 --- a/assets/my-js.js +++ b/assets/my-js.js @@ -1,11 +1,20 @@ +let socket_server; + +if (window.location.hostname === "20.20.20.26" && window.location.port === "3011") { + socket_server = "http://20.20.20.26:3014"; +} else { + socket_server = "https://socket-shenior.mywork-kkk.online"; +} + +console.log("Socket server:", socket_server); function logout() { return swal({ title: "Yakin?", text: "Anda akan keluar dari sistem", - type: "warning", + type: "warning", showCancelButton: !0, - confirmButtonColor: "#DD6B55", - confirmButtonText: "Ya, logout!", + confirmButtonColor: "#DD6B55", + confirmButtonText: "Ya, logout!", cancelButtonText: "Tidak, batal!", closeOnConfirm: !1, closeOnCancel: !1, @@ -16,7 +25,7 @@ function logout() { localStorage.removeItem('user'); localStorage.removeItem('role'); window.location.href = "/" - }else{ + } else { // close swal swal.close() } @@ -75,7 +84,31 @@ function enableInput(stat) { } + + function numberOnly(element) { //only number and remove comma element.value = element.value.replace(/[^0-9]/g, ''); element.value = element.value.replace(/,/g, ''); -} \ No newline at end of file +} + +function formatToMakassar(dateString) { + const dateObj = new Date(dateString); + + const options = { + timeZone: 'Asia/Makassar', + year: 'numeric', + month: '2-digit', + day: '2-digit', + hour: '2-digit', + minute: '2-digit', + second: '2-digit', + hour12: false, + }; + + const parts = new Intl.DateTimeFormat('id-ID', options).formatToParts(dateObj); + + const getPart = (type) => parts.find(p => p.type === type)?.value ?? ''; + + // Format: DD-MM-YYYY, HH.mm.ss + return `${getPart('day')}-${getPart('month')}-${getPart('year')}, ${getPart('hour')}.${getPart('minute')}.${getPart('second')}`; +} diff --git a/assets/sound/notif.mp3 b/assets/sound/notif.mp3 new file mode 100644 index 0000000..0e7c152 Binary files /dev/null and b/assets/sound/notif.mp3 differ diff --git a/assets/user.js b/assets/user.js new file mode 100644 index 0000000..c5a6d1a --- /dev/null +++ b/assets/user.js @@ -0,0 +1,76 @@ +const socket = io(socket_server); // Connects to your server + + +socket.on('connect', () => { + console.log('Connected to server:', socket.id); +}); + +function reloadTheTable() { + // check if tb-paket is available , if available destroy then reloadTable() + if (document.getElementById('tb-paket')) { + // If tb-paket is a DataTable instance + $('#tb-paket').DataTable().destroy(); + reloadTable(); + } +} + + +// notifikasi pembatalan paket oleh kurir +socket.on('pembatalan_paket_' + global_data._id, (data) => { + const sound = new Audio('/sound/notif.mp3'); + sound.play().catch(() => { }); + toastr.warning(`Pembatalan Pengiriman Paket
Status: ${data.status}`); + console.log(data); + // check if tb-paket is available , if available destroy then reloadTable() + reloadTheTable(); + + // console.log(data); +}); + + +// notifikasi kurir ditugaskan oleh admin +socket.on('kurir_ditugaskan_' + global_data._id, (data) => { + const sound = new Audio('/sound/notif.mp3'); + sound.play().catch(() => { }); + toastr.info(`Kurir Telah Ditugaskan Untuk Pengiriman Paket
No Resi: ${data._id}\nSila Liat Detail Pengiriman Untuk Informasi Lebih Lanjut`); + console.log(data); + // check if tb-paket is available , if available destroy then reloadTable() + reloadTheTable(); + + // console.log(data); +}); + + +// notifikasi pembatalan paket yang dilakukan oleh kurir +socket.on('pembatalan_paket_kurir_' + global_data._id, (data) => { + const sound = new Audio('/sound/notif.mp3'); + sound.play().catch(() => { }); + toastr.warning("Kurir Membatalkan Pengambilan Paket No Resi " + data._id + "\nAdmin akan menugaskan Kurir Baru.\nMohon Maaf dan Harap Tunggu."); + // check if tb-paket is available , if available destroy then reloadTable() + reloadTheTable(); +}); + + +// notifikasi kurir dalam perjalanan mengambil paket +socket.on('kurir_mengambil_pengiriman_' + global_data._id, (data) => { + const sound = new Audio('/sound/notif.mp3'); + sound.play().catch(() => { }); + toastr.info("Kurir Dalam Perjalanan Mengambil Paket No Resi " + data._id + "\nDiharap Pengirim Menunggu Kurir Sampai"); + // check if tb-paket is available , if available destroy then reloadTable() + reloadTheTable(); +}); + +// notifikasi kurir mengambil paket dari pengirim dan mengantarkan ke penerima +socket.on('kurir_menghantar_ke_penerima_' + global_data._id, (data) => { + const sound = new Audio('/sound/notif.mp3'); + sound.play().catch(() => { }); + // console.log(data) + if (data.status == 'Mengirim Paket Ke Alamat Penerima') { + toastr.info("Kurir Telah Mengambil Paket No Resi " + data._id + " dari Pengirim dan Dalam Perjalanan Mengantarkan ke Penerima di Alamat Penerima : " + data.alamat_penerima + ""); + }else { + toastr.success("Kurir Telah Mengantarkan Paket No Resi " + data._id + " ke Penerima di Alamat Penerima : " + data.alamat_penerima + ""); + } + // check if tb-paket is available , if available destroy then reloadTable() + reloadTheTable(); +}); + diff --git a/bot.ts b/bot.ts index 99ee71e..e838c7f 100644 --- a/bot.ts +++ b/bot.ts @@ -1,8 +1,16 @@ import { create, Whatsapp } from 'venom-bot'; import express, { type Request, type Response } from 'express'; +import type { UploadedFile } from 'express-fileupload'; let client: Whatsapp; +function convertToPhoneNumber(number: string): number { + if (number.startsWith('0')) { + number = number.slice(1); + } + return parseInt(`62${number}`); +} + async function initBot() { try { client = await create({ @@ -32,15 +40,8 @@ function startServer() { app.post('/send-otp', async (req: Request, res: Response) => { let { number, otp } = req.body; - - // remove the 0 in front of the number - if (number.startsWith('0')) { - number = number.slice(1); - } - // add +62 to the number - number = `+62${number}`; - // convert to int - number = parseInt(number); + + number = convertToPhoneNumber(number); console.log(`Sending OTP ${otp} to ${number}`); const formattedNumber = `${number}@c.us`; @@ -68,6 +69,28 @@ function startServer() { } }); + app.post('/send-message', async (req: Request, res: Response) => { + let { number, message, img_stat = false , foto_paket , foto_name} = req.body; + + + console.log(number, message, img_stat); + + number = convertToPhoneNumber(number); + + const formattedNumber = `${number}@c.us`; + try { + if(img_stat){ + await client.sendImage(formattedNumber, foto_paket, foto_name, message); + }else{ + await client.sendText(formattedNumber, message); + } + res.status(200).json({ success: true }); + } catch (error) { + console.error(error); + res.status(500).json({ error: 'Failed to send message.' }); + } + }); + const PORT = 3012; app.listen(PORT, () => { console.log(`WhatsApp bot API listening on http://localhost:${PORT}`); diff --git a/bun.lockb b/bun.lockb index 704035c..7cb7ae0 100755 Binary files a/bun.lockb and b/bun.lockb differ diff --git a/images/kiriman/6834bbead8098fbcd6f521f5/4ljb9-—Pngtree—cute hijab girl receive package_6843094.png b/images/kiriman/6834bbead8098fbcd6f521f5/4ljb9-—Pngtree—cute hijab girl receive package_6843094.png new file mode 100644 index 0000000..8d8ada8 Binary files /dev/null and b/images/kiriman/6834bbead8098fbcd6f521f5/4ljb9-—Pngtree—cute hijab girl receive package_6843094.png differ diff --git a/images/kiriman/6834bbead8098fbcd6f521f5/barang salah.jpeg b/images/kiriman/6834bbead8098fbcd6f521f5/barang salah.jpeg new file mode 100644 index 0000000..2119754 Binary files /dev/null and b/images/kiriman/6834bbead8098fbcd6f521f5/barang salah.jpeg differ diff --git a/images/kiriman/6834bbead8098fbcd6f521f5/tdzpi-cloud'.png b/images/kiriman/6834bbead8098fbcd6f521f5/tdzpi-cloud'.png new file mode 100644 index 0000000..dbbd0ca Binary files /dev/null and b/images/kiriman/6834bbead8098fbcd6f521f5/tdzpi-cloud'.png differ diff --git a/images/kiriman/684b4d814668889d04c4d76f/—Pngtree—cute hijab girl receive package_6843094.png b/images/kiriman/684b4d814668889d04c4d76f/—Pngtree—cute hijab girl receive package_6843094.png new file mode 100644 index 0000000..8d8ada8 Binary files /dev/null and b/images/kiriman/684b4d814668889d04c4d76f/—Pngtree—cute hijab girl receive package_6843094.png differ diff --git a/images/kiriman/6857ac770d7f62130cfc8cd6/barang salah.jpeg b/images/kiriman/6857ac770d7f62130cfc8cd6/barang salah.jpeg new file mode 100644 index 0000000..2119754 Binary files /dev/null and b/images/kiriman/6857ac770d7f62130cfc8cd6/barang salah.jpeg differ diff --git a/images/kiriman/6857b008951f8e2c637e78b1/ansible.webp b/images/kiriman/6857b008951f8e2c637e78b1/ansible.webp new file mode 100644 index 0000000..c5a331a Binary files /dev/null and b/images/kiriman/6857b008951f8e2c637e78b1/ansible.webp differ diff --git a/images/kiriman/6857c0a816895f660007052d/17505813016229134761528170500578.jpg b/images/kiriman/6857c0a816895f660007052d/17505813016229134761528170500578.jpg new file mode 100644 index 0000000..99b218b Binary files /dev/null and b/images/kiriman/6857c0a816895f660007052d/17505813016229134761528170500578.jpg differ diff --git a/images/kiriman/6857c0a816895f660007052d/98yqd-17505817103335653876403672777924.jpg b/images/kiriman/6857c0a816895f660007052d/98yqd-17505817103335653876403672777924.jpg new file mode 100644 index 0000000..af3c5c4 Binary files /dev/null and b/images/kiriman/6857c0a816895f660007052d/98yqd-17505817103335653876403672777924.jpg differ diff --git a/images/kiriman/6857c0a816895f660007052d/q40j2-17505817658111173313469910788624.jpg b/images/kiriman/6857c0a816895f660007052d/q40j2-17505817658111173313469910788624.jpg new file mode 100644 index 0000000..283f431 Binary files /dev/null and b/images/kiriman/6857c0a816895f660007052d/q40j2-17505817658111173313469910788624.jpg differ diff --git a/images/kiriman/6857c2dd16895f6600070590/17505819315367465573761214454608.jpg b/images/kiriman/6857c2dd16895f6600070590/17505819315367465573761214454608.jpg new file mode 100644 index 0000000..8e3a043 Binary files /dev/null and b/images/kiriman/6857c2dd16895f6600070590/17505819315367465573761214454608.jpg differ diff --git a/images/kiriman/6857c39b16895f66000705bd/17505821538948858467695520102822.jpg b/images/kiriman/6857c39b16895f66000705bd/17505821538948858467695520102822.jpg new file mode 100644 index 0000000..9c42cdc Binary files /dev/null and b/images/kiriman/6857c39b16895f66000705bd/17505821538948858467695520102822.jpg differ diff --git a/images/kurir/081244893900_kurir_06ztb.jpg b/images/kurir/081244893900_kurir_06ztb.jpg new file mode 100644 index 0000000..7cbcfa5 Binary files /dev/null and b/images/kurir/081244893900_kurir_06ztb.jpg differ diff --git a/images/kurir/081582333721_kurir_p66ks.jpg b/images/kurir/081582333721_kurir_p66ks.jpg new file mode 100644 index 0000000..384bc89 Binary files /dev/null and b/images/kurir/081582333721_kurir_p66ks.jpg differ diff --git a/images/kurir/081678003156_kurir_gpwls.jpg b/images/kurir/081678003156_kurir_gpwls.jpg new file mode 100644 index 0000000..9ef724d Binary files /dev/null and b/images/kurir/081678003156_kurir_gpwls.jpg differ diff --git a/images/kurir/081977350301_kurir_l36ti.jpg b/images/kurir/081977350301_kurir_l36ti.jpg new file mode 100644 index 0000000..914c2d3 Binary files /dev/null and b/images/kurir/081977350301_kurir_l36ti.jpg differ diff --git a/images/kurir/082314210507_kurir_kjfjl.jpg b/images/kurir/082314210507_kurir_kjfjl.jpg new file mode 100644 index 0000000..24c9e91 Binary files /dev/null and b/images/kurir/082314210507_kurir_kjfjl.jpg differ diff --git a/images/kurir/082570745818_kurir_vidsa.jpg b/images/kurir/082570745818_kurir_vidsa.jpg new file mode 100644 index 0000000..17b8b71 Binary files /dev/null and b/images/kurir/082570745818_kurir_vidsa.jpg differ diff --git a/images/kurir/083853755002_kurir_5741p.jpg b/images/kurir/083853755002_kurir_5741p.jpg new file mode 100644 index 0000000..57e0443 Binary files /dev/null and b/images/kurir/083853755002_kurir_5741p.jpg differ diff --git a/images/kurir/085278112570_kurir_ng2vg.jpg b/images/kurir/085278112570_kurir_ng2vg.jpg new file mode 100644 index 0000000..e9ebc2b Binary files /dev/null and b/images/kurir/085278112570_kurir_ng2vg.jpg differ diff --git a/images/kurir/085756776681_kurir_i8br6.jpg b/images/kurir/085756776681_kurir_i8br6.jpg new file mode 100644 index 0000000..3278ed2 Binary files /dev/null and b/images/kurir/085756776681_kurir_i8br6.jpg differ diff --git a/images/kurir/085775502450_kurir_w13zk.jpg b/images/kurir/085775502450_kurir_w13zk.jpg new file mode 100644 index 0000000..2fd16b1 Binary files /dev/null and b/images/kurir/085775502450_kurir_w13zk.jpg differ diff --git a/images/kurir/0895325697978_kurir_bcpys.jpg b/images/kurir/0895325697978_kurir_bcpys.jpg new file mode 100644 index 0000000..cf24807 Binary files /dev/null and b/images/kurir/0895325697978_kurir_bcpys.jpg differ diff --git a/images/kurir/0895805574850_kurir_p6wfb.jpg b/images/kurir/0895805574850_kurir_p6wfb.jpg new file mode 100644 index 0000000..d6ae655 Binary files /dev/null and b/images/kurir/0895805574850_kurir_p6wfb.jpg differ diff --git a/images/kurir/6288202103760_kurir_rvvv1.jpg b/images/kurir/6288202103760_kurir_rvvv1.jpg new file mode 100644 index 0000000..77f0b35 Binary files /dev/null and b/images/kurir/6288202103760_kurir_rvvv1.jpg differ diff --git a/images/motor/081244893900_motor_06ztb.jpg b/images/motor/081244893900_motor_06ztb.jpg new file mode 100644 index 0000000..e13651d Binary files /dev/null and b/images/motor/081244893900_motor_06ztb.jpg differ diff --git a/images/motor/081582333721_motor_p66ks.jpg b/images/motor/081582333721_motor_p66ks.jpg new file mode 100644 index 0000000..0acef50 Binary files /dev/null and b/images/motor/081582333721_motor_p66ks.jpg differ diff --git a/images/motor/081678003156_motor_gpwls.jpg b/images/motor/081678003156_motor_gpwls.jpg new file mode 100644 index 0000000..625f5bc Binary files /dev/null and b/images/motor/081678003156_motor_gpwls.jpg differ diff --git a/images/motor/081977350301_motor_l36ti.jpg b/images/motor/081977350301_motor_l36ti.jpg new file mode 100644 index 0000000..65b345f Binary files /dev/null and b/images/motor/081977350301_motor_l36ti.jpg differ diff --git a/images/motor/082314210507_motor_kjfjl.jpg b/images/motor/082314210507_motor_kjfjl.jpg new file mode 100644 index 0000000..156b234 Binary files /dev/null and b/images/motor/082314210507_motor_kjfjl.jpg differ diff --git a/images/motor/082570745818_motor_vidsa.jpg b/images/motor/082570745818_motor_vidsa.jpg new file mode 100644 index 0000000..860a0f6 Binary files /dev/null and b/images/motor/082570745818_motor_vidsa.jpg differ diff --git a/images/motor/083853755002_motor_5741p.jpg b/images/motor/083853755002_motor_5741p.jpg new file mode 100644 index 0000000..2026719 Binary files /dev/null and b/images/motor/083853755002_motor_5741p.jpg differ diff --git a/images/motor/085278112570_motor_ng2vg.jpg b/images/motor/085278112570_motor_ng2vg.jpg new file mode 100644 index 0000000..8037fa6 Binary files /dev/null and b/images/motor/085278112570_motor_ng2vg.jpg differ diff --git a/images/motor/085756776681_motor_i8br6.jpg b/images/motor/085756776681_motor_i8br6.jpg new file mode 100644 index 0000000..3bff4b5 Binary files /dev/null and b/images/motor/085756776681_motor_i8br6.jpg differ diff --git a/images/motor/085775502450_motor_w13zk.jpg b/images/motor/085775502450_motor_w13zk.jpg new file mode 100644 index 0000000..1bec20d Binary files /dev/null and b/images/motor/085775502450_motor_w13zk.jpg differ diff --git a/images/motor/0895325697978_motor_bcpys.jpg b/images/motor/0895325697978_motor_bcpys.jpg new file mode 100644 index 0000000..7c0a261 Binary files /dev/null and b/images/motor/0895325697978_motor_bcpys.jpg differ diff --git a/images/motor/0895805574850_motor_p6wfb.jpg b/images/motor/0895805574850_motor_p6wfb.jpg new file mode 100644 index 0000000..d6ae655 Binary files /dev/null and b/images/motor/0895805574850_motor_p6wfb.jpg differ diff --git a/images/motor/6288202103760_motor_rvvv1.jpg b/images/motor/6288202103760_motor_rvvv1.jpg new file mode 100644 index 0000000..6c57190 Binary files /dev/null and b/images/motor/6288202103760_motor_rvvv1.jpg differ diff --git a/images/user/6825d256a538bbaa8acf922a/1 1.jpeg b/images/user/6825d256a538bbaa8acf922a/1 1.jpeg new file mode 100644 index 0000000..d6ae655 Binary files /dev/null and b/images/user/6825d256a538bbaa8acf922a/1 1.jpeg differ diff --git a/index.ts b/index.ts index d920664..0690daa 100755 --- a/index.ts +++ b/index.ts @@ -1,16 +1,20 @@ // ini adalah file utama dari aplikasi ini import express, { type Request, type Response } from 'express'; -import http from 'http'; -import * as socket from './socket'; -const socket_client = socket.clientSocket; - - -// import formData from 'express-form-data'; +// import cors from 'cors'; import fileUpload from 'express-fileupload'; import {testDatabaseConnection} from './connection'; import path from 'path'; + +import { io, Socket } from 'socket.io-client'; + + + + + +const app = express(); + import adminRouter from './routes/admin_router'; import userRouter from './routes/user_router'; import kurirRouter from './routes/kurir_router'; @@ -21,13 +25,12 @@ import { config } from 'dotenv'; config(); console.log("diatas untuk dotenv"); +const socket_client: Socket = io(process.env.socket_server as string); -const app = express(); const port = process.env.PORT || 3011; -const server = http.createServer(app); -const io = socket.init(server); + @@ -43,6 +46,9 @@ app.use(fileUpload({ app.use(express.json()); app.use(express.urlencoded({ extended: true })); +// app.options('*', cors()) +// app.use(cors()) + @@ -53,48 +59,9 @@ app.use('/admin', adminRouter); app.use('/kurir', kurirRouter); app.use('/', userRouter); -io.on('connection', (socket) => { - const userID = socket.id; - // console.log('A user connected: ' + userID); +export { socket_client } - socket.on('scan_dia', (data: any) => { - console.log('Received scan_dia event: ' + data); - io.emit('scan_dia_lagi', "coba"); - // socket.broadcast.emit('scan_dia_lagi', "coba"); - // // cobadulu(); - // io.emit('scan_dia_lagi', 'ini coba'); - }); - - socket.on('scan_dia_lagi', (data: any) => { - console.log('Received scan_dia_lagi event: ' + data); - }); - - socket.on('disconnect', () => { - // console.log('User disconnected: ' + userID); - }); +app.listen(port, async () => { + console.log(`Server is running on port ${port}`); }); - -// function cobadulu(){ -// console.log("coba"); -// socket_client.emit('scan_dia_lagi', 'ini coba'); -// } - - - -// app.post('/submit', (req: Request, res: Response) => { -// console.log('Received form data:', req.body); -// res.json({ message: 'Form data received!', data: req.body }); -// }); - - - - -// app.listen(port, async () => { -// console.log(`Server is running on port ${port}`); -// }); -server.listen(port, () => { - console.log(`Server running on port ${port}`); -}); - -export default { app, server, io }; diff --git a/index1.ts b/index1.ts deleted file mode 100644 index 40b65b6..0000000 --- a/index1.ts +++ /dev/null @@ -1,43 +0,0 @@ - -import express from 'express'; -import { createServer } from 'http'; -import { Server } from 'socket.io'; -import path from 'path'; -import { fileURLToPath } from 'url'; - -const app = express(); -const server = createServer(app); -const io = new Server(server, { - cors: { - origin: "*", // allow all for dev - methods: ["GET", "POST"] - } -}); - -// Serve static files -const __filename = fileURLToPath(import.meta.url); -const __dirname = path.dirname(__filename); -app.use(express.static(path.join(__dirname, 'public'))); - -io.on('connection', (socket) => { - console.log('✅ A user connected:', socket.id); - - socket.on('scan_dia', (data: any) => { - console.log('📩 Received scan_dia:', data); - - }); - - socket.on('scan_dia_lagi', (data: any) => { - console.log('📩 Received scan_dia_lagi:', data); - // io.emit('scan_dia_lagi', "coba"); - }); - - socket.on('disconnect', () => { - console.log('❌ User disconnected:', socket.id); - }); -}); - -const PORT = 3011; -server.listen(PORT, () => { - console.log(`🚀 Server running at http://localhost:${PORT}`); -}); diff --git a/models/kiriman_model.ts b/models/kiriman_model.ts new file mode 100644 index 0000000..ca6155b --- /dev/null +++ b/models/kiriman_model.ts @@ -0,0 +1,40 @@ +import mongoose from "mongoose"; + +const timelineItemSchema = new mongoose.Schema({ + status: { type: String, required: true }, + waktu: { type: Date, default: Date.now }, + gambar: { type: String }, // optional image for this step + alasan: { type: String }, // optional text for this step + id_kurir: { type: String } +}, { _id: false }); // _id: false to prevent auto _id in sub-docs + +const kirimanSchema = new mongoose.Schema({ + id_pengirim: { type: String, required: true }, + no_telpon_pengirim: { type: String, required: true }, + nama_pengirim: { type: String, required: true }, + alamat_pengirim: { type: String, required: true }, + + no_telpon_penerima: { type: String, required: true }, + nama_penerima: { type: String, required: true }, + alamat_penerima: { type: String, required: true }, + + gambar_paket: { type: String, required: true }, + id_kurir: { type: String }, + + status: { type: String, default: 'Menunggu Admin Memproses' }, + + timeline: { + type: [timelineItemSchema], + default: () => ([{ + status: 'Menunggu Admin Memproses', + waktu: new Date() + }]) + } + +}, { + timestamps: true +}); + +const KirimanModel = mongoose.model('Kiriman_Collection', kirimanSchema); + +export default KirimanModel; diff --git a/package.json b/package.json index cfe4f31..312f288 100755 --- a/package.json +++ b/package.json @@ -16,12 +16,13 @@ "@types/express-fileupload": "^1.5.1", "@types/express-form-data": "^2.0.5", "axios": "^1.9.0", + "cors": "^2.8.5", "dotenv": "^16.4.7", "express": "^4.21.2", "express-fileupload": "^1.5.1", "express-form-data": "^2.0.23", + "form-data": "^4.0.3", "mongoose": "^8.12.1", - "socket.io": "^4.8.1", "socket.io-client": "^4.8.1", "venom-bot": "^5.3.0" } diff --git a/public/index.html b/public/index.html deleted file mode 100644 index a893b8c..0000000 --- a/public/index.html +++ /dev/null @@ -1,27 +0,0 @@ - - - - - - Receiver Page - - -

This is index.html (Receiver)

- - - - - - - - diff --git a/public/index2.html b/public/index2.html deleted file mode 100644 index 2669e39..0000000 --- a/public/index2.html +++ /dev/null @@ -1,26 +0,0 @@ - - - - - - Emitter Page - - -

This is index2.html (Emitter)

- - - - - - diff --git a/routes/admin_router.ts b/routes/admin_router.ts index c989da8..ad1ccef 100755 --- a/routes/admin_router.ts +++ b/routes/admin_router.ts @@ -2,9 +2,13 @@ import express from 'express'; import type { Request, Response } from 'express'; import type { UploadedFile } from 'express-fileupload'; +import KirimanModel from '../models/kiriman_model'; import path from 'path'; import fs from 'fs'; import KurirModel from '../models/kurir_model'; +import UserModel from '../models/user_model'; +import axios from 'axios'; +import { socket_client } from '../index'; const router = express.Router(); @@ -36,10 +40,10 @@ router.get('/kurir/gambar/:no_telpon/:jenis', (req: Request, res: Response) => { return } // Define file paths - const motorGambar = path.join(__dirname, '../images/'+ jenis +'/'+data.gambar_motor); - const kurirGambar = path.join(__dirname, '../images/kurir/'+data.gambar_kurir); + const motorGambar = path.join(__dirname, '../images/' + jenis + '/' + data.gambar_motor); + const kurirGambar = path.join(__dirname, '../images/kurir/' + data.gambar_kurir); - if(jenis == 'motor') { + if (jenis == 'motor') { res.sendFile(motorGambar); } else { res.sendFile(kurirGambar); @@ -106,7 +110,7 @@ router.post('/kurir', async (req: Request, res: Response) => { // Save to MongoDB const newKurir = new KurirModel({ no_telpon, - password : no_telpon, + password: no_telpon, nama, jenis_kelamin, dd_motor, @@ -126,6 +130,173 @@ router.post('/kurir', async (req: Request, res: Response) => { } }); +router.get('/check-kurir/tersedia', (req: Request, res: Response) => { + try { + // search by status = "Tersedia" || null || undefined + KurirModel.find({ status: { $in: ['Tersedia', null, undefined] } }).then((data) => { + res.json(data); + }); + } catch (error) { + console.log(error); + res.status(500).json([]); + } +}) + +router.get('/paket-baru', async (req: Request, res: Response) => { + try { + // search by status != "Dibatalkan Oleh Admin" + const response = await KirimanModel.find({ + status: { + $nin: ['Dibatalkan Oleh Admin','Paket Telah Diterima Penerima','Diterima Terverifikasi', "Dibatalkan Oleh Pengirim"], + $type: 'string' + } + }); + // console.log(response); + res.status(200).json(response); + } catch (error) { + console.log(error); + res.status(500).json([]); + } +}) + +router.get('/paket-all', async (req: Request, res: Response) => { + try { + // search by status != "Dibatalkan Oleh Admin" + const response = await KirimanModel.find(); + // console.log(response); + res.status(200).json(response); + } catch (error) { + console.log(error); + res.status(500).json([]); + } +}) + + +router.delete('/batalkan-pengiriman/', async (req: Request, res: Response) => { + try { + // const { id } = req.params; + const { alasan, id } = req.body; // optional reason from admin (e.g., from SweetAlert input) + // console.log(id, alasan); + + const updatedDoc = await KirimanModel.findByIdAndUpdate( + id, + { + $set: { + status: 'Dibatalkan Oleh Admin' + }, + $push: { + timeline: { + status: 'Dibatalkan Oleh Admin', + waktu: new Date(), + alasan: alasan || null + } + } + }, + { new: true } // Return the updated document + ); + // console.log(updatedDoc); + const userData = await UserModel.findById(updatedDoc?.id_pengirim); + + // console.log(userData) + socket_client.emit('pembatalan_paket', updatedDoc); + + try { + await axios.post('http://localhost:3012/send-message', { number: userData?.no_telpon, message: `🛵*_Kurir Shenior 🛵_*\nPengiriman anda dengan nomor resi ${updatedDoc?._id} telah dibatalkan oleh admin\nAlasan: *${alasan || 'Belum ada alasan'}* ❌❌` }); + } catch (err) { + console.log(err); + } + + + res.status(200).json("response"); + } catch (error) { + console.log(error); + res.status(500).json([]); + } +}); + +router.post('/tugaskan-kurir', async (req: Request, res: Response) => { + const { id_kiriman, id_kurir } = req.body; + console.log(id_kiriman, id_kurir); + try { + const updatedDoc = await KirimanModel.findByIdAndUpdate( + id_kiriman, + { + $set: { + status: 'Kurir Telah Ditugaskan', + id_kurir: id_kurir + }, + $push: { + timeline: { + status: 'Kurir Telah Ditugaskan', + waktu: new Date(), + // alasan: alasan || null + } + } + }, + { new: true } // Return the updated document + ); + + await KurirModel.findByIdAndUpdate( + id_kurir, + { + $set: { + status: 'Ditugaskan' + } + }, + { new: true } // Return the updated document + ); + + console.log(updatedDoc); + + socket_client.emit('tugaskan_kurir_server', updatedDoc); + + try { + const userData = await UserModel.findById(updatedDoc?.id_pengirim); + const kurirData = await KurirModel.findById(id_kurir); + await axios.post('http://localhost:3012/send-message', { number: userData?.no_telpon, message: `🛵 * _Kurir Shenior 🛵_*\nPengiriman anda dengan nomor resi ${updatedDoc?._id} \nStatus : *Kurir Telah DItugaskan*✅✅` }); + await axios.post('http://localhost:3012/send-message', { number: kurirData?.no_telpon, message: `🛵 *_Kurir Shenior 🛵_*\nAnda telah ditugaskan untuk mengirim paket\nNomor Resi : *${updatedDoc?._id}*\nAlamat Paket : _*${updatedDoc?.alamat_pengirim}* _\nSila buka situs Kurir Shenior dan login untuk detail lebih lanjut ✅✅` }); + } catch (err) { console.log(err) } + + res.status(200).json(updatedDoc); + + } catch (err) { + console.log(err); + res.status(500).json([]); + } +}); + + +// ini untuk user +router.get('/user', (req: Request, res: Response) => { + res.sendFile(__dirname + '/admin_ui/user.html'); +}); + +router.get('/user/data', async (req: Request, res: Response) => { + try { + const data = await UserModel.find(); + res.json(data); + } catch (error) { + console.log(error); + res.status(500).json([]); + } +}); + +router.get('/user/data/:id', async (req: Request, res: Response) => { + const { id } = req.params; + console.log(id, "ini id"); + try { + const data = await UserModel.findById(id); + res.json(data); + } catch (error) { + console.log(error); + res.status(500).json([]); + } +}); + +// ini untuk list penghantaran +router.get('/list', (req: Request, res: Response) => { + res.sendFile(__dirname + '/admin_ui/list.html'); +}); router.get('/login', (req: Request, res: Response) => { diff --git a/routes/admin_ui/index.html b/routes/admin_ui/index.html index 2e87411..b9a3728 100644 --- a/routes/admin_ui/index.html +++ b/routes/admin_ui/index.html @@ -1,5 +1,6 @@ + @@ -20,33 +21,42 @@ - + + + + + + + + + + -