Completed
Push — master ( 25c34c...cd9f03 )
by
unknown
19:21 queued 14s
created
apps/files_external/lib/AppInfo/Application.php 1 patch
Indentation   +99 added lines, -99 removed lines patch added patch discarded remove patch
@@ -59,103 +59,103 @@
 block discarded – undo
59 59
  * @package OCA\Files_External\AppInfo
60 60
  */
61 61
 class Application extends App implements IBackendProvider, IAuthMechanismProvider, IBootstrap {
62
-	public const APP_ID = 'files_external';
63
-
64
-	/**
65
-	 * Application constructor.
66
-	 *
67
-	 * @throws QueryException
68
-	 */
69
-	public function __construct(array $urlParams = []) {
70
-		parent::__construct(self::APP_ID, $urlParams);
71
-	}
72
-
73
-	public function register(IRegistrationContext $context): void {
74
-		$context->registerEventListener(UserDeletedEvent::class, UserDeletedListener::class);
75
-		$context->registerEventListener(GroupDeletedEvent::class, GroupDeletedListener::class);
76
-		$context->registerEventListener(LoadAdditionalScriptsEvent::class, LoadAdditionalListener::class);
77
-		$context->registerConfigLexicon(ConfigLexicon::class);
78
-	}
79
-
80
-	public function boot(IBootContext $context): void {
81
-		$context->injectFn(function (IMountProviderCollection $mountProviderCollection, ConfigAdapter $configAdapter): void {
82
-			$mountProviderCollection->registerProvider($configAdapter);
83
-		});
84
-		$context->injectFn(function (BackendService $backendService, UserPlaceholderHandler $userConfigHandler): void {
85
-			$backendService->registerBackendProvider($this);
86
-			$backendService->registerAuthMechanismProvider($this);
87
-			$backendService->registerConfigHandler('user', function () use ($userConfigHandler) {
88
-				return $userConfigHandler;
89
-			});
90
-		});
91
-
92
-		// force-load auth mechanisms since some will register hooks
93
-		// TODO: obsolete these and use the TokenProvider to get the user's password from the session
94
-		$this->getAuthMechanisms();
95
-	}
96
-
97
-	/**
98
-	 * @{inheritdoc}
99
-	 */
100
-	public function getBackends() {
101
-		$container = $this->getContainer();
102
-
103
-		$backends = [
104
-			$container->get(Local::class),
105
-			$container->get(FTP::class),
106
-			$container->get(DAV::class),
107
-			$container->get(OwnCloud::class),
108
-			$container->get(SFTP::class),
109
-			$container->get(AmazonS3::class),
110
-			$container->get(Swift::class),
111
-			$container->get(SFTP_Key::class),
112
-			$container->get(SMB::class),
113
-			$container->get(SMB_OC::class),
114
-		];
115
-
116
-		return $backends;
117
-	}
118
-
119
-	/**
120
-	 * @{inheritdoc}
121
-	 */
122
-	public function getAuthMechanisms() {
123
-		$container = $this->getContainer();
124
-
125
-		return [
126
-			// AuthMechanism::SCHEME_NULL mechanism
127
-			$container->get(NullMechanism::class),
128
-
129
-			// AuthMechanism::SCHEME_BUILTIN mechanism
130
-			$container->get(Builtin::class),
131
-
132
-			// AuthMechanism::SCHEME_PASSWORD mechanisms
133
-			$container->get(Password::class),
134
-			$container->get(SessionCredentials::class),
135
-			$container->get(LoginCredentials::class),
136
-			$container->get(UserProvided::class),
137
-			$container->get(GlobalAuth::class),
138
-			$container->get(UserGlobalAuth::class),
139
-
140
-			// AuthMechanism::SCHEME_OAUTH1 mechanisms
141
-			$container->get(OAuth1::class),
142
-
143
-			// AuthMechanism::SCHEME_OAUTH2 mechanisms
144
-			$container->get(OAuth2::class),
145
-
146
-			// AuthMechanism::SCHEME_PUBLICKEY mechanisms
147
-			$container->get(RSA::class),
148
-			$container->get(RSAPrivateKey::class),
149
-
150
-			// AuthMechanism::SCHEME_OPENSTACK mechanisms
151
-			$container->get(OpenStackV2::class),
152
-			$container->get(OpenStackV3::class),
153
-			$container->get(Rackspace::class),
154
-
155
-			// Specialized mechanisms
156
-			$container->get(AccessKey::class),
157
-			$container->get(KerberosAuth::class),
158
-			$container->get(KerberosApacheAuth::class),
159
-		];
160
-	}
62
+    public const APP_ID = 'files_external';
63
+
64
+    /**
65
+     * Application constructor.
66
+     *
67
+     * @throws QueryException
68
+     */
69
+    public function __construct(array $urlParams = []) {
70
+        parent::__construct(self::APP_ID, $urlParams);
71
+    }
72
+
73
+    public function register(IRegistrationContext $context): void {
74
+        $context->registerEventListener(UserDeletedEvent::class, UserDeletedListener::class);
75
+        $context->registerEventListener(GroupDeletedEvent::class, GroupDeletedListener::class);
76
+        $context->registerEventListener(LoadAdditionalScriptsEvent::class, LoadAdditionalListener::class);
77
+        $context->registerConfigLexicon(ConfigLexicon::class);
78
+    }
79
+
80
+    public function boot(IBootContext $context): void {
81
+        $context->injectFn(function (IMountProviderCollection $mountProviderCollection, ConfigAdapter $configAdapter): void {
82
+            $mountProviderCollection->registerProvider($configAdapter);
83
+        });
84
+        $context->injectFn(function (BackendService $backendService, UserPlaceholderHandler $userConfigHandler): void {
85
+            $backendService->registerBackendProvider($this);
86
+            $backendService->registerAuthMechanismProvider($this);
87
+            $backendService->registerConfigHandler('user', function () use ($userConfigHandler) {
88
+                return $userConfigHandler;
89
+            });
90
+        });
91
+
92
+        // force-load auth mechanisms since some will register hooks
93
+        // TODO: obsolete these and use the TokenProvider to get the user's password from the session
94
+        $this->getAuthMechanisms();
95
+    }
96
+
97
+    /**
98
+     * @{inheritdoc}
99
+     */
100
+    public function getBackends() {
101
+        $container = $this->getContainer();
102
+
103
+        $backends = [
104
+            $container->get(Local::class),
105
+            $container->get(FTP::class),
106
+            $container->get(DAV::class),
107
+            $container->get(OwnCloud::class),
108
+            $container->get(SFTP::class),
109
+            $container->get(AmazonS3::class),
110
+            $container->get(Swift::class),
111
+            $container->get(SFTP_Key::class),
112
+            $container->get(SMB::class),
113
+            $container->get(SMB_OC::class),
114
+        ];
115
+
116
+        return $backends;
117
+    }
118
+
119
+    /**
120
+     * @{inheritdoc}
121
+     */
122
+    public function getAuthMechanisms() {
123
+        $container = $this->getContainer();
124
+
125
+        return [
126
+            // AuthMechanism::SCHEME_NULL mechanism
127
+            $container->get(NullMechanism::class),
128
+
129
+            // AuthMechanism::SCHEME_BUILTIN mechanism
130
+            $container->get(Builtin::class),
131
+
132
+            // AuthMechanism::SCHEME_PASSWORD mechanisms
133
+            $container->get(Password::class),
134
+            $container->get(SessionCredentials::class),
135
+            $container->get(LoginCredentials::class),
136
+            $container->get(UserProvided::class),
137
+            $container->get(GlobalAuth::class),
138
+            $container->get(UserGlobalAuth::class),
139
+
140
+            // AuthMechanism::SCHEME_OAUTH1 mechanisms
141
+            $container->get(OAuth1::class),
142
+
143
+            // AuthMechanism::SCHEME_OAUTH2 mechanisms
144
+            $container->get(OAuth2::class),
145
+
146
+            // AuthMechanism::SCHEME_PUBLICKEY mechanisms
147
+            $container->get(RSA::class),
148
+            $container->get(RSAPrivateKey::class),
149
+
150
+            // AuthMechanism::SCHEME_OPENSTACK mechanisms
151
+            $container->get(OpenStackV2::class),
152
+            $container->get(OpenStackV3::class),
153
+            $container->get(Rackspace::class),
154
+
155
+            // Specialized mechanisms
156
+            $container->get(AccessKey::class),
157
+            $container->get(KerberosAuth::class),
158
+            $container->get(KerberosApacheAuth::class),
159
+        ];
160
+    }
161 161
 }
