©
                    本文档使用
                    php中文网手册 发布
                
插件改变了 PHP MySQL 连接的控制,新建连接会从一个连接池中获取,用于替代 client-server 的单一连接方式。连接池包含一组 master 连接,和可选数目的 slave 连接。
连接池中的每一个连接都有自己的状态,例如:SQL 用户变量、临时表、事物状态。 所有的链接状态可以参考 连接池与切换 说明。 如果插件决定要为负载均衡切换连接,应用可能得到一个不同状态的链接。 应用必须能够处理这些问题。
Example #1 配置了一个 master 和一个 slave 的插件
{
    "myapp": {
        "master": {
            "master_0": {
                "host": "localhost",
                "socket": "\/tmp\/mysql.sock"
            }
        },
        "slave": {
            "slave_0": {
                "host": "192.168.2.27",
                "port": "3306"
            }
        }
    }
} 
Example #2 陷阱:连接状态和 SQL 用户变量
  <?php
$mysqli  = new  mysqli ( "myapp" ,  "username" ,  "password" ,  "database" );
if (! $mysqli )
   
   die( sprintf ( "[%d] %s\n" ,  mysqli_connect_errno (),  mysqli_connect_error ()));
 
 if (! $mysqli -> query ( "SET @myrole='master'" )) {
  printf ( "[%d] %s\n" ,  $mysqli -> errno ,  $mysqli -> error );
}
 
 if (!( $res  =  $mysqli -> query ( "SELECT @myrole AS _role" ))) {
  printf ( "[%d] %s\n" ,  $mysqli -> errno ,  $mysqli -> error );
} else {
  $row  =  $res -> fetch_assoc ();
  $res -> close ();
  printf ( "@myrole = '%s'\n" ,  $row [ '_role' ]);
}
 $mysqli -> close ();
 ?>   以上例程会输出:
@myrole = ''
范例打开了负载均衡连接,并且执行两个查询。 第一个查询 SET @myrole='master' 没有以 SELECT 开头。然而并不能识别这是一个应该在 slave 中执行的查询,所以他被在 master 中执行。 所以这个变量被绑定在 master 连接中,master 连接设定被改变了。
然后执行 SELECT @myrole AS _role 查询,差将将其识别为只读查询, 并且发送给 slave 服务器。这样这个查询不会获得任何已经设定的 SQL 用户变量。 这个变量被设定在了第一次使用的 master 连接上面。所以范例将打印 @myrole = ''。
这是开发人员必须注意的问题,插件并不会监控所有连接的变化情况。 若要监控所有的变化,将消耗大量的 CPU 资源。
当然这种陷阱,可以通过 SQL hints 解决。