1c3437056SNickeau<?php 2c3437056SNickeau 3c3437056SNickeau 4c3437056SNickeaunamespace ComboStrap; 5c3437056SNickeau 6c3437056SNickeau 7c3437056SNickeauclass SqliteRequest 8c3437056SNickeau{ 9*d899a2a6Sgerardnico const UPSERT_REQUEST = "Upsert"; 10*d899a2a6Sgerardnico const SELECT_REQUEST = "Select"; 11*d899a2a6Sgerardnico 12*d899a2a6Sgerardnico /** 13*d899a2a6Sgerardnico * delete, insert, update, query with parameters 14*d899a2a6Sgerardnico */ 15*d899a2a6Sgerardnico const PARAMETRIZED_REQUEST = "Parametrized"; 16*d899a2a6Sgerardnico const STATEMENT_REQUEST = "Statement"; 17c3437056SNickeau /** 18c3437056SNickeau * @var Sqlite 19c3437056SNickeau */ 20c3437056SNickeau private $sqlite; 21c3437056SNickeau /** 22c3437056SNickeau * @var string 23c3437056SNickeau */ 24c3437056SNickeau private $tableName; 25c3437056SNickeau /** 26c3437056SNickeau * @var array 27c3437056SNickeau */ 28c3437056SNickeau private $data; 29c3437056SNickeau /** 30c3437056SNickeau * @var SqliteResult 31c3437056SNickeau */ 32c3437056SNickeau private $result; 33c3437056SNickeau /** 34c3437056SNickeau * @var string 35c3437056SNickeau */ 36c3437056SNickeau private $query; 37c3437056SNickeau 38*d899a2a6Sgerardnico private \helper_plugin_sqlite $sqlitePlugin; 39*d899a2a6Sgerardnico 40c3437056SNickeau /** 41c3437056SNickeau * A statement that is not a query 42*d899a2a6Sgerardnico * @var ?string 43c3437056SNickeau */ 44*d899a2a6Sgerardnico private ?string $statement = null; 45*d899a2a6Sgerardnico /** 46*d899a2a6Sgerardnico * The SQL parameters 47*d899a2a6Sgerardnico * @var array |null 48*d899a2a6Sgerardnico */ 49*d899a2a6Sgerardnico private ?array $parameters = null; 50c3437056SNickeau 51c3437056SNickeau /** 52c3437056SNickeau * SqliteRequest constructor. 53c3437056SNickeau * @param Sqlite $sqlite 54c3437056SNickeau */ 55c3437056SNickeau public function __construct(Sqlite $sqlite) 56c3437056SNickeau { 57c3437056SNickeau $this->sqlite = $sqlite; 58c3437056SNickeau $this->sqlitePlugin = $sqlite->getSqlitePlugin(); 59c3437056SNickeau } 60c3437056SNickeau 61c3437056SNickeau public function setTableRow(string $tableName, array $data): SqliteRequest 62c3437056SNickeau { 63c3437056SNickeau $this->tableName = $tableName; 64c3437056SNickeau $this->data = $data; 65c3437056SNickeau return $this; 66c3437056SNickeau } 67c3437056SNickeau 68c3437056SNickeau /** 6904fd306cSNickeau * @throws ExceptionCompile 70c3437056SNickeau */ 71c3437056SNickeau public function execute(): SqliteResult 72c3437056SNickeau { 73*d899a2a6Sgerardnico $sqLiteAdapater = $this->sqlitePlugin->getAdapter(); 74*d899a2a6Sgerardnico $requestType = $this->getRequestType(); 75*d899a2a6Sgerardnico switch ($requestType) { 76*d899a2a6Sgerardnico case self::UPSERT_REQUEST: 77*d899a2a6Sgerardnico $statement = $this->getParametrizeReplaceQuery($this->tableName, $this->data); 78*d899a2a6Sgerardnico $values = array_values($this->data); 79*d899a2a6Sgerardnico $res = $this->executeParametrizedStatement($statement, $values); 80*d899a2a6Sgerardnico $queryExecuted = "Upsert of table $this->tableName"; 81*d899a2a6Sgerardnico break; 82*d899a2a6Sgerardnico case self::SELECT_REQUEST: 83c3437056SNickeau $res = $this->sqlitePlugin->query($this->query); 8404fd306cSNickeau $queryExecuted = $this->query; 85*d899a2a6Sgerardnico break; 86*d899a2a6Sgerardnico case self::PARAMETRIZED_REQUEST: 87*d899a2a6Sgerardnico $res = $this->executeParametrizedStatement($this->statement, $this->parameters); 88*d899a2a6Sgerardnico $queryExecuted = array_merge([$this->statement], $this->parameters); 89*d899a2a6Sgerardnico break; 90*d899a2a6Sgerardnico case self::STATEMENT_REQUEST: 91*d899a2a6Sgerardnico if (!Sqlite::isJuneVersion($sqLiteAdapater)) { 92*d899a2a6Sgerardnico /** @noinspection PhpUndefinedMethodInspection */ 93*d899a2a6Sgerardnico $res = $sqLiteAdapater->executeQuery($this->statement); 94*d899a2a6Sgerardnico } else { 95*d899a2a6Sgerardnico $res = $sqLiteAdapater->query($this->statement); 96c3437056SNickeau } 9704fd306cSNickeau $queryExecuted = $this->statement; 98*d899a2a6Sgerardnico break; 99*d899a2a6Sgerardnico default: 100*d899a2a6Sgerardnico throw new ExceptionCompile("The request type ($requestType) was not processed"); 101c3437056SNickeau } 102c3437056SNickeau 103*d899a2a6Sgerardnico 104c3437056SNickeau if ($res === null) { 10504fd306cSNickeau throw new ExceptionCompile("No Sql request was found to be executed"); 106c3437056SNickeau } 107c3437056SNickeau 108c3437056SNickeau if ($res === false) { 109c3437056SNickeau $message = $this->getErrorMessage(); 11004fd306cSNickeau throw new ExceptionCompile("Error in the $requestType. Message: {$message}"); 11104fd306cSNickeau } 11204fd306cSNickeau 113*d899a2a6Sgerardnico if (!$res instanceof \PDOStatement) { 11404fd306cSNickeau $message = $this->getErrorMessage(); 11504fd306cSNickeau throw new ExceptionCompile("Error in the request type `$requestType`. res is not a PDOStatement but as the value ($res). Message: {$message}, Query: {$queryExecuted}"); 116c3437056SNickeau } 117c3437056SNickeau 118c3437056SNickeau $this->result = new SqliteResult($this, $res); 119c3437056SNickeau return $this->result; 120c3437056SNickeau } 121c3437056SNickeau 122*d899a2a6Sgerardnico public 123*d899a2a6Sgerardnico function getErrorMessage(): string 124c3437056SNickeau { 125c3437056SNickeau $adapter = $this->sqlitePlugin->getAdapter(); 126c3437056SNickeau if ($adapter === null) { 12704fd306cSNickeau throw new ExceptionRuntimeInternal("The database adapter is null, no error info can be retrieved"); 128c3437056SNickeau } 129*d899a2a6Sgerardnico if (!Sqlite::isJuneVersion($adapter)) { 130*d899a2a6Sgerardnico /** @noinspection PhpUndefinedMethodInspection */ 131c3437056SNickeau $do = $adapter->getDb(); 132*d899a2a6Sgerardnico } else { 133*d899a2a6Sgerardnico $do = $adapter->getPdo(); 134*d899a2a6Sgerardnico } 135c3437056SNickeau if ($do === null) { 13604fd306cSNickeau throw new ExceptionRuntimeInternal("The database object is null, it seems that the database connection has been closed. Are you in two differents execution context ?"); 137c3437056SNickeau } 138c3437056SNickeau $errorInfo = $do->errorInfo(); 139c3437056SNickeau $message = ""; 140c3437056SNickeau $errorCode = $errorInfo[0]; 141c3437056SNickeau if ($errorCode === '0000') { 142c3437056SNickeau $message = ("No rows were deleted or updated"); 143c3437056SNickeau } 144c3437056SNickeau $errorInfoAsString = implode(", ", $errorInfo); 145c3437056SNickeau return "$message. : {$errorInfoAsString}"; 146c3437056SNickeau } 147c3437056SNickeau 148*d899a2a6Sgerardnico public 149*d899a2a6Sgerardnico function getSqliteConnection(): Sqlite 150c3437056SNickeau { 151c3437056SNickeau return $this->sqlite; 152c3437056SNickeau } 153c3437056SNickeau 154*d899a2a6Sgerardnico public 155*d899a2a6Sgerardnico function close() 156c3437056SNickeau { 157c3437056SNickeau 158c3437056SNickeau if ($this->result !== null) { 159c3437056SNickeau $this->result->close(); 160c3437056SNickeau $this->result = null; 161c3437056SNickeau } 162c3437056SNickeau 163c3437056SNickeau } 164c3437056SNickeau 165*d899a2a6Sgerardnico public 166*d899a2a6Sgerardnico function setQuery(string $string): SqliteRequest 167c3437056SNickeau { 168c3437056SNickeau $this->query = $string; 169c3437056SNickeau return $this; 170c3437056SNickeau } 171c3437056SNickeau 172c3437056SNickeau /** 173c3437056SNickeau * @param string $executableSql 174c3437056SNickeau * @param array $parameters 175c3437056SNickeau * @return SqliteResult 176c3437056SNickeau */ 177*d899a2a6Sgerardnico public 178*d899a2a6Sgerardnico function setQueryParametrized(string $executableSql, array $parameters): SqliteRequest 179c3437056SNickeau { 180*d899a2a6Sgerardnico $this->statement = $executableSql; 181*d899a2a6Sgerardnico $this->parameters = $parameters; 182c3437056SNickeau return $this; 183c3437056SNickeau 184c3437056SNickeau } 185c3437056SNickeau 186c3437056SNickeau /** 187c3437056SNickeau * @param string $statement 188c3437056SNickeau * @return $this - a statement that will execute 189c3437056SNickeau */ 190*d899a2a6Sgerardnico public 191*d899a2a6Sgerardnico function setStatement(string $statement): SqliteRequest 192c3437056SNickeau { 193c3437056SNickeau $this->statement = $statement; 194c3437056SNickeau return $this; 195c3437056SNickeau } 196c3437056SNickeau 197*d899a2a6Sgerardnico private 198*d899a2a6Sgerardnico function getRequestType(): string 199*d899a2a6Sgerardnico { 200*d899a2a6Sgerardnico if ($this->data !== null && $this->tableName !== null) { 201*d899a2a6Sgerardnico 202*d899a2a6Sgerardnico return self::UPSERT_REQUEST; 203*d899a2a6Sgerardnico 204*d899a2a6Sgerardnico } 205*d899a2a6Sgerardnico 206*d899a2a6Sgerardnico if ($this->query !== null) { 207*d899a2a6Sgerardnico 208*d899a2a6Sgerardnico return self::SELECT_REQUEST; 209*d899a2a6Sgerardnico 210*d899a2a6Sgerardnico } 211*d899a2a6Sgerardnico 212*d899a2a6Sgerardnico if ($this->parameters !== null) { 213*d899a2a6Sgerardnico 214*d899a2a6Sgerardnico return self::PARAMETRIZED_REQUEST; 215*d899a2a6Sgerardnico 216*d899a2a6Sgerardnico } 217*d899a2a6Sgerardnico 218*d899a2a6Sgerardnico return self::STATEMENT_REQUEST; 219*d899a2a6Sgerardnico 220*d899a2a6Sgerardnico } 221*d899a2a6Sgerardnico 222*d899a2a6Sgerardnico /** 223*d899a2a6Sgerardnico * @param string $table 224*d899a2a6Sgerardnico * @param array $data 225*d899a2a6Sgerardnico * @return string - a replace parametrized query 226*d899a2a6Sgerardnico */ 227*d899a2a6Sgerardnico private function getParametrizeReplaceQuery(string $table, array $data): string 228*d899a2a6Sgerardnico { 229*d899a2a6Sgerardnico $columns = array_map(function ($column) { 230*d899a2a6Sgerardnico return '"' . $column . '"'; 231*d899a2a6Sgerardnico }, array_keys($data)); 232*d899a2a6Sgerardnico $placeholders = array_pad([], count($columns), '?'); 233*d899a2a6Sgerardnico /** @noinspection SqlResolve */ 234*d899a2a6Sgerardnico return 'REPLACE INTO "' . $table . '" (' . join(',', $columns) . ') VALUES (' . join(',', 235*d899a2a6Sgerardnico $placeholders) . ')'; 236*d899a2a6Sgerardnico } 237*d899a2a6Sgerardnico 238*d899a2a6Sgerardnico private function executeParametrizedStatement(string $statement, array $values): \PDOStatement 239*d899a2a6Sgerardnico { 240*d899a2a6Sgerardnico $sqLiteAdapater = $this->sqlitePlugin->getAdapter(); 241*d899a2a6Sgerardnico $queryParametrized = array_merge([$statement], $values); 242*d899a2a6Sgerardnico if (!Sqlite::isJuneVersion($sqLiteAdapater)) { 243*d899a2a6Sgerardnico /** @noinspection PhpParamsInspection */ 244*d899a2a6Sgerardnico return $sqLiteAdapater->query($queryParametrized); 245*d899a2a6Sgerardnico } 246*d899a2a6Sgerardnico $values = array_values($values); 247*d899a2a6Sgerardnico return $sqLiteAdapater->query($statement, $values); 248*d899a2a6Sgerardnico } 249*d899a2a6Sgerardnico 250c3437056SNickeau} 251