/** * @covers Alchemy\Phrasea\SearchEngine\SearchEngineOptions::fromRequest */ public function testFromRequestEmptyUnauthenticated() { $options = SearchEngineOptions::fromRequest(self::$DI['app'], new Request()); $this->assertEquals([], $options->getCollections()); $this->assertEquals([], $options->getFields()); $this->assertEquals(null, $options->getRecordType()); $this->assertEquals('0', $options->getSearchType()); $this->assertEquals(null, $options->getMaxDate()); $this->assertEquals(null, $options->getMinDate()); $this->assertEquals([], $options->getDateFields()); $this->assertEquals('desc', $options->getSortOrder()); $this->assertEquals(null, $options->getSortBy()); $this->assertEquals(false, $options->isStemmed()); }
/** * Query Phraseanet to fetch records * * @param Request $request * @return Response */ public function query(Request $request) { $query = (string) $request->request->get('qry'); // since the query comes from a submited form, normalize crlf,cr,lf ... $query = StringHelper::crlfNormalize($query); $json = array('query' => $query); $options = SearchEngineOptions::fromRequest($this->app, $request); $form = $options->serialize(); $perPage = (int) $this->getSettings()->getUserSetting($this->getAuthenticatedUser(), 'images_per_page'); $page = (int) $request->request->get('pag'); $firstPage = $page < 1; $engine = $this->getSearchEngine(); if ($page < 1) { $engine->resetCache(); $page = 1; } $user = $this->getAuthenticatedUser(); $userManipulator = $this->getUserManipulator(); $userManipulator->logQuery($user, $query); try { /** @var SearchEngineResult $result */ $result = $engine->query($query, ($page - 1) * $perPage, $perPage, $options); if ($this->getSettings()->getUserSetting($user, 'start_page') === 'LAST_QUERY') { $userManipulator->setUserSetting($user, 'start_page_query', $query); } foreach ($options->getDataboxes() as $databox) { $collections = array_map(function (\collection $collection) { return $collection->get_coll_id(); }, array_filter($options->getCollections(), function (\collection $collection) use($databox) { return $collection->get_databox()->get_sbas_id() == $databox->get_sbas_id(); })); $this->getSearchEngineLogger()->log($databox, $result->getQuery(), $result->getTotal(), $collections); } $proposals = $firstPage ? $result->getProposals() : false; $npages = $result->getTotalPages($perPage); $page = $result->getCurrentPage($perPage); $string = ''; if ($npages > 1) { $d2top = $npages - $page; $d2bottom = $page; if (min($d2top, $d2bottom) < 4) { if ($d2bottom < 4) { if ($page != 1) { $string .= "<a id='PREV_PAGE' class='btn btn-primary btn-mini'></a>"; } for ($i = 1; $i <= 4 && $i <= $npages === true; $i++) { if ($i == $page) { $string .= '<input onkeypress="if(event.keyCode == 13 && !isNaN(parseInt(this.value)))gotopage(parseInt(this.value))" type="text" value="' . $i . '" size="' . strlen((string) $i) . '" class="btn btn-mini" />'; } else { $string .= "<a onclick='gotopage(" . $i . ");return false;' class='btn btn-primary btn-mini'>" . $i . "</a>"; } } if ($npages > 4) { $string .= "<a id='NEXT_PAGE' class='btn btn-primary btn-mini'></a>"; } $string .= "<a onclick='gotopage(" . $npages . ");return false;' class='btn btn-primary btn-mini' id='last'></a>"; } else { $start = $npages - 4; if ($start > 0) { $string .= "<a onclick='gotopage(1);return false;' class='btn btn-primary btn-mini' id='first'></a>"; $string .= "<a id='PREV_PAGE' class='btn btn-primary btn-mini'></a>"; } else { $start = 1; } for ($i = $start; $i <= $npages; $i++) { if ($i == $page) { $string .= '<input onkeypress="if(event.keyCode == 13 && !isNaN(parseInt(this.value)))gotopage(parseInt(this.value))" type="text" value="' . $i . '" size="' . strlen((string) $i) . '" class="btn btn-mini" />'; } else { $string .= "<a onclick='gotopage(" . $i . ");return false;' class='btn btn-primary btn-mini'>" . $i . "</a>"; } } if ($page < $npages) { $string .= "<a id='NEXT_PAGE' class='btn btn-primary btn-mini'></a>"; } } } else { $string .= "<a onclick='gotopage(1);return false;' class='btn btn-primary btn-mini' id='first'></a>"; for ($i = $page - 2; $i <= $page + 2; $i++) { if ($i == $page) { $string .= '<input onkeypress="if(event.keyCode == 13 && !isNaN(parseInt(this.value)))gotopage(parseInt(this.value))" type="text" value="' . $i . '" size="' . strlen((string) $i) . '" class="btn btn-mini" />'; } else { $string .= "<a onclick='gotopage(" . $i . ");return false;' class='btn btn-primary btn-mini'>" . $i . "</a>"; } } $string .= "<a onclick='gotopage(" . $npages . ");return false;' class='btn btn-primary btn-mini' id='last'></a>"; } } $string .= '<div style="display:none;"><div id="NEXT_PAGE"></div><div id="PREV_PAGE"></div></div>'; $explain = "<div id=\"explainResults\" class=\"myexplain\">"; $explain .= "<img src=\"/assets/common/images/icons/answers.gif\" /><span><b>"; if ($result->getTotal() != $result->getAvailable()) { $explain .= $this->app->trans('reponses:: %available% Resultats rappatries sur un total de %total% trouves', ['available' => $result->getAvailable(), '%total%' => $result->getTotal()]); } else { $explain .= $this->app->trans('reponses:: %total% Resultats', ['%total%' => $result->getTotal()]); } $explain .= " </b></span>"; $explain .= '<br><div>' . $result->getDuration() / 1000 . ' s</div>dans index ' . $result->getIndexes(); $explain .= "</div>"; $infoResult = '<div id="docInfo">' . $this->app->trans('%number% documents<br/>selectionnes', ['%number%' => '<span id="nbrecsel"></span>']) . '</div><a href="#" class="infoDialog" infos="' . str_replace('"', '"', $explain) . '">' . $this->app->trans('%total% reponses', ['%total%' => '<span>' . $result->getTotal() . '</span>']) . '</a>'; $json['infos'] = $infoResult; $json['navigation'] = $string; $prop = null; if ($firstPage) { $propals = $result->getSuggestions(); if (count($propals) > 0) { foreach ($propals as $prop_array) { if ($prop_array->getSuggestion() !== $query && $prop_array->getHits() > $result->getTotal()) { $prop = $prop_array->getSuggestion(); break; } } } } if ($result->getTotal() === 0) { $template = 'prod/results/help.html.twig'; } else { $template = 'prod/results/records.html.twig'; } $json['results'] = $this->render($template, ['results' => $result]); /** Debug */ $json['parsed_query'] = $result->getQuery(); /** End debug */ $fieldLabels = ['Base_Name' => $this->app->trans('prod::facet:base_label'), 'Collection_Name' => $this->app->trans('prod::facet:collection_label'), 'Type_Name' => $this->app->trans('prod::facet:doctype_label')]; foreach ($this->app->getDataboxes() as $databox) { foreach ($databox->get_meta_structure() as $field) { if (!isset($fieldLabels[$field->get_name()])) { $fieldLabels[$field->get_name()] = $field->get_label($this->app['locale']); } } } $facets = []; foreach ($result->getFacets() as $facet) { $facetName = $facet['name']; $facet['label'] = isset($fieldLabels[$facetName]) ? $fieldLabels[$facetName] : $facetName; $facets[] = $facet; } $json['facets'] = $facets; $json['phrasea_props'] = $proposals; $json['total_answers'] = (int) $result->getAvailable(); $json['next_page'] = $page < $npages && $result->getAvailable() > 0 ? $page + 1 : false; $json['prev_page'] = $page > 1 && $result->getAvailable() > 0 ? $page - 1 : false; $json['form'] = $form; } catch (\Exception $e) { // we'd like a message from the parser so get all the exceptions messages $msg = ''; for (; $e; $e = $e->getPrevious()) { $msg .= ($msg ? "\n" : "") . $e->getMessage(); } $template = 'prod/results/help.html.twig'; $result = array('error' => $msg); $json['results'] = $this->render($template, ['results' => $result]); } return $this->app->json($json); }
private function prepare_search_request(Application $app, Request $request) { $options = SearchEngineOptions::fromRequest($app, $request); $offsetStart = (int) ($request->get('offset_start') ?: 0); $perPage = (int) $request->get('per_page') ?: 10; $query = (string) $request->get('query'); $app['phraseanet.SE']->resetCache(); $search_result = $app['phraseanet.SE']->query($query, $offsetStart, $perPage, $options); $app['manipulator.user']->logQuery($app['authentication']->getUser(), $search_result->getQuery()); foreach ($options->getDataboxes() as $databox) { $colls = array_map(function (\collection $collection) { return $collection->get_coll_id(); }, array_filter($options->getCollections(), function (\collection $collection) use($databox) { return $collection->get_databox()->get_sbas_id() == $databox->get_sbas_id(); })); $app['phraseanet.SE.logger']->log($databox, $search_result->getQuery(), $search_result->getTotal(), $colls); } $app['phraseanet.SE']->clearCache(); $ret = ['offset_start' => $offsetStart, 'per_page' => $perPage, 'available_results' => $search_result->getAvailable(), 'total_results' => $search_result->getTotal(), 'error' => $search_result->getError(), 'warning' => $search_result->getWarning(), 'query_time' => $search_result->getDuration(), 'search_indexes' => $search_result->getIndexes(), 'suggestions' => array_map(function (SearchEngineSuggestion $suggestion) { return $suggestion->toArray(); }, $search_result->getSuggestions()->toArray()), 'results' => [], 'query' => $search_result->getQuery()]; return [$ret, $search_result]; }
/** * Query Phraseanet to fetch records * * @param Application $app * @param Request $request * @return JsonResponse */ public function query(Application $app, Request $request) { $query = (string) $request->request->get('qry'); $mod = $app['settings']->getUserSetting($app['authentication']->getUser(), 'view'); $json = []; $options = SearchEngineOptions::fromRequest($app, $request); $form = $options->serialize(); $perPage = (int) $app['settings']->getUserSetting($app['authentication']->getUser(), 'images_per_page'); $page = (int) $request->request->get('pag'); $firstPage = $page < 1; if ($page < 1) { $app['phraseanet.SE']->resetCache(); $page = 1; } $result = $app['phraseanet.SE']->query($query, ($page - 1) * $perPage, $perPage, $options); $app['manipulator.user']->logQuery($app['authentication']->getUser(), $result->getQuery()); if ($app['settings']->getUserSetting($app['authentication']->getUser(), 'start_page') === 'LAST_QUERY') { $app['manipulator.user']->setUserSetting($app['authentication']->getUser(), 'start_page_query', $result->getQuery()); } foreach ($options->getDataboxes() as $databox) { $colls = array_map(function (\collection $collection) { return $collection->get_coll_id(); }, array_filter($options->getCollections(), function (\collection $collection) use($databox) { return $collection->get_databox()->get_sbas_id() == $databox->get_sbas_id(); })); $app['phraseanet.SE.logger']->log($databox, $result->getQuery(), $result->getTotal(), $colls); } $proposals = $firstPage ? $result->getProposals() : false; $npages = $result->getTotalPages($perPage); $page = $result->getCurrentPage($perPage); $string = ''; if ($npages > 1) { $d2top = $npages - $page; $d2bottom = $page; if (min($d2top, $d2bottom) < 4) { if ($d2bottom < 4) { for ($i = 1; $i <= 4 && $i <= $npages === true; $i++) { if ($i == $page) { $string .= '<input onkeypress="if(event.keyCode == 13 && !isNaN(parseInt(this.value)))gotopage(parseInt(this.value))" type="text" value="' . $i . '" size="' . strlen((string) $i) . '" class="btn btn-mini" />'; } else { $string .= "<a onclick='gotopage(" . $i . ");return false;' class='btn btn-primary btn-mini'>" . $i . "</a>"; } } if ($npages > 4) { $string .= "<a onclick='gotopage(" . $npages . ");return false;' class='btn btn-primary btn-mini'>>></a>"; } } else { $start = $npages - 4; if ($start > 0) { $string .= "<a onclick='gotopage(1);return false;' class='btn btn-primary btn-mini'><<</a>"; } else { $start = 1; } for ($i = $start; $i <= $npages; $i++) { if ($i == $page) { $string .= '<input onkeypress="if(event.keyCode == 13 && !isNaN(parseInt(this.value)))gotopage(parseInt(this.value))" type="text" value="' . $i . '" size="' . strlen((string) $i) . '" class="btn btn-mini" />'; } else { $string .= "<a onclick='gotopage(" . $i . ");return false;' class='btn btn-primary btn-mini'>" . $i . "</a>"; } } } } else { $string .= "<a onclick='gotopage(1);return false;' class='btn btn-primary btn-mini'><<</a>"; for ($i = $page - 2; $i <= $page + 2; $i++) { if ($i == $page) { $string .= '<input onkeypress="if(event.keyCode == 13 && !isNaN(parseInt(this.value)))gotopage(parseInt(this.value))" type="text" value="' . $i . '" size="' . strlen((string) $i) . '" class="btn btn-mini" />'; } else { $string .= "<a onclick='gotopage(" . $i . ");return false;' class='btn btn-primary btn-mini'>" . $i . "</a>"; } } $string .= "<a onclick='gotopage(" . $npages . ");return false;' class='btn btn-primary btn-mini'>>></a>"; } } $string .= '<div style="display:none;"><div id="NEXT_PAGE"></div><div id="PREV_PAGE"></div></div>'; $explain = "<div id=\"explainResults\" class=\"myexplain\">"; $explain .= "<img src=\"/skins/icons/answers.gif\" /><span><b>"; if ($result->getTotal() != $result->getAvailable()) { $explain .= $app->trans('reponses:: %available% Resultats rappatries sur un total de %total% trouves', ['available' => $result->getAvailable(), '%total%' => $result->getTotal()]); } else { $explain .= $app->trans('reponses:: %total% Resultats', ['%total%' => $result->getTotal()]); } $explain .= " </b></span>"; $explain .= '<br><div>' . $result->getDuration() . ' s</div>dans index ' . $result->getIndexes(); $explain .= "</div>"; $infoResult = '<a href="#" class="infoDialog" infos="' . str_replace('"', '"', $explain) . '">' . $app->trans('reponses:: %total% reponses', ['%total%' => $result->getTotal()]) . '</a> | ' . $app->trans('reponses:: %number% documents selectionnes', ['%number%' => '<span id="nbrecsel"></span>']); $json['infos'] = $infoResult; $json['navigation'] = $string; $prop = null; if ($firstPage) { $propals = $result->getSuggestions(); if (count($propals) > 0) { foreach ($propals as $prop_array) { if ($prop_array->getSuggestion() !== $query && $prop_array->getHits() > $result->getTotal()) { $prop = $prop_array->getSuggestion(); break; } } } } if ($result->getTotal() === 0) { $template = 'prod/results/help.html.twig'; } else { if ($mod == 'thumbs') { $template = 'prod/results/answergrid.html.twig'; } else { $template = 'prod/results/answerlist.html.twig'; } } $json['results'] = $app['twig']->render($template, ['results' => $result, 'highlight' => $result->getQuery(), 'searchEngine' => $app['phraseanet.SE'], 'searchOptions' => $options, 'suggestions' => $prop]); $json['query'] = $query; $json['phrasea_props'] = $proposals; $json['total_answers'] = (int) $result->getAvailable(); $json['next_page'] = $page < $npages && $result->getAvailable() > 0 ? $page + 1 : false; $json['prev_page'] = $page > 1 && $result->getAvailable() > 0 ? $page - 1 : false; $json['form'] = $form; return $app->json($json); }
/** * Queries database to fetch documents * * @param Application $app * @param Request $request * @return Response */ public function query(Application $app, Request $request) { $query = $this->buildQueryFromRequest($request); $displayMode = explode('X', $request->request->get('mod', '3X6')); if (count($displayMode) === 1) { $modRow = (int) $displayMode[0]; $modCol = 1; } else { $modRow = (int) $displayMode[0]; $modCol = (int) $displayMode[1]; } $perPage = $modCol * $modRow; $options = SearchEngineOptions::fromRequest($app, $request); $currentPage = (int) $request->request->get('pag', 0); if ($currentPage < 1) { $app['phraseanet.SE']->resetCache(); $currentPage = 1; } $result = $app['phraseanet.SE']->query($query, ($currentPage - 1) * $perPage, $perPage, $options); $userQuery = new UserQuery(); $userQuery->setUser($app['authentication']->getUser()); $userQuery->setQuery($query); $app['EM']->persist($userQuery); $app['EM']->flush(); if ($app['settings']->getUserSetting($app['authentication']->getUser(), 'start_page') === 'LAST_QUERY') { $app['manipulator.user']->setUserSetting($app['authentication']->getUser(), 'start_page_query', $query); } foreach ($options->getDataboxes() as $databox) { $colls = array_map(function (\collection $collection) { return $collection->get_coll_id(); }, array_filter($options->getCollections(), function (\collection $collection) use($databox) { return $collection->get_databox()->get_sbas_id() == $databox->get_sbas_id(); })); $app['phraseanet.SE.logger']->log($databox, $result->getQuery(), $result->getTotal(), $colls); } $searchData = $result->getResults(); if (count($searchData) === 0) { return new Response($app['twig']->render("client/help.html.twig")); } $resultData = []; foreach ($searchData as $record) { try { $record->get_subdef('document'); $lightInfo = $app['twig']->render('common/technical_datas.html.twig', ['record' => $record]); } catch (\Exception $e) { $lightInfo = ''; } $caption = $app['twig']->render('common/caption.html.twig', ['view' => 'answer', 'record' => $record]); $docType = $record->get_type(); $isVideo = $docType == 'video'; $isAudio = $docType == 'audio'; $isImage = $docType == 'image'; $isDocument = $docType == 'document'; if (!$isVideo && !$isAudio) { $isImage = true; } $canDownload = $app['acl']->get($app['authentication']->getUser())->has_right_on_base($record->get_base_id(), 'candwnldpreview') || $app['acl']->get($app['authentication']->getUser())->has_right_on_base($record->get_base_id(), 'candwnldhd') || $app['acl']->get($app['authentication']->getUser())->has_right_on_base($record->get_base_id(), 'cancmd'); try { $previewExists = $record->get_preview()->is_physically_present(); } catch (\Exception $e) { $previewExists = false; } $resultData[] = ['record' => $record, 'mini_logo' => \collection::getLogo($record->get_base_id(), $app), 'preview_exists' => $previewExists, 'light_info' => $lightInfo, 'caption' => $caption, 'is_video' => $isVideo, 'is_audio' => $isAudio, 'is_image' => $isImage, 'is_document' => $isDocument, 'can_download' => $canDownload, 'can_add_to_basket' => $app['acl']->get($app['authentication']->getUser())->has_right_on_base($record->get_base_id(), 'canputinalbum')]; } return new Response($app['twig']->render("client/answers.html.twig", ['mod_col' => $modCol, 'mod_row' => $modRow, 'result_data' => $resultData, 'per_page' => $perPage, 'search_engine' => $app['phraseanet.SE'], 'search_engine_option' => $options->serialize(), 'history' => \queries::history($app, $app['authentication']->getUser()->getId()), 'result' => $result, 'proposals' => $currentPage === 1 ? $result->getProposals() : null, 'help' => count($resultData) === 0 ? $this->getHelpStartPage($app) : ''])); }