1<?php 2 3namespace Kanboard\Controller; 4 5use Kanboard\Core\Base; 6use Kanboard\Core\Controller\AccessForbiddenException; 7use Kanboard\Core\Controller\PageNotFoundException; 8 9/** 10 * Base Controller 11 * 12 * @package Kanboard\Controller 13 * @author Frederic Guillot 14 */ 15abstract class BaseController extends Base 16{ 17 /** 18 * Check if the CSRF token from the URL is correct 19 * 20 * @access protected 21 */ 22 protected function checkCSRFParam() 23 { 24 if (! $this->token->validateCSRFToken($this->request->getStringParam('csrf_token'))) { 25 throw new AccessForbiddenException(); 26 } 27 } 28 29 protected function checkReusableCSRFParam() 30 { 31 if (! $this->token->validateReusableCSRFToken($this->request->getRawValue('csrf_token'))) { 32 throw new AccessForbiddenException(); 33 } 34 } 35 36 protected function checkReusableGETCSRFParam() 37 { 38 if (! $this->token->validateReusableCSRFToken($this->request->getStringParam('csrf_token'))) { 39 throw new AccessForbiddenException(); 40 } 41 } 42 43 protected function checkCSRFForm() 44 { 45 if (! $this->token->validateCSRFToken($this->request->getRawValue('csrf_token'))) { 46 throw new AccessForbiddenException(); 47 } 48 } 49 50 /** 51 * Check webhook token 52 * 53 * @access protected 54 */ 55 protected function checkWebhookToken() 56 { 57 if ($this->configModel->get('webhook_token') !== $this->request->getStringParam('token')) { 58 throw AccessForbiddenException::getInstance()->withoutLayout(); 59 } 60 } 61 62 /** 63 * Common method to get a task for task views 64 * 65 * @access protected 66 * @return array 67 * @throws PageNotFoundException 68 * @throws AccessForbiddenException 69 */ 70 protected function getTask() 71 { 72 $project_id = $this->request->getIntegerParam('project_id'); 73 $task = $this->taskFinderModel->getDetails($this->request->getIntegerParam('task_id')); 74 75 if (empty($task)) { 76 throw new PageNotFoundException(); 77 } 78 79 if ($project_id !== 0 && $project_id != $task['project_id']) { 80 throw new AccessForbiddenException(); 81 } 82 83 return $task; 84 } 85 86 /** 87 * Get Task or Project file 88 * 89 * @access protected 90 * @return array 91 * @throws PageNotFoundException 92 * @throws AccessForbiddenException 93 */ 94 protected function getFile() 95 { 96 $task_id = $this->request->getIntegerParam('task_id'); 97 $file_id = $this->request->getIntegerParam('file_id'); 98 $model = 'projectFileModel'; 99 100 if ($task_id > 0) { 101 $model = 'taskFileModel'; 102 } 103 104 $file = $this->$model->getById($file_id); 105 106 if (empty($file)) { 107 throw new PageNotFoundException(); 108 } 109 110 if (isset($file['task_id']) && $file['task_id'] != $task_id) { 111 throw new AccessForbiddenException(); 112 } 113 114 $file['model'] = $model; 115 return $file; 116 } 117 118 /** 119 * Common method to get a project 120 * 121 * @access protected 122 * @param integer $project_id Default project id 123 * @return array 124 * @throws PageNotFoundException 125 */ 126 protected function getProject($project_id = 0) 127 { 128 $project_id = $this->request->getIntegerParam('project_id', $project_id); 129 $project = $this->projectModel->getByIdWithOwnerAndTaskCount($project_id); 130 131 if (empty($project)) { 132 throw new PageNotFoundException(); 133 } 134 135 return $project; 136 } 137 138 /** 139 * Common method to get the user 140 * 141 * @access protected 142 * @return array 143 * @throws PageNotFoundException 144 * @throws AccessForbiddenException 145 */ 146 protected function getUser() 147 { 148 $user = $this->userModel->getById($this->request->getIntegerParam('user_id', $this->userSession->getId())); 149 150 if (empty($user)) { 151 throw new PageNotFoundException(); 152 } 153 154 if (! $this->userSession->isAdmin() && $this->userSession->getId() != $user['id']) { 155 // Always returns a 404 otherwise people might guess which user exist. 156 throw new PageNotFoundException(); 157 } 158 159 return $user; 160 } 161 162 protected function getSubtask(array $task) 163 { 164 $subtask = $this->subtaskModel->getById($this->request->getIntegerParam('subtask_id')); 165 166 if (empty($subtask)) { 167 throw new PageNotFoundException(); 168 } 169 170 if ($subtask['task_id'] != $task['id']) { 171 throw new AccessForbiddenException(); 172 } 173 174 return $subtask; 175 } 176 177 protected function getComment(array $task) 178 { 179 $comment = $this->commentModel->getById($this->request->getIntegerParam('comment_id')); 180 181 if (empty($comment)) { 182 throw new PageNotFoundException(); 183 } 184 185 if (! $this->userSession->isAdmin() && $comment['user_id'] != $this->userSession->getId()) { 186 throw new AccessForbiddenException(); 187 } 188 189 if ($comment['task_id'] != $task['id']) { 190 throw new AccessForbiddenException(); 191 } 192 193 return $comment; 194 } 195 196 protected function getExternalTaskLink(array $task) 197 { 198 $link = $this->taskExternalLinkModel->getById($this->request->getIntegerParam('link_id')); 199 200 if (empty($link)) { 201 throw new PageNotFoundException(); 202 } 203 204 if ($link['task_id'] != $task['id']) { 205 throw new AccessForbiddenException(); 206 } 207 208 return $link; 209 } 210 211 protected function getInternalTaskLink(array $task) 212 { 213 $link = $this->taskLinkModel->getById($this->request->getIntegerParam('link_id')); 214 215 if (empty($link)) { 216 throw new PageNotFoundException(); 217 } 218 219 if ($link['task_id'] != $task['id']) { 220 throw new AccessForbiddenException(); 221 } 222 223 return $link; 224 } 225 226 protected function getColumn(array $project) 227 { 228 $column = $this->columnModel->getById($this->request->getIntegerParam('column_id')); 229 230 if (empty($column)) { 231 throw new PageNotFoundException(); 232 } 233 234 if ($column['project_id'] != $project['id']) { 235 throw new AccessForbiddenException(); 236 } 237 238 return $column; 239 } 240 241 protected function getSwimlane(array $project) 242 { 243 $swimlane = $this->swimlaneModel->getById($this->request->getIntegerParam('swimlane_id')); 244 245 if (empty($swimlane)) { 246 throw new PageNotFoundException(); 247 } 248 249 if ($swimlane['project_id'] != $project['id']) { 250 throw new AccessForbiddenException(); 251 } 252 253 return $swimlane; 254 } 255 256 protected function getCategory(array $project) 257 { 258 $category = $this->categoryModel->getById($this->request->getIntegerParam('category_id')); 259 260 if (empty($category)) { 261 throw new PageNotFoundException(); 262 } 263 264 if ($category['project_id'] != $project['id']) { 265 throw new AccessForbiddenException(); 266 } 267 268 return $category; 269 } 270 271 protected function getProjectTag(array $project) 272 { 273 $tag = $this->tagModel->getById($this->request->getIntegerParam('tag_id')); 274 275 if (empty($tag)) { 276 throw new PageNotFoundException(); 277 } 278 279 if ($tag['project_id'] != $project['id']) { 280 throw new AccessForbiddenException(); 281 } 282 283 return $tag; 284 } 285 286 protected function getAction(array $project) 287 { 288 $action = $this->actionModel->getById($this->request->getIntegerParam('action_id')); 289 290 if (empty($action)) { 291 throw new PageNotFoundException(); 292 } 293 294 if ($action['project_id'] != $project['id']) { 295 throw new AccessForbiddenException(); 296 } 297 298 return $action; 299 } 300 301 protected function getCustomFilter(array $project) 302 { 303 $filter = $this->customFilterModel->getById($this->request->getIntegerParam('filter_id')); 304 305 if (empty($filter)) { 306 throw new PageNotFoundException(); 307 } 308 309 if ($filter['project_id'] != $project['id']) { 310 throw new AccessForbiddenException(); 311 } 312 313 return $filter; 314 } 315 316 /** 317 * Redirect the user after the authentication 318 * 319 * @access protected 320 */ 321 protected function redirectAfterLogin() 322 { 323 if (session_exists('redirectAfterLogin') && ! filter_var(session_get('redirectAfterLogin'), FILTER_VALIDATE_URL)) { 324 $redirect = session_get('redirectAfterLogin'); 325 session_remove('redirectAfterLogin'); 326 $this->response->redirect($redirect); 327 } else { 328 $this->response->redirect($this->helper->url->to('DashboardController', 'show')); 329 } 330 } 331} 332