UNPKG

@valuer/main

Version:

Valuer is an advanced declarative value validator

167 lines (166 loc) 7.08 kB
"use strict"; var __spreadArrays = (this && this.__spreadArrays) || function () { for (var s = 0, i = 0, il = arguments.length; i < il; i++) s += arguments[i].length; for (var r = Array(s), k = 0, i = 0; i < il; i++) for (var a = arguments[i], j = 0, jl = a.length; j < jl; j++, k++) r[k] = a[j]; return r; }; Object.defineProperty(exports, "__esModule", { value: true }); var brackets_1 = require("@valuer/brackets"); var is_1 = require("@valuer/is"); var help_1 = require("@valuer/help"); var deepmerge = require("deepmerge"); var constants_1 = require("../constants"); var helpers_1 = require("../helpers"); var errors_1 = require("./errors"); var validators_1 = require("./validators"); var configs_1 = require("./configs"); // *** /** @private */ var DESCRIPTOR_NAME_PREFIX = ":"; // *** /** @private */ var DESCRIPTOR_NAME_TO_DESCRIPTOR_MAP = Object.create(null); // *** /** @private */ var validateName = function (name) { var invalid = function (failure) { var args = []; for (var _i = 1; _i < arguments.length; _i++) { args[_i - 1] = arguments[_i]; } return errors_1.Errors.panic.apply(errors_1.Errors, __spreadArrays(["Unexpected error", "descriptor name " + failure], args)); }; if (!is_1.is._string(name)) return invalid("is not a string", help_1.help.getPrintable(name)); // remove heading colon if present var trimmed = name.trim(); var _name = trimmed.substr(+trimmed.startsWith(DESCRIPTOR_NAME_PREFIX)); if (!_name.length) return invalid("is empty"); else return DESCRIPTOR_NAME_PREFIX + _name; }; /** @private */ var getNamesOf = function (descriptive) { var isSame = is_1.is.equalTo(exports.Descriptors.create(descriptive)); return Object.keys(exports.Descriptors.defined).filter(function (name) { return isSame(exports.Descriptors.defined[name]); }); }; /** @private */ var warnSimilar = function (descriptor) { var existing = getNamesOf(descriptor); if (existing.length <= 1) return; var names = existing.map(brackets_1.brackets.surroundBy(brackets_1.brackets.collection.doubleQuotes.tight)); console.warn("Descriptor has been defined as " + help_1.help.getPrintableList(names)); }; /** @private */ var getDefined = function (name) { if (name in exports.Descriptors.defined) return exports.Descriptors.defined[name]; else return errors_1.Errors.panic("Unexpected error", "descriptor \"" + name + "\" is not defined"); }; /** @private */ var addToSet = function (descriptor, values) { var _a; if (!(descriptor.set instanceof Array)) descriptor.set = []; (_a = descriptor.set).push.apply(_a, values); }; /** @private */ var createFromValidations = function (validations) { var descriptor = {}; var thunks = []; for (var _i = 0, _a = help_1.help.getEntries(validations); _i < _a.length; _i++) { var _b = _a[_i], index = _b[0], validation = _b[1]; if (is_1.is._string(validation)) if (validators_1.Validators.isValidationString(validation)) for (var _c = 0, _d = validators_1.Validators.getFor(validation, index); _c < _d.length; _c++) { var validator = _d[_c]; descriptor[validator] = validation; } else if (validation.startsWith(DESCRIPTOR_NAME_PREFIX)) Object.assign(descriptor, deepmerge(descriptor, getDefined(validation))); else return errors_1.Errors.unknown.validation(validation, index); else if (validation instanceof RegExp) descriptor.pattern = validation; else if (helpers_1.isThunk(validation)) thunks.push(validation); else if (validation instanceof Array) addToSet(descriptor, validation); else return errors_1.Errors.unknown.validation(validation, index); } if (thunks.length) if (thunks.length > 1) for (var _e = 0, _f = help_1.help.getEntries(thunks); _e < _f.length; _e++) { var _g = _f[_e], index = _g[0], thunk = _g[1]; descriptor[constants_1.DEFAULT_FAILURE + ' ' + brackets_1.brackets.surround(index, brackets_1.brackets.collection.square.tight)] = thunk; } else descriptor[constants_1.DEFAULT_FAILURE] = thunks[0]; return descriptor; }; /** @private */ var disclose = function (descriptor) { if ("composite" in descriptor) for (var key in descriptor.composite) { if (!exports.Descriptors.isDescriptorFlow([descriptor.composite[key]])) descriptor.composite[key] = createFromValidations(descriptor.composite[key]); descriptor.composite[key] = disclose(descriptor.composite[key]); } return descriptor; }; // *** /** @internal */ exports.Descriptors = { get defined() { return DESCRIPTOR_NAME_TO_DESCRIPTOR_MAP; }, // *** isDescriptorFlow: function (args) { return is_1.is.inRange([1, 2])(args.length) && args.every(is_1.is.directInstanceOf(Object)); }, validate: function (descriptor) { if (!is_1.is._objectNonNull(descriptor)) return errors_1.Errors.panic("Invalid descriptor", help_1.help.getPrintable(descriptor)); else if (!is_1.is._any(descriptor)) null; for (var _i = 0, _a = help_1.help.getEntries(descriptor); _i < _a.length; _i++) { var _b = _a[_i], validator = _b[0], validation = _b[1]; if (validators_1.Validators.isValidator(validator)) validators_1.Validators.validate(validator, validation); else validators_1.Validators.validateThunk(validation); } return descriptor; }, create: function (descriptive) { if (is_1.is.array()(descriptive)) return createFromValidations(descriptive); else if (exports.Descriptors.isDescriptorFlow([descriptive])) return disclose(exports.Descriptors.validate(descriptive)); else return errors_1.Errors.panic("Invalid descriptor", help_1.help.getPrintable(descriptive)); }, /** * @example * const number = "integer"; * const spectrum = "positive"; * * valuer.define(":natural", { number, spectrum }); * valuer.define(":natural", [ number, spectrum ]); */ define: function (name, descriptive) { var _name = validateName(name); if (_name in exports.Descriptors.defined) return errors_1.Errors.panic("Unexpected error", "cannot redefine descriptor \"" + _name + "\""); else exports.Descriptors.defined[_name] = exports.Descriptors.create(descriptive); if (configs_1.Configs.current.warnOnMultipleNames) warnSimilar(exports.Descriptors.defined[_name]); }, };