diff --git a/src/__phutil_library_map__.php b/src/__phutil_library_map__.php --- a/src/__phutil_library_map__.php +++ b/src/__phutil_library_map__.php @@ -1843,10 +1843,12 @@ 'PhabricatorAuthSessionQuery' => 'applications/auth/query/PhabricatorAuthSessionQuery.php', 'PhabricatorAuthSetupCheck' => 'applications/config/check/PhabricatorAuthSetupCheck.php', 'PhabricatorAuthStartController' => 'applications/auth/controller/PhabricatorAuthStartController.php', + 'PhabricatorAuthTOTPKeyTemporaryTokenType' => 'applications/auth/factor/PhabricatorAuthTOTPKeyTemporaryTokenType.php', 'PhabricatorAuthTemporaryToken' => 'applications/auth/storage/PhabricatorAuthTemporaryToken.php', 'PhabricatorAuthTemporaryTokenGarbageCollector' => 'applications/auth/garbagecollector/PhabricatorAuthTemporaryTokenGarbageCollector.php', 'PhabricatorAuthTemporaryTokenQuery' => 'applications/auth/query/PhabricatorAuthTemporaryTokenQuery.php', 'PhabricatorAuthTemporaryTokenType' => 'applications/auth/tokentype/PhabricatorAuthTemporaryTokenType.php', + 'PhabricatorAuthTemporaryTokenTypeModule' => 'applications/auth/tokentype/PhabricatorAuthTemporaryTokenTypeModule.php', 'PhabricatorAuthTerminateSessionController' => 'applications/auth/controller/PhabricatorAuthTerminateSessionController.php', 'PhabricatorAuthTryFactorAction' => 'applications/auth/action/PhabricatorAuthTryFactorAction.php', 'PhabricatorAuthUnlinkController' => 'applications/auth/controller/PhabricatorAuthUnlinkController.php', @@ -6164,6 +6166,7 @@ 'PhabricatorAuthSessionQuery' => 'PhabricatorCursorPagedPolicyAwareQuery', 'PhabricatorAuthSetupCheck' => 'PhabricatorSetupCheck', 'PhabricatorAuthStartController' => 'PhabricatorAuthController', + 'PhabricatorAuthTOTPKeyTemporaryTokenType' => 'PhabricatorAuthTemporaryTokenType', 'PhabricatorAuthTemporaryToken' => array( 'PhabricatorAuthDAO', 'PhabricatorPolicyInterface', @@ -6171,6 +6174,7 @@ 'PhabricatorAuthTemporaryTokenGarbageCollector' => 'PhabricatorGarbageCollector', 'PhabricatorAuthTemporaryTokenQuery' => 'PhabricatorCursorPagedPolicyAwareQuery', 'PhabricatorAuthTemporaryTokenType' => 'Phobject', + 'PhabricatorAuthTemporaryTokenTypeModule' => 'PhabricatorConfigModule', 'PhabricatorAuthTerminateSessionController' => 'PhabricatorAuthController', 'PhabricatorAuthTryFactorAction' => 'PhabricatorSystemAction', 'PhabricatorAuthUnlinkController' => 'PhabricatorAuthController', diff --git a/src/applications/auth/factor/PhabricatorAuthTOTPKeyTemporaryTokenType.php b/src/applications/auth/factor/PhabricatorAuthTOTPKeyTemporaryTokenType.php new file mode 100644 --- /dev/null +++ b/src/applications/auth/factor/PhabricatorAuthTOTPKeyTemporaryTokenType.php @@ -0,0 +1,17 @@ +<?php + +final class PhabricatorAuthTOTPKeyTemporaryTokenType + extends PhabricatorAuthTemporaryTokenType { + + const TOKENTYPE = 'mfa:totp:key'; + + public function getTokenTypeDisplayName() { + return pht('TOTP Synchronization'); + } + + public function getTokenReadableTypeName( + PhabricatorAuthTemporaryToken $token) { + return pht('TOTP Sync Token'); + } + +} diff --git a/src/applications/auth/factor/PhabricatorTOTPAuthFactor.php b/src/applications/auth/factor/PhabricatorTOTPAuthFactor.php --- a/src/applications/auth/factor/PhabricatorTOTPAuthFactor.php +++ b/src/applications/auth/factor/PhabricatorTOTPAuthFactor.php @@ -2,8 +2,6 @@ final class PhabricatorTOTPAuthFactor extends PhabricatorAuthFactor { - const TEMPORARY_TOKEN_TYPE = 'mfa:totp:key'; - public function getFactorKey() { return 'totp'; } @@ -24,6 +22,8 @@ AphrontRequest $request, PhabricatorUser $user) { + $totp_token_type = PhabricatorAuthTOTPKeyTemporaryTokenType::TOKENTYPE; + $key = $request->getStr('totpkey'); if (strlen($key)) { // If the user is providing a key, make sure it's a key we generated. @@ -37,7 +37,7 @@ $temporary_token = id(new PhabricatorAuthTemporaryTokenQuery()) ->setViewer($user) ->withTokenResources(array($user->getPHID())) - ->withTokenTypes(array(self::TEMPORARY_TOKEN_TYPE)) + ->withTokenTypes(array($totp_token_type)) ->withExpired(false) ->withTokenCodes(array(PhabricatorHash::digest($key))) ->executeOne(); @@ -56,7 +56,7 @@ $unguarded = AphrontWriteGuard::beginScopedUnguardedWrites(); id(new PhabricatorAuthTemporaryToken()) ->setTokenResource($user->getPHID()) - ->setTokenType(self::TEMPORARY_TOKEN_TYPE) + ->setTokenType($totp_token_type) ->setTokenExpires(time() + phutil_units('1 hour in seconds')) ->setTokenCode(PhabricatorHash::digest($key)) ->save(); diff --git a/src/applications/auth/tokentype/PhabricatorAuthOneTimeLoginTemporaryTokenType.php b/src/applications/auth/tokentype/PhabricatorAuthOneTimeLoginTemporaryTokenType.php --- a/src/applications/auth/tokentype/PhabricatorAuthOneTimeLoginTemporaryTokenType.php +++ b/src/applications/auth/tokentype/PhabricatorAuthOneTimeLoginTemporaryTokenType.php @@ -5,6 +5,10 @@ const TOKENTYPE = 'login:onetime'; + public function getTokenTypeDisplayName() { + return pht('One-Time Login'); + } + public function getTokenReadableTypeName( PhabricatorAuthTemporaryToken $token) { return pht('One-Time Login Token'); diff --git a/src/applications/auth/tokentype/PhabricatorAuthPasswordResetTemporaryTokenType.php b/src/applications/auth/tokentype/PhabricatorAuthPasswordResetTemporaryTokenType.php --- a/src/applications/auth/tokentype/PhabricatorAuthPasswordResetTemporaryTokenType.php +++ b/src/applications/auth/tokentype/PhabricatorAuthPasswordResetTemporaryTokenType.php @@ -5,6 +5,10 @@ const TOKENTYPE = 'login:password'; + public function getTokenTypeDisplayName() { + return pht('Password Reset'); + } + public function getTokenReadableTypeName( PhabricatorAuthTemporaryToken $token) { return pht('Password Reset Token'); diff --git a/src/applications/auth/tokentype/PhabricatorAuthTemporaryTokenType.php b/src/applications/auth/tokentype/PhabricatorAuthTemporaryTokenType.php --- a/src/applications/auth/tokentype/PhabricatorAuthTemporaryTokenType.php +++ b/src/applications/auth/tokentype/PhabricatorAuthTemporaryTokenType.php @@ -3,6 +3,7 @@ abstract class PhabricatorAuthTemporaryTokenType extends Phobject { + abstract public function getTokenTypeDisplayName(); abstract public function getTokenReadableTypeName( PhabricatorAuthTemporaryToken $token); diff --git a/src/applications/auth/tokentype/PhabricatorAuthTemporaryTokenTypeModule.php b/src/applications/auth/tokentype/PhabricatorAuthTemporaryTokenTypeModule.php new file mode 100644 --- /dev/null +++ b/src/applications/auth/tokentype/PhabricatorAuthTemporaryTokenTypeModule.php @@ -0,0 +1,47 @@ +<?php + +final class PhabricatorAuthTemporaryTokenTypeModule + extends PhabricatorConfigModule { + + public function getModuleKey() { + return 'temporarytoken'; + } + + public function getModuleName() { + return pht('Temporary Tokens'); + } + + public function renderModuleStatus(AphrontRequest $request) { + $viewer = $request->getViewer(); + + $types = PhabricatorAuthTemporaryTokenType::getAllTypes(); + + $rows = array(); + foreach ($types as $type) { + $rows[] = array( + get_class($type), + $type->getTokenTypeConstant(), + $type->getTokenTypeDisplayName(), + ); + } + + $table = id(new AphrontTableView($rows)) + ->setHeaders( + array( + pht('Class'), + pht('Key'), + pht('Name'), + )) + ->setColumnClasses( + array( + null, + null, + 'wide pri', + )); + + return id(new PHUIObjectBoxView()) + ->setHeaderText(pht('Temporary Token Types')) + ->setTable($table); + } + +}