Compare commits

..

12 Commits

Author SHA1 Message Date
TonCherAmi 982b3d0cd4
Merge pull request #1 from TouchInstinct/feature/touchinstinct.styles
add touchinstinct styles
2020-07-10 14:06:11 +03:00
Vasili Karaev aa4090d540 adjust styles 2020-07-09 20:17:36 +03:00
Vasili Karaev 526e6266c6 add touchinstinct styles 2020-07-09 19:47:10 +03:00
Vasili Karaev 27ba862dde add oauth2 token expiration date fix 2020-06-05 17:53:36 +03:00
Vasili Karaev 78e6d09bce fix cas version 2020-06-05 17:52:36 +03:00
Vasili Karaev 75f7f05f82 fix upstream conflicts 2020-04-30 19:38:38 +03:00
Vasili Karaev 624c905af8 add module dependencies 2020-04-30 19:37:46 +03:00
Misagh Moayyed 2fc996f8c5
adjust logs and search 2020-04-30 13:13:26 +04:30
Misagh Moayyed 607c7b3a01
update tasks 2020-04-30 13:07:20 +04:30
Misagh Moayyed f941ad4359
update jib 2020-04-30 12:52:11 +04:30
Misagh Moayyed f8f1ca5297
update boot 2020-03-26 17:49:38 +04:30
Vasili Karaev 3b7c40b74f cas: fix version 2020-03-19 19:31:09 +03:00
11 changed files with 1419 additions and 13 deletions

View File

@ -20,7 +20,7 @@ buildscript {
dependencies {
classpath "de.undercouch:gradle-download-task:${project.gradleDownloadTaskVersion}"
classpath "org.springframework.boot:spring-boot-gradle-plugin:${project.springBootVersion}"
classpath "gradle.plugin.com.google.cloud.tools:jib-gradle-plugin:${project.jibVersion}"
classpath "com.google.cloud.tools:jib-gradle-plugin:${project.jibVersion}"
classpath "io.freefair.gradle:maven-plugin:${project.gradleMavenPluginVersion}"
classpath "io.freefair.gradle:lombok-plugin:${project.gradleLombokPluginVersion}"
}
@ -70,8 +70,21 @@ apply from: rootProject.file("gradle/springboot.gradle")
apply from: rootProject.file("gradle/dockerjib.gradle")
dependencies {
// Other CAS dependencies/modules may be listed here...
// implementation "org.apereo.cas:cas-server-support-json-service-registry:${casServerVersion}"
// Module dependencies
compile "org.apereo.cas:cas-server-support-ldap:${project.'cas.version'}"
compile "org.apereo.cas:cas-server-support-reports:${project.'cas.version'}"
compile "org.apereo.cas:cas-server-support-yaml-service-registry:${project.'cas.version'}"
compile "org.apereo.cas:cas-server-support-oauth-webflow:${project.'cas.version'}"
compile "org.apereo.cas:cas-server-support-redis-ticket-registry:${project.'cas.version'}"
// Api dependencies
compile "org.apereo.cas:cas-server-core-util-api:${project.'cas.version'}"
compile "org.apereo.cas:cas-server-core-api-services:${project.'cas.version'}"
compile "org.apereo.cas:cas-server-core-services-api:${project.'cas.version'}"
compile "org.apereo.cas:cas-server-core-authentication-api:${project.'cas.version'}"
compile "org.apereo.cas:cas-server-support-oauth-api:${project.'cas.version'}"
compile "org.apereo.cas:cas-server-support-oauth-core-api:${project.'cas.version'}"
compile "org.apereo.cas:cas-server-support-oauth-services:${project.'cas.version'}"
}
tasks.findByName("jibDockerBuild")
@ -108,4 +121,4 @@ idea {
downloadJavadoc = true
downloadSources = true
}
}
}

View File

@ -1,5 +1,5 @@
# Versions
cas.version=6.2.0-SNAPSHOT
cas.version=6.2.0-RC2
springBootVersion=2.2.5.RELEASE
# Use -jetty, -undertow to other containers
@ -7,13 +7,13 @@ springBootVersion=2.2.5.RELEASE
appServer=-tomcat
executable=false
tomcatVersion=9.0.33
tomcatVersion=9.0.34
group=org.apereo.cas
sourceCompatibility=11
targetCompatibility=11
jibVersion=2.1.0
jibVersion=2.2.0
# Location of the downloaded CAS shell JAR
shellDir=build/libs

View File

