PgController.php 5.3 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208
  1. <?php
  2. namespace ImiApp\ApiServer\Controller;
  3. use Imi\Db\Db;
  4. use Imi\Db\Interfaces\IDb;
  5. use Imi\RequestContext;
  6. use Imi\Redis\RedisManager;
  7. use ImiApp\Model\PgSql\World;
  8. use ImiApp\Model\PgSql\Fortune;
  9. use Imi\Util\Stream\MemoryStream;
  10. use Imi\Server\View\Annotation\View;
  11. use Imi\Server\View\Annotation\HtmlView;
  12. use Imi\Server\Http\Route\Annotation\Route;
  13. use Imi\Server\Http\Route\Annotation\Action;
  14. use Imi\Server\Http\Controller\HttpController;
  15. use Imi\Server\Http\Route\Annotation\Controller;
  16. use Imi\Server\Http\Message\Contract\IHttpResponse;
  17. /**
  18. * @Controller("/")
  19. */
  20. class PgController extends HttpController
  21. {
  22. const POOL_NAME = 'pgsql';
  23. /**
  24. * @Action
  25. */
  26. public function pgDbModel(): ?World
  27. {
  28. return World::find(\mt_rand(1, 10000));
  29. }
  30. /**
  31. * @Action
  32. */
  33. public function pgDbRaw(): array
  34. {
  35. $db = Db::getInstance(self::POOL_NAME);
  36. $stmt = $db->prepare('SELECT id, randomnumber FROM World WHERE id = ? LIMIT 1');
  37. $stmt->execute([\mt_rand(1, 10000)]);
  38. return $stmt->fetch();
  39. }
  40. /**
  41. * @Action
  42. */
  43. public function pgQueryModel($queries): array
  44. {
  45. $queries = (int)$queries;
  46. if($queries > 1)
  47. {
  48. $queryCount = \min($queries, 500);
  49. }
  50. else
  51. {
  52. $queryCount = 1;
  53. }
  54. $list = [];
  55. while ($queryCount--)
  56. {
  57. $list[] = World::find(\mt_rand(1, 10000));
  58. }
  59. return $list;
  60. }
  61. /**
  62. * @Action
  63. *
  64. * @return void
  65. */
  66. public function pgQueryRaw($queries): array
  67. {
  68. $queries = (int)$queries;
  69. if($queries > 1)
  70. {
  71. $queryCount = \min($queries, 500);
  72. }
  73. else
  74. {
  75. $queryCount = 1;
  76. }
  77. $list = [];
  78. $db = Db::getInstance(self::POOL_NAME);
  79. $stmt = $db->prepare('SELECT id, randomnumber FROM World WHERE id = ? LIMIT 1');
  80. while ($queryCount--)
  81. {
  82. $stmt->execute([\mt_rand(1, 10000)]);
  83. $list[] = $stmt->fetch();
  84. }
  85. return $list;
  86. }
  87. /**
  88. * @Action
  89. * @View(renderType="html")
  90. * @HtmlView("fortunes")
  91. */
  92. public function pgFortunes(): array
  93. {
  94. $this->response->setHeader('Content-Type', 'text/html; charset=UTF-8');
  95. $list = Fortune::select();
  96. $rows = [];
  97. foreach($list as $item)
  98. {
  99. $rows[$item->id] = $item->message;
  100. }
  101. $rows[0] = 'Additional fortune added at request time.';
  102. \asort($rows);
  103. return [
  104. 'rows' => $rows,
  105. ];
  106. }
  107. /**
  108. * @Action
  109. * @View(renderType="html")
  110. *
  111. * @return void
  112. */
  113. public function pgFortunesRaw(): IHttpResponse
  114. {
  115. $rows = [];
  116. foreach(Db::getInstance(self::POOL_NAME)->query('SELECT id, message FROM Fortune')->fetchAll() as $item)
  117. {
  118. $rows[$item['id']] = $item['message'];
  119. }
  120. $rows[0] = 'Additional fortune added at request time.';
  121. \asort($rows);
  122. $html = '';
  123. foreach ($rows as $id => $message)
  124. {
  125. $message = \htmlspecialchars($message, ENT_QUOTES, 'UTF-8');
  126. $html .= "<tr><td>{$id}</td><td>{$message}</td></tr>";
  127. }
  128. return $this->response->setHeader('Content-Type', 'text/html; charset=UTF-8')
  129. ->setBody(new MemoryStream("<!DOCTYPE html><html><head><title>Fortunes</title></head><body><table><tr><th>id</th><th>message</th></tr>{$html}</table></body></html>"));
  130. }
  131. /**
  132. * @Action
  133. */
  134. public function pgUpdateModel($queries): array
  135. {
  136. $queries = (int)$queries;
  137. if($queries > 1)
  138. {
  139. $queryCount = \min($queries, 500);
  140. }
  141. else
  142. {
  143. $queryCount = 1;
  144. }
  145. $list = [];
  146. while ($queryCount--)
  147. {
  148. $list[] = $row = World::find(\mt_rand(1, 10000));
  149. $row->randomNumber = \mt_rand(1, 10000);
  150. $row->update();
  151. }
  152. return $list;
  153. }
  154. /**
  155. * @Action
  156. */
  157. public function pgUpdateRaw($queries): array
  158. {
  159. $queries = (int)$queries;
  160. if($queries > 1)
  161. {
  162. $queryCount = \min($queries, 500);
  163. }
  164. else
  165. {
  166. $queryCount = 1;
  167. }
  168. $db = Db::getInstance(self::POOL_NAME);
  169. $stmtSelect = $db->prepare('SELECT id, randomnumber FROM World WHERE id = ? LIMIT 1');
  170. $stmtUpdate = $db->prepare('UPDATE World SET randomNumber = CASE id' . \str_repeat(' WHEN ?::INTEGER THEN ?::INTEGER ', $queryCount) . 'END WHERE id IN (' . \str_repeat('?::INTEGER,', $queryCount - 1) . '?::INTEGER)');
  171. $list = [];
  172. $keys = $values = [];
  173. while ($queryCount--)
  174. {
  175. $values[] = $keys[] = $id = \mt_rand(1, 10000);
  176. $stmtSelect->execute([$id]);
  177. $row = $stmtSelect->fetch();
  178. $values[] = $row['randomNumber'] = \mt_rand(1, 10000);
  179. $list[] = $row;
  180. }
  181. $db->beginTransaction();
  182. try {
  183. $stmtUpdate->execute([
  184. ...$values,
  185. ...$keys
  186. ]);
  187. $db->commit();
  188. } catch(\Throwable $th) {
  189. $db->rollBack();
  190. throw $th;
  191. }
  192. return $list;
  193. }
  194. }