fakeit
Version:
Command-line utility that generates fake data which can be output as JSON, YAML, CSON, or CSV formats based on models defined in YAML.
622 lines (508 loc) • 20.9 kB
JavaScript
'use strict';
Object.defineProperty(exports, "__esModule", {
value: true
});
exports.parsers = exports.pool = exports.readFiles = exports.findFiles = undefined;
var _stringify = require('babel-runtime/core-js/json/stringify');
var _stringify2 = _interopRequireDefault(_stringify);
var _promise = require('babel-runtime/core-js/promise');
var _promise2 = _interopRequireDefault(_promise);
var _regenerator = require('babel-runtime/regenerator');
var _regenerator2 = _interopRequireDefault(_regenerator);
var _getIterator2 = require('babel-runtime/core-js/get-iterator');
var _getIterator3 = _interopRequireDefault(_getIterator2);
var _asyncToGenerator2 = require('babel-runtime/helpers/asyncToGenerator');
var _asyncToGenerator3 = _interopRequireDefault(_asyncToGenerator2);
var _typeof2 = require('babel-runtime/helpers/typeof');
var _typeof3 = _interopRequireDefault(_typeof2);
/// @name findFiles
/// @description
/// This is a very efficient way to to recursively read a directory and get all the files.
/// @arg {string, array} globs - The glob(s) or dir(s) you want to get all the files from
/// @returns {array} All the files in the paths(s) that were passed
/// @async
var findFiles = exports.findFiles = function () {
var _ref = (0, _asyncToGenerator3.default)( /*#__PURE__*/_regenerator2.default.mark(function _callee2(globs) {
var _this = this;
var files, sort, find;
return _regenerator2.default.wrap(function _callee2$(_context2) {
while (1) {
switch (_context2.prev = _context2.next) {
case 0:
// all the files after
files = [];
sort = function sort(list) {
var to_search = [];
list = _toJs2.default.flatten(list);
var _iteratorNormalCompletion = true;
var _didIteratorError = false;
var _iteratorError = undefined;
try {
for (var _iterator = (0, _getIterator3.default)(list), _step; !(_iteratorNormalCompletion = (_step = _iterator.next()).done); _iteratorNormalCompletion = true) {
var item = _step.value;
if (!!_path2.default.extname(item)) {
files.push(item);
} else {
to_search.push(item);
}
}
} catch (err) {
_didIteratorError = true;
_iteratorError = err;
} finally {
try {
if (!_iteratorNormalCompletion && _iterator.return) {
_iterator.return();
}
} finally {
if (_didIteratorError) {
throw _iteratorError;
}
}
}
return to_search;
};
find = function () {
var _ref2 = (0, _asyncToGenerator3.default)( /*#__PURE__*/_regenerator2.default.mark(function _callee(items) {
return _regenerator2.default.wrap(function _callee$(_context) {
while (1) {
switch (_context.prev = _context.next) {
case 0:
_context.t0 = sort;
_context.next = 3;
return (0, _asyncArrayMethods.map)(items, function (item) {
if (_globby2.default.hasMagic(item)) {
return (0, _globby2.default)(item);
} else if (!!_path2.default.extname(item)) {
return item;
}
return (0, _globby2.default)(_path2.default.join(item, '*'));
});
case 3:
_context.t1 = _context.sent;
items = (0, _context.t0)(_context.t1);
if (!items.length) {
_context.next = 7;
break;
}
return _context.abrupt('return', find(items));
case 7:
case 'end':
return _context.stop();
}
}
}, _callee, _this);
}));
return function find(_x3) {
return _ref2.apply(this, arguments);
};
}();
_context2.next = 5;
return find(_toJs2.default.array(globs));
case 5:
return _context2.abrupt('return', files);
case 6:
case 'end':
return _context2.stop();
}
}
}, _callee2, this);
}));
return function findFiles(_x2) {
return _ref.apply(this, arguments);
};
}();
/// @name readFiles
/// @description
/// This will read all the files that have been passed to it and return them in an array of objects.
/// @arg {string, array} files - The files to read. This can be any file including `zip`.
/// @returns {array} An `array` of files where each object will have the following information
///
/// ```js
/// {
/// path: '', // the full path of the file
/// content: '', // the contents of the file as a string
/// // the rest of the keys are the same as what you would get from running `path.parse`
/// root: '',
/// dir: '',
/// base: '',
/// ext: '',
/// name: '',
/// }
/// ```
/// @async
var readFiles = exports.readFiles = function () {
var _ref3 = (0, _asyncToGenerator3.default)( /*#__PURE__*/_regenerator2.default.mark(function _callee5(files) {
var _this2 = this;
return _regenerator2.default.wrap(function _callee5$(_context5) {
while (1) {
switch (_context5.prev = _context5.next) {
case 0:
if (files) {
_context5.next = 2;
break;
}
return _context5.abrupt('return');
case 2:
files = _toJs2.default.array(files);
_context5.next = 5;
return (0, _asyncArrayMethods.map)(files, function () {
var _ref4 = (0, _asyncToGenerator3.default)( /*#__PURE__*/_regenerator2.default.mark(function _callee4(file) {
var info, zip;
return _regenerator2.default.wrap(function _callee4$(_context4) {
while (1) {
switch (_context4.prev = _context4.next) {
case 0:
file = _path2.default.resolve(file); // resolve the full path
info = _path2.default.parse(file); // parse the full path to get the name and extension
if (!(info.ext === '.zip')) {
_context4.next = 5;
break;
}
zip = new _admZip2.default(file);
return _context4.abrupt('return', (0, _asyncArrayMethods.map)(zip.getEntries(), function () {
var _ref5 = (0, _asyncToGenerator3.default)( /*#__PURE__*/_regenerator2.default.mark(function _callee3(entry) {
var file_info;
return _regenerator2.default.wrap(function _callee3$(_context3) {
while (1) {
switch (_context3.prev = _context3.next) {
case 0:
if (!(!entry.isDirectory && !entry.entryName.match(/^(\.|__MACOSX)/))) {
_context3.next = 7;
break;
}
file_info = _path2.default.parse(entry.entryName); // eslint-disable-line
file_info.path = entry.entryName;
_context3.next = 5;
return zip.readAsText(entry.entryName);
case 5:
file_info.content = _context3.sent;
return _context3.abrupt('return', file_info);
case 7:
case 'end':
return _context3.stop();
}
}
}, _callee3, _this2);
}));
return function (_x6) {
return _ref5.apply(this, arguments);
};
}()));
case 5:
info.path = file;
_context4.t0 = _toJs2.default;
_context4.next = 9;
return _fsExtraPromisify2.default.readFile(file);
case 9:
_context4.t1 = _context4.sent;
info.content = _context4.t0.string.call(_context4.t0, _context4.t1);
return _context4.abrupt('return', info);
case 12:
case 'end':
return _context4.stop();
}
}
}, _callee4, _this2);
}));
return function (_x5) {
return _ref4.apply(this, arguments);
};
}());
case 5:
files = _context5.sent;
return _context5.abrupt('return', _toJs2.default.flatten(files).filter(Boolean));
case 7:
case 'end':
return _context5.stop();
}
}
}, _callee5, this);
}));
return function readFiles(_x4) {
return _ref3.apply(this, arguments);
};
}();
/// @name pool
/// @description
/// This is very similar to the `Array.prototype.map` except that
/// it's used to limit the number of functions running at a time.
/// @arg {array} items - The array to loop over
/// @arg {function} fn - The function to run on each of the items. It has the same arguments the map function does
/// @arg {number} limit [100] - The number of promises that can run at any given item.
/// @returns {array} of the items that were returned by the fn.
/// @async
var pool = exports.pool = function () {
var _ref6 = (0, _asyncToGenerator3.default)( /*#__PURE__*/_regenerator2.default.mark(function _callee6(items, fn) {
var limit = arguments.length > 2 && arguments[2] !== undefined ? arguments[2] : 100;
var i, results, length, producer, runner;
return _regenerator2.default.wrap(function _callee6$(_context6) {
while (1) {
switch (_context6.prev = _context6.next) {
case 0:
i = 0;
results = [];
length = void 0;
if (typeof items === 'number') {
length = items;
items = [];
} else {
length = items.length;
}
producer = function producer() {
if (i < length) {
var index = i;
return fn(items[index] || i, i++, items).then(function (result) {
results[index] = result;
});
}
return null;
};
runner = new _es6PromisePool2.default(producer, limit);
_context6.next = 8;
return runner.start();
case 8:
return _context6.abrupt('return', results);
case 9:
case 'end':
return _context6.stop();
}
}
}, _callee6, this);
}));
return function pool(_x7, _x8) {
return _ref6.apply(this, arguments);
};
}();
/// @name parsers
/// @description
/// This holds all the parsers that this project uses and normalizes
/// them to all function the same way.
/// Each parser in this object has 2 functions `parse`, and `stringify`.
/// @type {object}
exports.objectSearch = objectSearch;
var _path = require('path');
var _path2 = _interopRequireDefault(_path);
var _globby = require('globby');
var _globby2 = _interopRequireDefault(_globby);
var _asyncArrayMethods = require('async-array-methods');
var _toJs = require('to-js');
var _toJs2 = _interopRequireDefault(_toJs);
var _admZip = require('adm-zip');
var _admZip2 = _interopRequireDefault(_admZip);
var _es6Promisify = require('es6-promisify');
var _es6Promisify2 = _interopRequireDefault(_es6Promisify);
var _fsExtraPromisify = require('fs-extra-promisify');
var _fsExtraPromisify2 = _interopRequireDefault(_fsExtraPromisify);
var _es6PromisePool = require('es6-promise-pool');
var _es6PromisePool2 = _interopRequireDefault(_es6PromisePool);
var _yamljs = require('yamljs');
var _yamljs2 = _interopRequireDefault(_yamljs);
var _cson = require('cson');
var _cson2 = _interopRequireDefault(_cson);
var _csvParse = require('csv-parse');
var _csvParse2 = _interopRequireDefault(_csvParse);
var _csvStringify = require('csv-stringify');
var _csvStringify2 = _interopRequireDefault(_csvStringify);
function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
/// @name objectSearch
/// @description Recursively looks through objects and finds the pattern provided
/// @arg {object, array} data - The data to search through
/// @arg {regex,string} pattern - The pattern used to match a path
/// @arg {string} current_path - The current part of the path. This is used as apart of the recursion and you shouldn't pass anyting to it manually.
/// @arg {array} paths - The paths that have been match. This is used as apart of the recursion and you shouldn't pass anyting to it manually.
/// @returns {array} - With the paths that have been matched
////
/// @name Utils
/// @page api/utils
/// @description These are all the utility functions used throughout the application
////
function objectSearch(data, pattern, current_path) {
var paths = arguments.length > 3 && arguments[3] !== undefined ? arguments[3] : [];
function appendPath(opath, index) {
opath = opath ? opath + '.' + index : '' + index;
opath = opath.replace(/^\.|\.$|\.{2,}/, '');
return opath;
}
if (Array.isArray(data)) {
for (var i = 0; i < data.length; i++) {
var test_path = appendPath(current_path, i);
if (test_path.match(pattern) && !(paths.indexOf(test_path) !== -1)) {
paths.push(test_path);
}
objectSearch(data[i], pattern, test_path, paths);
}
} else if ((typeof data === 'undefined' ? 'undefined' : (0, _typeof3.default)(data)) === 'object' && data !== null) {
for (var key in data) {
if (data.hasOwnProperty(key)) {
var _test_path = appendPath(current_path, key);
if (_test_path.match(pattern) && !(paths.indexOf(_test_path) !== -1)) {
paths.push(_test_path);
}
objectSearch(data[key], pattern, _test_path, paths);
}
}
}
return paths;
}var parsers = {};
var csv = {
parse: (0, _es6Promisify2.default)(_csvParse2.default),
stringify: (0, _es6Promisify2.default)(_csvStringify2.default)
};
///# @name parsers.yaml
///# @alias parsers.yml
///# @type {object}
parsers.yaml = parsers.yml = {
///# @name parsers.yaml.parse
///# @alias parsers.yml.parse
///# @arg {string, object} obj
///# @returns {object} - The javascript object
///# @async
parse: function parse(obj) {
return _promise2.default.resolve(_yamljs2.default.parse(obj));
},
///# @name parsers.yaml.stringify
///# @alias parsers.yml.stringify
///# @arg {object} obj
///# @arg {number} indent [2] The indent level
///# @returns {string} - The yaml string
///# @async
stringify: function stringify(obj) {
var indent = arguments.length > 1 && arguments[1] !== undefined ? arguments[1] : 2;
return _promise2.default.resolve(_yamljs2.default.stringify(obj, null, indent).trim());
}
};
///# @name parsers.json
///# @type {object}
parsers.json = {
///# @name parsers.json.parse
///# @arg {string, object} obj
///# @returns {object} - The javascript object
///# @async
parse: function parse(obj) {
return _promise2.default.resolve(JSON.parse(obj));
},
///# @name parsers.json.stringify
///# @arg {object} obj
///# @arg {number} indent [2] The indent level
///# @returns {string} - The yaml string
///# @async
stringify: function stringify(obj) {
var indent = arguments.length > 1 && arguments[1] !== undefined ? arguments[1] : 2;
return _promise2.default.resolve((0, _stringify2.default)(obj, null, !parseInt(indent) ? null : indent));
}
};
///# @name parsers.cson
///# @type {object}
parsers.cson = {
///# @name parsers.cson.parse
///# @arg {string, object} obj
///# @returns {object} - The javascript object
///# @async
parse: function parse(obj) {
return new _promise2.default(function (resolve, reject) {
_cson2.default.parse(obj, {}, function (err, result) {
/* istanbul ignore next */
if (err) {
return reject(err);
}
resolve(result);
});
});
},
///# @name parsers.cson.stringify
///# @arg {object} obj
///# @arg {number} indent [2] The indent level
///# @returns {string} - The yaml string
///# @async
stringify: function stringify(obj) {
var indent = arguments.length > 1 && arguments[1] !== undefined ? arguments[1] : 2;
return _promise2.default.resolve(_cson2.default.stringify(obj, null, indent));
}
};
///# @name parsers.csv
///# @type {object}
parsers.csv = {
///# @name parsers.csv.parse
///# @arg {string, object}
///# @returns {array} - The javascript object
///# @async
parse: function parse(obj) {
var _this3 = this;
return (0, _asyncToGenerator3.default)( /*#__PURE__*/_regenerator2.default.mark(function _callee7() {
var result, fix;
return _regenerator2.default.wrap(function _callee7$(_context7) {
while (1) {
switch (_context7.prev = _context7.next) {
case 0:
fix = function fix(a, b) {
/* istanbul ignore if : too hard to create a test case for it */
if (!a || !b) {
return a;
}
for (var k in b) {
// eslint-disable-line
if (b.hasOwnProperty(k)) {
/* istanbul ignore if : too hard to create a test case for it */
if (_toJs.is.plainObject(b[k])) {
a[k] = _toJs.is.plainObject(a[k]) ? fix(a[k], b[k]) : b[k];
} else if (_toJs.is.string(b[k]) && /^[0-9]+$/.test(b[k])) {
// convert string into a number
a[k] = _toJs2.default.number(b[k]);
} else if (_toJs.is.string(b[k]) && b[k][0] === '{') {
// convert string into an object
a[k] = fix({}, _toJs2.default.object(b[k]));
} else {
a[k] = b[k];
}
}
}
return a;
};
_context7.next = 3;
return csv.parse(obj, { columns: true });
case 3:
result = _context7.sent;
return _context7.abrupt('return', result.map(function (item) {
return fix({}, item);
}));
case 5:
case 'end':
return _context7.stop();
}
}
}, _callee7, _this3);
}))();
},
///# @name parsers.csv.stringify
///# @arg {object} obj
///# @arg {object} options [{ header: true, quotedString: true }] The csv options
///# @returns {string} - The yaml string
///# @async
stringify: function stringify(obj, options) {
var _this4 = this;
return (0, _asyncToGenerator3.default)( /*#__PURE__*/_regenerator2.default.mark(function _callee8() {
var result;
return _regenerator2.default.wrap(function _callee8$(_context8) {
while (1) {
switch (_context8.prev = _context8.next) {
case 0:
if ((typeof options === 'undefined' ? 'undefined' : (0, _typeof3.default)(options)) !== 'object') {
options = {};
}
options = _toJs2.default.extend({ header: true, quotedString: true }, options);
_context8.next = 4;
return csv.stringify(_toJs2.default.array(obj), options);
case 4:
result = _context8.sent;
return _context8.abrupt('return', result.trim());
case 6:
case 'end':
return _context8.stop();
}
}
}, _callee8, _this4);
}))();
}
};
exports.parsers = parsers;