TYPO3CMS  8
 All Classes Namespaces Files Functions Variables Pages
AdministrationController.php
Go to the documentation of this file.
1 <?php
2 namespace TYPO3\CMS\IndexedSearch\Controller;
3 
4 /*
5  * This file is part of the TYPO3 CMS project.
6  *
7  * It is free software; you can redistribute it and/or modify it under
8  * the terms of the GNU General Public License, either version 2
9  * of the License, or any later version.
10  *
11  * For the full copyright and license information, please read the
12  * LICENSE.txt file that was distributed with this source code.
13  *
14  * The TYPO3 project - inspiring people to share!
15  */
24 use TYPO3\CMS\Extbase\Mvc\Web\Request as WebRequest;
29 
34 {
39 
43  protected $pageUid = 0;
44 
48  protected $external_parsers = [];
49 
53  protected $indexerConfig = [];
54 
58  protected $enableMetaphoneSearch = false;
59 
65  protected $indexer;
66 
72  protected $defaultViewObjectName = BackendTemplateView::class;
73 
79  protected $view;
80 
86  protected function initializeView(ViewInterface $view)
87  {
88  if ($view instanceof BackendTemplateView) {
90  parent::initializeView($view);
91  $permissionClause = $this->getBackendUserAuthentication()->getPagePermsClause(1);
92  $pageRecord = BackendUtility::readPageAccess($this->pageUid, $permissionClause);
93  if ($pageRecord) {
94  $view->getModuleTemplate()->getDocHeaderComponent()->setMetaInformation($pageRecord);
95  }
96  $this->generateMenu();
97  $this->view->getModuleTemplate()->setFlashMessageQueue($this->controllerContext->getFlashMessageQueue());
98  }
99  }
100 
104  protected function generateMenu()
105  {
106  $menuItems = [
107  'index' => [
108  'controller' => 'Administration',
109  'action' => 'index',
110  'label' => $this->getLanguageService()->sL('LLL:EXT:indexed_search/Resources/Private/Language/locallang.xml:administration.menu.general')
111  ],
112  'pages' => [
113  'controller' => 'Administration',
114  'action' => 'pages',
115  'label' => $this->getLanguageService()->sL('LLL:EXT:indexed_search/Resources/Private/Language/locallang.xml:administration.menu.pages')
116  ],
117  'externalDocuments' => [
118  'controller' => 'Administration',
119  'action' => 'externalDocuments',
120  'label' => $this->getLanguageService()->sL('LLL:EXT:indexed_search/Resources/Private/Language/locallang.xml:administration.menu.externalDocuments')
121  ],
122  'statistic' => [
123  'controller' => 'Administration',
124  'action' => 'statistic',
125  'label' => $this->getLanguageService()->sL('LLL:EXT:indexed_search/Resources/Private/Language/locallang.xml:administration.menu.statistic')
126  ]
127  ];
128  $uriBuilder = $this->objectManager->get(UriBuilder::class);
129  $uriBuilder->setRequest($this->request);
130 
131  $menu = $this->view->getModuleTemplate()->getDocHeaderComponent()->getMenuRegistry()->makeMenu();
132  $menu->setIdentifier('IndexedSearchModuleMenu');
133 
134  foreach ($menuItems as $menuItemConfig) {
135  $isActive = $this->request->getControllerActionName() === $menuItemConfig['action'];
136  $menuItem = $menu->makeMenuItem()
137  ->setTitle($menuItemConfig['label'])
138  ->setHref($this->getHref($menuItemConfig['controller'], $menuItemConfig['action']))
139  ->setActive($isActive);
140  $menu->addMenuItem($menuItem);
141  }
142 
143  $this->view->getModuleTemplate()->getDocHeaderComponent()->getMenuRegistry()->addMenu($menu);
144  }
145 
151  public function initializeAction()
152  {
153  $this->pageUid = (int)GeneralUtility::_GET('id');
154  $this->indexerConfig = unserialize($GLOBALS['TYPO3_CONF_VARS']['EXT']['extConf']['indexed_search'], ['allowed_classes' => false]);
155  $this->enableMetaphoneSearch = (bool)$this->indexerConfig['enableMetaphoneSearch'];
156  $this->indexer = GeneralUtility::makeInstance(Indexer::class);
157 
158  parent::initializeAction();
159  }
160 
168  public function processRequest(\TYPO3\CMS\Extbase\Mvc\RequestInterface $request, \TYPO3\CMS\Extbase\Mvc\ResponseInterface $response)
169  {
170  $vars = GeneralUtility::_GET('tx_indexedsearch_web_indexedsearchisearch');
171 
172  $beUser = $this->getBackendUserAuthentication();
173  if (is_array($vars) && isset($vars['action']) && method_exists($this, $vars['action'] . 'Action')) {
174  $action = $vars['action'];
175 
176  switch ($action) {
177  case 'saveStopwordsKeywords':
178  $action = 'statisticDetails';
179  break;
180  case 'deleteIndexedItem':
181  $action = 'statistic';
182  break;
183  }
184 
185  $beUser->uc['indexed_search']['action'] = $action;
186  $beUser->uc['indexed_search']['arguments'] = $request->getArguments();
187  $beUser->writeUC();
188  } elseif (isset($beUser->uc['indexed_search']['action'])) {
189  if ($request instanceof WebRequest) {
190  $request->setControllerActionName($beUser->uc['indexed_search']['action']);
191  }
192  if (isset($beUser->uc['indexed_search']['arguments'])) {
193  $request->setArguments($beUser->uc['indexed_search']['arguments']);
194  }
195  }
196 
197  parent::processRequest($request, $response);
198  }
199 
205  {
206  $this->administrationRepository = $administrationRepository;
207  }
208 
214  public function indexAction()
215  {
216  $this->view->assignMultiple([
217  'records' => $this->administrationRepository->getRecordsNumbers(),
218  'phash' => $this->administrationRepository->getPageHashTypes()
219  ]);
220 
221  if ($this->pageUid) {
222  $expressionBuilder = GeneralUtility::makeInstance(ConnectionPool::class)
223  ->getQueryBuilderForTable('index_stat_word')
224  ->expr();
225 
226  $last24hours = $expressionBuilder->gt('tstamp', ($GLOBALS['EXEC_TIME'] - 86400));
227  $last30days = $expressionBuilder->gt('tstamp', ($GLOBALS['EXEC_TIME'] - 30 * 86400));
228 
229  $this->view->assignMultiple([
230  'pageUid' => $this->pageUid,
231  'all' => $this->administrationRepository->getGeneralSearchStatistic('', $this->pageUid),
232  'last24hours' => $this->administrationRepository->getGeneralSearchStatistic($last24hours, $this->pageUid),
233  'last30days' => $this->administrationRepository->getGeneralSearchStatistic($last30days, $this->pageUid),
234  ]);
235  }
236  }
237 
243  public function pagesAction()
244  {
245  $this->view->assign('records', $this->administrationRepository->getPageStatistic());
246  }
247 
253  public function externalDocumentsAction()
254  {
255  $this->view->assign('records', $this->administrationRepository->getExternalDocumentsStatistic());
256  }
257 
264  public function statisticDetailsAction($pageHash = 0)
265  {
266  $pageHash = (int)$pageHash;
267  // Set back button
268  $icon = $this->view->getModuleTemplate()->getIconFactory()->getIcon('actions-view-go-up', Icon::SIZE_SMALL);
269  $backButton = $this->view->getModuleTemplate()->getDocHeaderComponent()
270  ->getButtonBar()->makeLinkButton()
271  ->setTitle($this->getLanguageService()->sL('LLL:EXT:indexed_search/Resources/Private/Language/locallang.xml:administration.back'))
272  ->setIcon($icon)
273  ->setHref($this->getHref('Administration', 'statistic'));
274  $this->view->getModuleTemplate()->getDocHeaderComponent()
275  ->getButtonBar()->addButton($backButton);
276 
277  $queryBuilder = GeneralUtility::makeInstance(ConnectionPool::class)->getQueryBuilderForTable('index_phash');
278  $pageHashRow = $queryBuilder
279  ->select('*')
280  ->from('index_phash')
281  ->where(
282  $queryBuilder->expr()->eq(
283  'phash',
284  $queryBuilder->createNamedParameter($pageHash, \PDO::PARAM_INT)
285  )
286  )
287  ->execute()
288  ->fetch();
289 
290  if (!is_array($pageHashRow)) {
291  $this->redirect('statistic');
292  }
293 
294  $queryBuilder = GeneralUtility::makeInstance(ConnectionPool::class)->getQueryBuilderForTable('index_debug');
295  $debugRow = $queryBuilder
296  ->select('*')
297  ->from('index_debug')
298  ->where(
299  $queryBuilder->expr()->eq(
300  'phash',
301  $queryBuilder->createNamedParameter($pageHash, \PDO::PARAM_INT)
302  )
303  )
304  ->execute()
305  ->fetchAll();
306  $debugInfo = [];
307  $lexer = '';
308  if (is_array($debugRow)) {
309  $debugInfo = unserialize($debugRow[0]['debuginfo']);
310  $lexer = $debugInfo['lexer'];
311  unset($debugInfo['lexer']);
312  }
313  $pageRecord = BackendUtility::getRecord('pages', $pageHashRow['data_page_id']);
314  $keywords = is_array($pageRecord) ? array_flip(GeneralUtility::trimExplode(',', $pageRecord['keywords'], true)) : [];
315 
316  $queryBuilder = GeneralUtility::makeInstance(ConnectionPool::class)->getQueryBuilderForTable('index_words');
317  $wordRecords = $queryBuilder
318  ->select('index_words.*', 'index_rel.*')
319  ->from('index_words')
320  ->from('index_rel')
321  ->where(
322  $queryBuilder->expr()->eq(
323  'index_rel.phash',
324  $queryBuilder->createNamedParameter($pageHash, \PDO::PARAM_INT)
325  ),
326  $queryBuilder->expr()->eq(
327  'index_words.wid',
328  $queryBuilder->quoteIdentifier('index_rel.wid')
329  )
330  )
331  ->orderBy('index_words.baseword')
332  ->execute()
333  ->fetchAll();
334  foreach ($wordRecords as $id => $row) {
335  if (isset($keywords[$row['baseword']])) {
336  $wordRecords[$id]['is_keyword'] = true;
337  }
338  }
339  $metaphoneRows = $metaphone = [];
340  if ($this->enableMetaphoneSearch && is_array($wordRecords)) {
341  // Group metaphone hash
342  foreach ($wordRecords as $row) {
343  $metaphoneRows[$row['metaphone']][] = $row['baseword'];
344  }
345 
346  foreach ($metaphoneRows as $hash => $words) {
347  if (count($words) > 1) {
348  $metaphone[] = [
349  'metaphone' => $this->indexer->metaphone($words[0], 1), $hash,
350  'words' => $words,
351  'hash' => $hash
352  ];
353  }
354  }
355  }
356 
357  // sections
358  $queryBuilder = GeneralUtility::makeInstance(ConnectionPool::class)->getQueryBuilderForTable('index_section');
359  $sections = $queryBuilder
360  ->select('*')
361  ->from('index_section')
362  ->where(
363  $queryBuilder->expr()->eq(
364  'phash',
365  $queryBuilder->createNamedParameter($pageHash, \PDO::PARAM_INT)
366  )
367  )
368  ->execute()
369  ->fetchAll();
370 
371  // top words
372  $queryBuilder = GeneralUtility::makeInstance(ConnectionPool::class)->getQueryBuilderForTable('index_words');
373  $topCountWords = $queryBuilder
374  ->select('index_words.baseword', 'index_words.metaphone', 'index_rel.*')
375  ->from('index_words')
376  ->from('index_rel')
377  ->setMaxResults(20)
378  ->where(
379  $queryBuilder->expr()->eq(
380  'index_rel.phash',
381  $queryBuilder->createNamedParameter($pageHash, \PDO::PARAM_INT)
382  ),
383  $queryBuilder->expr()->eq(
384  'index_words.is_stopword',
385  $queryBuilder->createNamedParameter(0, \PDO::PARAM_INT)
386  ),
387  $queryBuilder->expr()->eq(
388  'index_words.wid',
389  $queryBuilder->quoteIdentifier('index_rel.wid')
390  )
391  )
392  ->orderBy('index_rel.count', 'DESC')
393  ->execute()
394  ->fetchAll();
395 
396  // top frequency
397  $queryBuilder = GeneralUtility::makeInstance(ConnectionPool::class)->getQueryBuilderForTable('index_words');
398  $topFrequency = $queryBuilder
399  ->select('index_words.baseword', 'index_words.metaphone', 'index_rel.*')
400  ->from('index_words')
401  ->from('index_rel')
402  ->setMaxResults(20)
403  ->where(
404  $queryBuilder->expr()->eq(
405  'index_rel.phash',
406  $queryBuilder->createNamedParameter($pageHash, \PDO::PARAM_INT)
407  ),
408  $queryBuilder->expr()->eq(
409  'index_words.is_stopword',
410  $queryBuilder->createNamedParameter(0, \PDO::PARAM_INT)
411  ),
412  $queryBuilder->expr()->eq(
413  'index_words.wid',
414  $queryBuilder->quoteIdentifier('index_rel.wid')
415  )
416  )
417  ->orderBy('index_rel.freq', 'DESC')
418  ->execute()
419  ->fetchAll();
420 
421  $this->view->assignMultiple([
422  'phash' => (int)$pageHash,
423  'phashRow' => $pageHashRow,
424  'words' => $wordRecords,
425  'sections' => $sections,
426  'topCount' => $topCountWords,
427  'topFrequency' => $topFrequency,
428  'debug' => $debugInfo,
429  'lexer' => $lexer,
430  'metaphone' => $metaphone,
431  'page' => $pageRecord,
432  'keywords' => $keywords
433  ]);
434  }
435 
445  public function saveStopwordsKeywordsAction($pageHash, $pageId, $stopwords = [], $keywords = [])
446  {
447  if ($this->getBackendUserAuthentication()->isAdmin()) {
448  if (is_array($stopwords) && !empty($stopwords)) {
449  $this->administrationRepository->saveStopWords($stopwords);
450  }
451  if (is_array($keywords) && !empty($keywords)) {
452  $this->administrationRepository->saveKeywords($keywords, $pageId);
453  }
454  }
455 
456  $this->redirect('statisticDetails', null, null, ['pageHash' => $pageHash]);
457  }
458 
466  public function wordDetailAction($id = 0, $pageHash = 0)
467  {
468  $queryBuilder = GeneralUtility::makeInstance(ConnectionPool::class)->getQueryBuilderForTable('index_phash');
469  $rows = $queryBuilder
470  ->select('index_phash.*', 'index_section.*', 'index_rel.*')
471  ->from('index_rel')
472  ->from('index_section')
473  ->from('index_phash')
474  ->where(
475  $queryBuilder->expr()->eq(
476  'index_rel.wid',
477  $queryBuilder->createNamedParameter($id, \PDO::PARAM_INT)
478  ),
479  $queryBuilder->expr()->eq(
480  'index_rel.phash',
481  $queryBuilder->quoteIdentifier('index_section.phash')
482  ),
483  $queryBuilder->expr()->eq(
484  'index_section.phash',
485  $queryBuilder->quoteIdentifier('index_phash.phash')
486  )
487  )
488  ->orderBy('index_rel.freq', 'desc')
489  ->execute()
490  ->fetchAll();
491 
492  $this->view->assignMultiple([
493  'rows' => $rows,
494  'phash' => $pageHash
495  ]);
496  }
497 
505  public function statisticAction($depth = 1, $mode = 'overview')
506  {
507  if (is_array($GLOBALS['TYPO3_CONF_VARS']['EXTCONF']['indexed_search']['external_parsers'])) {
508  foreach ($GLOBALS['TYPO3_CONF_VARS']['EXTCONF']['indexed_search']['external_parsers'] as $extension => $_objRef) {
510  $fileContentParser = GeneralUtility::getUserObj($_objRef);
511  if ($fileContentParser->softInit($extension)) {
512  $this->external_parsers[$extension] = $fileContentParser;
513  }
514  }
515  }
516  $this->administrationRepository->external_parsers = $this->external_parsers;
517 
518  $allLines = $this->administrationRepository->getTree($this->pageUid, $depth, $mode);
519 
520  $this->view->assignMultiple([
521  'levelTranslations' => explode('|', $this->getLanguageService()->sL('LLL:EXT:lang/Resources/Private/Language/locallang_core.xlf:labels.enterSearchLevels')),
522  'tree' => $allLines,
523  'pageUid' => $this->pageUid,
524  'mode' => $mode,
525  'depth' => $depth
526  ]);
527  }
528 
537  public function deleteIndexedItemAction($id, $depth = 1, $mode = 'overview')
538  {
539  $this->administrationRepository->removeIndexedPhashRow($id, $this->pageUid, $depth);
540  $this->redirect('statistic', null, null, ['depth' => $depth, 'mode' => $mode]);
541  }
542 
552  protected function getHref($controller, $action, $parameters = [])
553  {
554  $uriBuilder = $this->objectManager->get(UriBuilder::class);
555  $uriBuilder->setRequest($this->request);
556  return $uriBuilder->reset()->uriFor($action, $parameters, $controller);
557  }
558 
562  protected function getBackendUserAuthentication()
563  {
564  return $GLOBALS['BE_USER'];
565  }
566 
570  protected function getLanguageService()
571  {
572  return $GLOBALS['LANG'];
573  }
574 }
injectAdministrationRepository(AdministrationRepository $administrationRepository)
static trimExplode($delim, $string, $removeEmptyValues=false, $limit=0)
redirect($actionName, $controllerName=null, $extensionName=null, array $arguments=null, $pageUid=null, $delay=0, $statusCode=303)
static getRecord($table, $uid, $fields= '*', $where= '', $useDeleteClause=true)
saveStopwordsKeywordsAction($pageHash, $pageId, $stopwords=[], $keywords=[])
if(TYPO3_MODE=== 'BE') $GLOBALS['TYPO3_CONF_VARS']['SC_OPTIONS']['t3lib/class.t3lib_tsfebeuserauth.php']['frontendEditingController']['default']
static makeInstance($className,...$constructorArguments)
processRequest(\TYPO3\CMS\Extbase\Mvc\RequestInterface $request,\TYPO3\CMS\Extbase\Mvc\ResponseInterface $response)