CAS 登录页面,其中 select2 来源

问题描述 投票:0回答:1

在我们的 CAS 配置中,我们有很多身份验证源。因此,在此页面上,用户使用 select2 等方法搜索和选择源将很有用。 如何修改loginform.html片段? (https://github.com/apereo/cas/blob/master/support/cas-server-support-thymeleaf/src/main/resources/templates/fragments/loginform.html

感谢您的支持。

v.

thymeleaf cas apereo
1个回答
0
投票

答案在这里。

<!DOCTYPE html>
<html lang="en">

<head>
    <meta charset="UTF-8">
    <meta http-equiv="X-UA-Compatible" content="IE=edge"/>
    <meta name="viewport" content="width=device-width, initial-scale=1, shrink-to-fit=no"/>

    <title>Login Form Fragment</title>
    <link href="../../static/css/cas.css" rel="stylesheet" th:remove="tag"/>
</head>

<body>
<main class="container mt-3 mb-3">

    <div th:fragment="loginform" class="d-flex flex-column justify-content-between m-auto"
         th:with="loginFormEnabled=${#strings.defaultString(#themes.code('cas.login-form.enabled'), 'true') == 'true'},
                loginFormViewable=${@casThymeleafTemplatesDirector.isLoginFormViewable(#vars)}">

        <div th:if="${delegatedAuthenticationProviderPrimary == null}">
            <div th:if="${!#strings.isEmpty(#themes.code('cas.hero-banner.file'))}">
                <p>
                    <img id="heroimg"
                         th:title="${#strings.defaultString(#themes.code('cas.theme.name'), 'CAS')}"
                         th:src="@{${#themes.code('cas.hero-banner.file')}}"/>
                </p>
            </div>
            <div class="service-ui" th:replace="~{fragments/serviceui :: serviceUI}">
                <a href="fragments/serviceui.html">service ui fragment</a>
            </div>
        </div>

        <div class="form-wrapper">

            <form method="post" id="fm1" th:object="${credential}" action="login">
                <div id="login-form-controls" th:unless="${loginFormViewable or loginFormEnabled}">
                    <div id="loginErrorsPanel" class="alert alert-danger banner banner-danger banner-dismissible"
                         th:if="${#fields.hasErrors('*')}">
                        <p th:each="err : ${#fields.errors('*')}" th:utext="${err + ' '}">Example error</p>
                        <!--<a href="#" class="close" data-dismiss="alert" aria-label="close">&times;</a>-->
                    </div>
                </div>

                <div id="login-form-controls" th:if="${loginFormViewable and loginFormEnabled}">
                    <div th:if="${existingSingleSignOnSessionAvailable}">
                        <i class="mdi mdi-alert-decagram fas fa-exclamation-triangle"></i>&nbsp;
                        <span id="existingSsoMsg" th:if="${registeredService}" class="mdc-button__label"
                              th:utext="#{screen.welcome.forcedsso(${existingSingleSignOnSessionPrincipal?.id},${registeredService.name})}"/>
                        <span id="existingSsoMsg" th:unless="${registeredService}" class="mdc-button__label"
                              th:utext="#{screen.welcome.forcedsso(${existingSingleSignOnSessionPrincipal?.id}, 'CAS')}"/>
                    </div>
                    <h2 th:unless="${existingSingleSignOnSessionAvailable}" class="text-center">
                        <i class="mdi mdi-security fas fa-shield-alt" aria-hidden="true"></i>
                        <span th:utext="#{screen.welcome.instructions}">Enter your Username and Password:</span>
                    </h2>

                    <div id="loginErrorsPanel" class="banner banner-danger alert alert-danger banner-dismissible"
                         th:if="${#fields.hasErrors('*')}" role="alert">
                        <p th:each="err : ${#fields.errors('*')}" th:utext="${err + ' '}">Example error</p>
                        <!--<a href="#" class="close" data-dismiss="alert" aria-label="close">&times;</a>-->
                    </div>
                    <section class="cas-field form-group my-3" id="usernameSection">
                        <label for="username"
                               class="mdc-text-field mdc-text-field--outlined control-label w-100">
                            <span class="mdc-notched-outline">
                                <span class="mdc-notched-outline__leading"></span>
                                <span class="mdc-notched-outline__notch">
                                    <span class="mdc-floating-label"
                                          th:utext="#{screen.welcome.label.netid}">Username</span>
                                </span>
                                <span class="mdc-notched-outline__trailing"></span>
                            </span>
                            <input class="mdc-text-field__input form-control" id="username"
                                   size="25"
                                   type="text"
                                   th:readonly="!${@casThymeleafTemplatesDirector.isLoginFormUsernameInputVisible(#vars)}"
                                   th:field="*{username}"
                                   th:accesskey="#{screen.welcome.label.netid.accesskey}"
                                   autocapitalize="none"
                                   spellcheck="false"
                                   autocomplete="username" required />
                        </label>

                        <div class="mdc-text-field-helper-line invalid-feedback">
                            <div class="mdc-text-field-helper-text mdc-text-field-helper-text--validation-msg" aria-hidden="true">
                                <span id="usernameValidationMessage" th:utext="#{username.required}"></span>
                            </div>
                        </div>

                        <script type="text/javascript" th:inline="javascript">
                            /*<![CDATA[*/
                            let username = /*[[${@casThymeleafTemplatesDirector.getLoginFormUsername(#vars)}]]*/;
                            let disabled = /*[[${@casThymeleafTemplatesDirector.isLoginFormUsernameInputDisabled(#vars)}]]*/;

                            if (username != null && username !== '') {
                                $('#username').val(username);
                                if (disabled) {
                                    $('#usernameSection').hide();
                                }
                            }
                            /*]]>*/
                        </script>
                    </section>

                    <section class="cas-field form-group my-3 mdc-input-group form-group" id="passwordSection">
                        <div class="mdc-input-group-field mdc-input-group-field-append">
                            <label for="password"
                                   class="mdc-text-field caps-check mdc-text-field--outlined control-label mdc-text-field--with-trailing-icon control-label w-100">
                                    <span class="mdc-notched-outline">
                                        <span class="mdc-notched-outline__leading"></span>
                                        <span class="mdc-notched-outline__notch">
                                            <span class="mdc-floating-label" th:utext="#{screen.welcome.label.password}">Password</span>
                                        </span>
                                        <span class="mdc-notched-outline__trailing"></span>
                                    </span>
                                <input class="mdc-text-field__input form-control pwd"
                                       type="password"
                                       id="password"
                                       size="25"
                                       required
                                       th:accesskey="#{screen.welcome.label.password.accesskey}"
                                       th:field="*{password}"
                                       autocomplete="off"/>
                                <button
                                        class="reveal-password mdc-button mdc-button--unelevated mdc-input-group-append mdc-icon-button btn btn-primary"
                                        tabindex="-1" type="button">
                                    <i class="mdi mdi-eye reveal-password-icon fas fa-eye"></i>
                                    <span class="visually-hidden">Toggle Password</span>
                                </button>
                            </label>
                            <div class="mdc-text-field-helper-line invalid-feedback">
                                <div class="mdc-text-field-helper-text mdc-text-field-helper-text--validation-msg" aria-hidden="true">
                                    <span id="passwordValidationMessage" th:utext="#{password.required}"></span>
                                </div>
                            </div>

                        </div>

                        
                    </section>

                    <section id="authnSourceSection" class="cas-field form-group my-3"
                             th:if="${availableAuthenticationHandlerNames != null}">

<p>
Per poter accedere alla risorsa per favore selezioni o cerchi l'organizzazione con la quale è affiliato.
</p>
<style>
    li[data-isfound="false"] {
  display: none;
}

.hide-none {
  display: none !important;
}
</style>

<div class="mdc-menu-surface--anchor">
  <label class="mdc-text-field mdc-text-field--outlined">
        <span class="mdc-notched-outline">
            <span class="mdc-notched-outline__leading"></span>
            <span class="mdc-notched-outline__notch">
                <span class="mdc-floating-label" id="my-label-id" th:utext="#{screen.welcome.label.source}">Source</span>
            </span>
            <span class="mdc-notched-outline__trailing"></span>
        </span>
        <input id="searchSources" type="text" class="mdc-text-field__input mdc-select__selected-text" aria-labelledby="my-label-id">
    </label>

  <div id="menu" class="mdc-select__menu mdc-menu mdc-menu-surface mdc-menu-surface--fullwidth">
        <ul class="mdc-list" role="listbox" >
            <li id="menuNoData"  class="mdc-list-item hide-none" aria-selected="false" aria-disabled="true" data-value="notfound" role="option" value="">
                <span class="mdc-list-item__ripple"></span>
                <span class="mdc-list-item__text">Nessuna origine trovata.</span>
            </li>
            <li th:each="handler,iter : ${availableAuthenticationHandlerNames}"
                class="mdc-list-item " th:id="${handler + '-authnSource'}"
                th:classappend="${iter.index == 0 ? 'mdc-list-item--selected' : ''}"
                th:data-value="${handler}" role="option">
                <span class="mdc-list-item__ripple"></span>
                <span class="mdc-list-item__text" th:utext="${handler}">Option</span>
            </li>
        </ul>
    </div>
</div>

<script>
    var textFields = document.querySelectorAll('.mdc-text-field');
textFields.forEach(field => {
  mdc.textField.MDCTextField.attachTo(field);
});
var menuS = document.querySelector("#menu");
var menu = new mdc.menu.MDCMenu(menuS);
var searchFieldS = document.querySelector("#searchSources");
menu.setAnchorCorner(mdc.menuSurface.Corner.BOTTOM_LEFT);

document.querySelectorAll('#menu li').forEach(function(li) {
  li.addEventListener('click', function() {
    const selectedLi = this.getAttribute("data-value");
    if (selectedLi != "notfound") {
      // If you are going to post the text field data, I recommend you to get data-value.
      searchFieldS.value = selectedLi;
      searchFieldS.setAttribute("data-value", selectedLi);
      var hiddenInput = document.querySelector("#source");
      hiddenInput.setAttribute("data-value", selectedLi);
      hiddenInput.setAttribute("value", selectedLi);

    }
  });
});

// Open the menu when text field is focused. 
(function() {
  let menuFocused = false;
  searchFieldS.addEventListener("focusin", () => {
    if (!menuFocused) menu.open = true;
  });
  searchFieldS.addEventListener("click", () => {
    menu.open = true;
  });

  menuS.addEventListener("focusin", () => {
    menuFocused = true;
  });
  menuS.addEventListener("focusout", () => {
    // This interval is to help make sure that input.focusIn doesn't re-open the menu
    setTimeout(() => {
      menuFocused = false;
    }, 0);
  });
  searchFieldS.addEventListener("focusout", () => {
    setTimeout(() => {
      if (!menuFocused) menu.open = false;
    }, 0);
  });
})();
searchFieldS.addEventListener("keyup", function(e) {
  const keyT = event.target.value.toUpperCase();
  const menuList = document.querySelectorAll('.mdc-list > li > .mdc-list-item__text');
  const menuLiss = document.querySelectorAll('.mdc-list-item');
  const noDataEl = document.querySelector("#menuNoData");

  // 
  const arr = [];
  menuList.forEach(function(searchItem) {
    if (searchItem.parentElement.getAttribute('id') != "menuNoData") {
      searchItem.parentElement.dataset.isfound = searchItem.textContent.toUpperCase().includes(keyT) ? "true" : "false";
      arr.push(searchItem.parentElement.getAttribute("data-isfound"));
    }
  });
  if (arr.filter(function(countArr) {
      return countArr == "true"
    }).length == 0) {
    noDataEl.classList.remove("hide-none");
  } else {
    if (!noDataEl.classList.contains("hide-none")) {
      noDataEl.classList.add("hide-none");
    }
  }
});
</script>





                        <div class="d-flex">
                            <div th:if="${availableAuthenticationHandlerNames.size() > 1}"
                                 class="mdc-select mdc-select--outlined mdc-select--required mdc-menu-surface--fullwidth authn-source">





                                <input type="hidden" id="source" th:field="*{source}" name="source"/>
                            </div>

                            <span th:if="${availableAuthenticationHandlerNames.size() == 1}">
                                <input type="hidden" id="source" name="source"
                                       th:value="${availableAuthenticationHandlerNames.get(0)}"/>
                            </span>
                        </div>
                    </section>

                    <section class="cas-field form-group my-3">
                        <div th:each="entry: ${customLoginFormFields}">
                            <label class="mdc-text-field mdc-text-field--outlined control-label">
                                <input class="mdc-text-field__input form-control"
                                       th:id="${entry.key + '-customField'}" th:name="${entry.key + '-customField'}"
                                       size="25" type="text" th:field="*{customFields[__${entry.key}__]}"
                                       autocomplete="off"/>
                                <span class="mdc-notched-outline">
                                    <span class="mdc-notched-outline__leading"></span>
                                    <span class="mdc-notched-outline__notch">
                                        <span class="mdc-floating-label"
                                              th:text="#{${entry.value.messageBundleKey}}">Label</span>
                                    </span>
                                    <span class="mdc-notched-outline__trailing"></span>
                                </span>
                            </label>
                        </div>
                    </section>

                    <section class="cas-field form-check"
                             th:if="${'true' == #strings.defaultString(#themes.code('cas.warn-on-redirect.enabled'), 'true')}">
                        <div class="mdc-form-field ">
                            <div class="mdc-checkbox">
                                <input type="checkbox"
                                       class="mdc-checkbox__native-control form-check-input"
                                       name="warn"
                                       id="warn"/>
                                <div class="mdc-checkbox__background">
                                    <svg class="mdc-checkbox__checkmark"
                                         viewBox="0 0 24 24">
                                        <path class="mdc-checkbox__checkmark-path"
                                              fill="none"
                                              d="M1.73,12.91 8.1,19.28 22.79,4.59"/>
                                    </svg>
                                    <div class="mdc-checkbox__mixedmark"></div>
                                </div>
                                <div class="mdc-checkbox__ripple"></div>
                            </div>
                            <label class="form-check-label" for="warn"
                                   th:utext="#{screen.welcome.label.warn}">Warn Me</label>
                        </div>
                        <p/>
                    </section>

                    <section class="cas-field form-check"
                             th:if="${'true' == #strings.defaultString(#themes.code('cas.public-workstation.enabled'), 'true')}">
                        <div class="mdc-form-field ">
                            <div class="mdc-checkbox">
                                <input type="checkbox"
                                       class="mdc-checkbox__native-control form-check-input"
                                       name="publicWorkstation"
                                       id="publicWorkstation"/>
                                <div class="mdc-checkbox__background">
                                    <svg class="mdc-checkbox__checkmark"
                                         viewBox="0 0 24 24">
                                        <path class="mdc-checkbox__checkmark-path"
                                              fill="none"
                                              d="M1.73,12.91 8.1,19.28 22.79,4.59"/>
                                    </svg>
                                    <div class="mdc-checkbox__mixedmark"></div>
                                </div>
                                <div class="mdc-checkbox__ripple"></div>
                            </div>
                            <label class="form-check-label" for="publicWorkstation"
                                   th:text="#{screen.welcome.label.publicstation}">Public Workstation</label>
                        </div>
                        <p/>
                    </section>

                    <section class="cas-field form-check" th:if="${rememberMeAuthenticationEnabled}">
                        <div class="mdc-form-field ">
                            <div class="mdc-checkbox">
                                <input type="checkbox"
                                       class="mdc-checkbox__native-control form-check-input"
                                       name="rememberMe"
                                       id="rememberMe"/>
                                <div class="mdc-checkbox__background">
                                    <svg class="mdc-checkbox__checkmark"
                                         viewBox="0 0 24 24">
                                        <path class="mdc-checkbox__checkmark-path"
                                              fill="none"
                                              d="M1.73,12.91 8.1,19.28 22.79,4.59"/>
                                    </svg>
                                    <div class="mdc-checkbox__mixedmark"></div>
                                </div>
                                <div class="mdc-checkbox__ripple"></div>
                            </div>
                            <label class="form-check-label" for="rememberMe"
                                   th:text="#{screen.rememberme.checkbox.title}">Remember Me</label>
                        </div>
                        <p/>
                    </section>

                    <section class="cas-field">

                        <span th:if="${recaptchaLoginEnabled}">
                            <div th:replace="~{fragments/recaptcha :: recaptchaToken}"/>
                        </span>

                        <input type="hidden" name="execution" th:value="${flowExecutionKey}"/>
                        <input type="hidden" name="_eventId" value="submit"/>
                        <input type="hidden" name="geolocation"/>

                        <p th:if="${#strings.equalsIgnoreCase(httpRequestMethod, 'POST')}">
                            <span th:each="entry : ${httpRequestInitialPostParameters}" th:remove="tag">
                                <span th:each="entryValue : ${entry.value}" th:remove="tag">
                                    <input type="hidden" th:name="${entry.key}" th:value="${entryValue}"/>
                                </span>
                            </span>
                        </p>
                    </section>

                    <div th:replace="~{fragments/submitbutton :: submitButton (messageKey='screen.welcome.button.login')}"/>
                </div>
            </form>

            <div id="selectIdentityProvider"
                 th:if="${#bools.isTrue(delegatedAuthenticationDynamicProviderSelection) and loginFormViewable and loginFormEnabled}">
                <p>
                <form method="post" id="providerDiscoveryForm">
                    <input type="hidden" name="execution" th:value="${flowExecutionKey}"/>
                    <input type="hidden" name="_eventId" value="discovery"/>
                    <span class="fa fa-unlock"></span>
                    <button th:id="selectProviderButton"
                            class="mdc-button mdc-button--raised"
                            onclick="$('#providerDiscoveryForm').submit();"
                            th:value="#{screen.pac4j.button.selectprovider}">
                        <span class="mdc-button__label" th:text="#{screen.pac4j.button.selectprovider}">Select</span>
                    </button>
                </form>
            </div>

            <div id="x509Login" th:if="${x509ClientAuthLoginEndpointUrl}">
                <span th:if="${loginFormViewable and loginFormEnabled}">
                    <hr class="my-4"/>
                    <script th:inline="javascript">
                        /*<![CDATA[*/
                        function x509login() {
                            let url =  /*[[${x509ClientAuthLoginEndpointUrl}]]*/;
                            url += window.location.search;
                            window.location.assign(url)
                        }

                        /*]]>*/
                    </script>
                    <a id="x509LoginLink" class="mdc-button mdc-button--raised btn btn-primary"
                       onclick="javascript:x509login();"
                       th:text="#{screen.welcome.button.loginx509}">X509 Login</a>
                </span>
            </div>

            <hr th:if="${loginFormViewable and loginFormEnabled}" class="my-4"/>

            <span id="webauthnLoginPanel" th:if="${webAuthnPrimaryAuthenticationEnabled}">
                <script type="text/javascript">
                    $('#webauthnLoginPanel').show();
                </script>

                <div th:replace="~{fragments/webAuthnLogin :: webAuthnLogin}"/>
                <hr class="my-4"/>
            </span>


            <div th:if="${loginFormViewable and loginFormEnabled}">
                <span th:remove="tag"
                      th:if="${'true' == #strings.defaultString(#themes.code('cas.pm-links.enabled'), 'true')}">
                    <div th:replace="~{fragments/pmlinks :: pmlinks}"/>
                </span>
            </div>

            <script type="text/javascript" th:inline="javascript">
                /*<![CDATA[*/
                var i = /*[[@{#{screen.welcome.button.loginwip}}]]*/
                var j = /*[[@{#{screen.welcome.button.login}}]]*/
                    /*]]>*/
                    $(window).on('pageshow', function () {
                        $(':submit').prop('disabled', false);
                        $(':submit').attr('value', j);
                    });
                $(document).ready(function () {
                    $("#fm1").submit(function () {
                        $(":submit").attr("disabled", true);
                        $(":submit").attr("value", i);
                        return true;
                    });
                });

            </script>
        </div>

        <div th:if="${loginFormViewable and loginFormEnabled}">
            <div th:replace="~{fragments/loginsidebar :: loginsidebar}"/>
        </div>
    </div>
</main>
</body>

</html>
© www.soinside.com 2019 - 2024. All rights reserved.