diff --git a/extensions/yii/debug/models/search/Log.php b/extensions/yii/debug/models/search/Log.php index ab8c754..38fa343 100644 --- a/extensions/yii/debug/models/search/Log.php +++ b/extensions/yii/debug/models/search/Log.php @@ -22,7 +22,7 @@ class Log extends Base public $category; /** - * @var integer ajax attribute input search value + * @var integer message attribute input search value */ public $message; diff --git a/extensions/yii/debug/models/search/Profile.php b/extensions/yii/debug/models/search/Profile.php new file mode 100644 index 0000000..357c019 --- /dev/null +++ b/extensions/yii/debug/models/search/Profile.php @@ -0,0 +1,75 @@ + 'Category', + 'info' => 'Info', + ]; + } + + /** + * Returns data provider with filled models. Filter applied if needed. + * @param array $params + * @param array $models + * @return \yii\data\ArrayDataProvider + */ + public function search($params, $models) + { + $dataProvider = new ArrayDataProvider([ + 'allModels' => $models, + 'pagination' => [ + 'pageSize' => 10, + ], + 'sort' => [ + 'attributes' => ['category','info','duration'], + 'defaultOrder' => [ + 'duration' => SORT_DESC, + ], + ], + ]); + + if (!($this->load($params) && $this->validate())) { + return $dataProvider; + } + + $filter = new Filter(); + $this->addCondition($filter, 'category', true); + $this->addCondition($filter, 'info', true); + $dataProvider->allModels = $filter->filter($models); + + return $dataProvider; + } + +} diff --git a/extensions/yii/debug/panels/DbPanel.php b/extensions/yii/debug/panels/DbPanel.php index ebac11f..73b2fa7 100644 --- a/extensions/yii/debug/panels/DbPanel.php +++ b/extensions/yii/debug/panels/DbPanel.php @@ -121,7 +121,7 @@ class DbPanel extends Panel */ protected function getModels() { - if ($this->_models === null || $refresh) { + if ($this->_models === null) { $this->_models = []; $timings = $this->calculateTimings(); diff --git a/extensions/yii/debug/panels/ProfilingPanel.php b/extensions/yii/debug/panels/ProfilingPanel.php index 49cf081..e3037e9 100644 --- a/extensions/yii/debug/panels/ProfilingPanel.php +++ b/extensions/yii/debug/panels/ProfilingPanel.php @@ -9,8 +9,8 @@ namespace yii\debug\panels; use Yii; use yii\debug\Panel; -use yii\helpers\Html; use yii\log\Logger; +use yii\debug\models\search\Profile; /** * Debugger panel that collects and displays performance profiling info. @@ -20,6 +20,17 @@ use yii\log\Logger; */ class ProfilingPanel extends Panel { + + /** + * @var array profile messages timings + */ + private $_timings; + + /** + * @var array current request profile timings + */ + private $_models; + public function getName() { return 'Profiling'; @@ -27,25 +38,41 @@ class ProfilingPanel extends Panel public function getSummary() { - $memory = sprintf('%.1f MB', $this->data['memory'] / 1048576); - $time = number_format($this->data['time'] * 1000) . ' ms'; - $url = $this->getUrl(); - - return << - Time $time - -
- Memory $memory -
-EOD; + return Yii::$app->view->render('panels/profile/summary',[ + 'memory' => sprintf('%.1f MB', $this->data['memory'] / 1048576), + 'time' => number_format($this->data['time'] * 1000) . ' ms', + 'panel' => $this + ]); } public function getDetail() { + $searchModel = new Profile(); + $dataProvider = $searchModel->search($_GET, $this->getModels()); + + return Yii::$app->view->render('panels/profile/detail',[ + 'panel' => $this, + 'dataProvider' => $dataProvider, + 'searchModel' => $searchModel, + 'memory' => sprintf('%.1f MB', $this->data['memory'] / 1048576), + 'time' => number_format($this->data['time'] * 1000) . ' ms', + ]); + } + + /** + * Calculates given request profile messages timings. + * @return array timings + */ + protected function calculateTimings() + { + if ($this->_timings !== null) { + return $this->_timings; + } + $messages = $this->data['messages']; $timings = []; $stack = []; + foreach ($messages as $i => $log) { list($token, $level, $category, $timestamp, $traces) = $log; if ($level == Logger::LEVEL_PROFILE_BEGIN) { @@ -62,36 +89,7 @@ EOD; $timings[] = [count($stack), $last[0], $last[2], $now - $last[3], $last[4]]; } - $rows = []; - foreach ($timings as $timing) { - $time = sprintf('%.1f ms', $timing[3] * 1000); - $procedure = str_repeat('', $timing[0]) . Html::encode($timing[1]); - $category = Html::encode($timing[2]); - $rows[] = "$time$category$procedure"; - } - $rows = implode("\n", $rows); - - $memory = sprintf('%.1f MB', $this->data['memory'] / 1048576); - $time = number_format($this->data['time'] * 1000) . ' ms'; - - return <<Performance Profiling - -

Total processing time: $time; Peak memory: $memory.

- - - - - - - - - - -$rows - -
TimeCategoryProcedure
-EOD; + return $this->_timings = $timings; } public function save() @@ -104,4 +102,27 @@ EOD; 'messages' => $messages, ]; } + + /** + * Returns array of profiling models that can be used in data provider. + * @return array models + */ + protected function getModels() + { + if ($this->_models === null) { + $this->_models = []; + $timings = $this->calculateTimings(); + + foreach($timings as $profileTiming) { + $this->_models[] = [ + 'duration' => $profileTiming[3] * 1000, #in milliseconds + 'category' => $profileTiming[2], + 'info' => $profileTiming[1], + 'level' => $profileTiming[0], + ]; + } + } + return $this->_models; + } + } diff --git a/extensions/yii/debug/views/default/panels/db/summary.php b/extensions/yii/debug/views/default/panels/db/summary.php index 1c3bdfa..c21715e 100644 --- a/extensions/yii/debug/views/default/panels/db/summary.php +++ b/extensions/yii/debug/views/default/panels/db/summary.php @@ -1,6 +1,6 @@ diff --git a/extensions/yii/debug/views/default/panels/profile/detail.php b/extensions/yii/debug/views/default/panels/profile/detail.php new file mode 100644 index 0000000..0431c74 --- /dev/null +++ b/extensions/yii/debug/views/default/panels/profile/detail.php @@ -0,0 +1,34 @@ + +

Performance Profiling

+

Total processing time: ; Peak memory: .

+ $dataProvider, + 'id' => 'profile-panel-detailed-grid', + 'filterModel' => $searchModel, + 'filterUrl' => $panel->getUrl(), + 'columns' => [ + ['class' => 'yii\grid\SerialColumn'], + [ + 'attribute' => 'duration', + 'value' => function ($data) + { + return sprintf('%.1f ms',$data['duration']); + }, + ], + 'category', + [ + 'attribute' => 'info', + 'value' => function ($data) + { + return str_repeat('', $data['level']) . $data['info']; + }, + 'options' => [ + 'width' => '60%', + ], + ], + ], +]); +?> \ No newline at end of file diff --git a/extensions/yii/debug/views/default/panels/profile/summary.php b/extensions/yii/debug/views/default/panels/profile/summary.php new file mode 100644 index 0000000..dd2a679 --- /dev/null +++ b/extensions/yii/debug/views/default/panels/profile/summary.php @@ -0,0 +1,6 @@ +
+ Time +
+ \ No newline at end of file