/** * Turn any of the acceptable query shorthands into a full * Horde_Rdo_Query object. If you pass an existing Horde_Rdo_Query * object in, it will be cloned before it's returned so that it * can be safely modified. * * @param mixed $query The query to convert to an object. * @param Horde_Rdo_Mapper $mapper The Mapper object governing this query. * * @return Horde_Rdo_Query The full Horde_Rdo_Query object. */ public static function create($query, $mapper = null) { if ($query instanceof Horde_Rdo_Query || $query instanceof Horde_Rdo_Query_Literal) { $query = clone $query; if (!is_null($mapper)) { $query->setMapper($mapper); } return $query; } $q = new Horde_Rdo_Query($mapper); if (is_scalar($query)) { $q->addTest($mapper->tableDefinition->getPrimaryKey(), '=', $query); } elseif ($query) { $q->combineWith('AND'); foreach ($query as $key => $value) { $q->addTest($key, '=', $value); } } return $q; }
/** * find() can be called in several ways. * * Primary key mode: pass find() a numerically indexed array of primary * keys, and it will return a list of the objects that correspond to those * keys. * * If you pass find() no arguments, all objects of this type will be * returned. * * If you pass find() an associative array, it will be turned into a * Horde_Rdo_Query object. * * If you pass find() a Horde_Rdo_Query, it will return a list of all * objects matching that query. */ public function find($arg = null) { if (is_null($arg)) { $query = null; } elseif (is_array($arg)) { if (!count($arg)) { throw new Horde_Rdo_Exception('No criteria found'); } if (is_numeric(key($arg))) { // Numerically indexed arrays are assumed to be an array of // primary keys. $query = new Horde_Rdo_Query(); $query->combineWith('OR'); foreach ($argv[0] as $id) { $query->addTest($this->primaryKey, '=', $id); } } else { $query = $arg; } } else { $query = $arg; } // Build a full Query object. $query = Horde_Rdo_Query::create($query, $this); return new Horde_Rdo_List($query); }
/** * Inventory search * @param array filters a list of filter hashes, each having keys * string type ('note', 'stock_name', 'stock_id', 'categories', 'values') * string test * boolean exact (only search for full words, default to null) * mixed value (string for note, stock_name) * For the 'values' structure, value, value is a map of [values] and optional [property]} * @return array List of Stock items */ public function findStock($filters = array()) { $sm = $this->_mappers->create('Sesha_Entity_StockMapper'); if (empty($filters)) { return iterator_to_array($sm->find()); } $query = new Horde_Rdo_Query($sm); $query->combineWith('OR'); foreach ($filters as $filter) { switch ($filter['type']) { case 'note': case 'stock_name': case 'stock_id': $filter_values = is_array($filter['value']) ? $filter['value'] : array($filter['value']); $filter_test = empty($filter['test']) ? 'LIKE' : $filter['test']; $filter_field = $filter['type']; if ($filter_field == 'stock_id') { $filter_test = '='; } foreach ($filter_values as $filter_value) { if (strlen($filter_value)) { if ($filter_test == 'LIKE' && empty($filter['exact'])) { $filter_value = '%' . $filter_value . '%'; } $query->addTest($filter_field, $filter_test, $filter_value); } } break; case 'categories': $cm = $this->_mappers->create('Sesha_Entity_CategoryMapper'); $categories = is_array($filter['value']) ? $filter['value'] : array($filter['value']); $items = array(); foreach ($categories as $category) { if ($category instanceof Sesha_Entity_Category) { $category_id = $category->category_id; } else { $category_id = $category; $category = $cm->findOne($category_id); } foreach ($category->stock as $item) { /* prevent duplicates when an item has several * categories */ $items[$item->stock_id] = $item; } } if (count($filters == 1)) { return $items; } $query->addTest('stock_id', $filter['test'] ? $filter['test'] : 'IN', array_keys($items)); break; case 'values': $vm = $this->_mappers->create('Sesha_Entity_ValueMapper'); $items = array(); foreach ($filter['value'] as $propTest) { $values = is_array($propTest['values']) ? $propTest['values'] : array($propTest['values']); // Find all Value objects which match any of the $value[values] foreach ($values as $filter_value) { $valueQuery = new Horde_Rdo_Query($vm); if ($propTest['property']) { $valueQuery->addTest('property_id', '=', $propTest['property']); } if (empty($filter['exact'])) { $filter_value = '%' . $filter_value . '%'; } $valueQuery->addTest('txt_datavalue', 'LIKE', $filter_value); foreach ($vm->find($valueQuery) as $value) { // prevent doubles $items[$value->stock_id] = $value->stock; } } } if (count($filters == 1)) { return $items; } $query->addTest('stock_id', $filter['test'] ? $filter['test'] : 'IN', array_keys($items)); break; } } return iterator_to_array($sm->find($query)); }