diff --git a/.gitignore b/.gitignore index c8c19c7..5a9e784 100644 --- a/.gitignore +++ b/.gitignore @@ -1,4 +1,4 @@ -*.xlsx + # Created by .ignore support plugin (hsz.mobi) ### Node template # Logs diff --git a/components/admin/TheSidebar.vue b/components/admin/TheSidebar.vue index 34399f1..df1309e 100644 --- a/components/admin/TheSidebar.vue +++ b/components/admin/TheSidebar.vue @@ -339,10 +339,12 @@ :exact="false" :badge="pendingUsers ? { text: pendingUsers, color: 'danger' } : null" /> + + diff --git a/mixins/WS_Admin.js b/mixins/WS_Admin.js index 7978551..3e3a71a 100644 --- a/mixins/WS_Admin.js +++ b/mixins/WS_Admin.js @@ -58,6 +58,12 @@ export default { this.$store.commit('admin/set', ['newOldPieceRequests', data.newOldPieceRequests]) this.$store.commit('admin/set', ['newBufferRequests', data.newBufferRequests]) this.$store.commit('admin/set', ['newGuaranteeReports', data.newGuaranteeReports]) + + this.$store.commit('admin/set', ['newComplaintReports', data.newComplaintReports]) + this.$store.commit('admin/set', ['newWithdrawRequest', data.newWithdrawRequest]) + this.$store.commit('admin/set', ['pendingUsers', data.pendingUsers]) + this.$store.commit('admin/set', ['newAwardRequest', data.newAwardRequest]) + this.$store.commit('admin/set', ['newInstallDeviceRequest', data.newInstallDeviceRequest]) }) socket.on(`admin:notify`, data => { diff --git a/package-lock.json b/package-lock.json index 4ead9fc..c4278e0 100644 --- a/package-lock.json +++ b/package-lock.json @@ -28,6 +28,8 @@ "gsap": "^3.5.1", "jimp": "^0.16.1", "jquery": "^3.5.1", + "js-file-download": "^0.4.12", + "json-as-xlsx": "^2.5.6", "jsonwebtoken": "^8.5.1", "moment-jalaali": "^0.9.2", "mongoose": "^5.11.8", @@ -2842,6 +2844,17 @@ "node": ">=10.0.0" } }, + "node_modules/@e965/xlsx": { + "version": "0.20.3", + "resolved": "https://registry.npmjs.org/@e965/xlsx/-/xlsx-0.20.3.tgz", + "integrity": "sha512-703RN/3OdsRD5mtse2HBX7Um7xwaP9tlswEG6svOtjqokXoX7rJdQj7DyabD2I+xk22RgaIIU+R6BHgkpZGB/w==", + "bin": { + "xlsx": "bin/xlsx.njs" + }, + "engines": { + "node": ">=0.8" + } + }, "node_modules/@eslint-community/eslint-utils": { "version": "4.4.0", "resolved": "https://registry.npmjs.org/@eslint-community/eslint-utils/-/eslint-utils-4.4.0.tgz", @@ -12476,6 +12489,11 @@ "resolved": "https://registry.npmjs.org/js-cookie/-/js-cookie-2.2.1.tgz", "integrity": "sha512-HvdH2LzI/EAZcUwA8+0nKNtWHqS+ZmijLA30RwZA0bo7ToCckjK5MkGhjED9KoRcXO6BaGI3I9UIzSA1FKFPOQ==" }, + "node_modules/js-file-download": { + "version": "0.4.12", + "resolved": "https://registry.npmjs.org/js-file-download/-/js-file-download-0.4.12.tgz", + "integrity": "sha512-rML+NkoD08p5Dllpjo0ffy4jRHeY6Zsapvr/W86N7E0yuzAO6qa5X9+xog6zQNlH102J7IXljNY2FtS6Lj3ucg==" + }, "node_modules/js-tokens": { "version": "4.0.0", "resolved": "https://registry.npmjs.org/js-tokens/-/js-tokens-4.0.0.tgz", @@ -12509,6 +12527,14 @@ "node": ">=4" } }, + "node_modules/json-as-xlsx": { + "version": "2.5.6", + "resolved": "https://registry.npmjs.org/json-as-xlsx/-/json-as-xlsx-2.5.6.tgz", + "integrity": "sha512-z7phlB+VgS9wZv2N4SBKlguC3C7uauSj2PYSZICCrPaiu1lu8zkCpzZ4sOHWi0/3Je0CJl87q+J+3mpZbxpOew==", + "dependencies": { + "@e965/xlsx": "^0.20.0" + } + }, "node_modules/json-buffer": { "version": "3.0.1", "resolved": "https://registry.npmjs.org/json-buffer/-/json-buffer-3.0.1.tgz", diff --git a/package.json b/package.json index bdb5bf0..eceb62b 100644 --- a/package.json +++ b/package.json @@ -35,6 +35,8 @@ "gsap": "^3.5.1", "jimp": "^0.16.1", "jquery": "^3.5.1", + "js-file-download": "^0.4.12", + "json-as-xlsx": "^2.5.6", "jsonwebtoken": "^8.5.1", "moment-jalaali": "^0.9.2", "mongoose": "^5.11.8", diff --git a/pages/admin/gps/device/index.vue b/pages/admin/gps/device/index.vue new file mode 100644 index 0000000..280d29d --- /dev/null +++ b/pages/admin/gps/device/index.vue @@ -0,0 +1,177 @@ + + + diff --git a/pages/admin/gps/users/index.vue b/pages/admin/gps/users/index.vue index 8a606ea..0bd6a89 100644 --- a/pages/admin/gps/users/index.vue +++ b/pages/admin/gps/users/index.vue @@ -33,6 +33,30 @@ کاربران جی پی اس + + + + + + فیلتر ها + + + + + + +

