create-sip 0.14.3 → 0.15.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/create-sip.js CHANGED
@@ -61,7 +61,7 @@ const questions = [
61
61
  },
62
62
  {
63
63
  title: 'Express API',
64
- description: 'Express API with simple Sequelize',
64
+ description: 'Express API with simple Sequelize and ES modules',
65
65
  value: 'expressapi'
66
66
  },
67
67
  {
@@ -111,7 +111,7 @@ const questions = [
111
111
  return;
112
112
  }
113
113
  if(res.type === 'expressapi') {
114
- console.log('Create a new Express API...');
114
+ console.log('Create a new Express API with ES modules...');
115
115
  genExpressApi(res.name);
116
116
  return;
117
117
  }
@@ -65,11 +65,46 @@ npm start
65
65
  You can generate a model and controller with the following commands:
66
66
 
67
67
  ```bash
68
- node op create model thing
69
- node op create controller thing
68
+ node op make:model something
69
+ node op make:controller something
70
70
  ```
71
71
 
72
- The name after the model and controller statements must be given in the singular.
72
+ The name after the model and controller statements must be given in the singular. Controller generation automatically appends the "Controller" suffix.
73
+
74
+ ## Admin user
75
+
76
+ The admin user can be created with the following command:
77
+
78
+ ```bash
79
+ node op admin:generate
80
+ ```
81
+
82
+ The command will prompt for the password.
83
+
84
+ ## Config generation
85
+
86
+ The next command generates the default config file:
87
+
88
+ ```bash
89
+ node op conf:generate
90
+ ```
91
+
92
+ ## Database seed
93
+
94
+ The database can be seeded with the following command:
95
+
96
+ ```bash
97
+ node op db:seed <model_name> <file_path>
98
+ ```
99
+
100
+ The model name must be given in the singular and lowercase. The file extension must be:
101
+
102
+ * .json
103
+ * .csv
104
+
105
+ The keys in the JSON file and the field names in the CSV file must match the model fields.
106
+
107
+ If the CSV file contains quotation marks, they are automatically removed.
73
108
 
74
109
  ## Licence
75
110
 
@@ -1,4 +1,4 @@
1
1
  {
2
- "watch": ["app/index.js", "app"],
3
- "ext": "js"
2
+ "watch": ["app", "config"],
3
+ "ext": ".js,.json"
4
4
  }
package/expressapi/op CHANGED
@@ -1,20 +1,55 @@
1
- import replace from 'replace';
2
- import fs from 'fs-extra';
3
-
1
+ import replace from 'replace'
2
+ import fse from 'fs-extra'
4
3
  import fsp from 'fs/promises'
5
4
  import { generateApiKey } from 'generate-api-key'
6
-
7
5
  import bcrypt from 'bcryptjs';
8
6
  import path from 'path';
9
-
10
7
  import { read } from 'read'
11
8
 
12
- if(process.argv.length == 3 && process.argv[2] == 'key:generate') {
9
+ if(process.argv.length == 3 && process.argv[2] == 'help') {
10
+ console.log('Usable commands:');
11
+ console.log(' node op make:model <name>');
12
+ console.log(' node op make:controller <name>');
13
+ console.log(' node op key:generate');
14
+ console.log(' node op conf:generate');
15
+ console.log(' node op admin:generate');
16
+ console.log(' node op db:seed <model> <filePath>');
17
+ process.exit(0);
18
+ } else if(process.argv.length == 3 && process.argv[2] == 'key:generate') {
13
19
  startGenerateKey();
14
20
  } else if(process.argv.length == 3 && process.argv[2] == 'conf:generate') {
15
21
  startGenerateConf();
16
22
  } else if(process.argv.length == 3 && process.argv[2] == 'admin:generate') {
17
23
  startGenerateAdmin();
24
+ } else if(process.argv[2] === 'db:seed') {
25
+ if(process.argv.length < 5) {
26
+ console.log('Usage:');
27
+ console.log('node op db:seed <model> <filePath>');
28
+ console.log('Examples:');
29
+ console.log('node op db:seed thing somethings.json');
30
+ console.log('node op db:seed thing somethings.csv');
31
+ }
32
+ const model = process.argv[3];
33
+ const filePath = process.argv[4];
34
+ runSeed(model, filePath);
35
+ } else if(process.argv[2] === 'make:model') {
36
+ if(process.argv.length < 4) {
37
+ console.log('Usage:');
38
+ console.log('node op make:model <name>');
39
+ console.log('Examples:');
40
+ console.log('node op make:model something');
41
+ }
42
+ copyModel(process.argv[3]);
43
+
44
+ } else if(process.argv[2] === 'make:controller') {
45
+ if(process.argv.length < 4) {
46
+ console.log('Usage:');
47
+ console.log('node op make:controller <name>');
48
+ console.log('Examples:');
49
+ console.log('node op make:controller something');
50
+ }
51
+ copyController(process.argv[3]);
52
+
18
53
  } else if(process.argv.length < 4) {
19
54
  console.log('Usage:');
20
55
  console.log('node op <command> <type> <name>');
@@ -27,22 +62,20 @@ if(process.argv.length == 3 && process.argv[2] == 'key:generate') {
27
62
  if(process.argv[2] === 'create') {
28
63
  console.log('Create a new ' + process.argv[3] + '...');
29
64
  if(process.argv[3] === 'model') {
30
- copyModel();
65
+ copyModel(process.argv[4]);
31
66
  }
32
67
  if(process.argv[3] === 'controller') {
33
- copyController();
68
+ copyController(process.argv[4]);
34
69
  }
35
70
  }
36
71
  }
37
72
 
38
- async function copyController() {
39
-
40
- const className = process.argv[4]
73
+ async function copyController(className) {
41
74
  const lowerName = className.toLowerCase()
42
75
 
43
76
  const src = 'templates/controllerTemplate.js'
44
77
  const dest = `app/controllers/${lowerName}controller.js`
45
- await fs.copy(src, dest)
78
+ await fse.copy(src, dest)
46
79
 
47
80
  replace({
48
81
  regex: 'Thing',
@@ -61,14 +94,12 @@ async function copyController() {
61
94
  })
62
95
  }
63
96
 
64
- async function copyModel() {
65
-
66
- const className = process.argv[4]
97
+ async function copyModel(className) {
67
98
  const lowerName = className.toLowerCase()
68
-
69
99
  const src = 'templates/modelTemplate.js'
70
100
  const dest = `app/models/${lowerName}.js`
71
- await fs.copy(src, dest)
101
+
102
+ await fse.copy(src, dest)
72
103
 
73
104
  replace({
74
105
  regex: 'Thing',
@@ -96,16 +127,20 @@ function startGenerateKey() {
96
127
  return json
97
128
  })
98
129
  .then(json => JSON.stringify(json, null, 4))
99
- .then(body => fs.writeFile(fileName, body, 'utf8'))
130
+ .then(body => fse.writeFile(fileName, body, 'utf8'))
100
131
  .catch(error => console.log(error))
101
132
  }
102
133
 
103
- function startGenerateConf() {
134
+ async function startGenerateConf() {
104
135
  console.log('Generate conf...');
105
136
  const sourceFileName = 'config/default.json.example';
106
137
  const destinationFileName = 'config/default.json';
107
- fs.copyFile(sourceFileName, destinationFileName)
108
- .catch(error => console.log(error));
138
+ try {
139
+ await fse.copyFile(sourceFileName, destinationFileName)
140
+ } catch (error) {
141
+ console.log(error)
142
+ }
143
+
109
144
  }
110
145
 
111
146
  async function loadConfig() {
@@ -158,4 +193,89 @@ async function startGenerateAdmin() {
158
193
  console.error('Error creating admin!')
159
194
  console.error(err)
160
195
  }
161
- }
196
+ }
197
+
198
+ const seedFromJson = async (model, filePath) => {
199
+ try {
200
+ const data = JSON.parse(await fsp.readFile(filePath, 'utf8'))
201
+ await model.bulkCreate(data)
202
+ console.log(`Data seeded successfully! ${model.name}`)
203
+ } catch (error) {
204
+ console.error(error)
205
+ }
206
+ }
207
+
208
+ const seedFromCsv = async (model, filePath) => {
209
+ const sep = ','
210
+ try {
211
+ const data = await fsp.readFile(filePath, 'utf8')
212
+ const clearData = data.replace(/"/g, '').trim()
213
+ const rows = clearData.split('\n')
214
+ const headerColumns = rows.shift().split(sep)
215
+
216
+ const dataToInsert = rows.map(row => {
217
+ const columns = row.split(sep).map(item => {
218
+ const number = Number(item)
219
+ return Number.isNaN(number) ? `${item}` : number
220
+ })
221
+ return headerColumns.reduce((obj, header, index) => {
222
+ obj[header] = columns[index]
223
+ return obj
224
+ }, {})
225
+ })
226
+
227
+ await model.bulkCreate(dataToInsert)
228
+ console.log(`Data seeded successfully! ${model.name}`)
229
+ } catch (error) {
230
+ console.error(error)
231
+ }
232
+ }
233
+
234
+ async function runSeed(model, filePath) {
235
+
236
+ if(!filePath || !model) {
237
+ console.log('Usage: node seed.js <modelName> <filePath>')
238
+ process.exit(1)
239
+ }
240
+
241
+ try {
242
+ await import(`./app/models/${model}.js`)
243
+ } catch (error) {
244
+ console.log(`The ${model} model file does not exist!`)
245
+ process.exit(1)
246
+ }
247
+
248
+ try {
249
+ await fsp.stat(filePath)
250
+ } catch (error) {
251
+ if (error.code === 'ENOENT') {
252
+ console.log(`The file ${filePath} does not exist!`)
253
+ process.exit(1)
254
+ } else {
255
+ console.error(error)
256
+ process.exit(1)
257
+ }
258
+ }
259
+
260
+ const modelInstance = await import(`./app/models/${model}.js`)
261
+ const modelObject = modelInstance.default
262
+
263
+ const ext = path.extname(filePath).toLowerCase()
264
+ if(ext !== '.json' && ext !== '.csv') {
265
+ console.log('The file must have .json or .csv extension!')
266
+ process.exit(1)
267
+ }
268
+ const { default: sequelize } = await import('./app/database/database.js')
269
+ try {
270
+ await sequelize.sync({ force: true })
271
+ await sequelize.authenticate()
272
+ if(ext === '.csv') {
273
+ await seedFromCsv(modelObject, filePath)
274
+ }else {
275
+ await seedFromJson(modelObject, filePath)
276
+ }
277
+ } catch (error) {
278
+ console.error(error)
279
+ }
280
+
281
+ }
package/manager.js CHANGED
@@ -71,10 +71,11 @@ const genExpressApi = (target) => {
71
71
  console.log(' node op key:generate');
72
72
  console.log(' npm run dev');
73
73
  console.log('Usable commands:');
74
- console.log(' node op create model thing');
75
- console.log(' node op create controller thing');
74
+ console.log(' node op make:model something');
75
+ console.log(' node op make:controller something');
76
76
  console.log('The model and controller names must be');
77
- console.log('given in the singular');
77
+ console.log('given in the singular. More info:');
78
+ console.log(' node op help')
78
79
  }
79
80
 
80
81
  module.exports = {
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "create-sip",
3
- "version": "0.14.3",
3
+ "version": "0.15.1",
4
4
  "main": "index.js",
5
5
  "bin": {
6
6
  "create-sip": "create-sip.js"