zet-lib 3.3.7 → 4.0.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/lib/index.js CHANGED
@@ -50,7 +50,11 @@ const lazyModules = {
50
50
  return require("exceljs");
51
51
  },
52
52
  get pm2() {
53
- return require("pm2");
53
+ try {
54
+ return require("pm2");
55
+ } catch (e) {
56
+ return null;
57
+ }
54
58
  },
55
59
  get nodemailer() {
56
60
  return require("nodemailer");
@@ -0,0 +1,14 @@
1
+ let pm2Module
2
+ let attempted = false
3
+
4
+ module.exports = function getPm2 () {
5
+ if (attempted) return pm2Module
6
+ attempted = true
7
+ try {
8
+ pm2Module = require('pm2')
9
+ } catch (e) {
10
+ pm2Module = null
11
+ }
12
+ return pm2Module
13
+ }
14
+
@@ -1,359 +1,359 @@
1
- const router = require('express').Router();
2
- const {csrf} = require('zet-lib');
3
- const csrfProtection = csrf({cookie: true});
4
- const {Util, access, connection, moduleLib, zDebug, zRoute, zRole, zDataTable, zForm} = require('zet-lib');
5
- const MYMODEL = require('./../models/[[[TABLE_NAME]]]');
6
-
7
- router.get('/', async (req, res) => {
8
- await zRoute.attributeData(res, MYMODEL);
9
- let dataTable = new zDataTable(res.locals);
10
- dataTable.filterMODEL = await zRoute.dataTableFilterSync(req,res, MYMODEL, res.locals.gridFilter);
11
- const levels = zRole.myLevel(req, res, MYMODEL.table);
12
- dataTable.levels = levels;
13
- res.render(`layouts/${layout}`, {
14
- dataTable: dataTable,
15
- levels : levels,
16
- titleHeader: `<strong class="text text-info">${MYMODEL.title}</strong>`,
17
- breadcrumb : zForm.breadcrumbIndex(),
18
- myModal : zForm.modal({
19
- attributeData: res.locals.attributeData,
20
- visibles: res.locals.visibles,
21
- invisibles: res.locals.invisibles,
22
- routeName: MYMODEL.table,
23
- }, LANGUAGE),
24
- renderHead: `${MYMODEL.routeName}/indexcss.ejs`,
25
- renderBody: `${MYMODEL.routeName}/index.ejs`,
26
- renderEnd: `${MYMODEL.routeName}/indexjs.ejs`
27
- });
28
- });
29
-
30
- router.post('/list', async (req, res) => {
31
- const data = await zRoute.listData(req, res, MYMODEL, zRole);
32
- res.json(data);
33
- });
34
-
35
- router.get('/create', csrfProtection, async(req, res) => {
36
- let data = MYMODEL.datas;
37
- const zForms = await zRoute.formsFieldSync(req, res, MYMODEL, data);
38
- res.render(`layouts/${layout}`, {
39
- data: data,
40
- zForms: zForms,
41
- titleHeader: `${LANGUAGE['form_create']} : <strong><a href="/${MYMODEL.routeName}">${MYMODEL.title}</a></strong>`,
42
- csrfToken: req.csrfToken(),
43
- breadcrumb : zForm.breadcrumbCreate(MYMODEL.routeName),
44
- renderBody: `${MYMODEL.routeName}/create.ejs`,
45
- renderEnd: `${MYMODEL.routeName}/createjs.ejs`
46
- });
47
- });
48
-
49
- router.post('/create', csrfProtection, async (req, res) => {
50
- let json = Util.jsonSuccess(LANGUAGE['data_saved']);
51
- try {
52
- let data = zRoute.post(req,res, MYMODEL)[MYMODEL.routeName];
53
- const validator = zRoute.validator(data, MYMODEL);
54
- if(validator.status == 0) return res.json(validator.message);
55
- const result = await zRoute.insertSQL(req, res, MYMODEL.table, data);
56
- json.data=result;
57
- } catch (err) {
58
- if(Object.hasOwn(err,"sqlMessage")){
59
- json = Util.flashError(err.sqlMessage);
60
- } else {
61
- json = Util.flashError(err.toString());
62
- }
63
- zDebug(req, res, err);
64
- }
65
- res.json(json);
66
- });
67
-
68
- router.get('/update/:id', csrfProtection, async (req, res) => {
69
- const id = parseInt(req.params.id);
70
- const results = await connection.results({
71
- select:zRoute.selectData(MYMODEL),
72
- table: MYMODEL.table,
73
- where: {
74
- id: id,
75
- company_id: res.locals.companyId
76
- }
77
- });
78
- if (results.length == 0) {
79
- req.session.sessionFlash = Util.flashError(LANGUAGE['data_not_found']);
80
- return res.redirect('/' + MYMODEL.routeName);
81
- }
82
- let data = results[0];
83
- const zForms = await zRoute.formsFieldSync(req, res, MYMODEL, data);
84
- res.render(`layouts/${layout}`, {
85
- data: data,
86
- zForms: zForms,
87
- titleHeader: `${LANGUAGE['form_update']} : <strong><a href="/${MYMODEL.routeName}">${MYMODEL.title}</a></strong>`,
88
- csrfToken: req.csrfToken(),
89
- breadcrumb : zForm.breadcrumbUpdate(MYMODEL.routeName, id),
90
- renderBody: `${MYMODEL.routeName}/update.ejs`,
91
- renderEnd: `${MYMODEL.routeName}/updatejs.ejs`,
92
- });
93
- });
94
-
95
- router.post('/update/:id', csrfProtection, async (req, res) => {
96
- let json = Util.jsonSuccess(LANGUAGE['data_saved']);
97
- try {
98
- const id = parseInt(req.params.id);
99
- let data = zRoute.post(req,res, MYMODEL)[MYMODEL.routeName];
100
- const validator = zRoute.validator(data, MYMODEL);
101
- if(validator.status == 0) return res.json(validator.message);
102
- const result = await zRoute.updateSQL(req, res,MYMODEL.table, data, {id:id});
103
- json.data=result;
104
- } catch (err) {
105
- console.log(err)
106
- if(Object.hasOwn(err,"sqlMessage")){
107
- json = Util.flashError(err.sqlMessage);
108
- } else {
109
- json = Util.flashError(err.toString());
110
- }
111
- zDebug(req, res, err)
112
- }
113
- res.json(json);
114
- });
115
-
116
- router.delete('/delete', async (req, res) => {
117
- const id = req.body.id;
118
- let json = Util.jsonSuccess(LANGUAGE['data_delete']);
119
- try {
120
- await zRoute.deleteSQL(MYMODEL.table, id, res.locals.companyId);
121
- } catch (err) {
122
- json = Util.flashError(err.toString());
123
- zDebug(req, res, err)
124
- }
125
- res.json(json);
126
- });
127
-
128
- router.get('/view/:id', async (req, res) => {
129
- await zRoute.attributeData(res, MYMODEL);
130
- const id = req.params.id;
131
- let data = {};
132
- let zForms = {};
133
- try {
134
- const results = await connection.results({select:zRoute.selectData(MYMODEL),table:MYMODEL.table,where:{id:id}});
135
- if (results.length == 0) {
136
- req.session.sessionFlash = Util.flashError(LANGUAGE['data_not_found']);
137
- return res.redirect('/' + MYMODEL.routeName);
138
- }
139
- data = results[0];
140
- zForms = await zRoute.viewFormsSync(req, res, MYMODEL, data);
141
- } catch (err){
142
- zDebug(req, res, err);
143
- res.send("Err");
144
- }
145
- res.render(`layouts/${layout}`, {
146
- data: data,
147
- Util:Util,
148
- zForms:zForms,
149
- titleHeader: `View : <strong><a href="/${MYMODEL.routeName}">${MYMODEL.title}</a></strong>`,
150
- breadcrumb : zForm.breadcrumbView(MYMODEL.routeName),
151
- levels: zRole.myLevel(req, res, MYMODEL.table),
152
- renderBody: `${MYMODEL.routeName}/view.ejs`
153
- });
154
- });
155
-
156
- router.get('/excel-query', async (req,res) => {
157
- await zRoute.excelQuery(req, res, MYMODEL);
158
- });
159
-
160
- router.get('/excel', async (req, res) => {
161
- const fields = MYMODEL.keysExcel;
162
- const results = await connection.results({
163
- table: MYMODEL.table,
164
- where: {company_id: res.locals.companyId},
165
- orderBy: ['id', 'DESC']
166
- });
167
- await zRoute.excel(req, res, MYMODEL, fields, results);
168
- });
169
-
170
- router.get('/sample', async (req, res) => {
171
- let fields = [];
172
- for (let i = 0; i < MYMODEL.keysExcel.length; i++) {
173
- if (!Util.in_array(MYMODEL.keysExcel[i], Util.nots)) {
174
- fields.push(MYMODEL.keysExcel[i]);
175
- }
176
- }
177
- const results = await connection.results({
178
- table:MYMODEL.table,
179
- where:{
180
- company_id:res.locals.companyId
181
- },
182
- orderBy:["id","desc"], limit:10
183
- });
184
- let callback=(result,field)=> {
185
- return MYMODEL.widgets[field] && MYMODEL.widgets[field].name == 'datepicker' ? Util.dateSql(result[field]) : result[field];
186
- };
187
- await zRoute.excel(req, res, MYMODEL, fields, results, callback);
188
- });
189
-
190
- router.get('/import',csrfProtection, async (req, res) => {
191
- const room = res.locals.token;
192
- res.render(`layouts/${layout}`, {
193
- room: room,
194
- titleHeader: `Import / Upload data : <strong><a href="/${MYMODEL.routeName}">${MYMODEL.title}</a></strong>`,
195
- csrfToken: req.csrfToken(),
196
- breadcrumb : zForm.breadcrumbImport(MYMODEL.routeName),
197
- renderBody: `${MYMODEL.routeName}/import.ejs`,
198
- renderEnd: `${MYMODEL.routeName}/importjs.ejs`
199
- });
200
- });
201
-
202
-
203
- router.post('/import', async(req, res) => {
204
- res.json(await zRoute.import(req,res,MYMODEL));
205
- });
206
-
207
- router.get('/approval/:id', async (req, res) => {
208
- await zRoute.attributeData(res, MYMODEL);
209
- const id = req.params.id;
210
- let data = {};
211
- let data2 = {};
212
- let zForms = {};
213
- let zForms2 = {};
214
- let result = {};
215
- try {
216
- result = await connection.result({table: MYMODEL.table, where: {id: id}});
217
- if (!result.id) {
218
- req.session.sessionFlash = Util.flashError(LANGUAGE['data_not_found']);
219
- return res.redirect('/' + MYMODEL.routeName);
220
- }
221
- data=result;
222
- moduleLib.editor(req, res);
223
- zForms = await zRoute.viewFormsSync(req, res, MYMODEL, result);
224
- const contentScript = `$("#submit_draft").on("click", function () {$("#status").val(1);ajaxPost("/zzapproval",$("#form-group").serializeArray(), function (data) {
225
- if (data.status == 0) {
226
- toastr.error(data.message, data.title);
227
- } else {
228
- toastr.success(data.title, data.message);
229
- }
230
- });});
231
- $("#submit").on("click", function () {
232
- $('[name="zapprovals[status]"]').val(2);
233
- ajaxPost("/zzapproval",$("#form-group").serializeArray(), function (data) {
234
- if (data.status == 0) {
235
- toastr.error(data.message, data.title);
236
- } else {
237
- toastr.success(data.title, data.message);
238
- location.href = "";
239
- }
240
- });
241
- });
242
- `;
243
- await moduleLib.addScript(req, res, contentScript);
244
- const MODEL_APROVALS = require("./../models/zapprovals");
245
- const rows = await connection.results({
246
- table: "zapprovals",
247
- where: {table: MYMODEL.table, company_id: res.locals.companyId, id_data: id}
248
- });
249
- if (rows.length) {
250
- data2 = rows[0];
251
- } else {
252
- let obj = {};
253
- obj.token = Util.uuid();
254
- obj.status = 1;
255
- obj.table = MYMODEL.table;
256
- obj.company_id = res.locals.companyId;
257
- obj.id_data = id;
258
- obj.created_by = res.locals.userId;
259
- obj.updated_by = res.locals.userId;
260
- obj.created_at = Util.now();
261
- let zfields = await connection.result({table: "zfields", where: {table: MYMODEL.table}});
262
- let jsonApproval = zfields.approval_json || {}
263
- obj.template = jsonApproval.content || {}
264
- let title = jsonApproval.title;
265
- if (title) {
266
- let titleData = title;
267
- for (var key in data) {
268
- titleData = Util.replaceAll(titleData, "{{" + key + "}}", data[key])
269
- }
270
- obj.title = titleData
271
- }
272
- if (jsonApproval.hasOwnProperty("approvers")) {
273
- obj.approvers = JSON.stringify(jsonApproval.approvers);
274
- obj.knowings = JSON.stringify(jsonApproval.knowings);
275
- obj.type = 1;
276
- }
277
- //insert default data
278
- await connection.insert({table: "zapprovals", data: obj});
279
- data2 = obj;
280
- }
281
- zForms2 = await zRoute.formsFieldSync(req, res, MODEL_APROVALS, data2);
282
- } catch (err) {
283
- zDebug(req, res, err);
284
- res.send("Err");
285
- }
286
- res.render(`layouts/${layout}`, {
287
- zForms: zForms,
288
- zForms2: zForms2,
289
- data: result,
290
- result:result,
291
- data2: data2,
292
- Util: Util,
293
- levels: zRole.myLevel(req, res, MYMODEL.table),
294
- breadcrumb : zForm.breadcrumbApproval(MYMODEL.routeName, id),
295
- renderBody: `${MYMODEL.routeName}/approval.ejs`
296
- });
297
- });
298
-
299
- router.get('/preview/:token', async (req, res) => {
300
- let token = req.params.token;
301
- let data = {}, data2 = {};
302
- let template = "";
303
- let footers = "";
304
- try {
305
- let zfields = await connection.result({table: "zfields", where: {table: MYMODEL.table}});
306
- let jsonApproval = zfields.approval_json || {}
307
- let mytemplate = jsonApproval.content || {}
308
- let results = await connection.results({table: "zapprovals", where: {token: token}});
309
- if (results.length == 0) {
310
- req.session.sessionFlash = Util.flashError(LANGUAGE['data_not_found']);
311
- return res.redirect('/' + MYMODEL.routeName);
312
- }
313
- if(results[0].status == 1){
314
- await connection.update({
315
- table : "zapprovals",
316
- data: {
317
- template : mytemplate
318
- },
319
- where : {
320
- token:token
321
- }
322
- })
323
- results = await connection.results({table: "zapprovals", where: {token: token}});
324
- }
325
- let MYMODEL2 = require("./../models/zapprovals")
326
- data = await zRoute.viewTable(req, res, MYMODEL2, results[0], true);
327
- let row = await connection.result({table: results[0].table, where: {id: results[0].id_data}});
328
- data2 = await zRoute.viewTable(req, res, MYMODEL, row, true);
329
- template = data.template;
330
- let title = data.title || ""
331
- for (var key in data2) {
332
- template = Util.replaceAll(template, "{{" + key + "}}", data2[key])
333
- title = Util.replaceAll(title, "{{" + key + "}}", data2[key])
334
- }
335
- data.title = title;
336
- var details = await connection.results({table: "zapprovals_details", where: {title_id: results[0].id}});
337
- if (details.length) {
338
- footers = await zRoute.approversFooter(details);
339
- }
340
- } catch (err) {
341
- zDebug(req, res, err);
342
- res.send("Err");
343
- }
344
- res.render(`layouts/blank`, {
345
- template: template,
346
- data: data,
347
- footers: footers,
348
- Util: Util,
349
- details: details,
350
- renderBody: 'index/zapprovals_preview.ejs'
351
- });
352
- });
353
-
354
- router.post('/grid', access, zRoute.postGrid);
355
- router.post('/reload', access, zRoute.postGridReload);
356
- router.post('/chains', access, zRoute.chains);
357
- router.post('/get_attributes',access, zRoute.getAttributes);
358
-
359
- module.exports = router;
1
+ const router = require('express').Router();
2
+ const {csrf} = require('zet-lib');
3
+ const csrfProtection = csrf({cookie: true});
4
+ const {Util, access, connection, moduleLib, zDebug, zRoute, zRole, zDataTable, zForm} = require('zet-lib');
5
+ const MYMODEL = require('./../models/[[[TABLE_NAME]]]');
6
+
7
+ router.get('/', async (req, res) => {
8
+ await zRoute.attributeData(res, MYMODEL);
9
+ let dataTable = new zDataTable(res.locals);
10
+ dataTable.filterMODEL = await zRoute.dataTableFilterSync(req,res, MYMODEL, res.locals.gridFilter);
11
+ const levels = zRole.myLevel(req, res, MYMODEL.table);
12
+ dataTable.levels = levels;
13
+ res.render(`layouts/${layout}`, {
14
+ dataTable: dataTable,
15
+ levels : levels,
16
+ titleHeader: `<strong class="text text-info">${MYMODEL.title}</strong>`,
17
+ breadcrumb : zForm.breadcrumbIndex(),
18
+ myModal : zForm.modal({
19
+ attributeData: res.locals.attributeData,
20
+ visibles: res.locals.visibles,
21
+ invisibles: res.locals.invisibles,
22
+ routeName: MYMODEL.table,
23
+ }, LANGUAGE),
24
+ renderHead: `${MYMODEL.routeName}/indexcss.ejs`,
25
+ renderBody: `${MYMODEL.routeName}/index.ejs`,
26
+ renderEnd: `${MYMODEL.routeName}/indexjs.ejs`
27
+ });
28
+ });
29
+
30
+ router.post('/list', async (req, res) => {
31
+ const data = await zRoute.listData(req, res, MYMODEL, zRole);
32
+ res.json(data);
33
+ });
34
+
35
+ router.get('/create', csrfProtection, async(req, res) => {
36
+ let data = MYMODEL.datas;
37
+ const zForms = await zRoute.formsFieldSync(req, res, MYMODEL, data);
38
+ res.render(`layouts/${layout}`, {
39
+ data: data,
40
+ zForms: zForms,
41
+ titleHeader: `${LANGUAGE['form_create']} : <strong><a href="/${MYMODEL.routeName}">${MYMODEL.title}</a></strong>`,
42
+ csrfToken: req.csrfToken(),
43
+ breadcrumb : zForm.breadcrumbCreate(MYMODEL.routeName),
44
+ renderBody: `${MYMODEL.routeName}/create.ejs`,
45
+ renderEnd: `${MYMODEL.routeName}/createjs.ejs`
46
+ });
47
+ });
48
+
49
+ router.post('/create', csrfProtection, async (req, res) => {
50
+ let json = Util.jsonSuccess(LANGUAGE['data_saved']);
51
+ try {
52
+ let data = zRoute.post(req,res, MYMODEL)[MYMODEL.routeName];
53
+ const validator = zRoute.validator(data, MYMODEL);
54
+ if(validator.status == 0) return res.json(validator.message);
55
+ const result = await zRoute.insertSQL(req, res, MYMODEL.table, data);
56
+ json.data=result;
57
+ } catch (err) {
58
+ if(Object.hasOwn(err,"sqlMessage")){
59
+ json = Util.flashError(err.sqlMessage);
60
+ } else {
61
+ json = Util.flashError(err.toString());
62
+ }
63
+ zDebug(req, res, err);
64
+ }
65
+ res.json(json);
66
+ });
67
+
68
+ router.get('/update/:id', csrfProtection, async (req, res) => {
69
+ const id = parseInt(req.params.id);
70
+ const results = await connection.results({
71
+ select:zRoute.selectData(MYMODEL),
72
+ table: MYMODEL.table,
73
+ where: {
74
+ id: id,
75
+ company_id: res.locals.companyId
76
+ }
77
+ });
78
+ if (results.length == 0) {
79
+ req.session.sessionFlash = Util.flashError(LANGUAGE['data_not_found']);
80
+ return res.redirect('/' + MYMODEL.routeName);
81
+ }
82
+ let data = results[0];
83
+ const zForms = await zRoute.formsFieldSync(req, res, MYMODEL, data);
84
+ res.render(`layouts/${layout}`, {
85
+ data: data,
86
+ zForms: zForms,
87
+ titleHeader: `${LANGUAGE['form_update']} : <strong><a href="/${MYMODEL.routeName}">${MYMODEL.title}</a></strong>`,
88
+ csrfToken: req.csrfToken(),
89
+ breadcrumb : zForm.breadcrumbUpdate(MYMODEL.routeName, id),
90
+ renderBody: `${MYMODEL.routeName}/update.ejs`,
91
+ renderEnd: `${MYMODEL.routeName}/updatejs.ejs`,
92
+ });
93
+ });
94
+
95
+ router.post('/update/:id', csrfProtection, async (req, res) => {
96
+ let json = Util.jsonSuccess(LANGUAGE['data_saved']);
97
+ try {
98
+ const id = parseInt(req.params.id);
99
+ let data = zRoute.post(req,res, MYMODEL)[MYMODEL.routeName];
100
+ const validator = zRoute.validator(data, MYMODEL);
101
+ if(validator.status == 0) return res.json(validator.message);
102
+ const result = await zRoute.updateSQL(req, res,MYMODEL.table, data, {id:id});
103
+ json.data=result;
104
+ } catch (err) {
105
+ console.log(err)
106
+ if(Object.hasOwn(err,"sqlMessage")){
107
+ json = Util.flashError(err.sqlMessage);
108
+ } else {
109
+ json = Util.flashError(err.toString());
110
+ }
111
+ zDebug(req, res, err)
112
+ }
113
+ res.json(json);
114
+ });
115
+
116
+ router.delete('/delete', async (req, res) => {
117
+ const id = req.body.id;
118
+ let json = Util.jsonSuccess(LANGUAGE['data_delete']);
119
+ try {
120
+ await zRoute.deleteSQL(MYMODEL.table, id, res.locals.companyId);
121
+ } catch (err) {
122
+ json = Util.flashError(err.toString());
123
+ zDebug(req, res, err)
124
+ }
125
+ res.json(json);
126
+ });
127
+
128
+ router.get('/view/:id', async (req, res) => {
129
+ await zRoute.attributeData(res, MYMODEL);
130
+ const id = req.params.id;
131
+ let data = {};
132
+ let zForms = {};
133
+ try {
134
+ const results = await connection.results({select:zRoute.selectData(MYMODEL),table:MYMODEL.table,where:{id:id}});
135
+ if (results.length == 0) {
136
+ req.session.sessionFlash = Util.flashError(LANGUAGE['data_not_found']);
137
+ return res.redirect('/' + MYMODEL.routeName);
138
+ }
139
+ data = results[0];
140
+ zForms = await zRoute.viewFormsSync(req, res, MYMODEL, data);
141
+ } catch (err){
142
+ zDebug(req, res, err);
143
+ res.send("Err");
144
+ }
145
+ res.render(`layouts/${layout}`, {
146
+ data: data,
147
+ Util:Util,
148
+ zForms:zForms,
149
+ titleHeader: `View : <strong><a href="/${MYMODEL.routeName}">${MYMODEL.title}</a></strong>`,
150
+ breadcrumb : zForm.breadcrumbView(MYMODEL.routeName),
151
+ levels: zRole.myLevel(req, res, MYMODEL.table),
152
+ renderBody: `${MYMODEL.routeName}/view.ejs`
153
+ });
154
+ });
155
+
156
+ router.get('/excel-query', async (req,res) => {
157
+ await zRoute.excelQuery(req, res, MYMODEL);
158
+ });
159
+
160
+ router.get('/excel', async (req, res) => {
161
+ const fields = MYMODEL.keysExcel;
162
+ const results = await connection.results({
163
+ table: MYMODEL.table,
164
+ where: {company_id: res.locals.companyId},
165
+ orderBy: ['id', 'DESC']
166
+ });
167
+ await zRoute.excel(req, res, MYMODEL, fields, results);
168
+ });
169
+
170
+ router.get('/sample', async (req, res) => {
171
+ let fields = [];
172
+ for (let i = 0; i < MYMODEL.keysExcel.length; i++) {
173
+ if (!Util.in_array(MYMODEL.keysExcel[i], Util.nots)) {
174
+ fields.push(MYMODEL.keysExcel[i]);
175
+ }
176
+ }
177
+ const results = await connection.results({
178
+ table:MYMODEL.table,
179
+ where:{
180
+ company_id:res.locals.companyId
181
+ },
182
+ orderBy:["id","desc"], limit:10
183
+ });
184
+ let callback=(result,field)=> {
185
+ return MYMODEL.widgets[field] && MYMODEL.widgets[field].name == 'datepicker' ? Util.dateSql(result[field]) : result[field];
186
+ };
187
+ await zRoute.excel(req, res, MYMODEL, fields, results, callback);
188
+ });
189
+
190
+ router.get('/import',csrfProtection, async (req, res) => {
191
+ const room = res.locals.token;
192
+ res.render(`layouts/${layout}`, {
193
+ room: room,
194
+ titleHeader: `Import / Upload data : <strong><a href="/${MYMODEL.routeName}">${MYMODEL.title}</a></strong>`,
195
+ csrfToken: req.csrfToken(),
196
+ breadcrumb : zForm.breadcrumbImport(MYMODEL.routeName),
197
+ renderBody: `${MYMODEL.routeName}/import.ejs`,
198
+ renderEnd: `${MYMODEL.routeName}/importjs.ejs`
199
+ });
200
+ });
201
+
202
+
203
+ router.post('/import', async(req, res) => {
204
+ res.json(await zRoute.import(req,res,MYMODEL));
205
+ });
206
+
207
+ router.get('/approval/:id', async (req, res) => {
208
+ await zRoute.attributeData(res, MYMODEL);
209
+ const id = req.params.id;
210
+ let data = {};
211
+ let data2 = {};
212
+ let zForms = {};
213
+ let zForms2 = {};
214
+ let result = {};
215
+ try {
216
+ result = await connection.result({table: MYMODEL.table, where: {id: id}});
217
+ if (!result.id) {
218
+ req.session.sessionFlash = Util.flashError(LANGUAGE['data_not_found']);
219
+ return res.redirect('/' + MYMODEL.routeName);
220
+ }
221
+ data=result;
222
+ moduleLib.editor(req, res);
223
+ zForms = await zRoute.viewFormsSync(req, res, MYMODEL, result);
224
+ const contentScript = `$("#submit_draft").on("click", function () {$("#status").val(1);ajaxPost("/zzapproval",$("#form-group").serializeArray(), function (data) {
225
+ if (data.status == 0) {
226
+ toastr.error(data.message, data.title);
227
+ } else {
228
+ toastr.success(data.title, data.message);
229
+ }
230
+ });});
231
+ $("#submit").on("click", function () {
232
+ $('[name="zapprovals[status]"]').val(2);
233
+ ajaxPost("/zzapproval",$("#form-group").serializeArray(), function (data) {
234
+ if (data.status == 0) {
235
+ toastr.error(data.message, data.title);
236
+ } else {
237
+ toastr.success(data.title, data.message);
238
+ location.href = "";
239
+ }
240
+ });
241
+ });
242
+ `;
243
+ await moduleLib.addScript(req, res, contentScript);
244
+ const MODEL_APROVALS = require("./../models/zapprovals");
245
+ const rows = await connection.results({
246
+ table: "zapprovals",
247
+ where: {table: MYMODEL.table, company_id: res.locals.companyId, id_data: id}
248
+ });
249
+ if (rows.length) {
250
+ data2 = rows[0];
251
+ } else {
252
+ let obj = {};
253
+ obj.token = Util.uuid();
254
+ obj.status = 1;
255
+ obj.table = MYMODEL.table;
256
+ obj.company_id = res.locals.companyId;
257
+ obj.id_data = id;
258
+ obj.created_by = res.locals.userId;
259
+ obj.updated_by = res.locals.userId;
260
+ obj.created_at = Util.now();
261
+ let zfields = await connection.result({table: "zfields", where: {table: MYMODEL.table}});
262
+ let jsonApproval = zfields.approval_json || {}
263
+ obj.template = jsonApproval.content || {}
264
+ let title = jsonApproval.title;
265
+ if (title) {
266
+ let titleData = title;
267
+ for (var key in data) {
268
+ titleData = Util.replaceAll(titleData, "{{" + key + "}}", data[key])
269
+ }
270
+ obj.title = titleData
271
+ }
272
+ if (jsonApproval.hasOwnProperty("approvers")) {
273
+ obj.approvers = JSON.stringify(jsonApproval.approvers);
274
+ obj.knowings = JSON.stringify(jsonApproval.knowings);
275
+ obj.type = 1;
276
+ }
277
+ //insert default data
278
+ await connection.insert({table: "zapprovals", data: obj});
279
+ data2 = obj;
280
+ }
281
+ zForms2 = await zRoute.formsFieldSync(req, res, MODEL_APROVALS, data2);
282
+ } catch (err) {
283
+ zDebug(req, res, err);
284
+ res.send("Err");
285
+ }
286
+ res.render(`layouts/${layout}`, {
287
+ zForms: zForms,
288
+ zForms2: zForms2,
289
+ data: result,
290
+ result:result,
291
+ data2: data2,
292
+ Util: Util,
293
+ levels: zRole.myLevel(req, res, MYMODEL.table),
294
+ breadcrumb : zForm.breadcrumbApproval(MYMODEL.routeName, id),
295
+ renderBody: `${MYMODEL.routeName}/approval.ejs`
296
+ });
297
+ });
298
+
299
+ router.get('/preview/:token', async (req, res) => {
300
+ let token = req.params.token;
301
+ let data = {}, data2 = {};
302
+ let template = "";
303
+ let footers = "";
304
+ try {
305
+ let zfields = await connection.result({table: "zfields", where: {table: MYMODEL.table}});
306
+ let jsonApproval = zfields.approval_json || {}
307
+ let mytemplate = jsonApproval.content || {}
308
+ let results = await connection.results({table: "zapprovals", where: {token: token}});
309
+ if (results.length == 0) {
310
+ req.session.sessionFlash = Util.flashError(LANGUAGE['data_not_found']);
311
+ return res.redirect('/' + MYMODEL.routeName);
312
+ }
313
+ if(results[0].status == 1){
314
+ await connection.update({
315
+ table : "zapprovals",
316
+ data: {
317
+ template : mytemplate
318
+ },
319
+ where : {
320
+ token:token
321
+ }
322
+ })
323
+ results = await connection.results({table: "zapprovals", where: {token: token}});
324
+ }
325
+ let MYMODEL2 = require("./../models/zapprovals")
326
+ data = await zRoute.viewTable(req, res, MYMODEL2, results[0], true);
327
+ let row = await connection.result({table: results[0].table, where: {id: results[0].id_data}});
328
+ data2 = await zRoute.viewTable(req, res, MYMODEL, row, true);
329
+ template = data.template;
330
+ let title = data.title || ""
331
+ for (var key in data2) {
332
+ template = Util.replaceAll(template, "{{" + key + "}}", data2[key])
333
+ title = Util.replaceAll(title, "{{" + key + "}}", data2[key])
334
+ }
335
+ data.title = title;
336
+ var details = await connection.results({table: "zapprovals_details", where: {title_id: results[0].id}});
337
+ if (details.length) {
338
+ footers = await zRoute.approversFooter(details);
339
+ }
340
+ } catch (err) {
341
+ zDebug(req, res, err);
342
+ res.send("Err");
343
+ }
344
+ res.render(`layouts/blank`, {
345
+ template: template,
346
+ data: data,
347
+ footers: footers,
348
+ Util: Util,
349
+ details: details,
350
+ renderBody: 'index/zapprovals_preview.ejs'
351
+ });
352
+ });
353
+
354
+ router.post('/grid', access, zRoute.postGrid);
355
+ router.post('/reload', access, zRoute.postGridReload);
356
+ router.post('/chains', access, zRoute.chains);
357
+ router.post('/get_attributes',access, zRoute.getAttributes);
358
+
359
+ module.exports = router;
package/lib/zAppRouter.js CHANGED
@@ -18,7 +18,7 @@ const debug = require("./debug");
18
18
  const io = require("./io");
19
19
  const Mail = require("./Mail");
20
20
  const zCache = require("./zCache");
21
- const pm2 = require("pm2");
21
+ const getPm2 = require("./optionalPm2");
22
22
  const zFunction = require("./zFunction");
23
23
  const qs = require("qs");
24
24
  const zip = require("express-zip");
@@ -663,6 +663,11 @@ router.get("/layout_changes/:layout", access, async (req, res) => {
663
663
  router.get("/restart", access, async (req, res) => {
664
664
  var room = res.locals.user.token;
665
665
  if (env == "production") {
666
+ const pm2 = getPm2();
667
+ if (!pm2) {
668
+ io.to(room).emit("error", "pm2 module is not installed");
669
+ return res.json("ok");
670
+ }
666
671
  pm2.connect(function (err) {
667
672
  if (err) {
668
673
  io.to(room).emit("error", err.toString());
@@ -4,7 +4,7 @@ const csrf = require("./csrf");
4
4
  const csrfProtection = csrf({ cookie: true });
5
5
  const fs = require("fs-extra");
6
6
  const axios = require("axios");
7
- const pm2 = require("pm2");
7
+ const getPm2 = require("./optionalPm2");
8
8
  const uglifyJS = require("uglify-js");
9
9
  const { minify } = require("html-minifier-terser");
10
10
  const zRoute = require("./zRoute");
@@ -674,6 +674,8 @@ const generate = async (req, res) => {
674
674
 
675
675
  //restart pm2 module in production
676
676
  if (process.env.NODE_ENV == "production") {
677
+ const pm2 = getPm2();
678
+ if (!pm2) return Util.jsonSuccess("Success");
677
679
  pm2.connect(function (err) {
678
680
  if (err) {
679
681
  console.log(err.toString());
package/lib/zPage.js CHANGED
@@ -7,7 +7,7 @@ const fs = require('fs-extra');
7
7
  const nodemailer = require('nodemailer');
8
8
  const qs = require('qs');
9
9
  const moment = require('moment');
10
- const pm2 = require('pm2');
10
+ const getPm2 = require('./optionalPm2');
11
11
  const { minify } = require('html-minifier-terser');
12
12
  const connection = require('./connection');
13
13
  const Util = require('./Util');
@@ -39,6 +39,8 @@ zpage.build = async (req, res) => {
39
39
  fs.writeFileSync(path.join(dirRoot, "routes", "zindex.js"), server_code, 'utf-8');
40
40
  if (process.env.NODE_ENV === "production") {
41
41
  setTimeout(function () {
42
+ const pm2 = getPm2()
43
+ if (!pm2) return
42
44
  pm2.connect(function (err) {
43
45
  if (err) {
44
46
  console.log(err.toString());
@@ -167,6 +169,8 @@ zpage.buildLayout = async (obj) => {
167
169
  fs.writeFileSync(path.join(dirRoot, "views", "layouts", name + ".ejs"), html, 'utf-8');
168
170
  if (process.env.NODE_ENV === "production") {
169
171
  setTimeout(function () {
172
+ const pm2 = getPm2()
173
+ if (!pm2) return
170
174
  pm2.connect(function (err) {
171
175
  if (err) {
172
176
  console.log(err.toString());
package/lib/zReport.js CHANGED
@@ -3,7 +3,6 @@ const fs = require('fs-extra')
3
3
  const nodemailer = require('nodemailer')
4
4
  const qs = require('qs')
5
5
  const moment = require('moment')
6
- const XLSX = require('xlsx')
7
6
  const Excel = require('exceljs')
8
7
  const debug = require('./debug')
9
8
  const zRoute = require('./zRoute')
@@ -25,13 +24,43 @@ if (typeof global.dirRoot === 'undefined') {
25
24
  /*
26
25
  UI For edit excel File
27
26
  */
28
- zReport.reportData = (filename, data, sessions = {}) => {
29
- console.log(filename)
30
- const workbook = XLSX.readFile(filename)
31
- const Sheets = workbook.Sheets
32
- let sheet = Sheets[Object.keys(Sheets)[0]]
27
+ function colToLetter (col) {
28
+ let temp = ''
29
+ let n = col
30
+ while (n > 0) {
31
+ const r = (n - 1) % 26
32
+ temp = String.fromCharCode(65 + r) + temp
33
+ n = Math.floor((n - 1) / 26)
34
+ }
35
+ return temp
36
+ }
37
+
38
+ function cellToPrimitive (cell) {
39
+ // exceljs cell.text is safest for UI display
40
+ if (!cell) return ''
41
+ if (typeof cell.text === 'string' && cell.text !== '') return cell.text
42
+ const v = cell.value
43
+ if (v == null) return ''
44
+ if (typeof v === 'string' || typeof v === 'number' || typeof v === 'boolean') return v
45
+ if (typeof v === 'object') {
46
+ if (Object.prototype.hasOwnProperty.call(v, 'result')) return v.result ?? ''
47
+ if (Object.prototype.hasOwnProperty.call(v, 'text')) return v.text ?? ''
48
+ }
49
+ return String(v)
50
+ }
51
+
52
+ zReport.reportData = async (filename, data, sessions = {}) => {
53
+ const workbook = new Excel.Workbook()
54
+ await workbook.xlsx.readFile(filename)
55
+ const worksheet = workbook.worksheets[0]
56
+ if (!worksheet) {
57
+ throw new Error('Excel worksheet not found')
58
+ }
33
59
  let excel = Util.excelSequence()
34
- let ref = sheet['!ref']
60
+ const dim = worksheet.dimensions
61
+ const right = dim ? dim.right : (worksheet.actualColumnCount || 1)
62
+ const bottom = dim ? dim.bottom : (worksheet.actualRowCount || 1)
63
+ const ref = `A1:${colToLetter(right)}${bottom}`
35
64
  let explode = ref.split(':')
36
65
  let lastchar = explode[1]
37
66
  let stringPattern = /[A-Z]+/i
@@ -48,23 +77,23 @@ zReport.reportData = (filename, data, sessions = {}) => {
48
77
  let excelQuery = data.excel_query || {}
49
78
  let dataForExcel = excelQuery.excel
50
79
  let dataCallback = data.callback || []
51
- let callback = {}
80
+ let callbacks = {}
52
81
  let objQuery = {}
53
82
  let results = []
54
83
 
55
84
  //set callback as object
56
85
  dataCallback.map((m) => {
57
- callback[m.name] = m.value
86
+ callbacks[m.name] = m.value
58
87
  })
59
88
 
60
89
  //console.log(JSON.stringify(sessions));
61
90
 
62
91
  //create UI Button in excel cell
63
92
  if (dataForExcel) {
64
- dataForExcel.forEach((datafor, index) => {
93
+ dataForExcel.forEach((datafor) => {
65
94
  let button = '',
66
95
  name = datafor.name,
67
- callback = datafor.callback || '',
96
+ callbackValue = datafor.callback || '',
68
97
  value = datafor.value || ''
69
98
  let split = value.split('.')
70
99
  let len = split.length
@@ -93,7 +122,7 @@ zReport.reportData = (filename, data, sessions = {}) => {
93
122
 
94
123
  let labels = value.indexOf('_SESSIONS_') > -1 ? value.replace('_SESSIONS_.', '') : tableKey
95
124
  button += `<li class="dragged"> <button class="btn btn-info btn-excel" type="button" title="${name.replace('[', '').replace(']', '')} : ${value}">${MYMODEL.labels[labels]}
96
- <input type="hidden" class="EXCEL" name="${name}" value='${value}_CALLBACK_SEPARATOR_${callback}'> <i class="fa fa-code call-me"></i> <i class="fa fa-trash trash-me"></i></button></li>`
125
+ <input type="hidden" class="EXCEL" name="${name}" value='${value}_CALLBACK_SEPARATOR_${callbackValue}'> <i class="fa fa-code call-me"></i> <i class="fa fa-trash trash-me"></i></button></li>`
97
126
  excelValue[name] = button
98
127
  })
99
128
  }
@@ -106,7 +135,8 @@ zReport.reportData = (filename, data, sessions = {}) => {
106
135
  for (var i = 0; i <= maxColumn; i++) {
107
136
  let str = excel[i] + x
108
137
  let strkey = excel[i] + '[' + x + ']'
109
- let defaultValue = Object.prototype.hasOwnProperty.call(sheet, str) ? sheet[str].v : ''
138
+ const cell = worksheet.getCell(str)
139
+ let defaultValue = cellToPrimitive(cell)
110
140
  let value = excelValue[strkey] || defaultValue
111
141
  table += `<td width="80px" id="${str}" title="${str}" class="mydragable" data-col="${excel[i]}" data-row="${x}">${value}</td>`
112
142
  arr.push(value)
@@ -6,7 +6,7 @@ const bodyParser = require('body-parser')
6
6
  const path = require('path')
7
7
  const parseForm = bodyParser.urlencoded({ extended: true })
8
8
  const csrfProtection = csrf({ cookie: true })
9
- const pm2 = require('pm2')
9
+ const getPm2 = require('./optionalPm2')
10
10
  const env = process.env.NODE_ENV || 'development'
11
11
  const ejs = require('ejs')
12
12
  const Util = require('./Util')
@@ -99,6 +99,11 @@ router.post('/update/:id', async function (req, res, next) {
99
99
  await zCache.ROLES()
100
100
 
101
101
  if (env == 'production') {
102
+ const pm2 = getPm2()
103
+ if (!pm2) {
104
+ res.json(data)
105
+ return
106
+ }
102
107
  pm2.connect(function (err) {
103
108
  if (err) {
104
109
  //console.log(err.toString());
package/lib/zRoute.js CHANGED
@@ -4,7 +4,6 @@
4
4
  */
5
5
  require("dotenv").config();
6
6
  const path = require("path");
7
- const excelToJson = require("convert-excel-to-json");
8
7
  const qs = require("qs");
9
8
  //for generate PDF
10
9
  const puppeteer = require("puppeteer");
@@ -24,6 +23,7 @@ const cForm = require("./Form");
24
23
  const readXlsxFile = require("read-excel-file/node");
25
24
  //const { Dropbox } = require("dropbox");
26
25
  const zDropbox = require("./zDropbox");
26
+ const getPm2 = require("./optionalPm2");
27
27
 
28
28
  if (typeof global.dirRoot === 'undefined') {
29
29
  global.dirRoot = Util.dirRoot;
@@ -6241,6 +6241,8 @@ module.exports = (req, res, next) => {`;
6241
6241
  Util.writeFile(fileSystem, templateSystem);
6242
6242
  if (process.env.NODE_ENV === "production") {
6243
6243
  setTimeout(function () {
6244
+ const pm2 = getPm2()
6245
+ if (!pm2) return
6244
6246
  pm2.connect(function (err) {
6245
6247
  if (err) {
6246
6248
  console.log(err + "");
@@ -10,7 +10,7 @@ const myCache = require("./cache");
10
10
  const moduleLib = require("./moduleLib");
11
11
  const Model = require('./Model')
12
12
  const ejs = require('ejs')
13
- const pm2 = require("pm2");
13
+ const getPm2 = require("./optionalPm2");
14
14
 
15
15
  if (typeof global.dirRoot === 'undefined') {
16
16
  global.dirRoot = Util.dirRoot;
@@ -515,6 +515,8 @@ const generate = async (req, res) => {
515
515
  await createAllFiles(table)
516
516
  //restart pm2 module in production
517
517
  if (process.env.NODE_ENV == 'production') {
518
+ const pm2 = getPm2()
519
+ if (!pm2) return Util.jsonSuccess('Success')
518
520
  pm2.connect(function (err) {
519
521
  if (err) {
520
522
  console.log(err.toString())
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "zet-lib",
3
- "version": "3.3.7",
3
+ "version": "4.0.1",
4
4
  "description": "zet is a library that part of zet generator.",
5
5
  "engines": {
6
6
  "node": ">=18"
@@ -28,35 +28,35 @@
28
28
  },
29
29
  "sideEffects": false,
30
30
  "dependencies": {
31
- "axios": "^1.7.9",
32
- "convert-excel-to-json": "^1.7.0",
31
+ "axios": "^1.15.0",
33
32
  "dotenv": "^16.5.0",
34
33
  "dropbox": "^10.34.0",
35
34
  "ejs": "^3.1.10",
36
35
  "exceljs": "^4.4.0",
37
36
  "express-zip": "^3.0.0",
38
- "fs-extra": "^11.3.2",
37
+ "fs-extra": "^11.3.4",
39
38
  "html-minifier-terser": "^7.2.0",
40
39
  "isomorphic-fetch": "^3.0.0",
41
40
  "js-sha256": "^0.11.1",
42
41
  "jszip": "^3.10.1",
43
42
  "moment": "^2.30.1",
44
43
  "node-cache": "^5.1.2",
45
- "nodemailer": "^6.9.4",
44
+ "nodemailer": "^8.0.5",
46
45
  "pg": "^8.16.3",
47
- "pm2": "^5.3.1",
48
- "puppeteer": "^24.33.0",
46
+ "puppeteer": "^24.40.0",
49
47
  "qs": "^6.14.0",
50
48
  "randomstring": "^1.3.1",
51
49
  "read-excel-file": "^5.8.0",
52
50
  "socket.io": "^4.8.3",
53
51
  "uglify-js": "^3.19.3",
54
- "uuid": "^9.0.1",
55
- "xlsx": "^0.18.5"
52
+ "uuid": "^9.0.1"
56
53
  },
57
54
  "optionalDependencies": {
58
55
  "sharp": "^0.34.1"
59
56
  },
57
+ "devDependencies": {
58
+ "standard": "^17.1.2"
59
+ },
60
60
  "overrides": {
61
61
  "unzipper": "^0.12.3",
62
62
  "rimraf": "^6.1.2",