Skip to content

Commit

Permalink
Improvement: Add a side entrance login page for local logins if the l…
Browse files Browse the repository at this point in the history
…ocal login form is disabled on the standard login page, resolves #539. (#547)
  • Loading branch information
abias authored Jan 26, 2024
1 parent 30900ab commit c26338b
Show file tree
Hide file tree
Showing 8 changed files with 220 additions and 1 deletion.
1 change: 1 addition & 0 deletions CHANGES.md
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,7 @@ Changes

### Unreleased

* 2024-01-20 - Improvement: Add a side entrance login page for local logins if the local login form is disabled on the standard login page, resolves #539.
* 2024-01-20 - Improvement: Make all block regions available for the incourse and coursecategory page layouts, resolves #543.
* 2024-01-19 - Bugfix: Get rid of 'Undefined stdClass property' notices for static page settings, resolves #431.

Expand Down
2 changes: 2 additions & 0 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -201,6 +201,8 @@ With this setting, you can make the login form slightly transparent to let the b

With this setting, you control if the local login form is shown on the login page or not. By default, the local login form is shown and users an login into the site as normal. If you disable this setting, the local login form is hidden. This allows you to just provide login buttons for external identity providers like OAuth2 or OIDC.

Please note: As soon as you hide the local login form, you risk that admins cannot log in anymore with a local account if there is a problem with the external identity provider. To allow local logins anyway in such cases, a side entrance local login page is provided on /theme/boost_union/locallogin.php. On this side entrance local login page, all of Moodle's login security measures apply as well.

##### IDP login intro

With this setting, you control if the 'Log in using your account on' intro is shown above the IDP login buttons or not. By default, the intro is shown and users will be quickly informed what the IDP buttons are about. If you disable this setting, the IDP intro is hidden. This allows you to provide a clean user login interface if you just use external identity providers like OAuth2 or OIDC.
Expand Down
3 changes: 3 additions & 0 deletions lang/en/theme_boost_union.php
Original file line number Diff line number Diff line change
Expand Up @@ -206,6 +206,9 @@
// ... ... Setting: Local login form.
$string['loginlocalloginenablesetting'] = 'Local login';
$string['loginlocalloginenablesetting_desc'] = 'With this setting, you control if the local login form is shown on the login page or not. By default, the local login form is shown and users an login into the site as normal. If you disable this setting, the local login form is hidden. This allows you to just provide login buttons for external identity providers like OAuth2 or OIDC.';
$string['loginlocalloginenablesetting_note'] = 'Please note: As soon as you hide the local login form, you risk that admins cannot log in anymore with a local account if there is a problem with the external identity provider. To allow local logins anyway in such cases, a <a href="{$a->url}">side entrance local login page</a> is provided. On this side entrance local login page, all of Moodle\'s login security measures apply as well.';
$string['loginlocalloginformhead'] = 'Local login';
$string['loginlocalloginlocalnotdisabled'] = 'The local login is enabled on the standard login form. There is no need to log in on this local login page here. Please use the <a href="{$a->url}">standard login page</a> for logging in.';
// ... ... Setting: IDP login intro.
$string['loginidpshowintrosetting'] = 'IDP login intro';
$string['loginidpshowintrosetting_desc'] = 'With this setting, you control if the <em>\'{$a}\'</em> intro is shown above the IDP login buttons or not. By default, the intro is shown and users will be quickly informed what the IDP buttons are about. If you disable this setting, the IDP intro is hidden. This allows you to provide a clean user login interface if you just use external identity providers like OAuth2 or OIDC.';
Expand Down
85 changes: 85 additions & 0 deletions locallogin.php
Original file line number Diff line number Diff line change
@@ -0,0 +1,85 @@
<?php
// This file is part of Moodle - http://moodle.org/
//
// Moodle is free software: you can redistribute it and/or modify
// it under the terms of the GNU General Public License as published by
// the Free Software Foundation, either version 3 of the License, or
// (at your option) any later version.
//
// Moodle is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
// GNU General Public License for more details.
//
// You should have received a copy of the GNU General Public License
// along with Moodle. If not, see <http://www.gnu.org/licenses/>.

