Zend_Db_Profiler.xml 16 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417
  1. <sect1 id="zend.db.profiler" xmlns:xi="http://www.w3.org/2001/XInclude">
  2. <title>Zend_Db_Profiler</title>
  3. <sect2 id="zend.db.profiler.introduction">
  4. <title>Wprowadzenie</title>
  5. <para>
  6. <code>Zend_Db_Profiler</code> może być włączony aby pozwolić na
  7. profilowanie zapytań. Profilowanie umożliwia zbadanie czasu trwania
  8. zapytań pozwalając na inspekcję przeprowadzonych zapytań bez potrzeby
  9. dodawania dodatkowego kodu do klas. Zaawansowane użycie pozwala także
  10. programiście decydować o tym, jakich typów zapytania mają być profilowane.
  11. </para>
  12. <para>
  13. Włącz profiler przekazując odpowiednią dyrektywę do konstruktora
  14. adaptera, lub wywołując później metodę adaptera.
  15. </para>
  16. <programlisting role="php"><![CDATA[
  17. $params = array (
  18. 'host' => '127.0.0.1',
  19. 'username' => 'webuser',
  20. 'password' => 'xxxxxxxx',
  21. 'dbname' => 'test',
  22. 'profiler' => true // włącz profiler; ustaw false aby wyłączyć (domyślne wyłączony)
  23. );
  24. $db = Zend_Db::factory('PDO_MYSQL', $params);
  25. // wyłącz profiler:
  26. $db->getProfiler()->setEnabled(false);
  27. // włącz profiler:
  28. $db->getProfiler()->setEnabled(true);
  29. ]]>
  30. </programlisting>
  31. <para>
  32. Wartość opcji '<code>profiler</code>' jest dość elastyczna. Jest
  33. ona interpretowana zależnie id jej typu. W większości przypadków
  34. powinieneś użyć wartości logicznej, ale inne typy pozwalają na
  35. dostosowanie zachowania profilera do własnych potrzeb.
  36. </para>
  37. <para>
  38. Parametr logiczny włącza profiler jeśli ma wartość
  39. <code>true</code>, lub wyłącza jeśli ma wartość <code>false</code>.
  40. Klasą profilera domyślnie jest klasa <code>Zend_Db_Profiler</code>.
  41. <programlisting role="php"><![CDATA[
  42. $params['profiler'] = true;
  43. $db = Zend_Db::factory('PDO_MYSQL', $params);
  44. ]]>
  45. </programlisting>
  46. </para>
  47. <para>
  48. Przekazanie instancji obiektu profilera powoduje jej użycie przez
  49. sterownik bazy danych. Musi to być obiekt klasy
  50. <code>Zend_Db_Profiler</code> lub klasy ją rozszerzającej. Aktywacja
  51. profilera odbywa się osobno.
  52. <programlisting role="php"><![CDATA[
  53. $profiler = MyProject_Db_Profiler();
  54. $profiler->setEnabled(true);
  55. $params['profiler'] = $profiler;
  56. $db = Zend_Db::factory('PDO_MYSQL', $params);
  57. ]]>
  58. </programlisting>
  59. </para>
  60. <para>
  61. Argument może być tablicą asocjacyjną zawierającą wszystkie lub
  62. jeden z kluczy '<code>enabled</code>', '<code>instance</code>', oraz
  63. '<code>class</code>'. Klucz '<code>enabled</code>' odpowiada wartości
  64. logicznej, a '<code>instance</code>' wartości instancji, obie są
  65. opisane powyżej. Klucz '<code>class</code>' jest używany do podania
  66. nazwy klasy jaka ma być użyta we własnym profilerze. Musi być to
  67. obiekt klasy <code>Zend_Db_Profiler</code> lub klasy ją rozszerzającej.
  68. Instancja klasy jest tworzona bez żadnych argumentów. Opcja
  69. '<code>class</code>' jest ingorowana jeśli podana jest opcja
  70. '<code>instance</code>'.
  71. <programlisting role="php"><![CDATA[
  72. $params['profiler'] = array(
  73. 'enabled' => true,
  74. 'class' => 'MyProject_Db_Profiler'
  75. );
  76. $db = Zend_Db::factory('PDO_MYSQL', $params);
  77. ]]>
  78. </programlisting>
  79. </para>
  80. <para>
  81. Ostatecznie, argument może być obiektem klasy <code>Zend_Config</code>
  82. zawierającym właściwości, które są traktowane jako klucze tablicy
  83. opisane powyżej. Przykładowo plik "config.ini" może zawierać
  84. następujące dane:
  85. <programlisting role="ini"><![CDATA[
  86. [main]
  87. db.profiler.class = "MyProject_Db_Profiler"
  88. db.profiler.enabled = true
  89. ]]>
  90. </programlisting>
  91. Konfiguracja może być przekazana za pomocą takiego kodu PHP:
  92. <programlisting role="php"><![CDATA[
  93. $config = new Zend_Config_Ini('config.ini', 'main');
  94. $params['profiler'] = $config->db->profiler;
  95. $db = Zend_Db::factory('PDO_MYSQL', $params);
  96. ]]>
  97. </programlisting>
  98. Właściwość '<code>instance</code>' może być użyta w następujący sposób:
  99. <programlisting role="php"><![CDATA[
  100. $profiler = new MyProject_Db_Profiler();
  101. $profiler->setEnabled(true);
  102. $configData = array(
  103. 'instance' => $profiler
  104. );
  105. $config = new Zend_Config($configData);
  106. $params['profiler'] = $config;
  107. $db = Zend_Db::factory('PDO_MYSQL', $params);
  108. ]]>
  109. </programlisting>
  110. </para>
  111. </sect2>
  112. <sect2 id="zend.db.profiler.using">
  113. <title>Użycie profilera</title>
  114. <para>
  115. W dowolnym momencie możesz pobrać profiler używając metody
  116. adaptera <code>getProfiler()</code>:
  117. </para>
  118. <programlisting role="php"><![CDATA[
  119. $profiler = $db->getProfiler();
  120. ]]>
  121. </programlisting>
  122. <para>
  123. Zwraca to instancję <code>Zend_Db_Profiler</code>. Używając tej
  124. instancji programista może zbadać zapytania używając rozmaitych
  125. metod:
  126. </para>
  127. <itemizedlist>
  128. <listitem>
  129. <para>
  130. <code>getTotalNumQueries()</code> zwraca liczbę wszystkich
  131. zapytań które były profilowane.
  132. </para>
  133. </listitem>
  134. <listitem>
  135. <para>
  136. <code>getTotalElapsedSecs()</code> zwraca całkowity czas
  137. trwania profilowanych zapytań.
  138. </para>
  139. </listitem>
  140. <listitem>
  141. <para>
  142. <code>getQueryProfiles()</code> zwraca tablicę wszystkich
  143. profilów zapytań.
  144. </para>
  145. </listitem>
  146. <listitem>
  147. <para>
  148. <code>getLastQueryProfile()</code> zwraca ostatni (najnowszy)
  149. profil zapytania, niezależnie od tego czy zostało ono zakończone czy
  150. nie (jeśli nie zostało, to czas zakończenia będzie miał wartość null)
  151. </para>
  152. </listitem>
  153. <listitem>
  154. <para>
  155. <code>clear()</code> czyści wszystkie poprzednie profile
  156. zapytań ze stosu.
  157. </para>
  158. </listitem>
  159. </itemizedlist>
  160. <para>
  161. Wartość zwracana przez <code>getLastQueryProfile()</code> oraz
  162. pojedyncze elementy tablicy zwracanej przez <code>getQueryProfiles()</code>
  163. są obiektami <code>Zend_Db_Profiler_Query</code>, które dają możliwość
  164. sprawdzenia osobno każdego zapytania.
  165. </para>
  166. <itemizedlist>
  167. <listitem>
  168. <para>
  169. Metoda <code>getQuery()</code> zwraca tekst SQL zapytania.
  170. Tekst przygotowanego zapytania SQL z parametrami jest
  171. tekstem w takiej postaci w jakiej był on przygotowany, więc
  172. zawiera on etykiety, a nie wartości użyte podczas wykonania
  173. zapytania.
  174. </para>
  175. </listitem>
  176. <listitem>
  177. <para>
  178. Metoda <code>getQueryParams()</code> zwraca tablicę wartości
  179. parametrów użytych podczas wykonania przygotowanego
  180. zapytania. Odnosi się to do parametrów oraz do argumentów
  181. metody <code>execute()</code>. Klucze tablicy są oparte na
  182. pozycji (od 1 w górę) lub nazwane (łańcuchy znaków).
  183. </para>
  184. </listitem>
  185. <listitem>
  186. <para>
  187. Metoda <code>getElapsedSecs()</code> zwraca czas trwania zapytania
  188. </para>
  189. </listitem>
  190. </itemizedlist>
  191. <para>
  192. Informacja której dostarcza <code>Zend_Db_Profiler</code> jest
  193. użyteczna przy profilowaniu wąskich gardeł w aplikacjach oraz
  194. do szukania błędów w wykonanych zapytaniach. Na przykład aby
  195. zobaczyć ostatnie zapytanie jakie było wykonane:
  196. </para>
  197. <programlisting role="php"><![CDATA[
  198. $query = $profiler->getLastQueryProfile();
  199. echo $query->getQuery();
  200. ]]>
  201. </programlisting>
  202. <para>
  203. Możliwe, że strona generuje się powoli; użyj profilera aby ustalić
  204. czas wykonania wszystkich zapytań, a następnie przejść poprzez
  205. zapytania aby znaleść te, które trwało najdłużej:
  206. </para>
  207. <programlisting role="php"><![CDATA[
  208. $totalTime = $profiler->getTotalElapsedSecs();
  209. $queryCount = $profiler->getTotalNumQueries();
  210. $longestTime = 0;
  211. $longestQuery = null;
  212. foreach ($profiler->getQueryProfiles() as $query) {
  213. if ($query->getElapsedSecs() > $longestTime) {
  214. $longestTime = $query->getElapsedSecs();
  215. $longestQuery = $query->getQuery();
  216. }
  217. }
  218. echo 'Wykonano ' . $queryCount . ' zapytań w czasie ' . $totalTime . ' sekund' . "\n";
  219. echo 'Średni czas trwania zapytania: ' . $totalTime / $queryCount . ' sekund' . "\n";
  220. echo 'Zapytań na sekundę:: ' . $queryCount / $totalTime . "\n";
  221. echo 'Czas trwania najdłuższego zapytania: ' . $longestTime . "\n";
  222. echo "Najdłuższe zapytanie: \n" . $longestQuery . "\n";
  223. ]]>
  224. </programlisting>
  225. </sect2>
  226. <sect2 id="zend.db.profiler.advanced">
  227. <title>Zaawansowane użycie profilera</title>
  228. <para>
  229. Oprócz sprawdzania zapytań, profiler pozwala także programiście na
  230. określenie typów zapytań które mają być profilowane. Poniższe
  231. metody operują na instancji <code>Zend_Db_Profiler</code>:
  232. </para>
  233. <sect3 id="zend.db.profiler.advanced.filtertime">
  234. <title>Filtrowanie ze względu na czas trwania zapytania</title>
  235. <para>
  236. <code>setFilterElapsedSecs()</code> pozwala programiście ustalić
  237. minimalny czas trwania zapytania jaki jest potrzebny do tego by
  238. zostało ono profilowane. Aby usunąć filtr, wywołaj metodę z
  239. wartością null w parametrze.
  240. </para>
  241. <programlisting role="php"><![CDATA[
  242. // Profiluj tylko zapytania które trwają przynajmniej 5 sekund:
  243. $profiler->setFilterElapsedSecs(5);
  244. // Profiluj wszystkie zapytania, niezależnie od czasu ich trwania:
  245. $profiler->setFilterElapsedSecs(null);
  246. ]]>
  247. </programlisting>
  248. </sect3>
  249. <sect3 id="zend.db.profiler.advanced.filtertype">
  250. <title>Filtrowanie ze względu na typ zapytania</title>
  251. <para>
  252. <code>setFilterQueryType()</code> pozwala programiście określić,
  253. które typy zapytań powinny być profilowane; aby profilować
  254. zapytania wielu typów użyj logicznego operatora OR. Typy zapytań
  255. są zdefiniowane jako stałe w <code>Zend_Db_Profiler</code>:
  256. </para>
  257. <itemizedlist>
  258. <listitem>
  259. <para>
  260. <code>Zend_Db_Profiler::CONNECT</code>: operacje
  261. połączenia lub wybierania bazy danych.
  262. </para>
  263. </listitem>
  264. <listitem>
  265. <para>
  266. <code>Zend_Db_Profiler::QUERY</code>: ogólne zapytania
  267. które nie pasują do pozostałych typów.
  268. </para>
  269. </listitem>
  270. <listitem>
  271. <para>
  272. <code>Zend_Db_Profiler::INSERT</code>: każde zapytanie
  273. które wstawia nowe dane do bazy, generalnie SQL INSERT.
  274. </para>
  275. </listitem>
  276. <listitem>
  277. <para>
  278. <code>Zend_Db_Profiler::UPDATE</code>: każde zapytanie
  279. ktore uaktualnia dane w bazie, najczęściej SQL UPDATE.
  280. </para>
  281. </listitem>
  282. <listitem>
  283. <para>
  284. <code>Zend_Db_Profiler::DELETE</code>: każde zapytanie
  285. które usuwa istnięjące dane, najczęściej SQL DELETE.
  286. </para>
  287. </listitem>
  288. <listitem>
  289. <para>
  290. <code>Zend_Db_Profiler::SELECT</code>: każde zapytanie
  291. które pobiera istnięjące dane, najczęściej SQL SELECT.
  292. </para>
  293. </listitem>
  294. <listitem>
  295. <para>
  296. <code>Zend_Db_Profiler::TRANSACTION</code>: każda
  297. operacja transakcyjna, taka jak start transakcji, potwierdzenie
  298. zmian czy ich cofnięcie.
  299. </para>
  300. </listitem>
  301. </itemizedlist>
  302. <para>
  303. Analogicznie jak w metodzie <code>setFilterElapsedSecs()</code>,
  304. możesz usunąć wszystkie istniejące filtry przekazując metodzie
  305. pusty parametr <code>null</code>.
  306. </para>
  307. <programlisting role="php"><![CDATA[
  308. // profiluj tylko zapytania SELECT
  309. $profiler->setFilterQueryType(Zend_Db_Profiler::SELECT);
  310. // profiluj zapytania SELECT, INSERT, oraz UPDATE
  311. $profiler->setFilterQueryType(Zend_Db_Profiler::SELECT | Zend_Db_Profiler::INSERT | Zend_Db_Profiler::UPDATE);
  312. // profiluj zapytania DELETE
  313. $profiler->setFilterQueryType(Zend_Db_Profiler::DELETE);
  314. // Usuń wszystkie filtry
  315. $profiler->setFilterQueryType(null);
  316. ]]>
  317. </programlisting>
  318. </sect3>
  319. <sect3 id="zend.db.profiler.advanced.getbytype">
  320. <title>Pobieranie profili na podstawie typów zapytań</title>
  321. <para>
  322. Użycie metody <code>setFilterQueryType()</code> może zmniejszyć
  323. ilość wygenerowanych profili. Jakkolwiek, czasem bardziej użyteczne
  324. jest przechowywanie wszystkich profili i wyświetlanie tylko
  325. tych których potrzebujesz w danym momencie. Inną funkcjonalnością
  326. metody <code>getQueryProfiles()</code> jest to, że może ona
  327. przeprowadzić te filtrowanie w locie, po przekazaniu typu
  328. zapytań (lub logicznej kombinacji typów zapytań) jako pierwszego
  329. argumentu; przejdź do <xref linkend="zend.db.profiler.advanced.filtertype" />
  330. aby zobaczyć listę stałych określających typy zapytań.
  331. </para>
  332. <programlisting role="php"><![CDATA[
  333. // Pobierz jedynie profile zapytań SELECT
  334. $profiles = $profiler->getQueryProfiles(Zend_Db_Profiler::SELECT);
  335. // Pobierz jedynie profile zapytań SELECT, INSERT, oraz UPDATE
  336. $profiles = $profiler->getQueryProfiles(Zend_Db_Profiler::SELECT | Zend_Db_Profiler::INSERT | Zend_Db_Profiler::UPDATE);
  337. // Pobierz jedynie profile zapytań DELETE
  338. $profiles = $profiler->getQueryProfiles(Zend_Db_Profiler::DELETE);
  339. ]]>
  340. </programlisting>
  341. </sect3>
  342. </sect2>
  343. <sect2 id="zend.db.profiler.profilers">
  344. <title>Wyspecjalizowane profilery</title>
  345. <para>
  346. Wyspecjalizowany profiler jest obiektem klasy dziedziczącej po
  347. klasie <code>Zend_Db_Profiler</code>. Wyspecjalizowane profilery
  348. traktują profilowane informacje w szczególny sposób.
  349. </para>
  350. <xi:include href="Zend_Db_Profiler-Firebug.xml">
  351. <xi:fallback><xi:include href="../../en/module_specs/Zend_Db_Profiler-Firebug.xml" /></xi:fallback>
  352. </xi:include>
  353. </sect2>
  354. </sect1>