@ -33,7 +33,9 @@ project.ext."tomcatDirectory" = tomcatDirectory
def explodedDir = "${buildDir}/cas"
def explodedResourcesDir = "${buildDir}/cas-resources"
def resourceJarName = "cas-server-webapp-resources"
def resourcesJarName = "cas-server-webapp-resources"
def templateViewsJarName = "cas-server-support-thymeleaf"
task copyCasConfiguration(type: Copy, group: "build", description: "Copy the CAS configuration from this project to /etc/cas/config") {
from "etc/cas/config"
@ -47,12 +49,22 @@ task explodeWarOnly(type: Copy, group: "build", description: "Explodes the CAS w
dependsOn 'build'
from zipTree("build/libs/${casWebApplicationBinaryName}")
into explodedDir
doLast {
println "Exploded WAR into ${explodedDir}"
}
}
task explodeWar(type: Copy, group: "build", description: "Explodes the CAS archive and resources jar from the CAS web application archive") {
dependsOn explodeWarOnly
from zipTree("${explodedDir}/WEB-INF/lib/${resourceJarName}-${casServerVersion}.jar")
from zipTree("${explodedDir}/WEB-INF/lib/${templateViewsJarName}-${casServerVersion}.jar")
into explodedResourcesDir
from zipTree("${explodedDir}/WEB-INF/lib/${resourcesJarName}-${casServerVersion}.jar")
into explodedResourcesDir
doLast {
println "Exploded WAR resources into ${explodedResourcesDir}"
}
}
task run(group: "build", description: "Run the CAS web application in embedded container mode") {
@ -222,9 +234,11 @@ task listTemplateViews(group: "build", description: "List all CAS views") {
fileTree(explodedResourcesDir).matching {
include "**/*.html"
}
.collect { it.name }
.toSorted()
.each { println it }
.collect {
return it.path.replace(explodedResourcesDir, "")
}
.toSorted()
.each { println it }
}
}
@ -300,7 +314,11 @@ task getResource(group: "build", description: "Fetch a CAS resource and move it
return
}
if (results.size() > 1) {
println "Multiple resources found matching ${resourceName}: ${results}"
println "Multiple resources found matching ${resourceName}:\n"
results.each {
println "\t-" + it.path.replace(explodedResourcesDir, "")
}
println "\nNarrow down your search criteria and try again."
return
}

View File

@ -0,0 +1,282 @@
package org.apereo.cas.support.oauth.web.response.accesstoken;
import org.apereo.cas.authentication.DefaultAuthenticationBuilder;
import org.apereo.cas.configuration.CasConfigurationProperties;
import org.apereo.cas.configuration.support.Beans;
import org.apereo.cas.support.oauth.OAuth20Constants;
import org.apereo.cas.support.oauth.OAuth20ResponseTypes;
import org.apereo.cas.support.oauth.validator.token.device.InvalidOAuth20DeviceTokenException;
import org.apereo.cas.support.oauth.validator.token.device.ThrottledOAuth20DeviceUserCodeApprovalException;
import org.apereo.cas.support.oauth.validator.token.device.UnapprovedOAuth20DeviceUserCodeException;
import org.apereo.cas.support.oauth.web.response.accesstoken.ext.AccessTokenRequestDataHolder;
import org.apereo.cas.ticket.Ticket;
import org.apereo.cas.ticket.TicketGrantingTicket;
import org.apereo.cas.ticket.TicketState;
import org.apereo.cas.ticket.accesstoken.OAuth20AccessToken;
import org.apereo.cas.ticket.accesstoken.OAuth20AccessTokenFactory;
import org.apereo.cas.ticket.code.OAuth20Code;
import org.apereo.cas.ticket.device.OAuth20DeviceToken;
import org.apereo.cas.ticket.device.OAuth20DeviceTokenFactory;
import org.apereo.cas.ticket.device.OAuth20DeviceUserCode;
import org.apereo.cas.ticket.refreshtoken.OAuth20RefreshToken;
import org.apereo.cas.ticket.refreshtoken.OAuth20RefreshTokenFactory;
import org.apereo.cas.ticket.registry.TicketRegistry;
import org.apereo.cas.util.function.FunctionUtils;
import lombok.RequiredArgsConstructor;
import lombok.extern.slf4j.Slf4j;
import lombok.val;
import org.apache.commons.lang3.StringUtils;
import org.apache.commons.lang3.tuple.Pair;
import org.springframework.transaction.annotation.Transactional;
import java.time.ZoneOffset;
import java.time.ZonedDateTime;
import java.util.LinkedHashSet;
/**
* This is {@link OAuth20DefaultTokenGenerator}.
*
* @author Misagh Moayyed
* @since 5.2.0
*/
@Transactional(transactionManager = "ticketTransactionManager")
@Slf4j
@RequiredArgsConstructor
public class OAuth20DefaultTokenGenerator implements OAuth20TokenGenerator {
/**
* The Access token factory.
*/
protected final OAuth20AccessTokenFactory accessTokenFactory;
/**
* The device token factory.
*/
protected final OAuth20DeviceTokenFactory deviceTokenFactory;
/**
* The refresh token factory.
*/
protected final OAuth20RefreshTokenFactory refreshTokenFactory;
/**
* The Ticket registry.
*/
protected final TicketRegistry ticketRegistry;
/**
* CAS configuration settings.
*/
protected final CasConfigurationProperties casProperties;
@Override
public OAuth20TokenGeneratedResult generate(final AccessTokenRequestDataHolder holder) {
if (OAuth20ResponseTypes.DEVICE_CODE.equals(holder.getResponseType())) {
return generateAccessTokenOAuthDeviceCodeResponseType(holder);
}
val pair = generateAccessTokenOAuthGrantTypes(holder);
return generateAccessTokenResult(holder, pair);
}
/**
* Generate access token OAuth device code response type OAuth token generated result.
*
* @param holder the holder
* @return the OAuth token generated result
*/
protected OAuth20TokenGeneratedResult generateAccessTokenOAuthDeviceCodeResponseType(final AccessTokenRequestDataHolder holder) {
val deviceCode = holder.getDeviceCode();
if (StringUtils.isNotBlank(deviceCode)) {
val deviceCodeTicket = getDeviceTokenFromTicketRegistry(deviceCode);
val deviceUserCode = getDeviceUserCodeFromRegistry(deviceCodeTicket);
if (deviceUserCode.isUserCodeApproved()) {
this.ticketRegistry.deleteTicket(deviceCode);
val deviceResult = AccessTokenRequestDataHolder.builder()
.service(holder.getService())
.authentication(holder.getAuthentication())
.registeredService(holder.getRegisteredService())
.ticketGrantingTicket(holder.getTicketGrantingTicket())
.grantType(holder.getGrantType())
.scopes(new LinkedHashSet<>(0))
.responseType(holder.getResponseType())
.generateRefreshToken(holder.getRegisteredService() != null && holder.isGenerateRefreshToken())
.build();
val ticketPair = generateAccessTokenOAuthGrantTypes(deviceResult);
return generateAccessTokenResult(deviceResult, ticketPair);
}
if (deviceCodeTicket.getLastTimeUsed() != null) {
val interval = Beans.newDuration(casProperties.getAuthn().getOauth().getDeviceToken().getRefreshInterval()).getSeconds();
val shouldSlowDown = deviceCodeTicket.getLastTimeUsed().plusSeconds(interval).isAfter(ZonedDateTime.now(ZoneOffset.UTC));
if (shouldSlowDown) {
throw new ThrottledOAuth20DeviceUserCodeApprovalException(deviceCodeTicket.getId());
}
}
deviceCodeTicket.update();
this.ticketRegistry.updateTicket(deviceCodeTicket);
throw new UnapprovedOAuth20DeviceUserCodeException(deviceCodeTicket.getId());
}
val deviceTokens = createDeviceTokensInTicketRegistry(holder);
return OAuth20TokenGeneratedResult.builder()
.responseType(holder.getResponseType())
.registeredService(holder.getRegisteredService())
.deviceCode(deviceTokens.getLeft().getId())
.userCode(deviceTokens.getValue().getId())
.build();
}
private OAuth20DeviceUserCode getDeviceUserCodeFromRegistry(final OAuth20DeviceToken deviceCodeTicket) {
val userCode = this.ticketRegistry.getTicket(deviceCodeTicket.getUserCode(), OAuth20DeviceUserCode.class);
if (userCode == null) {
throw new InvalidOAuth20DeviceTokenException(deviceCodeTicket.getUserCode());
}
if (userCode.isExpired()) {
this.ticketRegistry.deleteTicket(userCode.getId());
throw new InvalidOAuth20DeviceTokenException(deviceCodeTicket.getUserCode());
}
return userCode;
}
private OAuth20DeviceToken getDeviceTokenFromTicketRegistry(final String deviceCode) {
val deviceCodeTicket = this.ticketRegistry.getTicket(deviceCode, OAuth20DeviceToken.class);
if (deviceCodeTicket == null) {
throw new InvalidOAuth20DeviceTokenException(deviceCode);
}
if (deviceCodeTicket.isExpired()) {
this.ticketRegistry.deleteTicket(deviceCode);
throw new InvalidOAuth20DeviceTokenException(deviceCode);
}
return deviceCodeTicket;
}
private Pair<OAuth20DeviceToken, OAuth20DeviceUserCode> createDeviceTokensInTicketRegistry(final AccessTokenRequestDataHolder holder) {
val deviceToken = deviceTokenFactory.createDeviceCode(holder.getService());
val deviceUserCode = deviceTokenFactory.createDeviceUserCode(deviceToken);
addTicketToRegistry(deviceToken);
addTicketToRegistry(deviceUserCode);
return Pair.of(deviceToken, deviceUserCode);
}
/**
* Generate access token OAuth grant types pair.
*
* @param holder the holder
* @return the pair
*/
protected Pair<OAuth20AccessToken, OAuth20RefreshToken> generateAccessTokenOAuthGrantTypes(final AccessTokenRequestDataHolder holder) {
val clientId = holder.getRegisteredService().getClientId();
val authn = DefaultAuthenticationBuilder
.newInstance(holder.getAuthentication())
.setAuthenticationDate(ZonedDateTime.now(ZoneOffset.UTC))
.addAttribute(OAuth20Constants.GRANT_TYPE, holder.getGrantType().toString())
.addAttribute(OAuth20Constants.SCOPE, holder.getScopes())
.addAttribute(OAuth20Constants.CLIENT_ID, clientId)
.addAttribute(OAuth20Constants.CLAIMS, holder.getClaims())
.build();
val ticketGrantingTicket = holder.getTicketGrantingTicket();
val accessToken = this.accessTokenFactory.create(holder.getService(),
authn, ticketGrantingTicket, holder.getScopes(),
clientId, holder.getClaims());
addTicketToRegistry(accessToken, ticketGrantingTicket);
updateOAuthCode(holder);
val refreshToken = FunctionUtils.doIf(holder.isGenerateRefreshToken(),
() -> generateRefreshToken(holder),
() -> {
return null;
}).get();
return Pair.of(accessToken, refreshToken);
}
/**
* Update OAuth code.
*
* @param holder the holder
*/
protected void updateOAuthCode(final AccessTokenRequestDataHolder holder) {
if (holder.getToken() instanceof OAuth20Code) {
val codeState = TicketState.class.cast(holder.getToken());
codeState.update();
if (holder.getToken().isExpired()) {
this.ticketRegistry.deleteTicket(holder.getToken().getId());
} else {
this.ticketRegistry.updateTicket(holder.getToken());
}
this.ticketRegistry.updateTicket(holder.getTicketGrantingTicket());
}
}
/**
* Add ticket to registry.
*
* @param ticket the ticket
* @param ticketGrantingTicket the ticket granting ticket
*/
protected void addTicketToRegistry(final Ticket ticket, final TicketGrantingTicket ticketGrantingTicket) {
this.ticketRegistry.addTicket(ticket);
if (ticketGrantingTicket != null) {
this.ticketRegistry.updateTicket(ticketGrantingTicket);
}
}
/**
* Add ticket to registry.
*
* @param ticket the ticket
*/
protected void addTicketToRegistry(final Ticket ticket) {
addTicketToRegistry(ticket, null);
}
/**
* Generate refresh token.
*
* @param responseHolder the response holder
* @return the refresh token
*/
protected OAuth20RefreshToken generateRefreshToken(final AccessTokenRequestDataHolder responseHolder) {
val refreshToken = this.refreshTokenFactory.create(responseHolder.getService(),
responseHolder.getAuthentication(),
responseHolder.getTicketGrantingTicket(),
responseHolder.getScopes(),
responseHolder.getClientId(),
responseHolder.getClaims());
addTicketToRegistry(refreshToken, responseHolder.getTicketGrantingTicket());
if (responseHolder.isExpireOldRefreshToken()) {
expireOldRefreshToken(responseHolder);
}
return refreshToken;
}
private void expireOldRefreshToken(final AccessTokenRequestDataHolder responseHolder) {
val oldRefreshToken = responseHolder.getToken();
oldRefreshToken.markTicketExpired();
ticketRegistry.deleteTicket(oldRefreshToken);
}
private static OAuth20TokenGeneratedResult generateAccessTokenResult(final AccessTokenRequestDataHolder holder,
final Pair<OAuth20AccessToken, OAuth20RefreshToken> pair) {
return OAuth20TokenGeneratedResult.builder()
.registeredService(holder.getRegisteredService())
.accessToken(pair.getKey())
.refreshToken(pair.getValue())
.grantType(holder.getGrantType())
.responseType(holder.getResponseType())
.build();
}
}

View File

@ -0,0 +1,461 @@
screen.welcome.welcome=Congratulations on bringing CAS online! To learn how to authenticate, please review the default authentication handler configuration.
screen.welcome.security=For security reasons, please <a href="logout">log out</a> and exit your web browser when you are done accessing \
services that require authentication!
screen.welcome.instructions=Enter Username & Password
screen.welcome.forcedsso=Welcome back, <code><strong>{0}</strong></code>. We have detected an existing single sign-on session for you. However, \
you are being asked to re-authenticate again. Please enter your Username and Password and proceed.
screen.welcome.label.source=Source:
screen.welcome.label.netid=Username
screen.welcome.label.netid.accesskey=u
screen.welcome.label.password=Password
screen.welcome.label.password.accesskey=p
screen.welcome.label.publicstation=I am at a public workstation.
screen.welcome.label.warn=<span class="accesskey">W</span>arn me!
screen.welcome.label.warn.accesskey=w
screen.welcome.label.warnremove=Do not warn me again
screen.welcome.button.login=LOGIN
screen.welcome.button.logout=LOGOUT
screen.welcome.button.loginwip=One moment please...
screen.welcome.button.register=Register
screen.welcome.button.print=Print
screen.welcome.button.clear=CLEAR
screen.welcome.label.loginwith=External Identity Providers
screen.welcome.label.navto=Navigating to authentication provider. Please wait...
screen.pm.button.submit=SUBMIT
screen.pm.button.cancel=CANCEL
screen.pm.button.forgotpwd=<a href="{0}">Forgot your password? </a>
screen.pm.button.resetPassword=Reset your password
screen.pm.button.forgotUsername=Forgot your username?
screen.pm.reset.username=Username:
screen.pm.reset.email=Email:
screen.pm.reset.heading=Password Reset Failed
screen.pm.reset.message=We were unable to process your password reset request at this time.
screen.pm.reset.qstitle=Answer Security Questions
screen.pm.reset.qsmsg=Welcome <strong>{0}</strong>. Before you can reset your password, you must answer the following security questions.
screen.pm.reset.sentInstructions=You should shortly receive an email with follow-instructions to reset your password. Please do not take \
long as the password reset instructions may expire.
screen.pm.reset.sent=Password Reset Instructions Sent Successfully.
screen.pm.reset.title=Reset your password
screen.pm.reset.instructions=Please provide your username. You will receive an email with follow-up instructions on how to reset your password.
screen.pm.password.policyViolation=Password does not match the password policy requirement.
screen.pm.password.confirmMismatch=Passwords do not match.
screen.pm.password.strength=Strength:
screen.pm.password.strength.0=Worst
screen.pm.password.strength.1=Bad
screen.pm.password.strength.2=Weak
screen.pm.password.strength.3=Good
screen.pm.password.strength.4=Strong
screen.pm.reset.contact.failed=Unable to send email/SMS as no email/SMS server is defined in the CAS configuration.
screen.pm.reset.username.required=No email is provided.
screen.pm.reset.contact.invalid=Provided contact information is missing or invalid.
screen.pm.reset.email.invalid=Provided email address is invalid.
screen.pm.reset.username.failed=Failed to send the username to the given email address.
screen.pm.forgotusername.title=Forgot your username?
screen.pm.forgotusername.instructions=Please provide your email address. You will receive an email with your username.
screen.pm.forgotusername.email.failed=Unable to send email as no email server is defined in the CAS configuration.
screen.pm.forgotusername.email.required=No email is provided.
screen.pm.forgotusername.contact.invalid=Provided email address or phone number is invalid.
screen.pm.forgotusername.username.missing=No username could be located for the given email address.
screen.pm.forgotusername.username.failed=Failed to send the username to the given email address.
screen.pm.forgotusername.sent=Instructions Sent Successfully.
screen.pm.forgotusername.sentInstructions=You should shortly receive an message with follow-instructions to how to retrieve your username.
screen.aup.heading=Acceptable Usage Policy
screen.aup.button.accept=ACCEPT
screen.aup.button.cancel=CANCEL
screen.saml.idp.discovery=SAML Identity Provider Discovery
screen.consent.confirm=CONFIRM
screen.consent.cancel=CANCEL
screen.consent.title=Attribute Consent
screen.consent.attributes=Attributes
screen.consent.options=Options
screen.consent.attributes.header=The following attributes will be released to <strong>[{0}]</strong>:
screen.consent.attributes.attribute=Attribute
screen.consent.attributes.values=Value(s)
screen.consent.attributes.data.info=Showing _START_ to _END_ of _TOTAL_ entries
screen.consent.options.header=How should I be prompted for consent again?
screen.consent.options.always=<strong>Every Time</strong>
screen.consent.options.desc.always=Show the consent screen every time I attempt to log into {0}.
screen.consent.options.attributename=<strong>Attribute Name</strong>
screen.consent.options.desc.attributename=Show the consent screen, if an attribute is added or removed from the collection of attributes released to {0}.
screen.consent.options.attributevalue=<strong>Attribute Value</strong>
screen.consent.options.desc.attributevalue.intro=Show the consent screen, if:
screen.consent.options.desc.attributevalue.first=A new attribute is authorized for release to {0}.
screen.consent.options.desc.attributevalue.second=An attribute is removed from the attribute bundle previously released to {0}.
screen.consent.options.desc.attributevalue.third=The value of an attribute authorized for release to {0} has changed.
screen.consent.options.reminder.header=How often should I be reminded to consent again?
screen.consent.options.reminder.expl=Show the consent screen, as a reminder, in the event that there is no change to the collection of attributes released to {0}.
screen.consent.options.timeunit.seconds=Seconds
screen.consent.options.timeunit.minutes=Minutes
screen.consent.options.timeunit.hours=Hours
screen.consent.options.timeunit.days=Days
screen.consent.options.timeunit.weeks=Weeks
screen.consent.options.timeunit.months=Months
screen.consent.options.timeunit.years=Years
screen.consent.review.header=Review Attribute Consent
screen.consent.review.loading=Loading consent decisions...
screen.consent.review.noconsentdecisions=There are no consent decisions registered for you.
screen.consent.review.success=Consent decision was deleted successfully.
screen.consent.review.error=There was an error!
screen.consent.review.confirm=Delete consent decision for [{}]?
screen.consent.review.yes=Yes
screen.consent.review.no=No
screen.consent.review.date=Date
screen.consent.review.service=Service
screen.consent.review.delete=DELETE
screen.consent.review.createddate=Created Date:
screen.consent.review.reminder=Reminder:
screen.consent.review.option=Option:
screen.consent.review.options.attributename=Attribute Name
screen.consent.review.options.attributevalue=Attribute Value
screen.consent.review.options.always=Always
screen.consent.review.options.desc.always=Show the consent screen every time I attempt to log in.
screen.consent.review.options.desc.attributename=Show the consent screen, if an attribute is added or removed from the collection of attributes released.
screen.consent.review.options.desc.attributevalue=Show the consent screen, if 1) a new attribute is authorized for release, 2) an attribute is removed from the attribute bundle previously released, 3) the value of an attribute authorized for release has changed.
screen.consent.review.attributes=Attributes:
screen.consent.review.data.search=Search
screen.consent.review.data.zerorecords=No matching decisions found
screen.consent.review.data.info=Showing _START_ to _END_ of _TOTAL_ entries
screen.consent.review.data.infofiltered=(filtered from _MAX_ total entries)
screen.consent.review.data.infoempty=No decisions to show
screen.consent.review.logout.success=You have successfully logged out of the Consent Review page. You may completely <a href="../logout">log out</a> of the Central Authentication Service and end your single sign-on session.
screen.nonsecure.title=Non-secure Connection
screen.nonsecure.message=You are currently accessing CAS over a non-secure connection. Single Sign On WILL NOT WORK. In order to have single sign on work, you MUST log in over HTTPS.
screen.defaultauthn.title=Static Authentication
screen.defaultauthn.heading=CAS is configured to accept a static list of users for primary authentication. Please be advised that this is ONLY useful for \
demo purposes. It is recommended that you connect CAS to LDAP, JDBC, etc instead.
logo.title=go to Apereo home page
copyright=Copyright &copy; 2005&ndash;2019 Apereo, Inc.
screen.capslock.on = CAPSLOCK key is turned on!
screen.button.continue=Continue
screen.post.response.message=You are being redirected to {0}.
screen.interrupt.title=Authentication Interrupt
screen.interrupt.message=The authentication flow has been interrupted. CAS has not yet established a single sign-on session for <strong>{0}</strong>.
screen.mdui.infolink.text=<a href="{0}" target="_blank">More information about this application</a>.
screen.mdui.privacylink.text=<a href="{0}" target="_blank">Privacy statement for application</a>.
screen.interrupt.btn.proceed=Proceed
screen.interrupt.btn.cancel=Cancel
# Generic Error Pages 401, 404, 500, etc
########################################
screen.error.page.heading=Error
screen.error.page.title.accessdenied=Error - 401
screen.error.page.title.permissiondenied=Error - Permission Denied
screen.error.page.title.pagenotfound=Error - Page Not Found
screen.error.page.title.requestunsupported=Error - Unsupported Request
screen.error.page.accessdenied=Access Denied
screen.error.page.permissiondenied=You do not have permission to view this page.
screen.error.page.requestunsupported=The request type or syntax is not supported.
screen.error.page.loginagain=Login Again
screen.error.page.notfound=Page Not Found
screen.error.page.doesnotexist=The page you are attempting to access does not exist at the moment.
screen.error.page.authdenied=Authorization Denied
# Remember-Me Authentication
screen.rememberme.checkbox.title=Remember Me
# Gua
screen.gua.confirm.message=If you do not recognize this image as yours, do NOT continue.
# Blocked Errors Page
screen.error.page.title.blocked=Error - Permission Denied
screen.blocked.header=Access Denied
screen.blocked.message=You've entered the wrong password for the user too many times. You've been throttled.
AbstractAccessDecisionManager.accessDenied=You are not authorized to access this resource. Contact your CAS administrator for more info.
# Confirmation Screen Messages
screen.confirmation.message=You asked to be warned before logging into applications. Please proceed.
screen.authentication.warning=Authentication Succeeded with Warnings
# Generic Success Screen Messages
screen.success.header=Log In Successful
screen.success.success=You, <strong>{0}</strong>, have successfully logged into the Central Authentication Service. However, you are seeing \
this page because CAS does not know about your target destination and how to get you there. Examine the authentication request again and \
make sure a target service/application that is authorized and registered with CAS is specified.
screen.success.security=When you are finished, for security reasons, please <a href="logout">log out</a> and exit your web browser.
# Logout Screen Messages
screen.logout.confirm.header=Do you want to log out completely?
screen.logout.confirm.text=<p>An application may have redirected you to the Central Authentication Service \
to completely log you out and destroy your single sign-on session. If you choose to log out, you will be asked again \
to provide your credentials and re-autheticate once you attempt to access an application.</p><p>Do you want to proceed?</p>
screen.logout.header=Logout successful
screen.logout.success=You have successfully logged out of the Central Authentication Service. You may <a href="login">log in</a> again.
screen.logout.fc.success=You have successfully logged out of the Central Authentication Service. Given single logout is enabled with CAS, \
the following list of applications are <strong> only notified</strong> to log you out and destroy your user session. Remember that this \
is just a notification, not a guarantee. It is up the application itself to honor these notifications and properly take action to log you \
out.
screen.logout.security=For security reasons, exit your web browser.
screen.service.sso.error.header=Re-Authentication Required to Access this Service
screen.service.sso.error.message=You attempted to access a service that requires authentication without re-authenticating. Please try authenticating again</a>.
screen.service.required.message=You attempted authentication without specifying the target application. Please re-examine the request and try again.
screen.service.initial.message=Attempting to access CAS or the indicated target application is disallowed at this time. \
The authentication policy requires that you change your starting application \
and then move onto other applications and services.
captchaError=reCAPTCHA validation failed.
username.required=Username is a required field.
password.required=Password is a required field.
source.required=Authentication source is a required field.
# Password Management
confirmedPassword.required=Password must be confirmed.
pm.passwordsMustMatch=Provided passwords do not match.
pm.passwordFailedCriteria=Provided password does not satisfy the password security policy. Please try again.
pm.updateFailure=Account password could not be modified. Please try again.
# Authentication failure messages
authenticationFailure.AccountDisabledException=This account has been disabled.
authenticationFailure.AccountLockedException=This account has been locked.
authenticationFailure.AccountExpiredException=This account has expired and is forbidden to login at this time.
authenticationFailure.CredentialExpiredException=Your password has expired.
authenticationFailure.InvalidLoginLocationException=You cannot login from this workstation.
authenticationFailure.InvalidLoginTimeException=Your account is forbidden to login at this time.
authenticationFailure.AccountNotFoundException=Your account is not recognized and cannot login at this time.
authenticationFailure.FailedLoginException=Authentication attempt has failed, likely due to invalid credentials. Please verify and try again.
authenticationFailure.MultifactorAuthenticationProviderAbsentException=Unable to satisfy multifactor authentication requirements. \
Your account is configured for a multifactor authentication strategy, yet CAS is unable to locate and execute that strategy \
most likely due to misconfiguration of the server. Contact the service administrators for assistance.
authenticationFailure.SurrogateAuthenticationException=You are not authorized to impersonate the indicated user at this time.
authenticationFailure.AccountPasswordMustChangeException=Your account password has expired and must be changed.
authenticationFailure.UnauthorizedServiceForPrincipalException=Service access denied due to missing privileges.
authenticationFailure.UNKNOWN=Authentication attempt has failed.
authenticationFailure.AuthenticationException=Credentials are rejected/invalid and authentication attempt has failed.
INVALID_REQUEST_PROXY=The request is incorrectly formatted. Ensure all required parameters are properly encoded and included.
INVALID_TICKET_SPEC=Ticket failed validation specification. Possible errors could include attempting to validate a Proxy Ticket via a Service Ticket validator, or not complying with the renew true request.
INVALID_REQUEST=Unable to identify, authorize or complete this request, likely due to malformed or missing required parameters.
INVALID_AUTHENTICATION_CONTEXT=The validation request for [''{0}''] cannot be satisfied. The request is either unrecognized or unfulfilled.
INVALID_TICKET=Ticket ''{0}'' not recognized
INVALID_PROXY_GRANTING_TICKET=PGT already generated for this ST. Cannot grant more than one PGT for ST
INVALID_SERVICE=Ticket ''{0}'' does not match supplied service. The original service was ''{1}'' and the supplied service was ''{2}''.
INVALID_PROXY_CALLBACK=The supplied proxy callback url ''{0}'' could not be authenticated. Either ''{0}'' cannot be reached, it is not \
allowed to exercise proxy authentication.
UNAUTHORIZED_SERVICE_PROXY=The supplied service ''{0}'' is not authorized to use CAS proxy authentication.
UNSATISFIED_AUTHN_POLICY=Service access denied due to an unsatisfied authentication policy.
INVALID_AUTHN_REQUEST=Authentication attempt has failed, likely due to invalid credentials.
screen.service.error.header=Application Not Authorized to Use CAS
service.principal.resolution.error=CAS is unable to determine the correct authentication principal. \
Either the principal could not be resolved correctly as a single unique entity or CAS has found \
mixed/multiple candidate principals and is unable to decide which should be used. \
This error may also be caused if the authenticated principal is not allowed to access the target application \
due to missing privileges set by the CAS server authorization policies.
service.not.authorized.missing.attr=You are not authorized to access the application as your account \
is missing privileges required by the CAS server to authenticate into this service. Please notify your support desk.
screen.service.error.message=The application you attempted to authenticate to is not authorized to use CAS. \
This usually indicates that the application is not registered with CAS, or its authorization policy defined in its registration record \
prevents it from leveraging CAS functionality, or it's malformed and unrecognized by CAS. \
Contact your CAS administrator to learn how you might register and integrate your application with CAS.
screen.service.empty.error.message=The services registry of CAS is empty and has no service definitions. \
Applications that wish to authenticate with CAS must explicitly be defined in the services registry.
screen.service.expired.message=The application you attempted to authenticate to has been expired in the CAS Service Registry. \
If this service should still be considered in use, please contact the service administrators to have the application renewed.
# Surrogate Account Selection
screen.surrogates.account.selection.header=Surrogate Account Selection
screen.surrogates.choose.account=Choose Account
screen.surrogates.message=<p>You are provided with a list of accounts on behalf of which you are allowed to authenticate.</p> \
<p>Select one and continue.</p>
screen.surrogates.button.cancel=Cancel
screen.surrogates.account.selection.error=You are not authorized to impersonate the indicated user at this time.
# Password policy
password.expiration.warning=Your password expires in {0} day(s). Please <a href="https://pm.example.edu">change your password</a> now.
password.expiration.loginsRemaining=You have {0} login(s) remaining before you <strong>MUST</strong> change your password.
screen.accountdisabled.heading=This account has been disabled.
screen.accountdisabled.message=Please contact the system administrator to regain access.
screen.accountlocked.heading=This account has been locked.
screen.accountlocked.message=Please contact the system administrator to regain access.
screen.expiredpass.heading=Your password has expired.
screen.expiredpass.message=Please <a href="{0}">change your password</a>.
screen.mustchangepass.heading=You must change your password.
screen.mustchangepass.message=Please <a href="{0}">change your password</a>.
screen.badhours.heading=Your account is forbidden to login at this time.
screen.badhours.message=Please try again later.
screen.authnblocked.heading=Authentication attempt is blocked.
screen.authnblocked.message=Your authentication attempt is untrusted and unauthorized from your current workstation.
screen.risk.authnblocked.heading=Authentication attempt is blocked.
screen.risk.authnblocked.message=Your authentication attempt is untrusted and unauthorized from your current workstation.
screen.badworkstation.heading=You cannot login from this workstation.
screen.badworkstation.message=Please contact the system administrator to regain access.
screen.button.changePassword=Change Password
screen.pm.success.header=Password Change Successful
screen.pm.success.message=Your account password is successfully updated.
screen.pm.confirmpsw=Confirm Password:
screen.pm.enterpsw=Enter Password:
screen.pac4j.unauthz.pagetitle=Unauthorized Access
screen.pac4j.unauthz.gotoapp=Goto Application
screen.pac4j.unauthz.login=Back to CAS
screen.pac4j.unauthz.heading=Unauthorized Access
screen.pac4j.unauthz.message=Either the authentication request was rejected/cancelled, or the authentication provider denied access due \
to permissions, etc. Review logs to find the root cause of the issue.
screen.delauthn.error.header=Delegated Authentication Failure
screen.delauthn.error.message=CAS is unable to complete the delegated authentication scenario, \
or redirect to the selected identity provider. Please examine the original authentication request and try again. \
You may need to close your browser and start again.
# GAuth
screen.authentication.gauth.register=Your account is not registered. Use the below settings to register your device with CAS.
screen.authentication.gauth.key=Secret key to register is {0}
# OAuth
screen.oauth.confirm.header=Authorization
screen.oauth.confirm.message=Do you want to grant access to "{0}" ?
screen.oauth.confirm.allow=Allow
screen.oauth.confirm.deny=Deny
cas.oauth.confirm.pagetitle=Approve Access
cas.oauth.device.confirm.header=Connect Device
cas.oauth.device.confirm.message=Enter the code displayed on your device to proceed.
cas.oauth.device.confirmed.header=Code Approved
cas.oauth.device.confirmed.message=Return to your device to continue.
cas.oauth.error.pagetitle=OAuth Error
cas.oauth.error.header=OAuth Authorization Error
OAUTH_BAD_SESSION_REQUEST=The OAuth request cannot be completed, as CAS is unable to locate or determine OAuth redirect URL. \
This is usually an indication of a stale or mismatched request where the processed request session id is different from the \
active session and may be caused by an complete logout operation. Clear cookies and history, restart your browser and try again please.
# OIDC
screen.oidc.confirm.infourl=Learn more about {0}.
screen.oidc.confirm.privacyurl=Learn about {0} privacy rules.
screen.oidc.confirm.scope.profile=This requests access to the profile claims excluding the address and email claims.
screen.oidc.confirm.scope.email=This requests access to the email claims.
screen.oidc.confirm.scope.address=This requests access to the address claims.
screen.oidc.confirm.scope.openid=This indicates an OpenID Connect authorization request.
screen.oidc.confirm.scope.phone=This requests access to the phone claims.
screen.oidc.confirm.scope.offline_access=This requests access for a refresh token used for offline access.
screen.oidc.confirm.claim.name=End-User's full name in displayable form including all name parts, possibly including titles and suffixes, ordered according to the End-User's locale and preferences.
screen.oidc.confirm.claim.given_name=Given name(s) or first name(s) of the End-User. Note that in some cultures, people can have multiple given names; all can be present, with the names being separated by space characters.
screen.oidc.confirm.claim.middle_name=Middle name(s) of the End-User. Note that in some cultures, people can have multiple middle names; all can be present, with the names being separated by space characters. Also note that in some cultures, middle names are not used.
screen.oidc.confirm.claim.family_name=Surname(s) or last name(s) of the End-User. Note that in some cultures, people can have multiple family names or no family name; all can be present, with the names being separated by space characters.
screen.oidc.confirm.claim.email=End-User's preferred e-mail address.
screen.oidc.confirm.claim.preferred_username=MAY be any valid JSON string including special characters such as @, /, or whitespace. The RP MUST NOT rely upon this value being unique.
screen.oidc.confirm.claim.profile=URL of the End-User's profile page. The contents of this Web page SHOULD be about the End-User.
screen.oidc.confirm.claim.picture=URL of the End-User's profile picture. This URL MUST refer to an image file (for example, a PNG, JPEG, or GIF image file), rather than to a Web page containing an image. Note that this URL SHOULD specifically reference a profile photo of the End-User suitable for displaying when describing the End-User, rather than an arbitrary photo taken by the End-User.
screen.oidc.confirm.claim.phone_number=End-User's preferred telephone number. It is RECOMMENDED as the format of this claim. \
For example, <code>+1 (425) 555-1212</code> or <code>+56 (2) 687 2400</code>.
screen.oidc.confirm.asksinfo=The client is asking for the following information:
screen.oidc.confirm.dynamic=This client was dynamically registered at <code>{0}</code>.
# Unavailable
screen.unavailable.header=CAS error
screen.unavailable.heading=CAS is unable to process this request: "{0}:{1}"
screen.unavailable.message=There was an error trying to complete your request. \
<strong>Please notify your support desk or try again.</strong> \
<div>Apereo is a non-profit open source software governance foundation. The CAS software is an Apereo sponsored project \
and is freely downloadable and usable by anyone. However, Apereo does not operate the systems of anyone using the \
software and in most cases doesn't even know who is using it or how to contact them unless they are an active part \
of the Apereo community.<br/></br>If you are having problems logging in using CAS, \
<strong>you will need to contact the IT staff or Help Desk of your organization for assistance</strong>. \
<br/><br/>We wish we could be more directly helpful to you.</div>
screen.mfaDenied.header=MFA Denied
screen.mfaDenied.heading=MFA attempt has been denied by provider
screen.mfaDenied.message=Your MFA provider has denied your attempt at second factor \
authentication. Contact your system administrator for help in restoring your account.
screen.mfaUnavailable.header=MFA Provider Unavailable
screen.mfaUnavailable.heading=MFA Provider Unavailable
screen.mfaUnavailable.message=CAS was unable to reach your configured MFA provider at this time. \
Due to failure policies configured for the service you are attempting to access, authentication can not \
be granted at this time.
#####################################################################
# Login View
#####################################################################
#Resources Labels
cas.login.pagetitle=Login
cas.login.resources.header=Resources
cas.login.resources.wiki=Documentation
cas.login.resources.endpoints=Actuator Endpoints
cas.login.resources.pulls=Pull Requests
cas.login.resources.mailinglist=Mailing Lists
cas.login.resources.chat=Chatroom
cas.login.resources.blog=Blog
cas.login.resources.support=Support
cas.login.resources.contribguide=Contributor Guidelines
####
# Acceptable Usage Policy View
#
cas.acceptableusagepolicyview.pagetitle=Acceptable Usage Policy View
##
# MFA
##
cas.mfa.providerselection.pagetitle=Multifactor Provider Selection
cas.mfa.providerselection.mfa-duo=Duo Security
cas.mfa.providerselection.mfa-duo.notes=Duo's wide variety of authentication methods enable every user to \
securely and quickly log in. Duo Push, sent by our Duo Mobile authentication app, allows users to approve \
push notifications to verify their identity.
cas.mfa.providerselection.mfa-gauth=Google Authenticator
cas.mfa.providerselection.mfa-gauth.notes=Google Authenticator is a software-based authenticator that \
implements two-step verification services for authenticating users of mobile applications by Google.
cas.mfa.duologin.pagetitle=Duo Security Login
cas.mfa.simple.pagetitle=CAS Multifactor Authentication Login
cas.mfa.simple.label.token=Token:
cas.mfa.simple.label.resend=Resend
cas.mfa.simple.label.tokensent=A multifactor authentication token is sent to you via an email or text message. \
Please locate the token and submit it here to continue. Note that the token will expire after a short period of time \
and will no longer be recognized by CAS, in which case, you may ask CAS to send you a new token.
cas.mfa.googleauth.pagetitle=Google Authenticator
cas.mfa.googleauth.label.token=Token:
cas.mfa.radius.pagetitle=Radius Authentication
cas.mfa.yubikey.pagetitle=YubiKey Authentication
cas.mfa.yubikey.authenticate=Use your registered YubiKey device to authenticate.
cas.mfa.yubikey.register=Your device is not yet registered. Use the below form to register your device with CAS.
cas.mfa.yubikey.label.token=Token:
cas.mfa.u2f.pagetitle=U2F Authentication
cas.mfa.u2f.authentication.device=Authentication Device
cas.mfa.u2f.authentication.message=<p><strong>Please touch the flashing U2F device now.</strong></p><p> You may be prompted to allow \
the site permission to access your security keys. After granting permission, the device will start to blink.</p>
cas.mfa.u2f.register.device=Register Device
cas.mfa.u2f.register.message=<p><strong>Please touch the flashing U2F device now.</strong></p><p> You may be prompted to allow \
the site permission to access your security keys. After granting permission, the device will start to blink.</p>
cas.mfa.authy.pagetitle=Authy Login
cas.mfa.swivel.pagetitle=Swivel Authentication
cas.mfa.swivel.label.token=Token:
cas.mfa.swivel.label.header=Swivel Authentication
cas.mfa.registerdevice.label.title=Register Device
cas.mfa.registerdevice.label.intro=Please name the current device.
cas.mfa.registerdevice.pagetitle=Register Device
cas.mfa.registerdevice.label.name=Name
cas.mfa.registerdevice.button.register=Register
cas.mfa.registerdevice.button.skip=Skip
passwordless.error.unknown.user=Provided username cannot be recognized and located by CAS.
passwordless.error.invalid.user=Provided username does not carry enough contact information.