/**
* Theme Boost Union - Local login page
*
* This file is copied, reduced and modified from /login/index.php.
*
* @package theme_boost_union
* @copyright 2023 Alexander Bias <[email protected]>
* based on code 1999 onwards Martin Dougiamas
* @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later
*/

// Include config.php.
// @codingStandardsIgnoreStart
// Let codechecker ignore the next line because otherwise it would complain about a missing login check
// after requiring config.php which is really not needed.
require(__DIR__.'/../../config.php');
// @codingStandardsIgnoreEnd

// Require the necessary libraries.
require_once($CFG->dirroot.'/lib/authlib.php');
require_once($CFG->dirroot.'/theme/boost_union/lib.php');

// Set page URL.
$PAGE->set_url('/theme/boost_union/locallogin.php');

// Set page layout.
$PAGE->set_pagelayout('login');

// Set page context.
$PAGE->set_context(context_system::instance());

// Get theme config.
$config = get_config('theme_boost_union');

// If the local login is not disabled, we just show a short friendly warning page and are done.
if ($config->loginlocalloginenable != THEME_BOOST_UNION_SETTING_SELECT_NO) {
echo $OUTPUT->header();
$loginurl = new moodle_url('/login/index.php');
$notification = new \core\output\notification(
get_string('loginlocalloginlocalnotdisabled', 'theme_boost_union', ['url' => $loginurl]),
\core\output\notification::NOTIFY_INFO);
$notification->set_show_closebutton(false);
echo $OUTPUT->render($notification);
echo $OUTPUT->footer();
die;
}

// If the user is already logged in or is a guest user.
if (isloggedin() || isguestuser()) {
// We just redirect him to the standard login page to handle this case.
redirect('/login/index.php');
}

// Set page title.
$PAGE->set_title(get_string('loginsite'));

// Start page output.
echo $OUTPUT->header();

// Prepare the local login form.
$templatecontext = [];
$templatecontext['loginurl'] = new moodle_url('/login/index.php');
$templatecontext['logintoken'] = \core\session\manager::get_login_token();

// Output the local login form.
echo $OUTPUT->render_from_template('theme_boost_union/localloginform', $templatecontext);

// Finish page.
echo $OUTPUT->footer();
4 changes: 3 additions & 1 deletion settings.php
Original file line number Diff line number Diff line change
Expand Up @@ -665,7 +665,9 @@
// Setting: Local login.
$name = 'theme_boost_union/loginlocalloginenable';
$title = get_string('loginlocalloginenablesetting', 'theme_boost_union', null, true);
$description = get_string('loginlocalloginenablesetting_desc', 'theme_boost_union', null, true);
$localloginurl = new moodle_url('/theme/boost_union/locallogin.php');
$description = get_string('loginlocalloginenablesetting_desc', 'theme_boost_union', null, true).'<br /><br />'.
get_string('loginlocalloginenablesetting_note', 'theme_boost_union', ['url' => $localloginurl], true);
$setting = new admin_setting_configselect($name, $title, $description, THEME_BOOST_UNION_SETTING_SELECT_YES, $yesnooption);
$tab->add($setting);

Expand Down
54 changes: 54 additions & 0 deletions templates/localloginform.mustache
Original file line number Diff line number Diff line change
@@ -0,0 +1,54 @@
{{!
This file is part of Moodle - http://moodle.org/
Moodle is free software: you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation, either version 3 of the License, or
(at your option) any later version.
Moodle is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with Moodle. If not, see <http://www.gnu.org/licenses/>.
}}
{{!
@template theme_boost_union/localloginform
Boost Union template for outputting the local login form on the local login page.
This is a limited and modified version of core/loginform.
Context variables required for this template:
* loginurl - Login url,
* logintoken - Random token to protect login request.,
Example context (json):
{
"loginurl": "http://localhost/stable_master/login/index.php",
"logintoken": "randomstring",
}
}}