Please login to merge, or discard this patch.
apps/files_external/lib/Service/BackendService.php 1 patch
Indentation   +314 added lines, -314 removed lines patch added patch discarded remove patch
@@ -22,318 +22,318 @@
 block discarded – undo
22 22
  */
23 23
 class BackendService {
24 24
 
25
-	/** Visibility constants for VisibilityTrait */
26
-	public const VISIBILITY_NONE = 0;
27
-	public const VISIBILITY_PERSONAL = 1;
28
-	public const VISIBILITY_ADMIN = 2;
29
-	//const VISIBILITY_ALIENS = 4;
30
-
31
-	public const VISIBILITY_DEFAULT = 3; // PERSONAL | ADMIN
32
-
33
-	/** Priority constants for PriorityTrait */
34
-	public const PRIORITY_DEFAULT = 100;
35
-
36
-	/** @var bool */
37
-	private $userMountingAllowed = true;
38
-
39
-	/** @var string[] */
40
-	private $userMountingBackends = [];
41
-
42
-	/** @var Backend[] */
43
-	private $backends = [];
44
-
45
-	/** @var IBackendProvider[] */
46
-	private $backendProviders = [];
47
-
48
-	/** @var AuthMechanism[] */
49
-	private $authMechanisms = [];
50
-
51
-	/** @var IAuthMechanismProvider[] */
52
-	private $authMechanismProviders = [];
53
-
54
-	/** @var callable[] */
55
-	private $configHandlerLoaders = [];
56
-
57
-	private $configHandlers = [];
58
-
59
-	public function __construct(
60
-		protected IAppConfig $appConfig,
61
-	) {
62
-		// Load config values
63
-		$this->userMountingAllowed = $appConfig->getValueBool('files_external', ConfigLexicon::ALLOW_USER_MOUNTING);
64
-		$this->userMountingBackends = explode(',', $appConfig->getValueString('files_external', ConfigLexicon::USER_MOUNTING_BACKENDS));
65
-
66
-		// if no backend is in the list an empty string is in the array and user mounting is disabled
67
-		if ($this->userMountingBackends === ['']) {
68
-			$this->userMountingAllowed = false;
69
-		}
70
-	}
71
-
72
-	/**
73
-	 * Register a backend provider
74
-	 *
75
-	 * @since 9.1.0
76
-	 * @param IBackendProvider $provider
77
-	 */
78
-	public function registerBackendProvider(IBackendProvider $provider) {
79
-		$this->backendProviders[] = $provider;
80
-	}
81
-
82
-	private function callForRegistrations() {
83
-		static $eventSent = false;
84
-		if (!$eventSent) {
85
-			Server::get(IEventDispatcher::class)->dispatch(
86
-				'OCA\\Files_External::loadAdditionalBackends',
87
-				new GenericEvent()
88
-			);
89
-			$eventSent = true;
90
-		}
91
-	}
92
-
93
-	private function loadBackendProviders() {
94
-		$this->callForRegistrations();
95
-		foreach ($this->backendProviders as $provider) {
96
-			$this->registerBackends($provider->getBackends());
97
-		}
98
-		$this->backendProviders = [];
99
-	}
100
-
101
-	/**
102
-	 * Register an auth mechanism provider
103
-	 *
104
-	 * @since 9.1.0
105
-	 * @param IAuthMechanismProvider $provider
106
-	 */
107
-	public function registerAuthMechanismProvider(IAuthMechanismProvider $provider) {
108
-		$this->authMechanismProviders[] = $provider;
109
-	}
110
-
111
-	private function loadAuthMechanismProviders() {
112
-		$this->callForRegistrations();
113
-		foreach ($this->authMechanismProviders as $provider) {
114
-			$this->registerAuthMechanisms($provider->getAuthMechanisms());
115
-		}
116
-		$this->authMechanismProviders = [];
117
-	}
118
-
119
-	/**
120
-	 * Register a backend
121
-	 *
122
-	 * @deprecated 9.1.0 use registerBackendProvider()
123
-	 * @param Backend $backend
124
-	 */
125
-	public function registerBackend(Backend $backend) {
126
-		if (!$this->isAllowedUserBackend($backend)) {
127
-			$backend->removeVisibility(BackendService::VISIBILITY_PERSONAL);
128
-		}
129
-		foreach ($backend->getIdentifierAliases() as $alias) {
130
-			$this->backends[$alias] = $backend;
131
-		}
132
-	}
133
-
134
-	/**
135
-	 * @deprecated 9.1.0 use registerBackendProvider()
136
-	 * @param Backend[] $backends
137
-	 */
138
-	public function registerBackends(array $backends) {
139
-		foreach ($backends as $backend) {
140
-			$this->registerBackend($backend);
141
-		}
142
-	}
143
-	/**
144
-	 * Register an authentication mechanism
145
-	 *
146
-	 * @deprecated 9.1.0 use registerAuthMechanismProvider()
147
-	 * @param AuthMechanism $authMech
148
-	 */
149
-	public function registerAuthMechanism(AuthMechanism $authMech) {
150
-		if (!$this->isAllowedAuthMechanism($authMech)) {
151
-			$authMech->removeVisibility(BackendService::VISIBILITY_PERSONAL);
152
-		}
153
-		foreach ($authMech->getIdentifierAliases() as $alias) {
154
-			$this->authMechanisms[$alias] = $authMech;
155
-		}
156
-	}
157
-
158
-	/**
159
-	 * @deprecated 9.1.0 use registerAuthMechanismProvider()
160
-	 * @param AuthMechanism[] $mechanisms
161
-	 */
162
-	public function registerAuthMechanisms(array $mechanisms) {
163
-		foreach ($mechanisms as $mechanism) {
164
-			$this->registerAuthMechanism($mechanism);
165
-		}
166
-	}
167
-
168
-	/**
169
-	 * Get all backends
170
-	 *
171
-	 * @return Backend[]
172
-	 */
173
-	public function getBackends() {
174
-		$this->loadBackendProviders();
175
-		// only return real identifiers, no aliases
176
-		$backends = [];
177
-		foreach ($this->backends as $backend) {
178
-			$backends[$backend->getIdentifier()] = $backend;
179
-		}
180
-		return $backends;
181
-	}
182
-
183
-	/**
184
-	 * Get all available backends
185
-	 *
186
-	 * @return Backend[]
187
-	 */
188
-	public function getAvailableBackends() {
189
-		return array_filter($this->getBackends(), function ($backend) {
190
-			return !$backend->checkDependencies();
191
-		});
192
-	}
193
-
194
-	/**
195
-	 * @param string $identifier
196
-	 * @return Backend|null
197
-	 */
198
-	public function getBackend($identifier) {
199
-		$this->loadBackendProviders();
200
-		if (isset($this->backends[$identifier])) {
201
-			return $this->backends[$identifier];
202
-		}
203
-		return null;
204
-	}
205
-
206
-	/**
207
-	 * Get all authentication mechanisms
208
-	 *
209
-	 * @return AuthMechanism[]
210
-	 */
211
-	public function getAuthMechanisms() {
212
-		$this->loadAuthMechanismProviders();
213
-		// only return real identifiers, no aliases
214
-		$mechanisms = [];
215
-		foreach ($this->authMechanisms as $mechanism) {
216
-			$mechanisms[$mechanism->getIdentifier()] = $mechanism;
217
-		}
218
-		return $mechanisms;
219
-	}
220
-
221
-	/**
222
-	 * Get all authentication mechanisms for schemes
223
-	 *
224
-	 * @param string[] $schemes
225
-	 * @return AuthMechanism[]
226
-	 */
227
-	public function getAuthMechanismsByScheme(array $schemes) {
228
-		return array_filter($this->getAuthMechanisms(), function ($authMech) use ($schemes) {
229
-			return in_array($authMech->getScheme(), $schemes, true);
230
-		});
231
-	}
232
-
233
-	/**
234
-	 * @param string $identifier
235
-	 * @return AuthMechanism|null
236
-	 */
237
-	public function getAuthMechanism($identifier) {
238
-		$this->loadAuthMechanismProviders();
239
-		if (isset($this->authMechanisms[$identifier])) {
240
-			return $this->authMechanisms[$identifier];
241
-		}
242
-		return null;
243
-	}
244
-
245
-	/**
246
-	 * @return bool
247
-	 */
248
-	public function isUserMountingAllowed() {
249
-		return $this->userMountingAllowed;
250
-	}
251
-
252
-	/**
253
-	 * Check a backend if a user is allowed to mount it
254
-	 *
255
-	 * @param Backend $backend
256
-	 * @return bool
257
-	 */
258
-	protected function isAllowedUserBackend(Backend $backend) {
259
-		if ($this->userMountingAllowed &&
260
-			array_intersect($backend->getIdentifierAliases(), $this->userMountingBackends)
261
-		) {
262
-			return true;
263
-		}
264
-		return false;
265
-	}
266
-
267
-	/**
268
-	 * Check an authentication mechanism if a user is allowed to use it
269
-	 *
270
-	 * @param AuthMechanism $authMechanism
271
-	 * @return bool
272
-	 */
273
-	protected function isAllowedAuthMechanism(AuthMechanism $authMechanism) {
274
-		return true; // not implemented
275
-	}
276
-
277
-	/**
278
-	 * registers a configuration handler
279
-	 *
280
-	 * The function of the provided $placeholder is mostly to act a sorting
281
-	 * criteria, so longer placeholders are replaced first. This avoids
282
-	 * "$user" overwriting parts of "$userMail" and "$userLang", for example.
283
-	 * The provided value should not contain the $ prefix, only a-z0-9 are
284
-	 * allowed. Upper case letters are lower cased, the replacement is case-
285
-	 * insensitive.
286
-	 *
287
-	 * The configHandlerLoader should just instantiate the handler on demand.
288
-	 * For now all handlers are instantiated when a mount is loaded, independent
289
-	 * of whether the placeholder is present or not. This may change in future.
290
-	 *
291
-	 * @since 16.0.0
292
-	 */
293
-	public function registerConfigHandler(string $placeholder, callable $configHandlerLoader) {
294
-		$placeholder = trim(strtolower($placeholder));
295
-		if (!(bool)\preg_match('/^[a-z0-9]*$/', $placeholder)) {
296
-			throw new \RuntimeException(sprintf(
297
-				'Invalid placeholder %s, only [a-z0-9] are allowed', $placeholder
298
-			));
299
-		}
300
-		if ($placeholder === '') {
301
-			throw new \RuntimeException('Invalid empty placeholder');
302
-		}
303
-		if (isset($this->configHandlerLoaders[$placeholder]) || isset($this->configHandlers[$placeholder])) {
304
-			throw new \RuntimeException(sprintf('A handler is already registered for %s', $placeholder));
305
-		}
306
-		$this->configHandlerLoaders[$placeholder] = $configHandlerLoader;
307
-	}
308
-
309
-	protected function loadConfigHandlers():void {
310
-		$this->callForRegistrations();
311
-		$newLoaded = false;
312
-		foreach ($this->configHandlerLoaders as $placeholder => $loader) {
313
-			$handler = $loader();
314
-			if (!$handler instanceof IConfigHandler) {
315
-				throw new \RuntimeException(sprintf(
316
-					'Handler for %s is not an instance of IConfigHandler', $placeholder
317
-				));
318
-			}
319
-			$this->configHandlers[$placeholder] = $handler;
320
-			$newLoaded = true;
321
-		}
322
-		$this->configHandlerLoaders = [];
323
-		if ($newLoaded) {
324
-			// ensure those with longest placeholders come first,
325
-			// to avoid substring matches
326
-			uksort($this->configHandlers, function ($phA, $phB) {
327
-				return strlen($phB) <=> strlen($phA);
328
-			});
329
-		}
330
-	}
331
-
332
-	/**
333
-	 * @since 16.0.0
334
-	 */
335
-	public function getConfigHandlers() {
336
-		$this->loadConfigHandlers();
337
-		return $this->configHandlers;
338
-	}
25
+    /** Visibility constants for VisibilityTrait */
26
+    public const VISIBILITY_NONE = 0;
27
+    public const VISIBILITY_PERSONAL = 1;
28
+    public const VISIBILITY_ADMIN = 2;
29
+    //const VISIBILITY_ALIENS = 4;
30
+
31
+    public const VISIBILITY_DEFAULT = 3; // PERSONAL | ADMIN
32
+
33
+    /** Priority constants for PriorityTrait */
34
+    public const PRIORITY_DEFAULT = 100;
35
+
36
+    /** @var bool */
37
+    private $userMountingAllowed = true;
38
+
39
+    /** @var string[] */
40
+    private $userMountingBackends = [];
41
+
42
+    /** @var Backend[] */
43
+    private $backends = [];
44
+
45
+    /** @var IBackendProvider[] */
46
+    private $backendProviders = [];
47
+
48
+    /** @var AuthMechanism[] */
49
+    private $authMechanisms = [];
50
+
51
+    /** @var IAuthMechanismProvider[] */
52
+    private $authMechanismProviders = [];
53
+
54
+    /** @var callable[] */
55
+    private $configHandlerLoaders = [];
56
+
57
+    private $configHandlers = [];
58
+
59
+    public function __construct(
60
+        protected IAppConfig $appConfig,
61
+    ) {
62
+        // Load config values
63
+        $this->userMountingAllowed = $appConfig->getValueBool('files_external', ConfigLexicon::ALLOW_USER_MOUNTING);
64
+        $this->userMountingBackends = explode(',', $appConfig->getValueString('files_external', ConfigLexicon::USER_MOUNTING_BACKENDS));
65
+
66
+        // if no backend is in the list an empty string is in the array and user mounting is disabled
67
+        if ($this->userMountingBackends === ['']) {
68
+            $this->userMountingAllowed = false;
69
+        }
70
+    }
71
+
72
+    /**
73
+     * Register a backend provider
74
+     *
75
+     * @since 9.1.0
76
+     * @param IBackendProvider $provider
77
+     */
78
+    public function registerBackendProvider(IBackendProvider $provider) {
79
+        $this->backendProviders[] = $provider;
80
+    }
81
+
82
+    private function callForRegistrations() {
83
+        static $eventSent = false;
84
+        if (!$eventSent) {
85
+            Server::get(IEventDispatcher::class)->dispatch(
86
+                'OCA\\Files_External::loadAdditionalBackends',
87
+                new GenericEvent()
88
+            );
89
+            $eventSent = true;
90
+        }
91
+    }
92
+
93
+    private function loadBackendProviders() {
94
+        $this->callForRegistrations();
95
+        foreach ($this->backendProviders as $provider) {
96
+            $this->registerBackends($provider->getBackends());
97
+        }
98
+        $this->backendProviders = [];
99
+    }
100
+
101
+    /**
102
+     * Register an auth mechanism provider
103
+     *
104
+     * @since 9.1.0
105
+     * @param IAuthMechanismProvider $provider
106
+     */
107
+    public function registerAuthMechanismProvider(IAuthMechanismProvider $provider) {
108
+        $this->authMechanismProviders[] = $provider;
109
+    }
110
+
111
+    private function loadAuthMechanismProviders() {
112
+        $this->callForRegistrations();
113
+        foreach ($this->authMechanismProviders as $provider) {
114
+            $this->registerAuthMechanisms($provider->getAuthMechanisms());
115
+        }
116
+        $this->authMechanismProviders = [];
117
+    }
118
+
119
+    /**
120
+     * Register a backend
121
+     *
122
+     * @deprecated 9.1.0 use registerBackendProvider()
123
+     * @param Backend $backend
124
+     */
125
+    public function registerBackend(Backend $backend) {
126
+        if (!$this->isAllowedUserBackend($backend)) {
127
+            $backend->removeVisibility(BackendService::VISIBILITY_PERSONAL);
128
+        }
129
+        foreach ($backend->getIdentifierAliases() as $alias) {
130
+            $this->backends[$alias] = $backend;
131
+        }
132
+    }
133
+
134
+    /**
135
+     * @deprecated 9.1.0 use registerBackendProvider()
136
+     * @param Backend[] $backends
137
+     */
138
+    public function registerBackends(array $backends) {
139
+        foreach ($backends as $backend) {
140
+            $this->registerBackend($backend);
141
+        }
142
+    }
143
+    /**
144
+     * Register an authentication mechanism
145
+     *
146
+     * @deprecated 9.1.0 use registerAuthMechanismProvider()
147
+     * @param AuthMechanism $authMech
148
+     */
149
+    public function registerAuthMechanism(AuthMechanism $authMech) {
150
+        if (!$this->isAllowedAuthMechanism($authMech)) {
151
+            $authMech->removeVisibility(BackendService::VISIBILITY_PERSONAL);
152
+        }
153
+        foreach ($authMech->getIdentifierAliases() as $alias) {
154
+            $this->authMechanisms[$alias] = $authMech;
155
+        }
156
+    }
157
+
158
+    /**
159
+     * @deprecated 9.1.0 use registerAuthMechanismProvider()
160
+     * @param AuthMechanism[] $mechanisms
161
+     */
162
+    public function registerAuthMechanisms(array $mechanisms) {
163
+        foreach ($mechanisms as $mechanism) {
164
+            $this->registerAuthMechanism($mechanism);
165
+        }
166
+    }
167
+
168
+    /**
169
+     * Get all backends
170
+     *
171
+     * @return Backend[]
172
+     */
173
+    public function getBackends() {
174
+        $this->loadBackendProviders();
175
+        // only return real identifiers, no aliases
176
+        $backends = [];
177
+        foreach ($this->backends as $backend) {
178
+            $backends[$backend->getIdentifier()] = $backend;
179
+        }
180
+        return $backends;
181
+    }
182
+
183
+    /**
184
+     * Get all available backends
185
+     *
186
+     * @return Backend[]
187
+     */
188
+    public function getAvailableBackends() {
189
+        return array_filter($this->getBackends(), function ($backend) {
190
+            return !$backend->checkDependencies();
191
+        });
192
+    }
193
+
194
+    /**
195
+     * @param string $identifier
196
+     * @return Backend|null
197
+     */
198
+    public function getBackend($identifier) {
199
+        $this->loadBackendProviders();
200
+        if (isset($this->backends[$identifier])) {
201
+            return $this->backends[$identifier];
202
+        }
203
+        return null;
204
+    }
205
+
206
+    /**
207
+     * Get all authentication mechanisms
208
+     *
209
+     * @return AuthMechanism[]
210
+     */
211
+    public function getAuthMechanisms() {
212
+        $this->loadAuthMechanismProviders();
213
+        // only return real identifiers, no aliases
214
+        $mechanisms = [];
215
+        foreach ($this->authMechanisms as $mechanism) {
216
+            $mechanisms[$mechanism->getIdentifier()] = $mechanism;
217
+        }
218
+        return $mechanisms;
219
+    }
220
+
221
+    /**
222
+     * Get all authentication mechanisms for schemes
223
+     *
224
+     * @param string[] $schemes
225
+     * @return AuthMechanism[]
226
+     */
227
+    public function getAuthMechanismsByScheme(array $schemes) {
228
+        return array_filter($this->getAuthMechanisms(), function ($authMech) use ($schemes) {
229
+            return in_array($authMech->getScheme(), $schemes, true);
230
+        });
231
+    }
232
+
233
+    /**
234
+     * @param string $identifier
235
+     * @return AuthMechanism|null
236
+     */
237
+    public function getAuthMechanism($identifier) {
238
+        $this->loadAuthMechanismProviders();
239
+        if (isset($this->authMechanisms[$identifier])) {
240
+            return $this->authMechanisms[$identifier];
241
+        }
242
+        return null;
243
+    }
244
+
245
+    /**
246
+     * @return bool
247
+     */
248
+    public function isUserMountingAllowed() {
249
+        return $this->userMountingAllowed;
250
+    }
251
+
252
+    /**
253
+     * Check a backend if a user is allowed to mount it
254
+     *
255
+     * @param Backend $backend
256
+     * @return bool
257
+     */
258
+    protected function isAllowedUserBackend(Backend $backend) {
259
+        if ($this->userMountingAllowed &&
260
+            array_intersect($backend->getIdentifierAliases(), $this->userMountingBackends)
261
+        ) {
262
+            return true;
263
+        }
264
+        return false;
265
+    }
266
+
267
+    /**
268
+     * Check an authentication mechanism if a user is allowed to use it
269
+     *
270
+     * @param AuthMechanism $authMechanism
271
+     * @return bool
272
+     */
273
+    protected function isAllowedAuthMechanism(AuthMechanism $authMechanism) {
274
+        return true; // not implemented
275
+    }
276
+
277
+    /**
278
+     * registers a configuration handler
279
+     *
280
+     * The function of the provided $placeholder is mostly to act a sorting
281
+     * criteria, so longer placeholders are replaced first. This avoids
282
+     * "$user" overwriting parts of "$userMail" and "$userLang", for example.
283
+     * The provided value should not contain the $ prefix, only a-z0-9 are
284
+     * allowed. Upper case letters are lower cased, the replacement is case-
285
+     * insensitive.
286
+     *
287
+     * The configHandlerLoader should just instantiate the handler on demand.
288
+     * For now all handlers are instantiated when a mount is loaded, independent
289
+     * of whether the placeholder is present or not. This may change in future.
290
+     *
291
+     * @since 16.0.0
292
+     */
293
+    public function registerConfigHandler(string $placeholder, callable $configHandlerLoader) {
294
+        $placeholder = trim(strtolower($placeholder));
295
+        if (!(bool)\preg_match('/^[a-z0-9]*$/', $placeholder)) {
296
+            throw new \RuntimeException(sprintf(
297
+                'Invalid placeholder %s, only [a-z0-9] are allowed', $placeholder
298
+            ));
299
+        }
300
+        if ($placeholder === '') {
301
+            throw new \RuntimeException('Invalid empty placeholder');
302
+        }
303
+        if (isset($this->configHandlerLoaders[$placeholder]) || isset($this->configHandlers[$placeholder])) {
304
+            throw new \RuntimeException(sprintf('A handler is already registered for %s', $placeholder));
305
+        }
306
+        $this->configHandlerLoaders[$placeholder] = $configHandlerLoader;
307
+    }
308
+
309
+    protected function loadConfigHandlers():void {
310
+        $this->callForRegistrations();
311
+        $newLoaded = false;
312
+        foreach ($this->configHandlerLoaders as $placeholder => $loader) {
313
+            $handler = $loader();
314
+            if (!$handler instanceof IConfigHandler) {
315
+                throw new \RuntimeException(sprintf(
316
+                    'Handler for %s is not an instance of IConfigHandler', $placeholder
317
+                ));
318
+            }
319
+            $this->configHandlers[$placeholder] = $handler;
320
+            $newLoaded = true;
321
+        }
322
+        $this->configHandlerLoaders = [];
323
+        if ($newLoaded) {
324
+            // ensure those with longest placeholders come first,
325
+            // to avoid substring matches
326
+            uksort($this->configHandlers, function ($phA, $phB) {
327
+                return strlen($phB) <=> strlen($phA);
328
+            });
329
+        }
330
+    }
331
+
332
+    /**
333
+     * @since 16.0.0
334
+     */
335
+    public function getConfigHandlers() {
336
+        $this->loadConfigHandlers();
337
+        return $this->configHandlers;
338
+    }
339 339
 }
