Halo semuanya.
Saya bekerja di kantor. Pengembang perangkat lunak. Dan terkadang saya makan. Ya setiap hari. Majikan memberi kita makan siang - pekerja memesan makan siang untuk besok, dan besok pemasok makan siang membawakan apa yang dipesan karyawan. Apa yang diperintahkan dan apa yang dibawa tidak selalu bersamaan, tetapi ini tidak terjadi. Makan siang dipesan di halaman pesanan makan siang. Tapi ...
Tapi pertama-tama, tentang bagaimana halaman pesanan makan siang terbentuk: pemasok mengirim file XLS dengan daftar harga selama seminggu.
Contoh daftar harga yang dikirim oleh pemasokOrang yang bertanggung jawab untuk makan malam mem-parsing melalui utilitas yang dikembangkan oleh seseorang di perut perusahaan kami, menerjemahkannya ke dalam bentuk yang dapat ditampilkan oleh portal perusahaan kami. Dan dia menampilkannya ...
Tangkapan layar dengan makan malam yang dipesan
Cuplikan layar halaman pemesanan makan siangPosisi dibagi menjadi beberapa kategori. Informasi tentang nama dan komposisi dalam teks lengkap dan sulit dinavigasi.
Saya ingin mengerti bahwa lebih baik tidak memesan, dan apa yang dapat Anda coba, karena orang lain menyukainya. Artinya, saya ingin peringkat. Saya juga ingin menerima pesanan saya di Telegram sehingga saya tidak ingat apa yang saya pesan di ruang makan.
Jadi tujuannya jelas. Saya harus mengatakan segera: jalan yang telah diambil oleh rekan saya dan saya jauh dari yang paling benar dan rasional. Meski begitu: ini adalah permainan yang lengkap dalam hal arsitektur / keamanan / dukungan / toleransi kesalahan. Tetapi apa yang telah tumbuh telah tumbuh.
Kami tidak memiliki akses ke server, jadi Anda hanya dapat mengubah tampilan halaman dengan skrip pengguna. Tapi bagaimana dengan peringkat? Tidak ada akses ke database juga. Kita membutuhkan server untuk pemrosesan pesanan, penilaian, dan interaksi dengan Telegram. Peran ini diambil oleh server NodeJS.
Sisi server
Saya akan mengurus server, dan seorang rekan akan mengurus skrip pengguna yang menambahkan fungsionalitas ke halaman. Kami mengambil server nodejs, menghubungkan express, tambahkan MySQL.
Letakkan Sequelize di atas . Dan kami akan berinteraksi dengan Telegram melalui
node-telegram-bot-api :
Secara singkat tentang fungsionalitas:
Path
/ dinners / user_menu mengembalikan skrip pengguna:
res.sendFile(__dirname + '/public_html/user_script.js');
Ini dilakukan agar tidak mengganggu kolega yang menggunakannya dengan menginstal versi skrip baru. Dikoreksi - melemparkannya ke server - semua orang diperbarui.
Ya, saya tahu bahwa dari sudut pandang keamanan ini buruk, tetapi fungsi itu sendiri tidak kritis dan kami akan mempertimbangkan server tempat skrip disimpan cukup aman.
Selanjutnya, di sepanjang jalur
/ makan malam / r /: id, Anda bisa mendapatkan peringkat untuk semua posisi dan menyimpan peringkat, yaitu, memilih hidangan.
Path
/ dinners / kirim ulang /: id berfungsi untuk mengirim pesan ke Telegram. Teks pesan dihasilkan pada klien, hanya interaksi dengan Telegram yang terjadi di server:
const parseMode: TelegramBot.SendMessageOptions = {parse_mode: "HTML"}; await this.bot.sendMessage(telegramId, htmlMessage, {...options, ...parseMode});
Setelah itu, Bot mengirim pesan dengan urutan.

