superconf 1.3.0 → 1.4.0

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/.eslintrc.json ADDED
@@ -0,0 +1,3 @@
1
+ {
2
+ "extends": "standard"
3
+ }
package/.firerc.json ADDED
@@ -0,0 +1,19 @@
1
+ {
2
+ "build": {
3
+ "destDir": "dist/",
4
+ "srcDir": "src/",
5
+ "copyFiles": [
6
+ "/package.json",
7
+ "/LICENSE",
8
+ "/README.md",
9
+ "Legacy.js"
10
+ ]
11
+ },
12
+ "features": {
13
+ "esModules": false,
14
+ "esDefaultParams": false,
15
+ "esClasses": true,
16
+ "esTemplates": true,
17
+ "extendRegExp": true
18
+ }
19
+ }
package/.fslintignore ADDED
@@ -0,0 +1 @@
1
+ docs/
package/.gitlab-ci.yml ADDED
@@ -0,0 +1,4 @@
1
+ include:
2
+ - project: 'Coffeebreak/coffeebreak-ci'
3
+ ref: develop
4
+ file: 'gitlab/firescript-module-pipeline.yml'
package/app.js CHANGED
@@ -1,23 +1,3 @@
1
- module.exports.__fsLocationMap = [[1, 8, 2, 7], [1, 23, 2, 27], [1, 8, 2, 42], [3, 1, 3, 1], [3, 6, 3, 10], [3, 17, 3, 21], [3, 23, 3, 27], [5, 1, 4, 1], [5, 7, 4, 7], [5, 24, 4, 24], [5, 31, 4, 31], [6, 1, 5, 1], [6, 8, 5, 8], [6, 18, 5, 18], [6, 19, 5, 19], [6, 25, 5, 25], [7, 9, 6, 15], [8, 5, 7, 3], [8, 11, 7, 9], [8, 20, 7, 18], [8, 24, 7, 22], [8, 34, 7, 32], [9, 5, 8, 3], [9, 12, 8, 10], [9, 19, 8, 17], [9, 28, 8, 26], [11, 1, 10, 1], [11, 8, 10, 8], [11, 15, 10, 15], [11, 22, 10, 22], [11, 31, 10, 31], [12, 11, 11, 26], [15, 5, 12, 16], [15, 5, 12, 28], [16, 5, 13, 16], [16, 5, 13, 28], [18, 8, 14, 1], [18, 13, 14, 10], [18, 21, 14, 18], [20, 5, 16, 3], [20, 12, 16, 10], [20, 16, 16, 14], [20, 26, 16, 24], [18, 13, 18, 16], [18, 13, 18, 25], [22, 8, 19, 1], [22, 14, 19, 7], [22, 22, 19, 15], [22, 32, 19, 25], [22, 42, 19, 35], [22, 14, 20, 16], [22, 14, 20, 24], [23, 8, 21, 1], [23, 14, 21, 7], [23, 21, 21, 14], [23, 31, 21, 24], [23, 41, 21, 34], [23, 14, 22, 16], [23, 14, 22, 23]];
2
- module.exports.__esModule = true;
3
- const Superconf = require('./Superconf').Superconf;
4
- function superconf (name, opts) {}
5
- const defaultExports = module.exports;
6
- module.exports = (name, opts) => {
7
- console.log('Superconf: Import namespace method is deprecated. Use named imports instead');
8
- const config = new Superconf(opts);
9
- return config.tryFiles(name);
10
- };
11
- Object.assign(module.exports, defaultExports);
12
- module.exports.default = superconf;
13
- module.exports.Superconf = Superconf;
14
- module.exports.superconf = superconf;
15
- function config (opts) {
16
- // log 'Superconf: Import of config() method is deprecated. Use named imports instead'
17
- return new Superconf(opts);
18
- }
19
- module.exports.config = config;
20
- const merge = Superconf.prototype.merge;
21
- module.exports.merge = merge;
22
- const copy = Superconf.prototype.copy;
23
- module.exports.copy = copy;
1
+ #!/usr/bin/node
2
+ require('firescript/register')
3
+ module.exports = require('./src/app')
@@ -0,0 +1,3 @@
1
+ #!/usr/bin/node
2
+ require('firescript/register')
3
+ require('./superconf')
@@ -0,0 +1,38 @@
1
+ import * as path from 'path'
2
+ import DocGenerator from 'doxydoc'
3
+ import Superconf from '../../'
4
+
5
+ export const doc = new DocGenerator()
6
+ doc.setTitle('Superconf')
7
+ doc.setFilename(path.join(__dirname, '../superconf.md'))
8
+ doc.setAsset('class', 'Superconf')
9
+
10
+ doc.intro = 'Superconf is a smart configuration loader for Node.js. It supports different config formats, ENV variables and validates config against a config schema'
11
+
12
+ # doc.property('obj', 'components', 'Contains app component')
13
+ # doc.property('arr', 'cssStyles', 'Holds all cssStyles used by Components')
14
+ # doc.property('arr', 'dataServices', 'Holdsw all dataservices used by Components')
15
+ # doc.property('arr', 'scripts', 'Contains all necesary scripts and clientLibs')
16
+ # doc.property('arr', 'signals', 'Holds all signals used by Components')
17
+ # doc.property('arr', 'states', 'Holds all states used by Components')
18
+ #
19
+ doc.method('void', 'schema', [{
20
+ type: 'obj', name: 'schemaConf', description: 'Schema config object'
21
+ }], 'Set schema config')
22
+
23
+ doc.method('void', 'fromFile', [{
24
+ type: 'str', name: 'name', description: 'Use `name` as filename'
25
+ }], 'Import config from file')
26
+
27
+
28
+ # Test data
29
+ const sc = new Superconf()
30
+
31
+ doc.setData(sc)
32
+ doc.example('json', sc, 'Superconf structure', 'This shows the data structure of a Superconf instance')
33
+
34
+ doc.generate().then(() =>
35
+ log 'Documentation' doc.filename 'generated'
36
+ ).catch((err) =>
37
+ throw err
38
+ )
@@ -0,0 +1,68 @@
1
+ Superconf
2
+ =========
3
+
4
+ Superconf is a smart configuration loader for Node.js. It supports different config formats, ENV variables and validates config against a config schema
5
+
6
+ #### Structure
7
+
8
+ ```coffee
9
+ class Superconf
10
+ # Methods
11
+ schema(obj schemaConf) : void
12
+ fromFile(str name) : void
13
+ ```
14
+
15
+
16
+
17
+ ### Methods
18
+
19
+ #### schema(*obj* schemaConf) : *void*
20
+ Set schema config
21
+
22
+ #### fromFile(*str* name) : *void*
23
+ Import config from file
24
+
25
+ ### Examples
26
+
27
+ #### Superconf structure
28
+
29
+ This shows the data structure of a Superconf instance
30
+
31
+ ```json
32
+ {
33
+ "files": [
34
+ "%s.json",
35
+ "%s.cson",
36
+ "%s.yaml",
37
+ "%s.yml",
38
+ ".%src",
39
+ ".%src.json",
40
+ ".%src.cson",
41
+ ".%src.yaml",
42
+ ".%src.yml",
43
+ "package.json"
44
+ ],
45
+ "cwd": "/home/andi/Projects/Nodejs/superconf",
46
+ "workingDir": "/home/andi/Projects/Nodejs/superconf",
47
+ "configData": {},
48
+ "verbose": false
49
+ }
50
+ ```
51
+
52
+
53
+
54
+ ### Undocumented
55
+
56
+ #### Undocumented properties and methods
57
+
58
+ | Name | Description |
59
+ |-----------------|----------------------------------------|
60
+ | files | Property files is not documented |
61
+ | cwd | Property cwd is not documented |
62
+ | workingDir | Property workingDir is not documented |
63
+ | configData | Property configData is not documented |
64
+ | verbose | Property verbose is not documented |
65
+ | constructor() | Method constructor is not documented |
66
+ | debug() | Method debug is not documented |
67
+ | getSchemaItem() | Method getSchemaItem is not documented |
68
+ | validate() | Method validate is not documented |
package/package.json CHANGED
@@ -1,11 +1,11 @@
1
1
  {
2
2
  "name": "superconf",
3
- "version": "1.3.0",
3
+ "version": "1.4.0",
4
4
  "description": "Smart configuration loader",
5
5
  "main": "app.js",
6
6
  "scripts": {
7
7
  "test": "inspectio run",
8
- "lint": "firelint",
8
+ "lint": "firelint || true",
9
9
  "build": "firescript build"
10
10
  },
11
11
  "keywords": [
@@ -13,27 +13,19 @@
13
13
  "config",
14
14
  "configuration"
15
15
  ],
16
- "author": "Andifeind <andifeind@noname-media.com>",
16
+ "author": "Andi Heinkelein <andi@noname-media.com>",
17
17
  "license": "MIT",
18
18
  "devDependencies": {
19
- "eslint": "^8.23.1",
20
- "eslint-config-standard": "^17.0.0",
21
- "eslint-plugin-import": "^2.26.0",
22
- "eslint-plugin-node": "^11.1.0",
23
- "eslint-plugin-promise": "^6.0.1",
24
- "eslint-plugin-standard": "^5.0.0",
25
- "firelint": "^0.10.0",
19
+ "firelint": "^0.12.0",
26
20
  "firescript": "^0.21.1",
27
- "firescript-test": "^0.11.10",
28
21
  "inspect.js": "^1.13.1",
29
- "inspectio": "^0.5.0",
30
- "mocha": "^10.0.0"
22
+ "inspectio": "^0.9.0"
31
23
  },
32
24
  "dependencies": {
33
25
  "coffeescript": "^2.7.0",
26
+ "firescript-firefs": "^0.3.3",
34
27
  "firescript-runtime": "^0.3.13",
35
- "js-yaml": "^4.1.0",
36
- "lagoon-reporter": "^0.7.9"
28
+ "js-yaml": "^4.1.0"
37
29
  },
38
30
  "directories": {
39
31
  "test": "tests"
@@ -45,6 +37,5 @@
45
37
  "bugs": {
46
38
  "url": "https://github.com/Andifeind/superconf/issues"
47
39
  },
48
- "homepage": "https://github.com/Andifeind/superconf#readme",
49
- "firescript": "0.21.1"
40
+ "homepage": "https://github.com/Andifeind/superconf#readme"
50
41
  }
@@ -49,7 +49,6 @@ class Superconf {
49
49
  }
50
50
 
51
51
  tryFiles (name) {
52
- console.error('superconf.tryFiles() is deprecated. Use .load() instead')
53
52
  if (!name) {
54
53
  throw new Error('Name arg must be set!')
55
54
  }
@@ -0,0 +1,258 @@
1
+ import Superconf as Legacy from './Legacy'
2
+ import * as colorfy from 'colorfy'
3
+ import * as path from 'path'
4
+ import FireFS from 'firescript-firefs'
5
+
6
+ const red = '\u001b[38;5;160m'
7
+ const ored = '\u001b[38;5;202m'
8
+ const yellow = '\u001b[38;5;226m'
9
+ const dgrey = '\u001b[38;5;244m'
10
+ const lgrey = '\u001b[38;5;250m'
11
+ const azure = '\u001b[38;5;39m'
12
+ const uncolor = '\u001b[m'
13
+
14
+ export class Superconf extends Legacy
15
+ constructor (opts = {})
16
+ super(opts)
17
+
18
+ this.workingDir = opts.workingDir || process.cwd()
19
+ this.config = {}
20
+ this.verbose = opts.verbose || false
21
+ this.mergeDept = opts.dept || 0
22
+
23
+ this.files = opts.files || [
24
+ '%s.json'
25
+ '%s.yaml'
26
+ '%s.yml'
27
+ '.%src.json'
28
+ '.%src.yaml'
29
+ '.%src.yml'
30
+ ]
31
+
32
+
33
+ debug (msg, ...data)
34
+ if this.verbose
35
+ log colorfy.yellow('Superconf:'), colorfy.grey(msg), ...data
36
+
37
+
38
+ schema (configSchema)
39
+ this.configSchema = {}
40
+ Object.entries(configSchema).forEach(([key, value]) =>
41
+ const schema = {
42
+ type: value.type || 'str'
43
+ required: value.required || false
44
+ }
45
+
46
+ if typeof value.default !== 'undefined'
47
+ schema.default = value.default
48
+
49
+ if typeof value.properties !== 'undefined'
50
+ schema.properties = value.properties
51
+
52
+ this.configSchema[key] = schema
53
+ )
54
+
55
+
56
+ getSchemaItem (schema, key)
57
+ return schema[key] || null
58
+
59
+
60
+ validate (conf)
61
+ if !this.configSchema
62
+ return true
63
+
64
+ this.validationErrors = []
65
+ const validateionData = conf || this.config
66
+ const validateionSchema = {
67
+ type: 'obj'
68
+ properties: this.configSchema
69
+ }
70
+
71
+ this.validateProperty(validateionSchema, 'config', validateionData)
72
+
73
+ return this.validationErrors.length === 0
74
+
75
+ validateProperty (schema, name, property)
76
+ this.debug('Validate property ${name} with value', property, 'against schema', schema)
77
+
78
+ if !schema
79
+ return true
80
+
81
+ if !property
82
+ if schema.required === true
83
+ this.validationErrors.push('Item ${name} is required but not set')
84
+
85
+ else
86
+ return true
87
+
88
+ if schema.type === 'str'
89
+ if typeof property !== 'string'
90
+ this.validationErrors.push('Item ${name} is not of type string')
91
+
92
+ elif schema.type === 'num'
93
+ if typeof property !== 'number'
94
+ this.validationErrors.push('Item ${name} is not of type number')
95
+
96
+ elif schema.type === 'bool'
97
+ if typeof property !== 'boolean'
98
+ this.validationErrors.push('Item ${name} is not of type boolean')
99
+
100
+ elif schema.type === 'arr'
101
+ if !Array.isArray(property)
102
+ this.validationErrors.push('Item ${name} is not of type array')
103
+
104
+ elif schema.type === 'obj'
105
+ if typeof property !== 'object'
106
+ this.validationErrors.push('Item ${name} is not of type object')
107
+
108
+ Object.entries(property).forEach(([key, value]) =>
109
+ const subSchema = this.getSchemaItem(schema.properties, key)
110
+ this.validateProperty(subSchema, '${name}.${key}', value)
111
+ )
112
+
113
+ Object.entries(schema.properties).forEach(([key, subSchema]) =>
114
+ if !property[key] && subSchema.default !== undefined
115
+ this.debug('Set default value for property ${name} to', subSchema.default)
116
+ property[key] = subSchema.default
117
+
118
+ elif !property[key] && subSchema.type === 'obj'
119
+ property[key] = {}
120
+
121
+ this.validateProperty(subSchema, '${name}.${key}', property[key])
122
+ )
123
+
124
+ async fromFile (filepath)
125
+ const fl = await FireFS.file(filepath)
126
+
127
+ if !fl.exists
128
+ this.debug('Try file', filepath)
129
+ return null
130
+
131
+ this.debug('Load from file', filepath)
132
+ if fl.ext === 'json'
133
+ return fl.readJSON()
134
+
135
+ if fl.ext === 'yaml' || fl.ext === 'yml'
136
+ const yaml = require('js-yaml')
137
+ const source = await fl.read()
138
+ return yaml.load(source)
139
+
140
+ return null
141
+
142
+ setDefaults (config)
143
+ Object.entries(this.configSchema).forEach(([key, value]) =>
144
+ if typeof config[key] === 'undefined' && typeof value.default !== 'undefined'
145
+ config[key] = value.default
146
+ )
147
+
148
+
149
+ async load (name)
150
+ this.debug('Load config', name)
151
+
152
+ for const file of this.files
153
+ const filepath = path.resolve(this.workingDir, file.replace('%s', name))
154
+ const config = await this.fromFile(filepath)
155
+
156
+ if config === null
157
+ continue
158
+
159
+ # if config
160
+ # this.setDefaults(config)
161
+
162
+ if !this.validate(config)
163
+ const validationErrors = this.validationErrors.join(' \n')
164
+ throw new Error('Invalid config loaded!\n ${validationErrors}')
165
+
166
+ this.config = config
167
+ return config
168
+
169
+ return null
170
+
171
+ merge (...args)
172
+ const conf = {}
173
+
174
+ const merge = (left, right, curdept) =>
175
+ if left === undefined || left === null
176
+ left = {}
177
+
178
+ if typeof right !== 'object'
179
+ return left
180
+
181
+
182
+ for const key in right
183
+ if right.hasOwnProperty(key)
184
+ if right[key] === undefined
185
+ continue
186
+
187
+ if right[key] === null
188
+ left[key] = null
189
+ continue
190
+
191
+ if Array.isArray(right[key])
192
+ left[key] = right[key].map((item) =>
193
+ if typeof item === 'object'
194
+ return JSON.parse(JSON.stringify(item))
195
+
196
+ return item
197
+ )
198
+
199
+ continue
200
+
201
+ if typeof right[key] === 'object'
202
+ if curdept
203
+ left[key] = merge(left[key], right[key], left[key]--)
204
+ continue
205
+
206
+ left[key] = Object.assign({}, right[key])
207
+ continue
208
+
209
+ left[key] = right[key]
210
+
211
+ return left
212
+
213
+ for let i = 0; i < args.length; i++
214
+ merge(conf, args[i], this.mergeDept)
215
+
216
+ return conf
217
+
218
+ copy (obj)
219
+ if typeof obj !== 'object' || obj === null
220
+ return obj
221
+
222
+ if Array.isArray(obj)
223
+ return obj.map((item) =>
224
+ this.copy(item)
225
+ )
226
+
227
+ const copied = {}
228
+ for const key in obj
229
+ if obj.hasOwnProperty(key)
230
+ if obj[key] === null
231
+ copied[key] = null
232
+ continue
233
+
234
+ if Array.isArray(obj[key])
235
+ copied[key] = obj[key].map((item) =>
236
+ this.copy(item)
237
+ )
238
+
239
+ continue
240
+
241
+ if typeof obj[key] === 'object'
242
+ copied[key] = this.copy(obj[key])
243
+ continue
244
+
245
+ copied[key] = obj[key]
246
+
247
+ return copied
248
+
249
+ get (configPath)
250
+ const keys = configPath.split('.')
251
+ let conf = this.config
252
+
253
+ for const key of keys
254
+ conf = conf[key]
255
+ if !conf
256
+ return null
257
+
258
+ return conf
package/src/app.fire ADDED
@@ -0,0 +1,23 @@
1
+ import Superconf from './Superconf'
2
+
3
+ func superconf (name, opts)
4
+
5
+ const defaultExports = module.exports
6
+ module.exports = (name, opts) =>
7
+ log 'Superconf: Import namespace method is deprecated. Use named imports instead'
8
+ const config = new Superconf(opts)
9
+ return config.tryFiles(name)
10
+
11
+ Object.assign(module.exports, defaultExports)
12
+ export ** superconf
13
+
14
+ export
15
+ Superconf
16
+ superconf
17
+
18
+ export func config (opts)
19
+ # log 'Superconf: Import of config() method is deprecated. Use named imports instead'
20
+ return new Superconf(opts)
21
+
22
+ export const merge = Superconf.prototype.merge
23
+ export const copy = Superconf.prototype.copy
@@ -0,0 +1,6 @@
1
+ {
2
+ "extends": "../.eslintrc",
3
+ "env": {
4
+ mocha: true
5
+ }
6
+ }
@@ -0,0 +1,156 @@
1
+ import * as path from 'path'
2
+ import Superconf from '../'
3
+
4
+ export class SuperconfTest
5
+ schemaTest()
6
+ const superconf = new Superconf()
7
+ superconf.schema({
8
+ fruit:
9
+ type: 'str'
10
+ required: true
11
+
12
+ price:
13
+ type: 'num'
14
+ default: 1328
15
+ })
16
+
17
+ inspect(superconf.configSchema).isEql({
18
+ fruit:
19
+ type: 'str'
20
+ required: true
21
+
22
+ price:
23
+ type: 'num'
24
+ required: false
25
+ default: 1328
26
+ })
27
+
28
+ validateTest ()
29
+ const superconf = new Superconf({
30
+ verbose: true
31
+ })
32
+
33
+ superconf.schema({
34
+ fruit:
35
+ type: 'str'
36
+ required: true
37
+
38
+ price:
39
+ type: 'num'
40
+ default: 1328
41
+ })
42
+
43
+ superconf.config = {
44
+ fruit: 'banana'
45
+ price: 1.99
46
+ }
47
+
48
+ inspect(superconf.validate()).isTrue()
49
+
50
+ async loadJSONTest ()
51
+ const superconf = new Superconf({
52
+ verbose: true
53
+ workingDir: path.join(__dirname, '/fixtures/')
54
+ })
55
+
56
+ const json = await superconf.load('jsontest')
57
+ inspect(json).isEql({
58
+ fruit: 'Banana'
59
+ vegetable: 'Tomato'
60
+ })
61
+
62
+ async loadYMLTest ()
63
+ const superconf = new Superconf({
64
+ verbose: true
65
+ workingDir: path.join(__dirname, '/fixtures/')
66
+ })
67
+
68
+ const json = await superconf.load('ymltest')
69
+ inspect(json).isEql({
70
+ fruit: 'Banana'
71
+ vegetable: 'Tomato'
72
+ })
73
+
74
+ async loadYAMLTest ()
75
+ const superconf = new Superconf({
76
+ verbose: true
77
+ workingDir: path.join(__dirname, '/fixtures/')
78
+ })
79
+
80
+ const json = await superconf.load('yamltest')
81
+ inspect(json).isEql({
82
+ fruit: 'Banana'
83
+ vegetable: 'Tomato'
84
+ })
85
+
86
+ async loadJSONRCTest ()
87
+ const superconf = new Superconf({
88
+ workingDir: path.join(__dirname, '/fixtures/')
89
+ })
90
+
91
+ const json = await superconf.load('rcjsontest')
92
+ inspect(json).isEql({
93
+ fruit: 'Banana'
94
+ vegetable: 'Tomato'
95
+ })
96
+
97
+ async loadYMLRCTest ()
98
+ const superconf = new Superconf({
99
+ workingDir: path.join(__dirname, '/fixtures/')
100
+ })
101
+
102
+ const json = await superconf.load('rcymltest')
103
+ inspect(json).isEql({
104
+ fruit: 'Banana'
105
+ vegetable: 'Tomato'
106
+ })
107
+
108
+ async loadYAMLRCTest ()
109
+ const superconf = new Superconf({
110
+ workingDir: path.join(__dirname, '/fixtures/')
111
+ })
112
+
113
+ const json = await superconf.load('rcyamltest')
114
+ inspect(json).isEql({
115
+ fruit: 'Banana'
116
+ vegetable: 'Tomato'
117
+ })
118
+
119
+ async getSubsetTest ()
120
+ const superconf = new Superconf({
121
+ verbose: true
122
+ workingDir: path.join(__dirname, '/fixtures/')
123
+ })
124
+
125
+ await superconf.load('fruits')
126
+ inspect(superconf.get('fruits')).isEql({
127
+ banana:
128
+ name: 'Banana'
129
+ color: 'yellow'
130
+
131
+ coconut:
132
+ name: 'Coconut'
133
+ color: 'brown'
134
+ })
135
+
136
+ async getSuperSubsetTest ()
137
+ const superconf = new Superconf({
138
+ verbose: true
139
+ workingDir: path.join(__dirname, '/fixtures/')
140
+ })
141
+
142
+ await superconf.load('fruits')
143
+ inspect(superconf.get('fruits.banana')).isEql({
144
+ name: 'Banana'
145
+ color: 'yellow'
146
+ })
147
+
148
+ async getNonExistingSuperSubsetTest ()
149
+ const superconf = new Superconf({
150
+ verbose: true
151
+ workingDir: path.join(__dirname, '/fixtures/')
152
+ })
153
+
154
+ await superconf.load('fruits')
155
+ inspect(superconf.get('vegetables')).isNull()
156
+ inspect(superconf.get('fruits.cherry')).isNull()
@@ -0,0 +1,4 @@
1
+ {
2
+ "fruit": "Banana",
3
+ "vegetable": "Tomato"
4
+ }
@@ -0,0 +1,2 @@
1
+ fruit: "Banana"
2
+ vegetable: "Tomato"
@@ -0,0 +1,2 @@
1
+ fruit: "Banana"
2
+ vegetable: "Tomato"
@@ -0,0 +1,4 @@
1
+ {
2
+ "fruit": "Banana",
3
+ "vegetable": "Tomato"
4
+ }
@@ -0,0 +1,8 @@
1
+ fruits:
2
+ banana:
3
+ name: 'Banana'
4
+ color: yellow
5
+
6
+ coconut:
7
+ name: 'Coconut'
8
+ color: 'brown'
@@ -0,0 +1,4 @@
1
+ {
2
+ "fruit": "Banana",
3
+ "vegetable": "Tomato"
4
+ }
@@ -0,0 +1,7 @@
1
+ {
2
+ "name": "test",
3
+ "pkgtest": {
4
+ "fruit": "Banana",
5
+ "vegetable": "Tomato"
6
+ }
7
+ }
@@ -0,0 +1,2 @@
1
+ fruit: "Banana"
2
+ vegetable: "Tomato"
@@ -0,0 +1,2 @@
1
+ fruit: "Banana"
2
+ vegetable: "Tomato"
@@ -0,0 +1,277 @@
1
+ 'use strict'
2
+
3
+ const path = require('path')
4
+
5
+ const inspect = require('inspect.js')
6
+ const superconf = require('../app.js')
7
+
8
+ console.log('SC', superconf)
9
+
10
+ process.chdir(path.join(__dirname, '/fixtures/'))
11
+
12
+ describe('Superconf', () => {
13
+ describe('JSON', () => {
14
+ it('Should load a JSON conf', () => {
15
+ const conf = superconf('pkgtest')
16
+ inspect(conf).isObject()
17
+ inspect(conf).isEql({
18
+ foo: 'bar',
19
+ bla: 'blub'
20
+ })
21
+ })
22
+
23
+ it('Should load a JSON conf', () => {
24
+ const conf = superconf('pkgtest')
25
+ inspect(conf).isObject()
26
+ inspect(conf).isEql({
27
+ foo: 'bar',
28
+ bla: 'blub'
29
+ })
30
+ })
31
+
32
+ it('Should load a JSON from defaultConf', () => {
33
+ const conf = superconf('defaulttest', {
34
+ defaultConf: path.join(__dirname, './fixtures/defaultConf.json')
35
+ })
36
+
37
+ inspect(conf).isObject()
38
+ inspect(conf).isEql({
39
+ foo: 'bar',
40
+ bla: 'blub'
41
+ })
42
+ })
43
+
44
+ it('Should not load a JSON from defaultConf', () => {
45
+ const conf = superconf('defaulttest')
46
+
47
+ inspect(conf).isNull()
48
+ })
49
+ })
50
+
51
+ describe('merge()', function () {
52
+ it('Should merge object using Object.assign()', function () {
53
+ const left = {
54
+ fruit: 'Apple',
55
+ vegetable: 'Carrot'
56
+ }
57
+
58
+ const right = {
59
+ fruit: 'Banana',
60
+ vegetable: undefined
61
+ }
62
+
63
+ const conf = Object.assign(left, right)
64
+ inspect(conf).isEql({
65
+ fruit: 'Banana',
66
+ vegetable: undefined
67
+ })
68
+ })
69
+
70
+ it('Should merge config objects', function () {
71
+ const left = {
72
+ fruit: 'Apple',
73
+ vegetable: 'Carrot'
74
+ }
75
+
76
+ const right = {
77
+ fruit: 'Banana',
78
+ vegetable: undefined
79
+ }
80
+
81
+ const conf = superconf.merge(left, right)
82
+ inspect(conf).isEql({
83
+ fruit: 'Banana',
84
+ vegetable: 'Carrot'
85
+ })
86
+ })
87
+
88
+ it('Should overwrite objects', function () {
89
+ const left = {
90
+ fruit: 'Apple',
91
+ vegetables: {
92
+ red: 'Tomato',
93
+ green: 'Curcumber',
94
+ blue: 'Red cabbage'
95
+ }
96
+ }
97
+
98
+ const right = {
99
+ fruit: 'Banana',
100
+ vegetables: {
101
+ red: 'Capsicum'
102
+ }
103
+ }
104
+
105
+ const conf = superconf.merge(left, right)
106
+ inspect(conf).isEql({
107
+ fruit: 'Banana',
108
+ vegetables: {
109
+ red: 'Capsicum'
110
+ }
111
+ })
112
+ })
113
+
114
+ it('Should overwrite arrays', function () {
115
+ const left = {
116
+ fruit: 'Apple',
117
+ vegetables: [
118
+ 'Tomato',
119
+ 'Curcumber',
120
+ 'Red cabbage'
121
+ ]
122
+ }
123
+
124
+ const right = {
125
+ fruit: 'Banana',
126
+ vegetables: [
127
+ 'Capsicum'
128
+ ]
129
+ }
130
+
131
+ const conf = superconf.merge(left, right)
132
+ inspect(conf).isEql({
133
+ fruit: 'Banana',
134
+ vegetables: [
135
+ 'Capsicum'
136
+ ]
137
+ })
138
+ })
139
+
140
+ it('Should merge the first level together', function () {
141
+ const left = {
142
+ fruit: 'Apple',
143
+ vegetables: {
144
+ red: 'Tomato',
145
+ green: 'Curcumber',
146
+ blue: 'Red cabbage'
147
+ }
148
+ }
149
+
150
+ const right = {
151
+ fruit: 'Banana',
152
+ vegetables: {
153
+ red: 'Capsicum'
154
+ }
155
+ }
156
+
157
+ const conf = superconf.config({
158
+ dept: 1
159
+ }).merge(left, right)
160
+
161
+ inspect(conf).isEql({
162
+ fruit: 'Banana',
163
+ vegetables: {
164
+ red: 'Capsicum',
165
+ green: 'Curcumber',
166
+ blue: 'Red cabbage'
167
+ }
168
+ })
169
+ })
170
+
171
+ it('Should merge the first level together, using arrays', function () {
172
+ const left = {
173
+ fruit: 'Apple',
174
+ vegetables: {
175
+ red: [
176
+ 'Tomato',
177
+ 'Capsicum'
178
+ ]
179
+ }
180
+ }
181
+
182
+ const right = {
183
+ fruit: 'Banana',
184
+ vegetables: {
185
+ green: [
186
+ 'Curcumber'
187
+ ]
188
+ }
189
+ }
190
+
191
+ const conf = superconf.config({
192
+ dept: 1
193
+ }).merge(left, right)
194
+ inspect(conf).isEql({
195
+ fruit: 'Banana',
196
+ vegetables: {
197
+ red: ['Tomato', 'Capsicum'],
198
+ green: ['Curcumber']
199
+ }
200
+ })
201
+ })
202
+ })
203
+
204
+ describe('copy()', () => {
205
+ it('copies a config object', () => {
206
+ const obj = {
207
+ foo: 'foo',
208
+ bar: 'bar',
209
+ bla: {
210
+ blub: 123
211
+ }
212
+ }
213
+
214
+ const copied = superconf.copy(obj)
215
+ inspect(copied).isEql(obj)
216
+ inspect(copied).isNotEqual(obj)
217
+ inspect(copied.bla).isNotEqual(obj.bla)
218
+ })
219
+
220
+ it('copies a config object with an array', () => {
221
+ const three = {
222
+ number: {
223
+ digit: 3
224
+ }
225
+ }
226
+
227
+ const obj = {
228
+ foo: 'foo',
229
+ bar: 'bar',
230
+ bla: [
231
+ 'one',
232
+ 'zwo',
233
+ three
234
+ ]
235
+ }
236
+
237
+ const copied = superconf.copy(obj)
238
+ inspect(copied).isEql(obj)
239
+ inspect(copied).isNotEqual(obj)
240
+ inspect(copied.bla).isArray().hasLength(3)
241
+ inspect(copied.bla).isNotEqual(obj.bla)
242
+ inspect(copied.bla[2]).isEql(three).isNotEqual(three)
243
+ })
244
+
245
+ it('copies a config object with all existing shit', () => {
246
+ const three = {
247
+ number: {
248
+ digit: 3,
249
+ str: 'three',
250
+ used: null,
251
+ none: undefined
252
+ }
253
+ }
254
+
255
+ const obj = {
256
+ foo: 'foo',
257
+ bar: 'bar',
258
+ bla: [
259
+ 'one',
260
+ 'zwo',
261
+ three,
262
+ 123,
263
+ null,
264
+ undefined,
265
+ ['sub-one']
266
+ ]
267
+ }
268
+
269
+ const copied = superconf.copy(obj)
270
+ inspect(copied).isEql(obj)
271
+ inspect(copied).isNotEqual(obj)
272
+ inspect(copied.bla).isArray().hasLength(7)
273
+ inspect(copied.bla).isNotEqual(obj.bla)
274
+ inspect(copied.bla[2]).isEql(three).isNotEqual(three)
275
+ })
276
+ })
277
+ })
package/Superconf.js DELETED
@@ -1,257 +0,0 @@
1
- module.exports.__fsLocationMap = [[1, 21, 2, 7], [1, 33, 2, 24], [1, 8, 2, 36], [2, 13, 3, 7], [2, 26, 3, 25], [3, 13, 4, 7], [3, 23, 4, 22], [4, 8, 5, 7], [4, 20, 5, 24], [4, 8, 5, 45], [6, 1, 6, 1], [6, 7, 6, 7], [6, 13, 6, 13], [7, 1, 7, 1], [7, 7, 7, 7], [7, 14, 7, 14], [8, 1, 8, 1], [8, 7, 8, 7], [8, 16, 8, 16], [9, 1, 9, 1], [9, 7, 9, 7], [9, 15, 9, 15], [10, 1, 10, 1], [10, 7, 10, 7], [10, 15, 10, 15], [11, 1, 11, 1], [11, 7, 11, 7], [11, 15, 11, 15], [12, 1, 12, 1], [12, 7, 12, 7], [12, 17, 12, 17], [14, 8, 13, 1], [14, 14, 13, 7], [14, 24, 13, 17], [14, 32, 13, 25], [15, 5, 14, 3], [15, 18, 14, 16], [15, 18, 15, 5], [15, 18, 15, 12], [16, 9, 16, 5], [16, 15, 16, 11], [18, 9, 17, 5], [18, 14, 17, 10], [18, 27, 17, 23], [18, 32, 17, 28], [18, 46, 17, 42], [18, 54, 17, 50], [19, 9, 18, 5], [19, 14, 18, 10], [20, 9, 19, 5], [20, 14, 19, 10], [20, 24, 19, 20], [20, 29, 19, 25], [20, 40, 19, 36], [21, 9, 20, 5], [21, 14, 20, 10], [21, 26, 20, 22], [21, 31, 20, 27], [21, 39, 20, 35], [23, 9, 21, 5], [23, 14, 21, 10], [23, 22, 21, 18], [23, 27, 21, 23], [23, 36, 21, 32], [24, 13, 22, 7], [25, 13, 23, 7], [26, 13, 24, 7], [27, 13, 25, 7], [28, 13, 26, 7], [29, 13, 27, 7], [33, 5, 31, 3], [33, 12, 31, 10], [33, 20, 31, 18], [34, 9, 32, 5], [34, 12, 32, 9], [34, 17, 32, 14], [35, 17, 33, 19], [35, 25, 33, 27], [35, 32, 33, 34], [35, 47, 33, 49], [35, 55, 33, 57], [35, 60, 33, 62], [35, 69, 33, 71], [38, 5, 37, 3], [38, 13, 37, 11], [39, 9, 38, 5], [39, 14, 38, 10], [40, 9, 39, 5], [40, 16, 39, 12], [40, 24, 39, 20], [40, 38, 39, 34], [40, 46, 39, 42], [40, 47, 39, 43], [40, 48, 39, 45], [40, 53, 39, 50], [41, 13, 40, 7], [41, 19, 40, 13], [42, 17, 41, 9], [42, 23, 41, 15], [42, 29, 41, 21], [42, 37, 41, 29], [43, 17, 42, 9], [43, 27, 42, 19], [43, 33, 42, 25], [43, 45, 42, 37], [46, 13, 44, 7], [46, 16, 44, 11], [46, 23, 44, 18], [46, 29, 44, 24], [46, 41, 44, 36], [47, 17, 45, 9], [47, 24, 45, 16], [47, 34, 45, 26], [47, 40, 45, 32], [49, 13, 47, 7], [49, 16, 47, 11], [49, 23, 47, 18], [49, 29, 47, 24], [49, 44, 47, 39], [50, 17, 48, 9], [50, 24, 48, 16], [50, 37, 48, 29], [50, 43, 48, 35], [52, 13, 50, 7], [52, 18, 50, 12], [52, 31, 50, 25], [52, 38, 50, 32], [56, 5, 54, 3], [56, 20, 54, 18], [56, 28, 54, 26], [57, 9, 55, 5], [57, 16, 55, 12], [57, 23, 55, 19], [57, 31, 55, 27], [60, 5, 58, 3], [60, 15, 58, 13], [61, 9, 59, 5], [61, 12, 59, 9], [61, 13, 59, 10], [61, 18, 59, 15], [62, 13, 60, 7], [62, 20, 60, 14], [64, 9, 62, 5], [64, 14, 62, 10], [64, 33, 62, 29], [65, 9, 63, 5], [65, 15, 63, 11], [65, 33, 63, 29], [65, 41, 63, 37], [65, 46, 63, 42], [66, 9, 64, 5], [66, 15, 64, 11], [67, 13, 65, 7], [67, 19, 65, 13], [68, 13, 66, 7], [68, 25, 66, 19], [68, 30, 66, 24], [71, 9, 68, 5], [71, 14, 68, 10], [71, 31, 68, 27], [71, 50, 68, 46], [71, 60, 68, 56], [73, 9, 69, 5], [73, 16, 69, 12], [73, 21, 69, 17], [73, 38, 69, 34], [73, 49, 69, 45], [75, 5, 72, 3], [75, 23, 72, 21], [75, 31, 72, 29], [75, 37, 72, 35], [76, 9, 73, 5], [76, 14, 73, 10], [76, 20, 73, 16], [76, 41, 73, 37], [76, 60, 73, 56], [76, 70, 73, 66], [76, 88, 73, 84], [78, 9, 74, 5], [78, 12, 74, 9], [78, 13, 74, 10], [79, 13, 75, 7], [79, 20, 75, 14], [81, 9, 77, 5], [81, 12, 77, 9], [81, 13, 77, 10], [82, 13, 78, 7], [82, 16, 78, 11], [82, 23, 78, 18], [82, 36, 78, 31], [83, 17, 79, 9], [83, 22, 79, 14], [83, 39, 79, 31], [83, 44, 79, 36], [83, 52, 79, 44], [85, 13, 80, 9], [86, 17, 81, 9], [86, 24, 81, 16], [88, 9, 84, 5], [88, 12, 84, 9], [88, 19, 84, 16], [88, 28, 84, 25], [89, 13, 85, 7], [89, 16, 85, 11], [89, 23, 85, 18], [89, 36, 85, 31], [90, 17, 86, 9], [90, 22, 86, 14], [90, 39, 86, 31], [90, 44, 86, 36], [90, 52, 86, 44], [92, 9, 88, 7], [92, 14, 88, 16], [92, 21, 88, 23], [92, 30, 88, 32], [93, 13, 89, 7], [93, 16, 89, 11], [93, 23, 89, 18], [93, 36, 89, 31], [94, 17, 90, 9], [94, 22, 90, 14], [94, 39, 90, 31], [94, 44, 90, 36], [94, 52, 90, 44], [96, 9, 92, 7], [96, 14, 92, 16], [96, 21, 92, 23], [96, 30, 92, 32], [97, 13, 93, 7], [97, 16, 93, 11], [97, 23, 93, 18], [97, 36, 93, 31], [98, 17, 94, 9], [98, 22, 94, 14], [98, 39, 94, 31], [98, 44, 94, 36], [98, 52, 94, 44], [100, 9, 96, 7], [100, 14, 96, 16], [100, 21, 96, 23], [100, 30, 96, 32], [101, 13, 97, 7], [101, 16, 97, 11], [101, 17, 97, 12], [101, 23, 97, 18], [101, 31, 97, 26], [102, 17, 98, 9], [102, 22, 98, 14], [102, 39, 98, 31], [102, 44, 98, 36], [102, 52, 98, 44], [104, 9, 100, 7], [104, 14, 100, 16], [104, 21, 100, 23], [104, 30, 100, 32], [105, 13, 101, 7], [105, 16, 101, 11], [105, 23, 101, 18], [105, 36, 101, 31], [106, 17, 102, 9], [106, 22, 102, 14], [106, 39, 102, 31], [106, 44, 102, 36], [106, 52, 102, 44], [108, 13, 104, 7], [108, 20, 104, 14], [108, 28, 104, 22], [108, 38, 104, 32], [108, 46, 104, 40], [108, 47, 104, 41], [108, 48, 104, 43], [108, 53, 104, 48], [109, 17, 105, 9], [109, 23, 105, 15], [109, 35, 105, 27], [109, 40, 105, 32], [109, 54, 105, 46], [109, 61, 105, 53], [109, 73, 105, 65], [110, 17, 106, 9], [110, 22, 106, 14], [110, 39, 106, 31], [110, 50, 106, 42], [110, 53, 106, 45], [110, 61, 106, 53], [110, 68, 106, 60], [113, 13, 108, 7], [113, 20, 108, 14], [113, 28, 108, 22], [113, 35, 108, 29], [113, 47, 108, 41], [113, 55, 108, 49], [113, 56, 108, 50], [113, 57, 108, 52], [113, 62, 108, 57], [114, 17, 109, 9], [114, 20, 109, 13], [114, 21, 109, 14], [114, 30, 109, 23], [114, 38, 109, 31], [114, 48, 109, 41], [115, 21, 110, 11], [115, 26, 110, 16], [115, 32, 110, 22], [115, 66, 110, 56], [115, 77, 110, 67], [115, 87, 110, 77], [116, 21, 111, 11], [116, 30, 111, 20], [116, 37, 111, 27], [116, 47, 111, 37], [118, 17, 112, 11], [118, 22, 112, 20], [118, 23, 112, 21], [118, 32, 112, 30], [118, 40, 112, 38], [118, 50, 112, 48], [118, 59, 112, 57], [119, 21, 113, 11], [119, 30, 113, 20], [121, 17, 115, 9], [121, 22, 115, 14], [121, 39, 115, 31], [121, 50, 115, 42], [121, 53, 115, 45], [121, 61, 115, 53], [121, 68, 115, 60], [121, 77, 115, 69], [124, 5, 120, 3], [124, 11, 120, 9], [124, 21, 120, 19], [125, 9, 121, 5], [125, 15, 121, 11], [125, 20, 121, 16], [125, 26, 121, 22], [125, 33, 121, 29], [125, 38, 121, 34], [127, 9, 122, 5], [127, 12, 122, 9], [127, 13, 122, 10], [127, 16, 122, 13], [128, 13, 123, 7], [128, 18, 123, 12], [128, 24, 123, 18], [128, 36, 123, 30], [129, 13, 124, 7], [129, 20, 124, 14], [131, 9, 126, 5], [131, 14, 126, 10], [131, 20, 126, 16], [131, 38, 126, 34], [132, 9, 127, 5], [132, 12, 127, 9], [132, 15, 127, 12], [132, 23, 127, 20], [133, 13, 128, 7], [133, 20, 128, 14], [133, 23, 128, 17], [135, 9, 130, 5], [135, 12, 130, 9], [135, 15, 130, 12], [135, 23, 130, 20], [135, 33, 130, 30], [135, 36, 130, 33], [135, 44, 130, 41], [136, 13, 131, 7], [136, 19, 131, 13], [136, 26, 131, 20], [136, 34, 131, 28], [137, 13, 132, 7], [137, 19, 132, 13], [137, 28, 132, 22], [137, 34, 132, 28], [137, 37, 132, 31], [138, 13, 133, 7], [138, 20, 133, 14], [138, 25, 133, 19], [138, 30, 133, 24], [140, 9, 135, 5], [140, 16, 135, 12], [142, 5, 138, 3], [142, 18, 138, 16], [143, 9, 139, 5], [143, 16, 139, 12], [143, 24, 139, 20], [143, 29, 139, 25], [143, 43, 139, 39], [143, 51, 139, 47], [143, 52, 139, 48], [143, 53, 139, 50], [143, 58, 139, 55], [144, 13, 140, 7], [144, 16, 140, 11], [144, 23, 140, 18], [144, 30, 140, 25], [144, 39, 140, 34], [144, 54, 140, 49], [144, 61, 140, 56], [144, 67, 140, 62], [144, 79, 140, 74], [145, 17, 141, 9], [145, 24, 141, 16], [145, 31, 141, 23], [145, 37, 141, 29], [149, 5, 146, 3], [149, 11, 146, 9], [149, 17, 146, 15], [150, 9, 147, 5], [150, 14, 147, 10], [150, 20, 147, 16], [150, 35, 147, 31], [152, 9, 148, 5], [152, 13, 148, 10], [152, 19, 148, 16], [152, 27, 148, 24], [152, 32, 148, 29], [153, 13, 149, 7], [153, 19, 149, 13], [153, 30, 149, 24], [153, 35, 149, 29], [153, 43, 149, 37], [153, 48, 149, 42], [153, 60, 149, 54], [153, 65, 149, 59], [153, 73, 149, 67], [153, 79, 149, 73], [154, 13, 150, 7], [154, 19, 150, 13], [154, 28, 150, 22], [154, 34, 150, 28], [154, 39, 150, 33], [154, 48, 150, 42], [156, 13, 151, 7], [156, 16, 151, 11], [156, 27, 151, 22], [157, 17, 152, 9], [162, 13, 156, 7], [162, 16, 156, 11], [162, 17, 156, 12], [162, 22, 156, 17], [162, 31, 156, 26], [163, 17, 157, 9], [163, 23, 157, 15], [163, 42, 157, 34], [163, 47, 157, 39], [163, 64, 157, 56], [163, 69, 157, 61], [164, 17, 158, 9], [164, 23, 158, 15], [164, 27, 158, 19], [164, 33, 158, 25], [164, 62, 158, 57], [166, 13, 160, 7], [166, 18, 160, 12], [166, 27, 160, 21], [167, 13, 161, 7], [167, 20, 161, 14], [169, 9, 163, 5], [169, 16, 163, 12], [171, 5, 166, 3], [171, 15, 166, 13], [172, 9, 167, 5], [172, 15, 167, 11], [174, 9, 168, 5], [174, 15, 168, 11], [174, 23, 168, 19], [174, 24, 168, 20], [174, 30, 168, 26], [174, 37, 168, 33], [175, 13, 169, 7], [175, 16, 169, 11], [175, 25, 169, 20], [175, 38, 169, 33], [175, 47, 169, 42], [176, 17, 170, 9], [178, 13, 172, 7], [178, 16, 172, 11], [178, 23, 172, 18], [178, 33, 172, 28], [179, 17, 173, 9], [179, 24, 173, 16], [182, 13, 175, 7], [182, 17, 175, 12], [182, 23, 175, 18], [182, 30, 175, 25], [183, 17, 176, 9], [183, 20, 176, 13], [183, 26, 176, 19], [183, 41, 176, 34], [184, 21, 177, 11], [184, 24, 177, 15], [184, 30, 177, 21], [184, 39, 177, 30], [185, 25, 178, 13], [187, 21, 180, 11], [187, 24, 180, 15], [187, 30, 180, 21], [187, 39, 180, 30], [188, 25, 181, 13], [188, 30, 181, 18], [188, 37, 181, 25], [189, 25, 182, 13], [191, 21, 184, 11], [191, 24, 184, 15], [191, 30, 184, 21], [191, 38, 184, 29], [191, 44, 184, 35], [192, 25, 185, 13], [192, 30, 185, 18], [192, 37, 185, 25], [192, 43, 185, 31], [192, 48, 185, 36], [192, 52, 185, 40], [192, 53, 185, 41], [193, 29, 186, 15], [193, 32, 186, 19], [193, 39, 186, 26], [193, 48, 186, 35], [194, 33, 187, 17], [194, 40, 187, 24], [194, 45, 187, 29], [194, 51, 187, 35], [194, 56, 187, 40], [194, 66, 187, 50], [196, 29, 189, 15], [196, 36, 189, 22], [199, 25, 191, 13], [201, 21, 193, 11], [201, 24, 193, 15], [201, 31, 193, 22], [201, 37, 193, 28], [201, 46, 193, 37], [202, 25, 194, 13], [202, 28, 194, 17], [203, 29, 195, 15], [203, 34, 195, 20], [203, 41, 195, 27], [203, 47, 195, 33], [203, 52, 195, 38], [203, 58, 195, 44], [203, 64, 195, 50], [203, 70, 195, 56], [203, 75, 195, 61], [204, 29, 196, 15], [206, 25, 198, 13], [206, 30, 198, 18], [206, 37, 198, 25], [206, 44, 198, 32], [206, 55, 198, 43], [206, 61, 198, 49], [207, 25, 199, 13], [209, 21, 201, 11], [209, 26, 201, 16], [209, 33, 201, 23], [209, 39, 201, 29], [211, 13, 204, 7], [211, 20, 204, 14], [213, 9, 206, 5], [213, 13, 206, 10], [213, 17, 206, 14], [213, 21, 206, 18], [213, 24, 206, 21], [213, 28, 206, 25], [213, 33, 206, 30], [213, 41, 206, 38], [214, 13, 207, 7], [214, 19, 207, 13], [214, 25, 207, 19], [214, 30, 207, 24], [214, 34, 207, 28], [214, 39, 207, 33], [216, 9, 209, 5], [216, 16, 209, 12], [218, 5, 212, 3], [218, 11, 212, 9], [219, 9, 213, 5], [219, 12, 213, 9], [219, 19, 213, 16], [219, 27, 213, 24], [219, 39, 213, 36], [219, 47, 213, 44], [220, 13, 214, 7], [220, 20, 214, 14], [222, 9, 216, 5], [222, 12, 216, 9], [222, 18, 216, 15], [222, 26, 216, 23], [223, 13, 217, 7], [223, 20, 217, 14], [223, 24, 217, 18], [223, 28, 217, 22], [223, 29, 217, 23], [224, 17, 218, 9], [224, 22, 218, 14], [224, 27, 218, 19], [227, 9, 221, 5], [227, 15, 221, 11], [228, 9, 222, 5], [228, 13, 222, 10], [228, 19, 222, 16], [228, 26, 222, 23], [229, 13, 223, 7], [229, 16, 223, 11], [229, 20, 223, 15], [229, 35, 223, 30], [230, 17, 224, 9], [230, 20, 224, 13], [230, 24, 224, 17], [230, 33, 224, 26], [231, 21, 225, 11], [231, 28, 225, 18], [231, 35, 225, 25], [232, 21, 226, 11], [234, 17, 228, 9], [234, 20, 228, 13], [234, 26, 228, 19], [234, 34, 228, 27], [234, 38, 228, 31], [235, 21, 229, 11], [235, 28, 229, 18], [235, 35, 229, 25], [235, 39, 229, 29], [235, 44, 229, 34], [235, 48, 229, 38], [235, 49, 229, 39], [236, 25, 230, 13], [236, 30, 230, 18], [236, 35, 230, 23], [239, 21, 232, 11], [241, 17, 234, 9], [241, 20, 234, 13], [241, 27, 234, 20], [241, 31, 234, 24], [241, 40, 234, 33], [242, 21, 235, 11], [242, 28, 235, 18], [242, 35, 235, 25], [242, 40, 235, 30], [242, 45, 235, 35], [242, 49, 235, 39], [243, 21, 236, 11], [245, 17, 238, 9], [245, 24, 238, 16], [245, 31, 238, 23], [245, 35, 238, 27], [247, 9, 241, 5], [247, 16, 241, 12], [249, 5, 244, 3], [249, 10, 244, 8], [250, 9, 245, 5], [250, 15, 245, 11], [250, 22, 245, 18], [250, 33, 245, 29], [250, 39, 245, 35], [251, 9, 246, 5], [251, 13, 246, 9], [251, 20, 246, 16], [251, 25, 246, 21], [253, 9, 247, 5], [253, 13, 247, 10], [253, 19, 247, 16], [253, 26, 247, 23], [254, 13, 248, 7], [254, 20, 248, 14], [254, 25, 248, 19], [255, 13, 249, 7], [255, 16, 249, 11], [255, 17, 249, 12], [256, 17, 250, 9], [256, 24, 250, 16], [258, 9, 253, 5], [258, 16, 253, 12], [14, 14, 256, 16], [14, 14, 256, 28]];
2
- module.exports.__esModule = true;
3
- const Legacy = require('./Legacy').Superconf;
4
- const colorfy = require('colorfy');
5
- const path = require('path');
6
- const FireFS = require('firescript-firefs').FireFS;
7
- const red = '\u001b[38;5;160m';
8
- const ored = '\u001b[38;5;202m';
9
- const yellow = '\u001b[38;5;226m';
10
- const dgrey = '\u001b[38;5;244m';
11
- const lgrey = '\u001b[38;5;250m';
12
- const azure = '\u001b[38;5;39m';
13
- const uncolor = '\u001b[m';
14
- class Superconf extends Legacy {
15
- constructor (opts) {
16
- opts = opts || {};
17
- super(opts);
18
- this.workingDir = opts.workingDir || process.cwd();
19
- this.config = {};
20
- this.verbose = opts.verbose || false;
21
- this.mergeDept = opts.dept || 0;
22
- this.files = opts.files || [
23
- '%s.json',
24
- '%s.yaml',
25
- '%s.yml',
26
- '.%src.json',
27
- '.%src.yaml',
28
- '.%src.yml'
29
- ];
30
- }
31
-
32
- debug (msg, ...data) {
33
- if (this.verbose) {
34
- console.log(colorfy.yellow('Superconf:'), colorfy.grey(msg), ...data);
35
- }
36
- }
37
-
38
- schema (configSchema) {
39
- this.configSchema = {};
40
- Object.entries(configSchema).forEach(([ key, value ]) => {
41
- const schema = {
42
- type: value.type || 'str',
43
- required: value.required || false
44
- };
45
- if (typeof value.default !== 'undefined') {
46
- schema.default = value.default;
47
- }
48
- if (typeof value.properties !== 'undefined') {
49
- schema.properties = value.properties;
50
- }
51
- this.configSchema[key] = schema;
52
- });
53
- }
54
-
55
- getSchemaItem (schema, key) {
56
- return schema[key] || null;
57
- }
58
-
59
- validate (conf) {
60
- if (!this.configSchema) {
61
- return true;
62
- }
63
- this.validationErrors = [ ];
64
- const validateionData = conf || this.config;
65
- const validateionSchema = {
66
- type: 'obj',
67
- properties: this.configSchema
68
- };
69
- this.validateProperty(validateionSchema, 'config', validateionData);
70
- return this.validationErrors.length === 0;
71
- }
72
-
73
- validateProperty (schema, name, property) {
74
- this.debug(`Validate property ${name} with value`, property, 'against schema', schema);
75
- if (!schema) {
76
- return true;
77
- }
78
- if (!property) {
79
- if (schema.required === true) {
80
- this.validationErrors.push(`Item ${name} is required but not set`);
81
- } else {
82
- return true;
83
- }
84
- }
85
- if (schema.type === 'str') {
86
- if (typeof property !== 'string') {
87
- this.validationErrors.push(`Item ${name} is not of type string`);
88
- }
89
- } else if (schema.type === 'num') {
90
- if (typeof property !== 'number') {
91
- this.validationErrors.push(`Item ${name} is not of type number`);
92
- }
93
- } else if (schema.type === 'bool') {
94
- if (typeof property !== 'boolean') {
95
- this.validationErrors.push(`Item ${name} is not of type boolean`);
96
- }
97
- } else if (schema.type === 'arr') {
98
- if (!Array.isArray(property)) {
99
- this.validationErrors.push(`Item ${name} is not of type array`);
100
- }
101
- } else if (schema.type === 'obj') {
102
- if (typeof property !== 'object') {
103
- this.validationErrors.push(`Item ${name} is not of type object`);
104
- }
105
- Object.entries(property).forEach(([ key, value ]) => {
106
- const subSchema = this.getSchemaItem(schema.properties, key);
107
- this.validateProperty(subSchema, `${name}.${key}`, value);
108
- });
109
- Object.entries(schema.properties).forEach(([ key, subSchema ]) => {
110
- if (!property[key] && subSchema.default) {
111
- this.debug(`Set default value for property ${name} to`, subSchema.default);
112
- property[key] = subSchema.default;
113
- } else if (!property[key] && subSchema.type === 'obj') {
114
- property[key] = {};
115
- }
116
- this.validateProperty(subSchema, `${name}.${key}`, property[key]);
117
- });
118
- }
119
- }
120
-
121
- async fromFile (filepath) {
122
- const fl = await FireFS.file(filepath);
123
- if (!fl.exists) {
124
- this.debug('Try file', filepath);
125
- return null;
126
- }
127
- this.debug('Load from file', filepath);
128
- if (fl.ext === 'json') {
129
- return fl.readJSON();
130
- }
131
- if (fl.ext === 'yaml' || fl.ext === 'yml') {
132
- const yaml = require('js-yaml');
133
- const source = await fl.read();
134
- return yaml.load(source);
135
- }
136
- return null;
137
- }
138
-
139
- setDefaults (config) {
140
- Object.entries(this.configSchema).forEach(([ key, value ]) => {
141
- if (typeof config[key] === 'undefined' && typeof value.default !== 'undefined') {
142
- config[key] = value.default;
143
- }
144
- });
145
- }
146
-
147
- async load (name) {
148
- this.debug('Load config', name);
149
- for (const file of this.files) {
150
- const filepath = path.resolve(this.workingDir, file.replace('%s', name));
151
- const config = await this.fromFile(filepath);
152
- if (config === null) {
153
- continue;
154
- }
155
- // if config
156
- // this.setDefaults(config)
157
- if (!this.validate(config)) {
158
- const validationErrors = this.validationErrors.join(' \n');
159
- throw new Error(`Invalid config loaded!////n ${validationErrors}`);
160
- }
161
- this.config = config;
162
- return config;
163
- }
164
- return null;
165
- }
166
-
167
- merge (...args) {
168
- const conf = {};
169
- const merge = (left, right, curdept) => {
170
- if (left === undefined || left === null) {
171
- left = {};
172
- }
173
- if (typeof right !== 'object') {
174
- return left;
175
- }
176
- for (const key in right) {
177
- if (right.hasOwnProperty(key)) {
178
- if (right[key] === undefined) {
179
- continue;
180
- }
181
- if (right[key] === null) {
182
- left[key] = null;
183
- continue;
184
- }
185
- if (Array.isArray(right[key])) {
186
- left[key] = right[key].map((item) => {
187
- if (typeof item === 'object') {
188
- return JSON.parse(JSON.stringify(item));
189
- }
190
- return item;
191
- });
192
- continue;
193
- }
194
- if (typeof right[key] === 'object') {
195
- if (curdept) {
196
- left[key] = merge(left[key], right[key], left[key]--);
197
- continue;
198
- }
199
- left[key] = Object.assign({}, right[key]);
200
- continue;
201
- }
202
- left[key] = right[key];
203
- }
204
- }
205
- return left;
206
- };
207
- for (let i = 0; i < args.length; i++) {
208
- merge(conf, args[i], this.mergeDept);
209
- }
210
- return conf;
211
- }
212
-
213
- copy (obj) {
214
- if (typeof obj !== 'object' || obj === null) {
215
- return obj;
216
- }
217
- if (Array.isArray(obj)) {
218
- return obj.map((item) => {
219
- this.copy(item);
220
- });
221
- }
222
- const copied = {};
223
- for (const key in obj) {
224
- if (obj.hasOwnProperty(key)) {
225
- if (obj[key] === null) {
226
- copied[key] = null;
227
- continue;
228
- }
229
- if (Array.isArray(obj[key])) {
230
- copied[key] = obj[key].map((item) => {
231
- this.copy(item);
232
- });
233
- continue;
234
- }
235
- if (typeof obj[key] === 'object') {
236
- copied[key] = this.copy(obj[key]);
237
- continue;
238
- }
239
- copied[key] = obj[key];
240
- }
241
- }
242
- return copied;
243
- }
244
-
245
- get (configPath) {
246
- const keys = configPath.split('.');
247
- let conf = this.config;
248
- for (const key of keys) {
249
- conf = conf[key];
250
- if (!conf) {
251
- return null;
252
- }
253
- }
254
- return conf;
255
- }
256
- }
257
- module.exports.Superconf = Superconf;