Please login to merge, or discard this patch.
apps/files_external/lib/ConfigLexicon.php 1 patch
Indentation   +14 added lines, -14 removed lines patch added patch discarded remove patch
@@ -21,21 +21,21 @@
 block discarded – undo
21 21
  * {@see IConfigLexicon}
22 22
  */
23 23
 class ConfigLexicon implements IConfigLexicon {
24
-	public const ALLOW_USER_MOUNTING = 'allow_user_mounting';
25
-	public const USER_MOUNTING_BACKENDS = 'user_mounting_backends';
24
+    public const ALLOW_USER_MOUNTING = 'allow_user_mounting';
25
+    public const USER_MOUNTING_BACKENDS = 'user_mounting_backends';
26 26
 
27
-	public function getStrictness(): ConfigLexiconStrictness {
28
-		return ConfigLexiconStrictness::NOTICE;
29
-	}
27
+    public function getStrictness(): ConfigLexiconStrictness {
28
+        return ConfigLexiconStrictness::NOTICE;
29
+    }
30 30
 
31
-	public function getAppConfigs(): array {
32
-		return [
33
-			new ConfigLexiconEntry(self::ALLOW_USER_MOUNTING, ValueType::BOOL, false, 'allow users to mount their own external filesystems', true),
34
-			new ConfigLexiconEntry(self::USER_MOUNTING_BACKENDS, ValueType::STRING, '', 'list of mounting backends available for users', true),
35
-		];
36
-	}
31
+    public function getAppConfigs(): array {
32
+        return [
33
+            new ConfigLexiconEntry(self::ALLOW_USER_MOUNTING, ValueType::BOOL, false, 'allow users to mount their own external filesystems', true),
34
+            new ConfigLexiconEntry(self::USER_MOUNTING_BACKENDS, ValueType::STRING, '', 'list of mounting backends available for users', true),
35
+        ];
36
+    }
37 37
 
38
-	public function getUserConfigs(): array {
39
-		return [];
40
-	}
38
+    public function getUserConfigs(): array {
39
+        return [];
40
+    }
41 41
 }
