数据验证

数据验证的位置

  • 前端(客户端)为了用户体验
  • 路由层:验证接口格式是否正常
  • 业务逻辑层:保证业务完整性
  • 数据库验证:保证数据完整性

相关库

  • validator:用于验证某个字符串是否满足某个规则
  • validator.js:用于验证某个对象的树形是否满足某些规则

常用验证函数

  1. 验证电子邮件地址

    js 复制代码
    const email = 'test@example.com';
    console.log(validator.isEmail(email)); // true
  2. 验证URL

    js 复制代码
    const url = 'https://example.com';
    console.log(validator.isURL(url)); // true
  3. 验证IP地址

    js 复制代码
    const ip = '192.168.1.1';
    console.log(validator.isIP(ip)); // true
  4. 验证手机号码

    js 复制代码
    const phone = '13800138000';
    console.log(validator.isMobilePhone(phone, 'zh-CN')); // true
  5. 验证字符串是否为数字

    js 复制代码
    const num = '123';
    console.log(validator.isNumeric(num)); // true
  6. 验证字符串是否为日期

    js 复制代码
    const date = '2023-10-01';
    console.log(validator.isDate(date)); // true
  7. 验证字符串是否为JSON

    js 复制代码
    const json = '{"name": "John"}';
    console.log(validator.isJSON(json)); // true

常用净化函数

  1. 去除字符串两端的空白字符

    js 复制代码
    const str = '  hello  ';
    console.log(validator.trim(str)); // 'hello'
  2. 转义HTML

    js 复制代码
    const html = '<script>alert("xss")</script>';
    console.log(validator.escape(html)); // '&lt;script&gt;alert(&quot;xss&quot;)&lt;/script&gt;'
  3. 去除非法字符

    js 复制代码
    const str = 'Hello <world>!';
    console.log(validator.stripLow(str)); // 'Hello !'

自定义验证

validator.js 还允许你自定义验证规则。例如,你可以使用 matches 函数来验证字符串是否符合特定的正则表达式:

js 复制代码
const str = 'abc123';
console.log(validator.matches(str, /^[a-z0-9]+$/)); // true

链式调用

validator.js 支持链式调用,可以一次性进行多个验证:

js 复制代码
const email = 'test@example.com';
const result = validator.isEmail(email) && validator.isLength(email, { min: 5, max: 30 });
console.log(result); // true

完整示例

必须验证的属性加上:presence:true

不允许以下格式存在(验证不通过):allowEmpty:false

  • {}
  • ""
  • " "
js 复制代码
exports.addStudent =async function (stuObj){
  //挑选属性
  stuObj=pink(stuObj,"name","birthday","sec","mobile","ClassId");
   //自定义规则
   validata.validators.classExits = async function(value){
    const c =await Class.findByPk(value)
    if(c){
      return;
    }
    return "班级不存在";
   }
  const rule ={
    //验证规则
    name:{
      presence:{
        allowEmpty:false
      },
      type:"string",
      length:{
        minimum:2,
        maximum:10
      }
    },
    birthday:{
      presence:{
        allowEmpty:false
      },
      datetime:{
        dateOnly:true,
        earliest:moment.utc().subtract(100,"y"),
        latest:+momnet.utc().subtract(5,"y")
      },
    },
    sec:{
      presence:{
        allowEmpty:false
      },
    },
    mobile:{
      presence:{
        allowEmpty:false
      },
      format:{
        pattern:/^1\d{10}/
      }
    },
    ClassId:{
      presence:true,
      // //严格
      // type:"integer",
      //不严格
      numericality:{
        onlyInteger:true,
        strict:false,
      },
      classExits:true
   }
  };
  await validate.async(stuObj,rule);
   const ins = await Student.create(stuObj);
   return ins.toJSON();
} 
js 复制代码
const validate = require("validate.js");
const moment = require("moment");
validate.extend(validate.validators.datetime, {
    /**
    * 该函数会自动用于日期格式转换
    * 它会在验证时自动触发,它需要将任何数据转换为时间戳返回
    * 如果无法转换,返回NaN
    * @param {*} value 传入要转换的值
    * @param {*} options 针对某个属性的验证配置
    */
    parse(value, options) {
      let formats = ["YYYY-MM-DD HH:mm:ss", "YYYY-M-D H:m:s", "x"];
      if (options.dateOnly) {
         formats = ["YYYY-MM-DD", "YYYY-M-D", "x"];
      }
      return +moment.utc(value, formats, true);
    },
    /**
    * 用户显示错误消息时,使用的显示字符串
    */
    format(value, options) {
       let format = "YYYY-MM-DD";
       if (!options.dateOnly) {
          format += " HH:mm:ss";
        }
       return moment.utc(value).format(format);
  },
}

对象属性处理

js 复制代码
exports.pick = function (obj, ...props) {
    if (!obj || typeof obj !== "object") {
        return obj;
    }
    const newObj = {};
    for (const key in obj) {
        if (props.includes(key)) {
            newObj[key] = obj[key];
        }
    }
    return newObj;
};
相关推荐
前端小端长7 分钟前
qiankun 微前端应用入门教程:从搭建到部署
前端
yinuo2 小时前
前端跨页面通讯终极指南⑥:SharedWorker 用法全解析
前端
廋到被风吹走6 小时前
【数据库】【MySQL】InnoDB外键解析:约束机制、性能影响与最佳实践
android·数据库·mysql
掘根6 小时前
【消息队列】交换机数据管理实现
网络·数据库
Logic1017 小时前
《Mysql数据库应用》 第2版 郭文明 实验6 数据库系统维护核心操作与思路解析
数据库·sql·mysql·学习笔记·计算机网络技术·形考作业·国家开放大学
PineappleCoder7 小时前
还在重复下载资源?HTTP 缓存让二次访问 “零请求”,用户体验翻倍
前端·性能优化
拉不动的猪7 小时前
webpack编译中为什么不建议load替换ast中节点删除consolg.log
前端·javascript·webpack
李姆斯7 小时前
Agent时代下,ToB前端的UI和交互会往哪走?
前端·agent·交互设计
AI Echoes7 小时前
构建一个LangChain RAG应用
数据库·python·langchain·prompt·agent
源码获取_wx:Fegn08957 小时前
基于springboot + vue健身房管理系统
java·开发语言·前端·vue.js·spring boot·后端·spring