【问题标题】:How to extract the key of a duplicate entry error(1062) from mysql/knexjs如何从 mysql/knexjs 中提取重复输入错误(1062)的键
【发布时间】:2018-04-23 00:27:37
【问题描述】:

我正在通过从 html 表单发送值来测试我的数据库。独特的插件很好,连接很好。我的问题是,当我故意发送重复(用户名)时 - 再次出于测试目的,我收到一条错误消息。这是完美的!

但是我想提取恰好是关键的原因。错误是根据 typeof(error) 的对象。具体如下:

错误:插入Userspasswordroleusername)值('1112131234434'、'basic'、'Cthulu')- 重复条目'Cthulu' 键'用户名'

  1. 我尝试在使用 JSON.stringify 将对象转换为 json 后提取密钥。但唯一节省的价值是: {"code":"ER_DUP_ENTRY","errno":1062,"sqlState":"#23000"} 消息的其余部分发生了什么?我不能将整个错误转换为字符串吗?并且对键进行子字符串搜索?还是我走错了路?

2。 另外,我写了一个函数来遍历对象的键,但是这个对象似乎是一个字符串,但它不是。我似乎无法提取字符串 - 特别是 - 这部分字符串:"'key 'username'" of the error above.

明确地说,我的目标是将密钥“用户名”发送回客户端表单,以表明他的用户名已被使用。稍后我也必须对电子邮件执行相同的操作,因此我需要密钥。

编辑:我相信我必须使用带有 GET DIAGNOSTICS 的存储过程。类似于this article

【问题讨论】:

    标签: javascript mysql angularjs json knex.js


    【解决方案1】:

    所以这(我认为)很丑陋。但是我有 的解决方案并且它有效! 是 我创建了一个存储过程(在 mysql 中),包括 GET DIAGNOSTICS 命令。

        DELIMITER //
    
        DROP PROCEDURE IF EXISTS `insert_new_user` //
        CREATE PROCEDURE `insert_new_user` (uname VARCHAR(45), pass CHAR(96), r varchar(15))
        BEGIN
            /**
            Return field that has triggered the error, otherwise, return good
            **/
         -- Declare variables to hold diagnostics area information
          DECLARE code CHAR(5) DEFAULT '00000';
          DECLARE msg TEXT;
          DECLARE rows INT;
          DECLARE result TEXT;
          -- Declare exception handler for failed insert
          DECLARE CONTINUE HANDLER FOR SQLEXCEPTION
            BEGIN
              GET DIAGNOSTICS CONDITION 1
                code = RETURNED_SQLSTATE, msg = MESSAGE_TEXT;
            END;
    
          -- Perform the insert
          INSERT INTO Users(username, password, role) VALUES (uname, pass,  'full');
    
          -- Check whether the insert was successful
          IF code = '00000' THEN
            GET DIAGNOSTICS rows = ROW_COUNT;
            SET result = CONCAT('insert succeeded, row count = ',rows);
          ELSE
            SET result = CONCAT('insert failed, error = ',code,', message = ',msg);
          END IF;
          -- Say what happened
        SELECT result;
    
        END //
    

    顺便说一句,我确实根据需要复制并更改了代码 - 我希望我记得该网站...

    然后在我的快递服务器上我写了一个 knex.raw(...) 语句。而在

    .then(result => { ... })
    

    函数(因为 knex 是一个承诺)我通过调用 getError(result) 函数检查了结果是否存在错误。如果它有错误,它会给我钥匙,在我的例子中:'用户名'。 (我仍然必须做没有错误的替代方案)即

    ---控制台输出---没有错误

    ERR_str: [[[{"result":"插入成功,行数 = 1"}],{"fieldCount":0,"affectedRows":0,"insertId":0,"info":"" ,"serverStatus":2,"warning .....它继续

    ---结束输出-------

    仅供参考,这是发生错误 1062 时的控制台输出

    ---控制台输出---1062错误

    ERR_str: [[[{"result":"insert failed, error = 23000, message = Duplicate entry 'leerman2' for key 'username'"}],{"fieldCount":0,"affectedRows":0, "insertId":0,"info":"","serverStatus":2,"warningStatus":0}],[[{"_b...继续

    ---结束输出-------

    这是提取密钥的代码:

        function getError(err) {
            const ERR_str = JSON.stringify(err);
            console.log(`Entered getError() function...proceeding to exctract error...`);
    
            console.log(`ERR_str: ${ERR_str}`);
            console.log(`Error is string. [typeOf(ERR_str)]: ${typeof(ERR_str)}. (Attempting to exctract key...`);
            const START = (ERR_str.indexOf('key')) + 'key'.length + 2; // 2 including spaces 
            console.log(`Start: ${START}`);
            const END = ERR_str.indexOf(`'"}`);
            console.log(`End: ${END}`);    
            const KEY = ERR_str.substr(START, END - START);
            console.log(`key to return to server: ${KEY}`);
    
            return KEY || 0;
        }
    

    不是最干净的代码,而是一个好的开始。我现在可以将它发送到 Angular 并按预期使用它。如果有人发现这种方法有任何问题,请随时告诉我。

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2018-05-01
      • 2011-07-13
      • 2017-10-09
      • 1970-01-01
      • 1970-01-01
      • 2021-09-01
      • 2011-08-12
      • 2011-06-07
      相关资源
      最近更新 更多