Please login to merge, or discard this patch.
apps/files_external/lib/Listener/LoadAdditionalListener.php 1 patch
Indentation   +16 added lines, -16 removed lines patch added patch discarded remove patch
@@ -22,20 +22,20 @@
 block discarded – undo
22 22
  */
23 23
 class LoadAdditionalListener implements IEventListener {
24 24
 
25
-	public function __construct(
26
-		private readonly IAppConfig $appConfig,
27
-		private IInitialState $initialState,
28
-	) {
29
-	}
30
-
31
-	public function handle(Event $event): void {
32
-		if (!($event instanceof LoadAdditionalScriptsEvent)) {
33
-			return;
34
-		}
35
-
36
-		$allowUserMounting = $this->appConfig->getValueBool('files_external', ConfigLexicon::ALLOW_USER_MOUNTING);
37
-		$this->initialState->provideInitialState('allowUserMounting', $allowUserMounting);
38
-
39
-		Util::addInitScript(Application::APP_ID, 'init');
40
-	}
25
+    public function __construct(
26
+        private readonly IAppConfig $appConfig,
27
+        private IInitialState $initialState,
28
+    ) {
29
+    }
30
+
31
+    public function handle(Event $event): void {
32
+        if (!($event instanceof LoadAdditionalScriptsEvent)) {
33
+            return;
34
+        }
35
+
36
+        $allowUserMounting = $this->appConfig->getValueBool('files_external', ConfigLexicon::ALLOW_USER_MOUNTING);
37
+        $this->initialState->provideInitialState('allowUserMounting', $allowUserMounting);
38
+
39
+        Util::addInitScript(Application::APP_ID, 'init');
40
+    }
41 41
 }
