lin-cms-test
Version:
The core library of Lin CMS, this package is just for test!
268 lines (267 loc) • 10.5 kB
JavaScript
"use strict";
Object.defineProperty(exports, "__esModule", { value: true });
const tslib_1 = require("tslib");
const is_async_function_1 = tslib_1.__importDefault(require("is-async-function"));
const lodash_1 = require("lodash");
const exception_1 = require("./exception");
const extendedValidator_1 = require("./extendedValidator");
const util_1 = require("./util");
/**
* 支持optional,支持array,支持nested object
*/
class ClassValidator {
constructor() {
/**
* 装载数据的容器
*/
this.data = {};
/**
* 解析后的数据容器
*/
this.parsed = {};
/**
* 数据校验错误容器
*/
this.errors = [];
}
async validate(ctx, alias) {
this.alias = alias;
const params = Object.assign({}, ctx.request.body, ctx.request.query, ctx.params, ctx.request.header);
for (const it of Object.keys(params)) {
lodash_1.set(this.data, it, lodash_1.get(params, it));
}
if (!(await this.checkRules())) {
let obj = {};
if (this.errors.length === 1) {
obj = this.errors[0].message;
}
else {
for (const err of this.errors) {
obj[err.key] = err.message;
}
}
throw new exception_1.ParametersException({ msg: obj });
}
else {
// 把validator挂载到ctx上
ctx.v = this;
return this;
}
}
replace(keys) {
// key 是原来的名字
if (!this.alias) {
return keys;
}
let arr = [];
for (let key of keys) {
if (this.alias[key]) {
this[this.alias[key]] = this[key];
lodash_1.unset(this, key);
arr.push(this.alias[key]);
}
else {
arr.push(key);
}
}
return arr;
}
async checkRules() {
// 筛选出是Rule或Rules的key
// 添加规则校验 validateKey
// default校验规则 throw
let keys = Object.keys(this).filter(key => {
const value = this[key];
if (lodash_1.isArray(value)) {
return value[0] instanceof Rule;
}
else {
return value instanceof Rule;
}
});
// 此处进行别名替换
keys = this.replace(keys);
for (const key of keys) {
// 标志位
let stoppedFlag = false;
let optional = false;
const value = this[key];
let defaultVal;
// 如果没有传入这个参数,检查这个校验链中是否有 isOptional 如果有通过,否则抛异常
if (extendedValidator_1.extendedValidator.isEmpty(this.data[key])) {
let msg;
if (lodash_1.isArray(value)) {
for (const it of value) {
if (it.optional) {
defaultVal = it.defaultValue && it.defaultValue;
optional = true;
}
else {
if (!msg) {
msg = it.message;
}
}
}
}
else {
if (value.optional) {
defaultVal = value.defaultValue && value.defaultValue;
optional = true;
}
else {
msg = value.message;
}
}
// 没有 isOptional 抛异常
// 有 isOptional 取它的默认值
if (!optional) {
this.errors.push({ key, message: msg || `${key}不可为空` });
}
else {
this.data[key] = defaultVal;
}
}
else {
if (lodash_1.isArray(value)) {
const errs = [];
for (const it of value) {
// 当rule的optional为false时,进行校验
if (!stoppedFlag && !it.optional) {
let valid;
if (is_async_function_1.default(it.validate)) {
valid = await it.validate(this.data[key]);
}
else {
valid = it.validate(this.data[key]);
}
if (!valid) {
errs.push(it.message);
// 如果当前key已有错误,则置stoppedFlag为true,后续会直接跳过校验
stoppedFlag = true;
}
}
it.parsedValue && (this.parsed[key] = it.parsedValue);
}
if (errs.length !== 0) {
this.errors.push({ key, message: errs });
}
}
else {
const errs = [];
if (!stoppedFlag && !value.optional) {
let valid;
if (is_async_function_1.default(value.validate)) {
valid = await value.validate(this.data[key]);
}
else {
valid = value.validate(this.data[key]);
}
if (!valid) {
errs.push(value.message);
// 如果当前key已有错误,则置stoppedFlag为true,后续会直接跳过校验
stoppedFlag = true;
}
}
value.parsedValue && (this.parsed[key] = value.parsedValue);
if (errs.length !== 0) {
this.errors.push({ key, message: errs });
}
}
}
}
let validateFuncKeys = util_1.getAllMethodNames(this).filter(key => {
return /validate([A-Z])\w+/g.test(key) && typeof this[key] === "function";
});
for (const validateFuncKey of validateFuncKeys) {
// 最后校验规则函数
const customerValidateFunc = lodash_1.get(this, validateFuncKey);
// 自定义校验函数,第一个参数是校验是否成功,第二个参数为错误信息
let validRes;
if (is_async_function_1.default(customerValidateFunc)) {
validRes = await customerValidateFunc.call(this);
}
else {
validRes = customerValidateFunc.call(this);
}
if (lodash_1.isArray(validRes) && !validRes[0]) {
let key;
if (validRes[2]) {
key = validRes[2];
}
else {
key = validateFuncKey.replace("validate", "").toLowerCase();
}
this.errors.push({ key, message: validRes[1] });
}
}
return this.errors.length === 0;
}
get(path, parsed = false) {
let defaultVal;
if (arguments.length >= 3) {
defaultVal = arguments[2];
}
if (parsed) {
return lodash_1.get(this.parsed, path, defaultVal && defaultVal);
}
else {
return lodash_1.get(this.data, path, defaultVal && defaultVal);
}
}
}
exports.ClassValidator = ClassValidator;
class Rule {
constructor(validateFunction, message, ...options) {
this.optional = false;
this.validateFunction = validateFunction;
this.message = message || "参数错误";
this.options = options;
if (this.validateFunction === "isOptional") {
// 如果当前项为optional,检查该项是否存在,若不存在,将optional置为true
// 如果是optional,那么没有传入的参数,可以使用默认值
this.optional = true;
this.defaultValue = options && options[0];
}
}
validate(value) {
this.rawValue = value;
if (typeof this.validateFunction === "function") {
return this.validateFunction(value, ...this.options);
}
else {
if (this.validateFunction === "isDate") {
typeof value === "string"
? (this.parsedValue = extendedValidator_1.extendedValidator.toDate(value))
: (this.parsedValue = value);
}
else if (this.validateFunction === "isInt") {
if (typeof value === "string") {
this.parsedValue = extendedValidator_1.extendedValidator.toInt(value);
return extendedValidator_1.extendedValidator.isInt2(value, ...this.options);
}
else {
this.parsedValue = value;
return extendedValidator_1.extendedValidator.isInt3(value, ...this.options);
}
}
else if (this.validateFunction === "isFloat") {
if (typeof value === "string") {
this.parsedValue = extendedValidator_1.extendedValidator.toFloat(value);
return extendedValidator_1.extendedValidator.isFloat(value, ...this.options);
}
else {
this.parsedValue = value;
return extendedValidator_1.extendedValidator.isFloat2(value, ...this.options);
}
}
else if (this.validateFunction === "isBoolean") {
typeof value === "string"
? (this.parsedValue = extendedValidator_1.extendedValidator.toBoolean(value))
: (this.parsedValue = value);
return extendedValidator_1.extendedValidator.isBoolean(value);
}
return extendedValidator_1.extendedValidator[this.validateFunction](value, ...this.options);
}
}
}
exports.Rule = Rule;