Skip to content

Commit dfadafc

Browse files
authored
Merge pull request #59627 from nextcloud/carl/alternative-login-provider
feat(auth): Add IAlternativeLoginProvider
2 parents e0cc023 + f4cae8c commit dfadafc

6 files changed

Lines changed: 107 additions & 1 deletion

File tree

lib/composer/composer/autoload_classmap.php

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -165,6 +165,7 @@
165165
'OCP\\Authentication\\Exceptions\\PasswordUnavailableException' => $baseDir . '/lib/public/Authentication/Exceptions/PasswordUnavailableException.php',
166166
'OCP\\Authentication\\Exceptions\\WipeTokenException' => $baseDir . '/lib/public/Authentication/Exceptions/WipeTokenException.php',
167167
'OCP\\Authentication\\IAlternativeLogin' => $baseDir . '/lib/public/Authentication/IAlternativeLogin.php',
168+
'OCP\\Authentication\\IAlternativeLoginProvider' => $baseDir . '/lib/public/Authentication/IAlternativeLoginProvider.php',
168169
'OCP\\Authentication\\IApacheBackend' => $baseDir . '/lib/public/Authentication/IApacheBackend.php',
169170
'OCP\\Authentication\\IProvideUserSecretBackend' => $baseDir . '/lib/public/Authentication/IProvideUserSecretBackend.php',
170171
'OCP\\Authentication\\LoginCredentials\\ICredentials' => $baseDir . '/lib/public/Authentication/LoginCredentials/ICredentials.php',

lib/composer/composer/autoload_static.php

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -206,6 +206,7 @@ class ComposerStaticInit749170dad3f5e7f9ca158f5a9f04f6a2
206206
'OCP\\Authentication\\Exceptions\\PasswordUnavailableException' => __DIR__ . '/../../..' . '/lib/public/Authentication/Exceptions/PasswordUnavailableException.php',
207207
'OCP\\Authentication\\Exceptions\\WipeTokenException' => __DIR__ . '/../../..' . '/lib/public/Authentication/Exceptions/WipeTokenException.php',
208208
'OCP\\Authentication\\IAlternativeLogin' => __DIR__ . '/../../..' . '/lib/public/Authentication/IAlternativeLogin.php',
209+
'OCP\\Authentication\\IAlternativeLoginProvider' => __DIR__ . '/../../..' . '/lib/public/Authentication/IAlternativeLoginProvider.php',
209210
'OCP\\Authentication\\IApacheBackend' => __DIR__ . '/../../..' . '/lib/public/Authentication/IApacheBackend.php',
210211
'OCP\\Authentication\\IProvideUserSecretBackend' => __DIR__ . '/../../..' . '/lib/public/Authentication/IProvideUserSecretBackend.php',
211212
'OCP\\Authentication\\LoginCredentials\\ICredentials' => __DIR__ . '/../../..' . '/lib/public/Authentication/LoginCredentials/ICredentials.php',

lib/private/AppFramework/Bootstrap/RegistrationContext.php

Lines changed: 24 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -16,6 +16,7 @@
1616
use OCP\AppFramework\Middleware;
1717
use OCP\AppFramework\Services\InitialStateProvider;
1818
use OCP\Authentication\IAlternativeLogin;
19+
use OCP\Authentication\IAlternativeLoginProvider;
1920
use OCP\Calendar\ICalendarProvider;
2021
use OCP\Calendar\Resource\IBackend as IResourceBackend;
2122
use OCP\Calendar\Room\IBackend as IRoomBackend;
@@ -44,6 +45,7 @@
4445
use OCP\TextProcessing\IProvider as ITextProcessingProvider;
4546
use OCP\Translation\ITranslationProvider;
4647
use OCP\UserMigration\IMigrator as IUserMigrator;
48+
use Override;
4749
use Psr\Log\LoggerInterface;
4850
use RuntimeException;
4951
use Throwable;
@@ -95,6 +97,9 @@ class RegistrationContext {
9597
/** @var ServiceRegistration<IAlternativeLogin>[] */
9698
private $alternativeLogins = [];
9799

100+
/** @var ServiceRegistration<IAlternativeLoginProvider>[] */
101+
private array $alternativeLoginProviders = [];
102+
98103
/** @var ServiceRegistration<InitialStateProvider>[] */
99104
private $initialStates = [];
100105

@@ -251,6 +256,14 @@ public function registerAlternativeLogin(string $class): void {
251256
);
252257
}
253258

