3、Zend_Db_Profiler
Zend_Db_Profiler可以启用查询分析功能。分析内容包括适配器处理的查询和查询的运行消耗时间。通过它,无需添加额外的调试代码,就可以检查已执行的查询。
$params = array(
'host' => '127.0.0.1',
'username' => 'webuser',
'password' => 'xxxxxxxx',
'dbname' => 'test'
'profiler' => true // turn on profiler
// set to false to disable (disabled by default)
);
$db = Zend_Db::factory('PDO_MYSQL', $params);
// turn off profiler:
$db->getProfiler()->setEnabled(false);
// turn on profiler:
$db->getProfiler()->setEnabled(true);
启用分析功能,配置方法是非常灵活的。大多数情况下,你只需使用一个简单的布尔值,但允许使用其他自定义类型来启用分析功能。
$params['profiler'] = true;
$db = Zend_Db::factory('PDO_MYSQL', $params);
适配器使用分析器对象时。分析器对象的类型必须是 Zend_Db_Profiler 或者其子类。
$profiler = MyProject_Db_Profiler();
$profiler->setEnabled(true);
$params['profiler'] = $profiler;
$db = Zend_Db::factory('PDO_MYSQL', $params);
配置参数可以是一个关联数组。其键名为'enabled', 'instance', 和'class'.
'enabled' 和 'instance' 键的值是一个boolean值和profiler对象的实例
'class' 指定自定义的分析器的类名。类必须是Zend_Db_Profiler或Zend_Db_Profiler的子类子类。实例化类时,无须传递构造参数。
$params['profiler'] = array(
'enabled' => true,
'class' => 'MyProject_Db_Profiler'
);
$db = Zend_Db::factory('PDO_MYSQL', $params);
上面的配置参数也可以使用Zend_Config实现。数组的key可以作为配置选项的名称。例如,一个“config.ini”文件可能包含以下数据:
[main]
db.profiler.class = "MyProject_Db_Profiler"
db.profiler.enabled = true
使用这些配置的方法:
$config = new Zend_Config_Ini('config.ini', 'main');
$params['profiler'] = $config->db->profiler;
$db = Zend_Db::factory('PDO_MYSQL', $params);
'instance' 配置选项可以按照如下方法使用:
$profiler = new MyProject_Db_Profiler();
$profiler->setEnabled(true);
$configData = array(
'instance' => $profiler
);
$config = new Zend_Config($configData);
$params['profiler'] = $config;
$db = Zend_Db::factory('PDO_MYSQL', $params);
3.1Using the Profiler
在任何时候, 要使用分析器。都要通过适配器的 getProfiler()方法调用$profiler = $db->getProfiler();
得到一个Zend_Db_Profiler 对象实例后,开发人员可以使用如下方法进行查询语句的分析工作:
-
getTotalNumQueries() 返回查询语句的个数
-
getTotalElapsedSecs() 返回所有查询语句消耗的时间
-
getQueryProfiles() 返回所有查询语句
-
getLastQueryProfile() 无论查询是否完成,都会返回最后一个(最近一个)查询信息,(如果没有的话,返回NULL)
-
clear() 从堆栈中清除以往任何查询信息。
-
getQuery() 返回SQL语句。 SQL语句是预处理statement 的语句,所以它包含参数占位符,而不是具体执行的语句。
-
getQueryParams() 返回一个数组,包含预处理查询执行时使用的参数值。 包括绑定参数和statement的execute() 方法的参数。数组的key是位置(索引从1开始)或者名称(字符串)参数索引
-
getElapsedSecs() 返回查询运行的秒数。
$query = $profiler->getLastQueryProfile();
echo $query->getQuery();
如果一个页面加载运行缓慢。可以使用Profiler来确定所有查询的消耗时间总数,然后逐步找到一个运行时间最长的查询:
$totalTime = $profiler->getTotalElapsedSecs();
$queryCount = $profiler->getTotalNumQueries();
$longestTime = 0;
$longestQuery = null;
foreach ($profiler->getQueryProfiles() as $query) {
if ($query->getElapsedSecs() > $longestTime) {
$longestTime = $query->getElapsedSecs();
$longestQuery = $query->getQuery();
}
}
echo 'Executed ' . $queryCount . ' queries in ' . $totalTime .
' seconds' . "\n";
echo 'Average query length: ' . $totalTime / $queryCount .
' seconds' . "\n";
echo 'Queries per second: ' . $queryCount / $totalTime . "\n";
echo 'Longest query length: ' . $longestTime . "\n";
echo "Longest query: \n" . $longestQuery . "\n";
3.2Advanced Profiler Usage 高级使用方法
除了可以对查询的检查分析,分析器也使开发人员能够分析过滤查询。Zend_Db_Profiler提供了相关的操作方法。3.3Filter by query elapsed time 通过查询时间进行过滤
setFilterElapsedSecs()允许开发人员可以设置一个最小的查询时间,来过滤查询。删除过滤器,只需要设置为NULL即可。 $profiler->setFilterElapsedSecs(5);
// Profile all queries regardless of length:
$profiler->setFilterElapsedSecs(null);
3.4Filter by query type 通过查询类型过滤
通过使用setFilterQueryType() 方法,开发人员可以根据类型来过滤查询。分析器Zend_Db_Profiler类中定义了多种查询类型常量。如下:-
Zend_Db_Profiler::CONNECT: connection operations, or selecting a database.链接操作,或者选择数据库
-
Zend_Db_Profiler::QUERY: general database queries that do not match other types. 没有具体匹配类型的查询
-
Zend_Db_Profiler::INSERT: any query that adds new data to the database, generallySQLINSERT.INSERT 插入语句
-
Zend_Db_Profiler::UPDATE: any query that updates existing data, usuallySQLUPDATE. UPDATE更新修改语句
-
Zend_Db_Profiler::DELETE: any query that deletes existing data, usuallySQLDELETE. DELETE删除语句
-
Zend_Db_Profiler::SELECT: any query that retrieves existing data, usuallySQLSELECT. SELECT语句
-
Zend_Db_Profiler::TRANSACTION: any transactional operation, such as start transaction, commit, or rollback. 事务处理语句例如commit和rollback
$profiler->setFilterQueryType(Zend_Db_Profiler::SELECT);
// profile SELECT, INSERT, and UPDATE queries
$profiler->setFilterQueryType(Zend_Db_Profiler::SELECT |
Zend_Db_Profiler::INSERT |
Zend_Db_Profiler::UPDATE);
// profile DELETE queries
$profiler->setFilterQueryType(Zend_Db_Profiler::DELETE);
// Remove all filters
$profiler->setFilterQueryType(null);
3.5Retrieve profiles by query type 设置分析查询的类型
使用 setFilterQueryType() 可以过滤查询。但是,有时需要多种过滤类型同时起作用。 getQueryProfiles()的第一个参数不仅可以是一个查询类型常量,也可以是对查询类型进行逻辑运算组合。如下: $profiles = $profiler->getQueryProfiles(Zend_Db_Profiler::SELECT);
// Retrieve only SELECT, INSERT, and UPDATE query profiles
$profiles = $profiler->getQueryProfiles(Zend_Db_Profiler::SELECT |
Zend_Db_Profiler::INSERT |
Zend_Db_Profiler::UPDATE);
// Retrieve DELETE query profiles
$profiles = $profiler->getQueryProfiles(Zend_Db_Profiler::DELETE);
3.6Specialized Profilers 特定的分析器
可以通过继承Zend_Db_Profiler实现一个特定的分析器。特定的分析器可以通过特殊的方式返回分析信息3.7Profiling with Firebug 通过Firebug进行性能分析
通过Zend_Db_Profiler_Firebug 将性能分析信息输出到Firebug 的Console控制台。
通过Zend_Wildfire_Channel_HttpHeaders的组件设置HTTP头发送所有的数据,以确保页面内容不被干扰。通过这种方法,当用户调试AJAX请求时,可以保证响应JSON和XML不会掺杂多余的信息。
Requirements:要求
-
Firefox Browser ideally version 3 but version 2 is also supported. 较新的火狐浏览器
-
Firebug Firefox Extension which you can download from » https://addons.mozilla.org/en-US/firefox/addon/1843. 安装Firebug
-
FirePHP Firefox Extension which you can download from » https://addons.mozilla.org/en-US/firefox/addon/6149.安装FirePHP
Example:DB Profiling with Zend_Controller_Front 通过Zend_Controller_Front做DB性能分析
// In your bootstrap file
$profiler = new Zend_Db_Profiler_Firebug('All DB Queries');
$profiler->setEnabled(true);
// Attach the profiler to your db adapter
$db->setProfiler($profiler);
// Dispatch your front controller
// All DB queries in your model, view and controller
// files will now be profiled and sent to Firebug
Example:DB Profiling without Zend_Controller_Front 不采用Zend_Controller_Front做DB性能分析
$profiler = new Zend_Db_Profiler_Firebug('All DB Queries');
$profiler->setEnabled(true);
// Attach the profiler to your db adapter
$db->setProfiler($profiler);
$request = new Zend_Controller_Request_Http();
$response = new Zend_Controller_Response_Http();
$channel = Zend_Wildfire_Channel_HttpHeaders::getInstance();
$channel->setRequest($request);
$channel->setResponse($response);
// Start output buffering
ob_start();
// Now you can run your DB queries to be profiled
// Flush profiling data to browser
$channel->flush();
$response->sendHeaders();
具体的使用方法,在FirePHP 的官方网站已经讲的很详细了。可以参考完成相关配置和使用。