public static function executeDynamicPlaylist($partner_id, $xml, $filter = null, $detailed = true, $pager = null) { list($total_results, $list_of_filters) = self::getPlaylistFilterListStruct($xml); $entry_filters = array(); if (!$list_of_filters) { return null; } // TODO - for now we assume that there are more or equal filters in the XML than the ones from the request $filterLimit = null; if ($filter && $filter->getLimit() > 0) { $filterLimit = $filter->getLimit(); // Get the max results from the limit of the first filter $total_results = min($total_results, $filterLimit); // Clear this limit so it won't overcloud the limits of $entry_filter_xml rules $filter->setLimit(null); } $numFiltersInList = count($list_of_filters); for ($i = 0; $i < $numFiltersInList; $i++) { $entry_filter_xml = $list_of_filters[$i]; /* @var $entry_filter_xml SimpleXMLElement */ // in general this service can fetch entries from kaltura networks. // for each filter we should decide if thie assumption is true... $allow_partner_only = true; self::replaceContextTokens($entry_filter_xml); // compile all the filters - only then execute them if not yet reached the total_results // TODO - optimize - maybe create them only when needed. - For now it's safer to compile all even if not needed. $entry_filter = new entryFilter(); // add the desired prefix "_" because the XML is not expected to have it while the entryFilter class expects it $entry_filter->fillObjectFromXml($entry_filter_xml, "_"); // make sure there is alway a limit for each filter - if not an explicit one - the system limit should be used if ($entry_filter->getLimit() == null || $entry_filter->getLimit() < 1) { $entry_filter->setLimit(self::TOTAL_RESULTS); } // merge the current_filter with the correcponding extra_filter // allow the extra_filter to override properties of the current filter if ($filter) { if ($filterLimit && $i == $numFiltersInList - 1) { // Hack (in order to preserve old behavior): // If the filter contained a limit, we'll add it to the last XML filter on the list // in order to make sure the number of requested ($limit) entries will be supplied. // This handles requests of a $limit which is higher than the total sum of inner XML filter limits. $filter->setLimit($filterLimit); } $entry_filter->fillObjectFromObject($filter, myBaseObject::CLONE_FIELD_POLICY_THIS, myBaseObject::CLONE_POLICY_PREFER_NEW, null, null, false); $entry_filter->setPartnerSearchScope(baseObjectFilter::MATCH_KALTURA_NETWORK_AND_PRIVATE); } self::updateEntryFilter($entry_filter, $partner_id, true); $entry_filters[] = $entry_filter; } if ($pager) { $startOffset = $pager->calcOffset(); $pageSize = $pager->calcPageSize(); if ($startOffset > $total_results) { return array(); } $total_results = min($total_results, $startOffset + $pageSize); } $entry_ids_list = array(); foreach ($entry_filters as $entry_filter) { $current_limit = max(0, $total_results - count($entry_ids_list)); // if the current_limit is < 0 - set it to be 0 // no need to fetch any more results if ($current_limit <= 0) { break; } $c = KalturaCriteria::create(entryPeer::OM_CLASS); // don't fetch the same entries twice - filter out all the entries that were already fetched if ($entry_ids_list) { $c->add(entryPeer::ID, $entry_ids_list, Criteria::NOT_IN); } $filter_limit = $entry_filter->getLimit(); if ($filter_limit > $current_limit) { // set a smaller limit incase the filter's limit is to high $entry_filter->setLimit($current_limit); } // read the _eq_display_in_search field but ignore it because it's part of a more complex criterion $display_in_search = $entry_filter->get("_eq_display_in_search"); if ($display_in_search >= 2) { $entry_filter->set("_eq_display_in_search", null); } $entry_filter->attachToCriteria($c); // add some hard-coded criteria $c->addAnd(entryPeer::TYPE, array(entryType::MEDIA_CLIP, entryType::MIX, entryType::LIVE_STREAM), Criteria::IN); // search only for clips or roughcuts $c->addAnd(entryPeer::STATUS, entryStatus::READY); // search only for READY entries $c->addAnd(entryPeer::DISPLAY_IN_SEARCH, mySearchUtils::DISPLAY_IN_SEARCH_SYSTEM, Criteria::NOT_EQUAL); if ($display_in_search >= 2) { // We don't allow searching in the KalturaNEtwork anymore (mainly for performance reasons) // allow only assets for the partner $c->addAnd(entryPeer::PARTNER_ID, $partner_id); // /* $crit = $c->getNewCriterion ( entryPeer::PARTNER_ID , $partner_id ); $crit->addOr ( $c->getNewCriterion ( entryPeer::DISPLAY_IN_SEARCH , $display_in_search ) ); $c->addAnd ( $crit ); */ } if (!self::$isAdminKs) { self::addSchedulingToCriteria($c); } self::addModerationToCriteria($c); $c = entryPeer::prepareEntitlementCriteriaAndFilters($c); $entry_ids_list_for_filter = $c->getFetchedIds(); // update total count and merge current result with the global list $entry_ids_list = array_merge($entry_ids_list, $entry_ids_list_for_filter); } if ($pager) { // Keep the paged entries only $entry_ids_list = array_slice($entry_ids_list, $startOffset, $pageSize); } // Disable entitlement, which was already applied in entryPeer::prepareEntitlementCriteriaAndFilters() // otherwise we will hit the 150 entries limit from SphinxCriterion KalturaCriterion::disableTag(KalturaCriterion::TAG_ENTITLEMENT_ENTRY); $db_entry_list = entryPeer::retrieveByPKs($entry_ids_list); KalturaCriterion::restoreTag(KalturaCriterion::TAG_ENTITLEMENT_ENTRY); // Map the entries to their IDs $entry_map = array(); foreach ($db_entry_list as $entry) { $entry_map[$entry->getId()] = $entry; } // Build entry_list according to the playlist order $entry_list = array(); foreach ($entry_ids_list as $entryId) { $entry_list[] = $entry_map[$entryId]; } return $entry_list; }
public static function executeDynamicPlaylist($partner_id, $xml, $extra_filters = null, $detailed = true) { list($total_results, $list_of_filters) = self::getPlaylistFilterListStruct($xml); $entry_filters = array(); if (!$list_of_filters) { return null; } // TODO - for now we assume that there are more or equal filters in the XML than the ones from the request $i = 1; // the extra_filter is 1-based foreach ($list_of_filters as $entry_filter_xml) { // in general this service can fetch entries from kaltura networks. // for each filter we should decide if thie assumption is true... $allow_partner_only = true; // compile all the filters - only then execute them if not yet reached the total_results // TODO - optimize - maybe create them only when needed. - For now it's safer to compile all even if not needed. $entry_filter = new entryFilter(); // add the desired prefix "_" because the XML is not expected to have it while the entryFilter class expects it $entry_filter->fillObjectFromXml($entry_filter_xml, "_"); // make sure there is alway a limit for each filter - if not an explicit one - the system limit should be used if ($entry_filter->getLimit() == null || $entry_filter->getLimit() < 1) { $entry_filter->setLimit(self::TOTAL_RESULTS); } $extra_filter = @$extra_filters[$i]; // merge the current_filter with the correcponding extra_filter // allow the extra_filter to override properties of the current filter if ($extra_filter) { $entry_filter->fillObjectFromObject($extra_filter, myBaseObject::CLONE_FIELD_POLICY_THIS, myBaseObject::CLONE_POLICY_PREFER_NEW, null, null, false); $entry_filter->setPartnerSearchScope(baseObjectFilter::MATCH_KALTURA_NETWORK_AND_PRIVATE); } self::updateEntryFilter($entry_filter, $partner_id, true); $entry_filters[] = $entry_filter; $i++; } $number_of_entries = 0; $entry_list = array(); $i = 1; foreach ($entry_filters as $entry_filter) { $current_limit = max(0, $total_results - $number_of_entries); // if the current_limit is < 0 - set it to be 0 $exclude_id_list = self::getIds($entry_list); $c = KalturaCriteria::create(entryPeer::OM_CLASS); // don't fetch the same entries twice - filter out all the entries that were already fetched if ($exclude_id_list) { $c->add(entryPeer::ID, $exclude_id_list, Criteria::NOT_IN); } // no need to fetch any more results if ($current_limit <= 0) { break; } $filter_limit = $entry_filter->getLimit(); if ($filter_limit > $current_limit) { // set a smaller limit incase the filter's limit is to high $entry_filter->setLimit($current_limit); } // read the _eq_display_in_search field but ignore it because it's part of a more complex criterion $display_in_search = $entry_filter->get("_eq_display_in_search"); if ($display_in_search >= 2) { $entry_filter->set("_eq_display_in_search", null); } $entry_filter->attachToCriteria($c); // add some hard-coded criteria $c->addAnd(entryPeer::TYPE, array(entryType::MEDIA_CLIP, entryType::MIX, entryType::LIVE_STREAM), Criteria::IN); // search only for clips or roughcuts $c->addAnd(entryPeer::STATUS, entryStatus::READY); // search only for READY entries $c->addAnd(entryPeer::DISPLAY_IN_SEARCH, mySearchUtils::DISPLAY_IN_SEARCH_SYSTEM, Criteria::NOT_EQUAL); if ($display_in_search >= 2) { // We don't allow searching in the KalturaNEtwork anymore (mainly for performance reasons) // allow only assets for the partner $c->addAnd(entryPeer::PARTNER_ID, $partner_id); // /* $crit = $c->getNewCriterion ( entryPeer::PARTNER_ID , $partner_id ); $crit->addOr ( $c->getNewCriterion ( entryPeer::DISPLAY_IN_SEARCH , $display_in_search ) ); $c->addAnd ( $crit ); */ } if (!self::$isAdminKs) { self::addSchedulingToCriteria($c); } self::addModerationToCriteria($c); KalturaCriterion::disableTag(KalturaCriterion::TAG_WIDGET_SESSION); if ($detailed) { $entry_list_for_filter = entryPeer::doSelectJoinkuser($c); } else { $entry_list_for_filter = entryPeer::doSelect($c); } // maybe join with kuser to add some data about the contributor KalturaCriterion::restoreTag(KalturaCriterion::TAG_WIDGET_SESSION); // update total count and merge current result with the global list $number_of_entries += count($entry_list_for_filter); $entry_list = array_merge($entry_list, $entry_list_for_filter); } return $entry_list; }