/** returns start sample and length of sample for given featurevectorsegment * */ public static function getInformationOnSegment($track_id, $segmentnr, $featurevectortypeid) { // get id from file by uri $crit = new Criteria(); $crit->add(FeaturevectorsegmentPeer::TRACK_ID, $track_id); $crit->add(FeaturevectorsegmentPeer::SEGMENTNR, $segmentnr); $crit->add(FeaturevectorsegmentPeer::FEATUREVECTORTYPE_ID, $featurevectortypeid); $fvsegm = FeaturevectorsegmentPeer::doSelectOne($crit); return $fvsegm; }
/** Action that is called if file has been uploaded (metadata may have been entered) * */ public function executeRelated(sfWebRequest $request) { try { // Load helpers $this->getContext()->getConfiguration()->loadHelpers('Asset'); $this->getContext()->getConfiguration()->loadHelpers('Url'); // get config $configFeaturevectortypeid = sfConfig::get('app_defaults_featurevectortypeid', 0); // get request params $reqparamtracknr = $request->getParameter('tracknr'); $filename = $request->getParameter('uploadedFilename'); $originalFilename = $request->getParameter('originalFilename'); $metadataquery = $request->getParameter('metadataquery'); // 2 possibilities: either tracknr is given or uploadedFilename if (isset($reqparamtracknr) && $reqparamtracknr != '' && $reqparamtracknr != 'undefined') { //get file via external key $tracknr = $reqparamtracknr; $fileForSearchSimilar = FilePeer::getFileByExternalKey($tracknr); //only if the file was found in the smafestore db if ($fileForSearchSimilar) { $originalFilename = $fileForSearchSimilar->getUri(); $filesavepath = $fileForSearchSimilar->getUri(); } else { throw new Exception("Could not find file in database with external_key: {$tracknr}"); } $bUploadedFile = false; } else { $originalFilename = $request->getParameter('originalFilename'); $filesavepath = smintUploadFileHelper::getUploadPath() . $filename; $bUploadedFile = true; } // variables about segment selection //$reqparamStartSegment = '10000'; // Start of segment in ms MOCKUP 10 to 20 seconds //$reqparamEndSegment = '20000'; // end of segment in ms MOCKUP $reqparamStartSegment = $request->getParameter('segmentStart'); // Start of segment in ms $reqparamEndSegment = $request->getParameter('segmentEnd'); $reqparamDuration = $request->getParameter('duration'); // end of segment in ms $aSegmSearch = array('enabled' => false, 'startSegment' => 0, 'endSegment' => 0); //$bSegmSearch = FALSE; // boolean: is this segmented search? To be set later. //$startSegment; // int value, to be set later //$endSegment; // int value, to be set later $empty_livequery = false; $empty_metadatafilteredquery = false; $omit_empty_metadataquery = $request->getParameter('omit_empty_metadataquery', false); ///// check validity of parameters if (isset($reqparamStartSegment)) { $aSegmSearch['startSegment'] = intval($reqparamStartSegment); } if (isset($reqparamEndSegment)) { $aSegmSearch['endSegment'] = intval($reqparamEndSegment); } if (isset($reqparamDuration)) { $aSegmSearch['duration'] = intval($reqparamDuration); } if (isset($reqparamStartSegment) && isset($reqparamEndSegment)) { mysfLog::log($this, "DEBUG: " . intval($reqparamStartSegment) . ", {$reqparamEndSegment} " . $aSegmSearch['startSegment']); } // for selection, both start and end must be given and of type int and greater or equal 0 // Note that the start and end times are set "inline" if (isset($reqparamStartSegment) && $aSegmSearch['startSegment'] > 0 || isset($reqparamEndSegment) && $aSegmSearch['endSegment'] > 0) { mysfLog::log($this, "DEBUG: Using segmented search with start-end in ms:" . $aSegmSearch['startSegment'] . " - " . $aSegmSearch['endSegment']); $aSegmSearch['enabled'] = TRUE; } else { mysfLog::log($this, "DEBUG: NOT using segmented search"); $aSegmSearch['enabled'] = false; } $this->exec_result = smintSmafeHelper::queryFile($filesavepath, $aSegmSearch); $results = smintSmafeHelper::getResultsOnly($this->exec_result["output"]); // $results = smintSmafeHelper::getResultsWithUri($this -> exec_result["output"]); // If we are here in a "search similar" scenario (track is in db, so it will be returned as result again) // we have to filter out the seed song if (!$bUploadedFile) { // do filtering $track_id_seed = $fileForSearchSimilar->getTrackId(); $results_no_seed = array(); foreach ($results as $key => $result) { if ($result[0] != $track_id_seed) { $results_no_seed[$key] = $result; } } $results = $results_no_seed; } if (count($results) == 0) { $empty_livequery = true; } // filter with metadata // select external_key,genre from file left join filedesc on file.external_key = filedesc.tracknr where filedesc.genre ilike '%metadata%' and track_id IN ('31469', '31465') limit 10 if (is_string($metadataquery) && strlen($metadataquery) > 0) { $bMDsearch = true; $filtered_results = $this->metadataFilter($results, $metadataquery); // omit metadata query if empty if ($omit_empty_metadataquery) { if (count($filtered_results) > 0) { // set results to filtered results if the metadata filter returns results $results = $filtered_results; } else { $empty_metadatafilteredquery = true; } } else { $results = $filtered_results; } } else { $bMDsearch = false; } // reduce to maxresults $this->limit = $this->getContext()->getConfiguration()->getSmintMaxQueryResults(); $this->results = array_slice($results, 0, $this->limit); //$this -> results = array_slice($results, 0, 50); ////// If this is segmented search, we perform re-ordering if ($aSegmSearch['enabled']) { // First, we get the length of the segments in samples mysfLog::log($this, "res " . print_r($this->results, true)); $aResultsEnhanced = array(); foreach ($this->results as $key => $value) { // check for negative segmentnr (indicates non-segment server) if ($value[1] < 0) { //throw new Exception("Negative value for segment nr. Probably the smafe server is not configured for segmented search?"); // Set dummy segments (whole track) array_push($aResultsEnhanced, array('track_id' => intval($value[0]), 'segmnr' => 0, 'dist' => doubleval($value[2]), 'start' => 0, 'end' => 0)); } else { $fvsegm = FeaturevectorsegmentPeer::getInformationOnSegment($value[0], $value[1], $configFeaturevectortypeid); $iSamplef = $fvsegm->getFile()->getSamplef(); array_push($aResultsEnhanced, array('track_id' => $fvsegm->getTrackId(), 'segmnr' => $fvsegm->getSegmentnr(), 'dist' => doubleval($value[2]), 'start' => intval($fvsegm->getStartsample() * 1000 / $iSamplef), 'end' => intval(($fvsegm->getStartsample() + $fvsegm->getLength()) * 1000 / $iSamplef))); //$value[3] = $value[1] * 262144; // this is correct for 44100 Hz samples audio //$value[4] = 262144; // this is correct for 44100 Hz samples audio } } //mysfLog::log($this, "DEBUG: " . print_r($aResultsEnhanced, true)); $aSegmSearch['resultsegments'] = array(); // Structure of $aSegmSearch['resultsegments']: // first dim: // each element corresponds to element at same position in $this -> results (and later: ->files) // second dim: // list of result segments for given track // third dim: // assoc array with start and end time for this result segment // INPUT for the aggregation algo: // - $aResultsEnhanced // - $this->results // OUTPUT // - $this -> results array of array[0]...track id , [1] segm nr, [2] distance // - $aSegmSearch['resultsegments'] (see above) switch (sfConfig::get('app_defaults_segm_search_aggregation_algo', 0)) { case 0: foreach ($aResultsEnhanced as $key => $value) { // new segment // conversion done from sample number to ms array_push($aSegmSearch['resultsegments'], array(array('start' => $value['start'], 'end' => $value['end'], 'dist' => $value['dist']))); } break; case 1: // extract 1st column (track ids) // do the actual work // $column = 0; // $result_trackids = array_map('array_slice', $this->results, array_fill(0, count( $this->results), $column), array_fill(0, count( $this->results), 1)); $result_trackids = array(); foreach ($this->results as $key => $value) { array_push($result_trackids, $value[0]); } mysfLog::log($this, "DEBUG: " . print_r($result_trackids, true)); $unique = array(); foreach ($result_trackids as $key => $value) { if (!in_array($value, $unique)) { array_push($unique, $value); } } // $unique = array_unique($result_trackids); //mysfLog::log($this, "DEBUG: " . print_r($unique, true)); foreach ($unique as $ukey => $uvalue) { // segments for $value $tmparray = array(); foreach ($aResultsEnhanced as $key => $value) { if ($uvalue == $value['track_id']) { array_push($tmparray, array('start' => $value['start'], 'end' => $value['end'], 'dist' => $value['dist'])); } } // Sort result segments ascending in start time $fCmpSegments = create_function('$a, $b', ' if ($a[\'start\'] == $b[\'start\']) { return 0; } else if ($a[\'start\'] < $b[\'start\']) { return -1; } else { return 1; } '); usort($tmparray, $fCmpSegments); // push segments to master array array_push($aSegmSearch['resultsegments'], $tmparray); } //mysfLog::log($this, "DEBUG: " . print_r($aSegmSearch['resultsegments'], true)); $this->results = $unique; break; default: throw new Exception("Bad value for app_defaults_segm_search_aggregation_algo: " . sfConfig::get('app_defaults_segm_search_aggregation_algo', 0)); break; } } else { // segmented search enabled // nothing to do, normal search } // segmented search enabled // not used in _result.php // $this -> distances = smintSmafeHelper::getDistances($this -> results); $this->files = $this->queryMetadataDatabase($this->results); //mysfLog::log($this, "DEBUG: " . print_r($this -> files, true)); // depending on whether it is an upload or not if ($bUploadedFile) { //tracknr is before underscore in filename $fileNameParts = explode("_", $filename); $tracknr = $fileNameParts[0]; $uploadedFileURL = _compute_public_path($filename, 'uploads/mp3uploads', 'mp3', false); //url_for("getAudioFile/download") . "?uploaded=" . rawurlencode($filename); // the url for getting the file via PHP, but incomplete. Format parameter is missing and will be // appended in mp3 helper class $uploadedFilePHPUrl_incomplete = url_for("getAudioFile/download", true) . "?uploaded=" . rawurlencode(basename($filename)); if ($aSegmSearch['enabled']) { $seedLabel = intval(($aSegmSearch['endSegment'] - $aSegmSearch['startSegment']) / 1000) . " seconds from {$originalFilename}"; if ($bMDsearch) { $seedlabel_topleft = "Seed track, results filtered by " . $metadataquery; } else { $seedlabel_topleft = "Seed track"; } } else { $seedLabel = $originalFilename; if ($bMDsearch) { $seedlabel_topleft = "Seed track, results filtered by " . $metadataquery; } else { $seedlabel_topleft = "Seed track"; } } } else { $queryFileMetadata = FiledescPeer::retrieveByPk($tracknr); $fileInfoName = $queryFileMetadata->getTitle() . " - " . $queryFileMetadata->getPerformers(); $uploadedFilePHPUrl_incomplete = url_for("getAudioFile/download", true) . "?tracknr=" . rawurlencode($tracknr); $uploadedFileURL = smintUploadFileHelper::getDirectFileUrl($fileForSearchSimilar->getUri()); $seedLabel = $fileInfoName; if ($bMDsearch) { $seedlabel_topleft = "Acoustic similarity, filtered by " . $metadataquery; } else { $seedlabel_topleft = "Acoustic similarity"; } } return $this->renderPartial('search/result', array('render' => 'related', 'id_prefix' => "id_prefix", 'tracknr' => $tracknr, 'uploadedFilePHPUrl_incomplete' => $uploadedFilePHPUrl_incomplete, 'uploadedFileURL' => $uploadedFileURL, 'files' => $this->files, 'queryTrackIsUploaded' => true, 'seedLabel' => $seedLabel, 'limit' => $this->limit, 'metadataquery' => $metadataquery, 'empty_livequery' => $empty_livequery, 'empty_metadatafilteredquery' => $empty_metadatafilteredquery, 'aSegmSearch' => $aSegmSearch, 'seedlabel_topleft' => $seedlabel_topleft)); } catch (Exception $e) { // an error occoured while trying to query the file mysfLog::log($this, "STARTING the QUERY failed: " . $e->getMessage()); return $this->renderPartial('search/error', array('error_message' => $e->getMessage())); } }
/** * If this collection has already been initialized with * an identical criteria, it returns the collection. * Otherwise if this File is new, it will return * an empty collection; or if this File has previously * been saved, it will retrieve related Featurevectorsegments from storage. * * This method is protected by default in order to keep the public * api reasonable. You can provide public methods for those you * actually need in File. */ public function getFeaturevectorsegmentsJoinFeaturevector($criteria = null, $con = null, $join_behavior = Criteria::LEFT_JOIN) { if ($criteria === null) { $criteria = new Criteria(FilePeer::DATABASE_NAME); } elseif ($criteria instanceof Criteria) { $criteria = clone $criteria; } if ($this->collFeaturevectorsegments === null) { if ($this->isNew()) { $this->collFeaturevectorsegments = array(); } else { $criteria->add(FeaturevectorsegmentPeer::FILE_ID, $this->id); $this->collFeaturevectorsegments = FeaturevectorsegmentPeer::doSelectJoinFeaturevector($criteria, $con, $join_behavior); } } else { // the following code is to determine if a new query is // called for. If the criteria is the same as the last // one, just return the collection. $criteria->add(FeaturevectorsegmentPeer::FILE_ID, $this->id); if (!isset($this->lastFeaturevectorsegmentCriteria) || !$this->lastFeaturevectorsegmentCriteria->equals($criteria)) { $this->collFeaturevectorsegments = FeaturevectorsegmentPeer::doSelectJoinFeaturevector($criteria, $con, $join_behavior); } } $this->lastFeaturevectorsegmentCriteria = $criteria; return $this->collFeaturevectorsegments; }
/** * Retrieve object using using composite pkey values. * @param int $segmentnr * @param int $track_id * @param int $featurevectortype_id * @param PropelPDO $con * @return Featurevectorsegment */ public static function retrieveByPK($segmentnr, $track_id, $featurevectortype_id, PropelPDO $con = null) { $key = serialize(array((string) $segmentnr, (string) $track_id, (string) $featurevectortype_id)); if (null !== ($obj = FeaturevectorsegmentPeer::getInstanceFromPool($key))) { return $obj; } if ($con === null) { $con = Propel::getConnection(FeaturevectorsegmentPeer::DATABASE_NAME, Propel::CONNECTION_READ); } $criteria = new Criteria(FeaturevectorsegmentPeer::DATABASE_NAME); $criteria->add(FeaturevectorsegmentPeer::SEGMENTNR, $segmentnr); $criteria->add(FeaturevectorsegmentPeer::TRACK_ID, $track_id); $criteria->add(FeaturevectorsegmentPeer::FEATUREVECTORTYPE_ID, $featurevectortype_id); $v = FeaturevectorsegmentPeer::doSelect($criteria, $con); return !empty($v) ? $v[0] : null; }
/** * Populates the object using an array. * * This is particularly useful when populating an object from one of the * request arrays (e.g. $_POST). This method goes through the column * names, checking to see whether a matching key exists in populated * array. If so the setByName() method is called for that column. * * You can specify the key type of the array by additionally passing one * of the class type constants BasePeer::TYPE_PHPNAME, BasePeer::TYPE_STUDLYPHPNAME, * BasePeer::TYPE_COLNAME, BasePeer::TYPE_FIELDNAME, BasePeer::TYPE_NUM. * The default key type is the column's phpname (e.g. 'AuthorId') * * @param array $arr An array to populate the object from. * @param string $keyType The type of keys the array uses. * @return void */ public function fromArray($arr, $keyType = BasePeer::TYPE_PHPNAME) { $keys = FeaturevectorsegmentPeer::getFieldNames($keyType); if (array_key_exists($keys[0], $arr)) { $this->setSegmentnr($arr[$keys[0]]); } if (array_key_exists($keys[1], $arr)) { $this->setTrackId($arr[$keys[1]]); } if (array_key_exists($keys[2], $arr)) { $this->setFeaturevectortypeId($arr[$keys[2]]); } if (array_key_exists($keys[3], $arr)) { $this->setData($arr[$keys[3]]); } if (array_key_exists($keys[4], $arr)) { $this->setFileId($arr[$keys[4]]); } if (array_key_exists($keys[5], $arr)) { $this->setStartsample($arr[$keys[5]]); } if (array_key_exists($keys[6], $arr)) { $this->setLength($arr[$keys[6]]); } if (array_key_exists($keys[7], $arr)) { $this->setInserted($arr[$keys[7]]); } if (array_key_exists($keys[8], $arr)) { $this->setUpdated($arr[$keys[8]]); } }