/** * Sets the constraints for QB for articles, supports article links etc.. * * @param midgard_query_builder $qb reference to the QB object * @param array $data reference to the request_data array */ public static function article_qb_constraints(&$qb, &$data, $handler_id) { $config =& $data['config']; // GUIDs of topics to list articles from. $guids_array = array(); $guids_array[] = $data['content_topic']->guid; // Resolve any other topics we may need $list_from_folders = $config->get('list_from_folders'); if ($list_from_folders) { // We have specific folders to list from, therefore list from them and current node $guids = explode('|', $config->get('list_from_folders')); foreach ($guids as $guid) { if (!$guid || !mgd_is_guid($guid)) { // Skip empty and broken guids continue; } $guids_array[] = $guid; } } /** * Ref #1776, expands GUIDs before adding them as constraints, should save query time */ $topic_ids = array(); $topic_ids[] = $data['content_topic']->id; if (!empty($guids_array)) { $mc = midcom_db_topic::new_collector('metadata.deleted', false); $mc->add_constraint('guid', 'IN', $guids_array); $topic_ids = $mc->get_values('id'); unset($mc); } // Include the article links to the indexes if enabled if ($config->get('enable_article_links')) { $mc = net_nehmer_blog_link_dba::new_collector('topic', $data['content_topic']->id); $mc->add_constraint('topic', '=', $data['content_topic']->id); $mc->add_order('metadata.published', 'DESC'); $mc->set_limit((int) $config->get('index_entries')); // Get the results $mc->execute(); $links = $mc->get_values('article'); $qb->begin_group('OR'); $qb->add_constraint('id', 'IN', $links); $qb->add_constraint('topic', 'IN', $topic_ids); $qb->end_group(); } else { $qb->add_constraint('topic', 'IN', $topic_ids); } if (count($topic_ids) > 1 && ($list_from_folders_categories = $config->get('list_from_folders_categories'))) { // TODO: check schema storage to get fieldname $multiple_categories = true; if (isset($data['schemadb']['default']) && isset($data['schemadb']['default']->fields['list_from_folders_categories']) && array_key_exists('allow_multiple', $data['schemadb']['default']->fields['list_from_folders_categories']['type_config']) && !$data['schemadb']['default']->fields['list_from_folders_categories']['type_config']['allow_multiple']) { $multiple_categories = false; } debug_add("multiple_categories={$multiple_categories}"); $qb->begin_group('OR'); $list_from_folders_categories = explode(',', $list_from_folders_categories); $is_content_topic = true; foreach ($topic_ids as $topic_id) { if ($is_content_topic) { $qb->add_constraint('topic', '=', $topic_id); $is_content_topic = false; continue; } $qb->begin_group('AND'); $qb->add_constraint('topic', '=', $topic_id); $qb->begin_group('OR'); foreach ($list_from_folders_categories as $category) { if ($category = trim($category)) { if ($multiple_categories) { $qb->add_constraint('extra1', 'LIKE', "%|{$category}|%"); } else { $qb->add_constraint('extra1', '=', $category); } } } $qb->end_group(); $qb->end_group(); } $qb->end_group(); } // Hide the articles that have the publish time in the future and if // the user is not administrator if ($config->get('enable_scheduled_publishing') && !midcom::get('auth')->admin) { // Show the article only if the publishing time has passed or the viewer // is the author $qb->begin_group('OR'); $qb->add_constraint('metadata.published', '<', gmdate('Y-m-d H:i:s')); if (midcom::get('auth')->user && isset(midcom::get('auth')->user->guid)) { $qb->add_constraint('metadata.authors', 'LIKE', '|' . midcom::get('auth')->user->guid . '|'); } $qb->end_group(); } $qb->add_constraint('up', '=', 0); }
/** * Helper for fetching enough of articles * * @param int $topic_id ID of the content topic * @param int $offset Offset for the query * @param int $limit How many results should be returned * @param array &$results Result set * @return Array Containing results */ private static function _get_linked_articles($topic_id, $offset, $limit, &$results) { $mc = net_nehmer_blog_link_dba::new_collector('topic', $topic_id); $mc->add_constraint('topic', '=', $topic_id); $mc->add_order('metadata.published', 'DESC'); $mc->set_offset($offset); // Double the limit, a sophisticated guess that there might be missing articles // and this should include enough of articles for us $mc->set_limit($limit * 2); // Get the results $links = $mc->add_value_property('article'); // Return the empty result set if (empty($links)) { return $results; } $i = 0; foreach ($links as $id) { try { $article = new midcom_db_article($id); } catch (midcom_error $e) { // If the article was not found, it is probably due to ACL $e->log(); continue; } $results[$id] = $article; $i++; // Break when we have enough of articles if ($i >= $limit) { break; } } // Quit the function if there is no possibility for more matches if (count($links) < $limit) { return $results; } // Push the offset $offset = $offset + $limit; self::_get_linked_articles($topic_id, $offset, $limit, $results); }