164ab5140SAndreas Gohr<?php 264ab5140SAndreas Gohr 364ab5140SAndreas Gohrnamespace dokuwiki\Action; 464ab5140SAndreas Gohr 564ab5140SAndreas Gohruse dokuwiki\Action\Exception\ActionAbort; 664ab5140SAndreas Gohr 7ab583a1bSAndreas Gohr/** 8ab583a1bSAndreas Gohr * Class Search 9ab583a1bSAndreas Gohr * 10ab583a1bSAndreas Gohr * Search for pages and content 11ab583a1bSAndreas Gohr * 12ab583a1bSAndreas Gohr * @package dokuwiki\Action 13ab583a1bSAndreas Gohr */ 14*8c7c53b0SAndreas Gohrclass Search extends AbstractAction 15*8c7c53b0SAndreas Gohr{ 1664ab5140SAndreas Gohr 176723156fSAndreas Gohr protected $pageLookupResults = []; 186723156fSAndreas Gohr protected $fullTextResults = []; 196723156fSAndreas Gohr protected $highlight = []; 206639a152SMichael Große 2164ab5140SAndreas Gohr /** @inheritdoc */ 22ec701221SAndreas Gohr public function minimumPermission() { 2364ab5140SAndreas Gohr return AUTH_NONE; 2464ab5140SAndreas Gohr } 2564ab5140SAndreas Gohr 2664ab5140SAndreas Gohr /** 2764ab5140SAndreas Gohr * we only search if a search word was given 2864ab5140SAndreas Gohr * 2964ab5140SAndreas Gohr * @inheritdoc 3064ab5140SAndreas Gohr */ 31b2c9cd19SAndreas Gohr public function checkPreconditions() { 32b2c9cd19SAndreas Gohr parent::checkPreconditions(); 3364ab5140SAndreas Gohr } 3464ab5140SAndreas Gohr 35d09b5b64SMichael Große public function preProcess() 36d09b5b64SMichael Große { 37d22b78c8SMichael Große global $QUERY, $ID, $conf, $INPUT; 38d22b78c8SMichael Große $s = cleanID($QUERY); 39d22b78c8SMichael Große 403286c65dSMichael Große if ($ID !== $conf['start'] && !$INPUT->has('q')) { 41d22b78c8SMichael Große parse_str($INPUT->server->str('QUERY_STRING'), $urlParts); 42d22b78c8SMichael Große $urlParts['q'] = $urlParts['id']; 43918638dcSSchplurtz le Déboulonné unset($urlParts['id']); 44cc21cb50SAndreas Gohr $url = wl($ID, $urlParts, true, '&'); 45d22b78c8SMichael Große send_redirect($url); 46d22b78c8SMichael Große } 47d22b78c8SMichael Große 48d22b78c8SMichael Große if ($s === '') throw new ActionAbort(); 49d09b5b64SMichael Große $this->adjustGlobalQuery(); 50d09b5b64SMichael Große } 51d09b5b64SMichael Große 5264ab5140SAndreas Gohr /** @inheritdoc */ 53d09b5b64SMichael Große public function tplContent() 54d09b5b64SMichael Große { 556639a152SMichael Große $this->execute(); 566639a152SMichael Große 576639a152SMichael Große $search = new \dokuwiki\Ui\Search($this->pageLookupResults, $this->fullTextResults, $this->highlight); 5821fcef82SMichael Große $search->show(); 5964ab5140SAndreas Gohr } 60d09b5b64SMichael Große 616639a152SMichael Große 626639a152SMichael Große /** 636639a152SMichael Große * run the search 646639a152SMichael Große */ 656639a152SMichael Große protected function execute() 666639a152SMichael Große { 676639a152SMichael Große global $INPUT, $QUERY; 68422bbbc6SMichael Große $after = $INPUT->str('min'); 69422bbbc6SMichael Große $before = $INPUT->str('max'); 703850270cSMichael Große $this->pageLookupResults = ft_pageLookup($QUERY, true, useHeading('navigation'), $after, $before); 713850270cSMichael Große $this->fullTextResults = ft_pageSearch($QUERY, $highlight, $INPUT->str('srt'), $after, $before); 726639a152SMichael Große $this->highlight = $highlight; 736639a152SMichael Große } 746639a152SMichael Große 75d09b5b64SMichael Große /** 7613ce475dSAndreas Gohr * Adjust the global query accordingly to the config search_nslimit and search_fragment 77d09b5b64SMichael Große * 78d09b5b64SMichael Große * This will only do something if the search didn't originate from the form on the searchpage itself 79d09b5b64SMichael Große */ 80d09b5b64SMichael Große protected function adjustGlobalQuery() 81d09b5b64SMichael Große { 82340f849aSMichael Große global $conf, $INPUT, $QUERY, $ID; 83d09b5b64SMichael Große 841265b193SMichael Große if ($INPUT->bool('sf')) { 85d09b5b64SMichael Große return; 86d09b5b64SMichael Große } 87d09b5b64SMichael Große 88d09b5b64SMichael Große $Indexer = idx_get_indexer(); 89d09b5b64SMichael Große $parsedQuery = ft_queryParser($Indexer, $QUERY); 90d09b5b64SMichael Große 91d09b5b64SMichael Große if (empty($parsedQuery['ns']) && empty($parsedQuery['notns'])) { 9213ce475dSAndreas Gohr if ($conf['search_nslimit'] > 0) { 93340f849aSMichael Große if (getNS($ID) !== false) { 94340f849aSMichael Große $nsParts = explode(':', getNS($ID)); 9513ce475dSAndreas Gohr $ns = implode(':', array_slice($nsParts, 0, $conf['search_nslimit'])); 96d09b5b64SMichael Große $QUERY .= " @$ns"; 97d09b5b64SMichael Große } 98d09b5b64SMichael Große } 99d09b5b64SMichael Große } 100d09b5b64SMichael Große 10113ce475dSAndreas Gohr if ($conf['search_fragment'] !== 'exact') { 102d09b5b64SMichael Große if (empty(array_diff($parsedQuery['words'], $parsedQuery['and']))) { 103d09b5b64SMichael Große if (strpos($QUERY, '*') === false) { 104d09b5b64SMichael Große $queryParts = explode(' ', $QUERY); 105d09b5b64SMichael Große $queryParts = array_map(function ($part) { 106d09b5b64SMichael Große if (strpos($part, '@') === 0) { 107d09b5b64SMichael Große return $part; 108d09b5b64SMichael Große } 109d09b5b64SMichael Große if (strpos($part, 'ns:') === 0) { 110d09b5b64SMichael Große return $part; 111d09b5b64SMichael Große } 112d09b5b64SMichael Große if (strpos($part, '^') === 0) { 113d09b5b64SMichael Große return $part; 114d09b5b64SMichael Große } 115d09b5b64SMichael Große if (strpos($part, '-ns:') === 0) { 116d09b5b64SMichael Große return $part; 117d09b5b64SMichael Große } 118d09b5b64SMichael Große 119d09b5b64SMichael Große global $conf; 120d09b5b64SMichael Große 12113ce475dSAndreas Gohr if ($conf['search_fragment'] === 'starts_with') { 122d09b5b64SMichael Große return $part . '*'; 123d09b5b64SMichael Große } 12413ce475dSAndreas Gohr if ($conf['search_fragment'] === 'ends_with') { 125d09b5b64SMichael Große return '*' . $part; 126d09b5b64SMichael Große } 127d09b5b64SMichael Große 128d09b5b64SMichael Große return '*' . $part . '*'; 129d09b5b64SMichael Große 130d09b5b64SMichael Große }, $queryParts); 131d09b5b64SMichael Große $QUERY = implode(' ', $queryParts); 132d09b5b64SMichael Große } 133d09b5b64SMichael Große } 134d09b5b64SMichael Große } 135d09b5b64SMichael Große } 13664ab5140SAndreas Gohr} 137