123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292 |
- import _objectSpread from "@babel/runtime/helpers/esm/objectSpread2";
- import _toConsumableArray from "@babel/runtime/helpers/esm/toConsumableArray";
- import _typeof from "@babel/runtime/helpers/esm/typeof";
- import _classCallCheck from "@babel/runtime/helpers/esm/classCallCheck";
- import _createClass from "@babel/runtime/helpers/esm/createClass";
- import _defineProperty from "@babel/runtime/helpers/esm/defineProperty";
- import { messages as defaultMessages, newMessages } from "./messages";
- import { asyncMap, complementError, convertFieldsError, deepMerge, format, warning } from "./util";
- import validators from "./validator/index";
- export * from "./interface";
- /**
- * Encapsulates a validation schema.
- *
- * @param descriptor An object declaring validation rules
- * for this schema.
- */
- var Schema = /*#__PURE__*/function () {
- function Schema(descriptor) {
- _classCallCheck(this, Schema);
- // ======================== Instance ========================
- _defineProperty(this, "rules", null);
- _defineProperty(this, "_messages", defaultMessages);
- this.define(descriptor);
- }
- _createClass(Schema, [{
- key: "define",
- value: function define(rules) {
- var _this = this;
- if (!rules) {
- throw new Error('Cannot configure a schema with no rules');
- }
- if (_typeof(rules) !== 'object' || Array.isArray(rules)) {
- throw new Error('Rules must be an object');
- }
- this.rules = {};
- Object.keys(rules).forEach(function (name) {
- var item = rules[name];
- _this.rules[name] = Array.isArray(item) ? item : [item];
- });
- }
- }, {
- key: "messages",
- value: function messages(_messages) {
- if (_messages) {
- this._messages = deepMerge(newMessages(), _messages);
- }
- return this._messages;
- }
- }, {
- key: "validate",
- value: function validate(source_) {
- var _this2 = this;
- var o = arguments.length > 1 && arguments[1] !== undefined ? arguments[1] : {};
- var oc = arguments.length > 2 && arguments[2] !== undefined ? arguments[2] : function () {};
- var source = source_;
- var options = o;
- var callback = oc;
- if (typeof options === 'function') {
- callback = options;
- options = {};
- }
- if (!this.rules || Object.keys(this.rules).length === 0) {
- if (callback) {
- callback(null, source);
- }
- return Promise.resolve(source);
- }
- function complete(results) {
- var errors = [];
- var fields = {};
- function add(e) {
- if (Array.isArray(e)) {
- var _errors;
- errors = (_errors = errors).concat.apply(_errors, _toConsumableArray(e));
- } else {
- errors.push(e);
- }
- }
- for (var i = 0; i < results.length; i++) {
- add(results[i]);
- }
- if (!errors.length) {
- callback(null, source);
- } else {
- fields = convertFieldsError(errors);
- callback(errors, fields);
- }
- }
- if (options.messages) {
- var messages = this.messages();
- if (messages === defaultMessages) {
- messages = newMessages();
- }
- deepMerge(messages, options.messages);
- options.messages = messages;
- } else {
- options.messages = this.messages();
- }
- var series = {};
- var keys = options.keys || Object.keys(this.rules);
- keys.forEach(function (z) {
- var arr = _this2.rules[z];
- var value = source[z];
- arr.forEach(function (r) {
- var rule = r;
- if (typeof rule.transform === 'function') {
- if (source === source_) {
- source = _objectSpread({}, source);
- }
- value = source[z] = rule.transform(value);
- if (value !== undefined && value !== null) {
- rule.type = rule.type || (Array.isArray(value) ? 'array' : _typeof(value));
- }
- }
- if (typeof rule === 'function') {
- rule = {
- validator: rule
- };
- } else {
- rule = _objectSpread({}, rule);
- }
- // Fill validator. Skip if nothing need to validate
- rule.validator = _this2.getValidationMethod(rule);
- if (!rule.validator) {
- return;
- }
- rule.field = z;
- rule.fullField = rule.fullField || z;
- rule.type = _this2.getType(rule);
- series[z] = series[z] || [];
- series[z].push({
- rule: rule,
- value: value,
- source: source,
- field: z
- });
- });
- });
- var errorFields = {};
- return asyncMap(series, options, function (data, doIt) {
- var rule = data.rule;
- var deep = (rule.type === 'object' || rule.type === 'array') && (_typeof(rule.fields) === 'object' || _typeof(rule.defaultField) === 'object');
- deep = deep && (rule.required || !rule.required && data.value);
- rule.field = data.field;
- function addFullField(key, schema) {
- return _objectSpread(_objectSpread({}, schema), {}, {
- fullField: "".concat(rule.fullField, ".").concat(key),
- fullFields: rule.fullFields ? [].concat(_toConsumableArray(rule.fullFields), [key]) : [key]
- });
- }
- function cb() {
- var e = arguments.length > 0 && arguments[0] !== undefined ? arguments[0] : [];
- var errorList = Array.isArray(e) ? e : [e];
- if (!options.suppressWarning && errorList.length) {
- Schema.warning('async-validator:', errorList);
- }
- if (errorList.length && rule.message !== undefined) {
- errorList = [].concat(rule.message);
- }
- // Fill error info
- var filledErrors = errorList.map(complementError(rule, source));
- if (options.first && filledErrors.length) {
- errorFields[rule.field] = 1;
- return doIt(filledErrors);
- }
- if (!deep) {
- doIt(filledErrors);
- } else {
- // if rule is required but the target object
- // does not exist fail at the rule level and don't
- // go deeper
- if (rule.required && !data.value) {
- if (rule.message !== undefined) {
- filledErrors = [].concat(rule.message).map(complementError(rule, source));
- } else if (options.error) {
- filledErrors = [options.error(rule, format(options.messages.required, rule.field))];
- }
- return doIt(filledErrors);
- }
- var fieldsSchema = {};
- if (rule.defaultField) {
- Object.keys(data.value).map(function (key) {
- fieldsSchema[key] = rule.defaultField;
- });
- }
- fieldsSchema = _objectSpread(_objectSpread({}, fieldsSchema), data.rule.fields);
- var paredFieldsSchema = {};
- Object.keys(fieldsSchema).forEach(function (field) {
- var fieldSchema = fieldsSchema[field];
- var fieldSchemaList = Array.isArray(fieldSchema) ? fieldSchema : [fieldSchema];
- paredFieldsSchema[field] = fieldSchemaList.map(addFullField.bind(null, field));
- });
- var schema = new Schema(paredFieldsSchema);
- schema.messages(options.messages);
- if (data.rule.options) {
- data.rule.options.messages = options.messages;
- data.rule.options.error = options.error;
- }
- schema.validate(data.value, data.rule.options || options, function (errs) {
- var finalErrors = [];
- if (filledErrors && filledErrors.length) {
- finalErrors.push.apply(finalErrors, _toConsumableArray(filledErrors));
- }
- if (errs && errs.length) {
- finalErrors.push.apply(finalErrors, _toConsumableArray(errs));
- }
- doIt(finalErrors.length ? finalErrors : null);
- });
- }
- }
- var res;
- if (rule.asyncValidator) {
- res = rule.asyncValidator(rule, data.value, cb, data.source, options);
- } else if (rule.validator) {
- try {
- res = rule.validator(rule, data.value, cb, data.source, options);
- } catch (error) {
- var _console$error, _console;
- (_console$error = (_console = console).error) === null || _console$error === void 0 || _console$error.call(_console, error);
- // rethrow to report error
- if (!options.suppressValidatorError) {
- setTimeout(function () {
- throw error;
- }, 0);
- }
- cb(error.message);
- }
- if (res === true) {
- cb();
- } else if (res === false) {
- cb(typeof rule.message === 'function' ? rule.message(rule.fullField || rule.field) : rule.message || "".concat(rule.fullField || rule.field, " fails"));
- } else if (res instanceof Array) {
- cb(res);
- } else if (res instanceof Error) {
- cb(res.message);
- }
- }
- if (res && res.then) {
- res.then(function () {
- return cb();
- }, function (e) {
- return cb(e);
- });
- }
- }, function (results) {
- complete(results);
- }, source);
- }
- }, {
- key: "getType",
- value: function getType(rule) {
- if (rule.type === undefined && rule.pattern instanceof RegExp) {
- rule.type = 'pattern';
- }
- if (typeof rule.validator !== 'function' && rule.type && !validators.hasOwnProperty(rule.type)) {
- throw new Error(format('Unknown rule type %s', rule.type));
- }
- return rule.type || 'string';
- }
- }, {
- key: "getValidationMethod",
- value: function getValidationMethod(rule) {
- if (typeof rule.validator === 'function') {
- return rule.validator;
- }
- var keys = Object.keys(rule);
- var messageIndex = keys.indexOf('message');
- if (messageIndex !== -1) {
- keys.splice(messageIndex, 1);
- }
- if (keys.length === 1 && keys[0] === 'required') {
- return validators.required;
- }
- return validators[this.getType(rule)] || undefined;
- }
- }]);
- return Schema;
- }();
- // ========================= Static =========================
- _defineProperty(Schema, "register", function register(type, validator) {
- if (typeof validator !== 'function') {
- throw new Error('Cannot register a validator by type, validator is not a function');
- }
- validators[type] = validator;
- });
- _defineProperty(Schema, "warning", warning);
- _defineProperty(Schema, "messages", defaultMessages);
- _defineProperty(Schema, "validators", validators);
- export default Schema;
|