1<?php 2 3namespace DDDBL; 4 5$objQueue = Singleton::getInstance('\DDDBL\Queue'); 6 7############################# 8### db-connection handler ### 9############################# 10 11# get (or first establish) connection to database 12# and store the DataObject of the connection in the Queue-State 13 14$cloStoreDBConnection = function(\DDDBL\Queue $objQueue, array $arrParameter) { 15 16 if(!isConnected()) 17 connect(); 18 19 $objQueue->getState()->update(array('DB' => getDBDataObject())); 20 21}; 22 23$objQueue->addHandler(QUEUE_GET_DB_CONNECTION_POSITION, $cloStoreDBConnection); 24 25############################### 26### query-definition-loader ### 27############################### 28 29# get the DataObject of the query and store it in the queue 30 31$cloGetQuery = function(\DDDBL\Queue $objQueue, array $arrParameter) { 32 33 $objDataObjectPool = new DataObjectPool('Query-Definition'); 34 35 # get the first entry of the parameter-list; this is the query-alias 36 $strAlias = array_shift($arrParameter); 37 38 if(empty($strAlias) || !is_string($strAlias)) 39 throw new \Exception('no query-alias defined!'); 40 41 if(!$objDataObjectPool->exists($strAlias)) 42 throw new \Exception("given query alias is unknown: $strAlias"); 43 44 $objQueue->getState()->update(array('QUERY' => $objDataObjectPool->get($strAlias))); 45 46}; 47 48$objQueue->addHandler(QUEUE_GET_QUERY_POSITION, $cloGetQuery); 49 50################################# 51### set BIND-DATA-TYPE option ### 52################################# 53 54# check if the query has a BIND-DATA-TYPE config. 55# if not check if there is one given for the database-connection. 56# if yes, store it as setting for the query, otherwise 57# set false for this option 58 59$cloSetBindDataTypeConfig = function(\DDDBL\Queue $objQueue, array $arrParameter) { 60 61 $objDB = $objQueue->getState()->get('DB'); 62 $objQuery = $objQueue->getState()->get('QUERY'); 63 64 # skip this step, if the query itselfs has its own 65 if($objQuery->exists('BIND-DATA-TYPE')) { 66 $objQuery->update(array('BIND-DATA-TYPE' => (bool) $objQuery->get('BIND-DATA-TYPE'))); #bugfix for php-bug #38409 67 return; 68 } 69 70 # set type to false, if no config is available, otherwise use the given config 71 if(!$objDB->exists('BIND-DATA-TYPE')) 72 $objQuery->update(array('BIND-DATA-TYPE' => false)); 73 else 74 $objQuery->update(array('BIND-DATA-TYPE' => (bool) $objDB->get('BIND-DATA-TYPE'))); 75 76}; 77 78$objQueue->addHandler(QUEUE_BIND_DATA_TYPE_POSITION, $cloSetBindDataTypeConfig); 79 80##################### 81### prepare query ### 82##################### 83 84# get the stored query and prepare() it for the given database-connection 85# store the resulting PDOStatement 86 87$cloPrepareQuery = function(\DDDBL\Queue $objQueue, array $arrParameter) { 88 89 # if query is not prepared yet, do this now 90 if(!$objQueue->getState()->get('QUERY')->exists('PDOStatement')) { 91 $objPDO = $objQueue->getState()->get('DB')->get('PDO'); 92 $objPDO = $objPDO->prepare($objQueue->getState()->get('QUERY')->get('QUERY')); 93 $objQueue->getState()->get('QUERY')->update(array('PDOStatement' => $objPDO)); 94 } 95 96 # copy reference of prepared statement into queue for execution 97 $objQueue->getState()->update(array('PDOStatement' => $objQueue->getState()->get('QUERY')->get('PDOStatement'))); 98 99}; 100 101$objQueue->addHandler(QUEUE_PREPARE_QUERY_POSITION, $cloPrepareQuery); 102 103######################### 104### execute the query ### 105######################### 106 107# handler, which maps the data-type of a variable to the PDO-constants 108 109$cloMapDataType = function($mixedParameter) { 110 111 $arrDataTypeMap = array('NULL' => \PDO::PARAM_NULL, 112 'boolean' => \PDO::PARAM_BOOL, 113 'integer' => \PDO::PARAM_INT, 114 'string' => \PDO::PARAM_STR); 115 116 $strDataType = gettype($mixedParameter); 117 118 if(!isset($arrDataTypeMap[$strDataType])) 119 throw new \Exception ("could not bind parameters data type - type is not supported by PDO: $strDataType"); 120 121 return $arrDataTypeMap[$strDataType]; 122 123}; 124 125# bind the given parameter to the prepared statement, 126# then set the fetch mode and execute the query 127 128$cloQueryExcecute = function(\DDDBL\Queue $objQueue, array $arrParameter) use ($cloMapDataType) { 129 130 $objPDO = $objQueue->getState()->get('PDOStatement'); 131 132 # remove the alias from the parameter list 133 array_shift($arrParameter); 134 135 $objQuery = $objQueue->getState()->get('QUERY'); 136 137 if(true === $objQuery->get('BIND-DATA-TYPE')) { 138 139 foreach($arrParameter AS $intIndex => $mixedParameter) 140 $objPDO->bindValue($intIndex + 1, $mixedParameter, $cloMapDataType($mixedParameter)); 141 142 } else { 143 144 foreach($arrParameter AS $intIndex => $mixedParameter) 145 $objPDO->bindValue($intIndex + 1, $mixedParameter); 146 147 } 148 149 $objPDO->setFetchMode(\PDO::FETCH_ASSOC); 150 151 # execute the query. if execution fails, throw an exception 152 if(!$objPDO->execute()) 153 throw new QueryException($objPDO, $objQuery->getAll()); 154 155}; 156 157$objQueue->addHandler(QUEUE_EXECUTE_QUERY_POSITION, $cloQueryExcecute); 158 159############################### 160### format the query result ### 161############################### 162 163# if a result-handler for the query is configured, call it 164 165$cloFormatQueryResult = function(\DDDBL\Queue $objQueue, array $arrParameter) { 166 167 $objQuery = $objQueue->getState()->get('QUERY'); 168 169 if(!$objQuery->exists('HANDLER')) 170 return ; 171 172 # get the handler and its config 173 $strHandlerConfig = $objQuery->get('HANDLER'); 174 $arrHandlerConfig = preg_split('/\s+/', $strHandlerConfig); 175 $strHandler = array_shift($arrHandlerConfig); 176 177 # remove handler-name from config 178 $strHandlerConfig = trim(str_replace($strHandler, '', $strHandlerConfig)); 179 180 $objDataObjectPool = new DataObjectPool('Result-Handler'); 181 182 if(!$objDataObjectPool->exists($strHandler)) 183 throw new \Exception ("unknown result-handler: $strHandler"); 184 185 $objHandler = $objDataObjectPool->get($strHandler); 186 $cloHandler = $objHandler->get('HANDLER'); 187 188 $cloHandler($objQueue, $strHandlerConfig); 189 190}; 191 192$objQueue->addHandler(QUEUE_FORMAT_RESULT_POSITION, $cloFormatQueryResult); 193 194#################### 195### close cursor ### 196#################### 197 198# closing the cursor of the PDOStatement. this will free 199# the result and enable the connection to execute the next query 200 201$cloCloseCursor = function(\DDDBL\Queue $objQueue, array $arrParameter) { 202 203 $objQueryResult = $objQueue->getState()->get('PDOStatement'); 204 $objQueryResult->closeCursor(); 205 206}; 207 208$objQueue->addHandler(QUEUE_CLOSE_CURSOR_POSITION, $cloCloseCursor); 209