259+
#[Override]
260+
public function registerAlternativeLoginProvider(string $class): void {
261+
$this->context->registerAlternativeLoginProvider(
262+
$this->appId,
263+
$class
264+
);
265+
}
266+
254267
public function registerInitialStateProvider(string $class): void {
255268
$this->context->registerInitialState(
256269
$this->appId,
@@ -495,6 +508,10 @@ public function registerAlternativeLogin(string $appId, string $class): void {
495508
$this->alternativeLogins[] = new ServiceRegistration($appId, $class);
496509
}
497510

511+
public function registerAlternativeLoginProvider(string $appId, string $class): void {
512+
$this->alternativeLoginProviders[] = new ServiceRegistration($appId, $class);
513+
}
514+
498515
public function registerInitialState(string $appId, string $class): void {
499516
$this->initialStates[] = new ServiceRegistration($appId, $class);
500517
}
@@ -828,6 +845,13 @@ public function getAlternativeLogins(): array {
828845
return $this->alternativeLogins;
829846
}
830847

848+
/**
849+
* @return ServiceRegistration<IAlternativeLoginProvider>[]
850+
*/
851+
public function getAlternativeLoginProviders(): array {
852+
return $this->alternativeLoginProviders;
853+
}
854+
831855
/**
832856
* @return ServiceRegistration<InitialStateProvider>[]
833857
*/

lib/private/legacy/OC_App.php

Lines changed: 47 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -19,6 +19,7 @@
1919
use OCP\App\AppPathNotFoundException;
2020
use OCP\App\IAppManager;
2121
use OCP\Authentication\IAlternativeLogin;
22+
use OCP\Authentication\IAlternativeLoginProvider;
2223
use OCP\BackgroundJob\IJobList;
2324
use OCP\EventDispatcher\IEventDispatcher;
2425
use OCP\IAppConfig;
@@ -41,6 +42,8 @@
4142
* upgrading and removing apps.
4243
*/
4344
class OC_App {
45+
46+
/** @var list<array{name: string, href: string, class: string}> */
4447
private static array $altLogin = [];
4548
private static array $alreadyRegistered = [];
4649
public const supportedApp = 300;
@@ -272,12 +275,55 @@ public static function registerLogIn(array $entry): void {
272275
}
273276

274277
/**
275-
* @return array
278+
* @return list<array{name: string, href: string, class: string}>
276279
*/
277280
public static function getAlternativeLogIns(): array {
278281
/** @var Coordinator $bootstrapCoordinator */
279282
$bootstrapCoordinator = Server::get(Coordinator::class);
280283

284+
foreach ($bootstrapCoordinator->getRegistrationContext()->getAlternativeLoginProviders() as $registration) {
285+
if (!in_array(IAlternativeLoginProvider::class, class_implements($registration->getService()), true)) {
286+
Server::get(LoggerInterface::class)->error('Alternative login option {option} does not implement {interface} and is therefore ignored.', [
287+
'option' => $registration->getService(),
288+
'interface' => IAlternativeLoginProvider::class,
289+
'app' => $registration->getAppId(),
290+
]);
291+
continue;
292+
}
293+
294+
try {
295+
/** @var IAlternativeLoginProvider $provider */
296+
$provider = Server::get($registration->getService());
297+
} catch (ContainerExceptionInterface $e) {
298+
Server::get(LoggerInterface::class)->error('Alternative login option {option} can not be initialized.',
299+
[
300+
'exception' => $e,
301+
'option' => $registration->getService(),
302+
'app' => $registration->getAppId(),
303+
]);
304+
continue;
305+
}
306+
307+
foreach ($provider->getAlternativeLogins() as $alternativeLogin) {
308+
try {
309+
$alternativeLogin->load();
310+
311+
self::$altLogin[] = [
312+
'name' => $alternativeLogin->getLabel(),
313+
'href' => $alternativeLogin->getLink(),
314+
'class' => $alternativeLogin->getClass(),
315+
];
316+
} catch (Throwable $e) {
317+
Server::get(LoggerInterface::class)->error('Alternative login option {option} had an error while loading.',
318+
[
319+
'exception' => $e,
320+
'option' => $registration->getService(),
321+
'app' => $registration->getAppId(),
322+
]);
323+
}
324+
}
325+
}
326+
281327
foreach ($bootstrapCoordinator->getRegistrationContext()->getAlternativeLogins() as $registration) {
282328
if (!in_array(IAlternativeLogin::class, class_implements($registration->getService()), true)) {
283329
Server::get(LoggerInterface::class)->error('Alternative login option {option} does not implement {interface} and is therefore ignored.', [

lib/public/AppFramework/Bootstrap/IRegistrationContext.php

Lines changed: 12 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -161,9 +161,21 @@ public function registerSearchProvider(string $class): void;
161161
* @return void
162162
*
163163
* @since 20.0.0
164+
* @deprecated 34.0.0 Use registerAlternativeLoginProvider instead.
164165
*/
165166
public function registerAlternativeLogin(string $class): void;
166167

168+
/**
169+
* Register an alternative login options provider
170+
*
171+
* It is allowed to register more than one option per app.
172+
*
173+
* @param class-string<\OCP\Authentication\IAlternativeLoginProvider> $class
174+
*
175+
* @since 34.0.0
176+
*/
177+
public function registerAlternativeLoginProvider(string $class): void;
178+
167179
/**
168180
* Register an initialstate provider
169181
*
Lines changed: 22 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,22 @@
1+
<?php
2+
3+
declare(strict_types=1);
4+
5+
/**
6+
* SPDX-FileCopyrightText: 2026 Nextcloud GmbH and Nextcloud contributors
7+
* SPDX-License-Identifier: AGPL-3.0-or-later
8+
*/
9+
namespace OCP\Authentication;
10+
11+
/**
12+
* Provider exposing one or multiple IAlternativeLogin.
13+
*
14+
* @since 34.0.0
15+
*/
16+
interface IAlternativeLoginProvider {
17+
/**
18+
* @return list<IAlternativeLogin>
19+
* @since 34.0.0
20+
*/
21+
public function getAlternativeLogins(): array;
22+
}

0 commit comments

Comments
 (0)