<div class="loginform">
<h1 class="login-heading mb-4">{{#str}}loginlocalloginformhead, theme_boost_union{{/str}}</h1>
<form class="login-form" action="{{loginurl}}" method="post" id="login">
<input type="hidden" name="logintoken" value="{{logintoken}}">
<div class="login-form-username form-group">
<label for="username" class="sr-only">{{#str}}username{{/str}}</label>
<input type="text" name="username" id="username" {{!
!}}class="form-control form-control-lg"{{!
!}}placeholder="{{#cleanstr}}username{{/cleanstr}}">
</div>
<div class="login-form-password form-group">
<label for="password" class="sr-only">{{#str}} password {{/str}}</label>
<input type="password" name="password" id="password" value="" {{!
!}}class="form-control form-control-lg" {{!
!}}placeholder="{{#cleanstr}}password{{/cleanstr}}">
</div>
<div class="login-form-submit form-group">
<button class="btn btn-primary btn-lg" type="submit" id="loginbtn">{{#str}}login{{/str}}</button>
</div>
</form>
</div>
43 changes: 43 additions & 0 deletions tests/behat/behat_theme_boost_union_base_look.php
Original file line number Diff line number Diff line change
@@ -0,0 +1,43 @@
<?php
// This file is part of Moodle - http://moodle.org/
//
// Moodle is free software: you can redistribute it and/or modify
// it under the terms of the GNU General Public License as published by
// the Free Software Foundation, either version 3 of the License, or
// (at your option) any later version.
//
// Moodle is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
// GNU General Public License for more details.
//
// You should have received a copy of the GNU General Public License
// along with Moodle. If not, see <http://www.gnu.org/licenses/>.

/**
* Theme Boost Union - Custom Behat rules for the 'Look' settings
*
* @package theme_boost_union
* @copyright 2023 Alexander Bias <[email protected]>
* @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later
*/

require_once(__DIR__ . '/../../../../lib/behat/behat_base.php');

/**
* Class behat_theme_boost_union_base_look
*
* @package theme_boost_union
* @copyright 2023 Alexander Bias <[email protected]>
* @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later
*/
class behat_theme_boost_union_base_look extends behat_base {
/**
* Open the local login page.
*
* @Given /^I am on local login page$/
*/
public function i_am_on_local_login_page() {
$this->execute('behat_general::i_visit', ['/theme/boost_union/locallogin.php']);
}
}
29 changes: 29 additions & 0 deletions tests/behat/theme_boost_union_looksettings_loginpage.feature
Original file line number Diff line number Diff line change
Expand Up @@ -151,6 +151,35 @@ Feature: Configuring the theme_boost_union plugin for the "Login page" tab on th
| yes | should |
| no | should not |

Scenario Outline: Setting: Local login - View the side entrance login page
Given the following config values are set as admin:
| config | value | plugin |
| loginlocalloginenable | <setting> | theme_boost_union |
When I am on local login page
Then I <shouldornot1> see "Local login"
And ".login-heading" "css_element" <shouldornot1> exist
And "#username" "css_element" <shouldornot1> exist
And "#password" "css_element" <shouldornot1> exist
And "#loginbtn" "css_element" <shouldornot1> exist
And I <shouldornot2> see "The local login is enabled on the standard login form"

Examples:
| setting | shouldornot1 | shouldornot2 |
| yes | should not | should |
| no | should | should not |

Scenario: Setting: Local login - Use the side entrance login page
Given the following config values are set as admin:
| config | value | plugin |
| loginlocalloginenable | no | theme_boost_union |
When I am on local login page
And I set the following fields to these values:
# With behat, the password is always the same as the username.
| Username | admin |
| Password | admin |
And I press "Log in"
Then I should see "Welcome, Admin" in the "page-header" "region"

Scenario Outline: Setting: IDP login intro
Given the following config values are set as admin:
| config | value | plugin |
Expand Down

0 comments on commit c26338b

Please sign in to comment.