View File

@ -0,0 +1,88 @@
#Welcome Screen Messages
screen.welcome.welcome=\u041F\u043E\u0437\u0434\u0440\u0430\u0432\u043B\u044F\u0435\u043C \u0441 \u0443\u0441\u043F\u0435\u0448\u043D\u044B\u043C \u0437\u0430\u043F\u0443\u0441\u043A\u043E\u043C \u0441\u0438\u0441\u0442\u0435\u043C\u044B CAS! "Authentication handler", \u0443\u0441\u0442\u0430\u043D\u043E\u0432\u043B\u0435\u043D\u043D\u044B\u0439 \u043F\u043E \u0443\u043C\u043E\u043B\u0447\u0430\u043D\u0438\u044E, \u043F\u0440\u043E\u0438\u0437\u0432\u043E\u0434\u0438\u0442 \u0443\u0441\u0442\u0430\u043D\u043E\u0432\u043B\u0435\u043D\u0438\u0435 \u043F\u043E\u0434\u043B\u0438\u043D\u043D\u043E\u0441\u0442\u0438 \u0432 \u0442\u043E\u043C \u0441\u043B\u0443\u0447\u0430\u0435 \u0435\u0441\u043B\u0438 \u0438\u043C\u044F \u043F\u043E\u043B\u044C\u0437\u043E\u0432\u0430\u0442\u0435\u043B\u044F \u0438 \u043F\u0430\u0440\u043E\u043B\u044C \u0441\u043E\u0432\u043F\u0430\u0434\u0430\u044E\u0442: \u043F\u043E\u043F\u0440\u043E\u0431\u0443\u0439\u0442\u0435 \u0441\u0438\u0441\u0442\u0435\u043C\u0443 CAS \u0432 \u0434\u0435\u0439\u0441\u0442\u0432\u0438\u0438.
screen.welcome.security=\u0412 \u0446\u0435\u043B\u044F\u0445 \u043D\u0430\u0434\u0435\u0436\u043D\u043E\u0433\u043E \u0443\u0440\u043E\u0432\u043D\u044F \u0431\u0435\u0437\u043E\u043F\u0430\u0441\u043D\u043E\u0441\u0442\u0438, \u043F\u043E\u0436\u0430\u043B\u0443\u0439\u0441\u0442\u0430, \u0432\u044B\u0439\u0434\u0438\u0442\u0435 \u0438\u0437 \u0441\u0438\u0441\u0442\u0435\u043C\u044B, \u0430 \u0442\u0430\u043A\u0436\u0435 \u0437\u0430\u043A\u0440\u043E\u0439\u0442\u0435 \u0431\u0440\u0430\u0443\u0437\u0435\u0440, \u0437\u0430\u043A\u043E\u043D\u0447\u0438\u0432 \u0434\u043E\u0441\u0442\u0443\u043F \u043A \u0441\u0435\u0440\u0432\u0438\u0441\u0443 \u043A\u043E\u0442\u043E\u0440\u044B\u0439 \u043D\u0443\u0436\u0434\u0430\u0435\u0442\u0441\u044F \u0432 \u0443\u0441\u0442\u0430\u043D\u043E\u0432\u043B\u0435\u043D\u0438\u0438 \u043F\u043E\u0434\u043B\u0438\u043D\u043D\u043E\u0441\u0442\u0438!
screen.welcome.instructions=\u0412\u0432\u0435\u0434\u0438\u0442\u0435 \u043B\u043E\u0433\u0438\u043D \u0438 \u043F\u0430\u0440\u043E\u043B\u044C
screen.welcome.label.netid=Логин
screen.welcome.label.netid.accesskey=\u043B
screen.welcome.label.password=Пароль
screen.welcome.label.password.accesskey=\u043F
screen.welcome.label.warn=<span class="accesskey">\u041F</span>\u0440\u0435\u0434\u0443\u043F\u0440\u0435\u0434\u0438\u0442\u044C \u043F\u0435\u0440\u0435\u0434 \u0432\u0445\u043E\u0434\u043E\u043C \u043D\u0430 \u0434\u0440\u0443\u0433\u0438\u0435 \u0441\u0430\u0439\u0442\u044B.
screen.welcome.label.warn.accesskey=\u0440
screen.welcome.button.login=\u0412\u041E\u0419\u0422\u0418
screen.welcome.button.clear=\u041E\u0427\u0418\u0421\u0422\u0418\u0422\u042C
logo.title=\u043F\u0435\u0440\u0435\u0439\u0442\u0438 \u043D\u0430 \u0434\u043E\u043C\u0430\u0448\u043D\u044E\u044E \u0441\u0442\u0440\u0430\u043D\u0438\u0446\u0443 Apereo
copyright=Copyright &copy; 2005&ndash;2015 Apereo, Inc. \u0412\u0441\u0435 \u043F\u0440\u0430\u0432\u0430 \u0437\u0430\u0449\u0438\u0449\u0435\u043D\u044B.
# Blocked Errors Page
screen.blocked.header=\u0421\u0435\u0440\u0432\u0438\u0441 \u043D\u0435 \u0438\u043C\u0435\u0435\u0442 \u043F\u0440\u0430\u0432\u0430 \u0434\u043E\u0441\u0442\u0443\u043F\u0430.
screen.blocked.message=\u0412\u044B \u0432\u0432\u0435\u043B\u0438 \u043D\u0435 \u043F\u0440\u0430\u0432\u0438\u043B\u044C\u043D\u044B\u0435 \u043B\u043E\u0433\u0438\u043D \u0438\u043B\u0438 \u043F\u0430\u0440\u043E\u043B\u044C \u0441\u043B\u0438\u0448\u043A\u043E\u043C \u043C\u043D\u043E\u0433\u043E \u0440\u0430\u0437. \u0414\u043E\u0441\u0442\u0443\u043F \u043A \u0441\u0435\u0440\u0432\u0438\u0441\u0443 \u043F\u0435\u0440\u0435\u043A\u0440\u044B\u0442.
#Confirmation Screen Messages
screen.confirmation.message=\u041D\u0430\u0436\u043C\u0438\u0442\u0435 <a href="{0}">\u0441\u044E\u0434\u0430</a> \u0434\u043B\u044F \u043F\u0435\u0440\u0435\u0445\u043E\u0434\u0430 \u0432 \u043F\u0440\u0438\u043B\u043E\u0436\u0435\u043D\u0438\u0435.
#Generic Success Screen Messages
screen.success.header=\u0412\u0445\u043E\u0434 \u0432 \u0441\u0438\u0441\u0442\u0435\u043C\u0443 \u0443\u0441\u043F\u0435\u0448\u0435\u043D.
screen.success.success=\u0412\u044B \u0443\u0441\u043F\u0435\u0448\u043D\u043E \u0432\u043E\u0448\u043B\u0438 \u0432 \u0441\u0438\u0441\u0442\u0435\u043C\u0443 Central Authentication Service.
screen.success.security=\u0412 \u0446\u0435\u043B\u044F\u0445 \u043D\u0430\u0434\u0435\u0436\u043D\u043E\u0433\u043E \u0443\u0440\u043E\u0432\u043D\u044F \u0431\u0435\u0437\u043E\u043F\u0430\u0441\u043D\u043E\u0441\u0442\u0438, \u043F\u043E\u0436\u0430\u043B\u0443\u0439\u0441\u0442\u0430, \u0432\u044B\u0439\u0434\u0438\u0442\u0435 \u0438\u0437 \u0441\u0438\u0441\u0442\u0435\u043C\u044B, \u0430 \u0442\u0430\u043A\u0436\u0435 \u0437\u0430\u043A\u0440\u043E\u0439\u0442\u0435 \u0431\u0440\u0430\u0443\u0437\u0435\u0440, \u0437\u0430\u043A\u043E\u043D\u0447\u0438\u0432 \u0434\u043E\u0441\u0442\u0443\u043F \u043A \u0441\u0435\u0440\u0432\u0438\u0441\u0443 \u043A\u043E\u0442\u043E\u0440\u044B\u0439 \u043D\u0443\u0436\u0434\u0430\u0435\u0442\u0441\u044F \u0432 \u0443\u0441\u0442\u0430\u043D\u043E\u0432\u043B\u0435\u043D\u0438\u0438 \u043F\u043E\u0434\u043B\u0438\u043D\u043D\u043E\u0441\u0442\u0438!
#Logout Screen Messages
screen.logout.header=\u0412\u044B\u0445\u043E\u0434 \u0438\u0437 \u0441\u0438\u0441\u0442\u0435\u043C\u044B \u0443\u0441\u043F\u0435\u0448\u0435\u043D.
screen.logout.success=\u0412\u044B \u0443\u0441\u043F\u0435\u0448\u043D\u043E \u0432\u044B\u0448\u043B\u0438 \u0438\u0437 \u0441\u0438\u0441\u0442\u0435\u043C\u044B Central Authentication Service.
screen.logout.security=\u0412 \u0446\u0435\u043B\u044F\u0445 \u043D\u0430\u0434\u0435\u0436\u043D\u043E\u0433\u043E \u0443\u0440\u043E\u0432\u043D\u044F \u0431\u0435\u0437\u043E\u043F\u0430\u0441\u043D\u043E\u0441\u0442\u0438, \u0437\u0430\u043A\u0440\u043E\u0439\u0442\u0435 \u0431\u0440\u0430\u0443\u0437\u0435\u0440.
screen.service.sso.error.header=\u041F\u0435\u0440\u0435\u0443\u0441\u0442\u0430\u043D\u043E\u0432\u043B\u0435\u043D\u0438\u0435 \u043F\u043E\u0434\u043B\u0438\u043D\u043D\u043E\u0441\u0442\u0438 \u043D\u0435\u043E\u0431\u0445\u043E\u0434\u0438\u043C\u043E \u0434\u043B\u044F \u0434\u043E\u0441\u0442\u0443\u043F\u0430 \u043A \u0441\u0435\u0440\u0432\u0438\u0441\u0443.
screen.service.sso.error.message=\u0412\u044B \u043F\u043E\u043F\u044B\u0442\u0430\u043B\u0438\u0441\u044C \u043F\u043E\u043B\u0443\u0447\u0438\u0442\u044C \u0434\u043E\u0441\u0442\u0443\u043F \u043A \u0441\u0435\u0440\u0432\u0438\u0441\u0443 \u043A\u043E\u0442\u043E\u0440\u043E\u043C\u0443 \u043D\u0435\u043E\u0431\u0445\u043E\u0434\u0438\u043C\u043E \u043F\u0435\u0440\u0435\u0443\u0441\u0442\u0430\u043D\u043E\u0432\u043B\u0435\u043D\u0438\u0435 \u043F\u043E\u0434\u043B\u0438\u043D\u043D\u043E\u0441\u0442\u0438. \u041F\u043E\u0436\u0430\u043B\u0443\u0439\u0441\u0442\u0430 <a href="{0}">\u0441\u0434\u0435\u043B\u0430\u0439\u0442\u0435 \u044D\u0442\u043E \u0441\u043D\u043E\u0432\u0430</a>.
username.required=\u0418\u043C\u044F \u043F\u043E\u043B\u044C\u0437\u043E\u0432\u0430\u0442\u0435\u043B\u044F - \u043E\u0431\u044F\u0437\u0430\u0442\u0435\u043B\u044C\u043D\u043E\u0435 \u043F\u043E\u043B\u0435 \u0432\u0432\u043E\u0434\u0430.
password.required=\u041F\u0430\u0440\u043E\u043B\u044C - \u043E\u0431\u044F\u0437\u0430\u0442\u0435\u043B\u044C\u043D\u043E\u0435 \u043F\u043E\u043B\u0435 \u0432\u0432\u043E\u0434\u0430.
# Authentication failure messages
authenticationFailure.AccountDisabledException=\u042D\u0442\u0430 \u0443\u0447\u0451\u0442\u043D\u0430\u044F \u0437\u0430\u043F\u0438\u0441\u044C \u0432\u0440\u0435\u043C\u0435\u043D\u043D\u043E \u043D\u0435\u0434\u0435\u0439\u0441\u0442\u0432\u0443\u044E\u0449\u0430\u044F.
authenticationFailure.AccountLockedException=\u042D\u0442\u0430 \u0443\u0447\u0451\u0442\u043D\u0430\u044F \u0437\u0430\u043F\u0438\u0441\u044C \u0437\u0430\u0431\u043B\u043E\u043A\u0438\u0440\u043E\u0432\u0430\u043D\u0430.
authenticationFailure.CredentialExpiredException=\u0412\u0430\u0448 \u043F\u0430\u0440\u043E\u043B\u044C \u043F\u0440\u043E\u0441\u0440\u043E\u0447\u0435\u043D.
authenticationFailure.InvalidLoginLocationException=\u0412\u0445\u043E\u0434 \u0432 \u0441\u0438\u0441\u0442\u0435\u043C\u0443 \u0438\u0437 \u0434\u0430\u043D\u043D\u043E\u0433\u043E \u043A\u043E\u043C\u043F\u044C\u044E\u0442\u0435\u0440\u0430 \u0437\u0430\u043F\u0440\u0435\u0449\u0451\u043D.
authenticationFailure.InvalidLoginTimeException=\u0412\u0445\u043E\u0434 \u0432 \u0441\u0438\u0441\u0442\u0435\u043C\u0443 \u0432 \u0434\u0430\u043D\u043D\u043E\u0435 \u0432\u0440\u0435\u043C\u044F \u0441\u0443\u0442\u043E\u043A \u0437\u0430\u043F\u0440\u0435\u0449\u0451\u043D.
authenticationFailure.AccountNotFoundException=\u041D\u0435\u0432\u0435\u0440\u043D\u044B\u0435 \u0434\u0430\u043D\u043D\u044B\u0435 \u043E \u043F\u043E\u0434\u043B\u0438\u043D\u043D\u043E\u0441\u0442\u0438.
authenticationFailure.FailedLoginException=\u041D\u0435\u0432\u0435\u0440\u043D\u044B\u0435 \u0434\u0430\u043D\u043D\u044B\u0435 \u043E \u043F\u043E\u0434\u043B\u0438\u043D\u043D\u043E\u0441\u0442\u0438.
authenticationFailure.UNKNOWN=\u041D\u0435\u0432\u0435\u0440\u043D\u044B\u0435 \u0434\u0430\u043D\u043D\u044B\u0435 \u043E \u043F\u043E\u0434\u043B\u0438\u043D\u043D\u043E\u0441\u0442\u0438.
INVALID_REQUEST_PROXY=\u041E\u0431\u0430 \u043F\u0430\u0440\u0430\u043C\u0435\u0442\u0440\u0430 'pgt' \u0438 'targetService' \u043E\u0431\u044F\u0437\u0430\u0442\u0435\u043B\u044C\u043D\u044B.
INVALID_TICKET_SPEC="Ticket" \u043D\u0435 \u043F\u0440\u043E\u0448\u0435\u043B \u0443\u0441\u043F\u0435\u0448\u043D\u0443\u044E \u043F\u0440\u043E\u0432\u0435\u0440\u043A\u0443 \u0434\u0435\u0439\u0441\u0442\u0432\u0438\u0442\u0435\u043B\u044C\u043D\u043E\u0441\u0442\u0438. \u0412\u043E\u0437\u043C\u043E\u0436\u043D\u044B\u0435 \u0438\u0441\u0442\u043E\u0447\u043D\u0438\u043A\u0438 \u043E\u0448\u0438\u0431\u043E\u043A \u043C\u043E\u0433\u0443\u0442 \u0432\u043A\u043B\u044E\u0447\u0430\u0442\u044C \u043F\u043E\u043F\u044B\u0442\u043A\u0443 \u043F\u0440\u043E\u0432\u0435\u0440\u043A\u0438 \u0434\u0435\u0438\u0441\u0442\u0432\u0438\u0442\u0435\u043B\u044C\u043D\u043E\u0441\u0442\u0438 "Proxy Ticket" \u043F\u043E\u0441\u0440\u0435\u0434\u0441\u0442\u0432\u043E\u043C "Service Ticket validator" \u0438\u043B\u0438 \u043D\u0435 \u0441\u043E\u043E\u0442\u0432\u0435\u0442\u0441\u0442\u0432\u0438\u0435 \u0438\u0441\u043F\u043E\u043B\u043D\u0435\u043D\u0438\u044F \u0441 \u0442\u0440\u0435\u0431\u043E\u0432\u0430\u043D\u0438\u0435\u043C "renew request: true".
INVALID_REQUEST=\u041E\u0431\u0430 \u043F\u0430\u0440\u0430\u043C\u0435\u0442\u0440\u0430 'service' \u0438 'ticket' \u043E\u0431\u044F\u0437\u0430\u0442\u0435\u043B\u044C\u043D\u044B.
INVALID_TICKET="Ticket" ''{0}'' \u043D\u0435 \u0440\u0430\u0441\u043F\u043E\u0437\u043D\u0430\u043D.
INVALID_SERVICE="Ticket" ''{0}'' \u043D\u0435 \u0441\u043E\u043E\u0442\u0432\u0435\u0442\u0441\u0442\u0432\u0443\u0435\u0442 \u043F\u0440\u0435\u0434\u043E\u0441\u0442\u0430\u0432\u043B\u0435\u043D\u043D\u043E\u043C\u0443 \u0441\u0435\u0440\u0432\u0438\u0441\u0443. \u0418\u0437\u043D\u0430\u0447\u0430\u043B\u044C\u043D\u044B\u0439 \u0441\u0435\u0440\u0432\u0438\u0441 \u0431\u044B\u043B ''{1}'' , \u0430 \u043F\u0440\u0435\u0434\u043E\u0441\u0442\u0430\u0432\u043B\u0435\u043D\u043D\u044B\u0439 \u0441\u0435\u0440\u0432\u0438\u0441 \u0431\u044B\u043B ''{2}''
INVALID_PROXY_CALLBACK=\u041F\u0440\u0435\u0434\u043E\u0441\u0442\u0430\u0432\u043B\u0435\u043D\u043D\u044B\u0439 proxy callback url ''{0}'' \u043D\u0435 \u043C\u043E\u0436\u0435\u0442 \u043F\u0440\u043E\u0439\u0442\u0438 \u043F\u0440\u043E\u0432\u0435\u0440\u043A\u0443 \u043F\u043E\u0434\u043B\u0438\u043D\u043D\u043E\u0441\u0442\u0438.
UNAUTHORIZED_SERVICE_PROXY=\u041F\u0440\u0435\u0434\u043E\u0441\u0442\u0430\u0432\u043B\u0435\u043D\u043D\u044B\u0439 \u0441\u0435\u0440\u0432\u0438\u0441 ''{0}'' \u043D\u0435 \u0443\u043F\u043E\u043B\u043D\u043E\u043C\u043E\u0447\u0435\u043D \u0438\u0441\u043F\u043E\u043B\u044C\u0437\u043E\u0432\u0430\u0442\u044C CAS proxy authentication.
screen.service.error.header=\u041F\u0440\u0438\u043B\u043E\u0436\u0435\u043D\u0438\u0435 \u043D\u0435 \u0443\u043F\u043E\u043B\u043D\u043E\u043C\u043E\u0447\u0435\u043D\u043E \u0438\u0441\u043F\u043E\u043B\u044C\u0437\u043E\u0432\u0430\u0442\u044C CAS
screen.service.error.message=\u041F\u0440\u0438\u043B\u043E\u0436\u0435\u043D\u0438\u0435, \u043A\u043E\u0442\u043E\u0440\u043E\u0435 \u043F\u044B\u0442\u0430\u043B\u043E\u0441\u044C \u043F\u0440\u043E\u0439\u0442\u0438 \u043F\u0440\u043E\u0432\u0435\u0440\u043A\u0443 \u043F\u043E\u0434\u043B\u0438\u043D\u043D\u043E\u0441\u0442\u0438, \u043D\u0435 \u0443\u043F\u043E\u043B\u043D\u043E\u043C\u043E\u0447\u0435\u043D\u043E \u0438\u0441\u043F\u043E\u043B\u044C\u0437\u043E\u0432\u0430\u0442\u044C CAS.
screen.service.empty.error.message=\u0420\u0435\u0433\u0438\u0441\u0442\u0440 \u0441\u0435\u0440\u0432\u0438\u0441\u043E\u0432 \u043F\u0443\u0441\u0442. \u041F\u0440\u0438\u043B\u043E\u0436\u0435\u043D\u0438\u044F, \u0438\u0441\u043F\u043E\u043B\u044C\u0437\u0443\u044E\u0449\u0438\u0435 CAS, \u0434\u043E\u043B\u0436\u043D\u044B \u0431\u044B\u0442\u044C \u0432\u0432\u0435\u0434\u0435\u043D\u044B \u0432 \u0440\u0435\u0433\u0438\u0441\u0442\u0440 \u0441\u0435\u0440\u0432\u0438\u0441\u043E\u0432.
# Password policy
password.expiration.warning=\u0421\u0440\u043E\u043A \u0433\u043E\u0434\u043D\u043E\u0441\u0442\u0438 \u043F\u0430\u0440\u043E\u043B\u044F \u0438\u0441\u0442\u0435\u043A\u0430\u0435\u0442 \u0447\u0435\u0440\u0435\u0437 {0} \u0434\u0435\u043D\u044C/\u0434\u043D\u0435\u0439. \u041F\u043E\u0436\u0430\u043B\u0443\u0439\u0441\u0442\u0430 <a href="{1}">\u0438\u0437\u043C\u0435\u043D\u0438\u0442\u0435 \u0441\u0432\u043E\u0439 \u043F\u0430\u0440\u043E\u043B\u044C</a> \u0441\u0435\u0439\u0447\u0430\u0441.
password.expiration.loginsRemaining=\u0423 \u0432\u0430\u0441 \u043E\u0441\u0442\u0430\u043B\u043E\u0441\u044C {0} \u0432\u0445\u043E\u0434/\u0432\u0445\u043E\u0434\u043E\u0432 \u0432 \u0441\u0438\u0441\u0442\u0435\u043C\u0443 \u043F\u0435\u0440\u0435\u0434 \u0442\u0435\u043C \u043A\u0430\u043A \u0432\u044B \u0431\u0443\u0434\u0435\u0442\u0435 <strong>\u041E\u0411\u042F\u0417\u0410\u041D\u042B</strong> \u043F\u043E\u043C\u0435\u043D\u044F\u0442\u044C \u043F\u0430\u0440\u043E\u043B\u044C.
screen.accountdisabled.heading=\u042D\u0442\u0430 \u0443\u0447\u0451\u0442\u043D\u0430\u044F \u0437\u0430\u043F\u0438\u0441\u044C \u0432\u0440\u0435\u043C\u0435\u043D\u043D\u043E \u043D\u0435\u0434\u0435\u0439\u0441\u0442\u0432\u0443\u044E\u0449\u0430\u044F.
screen.accountdisabled.message=\u041F\u043E\u0436\u0430\u043B\u0443\u0439\u0441\u0442\u0430 \u0441\u0432\u044F\u0436\u0438\u0442\u0435\u0441\u044C \u0441 \u0441\u0438\u0441\u0442\u0435\u043C\u043D\u044B\u043C \u0430\u0434\u043C\u0438\u043D\u0438\u0441\u0442\u0440\u0430\u0442\u043E\u0440\u043E\u043C \u0434\u043B\u044F \u043F\u043E\u043B\u0443\u0447\u0435\u043D\u0438\u044F \u0434\u043E\u0441\u0442\u0443\u043F\u0430 \u0432 \u0441\u0438\u0441\u0442\u0435\u043C\u0443.
screen.accountlocked.heading=\u042D\u0442\u0430 \u0443\u0447\u0451\u0442\u043D\u0430\u044F \u0437\u0430\u043F\u0438\u0441\u044C \u0437\u0430\u0431\u043B\u043E\u043A\u0438\u0440\u043E\u0432\u0430\u043D\u0430.
screen.accountlocked.message=\u041F\u043E\u0436\u0430\u043B\u0443\u0439\u0441\u0442\u0430 \u0441\u0432\u044F\u0436\u0438\u0442\u0435\u0441\u044C \u0441 \u0441\u0438\u0441\u0442\u0435\u043C\u043D\u044B\u043C \u0430\u0434\u043C\u0438\u043D\u0438\u0441\u0442\u0440\u0430\u0442\u043E\u0440\u043E\u043C \u0434\u043B\u044F \u043F\u043E\u043B\u0443\u0447\u0435\u043D\u0438\u044F \u0434\u043E\u0441\u0442\u0443\u043F\u0430 \u0432 \u0441\u0438\u0441\u0442\u0435\u043C\u0443.
screen.expiredpass.heading=\u0421\u0440\u043E\u043A \u0433\u043E\u0434\u043D\u043E\u0441\u0442\u0438 \u0432\u0430\u0448\u0435\u0433\u043E \u043F\u0430\u0440\u043E\u043B\u044F \u043F\u0440\u043E\u0441\u0440\u043E\u0447\u0435\u043D.
screen.expiredpass.message=\u041F\u043E\u0436\u0430\u043B\u0443\u0439\u0441\u0442\u0430 <a href="{0}">\u043F\u043E\u043C\u0435\u043D\u044F\u0439\u0442\u0435 \u0432\u0430\u0448 \u043F\u0430\u0440\u043E\u043B\u044C</a>.
screen.mustchangepass.heading=\u0412\u0430\u043C \u043D\u0435\u043E\u0431\u0445\u043E\u0434\u0438\u043C\u043E \u043F\u043E\u043C\u0435\u043D\u044F\u0442\u044C \u0432\u0430\u0448 \u043F\u0430\u0440\u043E\u043B\u044C.
screen.mustchangepass.message=\u041F\u043E\u0436\u0430\u043B\u0443\u0439\u0441\u0442\u0430 <a href="{0}">\u043F\u043E\u043C\u0435\u043D\u044F\u0439\u0442\u0435 \u0432\u0430\u0448 \u043F\u0430\u0440\u043E\u043B\u044C</a>.
screen.badhours.heading=\u0412\u0430\u0448\u0435\u0439 \u0443\u0447\u0435\u0442\u043D\u043E\u0439 \u0437\u0430\u043F\u0438\u0441\u0438 \u0437\u0430\u043F\u0440\u0435\u0449\u0451\u043D \u0432\u0445\u043E\u0434 \u0432 \u0441\u0438\u0441\u0442\u0435\u043C\u0443 \u0432 \u0434\u0430\u043D\u043D\u043E\u0435 \u0432\u0440\u0435\u043C\u044F \u0441\u0443\u0442\u043E\u043A.
screen.badhours.message=\u041F\u043E\u0436\u0430\u043B\u0443\u0439\u0441\u0442\u0430 \u043F\u043E\u043F\u0440\u043E\u0431\u0443\u0439\u0442\u0435 \u0432\u043E\u0439\u0442\u0438 \u0432 \u0441\u0438\u0441\u0442\u0435\u043C\u0443 \u043F\u043E\u0437\u0436\u0435.
screen.badworkstation.heading=\u0412\u044B \u043D\u0435 \u043C\u043E\u0436\u0435\u0442\u0435 \u0432\u043E\u0439\u0442\u0438 \u0432 \u0441\u0438\u0441\u0442\u0435\u043C\u0443 \u0441 \u0434\u0430\u043D\u043D\u043E\u0433\u043E \u043A\u043E\u043C\u043F\u044C\u044E\u0442\u0435\u0440\u0430.
screen.badworkstation.message=\u041F\u043E\u0436\u0430\u043B\u0443\u0439\u0441\u0442\u0430 \u0441\u0432\u044F\u0436\u0438\u0442\u0435\u0441\u044C \u0441 \u0441\u0438\u0441\u0442\u0435\u043C\u043D\u044B\u043C \u0430\u0434\u043C\u0438\u043D\u0438\u0441\u0442\u0440\u0430\u0442\u043E\u0440\u043E\u043C \u0434\u043B\u044F \u043F\u043E\u043B\u0443\u0447\u0435\u043D\u0438\u044F \u0434\u043E\u0441\u0442\u0443\u043F\u0430 \u0432 \u0441\u0438\u0441\u0442\u0435\u043C\u0443.
# OAuth
screen.oauth.confirm.header=\u0410\u0432\u0442\u043E\u0440\u0438\u0437\u0430\u0446\u0438\u044F
screen.oauth.confirm.message=\u0412\u044B \u043D\u0430\u043C\u0435\u0440\u0435\u043D\u044B \u0434\u0430\u0442\u044C \u043F\u043E\u043B\u043D\u044B\u0439 \u0434\u043E\u0441\u0442\u0443\u043F \u043A \u0432\u0430\u0448\u0435\u043C\u0443 \u043F\u0440\u043E\u0444\u0438\u043B\u044E \u0434\u0430\u043D\u043D\u043E\u043C\u0443 \u0441\u0435\u0440\u0432\u0438\u0441\u0443: "{0}" ?
screen.oauth.confirm.allow=\u0420\u0430\u0437\u0440\u0435\u0448\u0438\u0442\u044C \u0434\u043E\u0441\u0442\u0443\u043F
# Unavailable
screen.unavailable.heading=CAS \u043D\u0435 \u0434\u043E\u0441\u0442\u0443\u043F\u0435\u043D
screen.unavailable.message=\u041F\u0440\u043E\u0438\u0437\u043E\u0448\u043B\u0430 \u043E\u0448\u0438\u0431\u043A\u0430 \u0432 \u043F\u0440\u043E\u0446\u0435\u0441\u0441\u0435 \u043E\u0431\u0440\u0430\u0431\u043E\u0442\u043A\u0438 \u0432\u0430\u0448\u0435\u0433\u043E \u0437\u0430\u043F\u0440\u043E\u0441\u0430. \u041F\u043E\u0436\u0430\u043B\u0443\u0439\u0441\u0442\u0430 \u0441\u0432\u044F\u0436\u0438\u0442\u0435\u0441\u044C \u0441 \u0432\u0430\u0448\u0435\u0439 \u0441\u043B\u0443\u0436\u0431\u043E\u0439 \u0442\u0435\u0445\u043D\u0438\u0447\u0435\u0441\u043A\u043E\u0439 \u043F\u043E\u0434\u0434\u0435\u0440\u0436\u043A\u0438 \u0438\u043B\u0438 \u043F\u043E\u043F\u0440\u043E\u0431\u0443\u0439\u0442\u0435 \u0435\u0449\u0451 \u0440\u0430\u0437.

