zoukankan      html  css  js  c++  java
  • MySQL JDBC 出现多个 SHOW VARIABLES 语句。

    一次偶然的机会,show processlist 的时候,发现有个 Client 一直在执行  "mysql-connector-java-5.1.21 ( Revision: ${bzr.revision-id} ) */SHOW VARIABLES WHERE Variable_name"

    后面和基友一起讨论,稍微缕了一下。大概思路是这样的的:

    1.MySQL JDBC 连接过程大概如下(开启 general log 获得的信息):

    5089492 Connect user@ip on db
                    5089492 Query   /* mysql-connector-java-5.1.21 ( Revision: ${bzr.revision-id} ) */SHOW VARIABLES WHERE Variable_name ='language' OR Variable_name = 'net_write_timeout' OR Variable_name = 'interactive_timeout' OR Variable_name = 'wait_timeout' OR Variable_name = 'character_set_client' OR Variable_name = 'character_set_connection' OR Variable_name = 'character_set' OR Variable_name = 'character_set_server' OR Variable_name = 'tx_isolation' OR Variable_name = 'transaction_isolation' OR Variable_name = 'character_set_results' OR Variable_name = 'timezone' OR Variable_name = 'time_zone' OR Variable_name = 'system_time_zone' OR Variable_name = 'lower_case_table_names' OR Variable_name = 'max_allowed_packet' OR Variable_name = 'net_buffer_length' OR Variable_name = 'sql_mode' OR Variable_name = 'query_cache_type' OR Variable_name = 'query_cache_size' OR Variable_name = 'init_connect'
                    5089492 Query   /* mysql-connector-java-5.1.21 ( Revision: ${bzr.revision-id} ) */SELECT @@session.auto_increment_increment
                    5089492 Query   SHOW COLLATION
                    5089492 Query   SET NAMES utf8mb4
                    5089492 Query   SET character_set_results = NULL
                    5089492 Query   SET autocommit=1
                    5089492 Query   SET sql_mode='STRICT_TRANS_TABLES'
    

      1)Connect user@ip on db

      2)SHOW VARIABLES WHERE Variable_name ='language'... 获取 Client 关心的 session 级别变量。

      3)获取 @@session.auto_increment_increment . 这个参数的作用请参考 https://dev.mysql.com/doc/refman/5.5/en/replication-options-master.html#sysvar_auto_increment_increment 。主要是控制 auto_increment 属性的列每次自增的值的间隔。比如从1 3 5 7 增长的时候,auto_increment_increment 可以设置为2.

      4)接着就是后面的剩余操作。

    从这里可以看出,如果是一个新的JDBC 连接,它就需要这个请求过程,是不可避免的。那么如果尽量减少 Client 的请求呢。现在常用的就是使用 DB 连接池技术。

    正巧开发的同时配置的信息如下:

    <environments default="development">
            <environment id="development">
                <transactionManager type="JDBC" />
                <dataSource type="UNPOOLED">
                    <property name="driver" value="${db.driverClass}" />
                    <property name="url" value="${db.connectUrl}" />
                    <property name="username" value="${db.user}" />
                    <property name="password" value="${db.pass}" />
                </dataSource>
            </environment>
        </environments>

    最后推断是 <dataSource type="UNPOOLED"> 这个参数的设置问题。其中type 有三个可选值: type="[UNPOOLED|POOLED|JNDI]" 通过 http://www.mybatis.org/mybatis-3/configuration.html  的解释可以看到  UNPOOLED – This implementation of DataSource simply opens and closes a connection each time it is requested.

    后面让开发把配置改为  type="POOLED", 测试发现仍然会出现上面的 SQL 请求,频率会小一点。现在理解为:虽然有了连接池,但是第一次JDBC 连接的建立还是需要请求 MySQL variables 值的,只是后面重用连接的时候就没有必要再去获取这些值了。

    结论:

    1).通过JDBC 连接数据库的时候,尽量配上连接池,不然每次访问都需要额外的获取的变量,也是很消耗资源的。

    2).连接池第一次建立连接的过程大体上如下,不同jdbc 版本不同,可能请求会有略微差别。

    3).这是一个正常现象。

    还有一个疑问:下面的一个命令充斥着 MySQL slow query log。有人说是 client 来测试和数据库的连通性的。可是能不能换个其他方式来测试呢?用这个 SQL 会让我的 slow query log 全部是这个玩意儿,很烦人。

     

    # Time: 161122 11:21:01
    # User@Host: db[db] @  [ip]
    # Query_time: 0.000018  Lock_time: 0.000000 Rows_sent: 0  Rows_examined: 0 Logical_reads: 0 Physical_reads: 0
    SET timestamp=1479784861;
    # administrator command: Ping;
    

      

  • 相关阅读:
    2018JAVA面试题附答案
    微服务概述
    Java后台开发面试题总结
    郁金香搜索引擎方案
    单点登录
    Redis为什么是单线程
    数据库原理-范式
    权限分配之一级菜单优化添加和编辑页面图标
    权限分配之一级菜单保留原搜索条件
    django分页的东西, 不详细, 但是也足够了。
  • 原文地址:https://www.cnblogs.com/liushuiwuqing/p/6090672.html
Copyright © 2011-2022 走看看