zoukankan      html  css  js  c++  java
  • MySQL存储过程执行慢

    1.现象:
    1.执行MySQL存储过程在测试环境只要0.1s左右,到了生产环境qu却要5s左右,偏差很大。

    2.非常简单的存储过程函数,处理的数据只有8条。

    3.把存储过程里的查询单独拿出来查询速度很快,但是放在存储过程函数中就很慢。

    2.原因:
    数据库表中的字段是utf-8,而数据库字符集后来改成了utf8mb4。

    存储过程中定义参数时,没有指定字符集,会默认读取创建存储过程时的全局变量character_set_server,就变成了utf8mb4编码。

    utf8的,是不兼容utfbmb4的,字符集不同从而导致索引失效,进行导致执行变慢。

    3.解决方案:
    将索引的字符集改成utfbmb4。

    4.问题的存储函数
    CREATE DEFINER=`root`@`%` FUNCTION `getAVGResponseTime`(_sessionId varchar(32)) RETURNS int(11)
    COMMENT '获取单次会话平均响应时间(s)'
    BEGIN
    -- 完成循环
    DECLARE v_finished INTEGER DEFAULT 0;
    -- 响应次数
    DECLARE cnt int DEFAULT 0;
    -- 访客发送时间
    DECLARE visitorSendTime int DEFAULT 0;
    -- 聊天来源 1访客 2客服
    DECLARE _fromType int ;
    -- 会话类型 1机器人会话 2人工会话
    DECLARE sessionType int ;
    -- 发送时间
    DECLARE _sendTime int ;
    -- 客服接起时间
    DECLARE _pickUpTime int;
    -- 会话创建方式
    DECLARE _createType int;
    -- 总反应时间
    DECLARE totalResponseTime DOUBLE DEFAULT 0.0;
    -- 聊天游标
    DECLARE sessionCursor CURSOR FOR (
    SELECT TIME_TO_SEC(sendTime) sendTime,fromType
    FROM chat_log
    where sessionId =_sessionId
    ORDER BY sendTime
    );

    -- 游标结束
    DECLARE CONTINUE HANDLER
    FOR NOT FOUND SET v_finished = 1;
    -- 客服接起时间,创建类型,会话类型
    SELECT TIME_TO_SEC(pickUpTime) ,createType,type INTO _pickUpTime,_createType,sessionType
    FROM `session`
    WHERE sessionId = _sessionId;
    -- 机器人会话返回-1
    IF sessionType = 1 THEN
    return -1;
    END IF;
    -- 首次响应
    SET visitorSendTime =_pickUpTime;
    -- 开启游标
    OPEN sessionCursor;
    -- 遍历游标
    loop1 : LOOP
    -- 获取单条
    FETCH sessionCursor INTO _sendTime,_fromType;
    -- 游标结束退出循环
    IF v_finished = 1 THEN
    LEAVE loop1;
    END IF;

    IF _sendTime >_pickUpTime
    THEN
    -- 获取访客第一次发送时间
    IF _fromType = 1 AND visitorSendTime = 0
    THEN
    SET visitorSendTime =_sendTime;
    END IF;
    -- 获取客服第一次响应时间
    IF _fromType = 2 AND visitorSendTime>0
    THEN
    -- 总计响应时间
    SET totalResponseTime =totalResponseTime + _sendTime -visitorSendTime;
    -- 重置访客最后一次发送时间
    SET visitorSendTime =0;
    -- 响应次数+1
    SET cnt =cnt +1;
    END IF;
    END IF;
    END LOOP loop1;
    -- 关闭游标
    CLOSE sessionCursor;
    -- 如果是客服创建减去首次响应时间
    IF _createType = 3
    THEN
    SET cnt =cnt -1;
    END IF;
    -- 没有响应
    IF cnt <= 0 THEN
    RETURN -1;
    END IF;

    RETURN totalResponseTime/cnt;
    END
     

  • 相关阅读:
    Django中DEBUG模式详解
    Nginx 的负载均衡
    django 上线配置
    vue 项目实现打印
    vue 一键复制,vue-clipboard2的使用方法
    404.vue
    vue-router封装和用户是否需要登录
    uni-app uview 的使用方法
    grid自适应列表
    tomcat的目录分别代表什么含义
  • 原文地址:https://www.cnblogs.com/caiwuzi/p/13095856.html
Copyright © 2011-2022 走看看