Zend_Db_Select.xml 11 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430
  1. <sect1 id="zend.db.select">
  2. <title>Zend_Db_Select</title>
  3. <sect2 id="zend.db.select.introduction">
  4. <title>Inleiding</title>
  5. <para>
  6. Zend_Db_Select is een werktuig dat je helpt SQL SELECT verklaringen
  7. te bouwen op een manier waardoor deze niet database gebonden zijn.
  8. Het kan uiteraard niet perfect zijn, maar het helpt je een goed
  9. stuk om je queries database-onafhankelijk te maken, en daardoor
  10. overdraagbaar van een database naar een andere. Bovendien helpt het
  11. je je queries beter bestand te maken tegen SQL injectie aanvallen.
  12. </para>
  13. <para>
  14. De gemakkelijkste manier om een instantie van de Zend_Db_Select te
  15. verkrijgen is het gebruik van de Zend_Db_Adapter::select() methode.
  16. </para>
  17. <programlisting role="php"><![CDATA[<?php
  18. require_once 'Zend/Db.php';
  19. $params = array (
  20. 'host' => '127.0.0.1',
  21. 'username' => 'gweniver',
  22. 'password' => '******',
  23. 'dbname' => 'camelot'
  24. );
  25. $db = Zend_Db::factory('PDO_MYSQL', $params);
  26. $select = $db->select();
  27. // $select is nu een Zend_Db_Select_PdoMysql object
  28. ?>]]></programlisting>
  29. <para>
  30. Dan maak je een SELECT query via dat object en zijn methodes en
  31. die maakt dan een string die je aan Zend_Db_Adapter kan doorgeven
  32. om queries of ophalingen uit te voeren.
  33. </para>
  34. <programlisting role="php"><![CDATA[<?php
  35. //
  36. // SELECT *
  37. // FROM round_table
  38. // WHERE noble_title = "Sir"
  39. // ORDER BY first_name
  40. // LIMIT 10 OFFSET 20
  41. //
  42. // je kan een iteratieve stijl gebruiken...
  43. $select->from('round_table', '*');
  44. $select->where('noble_title' = ?', 'Sir');
  45. $select->order('first_name');
  46. $select->limit(10,20);
  47. // ...of een "vloeiende" stijl
  48. $select->from('round_table', '*')
  49. ->where('noble_title = ?', 'Sir')
  50. ->order('first_name')
  51. ->limit(10,20);
  52. // in ieder geval, het resultaat ophalen
  53. $sql = $select->__toString();
  54. $result = $db->fetchAll($sql);
  55. // een andere manier is om het $select object zelf door te geven;
  56. // Zend_Db_Adapter Is slim genoeg om de __toString() methode op
  57. // Zend_Db_Select objecten toe te passen om de querystring te
  58. // verkrijgen.
  59. $result = $db->fetchAll($select);
  60. ?>]]></programlisting>
  61. <para>
  62. Je kan ook gebonden parameters gebruiken in je queries plaats
  63. van ze één per één te quoten.
  64. </para>
  65. <programlisting role="php"><![CDATA[<?php
  66. //
  67. // SELECT *
  68. // FROM round_table
  69. // WHERE noble_title = "Sir"
  70. // ORDER BY first_name
  71. // LIMIT 10 OFFSET 20
  72. //
  73. $select->from('round_table', '*')
  74. ->where('noble_title = :title')
  75. ->order('first_name')
  76. ->limit(10,20);
  77. // in ieder geval, het resultaat ophalen door de parameters te binden
  78. $params = array('title' => 'Sir');
  79. $result = $db->fetchAll($select, $params);
  80. ?>]]></programlisting>
  81. </sect2>
  82. <sect2 id="zend.db.select.fromcols">
  83. <title>Kolommen FROM een tabel</title>
  84. <para>
  85. Om kolommen van een bepaalde tabel de selecteren gebruik je de
  86. from() methode, de tabel en de kolommen die je ervan wil
  87. verkijgen specificerend. Je kan zowel tabel als kolom aliassen
  88. gebruiken en je kan from() zoveel gebruiken als nodig is.
  89. </para>
  90. <programlisting role="php"><![CDATA[<?php
  91. // maak een $db object en neem aan dat we de Mysql adapter gebruiken
  92. $select = $db->select();
  93. // SELECT a, b, c FROM some_table
  94. $select->from('some_table', 'a, b, c');
  95. // hetzelfde, maar anders:
  96. $select->from('some_table', array('a', 'b', 'c');
  97. // SELECT bar.col FROM foo AS bar
  98. $select->from('foo AS bar', 'bar.col');
  99. // SELECT foo.col AS col1, bar.col AS col2 FROM foo, bar
  100. $select->from('foo', 'foo.col AS col1');
  101. $select->from('bar', 'bar.col AS col2');
  102. ?>]]></programlisting>
  103. </sect2>
  104. <sect2 id="zend.db.select.joincols">
  105. <title>Kolommen van geJOINde tabellen</title>
  106. <para>
  107. Om kolommen van gejoinde tabellen te selecteren kan je de
  108. join() methode gebruiken. Geef eerst de gejoinde tabelnaam op,
  109. dan de join voorwaarde en uiteindelijk de kolommen die je van
  110. de join wil terugkrijgen. Je kan join() zoveel maal gebruiken
  111. als dat nodig is.
  112. </para>
  113. <programlisting role="php"><![CDATA[<?php
  114. // maak een $db object en neem aan dat we de Mysql adapter gebruiken
  115. $select = $db->select();
  116. //
  117. // SELECT foo.*, bar.*
  118. // FROM foo
  119. // JOIN bar ON foo.id = bar.id
  120. //
  121. $select->from('foo', '*');
  122. $select->join('bar', 'foo.id = bar.id', '*');
  123. ?>]]></programlisting>
  124. <para>
  125. Voor het moment is alleen de JOIN syntax ondersteund; geen
  126. LEFT JOINs, RIGHT JOINs enz. Latere versies zullen deze
  127. concepten in een database-onafhankelijke manier ondersteunen.
  128. </para>
  129. </sect2>
  130. <sect2 id="zend.db.select.where">
  131. <title>WHERE voorwaarden</title>
  132. <para>
  133. Om WHERE voorwaarden toe te voegen gebruik je de where() methode.
  134. Je kan een gewone string doorgeven, of een string met de
  135. vraagteken plaatshouder en een waarde die er moet worden ingequote
  136. (de waarde zal in qoutes worden gewikkeld door
  137. Zend_Db_Adapter::quoteInto() te gebruiken.
  138. </para>
  139. <para>
  140. Meerdere aanvragen aan where() zal de voorwaarden aan elkaar AND-en;
  141. als je een OR voorwaarde nodig hebt, gebruik dan orWhere().
  142. </para>
  143. <programlisting role="php"><![CDATA[<?php
  144. // maak a $db object en verkrijg een SELECT werktuig.
  145. $select = $db->select();
  146. //
  147. // SELECT *
  148. // FROM round_table
  149. // WHERE noble_title = "Sir"
  150. // AND favorite_color = "yellow"
  151. //
  152. $select->from('round_table', '*');
  153. $select->where('noble_title = "Sir"); // ingebedde waarde
  154. $select->where('favorite_color = ?', 'yellow'); // waarde met quotes
  155. //
  156. // SELECT *
  157. // FROM foo
  158. // WHERE bar = "baz"
  159. // OR id IN("1", "2", "3")
  160. //
  161. $select->from('foo', '*');
  162. $select->where('bar = ?', 'baz');
  163. $select->orWhere('id IN(?)', array(1, 2, 3);
  164. ?>]]></programlisting>
  165. </sect2>
  166. <sect2 id="zend.db.select.group">
  167. <title>GROUP BY clausule</title>
  168. <para>
  169. Om rijen te groeperen gebruik je de group() methode zoveel maal
  170. als dat nodig is.
  171. </para>
  172. <programlisting role="php"><![CDATA[<?php
  173. // maak a $db object en verkrijg een SELECT werktuig.
  174. $select = $db->select();
  175. //
  176. // SELECT COUNT(id)
  177. // FROM foo
  178. // GROUP BY bar, baz
  179. //
  180. $select->from('foo', 'COUNT(id)');
  181. $select->group('bar');
  182. $select->group('baz');
  183. // een gelijkaardige oproep van group():
  184. $select->group('bar, baz');
  185. // een andere gelijkaardige oproep van group():
  186. $select->group(array('bar', 'baz'));
  187. ?>]]></programlisting>
  188. </sect2>
  189. <sect2 id="zend.db.select.having">
  190. <title>HAVING voorwaarden</title>
  191. <para>
  192. Om HAVING voorwaarden aan de selectieregels toe te voegen gebruik
  193. je de having() methode. Deze methode heeft een identieke werking
  194. als de where() methode.
  195. </para>
  196. <para>
  197. Indien je having() meerdere malen oproept worden de voorwaarden
  198. aaneen ge-AND; om OR voorwaarden te verkrijgen gebruik je orHaving().
  199. </para>
  200. <programlisting role="php"><![CDATA[<?php
  201. // maak a $db object en verkrijg een SELECT werktuig.
  202. $select = $db->select();
  203. //
  204. // SELECT COUNT(id) AS count_id
  205. // FROM foo
  206. // GROUP BY bar, baz
  207. // HAVING count_id > "1"
  208. //
  209. $select->from('foo', 'COUNT(id) AS count_id');
  210. $select->group('bar, baz');
  211. $select->having('count_id > ?', 1);
  212. ?>]]></programlisting>
  213. </sect2>
  214. <sect2 id="zend.db.select.order">
  215. <title>ORDER BY clausule</title>
  216. <para>
  217. Om kolommen te ordenen gebruik je de order() methode zoveel maal als
  218. dat nodig is.
  219. </para>
  220. <programlisting role="php"><![CDATA[<?php
  221. // maak a $db object en verkrijg een SELECT werktuig.
  222. $select = $db->select();
  223. //
  224. // SELECT * FROM round_table
  225. // ORDER BY noble_title DESC, first_name ASC
  226. //
  227. $select->from('round_table', '*');
  228. $select->order('noble_title DESC');
  229. $select->order('first_name');
  230. // een gelijkaardige oproep van order():
  231. $select->order('noble_title DESC, first_name');
  232. // een andere gelijkaardige oproep van order():
  233. $select->order(array('noble_title DESC', 'first_name'));
  234. ?>]]></programlisting>
  235. </sect2>
  236. <sect2 id="zend.db.select.limit">
  237. <title>LIMIT per Count en Offset</title>
  238. <para>
  239. Zend_Db_Select ondersteunt een database onafhankelijke LIMIT clausule.
  240. Voor vele databases, zoals MySQL en PostgreSQL is dit relatief
  241. eenvoudig omdat ze de "LIMIT :count [OFFSET :offset]" syntax
  242. ondersteunen.
  243. </para>
  244. <para>
  245. Voor andere databases, zoals Microsoft SQL en Oracle is dit niet zo
  246. eenvoudig omdat zij helemaal geen LIMIT clausule ondersteunen.
  247. MS-SQL heeft alleen een TOP-clausule, en voor Oracle moet de query
  248. op een specifieke manier worden geschreven om LIMIT te emuleren.
  249. Vanwege de innerlijke werking van Zend_Db_Select kunnen we de SELECT
  250. query on-the-fly herschrijven om de LIMIT functionaliteit van de
  251. voornoemde open source database systemen te emuleren.
  252. </para>
  253. <para>
  254. Om het teruggestuurde resultaat te LIMITeren per count en offset
  255. gebruik je de limit() methode met een count en een optionele offset.
  256. </para>
  257. <programlisting role="php"><![CDATA[<?php
  258. // eerst een eenvoudige "LIMIT :count"
  259. $select = $db->select();
  260. $select->from('foo', '*');
  261. $select->order('id');
  262. $select->limit(10);
  263. //
  264. // In MySQL/PostgreSQL/SQLite wordt dit vertaald naar:
  265. //
  266. // SELECT * FROM foo
  267. // ORDER BY id ASC
  268. // LIMIT 10
  269. //
  270. // Maar in Microsoft SQL wordt dit vertaald naar:
  271. //
  272. // SELECT TOP 10 * FROM FOO
  273. // ORDER BY id ASC
  274. //
  275. //
  276. // nu een meer complexe "LIMIT :count OFFSET :offset"
  277. $select = $db->select();
  278. $select->from('foo', '*');
  279. $select->order('id');
  280. $select->limit(10, 20);
  281. //
  282. // In MySQL/PostgreSQL/SQLite wordt dit vertaald naar:
  283. //
  284. // SELECT * FROM foo
  285. // ORDER BY id ASC
  286. // LIMIT 10 OFFSET 20
  287. //
  288. // Maar in Microsoft SQL die offset niet ondersteund, wordt dit vertaald
  289. // naar iets als dit:
  290. //
  291. // SELECT * FROM (
  292. // SELECT TOP 10 * FROM (
  293. // SELECT TOP 30 * FROM foo ORDER BY id DESC
  294. // ) ORDER BY id ASC
  295. // )
  296. //
  297. // Zend_Db_Adapter doet de vertaling van de query automatisch voor jou
  298. //
  299. ?>]]></programlisting>
  300. </sect2>
  301. <sect2 id="zend.db.select.paging">
  302. <title>LIMIT per Pagina en Count</title>
  303. <para>
  304. Zend_Db_Select biedt eveneens pagina-gebaseerde limits. Indien
  305. je een zeker aantal "pagina's" resultaten wil ophalen gebruik
  306. je de limitPage() methode; geef eerste het paginanummer aan en
  307. dan het aantal rijen dat op elke pagina moet worden afgebeeld.
  308. </para>
  309. <programlisting role="php"><![CDATA[<?php
  310. // bouw de basis select...
  311. $select = $db->select();
  312. $select->from('foo', '*');
  313. $select->order('id');
  314. // ... en limit naar pagina 3 en elke pagina heeft 10 rijen af te beelden
  315. $select->limitPage(3, 10);
  316. //
  317. // In MySQL/PostgreSQL/SQLite wordt dit vertaald naar:
  318. //
  319. // SELECT * FROM foo
  320. // ORDER BY id ASC
  321. // LIMIT 10 OFFSET 20
  322. //
  323. ?>]]></programlisting>
  324. </sect2>
  325. </sect1>
  326. <!--
  327. vim:se ts=4 sw=4 et:
  328. -->