جستجو در لیست:

+ +
+
+
+
+ @@ -42,7 +66,7 @@ - + @@ -96,7 +120,9 @@ export default { return { users: [], centerDialogVisible: false, - user: {} + user: {}, + filterText :'' + } }, @@ -106,6 +132,23 @@ export default { }, usersTypeList() { return this.$route.query?.type + }, + filteredItems() { + const filterText = this.filterText + if (!this.filterText.length) return this.users + else { + return this.users.filter(item => { + return ( + item.first_name.includes(filterText) || + item.last_name.includes(filterText) || + item.mobile_number.includes(filterText) || + item.national_code.includes(filterText) || + item.province_name?.includes(filterText) || + item.city_name?.includes(filterText) || + (item.first_name + ' ' + item.last_name).includes(filterText) + ) + }) + } } }, watch: { diff --git a/pages/admin/serials-exel/index.vue b/pages/admin/serials-exel/index.vue index 7ebad2b..c6c02f2 100644 --- a/pages/admin/serials-exel/index.vue +++ b/pages/admin/serials-exel/index.vue @@ -30,7 +30,7 @@ download target="_blank" title="برای دانلود کلیک کنید" - :href="scope?.row.url + scope?.row.name" + :href="scope?.row.url +'/'+ scope?.row.name" style="color: blue; display: block; direction: ltr !important; text-align: right" > {{ scope?.row.name }} diff --git a/server/controllers/GPS.Device.js b/server/controllers/GPS.Device.js index 0da37d8..2e977b3 100644 --- a/server/controllers/GPS.Device.js +++ b/server/controllers/GPS.Device.js @@ -1,10 +1,9 @@ const readXlsxFile = require('read-excel-file/node') -const validator = require('validator') const { body, param, validationResult } = require('express-validator'); +const xlsx = require("json-as-xlsx") const { _sr } = require('../plugins/serverResponses'); const { checkValidations, res500 } = require('../plugins/controllersHelperFunctions'); const Device = require('../models/GPS.Device'); - module.exports.addCode = [ [ body('model').notEmpty().isString().withMessage(_sr.fa.required.name), @@ -55,25 +54,48 @@ module.exports.importExel = async (req, res) => { module.exports.getAll = [ async (req, res) => { - let page; - let rows; - if (!req.query?.rows) { - rows = 10 - } else { - rows = req.query.rows + + const data = await Device.find().sort({ created_at: -1 }) + res.status(200).json(data) + } +] + +module.exports.downloadAll = [ + async (req, res) => { + + const device = await Device.find().sort({ created_at: -1 }) + const data = [ + { + sheet: "device", + columns: [ + { label: "IMEI", value: "IMEI" }, + { label: "مدل", value: "model" }, + { label: "قیمت به تومان", value: "tomanPrice" }, + { label: "سود به دلار", value: "dollarProfit" }, + { label: "سود به تومان", value: "profit" }, + { label: "امتیاز", value: "score" }, + { label: "سود از تمدید", value: "renewalProfit" }, + { label: "وضعیت نصب", value: "status" }, + ], + content: device, + } + ] + + const settings = { + writeOptions: { + type: "buffer", + bookType: "csv", + }, + RTL: true } - if (!req.query?.page) { - page = 0 - // eslint-disable-next-line eqeqeq - } else if (!req.query.page == 1) { - page = 0 - } else { - page = req.query.page - page = page * rows - rows - } - const data = await Device.find().sort({ created_at: -1 }).skip(page).limit(rows); - const total = Math.ceil((await Device.estimatedDocumentCount())) - res.status(200).json({ data, total }) + setTimeout(() => { + const buffer = xlsx(data, settings) + res.writeHead(200, { + "Content-Type": "application/octet-stream", + "Content-disposition": "attachment; filename=device.csv", + }) + res.end(buffer) + }, 2000); } ] @@ -99,7 +121,7 @@ module.exports.getOneByIMEI = [ ], checkValidations(validationResult), async (req, res) => { - const data = await Device.findOne({IMEI:req.params.imei}).sort({ created_at: -1 }) + const data = await Device.findOne({ IMEI: req.params.imei }).sort({ created_at: -1 }) if (!data) { res.status(404).json(_sr.fa.not_found.item_id) } else { @@ -151,10 +173,18 @@ const creator = (exel) => { return new Promise(async (resolve, reject) => { for (const row of exel) { // eslint-disable-next-line no-constant-condition - if (validator.isIMEI(row[0].toString().trim()) || true) { + if (/^[0-9]{15}$/gm.test(row[0].toString().trim())) { const device = await Device.findOne({ IMEI: row[0] }) if (device) { - console.warn("Repeated IMEI ", row[0]) + console.info("Repeated IMEI ", row[0]) + + device.model = row[1] + device.tomanPrice = row[2] + device.dollarProfit = row[3] || 1 + device.profit = row[4] || 1 + device.score = row[5] || 1 + device.renewalProfit = row[6] || 1 + device.save() } else { await Device.create( { @@ -174,4 +204,5 @@ const creator = (exel) => { } resolve("end") }) -} \ No newline at end of file +} + diff --git a/server/routes/admin.js b/server/routes/admin.js index fe5bbbb..a84c011 100644 --- a/server/routes/admin.js +++ b/server/routes/admin.js @@ -71,6 +71,7 @@ router.get('/gps/register-device', installedDevice.getAllForAdmin) /// ////////////// Device router.post('/gps/device',hasPermission('gps'), device.addCode) router.post('/gps/device/exel',hasPermission('gps'), device.importExel) +router.get('/gps/device/exel',hasPermission('gps'), device.downloadAll) router.get('/gps/device',hasPermission('gps'), device.getAll) router.get('/gps/device/imei/:imei',hasPermission('gps'), device.getOneByIMEI) router.get('/gps/device/id/:id',hasPermission('gps'), device.getOne) diff --git a/static/example.xlsx b/static/example.xlsx new file mode 100644 index 0000000..e135af3 Binary files /dev/null and b/static/example.xlsx differ diff --git a/store/admin.js b/store/admin.js index ca86cf2..133c28f 100644 --- a/store/admin.js +++ b/store/admin.js @@ -14,7 +14,11 @@ export const state = () => ({ verityProducts: [], panatechProducts: [], iranProvinces: [], - iranCities: [] + iranCities: [], + newWithdrawRequest: 0, + pendingUsers: 0, + newAwardRequest: 0, + newInstallDeviceRequest: 0 }) export const mutations = {