_resources[$name])) { $class = implode('_', array( $this->_getNamespace(), 'Model_Resources', ucfirst($name))); //Controllo l'esistenza della classe if (!class_exists($class)) { throw new App_Controller_Errors_WebServiceError("Errore generazione la classe risorsa '$class' potrebbe non esistere"); } $this->_resources[$name] = new $class(); } return $this->_resources[$name]; } private function _getNamespace() { $ns = explode('_', get_class($this)); return $ns[0]; } /*==================================================================================================== *======================= FUNZIONI GENERICHE PER OGNI TABELLA ========================== *====================================================================================================*/ /** * @param $resourceName * @param $info * @return mixed * @throws App_Controller_Errors_WebServiceError */ public function insert($resourceName, $info) { return $this->getResource($resourceName)->insert($info); } public function update($resourceName, $id, $info) { $resource = $this->getResource($resourceName); $idString = (is_int($id)) ? " = $id" : " = '$id'"; return $resource->update($info, $resource->getPrimaryKey() . $idString); } public function updateWhere($resourceName, $condition, $info) { //Se passo un array di condizioni viene construita la stringa if (is_array($condition)) { $last_key = key(array_slice($condition, -1, 1, TRUE)); $str = ""; foreach ($condition as $key => $val) { $str .= str_replace('?', $val, $key); if ($key != $last_key) $str .= " AND "; } $condition = $str; } $resource = $this->getResource($resourceName); return $resource->update($info, $condition); } public function delete($resourceName, $id) { $resource = $this->getResource($resourceName); $idString = (is_int($id)) ? " = $id" : " = '$id'"; return $resource->delete($resource->getPrimaryKey() . $idString); } public function deleteWhere($resourceName, $condition) { //Se passo un array di condizioni viene construita la stringa if (is_array($condition)) { $last_key = key(array_slice($condition, -1, 1, TRUE)); $str = ""; foreach ($condition as $key => $val) { $str .= str_replace('?', $val, $key); if ($key != $last_key) $str .= " AND "; } $condition = $str; } $resource = $this->getResource($resourceName); return $resource->delete($condition); } public function getById($resourceName, $id) { $resource = $this->getResource($resourceName); return $resource->getAdapter()->query('SELECT * FROM ' . $resource->getTableName() . ' WHERE ' . $resource->getPrimaryKey() . ' = ?', array($id))->fetch(); } public function getLastId($resourceName) { $resource = $this->getResource($resourceName); return $resource->getAdapter()->query('SELECT id FROM ' . $resource->getTableName() . ' ORDER BY ' . $resource->getPrimaryKey() . ' DESC LIMIT 1')->fetchColumn(0); } public function getCountTotal($resourceName) { $resource = $this->getResource($resourceName); return $resource->getAdapter()->query('SELECT COUNT(*) as num FROM ' . $resource->getTableName())->fetchColumn(0); } // FUNZIONE GET LIST CON OVERLOAD public function getList() { $args = func_get_args(); $functionName = (func_num_args() === 2 && is_array($args[1])) ? 'getListOptions' : 'getListDefault'; return call_user_func_array(array(&$this, $functionName), $args); } /** * #Overload * Funzione get list che accetta i parametri inseriti in un array in modo da non dover più rispettare l'ordine di inserimento * * @param $resourceName * @param array $options * @return Zend_Paginator * @throws Zend_Exception * @throws Zend_Paginator_Exception */ public function getListOptions($resourceName, array $options = []) { foreach ($options as $optionKey => $val) { if (!in_array($optionKey, self::ALLOWED_GETLIST_ARRAY_OPTIONS)) { throw new App_Controller_Errors_WebServiceError("'$optionKey' non e' una opzione valida per la funzione getList()"); } } return $this->getListDefault($resourceName, $options['page'], $options['count'], $options['where'], $options['order'], $options['selectList'], $options['joinOptions'], $options['groupBy'], $options['fetchRow'], $options['having']); } /** * Funzione getList completa (può sostituire anche la funzione getFilteredList) * * @param $resourceName * @param null $paged * @param null $count * @param array $where * @param null $order * @param string $selectList * @param null $joinData * @param null $groupBy * @param bool $fetchRow * @return Zend_Paginator * @throws Zend_Exception * @throws Zend_Paginator_Exception */ public function getListDefault($resourceName, $paged = null, $count = null, $where = array(), $order = null, $selectList = '*', $joinData = null, $groupBy = null, $fetchRow = false, $having = false) { $resource = $this->getResource($resourceName); // definizione della select list $selectList = (!is_null($selectList)) ? $selectList : $resource->getDefaultSelectColumns(); if (is_string($selectList)) { $selectList = explode(',', $selectList); } $select = $resource->getAdapter()->select()->from($resource->getTableName(), $selectList); //Gestione dell'eventuale Join $joinData = (!is_null($joinData)) ? $joinData : $resource->getDefaultJoinData(); if (is_array($joinData)) { $select = $this->applicateJoinData($select, $joinData); } //gestione dei parametri di ricerca if (is_array($where)) { foreach ($where as $key => $value) { // se trovo l'operatore '#OR' o '#ANDOR' significa che devo applicare l'or per gli elementi passati nel campo value, NB: il value deve essere una string separata da virgole if (preg_match("/#OR/", $key)) { // #ANDOR accoda la query es: WHERE ... OR (nome_campo = ?) $select = $this->applicateOrWhere($select, $key, $value, '#OR'); } else if (preg_match("/#ANDOR/", $key)) { // #ANDOR compone la query es: WHERE ... AND ( campo1 = ? OR campo2 = ?) //salvo le condizioni presenti e resetto temporaneamente le condizini $oldWhereConditions = $select->getPart(Zend_Db_Select::WHERE); $select->reset(Zend_Db_Select::WHERE); // genero le condizioni or $select = $this->applicateOrWhere($select, $key, $value, '#ANDOR'); // recupero le condizioni or generate e resetto di nuovo tutte le condizioni $orWhereConditions = $select->getPart(Zend_Db_Select::WHERE); $select->reset(Zend_Db_Select::WHERE); // reimposto le vecchie condizioni e accodo le nuove condizioni or if ($oldWhereConditions) $select->where(implode(' ', $oldWhereConditions)); $select->where(implode(' ', $orWhereConditions)); } else { //Di default utilizzo where con la AND $select->where($key, $value); } } } //Gestione dell'eventuale grouBy if ($groupBy) { $select->group($groupBy); } //gestione dell'ordinamento $order = (!$order) ? $resource->getDefaultOrder() : $order; if (is_string($order)) { $tmpOrder = explode(',', $order); foreach ($tmpOrder as &$ord) { // il '.' serve a definire il nome della tabella altrimenti imposto quella di default della risorsa che chiama la query if (!preg_match("/\./", $ord)) { $ord = $resource->getTableName() . "." . trim($ord); } // Se non esiste un verso di ordinamento assegno quello di default della risorsa per ogni campo ordinamento passato if (!preg_match("/(ASC|DESC|desc|asc)$/", $ord)) { $ord = explode(' ', trim($ord))[0] . ' ' . strtoupper($resource->getDefaultTipoOrder()); } } $order = $tmpOrder; } $select->order($order); //Gestione dell'eventuale grouBy if ($having && is_array($having)) { foreach (array_keys($having) as $key) { $select->having($key, $having[$key]); } } // Zend_Registry::get('log')->info(print_r($select->__toString(), true)); //Esecuzione della query di ricerca if (null !== $paged && null !== $count) { $adapter = new Zend_Paginator_Adapter_DbSelect($select); $paginator = new Zend_Paginator($adapter); $paginator->setItemCountPerPage($count)->setCurrentPageNumber((int)$paged); return $paginator; } $stmt = $resource->getAdapter()->query($select->__toString()); //Gestione del Fetch if ($fetchRow) return $stmt->fetch(); else return $stmt->fetchAll(); } /** * @param $resourceName * @param $where * @param null $order * @param null $selectList * @param null $joinData * @param null $groupBy * @return Zend_Paginator * @throws Zend_Exception * @throws Zend_Paginator_Exception */ public function getFiltered($resourceName, $where, $order = null, $selectList = null, $joinData = null, $groupBy = null) { return $this->getList($resourceName, null, null, $where, $order, $selectList, $joinData, $groupBy, true); } /** * Con questa funzione posso recuperare il numero di elementi di una tabella in base a parametri * @param $resourceName * @param $where * * @return Zend_Paginator */ public function countFiltered($resourceName, $where) { //Definizione della risorsa $resource = $this->getResource($resourceName); $select = $resource->getAdapter()->select()->from($resource->getTableName(), 'COUNT(*) as num'); //Applico le eventuali condizioni di ricerca foreach ($where as $key => $value) { $select->where($key, $value); } $stmt = $resource->getAdapter()->query($select->__toString()); return $stmt->fetchColumn(0); } /** * Questa funzione passato il nome della colonna su cui cercare cerca il valore scelto; * l'operatore di default è 'uguale' * altriemnti è possibile specificarne un altro trimete il parametro @op * * @param $resourceName * @param $columnName * @param $value * @param $fetchRow | Se impostato a true ritorna la riga come oggetto * @param $op * @param $joinData | per eseguire un join con altre tabelle * * @return mixed */ public function getByColumnName($resourceName, $columnName, $value, $op = "=", $fetchRow = false, $order = null, $joinData = null) { $resource = $this->getResource($resourceName); //GESTIONE OPERATORI switch ($op) { case'LIKE': $value = "%" . $value . "%"; break; case'LIKEPRE': $value = "%" . $value; break; case'LIKEPOST': $value = $value . "%"; break; default: break; } $select = $resource->getAdapter()->select()->from($resource->getTableName()); //Gestione dell'eventuale Join if (is_array($joinData)) { $select = $this->applicateJoinData($select, $joinData); } $select->where($columnName . ' ' . $op . ' ?', $value); if ($order != null && (is_array($order) || is_string($order))) { $select->order($order); } if ($fetchRow) { if ($order != null && (is_array($order) || is_string($order))) { return $resource->fetchRow($resource->select()->where($columnName . ' ' . $op . ' ?', $value)->order($order)); } else { return $resource->fetchRow($resource->select()->where($columnName . ' ' . $op . ' ?', $value)); } } else { return $resource->getAdapter()->query($select->__toString())->fetch(); } } /** * @param $query * @param null $params * @param bool $fetchRow * @return mixed * * @throws App_Controller_Errors_WebServiceError */ public function customQuery($query, $params = null, $fetchRow = false) { $resource = $this->getResource('Abstract'); $stmt = $resource->getAdapter()->query($query, $params); //Gestione del Fetch if ($fetchRow) return $stmt->fetch(); else return $stmt->fetchAll(); } /** * @param $select * @param $joinData * @return mixed * * @throws App_Controller_Errors_WebServiceError */ private function applicateJoinData($select, $joinData) { if (!isset($joinData[0])) { if (!array_key_exists(self::JOIN_TABLE_NAME, $joinData)) throw new App_Controller_Errors_WebServiceError("Nome tabella per il join non trovato"); if (!array_key_exists(self::JOIN_CONDITION_NAME, $joinData)) throw new App_Controller_Errors_WebServiceError("Nome del campo di condizione per il join non trovato"); $colonne = (!$joinData[self::JOIN_COLUMNS_NAME]) ? array('*') : $joinData[self::JOIN_COLUMNS_NAME]; $joinFunctionName = (in_array($joinData[self::JOIN_TYPE], self::JOIN_FUNCTION_NAME_ALLOWED)) ? $joinData[self::JOIN_TYPE] : 'join'; return $select->$joinFunctionName($joinData[self::JOIN_TABLE_NAME], $joinData[self::JOIN_CONDITION_NAME], $colonne); } else { // Gestione di più join contemporanei foreach ($joinData as $key => $join) { if (!array_key_exists(self::JOIN_TABLE_NAME, $join)) throw new App_Controller_Errors_WebServiceError("Nome tabella per il join non trovato per il join index: [$key]"); if (!array_key_exists(self::JOIN_CONDITION_NAME, $join)) throw new App_Controller_Errors_WebServiceError("Nome del campo di condizione per il join non trovato per il join index: [$key]"); $colonne = (!$join[self::JOIN_COLUMNS_NAME]) ? array('*') : $join[self::JOIN_COLUMNS_NAME]; $joinFunctionName = (in_array($join[self::JOIN_TYPE], self::JOIN_FUNCTION_NAME_ALLOWED)) ? $join[self::JOIN_TYPE] : 'join'; $select->$joinFunctionName($join[self::JOIN_TABLE_NAME], $join[self::JOIN_CONDITION_NAME], $colonne); } return $select; } } private function applicateOrWhere($select, string $keyNomeCampo, $valoriOr, string $op = '#OR') { $valueOrDaApplicare = null; if (is_string($valoriOr)) $valueOrDaApplicare = explode(',', $valoriOr); elseif (is_array($valoriOr)) $valueOrDaApplicare = $valoriOr; if (!$valueOrDaApplicare) { throw new App_Controller_Errors_WebServiceError("Valori per la condizione '$op' non validi per generare la query", App_Controller_Errors_WebServiceError::WEBSERVICE_GENERIC_ERROR); } $keyDaApplicare = str_replace($op, '=', $keyNomeCampo); if (is_array($valueOrDaApplicare) && count($valueOrDaApplicare) > 0) { foreach ($valueOrDaApplicare as $val) { $select->orwhere($keyDaApplicare, $val); } } return $select; } }