You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
148 lines
3.5 KiB
148 lines
3.5 KiB
import AsyncValidator from 'async-validator' |
|
const utils = { |
|
validate: (model, rules, callback, options) => { |
|
const initOptions = { |
|
showMessage: true |
|
} |
|
options = Object.assign({}, initOptions, options || {}) |
|
let promise = null; |
|
if (typeof callback !== 'function') { |
|
promise = new Promise((resolve, reject) => { |
|
callback = function(valid) { |
|
valid ? resolve(valid) : reject(valid) |
|
} |
|
}) |
|
} |
|
// 如果需要验证的fields为空,调用验证时立刻返回callback |
|
if (!rules || (Array.isArray(rules) && rules.length === 0) || (typeof rules === 'object' && Object.keys(rules).length === |
|
0)) { |
|
callback(true, null); |
|
if(promise){ |
|
return promise |
|
} |
|
return |
|
} |
|
let errors = [] |
|
const props = Object.keys(rules) |
|
let count = 0 |
|
for (let i in props) { |
|
const prop = props[i] |
|
const value = utils.getValueByProp(model, prop) |
|
utils.validateItem(rules, prop, value, (err) => { |
|
if (err && err.length > 0) { |
|
errors = errors.concat(err) |
|
} |
|
// 处理异步校验,等所有校验都结束时再callback |
|
count++ |
|
if (count === props.length) { |
|
if (errors.length > 0) { |
|
if (options.showMessage) { |
|
utils.showToast(errors[0].message) |
|
} |
|
callback(false, errors) |
|
} else { |
|
callback(true, null) |
|
} |
|
} |
|
}) |
|
} |
|
if (promise) { |
|
return promise |
|
} |
|
}, |
|
validateField: (model, rules, props, callback, options) => { |
|
const initOptions = { |
|
showMessage: true |
|
} |
|
options = Object.assign({}, initOptions, options || {}) |
|
let promise = null; |
|
if (typeof callback !== 'function') { |
|
promise = new Promise((resolve, reject) => { |
|
callback = function(valid) { |
|
valid ? resolve(valid) : reject(valid) |
|
} |
|
}) |
|
} |
|
props = [].concat(props) |
|
if (props.length === 0) { |
|
return |
|
} |
|
let errors = [] |
|
let count = 0 |
|
for (let i in props) { |
|
const prop = props[i] |
|
const value = utils.getValueByProp(model, prop) |
|
utils.validateItem(rules, prop, value, (err) => { |
|
if (err && err.length > 0) { |
|
errors = errors.concat(err) |
|
} |
|
// 处理异步校验,等所有校验都结束时再callback |
|
count++ |
|
if (count === props.length) { |
|
if (errors.length > 0) { |
|
if (options.showMessage) { |
|
utils.showToast(errors[0].message) |
|
} |
|
callback(false, errors) |
|
} else { |
|
callback(true, null) |
|
} |
|
} |
|
}) |
|
} |
|
if (promise) { |
|
return promise |
|
} |
|
}, |
|
validateItem(rules, prop, value, callback) { |
|
if (!rules || JSON.stringify(rules) === '{}') { |
|
if (callback instanceof Function) { |
|
callback(); |
|
} |
|
return true; |
|
} |
|
const propRules = [].concat(rules[prop] || []); |
|
propRules.forEach((rule) => { |
|
if (rule.pattern) { |
|
rule.pattern = new RegExp(rule.pattern) |
|
} |
|
}) |
|
const descriptor = { |
|
[prop]: propRules |
|
}; |
|
const validator = new AsyncValidator(descriptor); |
|
const model = { |
|
[prop]: value |
|
}; |
|
validator.validate(model, { |
|
firstFields: true |
|
}, (errors) => { |
|
callback(errors); |
|
}); |
|
}, |
|
getValueByProp: (obj, prop) => { |
|
let tempObj = obj; |
|
prop = prop.replace(/\[(\w+)\]/g, '.$1').replace(/^\./, ''); |
|
let keyArr = prop.split('.'); |
|
let i = 0; |
|
for (let len = keyArr.length; i < len - 1; ++i) { |
|
if (!tempObj) break; |
|
let key = keyArr[i]; |
|
if (key in tempObj) { |
|
tempObj = tempObj[key]; |
|
} else { |
|
break; |
|
} |
|
} |
|
return tempObj ? (typeof tempObj[keyArr[i]] === 'string' ? tempObj[keyArr[i]].trim() : tempObj[keyArr[i]]) : |
|
null |
|
}, |
|
showToast: (message) => { |
|
uni.showToast({ |
|
title: message, |
|
icon: 'none' |
|
}) |
|
} |
|
} |
|
|
|
export default utils
|
|
|