View File

@ -0,0 +1,202 @@
html {
box-sizing: border-box;
}
*,
*::before,
*::after {
box-sizing: inherit;
}
body {
margin: 0;
background-color: #ffffff;
font-family: "Ubuntu", Arial, sans-serif;
font-size: 15px;
line-height: 17px;
}
img {
max-width: 100%;
}
a {
text-decoration: none;
}
button {
cursor: pointer;
}
.hidden {
display: none;
}
.visually-hidden:not(:focus):not(:active) {
position: absolute;
width: 1px;
height: 1px;
margin: -1px;
border: 0;
padding: 0;
white-space: nowrap;
clip-path: inset(100%);
clip: rect(0 0 0 0);
overflow: hidden;
}
#content {
justify-items: center;
}
#loginForm {
margin: auto;
}
.logo {
display: block;
margin: 60px auto;
}
/* form */
.form {
display: flex;
flex-direction: column;
min-height: 60vh;
margin: 0 auto;
padding: 0 9.6vw;
}
@media screen and (min-width: 550px) {
.form {
max-width: 460px;
min-height: 410px;
margin-bottom: 60px;
padding: 60px;
border: 1px solid #e8e8e8;
border-radius: 10px;
background-color: #ffffff;
}
}
.form__title {
margin: 0 0;
font-weight: bold;
font-size: 18px;
line-height: 24px;
text-align: center;
text-transform: uppercase;
}
.form__title:last-of-type {
margin-bottom: 50px;
}
.form__title + .form__title {
margin-top: 16px;
}
.form__title--main {
margin-bottom: 50px;
}
.form__title--light {
color: #9f9f9f;
}
.form__title--no-transform {
text-transform: none;
}
.form__input ~ .form__input {
margin-top: 10px;
}
.form__positioner {
position: relative;
}
.form__show-btn {
position: absolute;
top: -32px;
right: 20px;
width: 15px;
height: 15px;
border: 0;
padding: 0;
background-image: url("../images/icon-show.svg");
background-repeat: no-repeat;
background-color: transparent;
opacity: 0.6;
}
.form__show-btn:hover {
opacity: 1;
}
.form__error-text {
/* opacity: 0; */
margin: 15px 0;
color: #eb515a;
text-align: center;
}
/* input */
.input {
width: 100%;
padding: 15px 19px;
border: 1px solid #e8e8e8;
border-radius: 10px;
font-family: inherit;
font-weight: 500;
font-size: inherit;
line-height: inherit;
color: #383838;
outline: none;
}
.input::placeholder {
font-weight: 400;
color: #9f9f9f;
}
.input--error:not(:focus) {
border-color: #f17980;
color: #9F9F9F;
}
.input--error ~ .form__error-text {
opacity: 1;
}
input[type="password"] {
padding-right: 40px;
}
/* button */
.button {
width: 100%;
margin-top: auto;
padding: 16px 20px;
border: none;
border-radius: 10px;
background-color: #4a7cc8;
font-size: inherit;
line-height: inherit;
color: #ffffff;
text-transform: uppercase;
text-align: center;
outline: none;
}
.button:hover,
.button:active {
background-color: #2859a2;
}
.button:disabled {
background-color: #e8e8e8;
}

