Passed
Push — master ( 28aace...5efe1b )
by Pauli
04:20
created

AmpacheMiddleware::checkAuthentication()   A

Complexity

Conditions 6
Paths 4

Size

Total Lines 17
Code Lines 11

Duplication

Lines 0
Ratio 0 %

Code Coverage

Tests 0
CRAP Score 42

Importance

Changes 1
Bugs 0 Features 0
Metric Value
cc 6
eloc 11
nc 4
nop 0
dl 0
loc 17
ccs 0
cts 10
cp 0
crap 42
rs 9.2222
c 1
b 0
f 0
1
<?php
2
3
/**
4
 * ownCloud - Music app
5
 *
6
 * This file is licensed under the Affero General Public License version 3 or
7
 * later. See the COPYING file.
8
 *
9
 * @author Morris Jobke <[email protected]>
10
 * @author Pauli Järvinen <[email protected]>
11
 * @copyright Morris Jobke 2013, 2014
12
 * @copyright Pauli Järvinen 2018 - 2020
13
 */
14
15
namespace OCA\Music\Middleware;
16
17
use \OCP\IRequest;
0 ignored issues
show
Bug introduced by
The type OCP\IRequest was not found. Maybe you did not declare it correctly or list all dependencies?

The issue could also be caused by a filter entry in the build configuration. If the path has been excluded in your configuration, e.g. excluded_paths: ["lib/*"], you can move it to the dependency path list as follows:

filter:
    dependency_paths: ["lib/*"]

For further information see https://scrutinizer-ci.com/docs/tools/php/php-scrutinizer/#list-dependency-paths

Loading history...
18
use \OCP\AppFramework\Middleware;
0 ignored issues
show
Bug introduced by
The type OCP\AppFramework\Middleware was not found. Maybe you did not declare it correctly or list all dependencies?

The issue could also be caused by a filter entry in the build configuration. If the path has been excluded in your configuration, e.g. excluded_paths: ["lib/*"], you can move it to the dependency path list as follows:

filter:
    dependency_paths: ["lib/*"]

For further information see https://scrutinizer-ci.com/docs/tools/php/php-scrutinizer/#list-dependency-paths

Loading history...
19
20
use \OCA\Music\AppFramework\BusinessLayer\BusinessLayerException;
21
use \OCA\Music\AppFramework\Core\Logger;
22
use \OCA\Music\Controller\AmpacheController;
23
use \OCA\Music\Db\AmpacheSessionMapper;
24
use \OCA\Music\Utility\AmpacheUser;
25
26
/**
27
 * Checks the authentication on each Ampache API call before the
28
 * request is allowed to be passed to AmpacheController.
29
 * Map identified exceptions from the controller to proper Ampache error results.
30
 */
31
class AmpacheMiddleware extends Middleware {
32
	private $request;
33
	private $ampacheSessionMapper;
34
	private $ampacheUser;
35
	private $logger;
36
37
	/**
38
	 * @param Request $request an instance of the request
0 ignored issues
show
Bug introduced by
The type OCA\Music\Middleware\Request was not found. Maybe you did not declare it correctly or list all dependencies?

The issue could also be caused by a filter entry in the build configuration. If the path has been excluded in your configuration, e.g. excluded_paths: ["lib/*"], you can move it to the dependency path list as follows:

filter:
    dependency_paths: ["lib/*"]

For further information see https://scrutinizer-ci.com/docs/tools/php/php-scrutinizer/#list-dependency-paths

Loading history...
39
	 */
40
	public function __construct(
41
			IRequest $request, AmpacheSessionMapper $ampacheSessionMapper,
42
			AmpacheUser $ampacheUser, Logger $logger) {
43
		$this->request = $request;
44
		$this->ampacheSessionMapper = $ampacheSessionMapper;
45
		$this->ampacheUser = $ampacheUser; // used to share user info with controller
46
		$this->logger = $logger;
47
	}
48
49
	/**
50
	 * This runs all the security checks before a method call. The
51
	 * security checks are determined by inspecting the controller method
52
	 * annotations
53
	 * @param Controller $controller the controller that is being called
0 ignored issues
show
Bug introduced by
The type OCA\Music\Middleware\Controller was not found. Maybe you did not declare it correctly or list all dependencies?

The issue could also be caused by a filter entry in the build configuration. If the path has been excluded in your configuration, e.g. excluded_paths: ["lib/*"], you can move it to the dependency path list as follows:

filter:
    dependency_paths: ["lib/*"]

For further information see https://scrutinizer-ci.com/docs/tools/php/php-scrutinizer/#list-dependency-paths

Loading history...
54
	 * @param string $methodName the name of the method
55
	 * @throws AmpacheException when a security check fails
56
	 */
57
	public function beforeController($controller, $methodName) {
58
59
		if ($controller instanceof AmpacheController) {
60
61
			if ($methodName === 'jsonApi') {
62
				$controller->setJsonMode(true);
63
			}
64
65
			// don't try to authenticate for the handshake request
66
			if ($this->request['action'] !== 'handshake') {
67
				$this->checkAuthentication();
68
			}
69
		}
70
	}
71
72
	private function checkAuthentication() {
73
		$token = $this->request['auth'] ?: $this->request['ssid'] ?: null;
74
75
		if (empty($token)) {
76
			// ping is allowed without a session (but if session token is passed, then it has to be valid)
77
			if ($this->request['action'] !== 'ping') {
78
				throw new AmpacheException('Invalid Login - session token missing', 401);
79
			}
80
		}
81
		else {
82
			$user = $this->ampacheSessionMapper->findByToken($token);
83
			if ($user !== false) {
84
				$this->ampacheUser->setUserId($user);
85
				// also extend the session deadline on any authorized API call
86
				$this->ampacheSessionMapper->extend($token, \time() + AmpacheController::SESSION_EXPIRY_TIME);
87
			} else {
88
				throw new AmpacheException('Invalid Login - invalid session token', 401);
89
			}
90
		}
91
	}
92
93
	/**
94
	 * If an AmpacheException is being caught, the appropiate ampache
95
	 * exception response is rendered
96
	 * @param Controller $controller the controller that is being called
97
	 * @param string $methodName the name of the method that will be called on
98
	 *                           the controller
99
	 * @param \Exception $exception the thrown exception
100
	 * @throws \Exception the passed in exception if it wasn't handled
101
	 * @return Response a Response object if the exception was handled
0 ignored issues
show
Bug introduced by
The type OCA\Music\Middleware\Response was not found. Maybe you did not declare it correctly or list all dependencies?

The issue could also be caused by a filter entry in the build configuration. If the path has been excluded in your configuration, e.g. excluded_paths: ["lib/*"], you can move it to the dependency path list as follows:

filter:
    dependency_paths: ["lib/*"]

For further information see https://scrutinizer-ci.com/docs/tools/php/php-scrutinizer/#list-dependency-paths

Loading history...
102
	 */
103
	public function afterException($controller, $methodName, \Exception $exception) {
104
		if ($controller instanceof AmpacheController) {
105
			if ($exception instanceof AmpacheException) {
106
				return $this->errorResponse($controller, $exception->getCode(), $exception->getMessage());
107
			}
108
			elseif ($exception instanceof BusinessLayerException) {
109
				return $this->errorResponse($controller, 400, 'Entity not found');
110
			}
111
		}
112
		throw $exception;
113
	}
114
115
	private function errorResponse(AmpacheController $controller, $code, $message) {
116
		$this->logger->log($message, 'debug');
117
118
		return $controller->ampacheResponse([
119
			'error' => [
120
				'code' => $code,
121
				'value' => $message
122
			]
123
		]);
124
	}
125
}
126