Updated user settings page and user forms
This commit is contained in:
@@ -13,3 +13,5 @@ Fixes/tweaks a few "issues" with the default UserFrosting installation, includin
|
|||||||
- Allow site-admins to edit basic role details (name, slug & description)
|
- Allow site-admins to edit basic role details (name, slug & description)
|
||||||
- Added 'hasRole' twig function to check if a user has a role (if a role doesn't exist, always returns false)
|
- Added 'hasRole' twig function to check if a user has a role (if a role doesn't exist, always returns false)
|
||||||
- Added 'Auditer' role and split the activities permission away from site-admins (exclusive only) and everyone else
|
- Added 'Auditer' role and split the activities permission away from site-admins (exclusive only) and everyone else
|
||||||
|
- Made the input elements on the account settings page more in line with the other inputs (including the "hidden" and "disabled" mechanisms)
|
||||||
|
- Update the "User" form to use the partial form elements for common styling with accounts page
|
||||||
15
routes/routes.php
Normal file
15
routes/routes.php
Normal file
@@ -0,0 +1,15 @@
|
|||||||
|
<?php
|
||||||
|
|
||||||
|
/*
|
||||||
|
* AVSDev UF Tweaks (https://avsdev.uk)
|
||||||
|
*
|
||||||
|
* @link https://git.avsdev.uk/avsdev/sprinkle-uf-tweaks
|
||||||
|
* @license https://git.avsdev.uk/avsdev/sprinkle-uf-tweaks/blob/master/LICENSE.md (LGPL-3.0 License)
|
||||||
|
*/
|
||||||
|
|
||||||
|
use UserFrosting\Sprinkle\Core\Util\NoCache;
|
||||||
|
|
||||||
|
$app->group('/account', function () {
|
||||||
|
$this->get('/settings', 'UserFrosting\Sprinkle\UFTweaks\Controller\AccountController:pageSettings')
|
||||||
|
->add('authGuard');
|
||||||
|
})->add(new NoCache());
|
||||||
111
src/Controller/AccountController.php
Normal file
111
src/Controller/AccountController.php
Normal file
@@ -0,0 +1,111 @@
|
|||||||
|
<?php
|
||||||
|
|
||||||
|
/*
|
||||||
|
* AVSDev UF Tweaks (https://avsdev.uk)
|
||||||
|
*
|
||||||
|
* @link https://git.avsdev.uk/avsdev/sprinkle-uf-tweaks
|
||||||
|
* @license https://git.avsdev.uk/avsdev/sprinkle-uf-tweaks/blob/master/LICENSE.md (LGPL-3.0 License)
|
||||||
|
*/
|
||||||
|
|
||||||
|
namespace UserFrosting\Sprinkle\UFTweaks\Controller;
|
||||||
|
|
||||||
|
use Carbon\Carbon;
|
||||||
|
use Illuminate\Database\Capsule\Manager as Capsule;
|
||||||
|
use Psr\Http\Message\ResponseInterface as Response;
|
||||||
|
use Psr\Http\Message\ServerRequestInterface as Request;
|
||||||
|
use UserFrosting\Fortress\Adapter\JqueryValidationAdapter;
|
||||||
|
use UserFrosting\Fortress\RequestDataTransformer;
|
||||||
|
use UserFrosting\Fortress\RequestSchema;
|
||||||
|
use UserFrosting\Fortress\ServerSideValidator;
|
||||||
|
use UserFrosting\Sprinkle\Account\Controller\AccountController as UFAccountController;
|
||||||
|
use UserFrosting\Support\Exception\BadRequestException;
|
||||||
|
use UserFrosting\Support\Exception\ForbiddenException;
|
||||||
|
use UserFrosting\Support\Exception\NotFoundException;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Override account controller class to tweak the Settings page
|
||||||
|
*
|
||||||
|
* @author Craig Williams (craig@avsdev.uk)
|
||||||
|
*/
|
||||||
|
class AccountController extends UFAccountController
|
||||||
|
{
|
||||||
|
/**
|
||||||
|
* Account settings page.
|
||||||
|
*
|
||||||
|
* Provides a form for users to modify various properties of their account, such as name, email, locale, etc.
|
||||||
|
* Any fields that the user does not have permission to modify will be automatically disabled.
|
||||||
|
* This page requires authentication.
|
||||||
|
*
|
||||||
|
* AuthGuard: true
|
||||||
|
* Route: /account/settings
|
||||||
|
* Route Name: {none}
|
||||||
|
* Request type: GET
|
||||||
|
*
|
||||||
|
* @param Request $request
|
||||||
|
* @param Response $response
|
||||||
|
* @param array $args
|
||||||
|
*
|
||||||
|
* @throws ForbiddenException If user is not authorized to access page
|
||||||
|
*/
|
||||||
|
public function pageSettings(Request $request, Response $response, $args)
|
||||||
|
{
|
||||||
|
/** @var \UserFrosting\Support\Repository\Repository $config */
|
||||||
|
$config = $this->ci->config;
|
||||||
|
|
||||||
|
/** @var \UserFrosting\Sprinkle\Account\Authorize\AuthorizationManager */
|
||||||
|
$authorizer = $this->ci->authorizer;
|
||||||
|
|
||||||
|
/** @var \UserFrosting\Sprinkle\Account\Database\Models\Interfaces\UserInterface $currentUser */
|
||||||
|
$currentUser = $this->ci->currentUser;
|
||||||
|
|
||||||
|
// Access-controlled page
|
||||||
|
if (!$authorizer->checkAccess($currentUser, 'uri_account_settings')) {
|
||||||
|
throw new ForbiddenException();
|
||||||
|
}
|
||||||
|
|
||||||
|
// Load validation rules
|
||||||
|
$schema = new RequestSchema('schema://requests/account-settings.yaml');
|
||||||
|
$schema->set('password.validators.length.min', $config['site.password.length.min']);
|
||||||
|
$schema->set('password.validators.length.max', $config['site.password.length.max']);
|
||||||
|
$schema->set('passwordc.validators.length.min', $config['site.password.length.min']);
|
||||||
|
$schema->set('passwordc.validators.length.max', $config['site.password.length.max']);
|
||||||
|
$validatorAccountSettings = new JqueryValidationAdapter($schema, $this->ci->translator);
|
||||||
|
|
||||||
|
$schema = new RequestSchema('schema://requests/profile-settings.yaml');
|
||||||
|
$validatorProfileSettings = new JqueryValidationAdapter($schema, $this->ci->translator);
|
||||||
|
|
||||||
|
// Get a list of all locales
|
||||||
|
$locales = $this->ci->locale->getAvailableOptions();
|
||||||
|
|
||||||
|
// Hide the locale field if there is only 1 locale available
|
||||||
|
$fields = [
|
||||||
|
'hidden' => [],
|
||||||
|
'disabled' => [],
|
||||||
|
];
|
||||||
|
if (count($locales) <= 1) {
|
||||||
|
$fields['hidden'][] = 'locale';
|
||||||
|
}
|
||||||
|
if (!$authorizer->checkAccess($currentUser, 'update_account_settings')) {
|
||||||
|
$fields['disabled'][] = 'name';
|
||||||
|
$fields['disabled'][] = 'locale';
|
||||||
|
$fields['disabled'][] = 'email';
|
||||||
|
$fields['disabled'][] = 'copy';
|
||||||
|
$fields['hidden'][] = 'password';
|
||||||
|
$fields['hidden'][] = 'submit';
|
||||||
|
}
|
||||||
|
|
||||||
|
return $this->ci->view->render($response, 'pages/account-settings.html.twig', [
|
||||||
|
'user' => $currentUser,
|
||||||
|
'locales' => $locales,
|
||||||
|
'form' => [
|
||||||
|
'fields' => $fields,
|
||||||
|
],
|
||||||
|
'page' => [
|
||||||
|
'validators' => [
|
||||||
|
'account_settings' => $validatorAccountSettings->rules('json', false),
|
||||||
|
'profile_settings' => $validatorProfileSettings->rules('json', false),
|
||||||
|
]
|
||||||
|
],
|
||||||
|
]);
|
||||||
|
}
|
||||||
|
}
|
||||||
11
templates/forms/partials/input-current_password.html.twig
Normal file
11
templates/forms/partials/input-current_password.html.twig
Normal file
@@ -0,0 +1,11 @@
|
|||||||
|
{% block input_current_password %}
|
||||||
|
{% if 'password' not in form.fields.hidden %}
|
||||||
|
<div class="form-group">
|
||||||
|
<label for="input-passwordcheck" class="control-label">{{translate("PASSWORD.CURRENT")}}</label>
|
||||||
|
<div class="input-group">
|
||||||
|
<span class="input-group-addon"><i class="fas fa-key"></i></span>
|
||||||
|
<input type="password" id="input-passwordcheck" class="form-control" name="passwordcheck" placeholder="{{translate("PASSWORD.CURRENT_EXPLAIN")}}" {% if 'password' in form.fields.disabled %}disabled{% endif %}>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
{% endif %}
|
||||||
|
{% endblock %}
|
||||||
18
templates/forms/partials/input-email.html.twig
Normal file
18
templates/forms/partials/input-email.html.twig
Normal file
@@ -0,0 +1,18 @@
|
|||||||
|
{% block input_email %}
|
||||||
|
{% if 'email' not in form.fields.hidden %}
|
||||||
|
<div class="form-group">
|
||||||
|
<label for="input-email" class="control-label">{{translate('EMAIL')}}</label>
|
||||||
|
<div class="input-group js-copy-container">
|
||||||
|
<span class="input-group-addon"><i class="fas fa-envelope fa-fw"></i></span>
|
||||||
|
<input type="text" class="form-control js-copy-target" name="email" autocomplete="off" value="{{user.email}}" placeholder="{{translate('EMAIL')}}" {% if 'email' in form.fields.disabled %}disabled{% endif %}>
|
||||||
|
{% if 'email' in form.fields.disabled %}
|
||||||
|
{% if 'copy' not in form.fields.disabled %}
|
||||||
|
<span class="input-group-btn">
|
||||||
|
<button class="btn btn-default uf-copy-trigger js-copy-trigger" type="button"><i class="fas fa-clipboard"></i></button>
|
||||||
|
</span>
|
||||||
|
{% endif %}
|
||||||
|
{% endif %}
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
{% endif %}
|
||||||
|
{% endblock %}
|
||||||
11
templates/forms/partials/input-first_name.html.twig
Normal file
11
templates/forms/partials/input-first_name.html.twig
Normal file
@@ -0,0 +1,11 @@
|
|||||||
|
{% block input_first_name %}
|
||||||
|
{% if 'first_name' not in form.fields.hidden %}
|
||||||
|
<div class="form-group">
|
||||||
|
<label for="input-first-name" class="control-label">{{translate('FIRST_NAME')}}</label>
|
||||||
|
<div class="input-group">
|
||||||
|
<span class="input-group-addon"><i class="fas fa-edit fa-fw"></i></span>
|
||||||
|
<input type="text" id="input-first-name" name="first_name" class="form-control" autocomplete="off" value="{{user.first_name}}" placeholder="{{translate('FIRST_NAME')}}" {% if 'name' in form.fields.disabled %}disabled{% endif %}>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
{% endif %}
|
||||||
|
{% endblock %}
|
||||||
21
templates/forms/partials/input-group.html.twig
Normal file
21
templates/forms/partials/input-group.html.twig
Normal file
@@ -0,0 +1,21 @@
|
|||||||
|
{% block input_group %}
|
||||||
|
{% if 'group' not in form.fields.hidden %}
|
||||||
|
<div class="form-group">
|
||||||
|
<label for="input-group">{{translate('GROUP')}}</label>
|
||||||
|
<div class="input-group">
|
||||||
|
<span class="input-group-addon"><i class="fas fa-users fa-fw"></i></span>
|
||||||
|
{% if 'group' in form.fields.disabled %}
|
||||||
|
<input type="text" class="form-control" name="theme" value="{{user.group.name}}" disabled>
|
||||||
|
{% else %}
|
||||||
|
<select id="input-group" class="form-control js-select2" name="group_id">
|
||||||
|
<option value="0">{{translate('GROUP.NONE')}}</option>
|
||||||
|
<option disabled="disabled">-----</option>
|
||||||
|
{% for group in groups %}
|
||||||
|
<option value="{{group.id}}" {% if (group.id == user.group_id) %}selected{% endif %}>{{group.name}}</option>
|
||||||
|
{% endfor %}
|
||||||
|
</select>
|
||||||
|
{% endif %}
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
{% endif %}
|
||||||
|
{% endblock %}
|
||||||
11
templates/forms/partials/input-last_name.html.twig
Normal file
11
templates/forms/partials/input-last_name.html.twig
Normal file
@@ -0,0 +1,11 @@
|
|||||||
|
{% block input_last_name %}
|
||||||
|
{% if 'last_name' not in form.fields.hidden %}
|
||||||
|
<div class="form-group">
|
||||||
|
<label for="input-last-name" class="control-label">{{translate('LAST_NAME')}}</label>
|
||||||
|
<div class="input-group">
|
||||||
|
<span class="input-group-addon"><i class="fas fa-edit fa-fw"></i></span>
|
||||||
|
<input type="text" id="input-last-name" name="last_name" class="form-control" autocomplete="off" value="{{user.last_name}}" placeholder="{{translate('LAST_NAME')}}" {% if 'name' in form.fields.disabled %}disabled{% endif %}>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
{% endif %}
|
||||||
|
{% endblock %}
|
||||||
19
templates/forms/partials/input-locale.html.twig
Normal file
19
templates/forms/partials/input-locale.html.twig
Normal file
@@ -0,0 +1,19 @@
|
|||||||
|
{% block input_locale %}
|
||||||
|
{% if 'locale' not in form.fields.hidden %}
|
||||||
|
<div class="form-group">
|
||||||
|
<label for="input-locale" class="control-label">{{translate('LOCALE')}}</label>
|
||||||
|
<div class="input-group">
|
||||||
|
<span class="input-group-addon"><i class="fas fa-language fa-fw"></i></span>
|
||||||
|
{% if 'locale' in form.fields.disabled %}
|
||||||
|
<input type="text" class="form-control" name="theme" value="{{locales[user.locale]}}" disabled>
|
||||||
|
{% else %}
|
||||||
|
<select id="input-locale" class="form-control js-select2" name="locale">
|
||||||
|
{% for option, label in locales %}
|
||||||
|
<option value="{{option}}" {% if (option == user.locale) %}selected{% endif %}>{{label}}</option>
|
||||||
|
{% endfor %}
|
||||||
|
</select>
|
||||||
|
{% endif %}
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
{% endif %}
|
||||||
|
{% endblock %}
|
||||||
18
templates/forms/partials/input-new_password.html.twig
Normal file
18
templates/forms/partials/input-new_password.html.twig
Normal file
@@ -0,0 +1,18 @@
|
|||||||
|
{% block input_new_password %}
|
||||||
|
{% if 'password' not in form.fields.hidden %}
|
||||||
|
<div class="form-group">
|
||||||
|
<label for="input-password" class="control-label">{{translate("PASSWORD.NEW")}}</label>
|
||||||
|
<div class="input-group">
|
||||||
|
<span class="input-group-addon"><i class="fas fa-key"></i></span>
|
||||||
|
<input type="password" id="input-password" class="form-control" name="password" placeholder="{{translate("PASSWORD.BETWEEN", {min: site.password.length.min, max: site.password.length.max})}} ({{translate("OPTIONAL")}})" {% if 'password' in form.fields.disabled %}disabled{% endif %}>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<div class="form-group">
|
||||||
|
<label for="input-passwordc" class="control-label">{{translate("PASSWORD.CONFIRM_NEW")}}</label>
|
||||||
|
<div class="input-group">
|
||||||
|
<span class="input-group-addon"><i class="fas fa-key"></i></span>
|
||||||
|
<input type="password" id="input-passwordc" class="form-control" name="passwordc" placeholder="{{translate("PASSWORD.CONFIRM_NEW_HELP")}}" {% if 'password' in form.fields.disabled %}disabled{% endif %}>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
{% endif %}
|
||||||
|
{% endblock %}
|
||||||
19
templates/forms/partials/input-theme.html.twig
Normal file
19
templates/forms/partials/input-theme.html.twig
Normal file
@@ -0,0 +1,19 @@
|
|||||||
|
{% block input_theme %}
|
||||||
|
{% if 'theme' not in form.fields.hidden %}
|
||||||
|
<div class="form-group">
|
||||||
|
<label for="input-theme">{{translate('THEME')}}</label>
|
||||||
|
<div class="input-group">
|
||||||
|
<span class="input-group-addon"><i class="fas fa-puzzle-piece fa-fw"></i></span>
|
||||||
|
{% if 'theme' in form.fields.disabled %}
|
||||||
|
<input type="text" class="form-control" name="theme" value="{{themes[user.theme]}}" disabled>
|
||||||
|
{% else %}
|
||||||
|
<select id="input-theme" class="form-control js-select2" name="theme">
|
||||||
|
{% for option, label in theme %}
|
||||||
|
<option value="{{option}}" {% if (option == user.theme) %}selected{% endif %}>{{label}}</option>
|
||||||
|
{% endfor %}
|
||||||
|
</select>
|
||||||
|
{% endif %}
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
{% endif %}
|
||||||
|
{% endblock %}
|
||||||
11
templates/forms/partials/input-user_name.html.twig
Normal file
11
templates/forms/partials/input-user_name.html.twig
Normal file
@@ -0,0 +1,11 @@
|
|||||||
|
{% block input_user_name %}
|
||||||
|
{% if 'user_name' not in form.fields.hidden %}
|
||||||
|
<div class="form-group">
|
||||||
|
<label>{{translate('USERNAME')}}</label>
|
||||||
|
<div class="input-group">
|
||||||
|
<span class="input-group-addon"><i class="fas fa-edit fa-fw"></i></span>
|
||||||
|
<input type="text" class="form-control" name="user_name" autocomplete="off" value="{{user.user_name}}" placeholder="{{translate('USERNAME')}}" {% if 'user_name' in form.fields.disabled %}disabled{% endif %}>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
{% endif %}
|
||||||
|
{% endblock %}
|
||||||
39
templates/forms/settings-account.html.twig
Normal file
39
templates/forms/settings-account.html.twig
Normal file
@@ -0,0 +1,39 @@
|
|||||||
|
<form id="account-settings" role="form" action="{{site.uri.public}}/account/settings" method="post">
|
||||||
|
<div class="box-header">
|
||||||
|
<h3 class="box-title"><i class="fas fa-cog fa-fw"></i> {{translate("ACCOUNT.SETTINGS")}}</h3>
|
||||||
|
</div>
|
||||||
|
<div class="box-body">
|
||||||
|
{% include "forms/csrf.html.twig" %}
|
||||||
|
<!-- Prevent browsers from trying to autofill the password field. See http://stackoverflow.com/a/23234498/2970321 -->
|
||||||
|
<input type="text" style="display:none">
|
||||||
|
<input type="password" style="display:none">
|
||||||
|
|
||||||
|
{% block settings_account %}
|
||||||
|
<div class="row">
|
||||||
|
<div class="col-sm-12">
|
||||||
|
{% include "forms/partials/input-email.html.twig" %}
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="row">
|
||||||
|
<div class="col-sm-12">
|
||||||
|
{% include "forms/partials/input-new_password.html.twig" %}
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
{% if 'password' not in form.fields.hidden %}
|
||||||
|
<hr>
|
||||||
|
{% endif %}
|
||||||
|
<div class="row">
|
||||||
|
<div class="col-sm-12">
|
||||||
|
{% include "forms/partials/input-current_password.html.twig" %}
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
{% endblock %}
|
||||||
|
</div>
|
||||||
|
{% if 'submit' not in form.fields.hidden %}
|
||||||
|
<div class="box-footer text-center">
|
||||||
|
<button type="reset" class="btn btn-default">{{translate('RESET')}}</button>
|
||||||
|
<button type="submit" class="btn btn-primary js-submit">{{translate('SAVE')}}</button>
|
||||||
|
</div>
|
||||||
|
{% endif %}
|
||||||
|
</form>
|
||||||
33
templates/forms/settings-profile.html.twig
Normal file
33
templates/forms/settings-profile.html.twig
Normal file
@@ -0,0 +1,33 @@
|
|||||||
|
<form id="profile-settings" role="form" action="{{site.uri.public}}/account/settings/profile" method="post">
|
||||||
|
<div class="box-header">
|
||||||
|
<h3 class="box-title"><i class="fas fa-user fa-fw"></i> {{translate("PROFILE.SETTINGS")}}</h3>
|
||||||
|
</div>
|
||||||
|
<div class="box-body">
|
||||||
|
{% include "forms/csrf.html.twig" %}
|
||||||
|
|
||||||
|
{% block settings_profile %}
|
||||||
|
{% if 'name' not in form.fields.hidden %}
|
||||||
|
<div class="row">
|
||||||
|
<div class="col-sm-6">
|
||||||
|
{% include "forms/partials/input-first_name.html.twig" %}
|
||||||
|
</div>
|
||||||
|
<div class="col-sm-6">
|
||||||
|
{% include "forms/partials/input-last_name.html.twig" %}
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
{% endif %}
|
||||||
|
|
||||||
|
<div class="row">
|
||||||
|
<div class="col-sm-12">
|
||||||
|
{% include "forms/partials/input-locale.html.twig" %}
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
{% endblock %}
|
||||||
|
</div>
|
||||||
|
{% if 'submit' not in form.fields.hidden %}
|
||||||
|
<div class="box-footer text-center">
|
||||||
|
<button type="reset" class="btn btn-default">{{translate('RESET')}}</button>
|
||||||
|
<button type="submit" class="btn btn-primary js-submit">{{translate('SAVE')}}</button>
|
||||||
|
</div>
|
||||||
|
{% endif %}
|
||||||
|
</form>
|
||||||
46
templates/forms/user.html.twig
Normal file
46
templates/forms/user.html.twig
Normal file
@@ -0,0 +1,46 @@
|
|||||||
|
{% extends "@admin/forms/user.html.twig" %}
|
||||||
|
|
||||||
|
{% block user_form %}
|
||||||
|
{% if 'user_name' not in form.fields.hidden %}
|
||||||
|
<div class="col-sm-6">
|
||||||
|
{% include "forms/partials/input-user_name.html.twig" %}
|
||||||
|
</div>
|
||||||
|
{% endif %}
|
||||||
|
|
||||||
|
{% if 'group' not in form.fields.hidden %}
|
||||||
|
<div class="col-sm-6">
|
||||||
|
{% include "forms/partials/input-group.html.twig" %}
|
||||||
|
</div>
|
||||||
|
{% endif %}
|
||||||
|
|
||||||
|
{% if 'name' not in form.fields.hidden %}
|
||||||
|
<div class="col-sm-6">
|
||||||
|
{% include "forms/partials/input-first_name.html.twig" %}
|
||||||
|
</div>
|
||||||
|
<div class="col-sm-6">
|
||||||
|
{% include "forms/partials/input-last_name.html.twig" %}
|
||||||
|
</div>
|
||||||
|
{% endif %}
|
||||||
|
|
||||||
|
{% if 'email' not in form.fields.hidden %}
|
||||||
|
<div class="col-sm-6">
|
||||||
|
{% include "forms/partials/input-email.html.twig" %}
|
||||||
|
</div>
|
||||||
|
{% endif %}
|
||||||
|
|
||||||
|
{% if 'theme' not in form.fields.hidden %}
|
||||||
|
<div class="col-sm-6">
|
||||||
|
{% include "forms/partials/input-theme.html.twig" %}
|
||||||
|
</div>
|
||||||
|
{% endif %}
|
||||||
|
|
||||||
|
{% if 'locale' not in form.fields.hidden %}
|
||||||
|
<div class="col-sm-6">
|
||||||
|
{% include "forms/partials/input-locale.html.twig" %}
|
||||||
|
</div>
|
||||||
|
{% endif %}
|
||||||
|
|
||||||
|
{% if 'password' not in form.fields.hidden %}
|
||||||
|
{% include "forms/partials/user-set-password.html.twig" %}
|
||||||
|
{% endif %}
|
||||||
|
{% endblock %}
|
||||||
Reference in New Issue
Block a user