Selanjutnya, di sepanjang jalur
/ makan malam / pesanan ,
pesanan disimpan. Karena permintaan pesanan asli sulit untuk ditentukan (setelah mengklik tombol "Simpan", peringatan muncul dengan tombol konfirmasi pesanan), permintaan ke server dengan pesanan dikirim ketika halaman pesanan dimuat (dan seluruh sistem pesanan di situs dibagi menjadi 2 halaman - halaman pesanan dan halaman menu - Pilihan hidangan untuk hari tertentu - yaitu, pembentukan pesanan). Sangat tidak rasional untuk mengirim permintaan setiap kali Anda memasuki halaman pesanan, tetapi tidak ada opsi yang lebih baik untuk snap.
Akhirnya, jalur
/ makan malam / hari menentukan hari untuk memesan makan siang. Bagian dari fungsi ini telah muncul untuk operasi yang benar dari pengingat tentang pesanan yang belum selesai - Anda perlu tahu apa hari berikutnya dari pesanan itu (ada akhir pekan dan hari libur di tengah minggu). Alih-alih mengambil penerapan kalender produksi, saya hanya menguraikan tanggal pada halaman pesanan, di mana hari kerja dan non-kerja sudah ditandai (Anda tidak dapat melakukan pemesanan untuk hari yang tidak bekerja). Hari yang tidak bekerja ditandai di portal dengan kelas isHoliday:
Oh ya, gunakan jquery untuk memetik. Sangat mudah untuk mempelajari pohon halaman.
Bot telegram
Bagian lain dari keseluruhan add-on adalah bot telegram.
Dengan fungsi seperti ituMemperoleh ID adalah sistem identifikasi. Untuk mengaitkan skrip pengguna pada browser tertentu dengan userId di telegram.
Lihat pesanan hari ini, lihat daftar pesanan (5 terakhir), tetapkan pengingat.
Makan siang secara otomatis dikirim ke pemasok pada waktu yang sama setiap hari, jadi penting untuk melakukan pemesanan sebelum waktu tertentu, misalnya, 13:00.
Setelah itu, kemampuan untuk melakukan pemesanan diblokir.
Pengingat:
Bot memberikan kesempatan untuk memilih waktu pengingat: 9, 10 atau 11 jam.Selain itu, jika setelah pengingat Anda tidak melakukan pemesanan, maka setiap 10 menit berikutnya bot akan mengingatkan Anda tentang pesanan sampai Anda memesannya, atau sampai pesanan diblokir.
Ini dilakukan oleh tugas cron (menggunakan
node-schedule ):
schedule.scheduleJob('*/10 9-13 * * 1-5', async function() {
Bagian klien. Menu
Saya ulangi bahwa antarmuka saat ini dalam hubungannya dengan teks dari item menu yang dikirim pemasok hanya mengerikan (lihat layar 2). Dan pada satu titik, Anda berhenti melihat apa pun dalam banyak teks monoton padat dan sedikit berguna.
Setelah mencari melalui Internet yang dapat membantu kami, kami menemukan plugin yang cukup bagus untuk skrip Greasemonkey khusus, dan mereka memutuskan untuk menggunakannya.
Pertama-tama, kami membuat skrip pengguna dan memberikan hak untuk berkomunikasi dengan portal dan server perusahaan, di mana peringkat dan kemampuan untuk mengirim permintaan ditingkatkan.
Juga, untuk memodifikasi halaman makan siang itu sendiri, kami menggunakan jQuery, menghubungkannya menggunakan
// @requireSekarang mari kita mulai menyekop halaman makan siang. Setelah melihat kode html halaman, kami menemukan pengidentifikasi tabel makan siang, kami mendapatkan tabel dan memodifikasinya.
const table = $(".dinner__innerData"); const categoryList = [];
Saya ingin mencatat bahwa pada halaman pembentukan makan siang, ketika menghitung jumlah pesanan, itu dipertimbangkan pada semua baris tabel, menerima jumlah item yang dipesan dikalikan dengan harga. Untuk alasan ini, jika Anda menambahkan baris dengan nama kategori, semuanya akan rusak ... Saya harus memasukkan kolom tersembunyi dengan jumlah dan jumlah nol untuk baris ini.
Sekarang mari kita lanjutkan untuk membersihkan teks dan menambahkan informasi pada peringkat hidangan. Pertama, beberapa fungsi pembantu. Piringan dalam peringkat diidentifikasi dengan nama tanpa sampah dalam bentuk gram, tanda baca dan spasi. Yaitu, hidangan yang disebut “Kaldu Ayam dengan Telur (kaldu ayam, wortel, bawang, telur, sayuran). Dalam 100g: protein-3,43; lemak-2.86; karbohidrat-1.0; en.value-43.39kcal (200gr) ”diidentifikasi sebagai“ bouillon curd ”. Ini disebabkan oleh fakta bahwa pemasok dapat merangkak di ruang ekstra, tanda, dan sesuatu yang lain. Seperti yang telah ditunjukkan oleh praktik, ini cukup untuk mengidentifikasi piringan secara akurat dalam 90% kasus, dan kami memutuskan untuk tidak repot dan memasukkan pencarian teks lengkap.
function findByName(items, tdText) { tdText = clearTrash(tdText, true, true, true); return items.find(({clear_name}) => { return clear_name.trim().toLowerCase() === tdText; }); } function clearTrash(text, clearDescr, clearGrams, clearSymbols) {
Dan ini adalah pembentukan peringkat:
const table = $(".dinner__innerData"); const nameTd = $(table).find(“tr td:nth-child(2)”); for (let index = 0; index <= nameTd.length; index++) { const tdText = $(nameTd[index]).text();
Dan itulah yang terjadi.
Setuju, jauh lebih baik dan lebih nyaman?Bagian klien. Voting
Selanjutnya, kami akan beralih ke menambahkan kemampuan untuk memilih hidangan yang dipesan, serta mengirim pesan dengan pesanan ke telegram.
Halaman dengan pesanan tanpa skripPada halaman hidangan yang dipesan, tambahkan peringkat:
async function addRatingForm() { const table = $(".dinner__innerData"); const nameTd = $(table).find("tr td:nth-child(1)");
Dan inilah yang kami dapatkan di output:

Ya - kodenya mengerikan. Ya - tidak dioptimalkan. Dan ya - di beberapa tempat tidak masuk akal. Tetapi waktu yang dihabiskan minimum, dan fungsi dan kenyamanan meningkat secara signifikan.
Tujuannya adalah membuat memesan makan malam lebih menyenangkan bagi saya dan rekan-rekan saya, dan tujuan ini, menurut pendapat saya, tercapai.