Binary file not shown.

After

Width:  |  Height:  |  Size: 31 KiB

View File

@ -0,0 +1,91 @@
<!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>Header Fragment</title>
<link href="../../static/css/cas.css" rel="stylesheet" th:remove="tag"/>
</head>
<body>
<header th:fragment="header" role="banner">
<svg class="logo" width="140" height="55" viewBox="0 0 140 55" fill="none" xmlns="http://www.w3.org/2000/svg">
<path
d="M28.3142 10.3163C25.2658 15.5466 23.5583 21.4549 22.5117 27.3343C21.6691 32.066 21.1612 36.8656 21.0175 41.6649C20.9921 42.5244 20.9713 43.3851 20.9867 44.2449C21.0228 46.2946 22.835 48.2622 25.0622 48.166C27.2392 48.0721 29.1768 46.4422 29.138 44.2449C29.0885 41.467 29.2681 38.673 29.5192 35.9074C29.6389 34.5879 29.7863 33.271 29.9612 31.9576C30.6924 26.9615 31.8246 21.9725 33.7983 17.2874C34.2674 16.2603 34.7816 15.2535 35.3527 14.2744C36.3952 12.4849 35.8599 9.91065 33.8906 8.90963C33.2412 8.5796 32.5217 8.41491 31.8109 8.41491C30.4153 8.41491 29.0517 9.0502 28.3142 10.3163Z"
fill="url(#paint0_linear)" />
<path
d="M16.91 2.29573C12.888 10.1688 11.0119 19.0269 10.3034 27.726C9.75873 34.4141 9.80755 41.179 10.4622 47.8591C10.5802 49.0634 10.6528 50.314 10.9029 51.5026C11.1222 52.5448 11.5178 53.447 12.4072 54.1315C13.1876 54.7324 14.3993 55.1181 15.403 54.9672C17.4259 54.6626 19.4574 52.7902 19.0044 50.6376C18.7957 49.6456 18.7302 48.6044 18.6249 47.5998C18.3494 44.9618 18.1799 42.3132 18.0996 39.663C18.0444 37.8427 18.0341 36.0211 18.0682 34.2002C18.2765 27.1444 19.1545 20.0658 21.1817 13.2703C22.036 10.6008 23.0779 7.99082 24.3591 5.48248C25.3013 3.63836 24.2849 1.06214 22.2908 0.305586C21.7468 0.0990735 21.1938 -1.80801e-06 20.6554 -1.80801e-06C19.0953 -1.80801e-06 17.6576 0.832157 16.91 2.29573Z"
fill="url(#paint1_linear)" />
<path
d="M19.1563 7.43707C17.727 14.8688 17.1375 22.4692 17.8299 30.009C18.2405 34.4798 18.9728 38.9854 20.3614 43.2803C20.5797 43.9555 20.8047 44.6355 21.0896 45.2885C21.5199 46.2756 21.9613 47.0679 22.9623 47.6315C23.836 48.1236 25.1236 48.3317 26.1029 48.0268C27.0893 47.7199 28.0409 47.1319 28.5387 46.2248C29.0129 45.3618 29.3623 44.1501 28.9497 43.2037C27.9988 41.0232 27.431 38.6438 26.9409 36.3375C26.678 35.1013 26.4574 33.8574 26.2718 32.6087C25.4359 26.2066 25.5302 19.7157 26.3718 13.3181C26.5587 12.0481 26.774 10.7827 27.0167 9.52178C27.2197 8.46736 27.1856 7.45348 26.6058 6.50038C26.111 5.68689 25.1417 4.91135 24.17 4.69873C23.8644 4.6315 23.5448 4.59869 23.2211 4.59869C21.4266 4.59869 19.5078 5.61 19.1563 7.43707Z"
fill="url(#paint2_linear)" />
<path
d="M0.0158547 17.3909C-0.18175 19.998 1.4907 22.2397 3.75196 22.3986C6.01289 22.5569 8.00566 20.5719 8.20326 17.9648C8.40053 15.358 6.72774 13.116 4.46682 12.9574C4.38222 12.9513 4.29797 12.9484 4.21438 12.9484C2.05945 12.9487 0.20577 14.8816 0.0158547 17.3909Z"
fill="url(#paint3_linear)" />
<path d="M49.5854 23.6209V25.2253H46.3267V33.8208H44.3838V25.2253H41.125V23.6209H49.5854Z" fill="#4F4F4F" />
<path
d="M55.46 29.9658C55.46 29.2005 55.2892 28.5949 54.9473 28.1482C54.6054 27.7019 54.1291 27.4783 53.5171 27.4783C52.9052 27.4783 52.428 27.7019 52.0865 28.1482C51.7446 28.5949 51.5738 29.2005 51.5738 29.9658C51.5738 30.7415 51.7446 31.3545 52.0865 31.8057C52.428 32.2574 52.9052 32.483 53.5171 32.483C54.1291 32.483 54.6054 32.2574 54.9473 31.8057C55.2892 31.3545 55.46 30.7415 55.46 29.9658ZM57.3571 29.9658C57.3571 30.5743 57.265 31.1289 57.0815 31.6291C56.8979 32.1297 56.6381 32.5567 56.3013 32.9095C55.965 33.2627 55.5593 33.5377 55.0851 33.7341C54.6105 33.9297 54.088 34.0281 53.5171 34.0281C52.9458 34.0281 52.4254 33.9297 51.9564 33.7341C51.4874 33.5377 51.0843 33.2627 50.7479 32.9095C50.4111 32.5567 50.1484 32.1297 49.9601 31.6291C49.7709 31.1289 49.6768 30.5743 49.6768 29.9658C49.6768 29.3573 49.7709 28.8057 49.9601 28.31C50.1484 27.8147 50.4137 27.3902 50.7556 27.037C51.0971 26.6838 51.5024 26.4116 51.9718 26.2202C52.4408 26.0288 52.9557 25.9332 53.5171 25.9332C54.0777 25.9332 54.5955 26.0288 55.0697 26.2202C55.5443 26.4116 55.9496 26.6838 56.2859 27.037C56.6227 27.3902 56.885 27.8147 57.0738 28.31C57.2625 28.8057 57.3571 29.3573 57.3571 29.9658Z"
fill="#4F4F4F" />
<path
d="M65.8327 33.5854C65.4758 33.6736 65.0115 33.7645 64.4406 33.8576C63.8693 33.951 63.2419 33.9976 62.5589 33.9976C61.9161 33.9976 61.3782 33.909 60.9447 33.7328C60.5112 33.5562 60.1646 33.3108 59.9044 32.9967C59.6442 32.6826 59.458 32.3075 59.3459 31.8707C59.2334 31.4343 59.1777 30.9559 59.1777 30.4359V26.123H61.029V30.156C61.029 30.9802 61.1535 31.5689 61.4035 31.9222C61.6534 32.2754 62.0895 32.452 62.7117 32.452C62.9359 32.452 63.173 32.4426 63.4229 32.4224C63.6728 32.403 63.859 32.3788 63.9814 32.3491V26.123H65.8327V33.5854Z"
fill="#4F4F4F" />
<path
d="M67.7451 29.9801C67.7451 29.4111 67.8371 28.8788 68.0207 28.3831C68.2043 27.8878 68.4666 27.4584 68.8086 27.0953C69.1501 26.7326 69.5656 26.4477 70.0552 26.2419C70.5447 26.0356 71.0955 25.9327 71.7074 25.9327C72.4623 25.9327 73.1761 26.0652 73.8493 26.33L73.4517 27.787C73.2373 27.6989 72.9951 27.6252 72.7247 27.5663C72.4546 27.5074 72.1666 27.4778 71.8606 27.4778C71.1361 27.4778 70.5854 27.6964 70.2084 28.1328C69.8309 28.5696 69.6422 29.1855 69.6422 29.9801C69.6422 30.7454 69.8206 31.3515 70.1775 31.7978C70.5345 32.2444 71.1361 32.4676 71.983 32.4676C72.2989 32.4676 72.6104 32.4379 72.9164 32.3791C73.2224 32.3202 73.4873 32.2465 73.7119 32.1584L73.9717 33.6302C73.7676 33.7282 73.4594 33.8167 73.0465 33.8954C72.6331 33.9736 72.2073 34.0127 71.7686 34.0127C71.0852 34.0127 70.4912 33.9122 69.9867 33.7109C69.4817 33.51 69.0632 33.2305 68.732 32.8723C68.4003 32.5141 68.1529 32.0876 67.9899 31.5915C67.8269 31.0962 67.7451 30.5589 67.7451 29.9801Z"
fill="#4F4F4F" />
<path
d="M75.4092 33.8208V22.6938L77.2605 22.3994V26.2118C77.4642 26.143 77.7017 26.0841 77.9717 26.0347C78.2417 25.9857 78.5096 25.9615 78.775 25.9615C79.4177 25.9615 79.9501 26.0475 80.3738 26.2188C80.7966 26.3904 81.1359 26.6309 81.391 26.9401C81.646 27.2493 81.827 27.6198 81.934 28.0512C82.0414 28.4831 82.0949 28.9636 82.0949 29.4938V33.8208H80.2437V29.7734C80.2437 29.3613 80.2154 29.0105 80.1594 28.7207C80.1033 28.4317 80.0117 28.1962 79.8842 28.0146C79.7567 27.833 79.5859 27.7005 79.3715 27.6169C79.1575 27.5337 78.8922 27.4922 78.576 27.4922C78.3312 27.4922 78.0813 27.5169 77.8266 27.5658C77.5716 27.6148 77.3829 27.6589 77.2605 27.698V33.8208H75.4092Z"
fill="#4F4F4F" />
<path d="M87.9697 23.6209H89.8972V33.8208H87.9697V23.6209Z" fill="#4F4F4F" />
<path
d="M92.3447 26.3736C92.7016 26.2756 93.1655 26.1825 93.7368 26.094C94.3077 26.0059 94.9402 25.9615 95.6339 25.9615C96.2865 25.9615 96.8326 26.0475 97.2708 26.2188C97.7094 26.3909 98.0586 26.6313 98.3188 26.9405C98.579 27.2492 98.7626 27.6222 98.87 28.0587C98.977 28.4955 99.0301 28.9739 99.0301 29.4938V33.8208H97.1792V29.7734C97.1792 29.3613 97.151 29.0105 97.0949 28.7211C97.0388 28.4321 96.9468 28.1966 96.8193 28.0146C96.6922 27.833 96.5185 27.7005 96.2994 27.6173C96.0802 27.5341 95.8124 27.4922 95.4961 27.4922C95.2616 27.4922 95.0168 27.507 94.7618 27.5362C94.5067 27.5658 94.3184 27.5901 94.196 27.6099V33.8208H92.3447V26.3736Z"
fill="#4F4F4F" />
<path
d="M103.299 32.5414C103.788 32.5414 104.145 32.485 104.369 32.3721C104.594 32.2593 104.706 32.0654 104.706 31.7908C104.706 31.536 104.586 31.3248 104.347 31.158C104.107 30.9909 103.712 30.8098 103.161 30.6134C102.824 30.4956 102.516 30.3705 102.236 30.2379C101.954 30.1053 101.713 29.9509 101.509 29.7743C101.304 29.5977 101.144 29.3844 101.027 29.1341C100.909 28.8838 100.851 28.5775 100.851 28.2144C100.851 27.5075 101.121 26.9509 101.662 26.5437C102.202 26.1366 102.937 25.9328 103.865 25.9328C104.334 25.9328 104.783 25.9748 105.211 26.0579C105.639 26.1415 105.96 26.2226 106.175 26.3008L105.838 27.743C105.634 27.6549 105.374 27.5738 105.058 27.5005C104.742 27.4268 104.375 27.3902 103.956 27.3902C103.579 27.3902 103.273 27.4515 103.038 27.5738C102.804 27.6969 102.687 27.8855 102.687 28.1407C102.687 28.2683 102.709 28.3811 102.756 28.4791C102.801 28.5775 102.881 28.6681 102.993 28.7513C103.105 28.8348 103.253 28.9184 103.436 29.0016C103.62 29.0851 103.844 29.1708 104.11 29.2593C104.548 29.4161 104.921 29.5705 105.227 29.7229C105.533 29.8752 105.785 30.0465 105.984 30.2379C106.183 30.4293 106.328 30.648 106.42 30.8929C106.512 31.1383 106.557 31.4327 106.557 31.776C106.557 32.5121 106.275 33.0687 105.708 33.4467C105.142 33.8242 104.334 34.0132 103.284 34.0132C102.58 34.0132 102.014 33.9568 101.585 33.844C101.157 33.7312 100.856 33.6406 100.683 33.5714L101.004 32.0852C101.279 32.1931 101.608 32.296 101.99 32.394C102.373 32.4924 102.809 32.5414 103.299 32.5414Z"
fill="#4F4F4F" />
<path
d="M108.194 24.0921L110.046 23.7977V26.123H112.891V27.6096H110.046V30.7447C110.046 31.3627 110.147 31.8044 110.352 32.0696C110.555 32.3343 110.902 32.4669 111.392 32.4669C111.728 32.4669 112.027 32.4327 112.287 32.3635C112.547 32.2952 112.754 32.2314 112.907 32.1725L113.212 33.5854C112.998 33.6736 112.718 33.7645 112.371 33.8576C112.024 33.9506 111.616 33.9976 111.147 33.9976C110.576 33.9976 110.099 33.9239 109.717 33.7765C109.334 33.6295 109.031 33.4162 108.807 33.1363C108.582 32.8567 108.424 32.5183 108.332 32.1206C108.24 31.7237 108.194 31.2696 108.194 30.7591V24.0921Z"
fill="#4F4F4F" />
<path
d="M116.547 33.8208H114.697V26.1233H116.547V33.8208ZM116.746 23.8713C116.746 24.2051 116.634 24.4703 116.41 24.6658C116.185 24.8626 115.92 24.9606 115.614 24.9606C115.298 24.9606 115.027 24.8626 114.804 24.6658C114.579 24.4703 114.467 24.2051 114.467 23.8713C114.467 23.5279 114.579 23.2582 114.804 23.0619C115.027 22.8659 115.298 22.7675 115.614 22.7675C115.92 22.7675 116.185 22.8659 116.41 23.0619C116.634 23.2582 116.746 23.5279 116.746 23.8713Z"
fill="#4F4F4F" />
<path
d="M118.903 26.3736C119.26 26.2756 119.724 26.1825 120.296 26.094C120.867 26.0059 121.499 25.9615 122.192 25.9615C122.846 25.9615 123.391 26.0475 123.829 26.2188C124.268 26.3909 124.617 26.6313 124.877 26.9405C125.138 27.2492 125.321 27.6222 125.428 28.0587C125.536 28.4955 125.589 28.9739 125.589 29.4938V33.8208H123.738V29.7734C123.738 29.3613 123.71 29.0105 123.653 28.7211C123.597 28.4321 123.506 28.1966 123.378 28.0146C123.251 27.833 123.077 27.7005 122.858 27.6173C122.639 27.5341 122.371 27.4922 122.055 27.4922C121.82 27.4922 121.575 27.507 121.321 27.5362C121.065 27.5658 120.877 27.5901 120.755 27.6099V33.8208H118.903V26.3736Z"
fill="#4F4F4F" />
<path
d="M127.409 29.9801C127.409 29.4111 127.501 28.8788 127.684 28.3831C127.868 27.8878 128.13 27.4584 128.472 27.0953C128.814 26.7326 129.23 26.4477 129.719 26.2419C130.209 26.0356 130.76 25.9327 131.372 25.9327C132.126 25.9327 132.84 26.0652 133.513 26.33L133.115 27.787C132.901 27.6989 132.659 27.6252 132.389 27.5663C132.118 27.5074 131.831 27.4778 131.524 27.4778C130.8 27.4778 130.249 27.6964 129.872 28.1328C129.495 28.5696 129.306 29.1855 129.306 29.9801C129.306 30.7454 129.485 31.3515 129.842 31.7978C130.199 32.2444 130.8 32.4676 131.647 32.4676C131.963 32.4676 132.274 32.4379 132.58 32.3791C132.886 32.3202 133.151 32.2465 133.376 32.1584L133.635 33.6302C133.432 33.7282 133.123 33.8167 132.71 33.8954C132.297 33.9736 131.871 34.0127 131.433 34.0127C130.749 34.0127 130.155 33.9122 129.65 33.7109C129.145 33.51 128.727 33.2305 128.396 32.8723C128.064 32.5141 127.817 32.0876 127.654 31.5915C127.49 31.0962 127.409 30.5589 127.409 29.9801Z"
fill="#4F4F4F" />
<path
d="M134.982 24.0921L136.834 23.7977V26.123H139.68V27.6096H136.834V30.7447C136.834 31.3627 136.936 31.8044 137.14 32.0696C137.343 32.3343 137.69 32.4669 138.18 32.4669C138.516 32.4669 138.815 32.4327 139.075 32.3635C139.335 32.2952 139.542 32.2314 139.695 32.1725L140.001 33.5854C139.787 33.6736 139.506 33.7645 139.159 33.8576C138.812 33.9506 138.404 33.9976 137.935 33.9976C137.364 33.9976 136.887 33.9239 136.505 33.7765C136.122 33.6295 135.819 33.4162 135.594 33.1363C135.37 32.8567 135.212 32.5183 135.12 32.1206C135.028 31.7237 134.982 31.2696 134.982 30.7591V24.0921Z"
fill="#4F4F4F" />
<defs>
<linearGradient id="paint0_linear" x1="22.7517" y1="50.2753" x2="33.7241" y2="-5.17782"
gradientUnits="userSpaceOnUse">
<stop stop-color="#FFE300" />
<stop offset="0.67044" stop-color="#FF1E00" />
<stop offset="1" stop-color="#FF6E0D" />
</linearGradient>
<linearGradient id="paint1_linear" x1="16.9493" y1="56.4025" x2="17.4978" y2="-1.25871"
gradientUnits="userSpaceOnUse">
<stop stop-color="#FFE300" />
<stop offset="0.67044" stop-color="#FF4600" />
<stop offset="1" stop-color="#FF8C00" />
</linearGradient>
<linearGradient id="paint2_linear" x1="22.4111" y1="49.381" x2="24.8006" y2="3.23446"
gradientUnits="userSpaceOnUse">
<stop stop-color="#FFE300" />
<stop offset="0.67044" stop-color="#FF1E00" />
<stop offset="1" stop-color="#FF6E0D" />
</linearGradient>
<linearGradient id="paint3_linear" x1="-5.69431" y1="66.914" x2="9.18195" y2="-13.8092"
gradientUnits="userSpaceOnUse">
<stop stop-color="#FFE300" />
<stop offset="1" stop-color="#FF002A" />
</linearGradient>
</defs>
</svg>
</header>
</body>
</html>

