sunnysideup /
silverstripe-searchplus
This project does not seem to handle request data directly as such no vulnerable execution paths were found.
include, or for example
via PHP's auto-loading mechanism.
These results are based on our legacy PHP analysis, consider migrating to our new PHP analysis engine instead. Learn more
| 1 | <?php |
||
| 2 | /* |
||
| 3 | *@author: nicolaas [at] sunnysideup.co.nz |
||
| 4 | * |
||
| 5 | * |
||
| 6 | **/ |
||
| 7 | |||
| 8 | class SearchPlusPage extends Page |
||
| 9 | { |
||
| 10 | private static $add_action = 'Search Plus Page'; |
||
|
0 ignored issues
–
show
|
|||
| 11 | |||
| 12 | private static $can_be_root = true; |
||
|
0 ignored issues
–
show
|
|||
| 13 | |||
| 14 | private static $icon = 'searchplus/images/treeicons/SearchPlusPage'; |
||
|
0 ignored issues
–
show
|
|||
| 15 | |||
| 16 | private static $db = array(); |
||
|
0 ignored issues
–
show
|
|||
| 17 | |||
| 18 | private static $has_many = array( |
||
|
0 ignored issues
–
show
|
|||
| 19 | "RecommendedSearchPlusSections" => "RecommendedSearchPlusSection" |
||
| 20 | ); |
||
| 21 | |||
| 22 | public function canCreate($member = null) |
||
| 23 | { |
||
| 24 | return SearchPlusPage::get()->count ? false : true; |
||
| 25 | } |
||
| 26 | |||
| 27 | public function canDelete($member = null) |
||
| 28 | { |
||
| 29 | return false; |
||
| 30 | } |
||
| 31 | |||
| 32 | private static $result_length = 10; |
||
|
0 ignored issues
–
show
|
|||
| 33 | |||
| 34 | public function getCMSFields($params = null) |
||
| 35 | { |
||
| 36 | $fields = parent::getCMSFields($params); |
||
| 37 | $fields->addFieldToTab( |
||
| 38 | "Root.RecommendedSections", |
||
| 39 | new GridField( |
||
| 40 | $name = "RecommendedSearchPlusSections", |
||
| 41 | $sourceClass = "Recommended Extras", |
||
| 42 | RecommendedSearchPlusSection::get() |
||
| 43 | ) |
||
| 44 | ); |
||
| 45 | $fields->addFieldToTab( |
||
| 46 | "Root.PopularSearchPhrases", |
||
| 47 | new LiteralField( |
||
| 48 | "PopularSearchPhrasesLink", |
||
| 49 | '<p>Please make sure to regular <a href="'.$this->Link().'popularsearchwords/100/10">review the most popular search phrases</a> and to add recommendations for each</a>.</p>' |
||
| 50 | ) |
||
| 51 | ); |
||
| 52 | return $fields; |
||
| 53 | } |
||
| 54 | } |
||
| 55 | |||
| 56 | class SearchPlusPage_Controller extends Page_Controller |
||
| 57 | { |
||
| 58 | public function init() |
||
| 59 | { |
||
| 60 | parent::init(); |
||
| 61 | Requirements::javascript("searchplus/javascript/searchpluspage.js"); |
||
| 62 | } |
||
| 63 | |||
| 64 | private static $search_history_object = null; |
||
| 65 | |||
| 66 | public function Form() |
||
| 67 | { |
||
| 68 | return $this->SearchPlusForm("MainSearchForm", "MainSearch", ""); |
||
| 69 | } |
||
| 70 | |||
| 71 | public function results($data) |
||
| 72 | { |
||
| 73 | if (isset($data["Search"]) || isset($data["MainSearch"])) { |
||
| 74 | // there is a search |
||
| 75 | Requirements::themedCSS("searchpluspage_searchresults", "searchplus"); |
||
| 76 | if (isset($data["MainSearch"]) || !isset($data["Search"])) { |
||
| 77 | $data["Search"] = $data["MainSearch"]; |
||
| 78 | } |
||
| 79 | //redirect if needed |
||
| 80 | $data["Search"] = urldecode($data["Search"]); |
||
| 81 | $form = $this->SearchPlusForm(); |
||
| 82 | if (!isset($_GET["redirect"])) { |
||
| 83 | self::$search_history_object = SearchHistory::add_entry($data["Search"]); |
||
| 84 | if (self::$search_history_object) { |
||
| 85 | if (self::$search_history_object->RedirectTo && self::$search_history_object->RedirectTo != self::$search_history_object->Title) { |
||
| 86 | $this->redirect( |
||
| 87 | str_replace( |
||
| 88 | "Search=".urlencode(self::$search_history_object->Title), |
||
| 89 | "Search=".urlencode(self::$search_history_object->RedirectTo), |
||
| 90 | HTTP::RAW_setGetVar('redirect', 1, null) |
||
| 91 | ) |
||
| 92 | ); |
||
| 93 | } |
||
| 94 | } |
||
| 95 | } else { |
||
| 96 | self::$search_history_object = SearchHistory::find_entry($data["Search"]); |
||
| 97 | } |
||
| 98 | //load data for recommended pages |
||
| 99 | $recommendationsSet = $this->Recommendations(); |
||
| 100 | $matchArrayRecommended = array(); |
||
| 101 | $matchArrayResults = array(); |
||
| 102 | if ($recommendationsSet) { |
||
| 103 | foreach ($recommendationsSet as $rec) { |
||
| 104 | $matchArrayRecommended[$rec->ClassName.$rec->ID] = $rec->ClassName.$rec->ID; |
||
| 105 | } |
||
| 106 | } |
||
| 107 | //work out positions |
||
| 108 | $results = $form->getResults(); |
||
| 109 | $query = $form->getSearchQuery(); |
||
| 110 | $startingPosition = isset($_REQUEST["start"]) ? $_REQUEST["start"] : 0; |
||
| 111 | $endingPosition = $startingPosition + Config::inst()->get("SearchPlusPage", "result_length"); |
||
| 112 | $startingPosition++; |
||
| 113 | if ($results) { |
||
| 114 | $total = $results->TotalItems(); |
||
| 115 | } else { |
||
| 116 | $total = 0; |
||
| 117 | } |
||
| 118 | if ($endingPosition > $total) { |
||
| 119 | $endingPosition = $total; |
||
| 120 | } |
||
| 121 | //highlight search text and check which ones are recommended |
||
| 122 | if ($total) { |
||
| 123 | foreach ($results as $result) { |
||
| 124 | $title = $result->getTitle(); |
||
| 125 | $dbField = DBField::create_field($className = "Text", $title); |
||
| 126 | $result->HighlightedTitle = $dbField->ContextSummary(); |
||
| 127 | $result->IsRecommended = false; |
||
| 128 | $matchArrayResults[$result->ClassName.$result->ID] = $result->ClassName.$result->ID; |
||
| 129 | if (isset($matchArrayRecommended[$result->ClassName.$result->ID])) { |
||
| 130 | $result->IsRecommended = true; |
||
| 131 | } |
||
| 132 | } |
||
| 133 | } |
||
| 134 | $data = array( |
||
| 135 | 'Results' => $results, |
||
| 136 | 'Query' => $query, |
||
| 137 | 'From' => $startingPosition, |
||
| 138 | 'To' => $endingPosition, |
||
| 139 | 'Total' => $total, |
||
| 140 | 'HasResults' => $total ? true : false, |
||
| 141 | 'Recommendations' => $this->Recommendations(), |
||
| 142 | 'RecommendedSearchPlusSection' => $this->dataRecord->RecommendedSearchPlusSections(), |
||
| 143 | ); |
||
| 144 | $this->Title = 'Search Results'; |
||
| 145 | $this->MenuTitle = 'Search Results'; |
||
| 146 | return $this->customise($data)->renderWith(array('SearchPlusPage_results', 'Page')); |
||
| 147 | } |
||
| 148 | return array(); |
||
| 149 | } |
||
| 150 | |||
| 151 | public function Recommendations() |
||
| 152 | { |
||
| 153 | if (self::$search_history_object) { |
||
| 154 | return self::$search_history_object->Recommendations(); |
||
| 155 | } |
||
| 156 | } |
||
| 157 | |||
| 158 | public function HasPopularSearchWords() |
||
| 159 | { |
||
| 160 | return Permission::check("ADMIN"); |
||
| 161 | } |
||
| 162 | |||
| 163 | public function PopularSearchWordsForAllUsers($days = 100, $limit = 7) |
||
| 164 | { |
||
| 165 | $do = $this->getPopularSearchWords($days, $limit, $mergeRedirects = true); |
||
| 166 | return $do->DataByCount; |
||
| 167 | } |
||
| 168 | |||
| 169 | public function popularsearchwords(HTTPRequest $HTTPRequest) |
||
| 170 | { |
||
| 171 | if (!$this->HasPopularSearchWords()) { |
||
| 172 | Security::permissionFailure($this, _t('Security.PERMFAILURE', ' This page is secured and you need administrator rights to access it. Enter your credentials below and we will send you right along.')); |
||
| 173 | return; |
||
| 174 | } |
||
| 175 | Requirements::themedCSS("popularsearches", "searchplus"); |
||
| 176 | $days = intval($HTTPRequest->param("ID")); |
||
| 177 | if (!$days) { |
||
| 178 | $days = 100; |
||
| 179 | } |
||
| 180 | $limit = intval($HTTPRequest->param("OtherID")+0); |
||
| 181 | if (!$limit) { |
||
| 182 | $limit++; |
||
| 183 | } |
||
| 184 | $do = $this->getPopularSearchWords($days, $limit); |
||
| 185 | $page->MenuTitle = $do->Title; |
||
| 186 | $do->Title = $do->Title; |
||
| 187 | return $this->customise($do)->renderWith(array('SearchPlusPage_popularsearches', 'Page')); |
||
| 188 | } |
||
| 189 | |||
| 190 | protected function getPopularSearchWords($days, $limit, $mergeRedirects = false) |
||
| 191 | { |
||
| 192 | $extraWhere = ''; |
||
| 193 | if ($mergeRedirects) { |
||
| 194 | $extraWhere = " AND {$bt}RedirectTo{$bt} = '' OR {$bt}RedirectTo{$bt} IS NULL"; |
||
| 195 | } |
||
| 196 | $data = DB::query("
|
||
| 197 | SELECT COUNT(\"SearchHistoryLog\".\"ID\") count, \"SearchHistory\".\"RedirectTo\" RedirectTo, \"SearchHistory\".\"Title\" title, \"SearchHistory\".\"ID\" id |
||
| 198 | FROM \"SearchHistoryLog\" |
||
| 199 | INNER JOIN \"SearchHistory\" ON \"SearchHistory\".\"ID\" = \"SearchHistoryLog\".\"SearchedForID\" |
||
| 200 | WHERE \"SearchHistoryLog\".\"Created\" > ( NOW() - INTERVAL $days DAY ) ".$extraWhere." |
||
| 201 | GROUP BY \"SearchHistory\".\"ID\" |
||
| 202 | ORDER BY count DESC |
||
| 203 | LIMIT 0, $limit |
||
| 204 | "); |
||
| 205 | $do = new DataObject(); |
||
| 206 | $do->Title = "Search phrase popularity, $days days $limit entries"; |
||
| 207 | $do->DataByCount = new ArrayList(); |
||
| 208 | $do->DataByTitle = new ArrayList(); |
||
| 209 | $do->Limit = $limit; |
||
| 210 | $do->Days = $days; |
||
| 211 | $list = array(); |
||
| 212 | foreach ($data as $key => $row) { |
||
| 213 | if (!$key) { |
||
| 214 | $max = $row["count"]; |
||
| 215 | } |
||
| 216 | if ($mergeRedirects) { |
||
| 217 | $data = DB::query("
|
||
| 218 | SELECT COUNT(\"SearchHistoryLog\".\"ID\") count |
||
| 219 | FROM \"SearchHistoryLog\" |
||
| 220 | INNER JOIN \"SearchHistory\" |
||
| 221 | ON \"SearchHistory\".\"ID\" = \"SearchHistoryLog\".\"SearchedForID\" |
||
| 222 | WHERE \"SearchHistoryLog\".\"Created\" > ( NOW() - INTERVAL $days DAY ) |
||
| 223 | AND \"SearchHistory\".\"RedirectTo\" = '".$row["title"]."' |
||
| 224 | GROUP BY \"SearchHistory\".\"RedirectTo\" |
||
| 225 | ORDER BY count |
||
| 226 | DESC LIMIT 1 |
||
| 227 | "); |
||
| 228 | if ($data) { |
||
| 229 | $extraCounts = $data->value(); |
||
| 230 | } |
||
| 231 | $row["count"] += $extraCounts; |
||
| 232 | } |
||
| 233 | $percentage = floor(($row["count"]/$max)*100); |
||
| 234 | $subDataSet = new ArrayData( |
||
| 235 | array( |
||
| 236 | "ParentID" => $row["id"], |
||
| 237 | "Title" => $row["title"], |
||
| 238 | "Width" => $percentage, |
||
| 239 | "Count" => $row["count"], |
||
| 240 | "Link" => $this->Link()."results/?Search=".urldecode($row["title"])."&action_results=Search" |
||
| 241 | ) |
||
| 242 | ); |
||
| 243 | $list[$row["title"]] = $subDataSet; |
||
| 244 | $do->DataByCount->push($subDataSet); |
||
| 245 | } |
||
| 246 | ksort($list); |
||
| 247 | foreach ($list as $subDataSet) { |
||
| 248 | $do->DataByTitle->push($subDataSet); |
||
| 249 | } |
||
| 250 | return $do; |
||
| 251 | } |
||
| 252 | } |
||
| 253 |
This check marks private properties in classes that are never used. Those properties can be removed.