Please login to merge, or discard this patch.
apps/files_external/tests/Service/BackendServiceTest.php 1 patch
Indentation   +235 added lines, -235 removed lines patch added patch discarded remove patch
@@ -16,239 +16,239 @@
 block discarded – undo
16 16
 
17 17
 class BackendServiceTest extends \Test\TestCase {
18 18
 
19
-	/** @var IAppConfig|\PHPUnit\Framework\MockObject\MockObject */
20
-	protected $appConfig;
21
-
22
-	protected function setUp(): void {
23
-		$this->appConfig = $this->createMock(IAppConfig::class);
24
-	}
25
-
26
-	/**
27
-	 * @param string $class
28
-	 *
29
-	 * @return \OCA\Files_External\Lib\Backend\Backend|\PHPUnit\Framework\MockObject\MockObject
30
-	 */
31
-	protected function getBackendMock($class) {
32
-		$backend = $this->getMockBuilder(Backend::class)
33
-			->disableOriginalConstructor()
34
-			->getMock();
35
-		$backend->method('getIdentifier')->willReturn('identifier:' . $class);
36
-		$backend->method('getIdentifierAliases')->willReturn(['identifier:' . $class]);
37
-		return $backend;
38
-	}
39
-
40
-	/**
41
-	 * @param string $class
42
-	 *
43
-	 * @return AuthMechanism|\PHPUnit\Framework\MockObject\MockObject
44
-	 */
45
-	protected function getAuthMechanismMock($class) {
46
-		$backend = $this->getMockBuilder(AuthMechanism::class)
47
-			->disableOriginalConstructor()
48
-			->getMock();
49
-		$backend->method('getIdentifier')->willReturn('identifier:' . $class);
50
-		$backend->method('getIdentifierAliases')->willReturn(['identifier:' . $class]);
51
-		return $backend;
52
-	}
53
-
54
-	public function testRegisterBackend(): void {
55
-		$service = new BackendService($this->appConfig);
56
-
57
-		$backend = $this->getBackendMock('\Foo\Bar');
58
-
59
-		/** @var \OCA\Files_External\Lib\Backend\Backend|\PHPUnit\Framework\MockObject\MockObject $backendAlias */
60
-		$backendAlias = $this->getMockBuilder(Backend::class)
61
-			->disableOriginalConstructor()
62
-			->getMock();
63
-		$backendAlias->method('getIdentifierAliases')
64
-			->willReturn(['identifier_real', 'identifier_alias']);
65
-		$backendAlias->method('getIdentifier')
66
-			->willReturn('identifier_real');
67
-
68
-		$service->registerBackend($backend);
69
-		$service->registerBackend($backendAlias);
70
-
71
-		$this->assertEquals($backend, $service->getBackend('identifier:\Foo\Bar'));
72
-		$this->assertEquals($backendAlias, $service->getBackend('identifier_real'));
73
-		$this->assertEquals($backendAlias, $service->getBackend('identifier_alias'));
74
-
75
-		$backends = $service->getBackends();
76
-		$this->assertCount(2, $backends);
77
-		$this->assertArrayHasKey('identifier:\Foo\Bar', $backends);
78
-		$this->assertArrayHasKey('identifier_real', $backends);
79
-		$this->assertArrayNotHasKey('identifier_alias', $backends);
80
-	}
81
-
82
-	public function testBackendProvider(): void {
83
-		$service = new BackendService($this->appConfig);
84
-
85
-		$backend1 = $this->getBackendMock('\Foo\Bar');
86
-		$backend2 = $this->getBackendMock('\Bar\Foo');
87
-
88
-		/** @var IBackendProvider|\PHPUnit\Framework\MockObject\MockObject $providerMock */
89
-		$providerMock = $this->createMock(IBackendProvider::class);
90
-		$providerMock->expects($this->once())
91
-			->method('getBackends')
92
-			->willReturn([$backend1, $backend2]);
93
-		$service->registerBackendProvider($providerMock);
94
-
95
-		$this->assertEquals($backend1, $service->getBackend('identifier:\Foo\Bar'));
96
-		$this->assertEquals($backend2, $service->getBackend('identifier:\Bar\Foo'));
97
-
98
-		$this->assertCount(2, $service->getBackends());
99
-	}
100
-
101
-	public function testAuthMechanismProvider(): void {
102
-		$service = new BackendService($this->appConfig);
103
-
104
-		$backend1 = $this->getAuthMechanismMock('\Foo\Bar');
105
-		$backend2 = $this->getAuthMechanismMock('\Bar\Foo');
106
-
107
-		/** @var IAuthMechanismProvider|\PHPUnit\Framework\MockObject\MockObject $providerMock */
108
-		$providerMock = $this->createMock(IAuthMechanismProvider::class);
109
-		$providerMock->expects($this->once())
110
-			->method('getAuthMechanisms')
111
-			->willReturn([$backend1, $backend2]);
112
-		$service->registerAuthMechanismProvider($providerMock);
113
-
114
-		$this->assertEquals($backend1, $service->getAuthMechanism('identifier:\Foo\Bar'));
115
-		$this->assertEquals($backend2, $service->getAuthMechanism('identifier:\Bar\Foo'));
116
-
117
-		$this->assertCount(2, $service->getAuthMechanisms());
118
-	}
119
-
120
-	public function testMultipleBackendProviders(): void {
121
-		$service = new BackendService($this->appConfig);
122
-
123
-		$backend1a = $this->getBackendMock('\Foo\Bar');
124
-		$backend1b = $this->getBackendMock('\Bar\Foo');
125
-
126
-		$backend2 = $this->getBackendMock('\Dead\Beef');
127
-
128
-		/** @var IBackendProvider|\PHPUnit\Framework\MockObject\MockObject $provider1Mock */
129
-		$provider1Mock = $this->createMock(IBackendProvider::class);
130
-		$provider1Mock->expects($this->once())
131
-			->method('getBackends')
132
-			->willReturn([$backend1a, $backend1b]);
133
-		$service->registerBackendProvider($provider1Mock);
134
-		/** @var IBackendProvider|\PHPUnit\Framework\MockObject\MockObject $provider2Mock */
135
-		$provider2Mock = $this->createMock(IBackendProvider::class);
136
-		$provider2Mock->expects($this->once())
137
-			->method('getBackends')
138
-			->willReturn([$backend2]);
139
-		$service->registerBackendProvider($provider2Mock);
140
-
141
-		$this->assertEquals($backend1a, $service->getBackend('identifier:\Foo\Bar'));
142
-		$this->assertEquals($backend1b, $service->getBackend('identifier:\Bar\Foo'));
143
-		$this->assertEquals($backend2, $service->getBackend('identifier:\Dead\Beef'));
144
-
145
-		$this->assertCount(3, $service->getBackends());
146
-	}
147
-
148
-	public function testUserMountingBackends(): void {
149
-		$this->appConfig->expects($this->once())
150
-			->method('getValueString')
151
-			->with('files_external', 'user_mounting_backends')
152
-			->willReturn('identifier:\User\Mount\Allowed,identifier_alias');
153
-		$this->appConfig->expects($this->once())
154
-			->method('getValueBool')
155
-			->with('files_external', 'allow_user_mounting')
156
-			->willReturn(true);
157
-
158
-		$service = new BackendService($this->appConfig);
159
-
160
-		$backendAllowed = $this->getBackendMock('\User\Mount\Allowed');
161
-		$backendAllowed->expects($this->never())
162
-			->method('removeVisibility');
163
-		$backendNotAllowed = $this->getBackendMock('\User\Mount\NotAllowed');
164
-		$backendNotAllowed->expects($this->once())
165
-			->method('removeVisibility')
166
-			->with(BackendService::VISIBILITY_PERSONAL);
167
-
168
-		$backendAlias = $this->getMockBuilder(Backend::class)
169
-			->disableOriginalConstructor()
170
-			->getMock();
171
-		$backendAlias->method('getIdentifierAliases')
172
-			->willReturn(['identifier_real', 'identifier_alias']);
173
-		$backendAlias->expects($this->never())
174
-			->method('removeVisibility');
175
-
176
-		$service->registerBackend($backendAllowed);
177
-		$service->registerBackend($backendNotAllowed);
178
-		$service->registerBackend($backendAlias);
179
-	}
180
-
181
-	public function testGetAvailableBackends(): void {
182
-		$service = new BackendService($this->appConfig);
183
-
184
-		$backendAvailable = $this->getBackendMock('\Backend\Available');
185
-		$backendAvailable->expects($this->once())
186
-			->method('checkDependencies')
187
-			->willReturn([]);
188
-		$backendNotAvailable = $this->getBackendMock('\Backend\NotAvailable');
189
-		$backendNotAvailable->expects($this->once())
190
-			->method('checkDependencies')
191
-			->willReturn([
192
-				$this->getMockBuilder('\OCA\Files_External\Lib\MissingDependency')
193
-					->disableOriginalConstructor()
194
-					->getMock()
195
-			]);
196
-
197
-		$service->registerBackend($backendAvailable);
198
-		$service->registerBackend($backendNotAvailable);
199
-
200
-		$availableBackends = $service->getAvailableBackends();
201
-		$this->assertArrayHasKey('identifier:\Backend\Available', $availableBackends);
202
-		$this->assertArrayNotHasKey('identifier:\Backend\NotAvailable', $availableBackends);
203
-	}
204
-
205
-	public function invalidConfigPlaceholderProvider() {
206
-		return [
207
-			[['@user']],
208
-			[['$user']],
209
-			[['hællo']],
210
-			[['spa ce']],
211
-			[['yo\o']],
212
-			[['<script>…</script>']],
213
-			[['xxyoloxx', 'invÆlid']],
214
-			[['tautology', 'tautology']],
215
-			[['tautology2', 'TAUTOLOGY2']],
216
-		];
217
-	}
218
-
219
-	/**
220
-	 * @dataProvider invalidConfigPlaceholderProvider
221
-	 */
222
-	public function testRegisterConfigHandlerInvalid(array $placeholders): void {
223
-		$this->expectException(\RuntimeException::class);
224
-
225
-		$service = new BackendService($this->appConfig);
226
-		$mock = $this->createMock(IConfigHandler::class);
227
-		$cb = function () use ($mock) {
228
-			return $mock;
229
-		};
230
-		foreach ($placeholders as $placeholder) {
231
-			$service->registerConfigHandler($placeholder, $cb);
232
-		}
233
-	}
234
-
235
-	public function testConfigHandlers(): void {
236
-		$service = new BackendService($this->appConfig);
237
-		$mock = $this->createMock(IConfigHandler::class);
238
-		$mock->expects($this->exactly(3))
239
-			->method('handle');
240
-		$cb = function () use ($mock) {
241
-			return $mock;
242
-		};
243
-		$service->registerConfigHandler('one', $cb);
244
-		$service->registerConfigHandler('2', $cb);
245
-		$service->registerConfigHandler('Three', $cb);
246
-
247
-		/** @var IConfigHandler[] $handlers */
248
-		$handlers = $service->getConfigHandlers();
249
-
250
-		foreach ($handlers as $handler) {
251
-			$handler->handle('Something');
252
-		}
253
-	}
19
+    /** @var IAppConfig|\PHPUnit\Framework\MockObject\MockObject */
20
+    protected $appConfig;
21
+
22
+    protected function setUp(): void {
23
+        $this->appConfig = $this->createMock(IAppConfig::class);
24
+    }
25
+
26
+    /**
27
+     * @param string $class
28
+     *
29
+     * @return \OCA\Files_External\Lib\Backend\Backend|\PHPUnit\Framework\MockObject\MockObject
30
+     */
31
+    protected function getBackendMock($class) {
32
+        $backend = $this->getMockBuilder(Backend::class)
33
+            ->disableOriginalConstructor()
34
+            ->getMock();
35
+        $backend->method('getIdentifier')->willReturn('identifier:' . $class);
36
+        $backend->method('getIdentifierAliases')->willReturn(['identifier:' . $class]);
37
+        return $backend;
38
+    }
39
+
40
+    /**
41
+     * @param string $class
42
+     *
43
+     * @return AuthMechanism|\PHPUnit\Framework\MockObject\MockObject
44
+     */
45
+    protected function getAuthMechanismMock($class) {
46
+        $backend = $this->getMockBuilder(AuthMechanism::class)
47
+            ->disableOriginalConstructor()
48
+            ->getMock();
49
+        $backend->method('getIdentifier')->willReturn('identifier:' . $class);
50
+        $backend->method('getIdentifierAliases')->willReturn(['identifier:' . $class]);
51
+        return $backend;
52
+    }
53
+
54
+    public function testRegisterBackend(): void {
55
+        $service = new BackendService($this->appConfig);
56
+
57
+        $backend = $this->getBackendMock('\Foo\Bar');
58
+
59
+        /** @var \OCA\Files_External\Lib\Backend\Backend|\PHPUnit\Framework\MockObject\MockObject $backendAlias */
60
+        $backendAlias = $this->getMockBuilder(Backend::class)
61
+            ->disableOriginalConstructor()
62
+            ->getMock();
63
+        $backendAlias->method('getIdentifierAliases')
64
+            ->willReturn(['identifier_real', 'identifier_alias']);
65
+        $backendAlias->method('getIdentifier')
66
+            ->willReturn('identifier_real');
67
+
68
+        $service->registerBackend($backend);
69
+        $service->registerBackend($backendAlias);
70
+
71
+        $this->assertEquals($backend, $service->getBackend('identifier:\Foo\Bar'));
72
+        $this->assertEquals($backendAlias, $service->getBackend('identifier_real'));
73
+        $this->assertEquals($backendAlias, $service->getBackend('identifier_alias'));
74
+
75
+        $backends = $service->getBackends();
76
+        $this->assertCount(2, $backends);
77
+        $this->assertArrayHasKey('identifier:\Foo\Bar', $backends);
78
+        $this->assertArrayHasKey('identifier_real', $backends);
79
+        $this->assertArrayNotHasKey('identifier_alias', $backends);
80
+    }
81
+
82
+    public function testBackendProvider(): void {
83
+        $service = new BackendService($this->appConfig);
84
+
85
+        $backend1 = $this->getBackendMock('\Foo\Bar');
86
+        $backend2 = $this->getBackendMock('\Bar\Foo');
87
+
88
+        /** @var IBackendProvider|\PHPUnit\Framework\MockObject\MockObject $providerMock */
89
+        $providerMock = $this->createMock(IBackendProvider::class);
90
+        $providerMock->expects($this->once())
91
+            ->method('getBackends')
92
+            ->willReturn([$backend1, $backend2]);
93
+        $service->registerBackendProvider($providerMock);
94
+
95
+        $this->assertEquals($backend1, $service->getBackend('identifier:\Foo\Bar'));
96
+        $this->assertEquals($backend2, $service->getBackend('identifier:\Bar\Foo'));
97
+
98
+        $this->assertCount(2, $service->getBackends());
99
+    }
100
+
101
+    public function testAuthMechanismProvider(): void {
102
+        $service = new BackendService($this->appConfig);
103
+
104
+        $backend1 = $this->getAuthMechanismMock('\Foo\Bar');
105
+        $backend2 = $this->getAuthMechanismMock('\Bar\Foo');
106
+
107
+        /** @var IAuthMechanismProvider|\PHPUnit\Framework\MockObject\MockObject $providerMock */
108
+        $providerMock = $this->createMock(IAuthMechanismProvider::class);
109
+        $providerMock->expects($this->once())
110
+            ->method('getAuthMechanisms')
111
+            ->willReturn([$backend1, $backend2]);
112
+        $service->registerAuthMechanismProvider($providerMock);
113
+
114
+        $this->assertEquals($backend1, $service->getAuthMechanism('identifier:\Foo\Bar'));
115
+        $this->assertEquals($backend2, $service->getAuthMechanism('identifier:\Bar\Foo'));
116
+
117
+        $this->assertCount(2, $service->getAuthMechanisms());
118
+    }
119
+
120
+    public function testMultipleBackendProviders(): void {
121
+        $service = new BackendService($this->appConfig);
122
+
123
+        $backend1a = $this->getBackendMock('\Foo\Bar');
124
+        $backend1b = $this->getBackendMock('\Bar\Foo');
125
+
126
+        $backend2 = $this->getBackendMock('\Dead\Beef');
127
+
128
+        /** @var IBackendProvider|\PHPUnit\Framework\MockObject\MockObject $provider1Mock */
129
+        $provider1Mock = $this->createMock(IBackendProvider::class);
130
+        $provider1Mock->expects($this->once())
131
+            ->method('getBackends')
132
+            ->willReturn([$backend1a, $backend1b]);
133
+        $service->registerBackendProvider($provider1Mock);
134
+        /** @var IBackendProvider|\PHPUnit\Framework\MockObject\MockObject $provider2Mock */
135
+        $provider2Mock = $this->createMock(IBackendProvider::class);
136
+        $provider2Mock->expects($this->once())
137
+            ->method('getBackends')
138
+            ->willReturn([$backend2]);
139
+        $service->registerBackendProvider($provider2Mock);
140
+
141
+        $this->assertEquals($backend1a, $service->getBackend('identifier:\Foo\Bar'));
142
+        $this->assertEquals($backend1b, $service->getBackend('identifier:\Bar\Foo'));
143
+        $this->assertEquals($backend2, $service->getBackend('identifier:\Dead\Beef'));
144
+
145
+        $this->assertCount(3, $service->getBackends());
146
+    }
147
+
148
+    public function testUserMountingBackends(): void {
149
+        $this->appConfig->expects($this->once())
150
+            ->method('getValueString')
151
+            ->with('files_external', 'user_mounting_backends')
152
+            ->willReturn('identifier:\User\Mount\Allowed,identifier_alias');
153
+        $this->appConfig->expects($this->once())
154
+            ->method('getValueBool')
155
+            ->with('files_external', 'allow_user_mounting')
156
+            ->willReturn(true);
157
+
158
+        $service = new BackendService($this->appConfig);
159
+
160
+        $backendAllowed = $this->getBackendMock('\User\Mount\Allowed');
161
+        $backendAllowed->expects($this->never())
162
+            ->method('removeVisibility');
163
+        $backendNotAllowed = $this->getBackendMock('\User\Mount\NotAllowed');
164
+        $backendNotAllowed->expects($this->once())
165
+            ->method('removeVisibility')
166
+            ->with(BackendService::VISIBILITY_PERSONAL);
167
+
168
+        $backendAlias = $this->getMockBuilder(Backend::class)
169
+            ->disableOriginalConstructor()
170
+            ->getMock();
171
+        $backendAlias->method('getIdentifierAliases')
172
+            ->willReturn(['identifier_real', 'identifier_alias']);
173
+        $backendAlias->expects($this->never())
174
+            ->method('removeVisibility');
175
+
176
+        $service->registerBackend($backendAllowed);
177
+        $service->registerBackend($backendNotAllowed);
178
+        $service->registerBackend($backendAlias);
179
+    }
180
+
181
+    public function testGetAvailableBackends(): void {
182
+        $service = new BackendService($this->appConfig);
183
+
184
+        $backendAvailable = $this->getBackendMock('\Backend\Available');
185
+        $backendAvailable->expects($this->once())
186
+            ->method('checkDependencies')
187
+            ->willReturn([]);
188
+        $backendNotAvailable = $this->getBackendMock('\Backend\NotAvailable');
189
+        $backendNotAvailable->expects($this->once())
190
+            ->method('checkDependencies')
191
+            ->willReturn([
192
+                $this->getMockBuilder('\OCA\Files_External\Lib\MissingDependency')
193
+                    ->disableOriginalConstructor()
194
+                    ->getMock()
195
+            ]);
196
+
197
+        $service->registerBackend($backendAvailable);
198
+        $service->registerBackend($backendNotAvailable);
199
+
200
+        $availableBackends = $service->getAvailableBackends();
201
+        $this->assertArrayHasKey('identifier:\Backend\Available', $availableBackends);
202
+        $this->assertArrayNotHasKey('identifier:\Backend\NotAvailable', $availableBackends);
203
+    }
204
+
205
+    public function invalidConfigPlaceholderProvider() {
206
+        return [
207
+            [['@user']],
208
+            [['$user']],
209
+            [['hællo']],
210
+            [['spa ce']],
211
+            [['yo\o']],
212
+            [['<script>…</script>']],
213
+            [['xxyoloxx', 'invÆlid']],
214
+            [['tautology', 'tautology']],
215
+            [['tautology2', 'TAUTOLOGY2']],
216
+        ];
217
+    }
218
+
219
+    /**
220
+     * @dataProvider invalidConfigPlaceholderProvider
221
+     */
222
+    public function testRegisterConfigHandlerInvalid(array $placeholders): void {
223
+        $this->expectException(\RuntimeException::class);
224
+
225
+        $service = new BackendService($this->appConfig);
226
+        $mock = $this->createMock(IConfigHandler::class);
227
+        $cb = function () use ($mock) {
228
+            return $mock;
229
+        };
230
+        foreach ($placeholders as $placeholder) {
231
+            $service->registerConfigHandler($placeholder, $cb);
232
+        }
233
+    }
234
+
235
+    public function testConfigHandlers(): void {
236
+        $service = new BackendService($this->appConfig);
237
+        $mock = $this->createMock(IConfigHandler::class);
238
+        $mock->expects($this->exactly(3))
239
+            ->method('handle');
240
+        $cb = function () use ($mock) {
241
+            return $mock;
242
+        };
243
+        $service->registerConfigHandler('one', $cb);
244
+        $service->registerConfigHandler('2', $cb);
245
+        $service->registerConfigHandler('Three', $cb);
246
+
247
+        /** @var IConfigHandler[] $handlers */
248
+        $handlers = $service->getConfigHandlers();
249
+
250
+        foreach ($handlers as $handler) {
251
+            $handler->handle('Something');
252
+        }
253
+    }
254 254
 }
Please login to merge, or discard this patch.