View File

@ -0,0 +1,210 @@
<!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>
<!-- Login form template begins here -->
<form th:fragment="loginform" class="form" method="post" id="fm1" th:object="${credential}" action="login">
<div th:if="${existingSingleSignOnSessionAvailable}">
<h6>
<i class="fas fa-info-circle"></i>&nbsp;
<span th:utext="#{screen.welcome.forcedsso(${existingSingleSignOnSessionPrincipal.id})}" />
</h6>
</div>
<p class="form__title form__title--main" th:unless="${existingSingleSignOnSessionAvailable}"
th:utext="#{screen.welcome.instructions}">
Enter your Username and Password:
</p>
<section class="form-group">
<span th:if="${availableAuthenticationHandlerNames != null}">
<span th:if="${availableAuthenticationHandlerNames.size() > 1}">
<label for="source" th:utext="#{screen.welcome.label.source}">Source</label>
<div>
<select class="form-control required" id="source" name="source" tabindex="0" th:field="*{source}">
<option th:each="handler : ${availableAuthenticationHandlerNames}" th:value="${handler}" th:text="${handler}">
Source</option>
</select>
</div>
</span>
<span th:if="${availableAuthenticationHandlerNames.size() == 1}">
<input type="hidden" id="source" name="source" th:value="${availableAuthenticationHandlerNames.get(0)}" />
</span>
</span>
</section>
<label class="visually-hidden" for="username" th:utext="#{screen.welcome.label.netid}">
Username
</label>
<div th:if="${openIdLocalId}">
<strong>
<span th:utext="${openIdLocalId}"/>
</strong>
<input type="hidden"
id="username"
name="username"
th:value="${openIdLocalId}"/>
</div>
<input
required
id="username"
class="input form__input"
size="25"
tabindex="1"
type="text"
autocomplete="off"
th:unless="${openIdLocalId}"
th:placeholder="#{screen.welcome.label.netid}"
th:disabled="${guaEnabled}"
th:field="*{username}"
th:accesskey="#{screen.welcome.label.netid.accesskey}"
/>
<label class="visually-hidden" for="password" th:utext="#{screen.welcome.label.password}">
Password
</label>
<input
required
id="password"
class="input form__input"
type="password"
size="25"
tabindex="2"
autocomplete="off"
th:field="*{password}"
th:placeholder="#{screen.welcome.label.password}"
th:accesskey="#{screen.welcome.label.password.accesskey}"
/>
<div class="form__error-text" th:if="${#fields.hasErrors('*')}">
<span th:each="err : ${#fields.errors('*')}" th:utext="${err + ' '}">Example error</span>
</div>
<section class="form-group">
<div th:each="entry: ${customLoginFormFields}">
<div>
<span th:text="#{${entry.value.messageBundleKey}}">Label</span>
<input class="form-control required" type="text" name="data" th:field="*{customFields[__${entry.key}__]}">
</div>
</div>
</section>
<section class="form-check"
th:if="${passwordManagementEnabled != null && passwordManagementEnabled && param.doChangePassword != null}">
<p>
<input type="checkbox" name="doChangePassword" id="doChangePassword"
value="true" th:checked="${param.doChangePassword != null}" tabindex="4"/>
<label for="doChangePassword" th:text="#{screen.button.changePassword}">Change Password</label>
</p>
</section>
<input
checked
class="hidden"
type="checkbox"
name="rememberMe"
id="rememberMe"
value="true"
tabindex="5"
th:if="${rememberMeAuthenticationEnabled}"
/>
<span th:if="${recaptchaVersion=='v2'}" th:remove="tag">
<section class="form-group" th:if="${recaptchaSiteKey != null AND recaptchaInvisible != null AND !recaptchaInvisible}">
<div class="g-recaptcha" th:attr="data-sitekey=${recaptchaSiteKey}"/>
</section>
</span>
<span th:if="${recaptchaVersion=='v3'}" th:remove="tag">
<input type="hidden" id="g-recaptcha-token" name="g-recaptcha-token"/>
</span>
<input type="hidden" name="execution" th:value="${flowExecutionKey}" />
<input type="hidden" name="_eventId" value="submit" />
<input type="hidden" name="geolocation" />
<p th:if="${#request.getMethod().equalsIgnoreCase('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>
<input
class="button"
th:if="${recaptchaSiteKey == null}"
name="submit"
accesskey="l"
th:value="#{screen.welcome.button.login}"
tabindex="6"
type="submit"
value="Login8"
/>
<span th:if="${recaptchaVersion=='v2'}" th:remove="tag">
<input
class="btn btn-block btn-submit"
th:unless="${recaptchaSiteKey != null AND recaptchaInvisible != null AND recaptchaInvisible}"
name="submit"
accesskey="l"
th:value="#{screen.welcome.button.login}"
tabindex="6"
type="submit"
value="Login3"
/>
<button
class="btn btn-block btn-submit g-recaptcha"
th:if="${recaptchaSiteKey != null AND recaptchaInvisible != null AND recaptchaInvisible}"
th:attr="data-sitekey=${recaptchaSiteKey}, data-badge=${recaptchaPosition}"
data-callback="onRecaptchaV2Submit"
name="submitBtn"
accesskey="l"
th:text="#{screen.welcome.button.login}"
tabindex="6"
/>
</span>
<span th:if="${recaptchaVersion=='v3'}" th:remove="tag">
<input
class="btn btn-block btn-submit"
th:if="${recaptchaSiteKey != null}"
name="submit"
th:attr="data-sitekey=${recaptchaSiteKey}"
accesskey="l"
th:value="#{screen.welcome.button.login}"
tabindex="6"
type="submit"
value="Login3"
/>
</span>
</form>
<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> -->
</body>
</html>

