diff --git a/Application/Controller/Admin/d3totpadminlogin.php b/Application/Controller/Admin/d3totpadminlogin.php index 0095f0c..dd044e0 100644 --- a/Application/Controller/Admin/d3totpadminlogin.php +++ b/Application/Controller/Admin/d3totpadminlogin.php @@ -33,12 +33,12 @@ use Psr\Log\LoggerInterface; class d3totpadminlogin extends AdminController { - protected $_sThisTemplate = '@'.Constants::OXID_MODULE_ID.'/wave/d3totpadminlogin'; + protected $_sThisTemplate = '@'.Constants::OXID_MODULE_ID.'/admin/d3totplogin'; /** * @return bool */ - protected function _authorize(): bool + protected function authorize(): bool { return true; } diff --git a/Application/Controller/d3totplogin.php b/Application/Controller/d3totplogin.php index 982f7a1..a8cd5af 100644 --- a/Application/Controller/d3totplogin.php +++ b/Application/Controller/d3totplogin.php @@ -25,7 +25,7 @@ use OxidEsales\Eshop\Core\Utils; class d3totplogin extends FrontendController { - protected $_sThisTemplate = '@'.Constants::OXID_MODULE_ID.'/admin/d3totplogin'; + protected $_sThisTemplate = '@'.Constants::OXID_MODULE_ID.'/apex/d3totplogin'; public function render() { diff --git a/Application/translations/de/translations.php b/Application/translations/de/translations.php index 5b864f3..4005ec7 100644 --- a/Application/translations/de/translations.php +++ b/Application/translations/de/translations.php @@ -25,8 +25,6 @@ return [ 'D3_TOTP_ACCOUNT' => '2-Faktor-Authentisierung', 'D3_TOTP_ACCOUNT_DESC' => 'Sichern Sie Ihre Kontoanmeldung mit einem zweiten Faktor.', - 'D3_TOTP_ACCOUNT_USE' => '2-Faktor-Authentisierung verwenden', - 'D3_TOTP_REGISTERNEW' => 'neue Registrierung erstellen', 'D3_TOTP_QRCODE' => 'QR-Code', 'D3_TOTP_QRCODE_HELP' => 'Scannen Sie diesen QR-Code mit Ihrer Authentisierungs-App, um dieses Benutzerkonto dort zu hinterlegen.', @@ -35,6 +33,9 @@ return [ 'D3_TOTP_CURROTP' => 'Bestätigung mit Einmalpasswort', 'D3_TOTP_CURROTP_HELP' => 'Haben Sie dieses Kundenkonto in Ihrer Authentisierungs-App registriert, generieren Sie damit ein Einmalpasswort, tragen Sie es hier ein und senden das Formular direkt darauf hin ab.', + 'D3_TOTP_STATUS' => 'Status', + 'D3_TOTP_ACCOUNT_USE' => '2-Faktor-Authentisierung verwenden', + 'D3_TOTP_REGISTEREXIST' => 'vorhandene Registrierung', 'D3_TOTP_REGISTERDELETE_DESC' => 'Um die Registrierung zu ändern, löschen Sie diese bitte vorerst. Sie können sofort im Anschluss eine neue Registrierung anlegen.
Wenn Sie die Registrierung löschen, ist das Konto nicht mehr durch die Zwei-Faktor-Authentisierung geschützt.', 'D3_TOTP_REGISTERDELETE_CONFIRM' => 'Soll die bestehende 2-Faktor-Authentisierung gelöscht werden?', @@ -44,6 +45,13 @@ return [ 'D3_TOTP_AVAILBACKUPCODECOUNT' => 'noch %1$s Backupcode(s) verfügbar', 'D3_TOTP_AVAILBACKUPCODECOUNT_DESC' => 'Um neue Backupcodes zu erstellen, löschen Sie die bestehende Registrierung und legen diese bitte neu an.', + 'D3_TOTP_INPUT_FIRST' => 'erste TOTP-Ziffer', + 'D3_TOTP_INPUT_SECOND' => 'zweite TOTP-Ziffer', + 'D3_TOTP_INPUT_THIRD' => 'dritte TOTP-Ziffer', + 'D3_TOTP_INPUT_FOURTH' => 'vierte TOTP-Ziffer', + 'D3_TOTP_INPUT_FIFTH' => 'fünfte TOTP-Ziffer', + 'D3_TOTP_INPUT_SIXTH' => 'sechste TOTP-Ziffer', + 'D3_TOTP_ACCOUNT_SAVE' => 'Einstellungen übernehmen', ]; diff --git a/Application/translations/en/translations.php b/Application/translations/en/translations.php index 31566f1..8409be1 100644 --- a/Application/translations/en/translations.php +++ b/Application/translations/en/translations.php @@ -25,8 +25,6 @@ return [ 'D3_TOTP_ACCOUNT' => '2-factor authentication', 'D3_TOTP_ACCOUNT_DESC' => 'Secure your account login with a second factor.', - 'D3_TOTP_ACCOUNT_USE' => 'Use 2-factor authentication', - 'D3_TOTP_REGISTERNEW' => 'create a new registration', 'D3_TOTP_QRCODE' => 'QR code', 'D3_TOTP_QRCODE_HELP' => 'Scan this QR code with your authentication app to store this user account there.', @@ -35,15 +33,25 @@ return [ 'D3_TOTP_CURROTP' => 'Confirmation with one-time password', 'D3_TOTP_CURROTP_HELP' => 'If you have registered this customer account in your authentication app, use it to generate a one-time password, enter it here and send the form directly afterwards.', - 'D3_TOTP_REGISTEREXIST' => 'existing registration', + 'D3_TOTP_STATUS' => 'Status', + 'D3_TOTP_ACCOUNT_USE' => 'use 2-factor authentication', + + 'D3_TOTP_REGISTEREXIST' => 'Existing registration', 'D3_TOTP_REGISTERDELETE_DESC' => 'To change the registration, please delete it first. You can then create a new registration immediately.
If you delete the registration, the account is no longer protected by two-factor authentication.', 'D3_TOTP_REGISTERDELETE_CONFIRM' => 'Should the existing 2-factor authentication be deleted?', - 'D3_TOTP_BACKUPCODES' => 'backup codes', + 'D3_TOTP_BACKUPCODES' => 'Backup codes', 'D3_TOTP_BACKUPCODES_DESC' => 'You can use these backup codes to log on if it is not possible to generate the one-time password (e.g. device lost or newly installed). You can then change the settings to use 2-factor authentication or create a new account. Please save these codes securely at this moment. After leaving this page, these codes cannot be displayed again.', 'D3_TOTP_AVAILBACKUPCODECOUNT' => 'still %1$s backup code(s) available', 'D3_TOTP_AVAILBACKUPCODECOUNT_DESC' => 'To create new backup codes, delete the existing registry and create a new one.', + 'D3_TOTP_INPUT_FIRST' => 'first TOTP digit', + 'D3_TOTP_INPUT_SECOND' => 'second TOTP digit', + 'D3_TOTP_INPUT_THIRD' => 'third TOTP digit', + 'D3_TOTP_INPUT_FOURTH' => 'fourth TOTP digit', + 'D3_TOTP_INPUT_FIFTH' => 'fifth TOTP digit', + 'D3_TOTP_INPUT_SIXTH' => 'sixth TOTP digit', + 'D3_TOTP_ACCOUNT_SAVE' => 'Confirm settings', ]; diff --git a/Application/views/de/translations.php b/Application/views/de/translations.php index 153aeae..fe938a1 100644 --- a/Application/views/de/translations.php +++ b/Application/views/de/translations.php @@ -47,6 +47,13 @@ return [ 'D3_TOTP_AVAILBACKUPCODECOUNT' => 'noch %1$s Backupcode(s) verfügbar', 'D3_TOTP_AVAILBACKUPCODECOUNT_DESC' => 'Um neue Backupcodes zu erstellen, löschen Sie die bestehende Registrierung und legen diese bitte neu an.', + 'D3_TOTP_INPUT_FIRST' => 'erste TOTP-Ziffer', + 'D3_TOTP_INPUT_SECOND' => 'zweite TOTP-Ziffer', + 'D3_TOTP_INPUT_THIRD' => 'dritte TOTP-Ziffer', + 'D3_TOTP_INPUT_FOURTH' => 'vierte TOTP-Ziffer', + 'D3_TOTP_INPUT_FIFTH' => 'fünfte TOTP-Ziffer', + 'D3_TOTP_INPUT_SIXTH' => 'sechste TOTP-Ziffer', + 'D3_TOTP_SAVE' => 'Speichern', 'D3_TOTP_ERROR_UNVALID' => 'Das Einmalpasswort ist ungültig.', diff --git a/Application/views/en/translations.php b/Application/views/en/translations.php index 8a45e1f..ce0e15c 100644 --- a/Application/views/en/translations.php +++ b/Application/views/en/translations.php @@ -47,6 +47,13 @@ return [ 'D3_TOTP_AVAILBACKUPCODECOUNT' => '%1$s backup code(s) still available', 'D3_TOTP_AVAILBACKUPCODECOUNT_DESC' => 'To create new backup codes, delete the existing registry and create a new one.', + 'D3_TOTP_INPUT_FIRST' => 'first TOTP digit', + 'D3_TOTP_INPUT_SECOND' => 'second TOTP digit', + 'D3_TOTP_INPUT_THIRD' => 'third TOTP digit', + 'D3_TOTP_INPUT_FOURTH' => 'fourth TOTP digit', + 'D3_TOTP_INPUT_FIFTH' => 'fifth TOTP digit', + 'D3_TOTP_INPUT_SIXTH' => 'sixth TOTP digit', + 'D3_TOTP_SAVE' => 'Save', 'D3_TOTP_ERROR_UNVALID' => 'The one-time password is invalid.', diff --git a/Modules/Application/Component/d3_totp_UserComponent.php b/Modules/Application/Component/d3_totp_UserComponent.php index 2aad5c4..f68c80e 100644 --- a/Modules/Application/Component/d3_totp_UserComponent.php +++ b/Modules/Application/Component/d3_totp_UserComponent.php @@ -15,11 +15,13 @@ declare(strict_types=1); namespace D3\Totp\Modules\Application\Component; +use Assert\Assert; use D3\Totp\Application\Model\d3totp; use D3\Totp\Application\Model\d3totp_conf; use D3\Totp\Application\Model\Exceptions\d3totp_wrongOtpException; use D3\Totp\Modules\Application\Model\d3_totp_user; -use Doctrine\DBAL\DBALException; +use Doctrine\DBAL\Driver\Exception; +use Doctrine\DBAL\Exception as DBALException; use InvalidArgumentException; use OxidEsales\Eshop\Application\Model\User; use OxidEsales\Eshop\Core\Exception\DatabaseConnectionException; @@ -27,6 +29,8 @@ use OxidEsales\Eshop\Core\Registry; use OxidEsales\Eshop\Core\Session; use OxidEsales\Eshop\Core\Utils; use OxidEsales\Eshop\Core\UtilsView; +use Psr\Container\ContainerExceptionInterface; +use Psr\Container\NotFoundExceptionInterface; class d3_totp_UserComponent extends d3_totp_UserComponent_parent { @@ -36,13 +40,12 @@ class d3_totp_UserComponent extends d3_totp_UserComponent_parent * @return string * @throws DatabaseConnectionException */ - protected function _afterLogin($oUser) + protected function afterLogin($oUser) { - if (!$oUser instanceof User) { - throw oxNew(InvalidArgumentException::class, 'user argument must an instance of User class'); - } + Assert::that($oUser)->isInstanceOf(User::class, 'user argument must an instance of User class'); - if ($oUser->getId()) { + try { + Assert::that($oUser->getId())->notBlank('user must logged in'); $totp = $this->d3GetTotpObject(); $totp->loadByUserId($oUser->getId()); @@ -65,9 +68,9 @@ class d3_totp_UserComponent extends d3_totp_UserComponent_parent $sUrl = Registry::getConfig()->getShopHomeUrl() . 'cl=d3totplogin'; $this->d3TotpGetUtils()->redirect($sUrl, false); } - } + } catch (InvalidArgumentException) {} - return parent::_afterLogin($oUser); + return parent::afterLogin($oUser); } /** @@ -79,10 +82,14 @@ class d3_totp_UserComponent extends d3_totp_UserComponent_parent } /** - * @throws DBALException + * @return false|string * @throws DatabaseConnectionException + * @throws Exception + * @throws DBALException + * @throws ContainerExceptionInterface + * @throws NotFoundExceptionInterface */ - public function d3TotpCheckTotpLogin() + public function d3TotpCheckTotpLogin(): false|string { $sTotp = implode('', Registry::getRequest()->getRequestEscapedParameter('d3totp') ?: []); @@ -101,7 +108,7 @@ class d3_totp_UserComponent extends d3_totp_UserComponent_parent $this->d3TotpGetSession()->setVariable(d3totp_conf::OXID_FRONTEND_AUTH, $oUser->getId()); $this->setUser($oUser); $this->setLoginStatus(USER_LOGIN_SUCCESS); - $this->_afterLogin($oUser); + $this->afterLogin($oUser); $this->d3TotpClearSessionVariables(); @@ -117,7 +124,7 @@ class d3_totp_UserComponent extends d3_totp_UserComponent_parent /** * @return UtilsView */ - public function d3TotpGetUtilsView() + public function d3TotpGetUtilsView(): UtilsView { return Registry::getUtilsView(); } @@ -125,12 +132,12 @@ class d3_totp_UserComponent extends d3_totp_UserComponent_parent /** * @return Utils */ - public function d3TotpGetUtils() + public function d3TotpGetUtils(): Utils { return Registry::getUtils(); } - public function d3TotpCancelTotpLogin() + public function d3TotpCancelTotpLogin(): bool { $this->d3TotpClearSessionVariables(); @@ -141,7 +148,7 @@ class d3_totp_UserComponent extends d3_totp_UserComponent_parent * @param d3totp $totp * @return bool */ - public function d3TotpIsNoTotpOrNoLogin($totp) + public function d3TotpIsNoTotpOrNoLogin($totp): bool { return false == Registry::getSession()->getVariable(d3totp_conf::SESSION_CURRENTUSER) || false == $totp->isActive(); @@ -154,13 +161,13 @@ class d3_totp_UserComponent extends d3_totp_UserComponent_parent * @throws DatabaseConnectionException * @throws d3totp_wrongOtpException */ - public function d3TotpHasValidTotp($sTotp, $totp) + public function d3TotpHasValidTotp($sTotp, $totp): bool { return Registry::getSession()->getVariable(d3totp_conf::SESSION_AUTH) || $totp->verify($sTotp); } - public function d3TotpClearSessionVariables() + public function d3TotpClearSessionVariables(): void { $this->d3TotpGetSession()->deleteVariable(d3totp_conf::SESSION_CURRENTCLASS); $this->d3TotpGetSession()->deleteVariable(d3totp_conf::SESSION_CURRENTUSER); @@ -170,7 +177,7 @@ class d3_totp_UserComponent extends d3_totp_UserComponent_parent /** * @return Session */ - public function d3TotpGetSession() + public function d3TotpGetSession(): Session { return Registry::getSession(); } diff --git a/Modules/Application/Controller/Admin/d3_totp_LoginController.php b/Modules/Application/Controller/Admin/d3_totp_LoginController.php index cbece90..cea75c8 100644 --- a/Modules/Application/Controller/Admin/d3_totp_LoginController.php +++ b/Modules/Application/Controller/Admin/d3_totp_LoginController.php @@ -64,7 +64,7 @@ class d3_totp_LoginController extends d3_totp_LoginController_parent return $this->d3CallMockableFunction([d3_totp_LoginController_parent::class, 'checklogin']); } - public function d3totpAfterLogin() + public function d3totpAfterLogin(): void { $myUtilsServer = $this->d3TotpGetUtilsServer(); $sProfile = $this->d3TotpGetSession()->getVariable(d3totp_conf::SESSION_ADMIN_PROFILE); diff --git a/Modules/Core/totpSystemEventHandler.php b/Modules/Core/totpSystemEventHandler.php index 5bcbab9..ecc8e25 100644 --- a/Modules/Core/totpSystemEventHandler.php +++ b/Modules/Core/totpSystemEventHandler.php @@ -50,6 +50,7 @@ class totpSystemEventHandler extends totpSystemEventHandler_parent $this->getUtilsObject()->redirect( 'index.php?cl=d3totpadminlogin&'. + 'stoken='.Registry::getRequest()->getRequestEscapedParameter('stoken').'&'. 'profile='.$this->d3TotpGetSession()->getVariable(d3totp_conf::SESSION_ADMIN_PROFILE).'&'. 'chlanguage='.$this->d3TotpGetSession()->getVariable(d3totp_conf::SESSION_ADMIN_CHLANGUAGE), false diff --git a/views/smarty/admin/tpl/d3totplogin.tpl b/views/smarty/admin/tpl/d3totplogin.tpl index 6dd26e1..572f593 100644 --- a/views/smarty/admin/tpl/d3totplogin.tpl +++ b/views/smarty/admin/tpl/d3totplogin.tpl @@ -33,17 +33,17 @@ [{$oView->getBackupCodeCountMessage()}]
- + - + - + - + - + - +
diff --git a/views/smarty/wave/d3totpadminlogin.tpl b/views/smarty/wave/d3totpadminlogin.tpl index c6ec44d..28e15aa 100644 --- a/views/smarty/wave/d3totpadminlogin.tpl +++ b/views/smarty/wave/d3totpadminlogin.tpl @@ -24,17 +24,17 @@ [{$oView->getBackupCodeCountMessage()}]
- + - + - + - + - + - +
diff --git a/views/twig/admin/d3totplogin.html.twig b/views/twig/admin/d3totplogin.html.twig index 8683c78..8183e8c 100644 --- a/views/twig/admin/d3totplogin.html.twig +++ b/views/twig/admin/d3totplogin.html.twig @@ -33,21 +33,21 @@ {{ oView.getBackupCodeCountMessage()|raw }}
- + - + - + - + - + - +
- {% set name = "d3js" %} + {% set d3js %} function clickEvent(previous, next){ const digitKeys = ['0', '1', '2', '3', '4', '5', '6', '7', '8', '9']; const deleteKeys = ['Backspace', 'Delete']; @@ -58,8 +58,7 @@ } } document.addEventListener("paste", function(e) { - if (e.target.type is same as("text") { -) + if (e.target.type === "text") { var data = e.clipboardData.getData('Text'); data = data.split(''); [].forEach.call(document.querySelectorAll("#login input[type=text]"), (node, index) => { @@ -68,7 +67,7 @@ } }); {% endset %} - {{ script({ add: d3js, dynamic: __oxid_include_dynamic }) }} + {{ script({ add: d3js.__toString(), dynamic: __oxid_include_dynamic }) }}
{{ translate({ ident: "TOTP_INPUT_HELP" }) }}
@@ -78,7 +77,7 @@ onclick="document.getElementById('login').fnc.value='d3CancelLogin'; document.getElementById('login').submit();" > - {{ style({ include: oViewConf.getModuleUrl('d3totp', 'out/admin/src/css/d3totplogin.css'): 'out/admin/src/css/d3totplogin.css') }) }} + {{ style({ include: oViewConf.getModuleUrl('d3totp', 'out/admin/src/css/d3totplogin.css') }) }} {{ style() }} diff --git a/views/twig/admin/d3totplogin.tpl b/views/twig/admin/d3totplogin.tpl deleted file mode 100644 index 6dd26e1..0000000 --- a/views/twig/admin/d3totplogin.tpl +++ /dev/null @@ -1,126 +0,0 @@ - - - - [{oxmultilang ident="LOGIN_TITLE"}] - - - - - - - - -
- - - -
- - [{block name="admin_login_form"}] - [{$oViewConf->getHiddenSid()}] - - - - - - -

[{oxmultilang ident="TOTP_INPUT"}]

- - [{if !empty($Errors.default)}] - [{include file="inc_error.tpl" Errorlist=$Errors.default}] - [{/if}] - - [{$oView->getBackupCodeCountMessage()}] - -
- - - - - - - - - - - - -
- - [{capture name="d3js"}] - function clickEvent(previous, next){ - const digitKeys = ['0', '1', '2', '3', '4', '5', '6', '7', '8', '9']; - const deleteKeys = ['Backspace', 'Delete']; - if(next && digitKeys.includes(event.key)){ - document.getElementById(next).focus(); - } else if(previous && deleteKeys.includes(event.key)){ - document.getElementById(previous).focus(); - } - } - document.addEventListener("paste", function(e) { - if (e.target.type === "text") { - var data = e.clipboardData.getData('Text'); - data = data.split(''); - [].forEach.call(document.querySelectorAll("#login input[type=text]"), (node, index) => { - node.value = data[index]; - }); - } - }); - [{/capture}] - [{oxscript add=$smarty.capture.d3js}] - -
[{oxmultilang ident="TOTP_INPUT_HELP"}]
- -
- - - - [{oxstyle include=$oViewConf->getModuleUrl('d3totp', 'out/admin/src/css/d3totplogin.css')}] - [{oxstyle}] - - - -[{** - - - - - - [{$oViewConf->getHiddenSid()}] - - - - - [{if !empty($Errors.default)}] - [{include file="inc_error.tpl" Errorlist=$Errors.default}] - [{/if}] - -
-
- [{include file=$oViewConf->getModulePath('d3webauthn', 'out/img/fingerprint.svg')}] -
-
[{oxmultilang ident="WEBAUTHN_INPUT_HELP"}]
-
-**}] - [{* prevent cancel button (1st button) action when form is sent via Enter key *}] -[{** - - - - - [{oxstyle include=$oViewConf->getModuleUrl('d3webauthn', 'out/admin/src/css/d3webauthnlogin.css')}] - [{oxstyle}] -**}] - [{/block}] -
-
- -[{oxscript}] - - - - diff --git a/views/twig/admin/d3user_totp.tpl b/views/twig/admin/d3user_totp.tpl deleted file mode 100644 index 999662b..0000000 --- a/views/twig/admin/d3user_totp.tpl +++ /dev/null @@ -1,194 +0,0 @@ -[{include file="headitem.tpl" title="GENERAL_ADMIN_TITLE"|oxmultilangassign}] - -[{oxstyle include="https://maxcdn.bootstrapcdn.com/bootstrap/4.0.0/css/bootstrap.min.css"}] -[{oxscript include="https://code.jquery.com/jquery-3.2.1.slim.min.js"}] -[{oxscript include="https://cdnjs.cloudflare.com/ajax/libs/popper.js/1.12.9/umd/popper.min.js"}] -[{oxscript include="https://maxcdn.bootstrapcdn.com/bootstrap/4.0.0/js/bootstrap.min.js"}] -[{oxstyle include="https://cdnjs.cloudflare.com/ajax/libs/font-awesome/5.15.3/css/solid.min.css"}] -[{oxstyle}] - -[{assign var="totp" value=$edit->d3GetTotp()}] -[{assign var="userid" value=$edit->getId()}] -[{$totp->loadByUserId($userid)}] - -[{if $readonly}] - [{assign var="readonly" value="readonly disabled"}] -[{else}] - [{assign var="readonly" value=""}] -[{/if}] - - - -[{if $force2FA}] -
-

[{oxmultilang ident="D3_TOTP_FORCE2FATITLE"}]

-
[{oxmultilang ident="D3_TOTP_FORCE2FASUB"}]
-
-[{/if}] - -
- [{$oViewConf->getHiddenSid()}] - - -
- -
- [{$oViewConf->getHiddenSid()}] - - - - - - - [{if $sSaveError}] - - - - - -
[{oxmultilang ident=$sSaveError}]
- [{/if}] - - [{if $oxid && $oxid != '-1'}] -
-
-
-
- [{block name="user_d3user_totp_form1"}] - [{if false == $totp->getId()}] -
- [{oxmultilang ident="D3_TOTP_REGISTERNEW"}] -
-
-
-
- [{oxmultilang ident="D3_TOTP_QRCODE" suffix="COLON"}] -
-
- [{$totp->getQrCodeElement()}] - [{oxinputhelp ident="D3_TOTP_QRCODE_HELP"}] -
-
-
- [{elseif $force2FA}] -
- [{oxmultilang ident="D3_TOTP_ADMINBACKEND"}] -
-
- -
- [{else}] -
- [{oxmultilang ident="D3_TOTP_REGISTEREXIST"}] -
-
-
-
- [{oxmultilang ident="D3_TOTP_REGISTERDELETE_DESC"}] -
-
- -
-
-
-
- [{/if}] - [{/block}] -
-
-
-
- [{block name="user_d3user_totp_form2"}] - [{if false == $totp->getId()}] -
- [{oxmultilang ident="D3_TOTP_CONFIRMATION"}] -
-
-
-
- -
-
- - [{oxinputhelp ident="D3_TOTP_SECRET_HELP"}] -
-
-
-
- -
-
- - [{oxinputhelp ident="D3_TOTP_CURROTP_HELP"}] -
-
-
-
-
- -
-
-
- [{else}] -
- [{oxmultilang ident="D3_TOTP_BACKUPCODES"}] -
-
- [{if $oView->getBackupCodes()}] -
-
- -
-
- -
-
- [{else}] -
-
- [{oxmultilang ident="D3_TOTP_AVAILBACKUPCODECOUNT" args=$oView->getAvailableBackupCodeCount()}] -
-
- [{oxmultilang ident="D3_TOTP_AVAILBACKUPCODECOUNT_DESC"}] -
-
- [{/if}] -
- [{/if}] - [{/block}] -
-
-
-
- [{/if}] -
- -[{if !$force2FA}] - [{include file="bottomnaviitem.tpl"}] - [{include file="bottomitem.tpl"}] -[{/if}] diff --git a/views/twig/apex/d3_account_totp.html.twig b/views/twig/apex/d3_account_totp.html.twig index 79fa9d2..30d2b6b 100644 --- a/views/twig/apex/d3_account_totp.html.twig +++ b/views/twig/apex/d3_account_totp.html.twig @@ -38,7 +38,7 @@