View File

@ -0,0 +1,41 @@
<!DOCTYPE html>
<html xmlns:layout="http://www.ultraq.net.nz/thymeleaf/layout">
<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 layout:title-pattern="$CONTENT_TITLE - $LAYOUT_TITLE">CAS &#8211; Central Authentication Service</title>
<link rel="stylesheet" type="text/css" th:href="@{#{webjars.fontawesomemin.css}}"/>
<link rel="stylesheet" type="text/css" th:href="@{#{webjars.bootstrapmin.css}}"/>
<!--/* Core CAS CSS */-->
<link rel="stylesheet" type="text/css" href="../static/css/cas.css" th:href="@{${#themes.code('cas.standard.css.file')}}"/>
<link rel="icon" th:href="@{/favicon.ico}" type="image/x-icon"/>
<script type="text/javascript" th:src="@{#{webjars.jquerymin.js}}"></script>
</head>
<body>
<script th:replace="fragments/scripts"/>
<div th:replace="fragments/header :: header">
<a href="fragments/header.html">Header</a> fragment will go here
</div>
<main role="main" class="container mt-3 mb-3">
<div layout:fragment="content" id="content">
CAS content will go here
</div>
</main>
<div th:replace="fragments/footer :: footer">
<a href="fragments/footer.html">Footer</a> fragment will go here
</div>
</body>
</html>