mirror of
https://github.com/Alfresco/alfresco-ng2-components.git
synced 2025-07-31 17:38:48 +00:00
[ADF-589] Login component different bug fixes (#1953)
* Basic style changes * Further design changes * Responsive design fixes * Different sign in button style for the different login steps
This commit is contained in:
committed by
Eugenio Romano
parent
969658891d
commit
c0ca744d17
@@ -17,7 +17,7 @@
|
|||||||
|
|
||||||
import { NgModule, ModuleWithProviders } from '@angular/core';
|
import { NgModule, ModuleWithProviders } from '@angular/core';
|
||||||
import { CoreModule } from 'ng2-alfresco-core';
|
import { CoreModule } from 'ng2-alfresco-core';
|
||||||
import { MdInputModule, MdIconModule, MdCheckboxModule } from '@angular/material';
|
import { MdInputModule, MdIconModule, MdCheckboxModule, MdProgressSpinnerModule } from '@angular/material';
|
||||||
|
|
||||||
import { LoginHeaderDirective } from './src/directives/login-header.directive';
|
import { LoginHeaderDirective } from './src/directives/login-header.directive';
|
||||||
import { LoginFooterDirective } from './src/directives/login-footer.directive';
|
import { LoginFooterDirective } from './src/directives/login-footer.directive';
|
||||||
@@ -39,7 +39,8 @@ export const ALFRESCO_LOGIN_DIRECTIVES: any[] = [
|
|||||||
CoreModule,
|
CoreModule,
|
||||||
MdInputModule,
|
MdInputModule,
|
||||||
MdIconModule,
|
MdIconModule,
|
||||||
MdCheckboxModule
|
MdCheckboxModule,
|
||||||
|
MdProgressSpinnerModule
|
||||||
],
|
],
|
||||||
declarations: [
|
declarations: [
|
||||||
...ALFRESCO_LOGIN_DIRECTIVES
|
...ALFRESCO_LOGIN_DIRECTIVES
|
||||||
|
@@ -24,25 +24,62 @@
|
|||||||
:host .content-layout {
|
:host .content-layout {
|
||||||
background-size: cover;
|
background-size: cover;
|
||||||
background-position: center;
|
background-position: center;
|
||||||
height: 100%;
|
min-height: 100%;
|
||||||
padding: 0;
|
padding: 0;
|
||||||
|
|
||||||
|
-webkit-box-orient: vertical;
|
||||||
|
-moz-box-orient: vertical;
|
||||||
|
box-orient: vertical;
|
||||||
|
flex-direction: column;
|
||||||
|
|
||||||
|
align-items: center;
|
||||||
|
justify-content: center;
|
||||||
}
|
}
|
||||||
|
|
||||||
:host .login-card-wide.mdl-card {
|
:host .login-card-wide.mdl-card {
|
||||||
align-self: center;
|
|
||||||
margin: auto;
|
|
||||||
border-radius: 8px;
|
border-radius: 8px;
|
||||||
background-color: #ffffff;
|
background-color: #ffffff;
|
||||||
box-shadow: 0 2px 2px 0 rgba(0, 0, 0, 0.24), 0 0 2px 0 rgba(0, 0, 0, 0.12);
|
box-shadow: 0 2px 2px 0 rgba(0, 0, 0, 0.24), 0 0 2px 0 rgba(0, 0, 0, 0.12);
|
||||||
|
width: 450px;
|
||||||
|
min-width: 350px;
|
||||||
|
min-height: 450px;
|
||||||
|
padding: 21px 64px 34px 64px;
|
||||||
|
box-sizing: border-box;
|
||||||
|
}
|
||||||
|
|
||||||
|
@media (max-width: 482px) {
|
||||||
|
:host .login-card-wide.mdl-card {
|
||||||
|
width: calc(100% - 32px);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
:host .error {
|
:host .error {
|
||||||
|
display: -webkit-box;
|
||||||
|
display: -moz-box;
|
||||||
|
display: -ms-flexbox;
|
||||||
|
display: -webkit-flex;
|
||||||
|
display: flex;
|
||||||
|
|
||||||
|
-webkit-box-orient: horizontal;
|
||||||
|
-moz-box-orient: horizontal;
|
||||||
|
box-orient: horizontal;
|
||||||
|
flex-direction: row;
|
||||||
|
|
||||||
|
-webkit-box-pack: flex-start;
|
||||||
|
-moz-box-pack: flex-start;
|
||||||
|
box-pack: flex-start;
|
||||||
|
justify-content: flex-start;
|
||||||
|
|
||||||
color: red;
|
color: red;
|
||||||
padding: 8px;
|
padding: 0px;
|
||||||
margin-bottom: 4px;
|
margin-bottom: 4px;
|
||||||
font-size: 13px;
|
font-size: 13px;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
:host .error .error-icon {
|
||||||
|
margin-right: 10px;
|
||||||
|
}
|
||||||
|
|
||||||
:host .center {
|
:host .center {
|
||||||
display: block;
|
display: block;
|
||||||
margin-left: auto;
|
margin-left: auto;
|
||||||
@@ -50,7 +87,7 @@
|
|||||||
}
|
}
|
||||||
|
|
||||||
:host .alfresco-logo {
|
:host .alfresco-logo {
|
||||||
margin-top: 5px;
|
padding: 24px 16px 24px 16px;
|
||||||
}
|
}
|
||||||
|
|
||||||
:host .alfresco-logo img {
|
:host .alfresco-logo img {
|
||||||
@@ -58,15 +95,70 @@
|
|||||||
}
|
}
|
||||||
|
|
||||||
:host .mdl-button--raised.mdl-button--colored {
|
:host .mdl-button--raised.mdl-button--colored {
|
||||||
width: 98%;
|
width: 100%;
|
||||||
height: 36px;
|
height: 36px;
|
||||||
|
line-height: 38px;
|
||||||
border-radius: 4px;
|
border-radius: 4px;
|
||||||
|
box-shadow: none;
|
||||||
}
|
}
|
||||||
|
|
||||||
:host .mdl-button--raised.mdl-button--colored {
|
.login-button-label {
|
||||||
color: rgb(255, 255, 255);
|
color: rgb(255, 255, 255);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
:host .mdl-button--raised.mdl-button--colored[disabled] {
|
||||||
|
background-color: rgba(0, 0, 0, 0.07);
|
||||||
|
}
|
||||||
|
|
||||||
|
:host .mdl-button--raised.mdl-button--colored[disabled] .login-button-label {
|
||||||
|
color: rgb(175, 175, 175);
|
||||||
|
}
|
||||||
|
|
||||||
|
.adf-login-button.isChecking {
|
||||||
|
background-color: #e0f7fa;
|
||||||
|
}
|
||||||
|
|
||||||
|
.adf-login-button.isChecking .login-button-label{
|
||||||
|
color: #00bcd4;
|
||||||
|
}
|
||||||
|
|
||||||
|
.adf-login-button.isWelcome {
|
||||||
|
background-color: #00bcd4;
|
||||||
|
color: #ffffff;
|
||||||
|
}
|
||||||
|
|
||||||
|
.adf-login-button.isWelcome .welcome-icon {
|
||||||
|
margin: 5px 0 0 10px;
|
||||||
|
}
|
||||||
|
|
||||||
|
.adf-interactive-login-label {
|
||||||
|
display: -webkit-box;
|
||||||
|
display: -moz-box;
|
||||||
|
display: -ms-flexbox;
|
||||||
|
display: -webkit-flex;
|
||||||
|
display: flex;
|
||||||
|
|
||||||
|
-webkit-box-orient: horizontal;
|
||||||
|
-moz-box-orient: horizontal;
|
||||||
|
box-orient: horizontal;
|
||||||
|
flex-direction: row;
|
||||||
|
|
||||||
|
-webkit-box-pack: center;
|
||||||
|
-moz-box-pack: center;
|
||||||
|
box-pack: center;
|
||||||
|
justify-content: center;
|
||||||
|
}
|
||||||
|
|
||||||
|
.adf-login-checking-spinner {
|
||||||
|
height: 30px;
|
||||||
|
width: 20px;
|
||||||
|
margin-left: 10px;
|
||||||
|
}
|
||||||
|
|
||||||
|
.adf-login-checking-spinner.mat-spinner >>> path {
|
||||||
|
stroke: #00bcd4;
|
||||||
|
}
|
||||||
|
|
||||||
:host .login-card-wide > .mdl-card__menu {
|
:host .login-card-wide > .mdl-card__menu {
|
||||||
color: #000;
|
color: #000;
|
||||||
}
|
}
|
||||||
@@ -81,19 +173,43 @@
|
|||||||
color: #ff9100;
|
color: #ff9100;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
:host .login-controls {
|
||||||
|
padding: 0 0 26px 0;
|
||||||
|
overflow: visible;
|
||||||
|
width: 100%;
|
||||||
|
}
|
||||||
|
|
||||||
:host .login-action {
|
:host .login-action {
|
||||||
margin: 20px;
|
margin-top: 20px;
|
||||||
margin-bottom: 50px;
|
display: -webkit-box;
|
||||||
|
display: -moz-box;
|
||||||
|
display: -ms-flexbox;
|
||||||
|
display: -webkit-flex;
|
||||||
|
display: flex;
|
||||||
|
|
||||||
|
-webkit-box-orient: horizontal;
|
||||||
|
-moz-box-orient: horizontal;
|
||||||
|
box-orient: horizontal;
|
||||||
|
flex-direction: row;
|
||||||
|
|
||||||
|
-webkit-box-pack: space-between;
|
||||||
|
-moz-box-pack: space-between;
|
||||||
|
box-pack: space-between;
|
||||||
|
justify-content: space-between;
|
||||||
}
|
}
|
||||||
|
|
||||||
:host .login-action-left {
|
:host .login-action-left a,
|
||||||
float: left;
|
:host .login-action-right a {
|
||||||
margin-left: 10px;
|
text-decoration: none;
|
||||||
}
|
}
|
||||||
|
|
||||||
:host .login-action-right {
|
/* Known issue in angular material design module in betas */
|
||||||
float: right;
|
:host >>> .rememberme-cb label > div {
|
||||||
margin-right: 10px;
|
margin-right: 8px;
|
||||||
|
}
|
||||||
|
|
||||||
|
:host .mat-input-underline .mat-input-ripple {
|
||||||
|
background-color: #ffab40;
|
||||||
}
|
}
|
||||||
|
|
||||||
.ng-invalid.ng-invalid.ng-touched {
|
.ng-invalid.ng-invalid.ng-touched {
|
||||||
@@ -124,6 +240,15 @@
|
|||||||
color: #ff1744;
|
color: #ff1744;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
:host .copyright {
|
||||||
|
width: 450px;
|
||||||
|
text-align: center;
|
||||||
|
padding-top: 16px;
|
||||||
|
font-size: 12px;
|
||||||
|
color: #000;
|
||||||
|
opacity: 0.54;
|
||||||
|
}
|
||||||
|
|
||||||
.ng-invalid.ng-touched:not(:focus) + label::before {
|
.ng-invalid.ng-touched:not(:focus) + label::before {
|
||||||
font-family: 'Material Icons';
|
font-family: 'Material Icons';
|
||||||
font-weight: normal;
|
font-weight: normal;
|
||||||
@@ -188,20 +313,29 @@
|
|||||||
bottom: 20px;
|
bottom: 20px;
|
||||||
}
|
}
|
||||||
|
|
||||||
.alfresco-login__password {
|
.mat-input-container .alfresco-login__password-icon.mat-icon {
|
||||||
padding-right: 25px;
|
font-size: 24px;
|
||||||
}
|
|
||||||
|
|
||||||
.alfresco-login__password-icon {
|
|
||||||
float: right;
|
|
||||||
margin-right: -30px;
|
|
||||||
margin-top: 14px;
|
|
||||||
cursor: pointer;
|
cursor: pointer;
|
||||||
|
|
||||||
user-select: none;
|
user-select: none;
|
||||||
-moz-user-select: none;
|
-moz-user-select: none;
|
||||||
-webkit-user-select: none;
|
-webkit-user-select: none;
|
||||||
-ms-user-select: none;
|
-ms-user-select: none;
|
||||||
|
position: relative;
|
||||||
|
top: -6px;
|
||||||
|
height: 20px;
|
||||||
|
}
|
||||||
|
|
||||||
|
.adf-login__field >>> .mat-input-wrapper {
|
||||||
|
margin: 1em 0 0 0;
|
||||||
|
font-size: 16px;
|
||||||
|
}
|
||||||
|
|
||||||
|
.adf-login__field >>> input {
|
||||||
|
color: rgba(0, 0, 0, 0.87);
|
||||||
|
}
|
||||||
|
|
||||||
|
.adf-login__field .mat-focused >>> .mat-input-placeholder {
|
||||||
|
color: rgba(0, 0, 0, 0.38);
|
||||||
}
|
}
|
||||||
|
|
||||||
.alfresco-login__container {
|
.alfresco-login__container {
|
||||||
@@ -232,12 +366,17 @@
|
|||||||
}
|
}
|
||||||
|
|
||||||
.adf-login__remember-me {
|
.adf-login__remember-me {
|
||||||
padding-top: 15px;
|
padding-top: 22px;
|
||||||
|
}
|
||||||
|
|
||||||
|
.adf-login__remember-me >>> .mat-checkbox-label {
|
||||||
|
color: #000000;
|
||||||
|
opacity: 0.87;
|
||||||
}
|
}
|
||||||
|
|
||||||
.adf-login__field {
|
.adf-login__field {
|
||||||
display: block;
|
display: block;
|
||||||
margin-left: auto;
|
margin-left: auto;
|
||||||
margin-right: auto;
|
margin-right: auto;
|
||||||
padding-bottom: 24px;
|
padding-bottom: 18px;
|
||||||
}
|
}
|
||||||
|
@@ -10,18 +10,21 @@
|
|||||||
</ng-template>
|
</ng-template>
|
||||||
<img *ngIf="!headerTemplate" class="center" [src]="logoImageUrl" alt="{{'LOGIN.LOGO' | translate }}">
|
<img *ngIf="!headerTemplate" class="center" [src]="logoImageUrl" alt="{{'LOGIN.LOGO' | translate }}">
|
||||||
</div>
|
</div>
|
||||||
<div class="mdl-card__supporting-text">
|
<div class="mdl-card__supporting-text login-controls">
|
||||||
|
|
||||||
<!--ERRORS AREA-->
|
<!--ERRORS AREA-->
|
||||||
<div>
|
<div>
|
||||||
<div *ngIf="error" id="login-error" data-automation-id="login-error"
|
<div *ngIf="error" id="login-error" data-automation-id="login-error"
|
||||||
class="error mdl-card__supporting-text">{{errorMsg | translate }}</div>
|
class="error mdl-card__supporting-text adf-error-message">
|
||||||
|
<md-icon class="error-icon">warning</md-icon>
|
||||||
|
<span class="login-error-message">{{errorMsg | translate }}</span>
|
||||||
|
</div>
|
||||||
<div *ngIf="success" id="login-success" data-automation-id="login-success" class="mdl-card__supporting-text" class="alfresco-login__message">{{'LOGIN.MESSAGES.LOGIN-SUCCESS' | translate }}</div>
|
<div *ngIf="success" id="login-success" data-automation-id="login-success" class="mdl-card__supporting-text" class="alfresco-login__message">{{'LOGIN.MESSAGES.LOGIN-SUCCESS' | translate }}</div>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
<!--USERNAME FIELD-->
|
<!--USERNAME FIELD-->
|
||||||
<div class="adf-login__field" [ngClass]="{'is-invalid': isErrorStyle(form.controls.username)}">
|
<div class="adf-login__field" [ngClass]="{'is-invalid': isErrorStyle(form.controls.username)}">
|
||||||
<md-input-container class="adf-full-width">
|
<md-input-container class="adf-full-width" floatPlaceholder="never" color="accent">
|
||||||
<input mdInput placeholder="{{'LOGIN.LABEL.USERNAME' | translate }}"
|
<input mdInput placeholder="{{'LOGIN.LABEL.USERNAME' | translate }}"
|
||||||
type="text"
|
type="text"
|
||||||
class="adf-full-width"
|
class="adf-full-width"
|
||||||
@@ -40,16 +43,15 @@
|
|||||||
|
|
||||||
<!--PASSWORD FIELD-->
|
<!--PASSWORD FIELD-->
|
||||||
<div class="adf-login__field alfresco-login__password">
|
<div class="adf-login__field alfresco-login__password">
|
||||||
<md-icon *ngIf="!isPasswordShow" class="alfresco-login__password-icon" data-automation-id="show_password" (click)="toggleShowPassword()">visibility</md-icon>
|
<md-input-container class="adf-full-width" floatPlaceholder="never" color="accent">
|
||||||
<md-icon *ngIf="isPasswordShow" class="alfresco-login__password-icon" data-automation-id="hide_password" (click)="toggleShowPassword()">visibility_off</md-icon>
|
|
||||||
|
|
||||||
<md-input-container class="adf-full-width">
|
|
||||||
<input mdInput placeholder="{{'LOGIN.LABEL.PASSWORD' | translate }}"
|
<input mdInput placeholder="{{'LOGIN.LABEL.PASSWORD' | translate }}"
|
||||||
type="password"
|
type="password"
|
||||||
[formControl]="form.controls['password']"
|
[formControl]="form.controls['password']"
|
||||||
id="password"
|
id="password"
|
||||||
data-automation-id="password"
|
data-automation-id="password"
|
||||||
tabindex="2">
|
tabindex="2">
|
||||||
|
<md-icon *ngIf="isPasswordShow" mdSuffix class="alfresco-login__password-icon" data-automation-id="show_password" (click)="toggleShowPassword()">visibility</md-icon>
|
||||||
|
<md-icon *ngIf="!isPasswordShow" mdSuffix class="alfresco-login__password-icon" data-automation-id="hide_password" (click)="toggleShowPassword()">visibility_off</md-icon>
|
||||||
</md-input-container>
|
</md-input-container>
|
||||||
<span class="alfresco-login__validation" for="password" *ngIf="formError.password">
|
<span class="alfresco-login__validation" for="password" *ngIf="formError.password">
|
||||||
<span id="password-required" class="alfresco-login__error" data-automation-id="password-required">{{formError.password | translate }}</span>
|
<span id="password-required" class="alfresco-login__error" data-automation-id="password-required">{{formError.password | translate }}</span>
|
||||||
@@ -61,10 +63,26 @@
|
|||||||
|
|
||||||
<br>
|
<br>
|
||||||
<button type="submit" id="login-button" tabindex="3"
|
<button type="submit" id="login-button" tabindex="3"
|
||||||
class="center mdl-button mdl-js-button mdl-button--raised mdl-js-ripple-effect mdl-button--colored"
|
class="adf-login-button center mdl-button mdl-js-button mdl-button--raised mdl-js-ripple-effect mdl-button--colored"
|
||||||
data-automation-id="login-button" [disabled]="!form.valid">{{'LOGIN.BUTTON.LOGIN' | translate }}</button>
|
[class.isChecking]="actualLoginStep === LoginSteps.Checking"
|
||||||
|
[class.isWelcome]="actualLoginStep === LoginSteps.Welcome"
|
||||||
|
data-automation-id="login-button" [disabled]="!form.valid">
|
||||||
|
|
||||||
|
<span *ngIf="actualLoginStep === LoginSteps.Landing" class="login-button-label">{{ 'LOGIN.BUTTON.LOGIN' | translate }}</span>
|
||||||
|
|
||||||
|
<div *ngIf="actualLoginStep === LoginSteps.Checking" class="adf-interactive-login-label">
|
||||||
|
<span class="login-button-label">{{ 'LOGIN.BUTTON.CHECKING' | translate }}</span>
|
||||||
|
<md-spinner id="checking-spinner" class="adf-login-checking-spinner"></md-spinner>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div *ngIf="actualLoginStep === LoginSteps.Welcome" class="adf-interactive-login-label">
|
||||||
|
<span class="login-button-label">{{ 'LOGIN.BUTTON.WELCOME' | translate }}</span>
|
||||||
|
<md-icon class="welcome-icon">done</md-icon>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
</button>
|
||||||
<div *ngIf="showRememberMe" class="adf-login__remember-me" id ="login-remember">
|
<div *ngIf="showRememberMe" class="adf-login__remember-me" id ="login-remember">
|
||||||
<md-checkbox>{{'LOGIN.LABEL.REMEMBER' | translate }}</md-checkbox>
|
<md-checkbox class="rememberme-cb" checked="true">{{ 'LOGIN.LABEL.REMEMBER' | translate }}</md-checkbox>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
<div class="mdl-card__actions mdl-card--border mdl-card__link">
|
<div class="mdl-card__actions mdl-card--border mdl-card__link">
|
||||||
@@ -88,4 +106,8 @@
|
|||||||
</div>
|
</div>
|
||||||
</form>
|
</form>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
|
<div class="copyright">
|
||||||
|
© 2016 Alfresco Software, Inc. All Rights Reserved.
|
||||||
|
</div>
|
||||||
</div>
|
</div>
|
||||||
|
@@ -32,6 +32,9 @@ describe('AlfrescoLogin', () => {
|
|||||||
|
|
||||||
let usernameInput, passwordInput;
|
let usernameInput, passwordInput;
|
||||||
|
|
||||||
|
const getLoginErrorElement = () => element.querySelector('#login-error');
|
||||||
|
const getLoginErrorMessage = () => element.querySelector('#login-error .login-error-message').innerText;
|
||||||
|
|
||||||
beforeEach(async(() => {
|
beforeEach(async(() => {
|
||||||
TestBed.configureTestingModule({
|
TestBed.configureTestingModule({
|
||||||
imports: [
|
imports: [
|
||||||
@@ -61,6 +64,52 @@ describe('AlfrescoLogin', () => {
|
|||||||
fixture.detectChanges();
|
fixture.detectChanges();
|
||||||
});
|
});
|
||||||
|
|
||||||
|
describe('Login button', () => {
|
||||||
|
|
||||||
|
const getLoginButton = () => element.querySelector('#login-button');
|
||||||
|
const getLoginButtonText = () => element.querySelector('#login-button span.login-button-label').innerText;
|
||||||
|
|
||||||
|
function loginWithCredentials(username, password) {
|
||||||
|
component.providers = 'ECM';
|
||||||
|
usernameInput.value = username;
|
||||||
|
passwordInput.value = password;
|
||||||
|
|
||||||
|
usernameInput.dispatchEvent(new Event('input'));
|
||||||
|
passwordInput.dispatchEvent(new Event('input'));
|
||||||
|
fixture.detectChanges();
|
||||||
|
|
||||||
|
element.querySelector('button').click();
|
||||||
|
fixture.detectChanges();
|
||||||
|
}
|
||||||
|
|
||||||
|
it('should be rendered with the proper key by default', () => {
|
||||||
|
expect(getLoginButton()).not.toBeNull();
|
||||||
|
expect(getLoginButtonText()).toEqual('LOGIN.BUTTON.LOGIN');
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should be changed to the "checking key" after a login attempt', () => {
|
||||||
|
const authService = TestBed.get(AlfrescoAuthenticationService);
|
||||||
|
spyOn(authService, 'login').and.returnValue({ subscribe: () => { } });
|
||||||
|
|
||||||
|
loginWithCredentials('fake-username', 'fake-password');
|
||||||
|
|
||||||
|
expect(element.querySelector('#checking-spinner')).not.toBeNull();
|
||||||
|
expect(getLoginButtonText()).toEqual('LOGIN.BUTTON.CHECKING');
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should be changed back to the default after a failed login attempt', () => {
|
||||||
|
loginWithCredentials('fake-wrong-username', 'fake-wrong-password');
|
||||||
|
|
||||||
|
expect(getLoginButtonText()).toEqual('LOGIN.BUTTON.LOGIN');
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should be changed to the "welcome key" after a successful login attempt', () => {
|
||||||
|
loginWithCredentials('fake-username', 'fake-password');
|
||||||
|
|
||||||
|
expect(getLoginButtonText()).toEqual('LOGIN.BUTTON.WELCOME');
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
it('should render Login form with all the keys to be translated', () => {
|
it('should render Login form with all the keys to be translated', () => {
|
||||||
expect(element.querySelector('[for="username"]')).toBeDefined();
|
expect(element.querySelector('[for="username"]')).toBeDefined();
|
||||||
expect(element.querySelector('[for="username"]').innerText).toEqual('LOGIN.LABEL.USERNAME');
|
expect(element.querySelector('[for="username"]').innerText).toEqual('LOGIN.LABEL.USERNAME');
|
||||||
@@ -71,9 +120,6 @@ describe('AlfrescoLogin', () => {
|
|||||||
expect(element.querySelector('[for="password"]')).toBeDefined();
|
expect(element.querySelector('[for="password"]')).toBeDefined();
|
||||||
expect(element.querySelector('[for="password"]').innerText).toEqual('LOGIN.LABEL.PASSWORD');
|
expect(element.querySelector('[for="password"]').innerText).toEqual('LOGIN.LABEL.PASSWORD');
|
||||||
|
|
||||||
expect(element.querySelector('#login-button')).toBeDefined();
|
|
||||||
expect(element.querySelector('#login-button').innerText).toEqual('LOGIN.BUTTON.LOGIN');
|
|
||||||
|
|
||||||
expect(element.querySelector('#login-action-help')).toBeDefined();
|
expect(element.querySelector('#login-action-help')).toBeDefined();
|
||||||
expect(element.querySelector('#login-action-help').innerText).toEqual('LOGIN.ACTION.HELP');
|
expect(element.querySelector('#login-action-help').innerText).toEqual('LOGIN.ACTION.HELP');
|
||||||
|
|
||||||
@@ -245,8 +291,8 @@ describe('AlfrescoLogin', () => {
|
|||||||
|
|
||||||
expect(component.error).toBe(true);
|
expect(component.error).toBe(true);
|
||||||
expect(component.success).toBe(false);
|
expect(component.success).toBe(false);
|
||||||
expect(element.querySelector('#login-error')).toBeDefined();
|
expect(getLoginErrorElement()).toBeDefined();
|
||||||
expect(element.querySelector('#login-error').innerText).toEqual('LOGIN.MESSAGES.LOGIN-ERROR-CREDENTIALS');
|
expect(getLoginErrorMessage()).toEqual('LOGIN.MESSAGES.LOGIN-ERROR-CREDENTIALS');
|
||||||
});
|
});
|
||||||
|
|
||||||
it('should return error with a wrong password', () => {
|
it('should return error with a wrong password', () => {
|
||||||
@@ -268,8 +314,8 @@ describe('AlfrescoLogin', () => {
|
|||||||
|
|
||||||
expect(component.error).toBe(true);
|
expect(component.error).toBe(true);
|
||||||
expect(component.success).toBe(false);
|
expect(component.success).toBe(false);
|
||||||
expect(element.querySelector('#login-error')).toBeDefined();
|
expect(getLoginErrorElement()).toBeDefined();
|
||||||
expect(element.querySelector('#login-error').innerText).toEqual('LOGIN.MESSAGES.LOGIN-ERROR-CREDENTIALS');
|
expect(getLoginErrorMessage()).toEqual('LOGIN.MESSAGES.LOGIN-ERROR-CREDENTIALS');
|
||||||
});
|
});
|
||||||
|
|
||||||
it('should return error with a wrong username and password', () => {
|
it('should return error with a wrong username and password', () => {
|
||||||
@@ -291,8 +337,8 @@ describe('AlfrescoLogin', () => {
|
|||||||
|
|
||||||
expect(component.error).toBe(true);
|
expect(component.error).toBe(true);
|
||||||
expect(component.success).toBe(false);
|
expect(component.success).toBe(false);
|
||||||
expect(element.querySelector('#login-error')).toBeDefined();
|
expect(getLoginErrorElement()).toBeDefined();
|
||||||
expect(element.querySelector('#login-error').innerText).toEqual('LOGIN.MESSAGES.LOGIN-ERROR-CREDENTIALS');
|
expect(getLoginErrorMessage()).toEqual('LOGIN.MESSAGES.LOGIN-ERROR-CREDENTIALS');
|
||||||
});
|
});
|
||||||
|
|
||||||
it('should return CORS error when server CORS error occurs', () => {
|
it('should return CORS error when server CORS error occurs', () => {
|
||||||
@@ -314,8 +360,8 @@ describe('AlfrescoLogin', () => {
|
|||||||
|
|
||||||
expect(component.error).toBe(true);
|
expect(component.error).toBe(true);
|
||||||
expect(component.success).toBe(false);
|
expect(component.success).toBe(false);
|
||||||
expect(element.querySelector('#login-error')).toBeDefined();
|
expect(getLoginErrorElement()).toBeDefined();
|
||||||
expect(element.querySelector('#login-error').innerText).toEqual('ERROR: the network is offline, Origin is not allowed by Access-Control-Allow-Origin');
|
expect(getLoginErrorMessage()).toEqual('ERROR: the network is offline, Origin is not allowed by Access-Control-Allow-Origin');
|
||||||
});
|
});
|
||||||
|
|
||||||
it('should return CSRF error when server CSRF error occurs', () => {
|
it('should return CSRF error when server CSRF error occurs', () => {
|
||||||
@@ -337,8 +383,8 @@ describe('AlfrescoLogin', () => {
|
|||||||
|
|
||||||
expect(component.error).toBe(true);
|
expect(component.error).toBe(true);
|
||||||
expect(component.success).toBe(false);
|
expect(component.success).toBe(false);
|
||||||
expect(element.querySelector('#login-error')).toBeDefined();
|
expect(getLoginErrorElement()).toBeDefined();
|
||||||
expect(element.querySelector('#login-error').innerText).toEqual('LOGIN.MESSAGES.LOGIN-ERROR-CSRF');
|
expect(getLoginErrorMessage()).toEqual('LOGIN.MESSAGES.LOGIN-ERROR-CSRF');
|
||||||
});
|
});
|
||||||
|
|
||||||
it('should return ECOM read-oly error when error occurs', () => {
|
it('should return ECOM read-oly error when error occurs', () => {
|
||||||
@@ -360,8 +406,8 @@ describe('AlfrescoLogin', () => {
|
|||||||
|
|
||||||
expect(component.error).toBe(true);
|
expect(component.error).toBe(true);
|
||||||
expect(component.success).toBe(false);
|
expect(component.success).toBe(false);
|
||||||
expect(element.querySelector('#login-error')).toBeDefined();
|
expect(getLoginErrorElement()).toBeDefined();
|
||||||
expect(element.querySelector('#login-error').innerText).toEqual('LOGIN.MESSAGES.LOGIN-ECM-LICENSE');
|
expect(getLoginErrorMessage()).toEqual('LOGIN.MESSAGES.LOGIN-ECM-LICENSE');
|
||||||
});
|
});
|
||||||
|
|
||||||
it('should emit onSuccess event after the login has succeeded', () => {
|
it('should emit onSuccess event after the login has succeeded', () => {
|
||||||
@@ -415,8 +461,8 @@ describe('AlfrescoLogin', () => {
|
|||||||
|
|
||||||
expect(component.error).toBe(true);
|
expect(component.error).toBe(true);
|
||||||
expect(component.success).toBe(false);
|
expect(component.success).toBe(false);
|
||||||
expect(element.querySelector('#login-error')).toBeDefined();
|
expect(getLoginErrorElement()).toBeDefined();
|
||||||
expect(element.querySelector('#login-error').innerText).toEqual('LOGIN.MESSAGES.LOGIN-ERROR-CREDENTIALS');
|
expect(getLoginErrorMessage()).toEqual('LOGIN.MESSAGES.LOGIN-ERROR-CREDENTIALS');
|
||||||
expect(component.onError.emit).toHaveBeenCalledWith('Fake server error');
|
expect(component.onError.emit).toHaveBeenCalledWith('Fake server error');
|
||||||
});
|
});
|
||||||
|
|
||||||
@@ -460,8 +506,8 @@ describe('AlfrescoLogin', () => {
|
|||||||
|
|
||||||
expect(component.error).toBe(true);
|
expect(component.error).toBe(true);
|
||||||
expect(component.success).toBe(false);
|
expect(component.success).toBe(false);
|
||||||
expect(element.querySelector('#login-error')).toBeDefined();
|
expect(getLoginErrorElement()).toBeDefined();
|
||||||
expect(element.querySelector('#login-error').innerText).toEqual('LOGIN.MESSAGES.LOGIN-ERROR-PROVIDERS');
|
expect(getLoginErrorMessage()).toEqual('LOGIN.MESSAGES.LOGIN-ERROR-PROVIDERS');
|
||||||
expect(component.onError.emit).toHaveBeenCalledWith('LOGIN.MESSAGES.LOGIN-ERROR-PROVIDERS');
|
expect(component.onError.emit).toHaveBeenCalledWith('LOGIN.MESSAGES.LOGIN-ERROR-PROVIDERS');
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
@@ -22,6 +22,12 @@ import { FormSubmitEvent } from '../models/form-submit-event.model';
|
|||||||
|
|
||||||
declare let componentHandler: any;
|
declare let componentHandler: any;
|
||||||
|
|
||||||
|
enum LoginSteps {
|
||||||
|
Landing = 0,
|
||||||
|
Checking = 1,
|
||||||
|
Welcome = 2
|
||||||
|
}
|
||||||
|
|
||||||
@Component({
|
@Component({
|
||||||
selector: 'alfresco-login',
|
selector: 'alfresco-login',
|
||||||
templateUrl: './alfresco-login.component.html',
|
templateUrl: './alfresco-login.component.html',
|
||||||
@@ -72,6 +78,8 @@ export class AlfrescoLoginComponent implements OnInit {
|
|||||||
error: boolean = false;
|
error: boolean = false;
|
||||||
errorMsg: string;
|
errorMsg: string;
|
||||||
success: boolean = false;
|
success: boolean = false;
|
||||||
|
actualLoginStep: any = LoginSteps.Landing;
|
||||||
|
LoginSteps: any = LoginSteps;
|
||||||
formError: { [id: string]: string };
|
formError: { [id: string]: string };
|
||||||
minLength: number = 2;
|
minLength: number = 2;
|
||||||
footerTemplate: TemplateRef<any>;
|
footerTemplate: TemplateRef<any>;
|
||||||
@@ -162,13 +170,16 @@ export class AlfrescoLoginComponent implements OnInit {
|
|||||||
* @param values
|
* @param values
|
||||||
*/
|
*/
|
||||||
private performLogin(values: any) {
|
private performLogin(values: any) {
|
||||||
|
this.actualLoginStep = LoginSteps.Checking;
|
||||||
this.authService.login(values.username, values.password)
|
this.authService.login(values.username, values.password)
|
||||||
.subscribe(
|
.subscribe(
|
||||||
(token: any) => {
|
(token: any) => {
|
||||||
|
this.actualLoginStep = LoginSteps.Welcome;
|
||||||
this.success = true;
|
this.success = true;
|
||||||
this.onSuccess.emit({token: token, username: values.username, password: values.password});
|
this.onSuccess.emit({token: token, username: values.username, password: values.password});
|
||||||
},
|
},
|
||||||
(err: any) => {
|
(err: any) => {
|
||||||
|
this.actualLoginStep = LoginSteps.Landing;
|
||||||
this.displayErrorMessage(err);
|
this.displayErrorMessage(err);
|
||||||
this.enableError();
|
this.enableError();
|
||||||
this.onError.emit(err);
|
this.onError.emit(err);
|
||||||
|
@@ -19,7 +19,9 @@
|
|||||||
"LOGIN-ECM-LICENSE": "Content Services repository is in read-only mode"
|
"LOGIN-ECM-LICENSE": "Content Services repository is in read-only mode"
|
||||||
},
|
},
|
||||||
"BUTTON": {
|
"BUTTON": {
|
||||||
"LOGIN": "SIGN IN"
|
"LOGIN": "SIGN IN",
|
||||||
|
"CHECKING": "CHECKING",
|
||||||
|
"WELCOME": "WELCOME"
|
||||||
},
|
},
|
||||||
"ACTION": {
|
"ACTION": {
|
||||||
"HELP": "NEED HELP?",
|
"HELP": "NEED HELP?",
|
||||||
|
24
ng2-components/package-lock.json
generated
24
ng2-components/package-lock.json
generated
@@ -2960,7 +2960,7 @@
|
|||||||
"glob": {
|
"glob": {
|
||||||
"version": "7.1.2",
|
"version": "7.1.2",
|
||||||
"resolved": "https://registry.npmjs.org/glob/-/glob-7.1.2.tgz",
|
"resolved": "https://registry.npmjs.org/glob/-/glob-7.1.2.tgz",
|
||||||
"integrity": "sha512-MJTUg1kjuLeQCJ+ccE4Vpa6kKVXkPYJ2mOCQyUuKLcLQsdrMCpBPUi8qVE6+YuaJkozeA9NusTAw3hLr8Xe5EQ==",
|
"integrity": "sha1-wZyd+aAocC1nhhI4SmVSQExjbRU=",
|
||||||
"dev": true
|
"dev": true
|
||||||
},
|
},
|
||||||
"lodash": {
|
"lodash": {
|
||||||
@@ -3903,7 +3903,7 @@
|
|||||||
"joi": {
|
"joi": {
|
||||||
"version": "10.5.2",
|
"version": "10.5.2",
|
||||||
"resolved": "https://registry.npmjs.org/joi/-/joi-10.5.2.tgz",
|
"resolved": "https://registry.npmjs.org/joi/-/joi-10.5.2.tgz",
|
||||||
"integrity": "sha512-Do/NXTokq86nvFfggE4UbwNnyzvALn3Ay+gMwQSAkrQoWTYc4LvkabhypVZiqDZq0TbtVhUpOphe4dmKB6/Pxg==",
|
"integrity": "sha1-ZPaFOwgOnfDPTMniBPoSzI95LEg=",
|
||||||
"dev": true,
|
"dev": true,
|
||||||
"dependencies": {
|
"dependencies": {
|
||||||
"hoek": {
|
"hoek": {
|
||||||
@@ -4016,7 +4016,7 @@
|
|||||||
"glob": {
|
"glob": {
|
||||||
"version": "7.1.2",
|
"version": "7.1.2",
|
||||||
"resolved": "https://registry.npmjs.org/glob/-/glob-7.1.2.tgz",
|
"resolved": "https://registry.npmjs.org/glob/-/glob-7.1.2.tgz",
|
||||||
"integrity": "sha512-MJTUg1kjuLeQCJ+ccE4Vpa6kKVXkPYJ2mOCQyUuKLcLQsdrMCpBPUi8qVE6+YuaJkozeA9NusTAw3hLr8Xe5EQ==",
|
"integrity": "sha1-wZyd+aAocC1nhhI4SmVSQExjbRU=",
|
||||||
"dev": true
|
"dev": true
|
||||||
},
|
},
|
||||||
"lodash": {
|
"lodash": {
|
||||||
@@ -4580,7 +4580,7 @@
|
|||||||
"minimatch": {
|
"minimatch": {
|
||||||
"version": "3.0.4",
|
"version": "3.0.4",
|
||||||
"resolved": "https://registry.npmjs.org/minimatch/-/minimatch-3.0.4.tgz",
|
"resolved": "https://registry.npmjs.org/minimatch/-/minimatch-3.0.4.tgz",
|
||||||
"integrity": "sha512-yJHVQEhyqPLUTgt9B83PXu6W3rx4MvvHvSUvToogpwoGDOUQ+yDrR0HRot+yOCdCO7u4hX3pWft6kWBBcqh0UA==",
|
"integrity": "sha1-UWbihkV/AzBgZL5Ul+jbsMPTIIM=",
|
||||||
"dev": true
|
"dev": true
|
||||||
},
|
},
|
||||||
"minimist": {
|
"minimist": {
|
||||||
@@ -4846,7 +4846,7 @@
|
|||||||
"glob": {
|
"glob": {
|
||||||
"version": "7.1.2",
|
"version": "7.1.2",
|
||||||
"resolved": "https://registry.npmjs.org/glob/-/glob-7.1.2.tgz",
|
"resolved": "https://registry.npmjs.org/glob/-/glob-7.1.2.tgz",
|
||||||
"integrity": "sha512-MJTUg1kjuLeQCJ+ccE4Vpa6kKVXkPYJ2mOCQyUuKLcLQsdrMCpBPUi8qVE6+YuaJkozeA9NusTAw3hLr8Xe5EQ==",
|
"integrity": "sha1-wZyd+aAocC1nhhI4SmVSQExjbRU=",
|
||||||
"dev": true
|
"dev": true
|
||||||
},
|
},
|
||||||
"semver": {
|
"semver": {
|
||||||
@@ -4880,7 +4880,7 @@
|
|||||||
"glob": {
|
"glob": {
|
||||||
"version": "7.1.2",
|
"version": "7.1.2",
|
||||||
"resolved": "https://registry.npmjs.org/glob/-/glob-7.1.2.tgz",
|
"resolved": "https://registry.npmjs.org/glob/-/glob-7.1.2.tgz",
|
||||||
"integrity": "sha512-MJTUg1kjuLeQCJ+ccE4Vpa6kKVXkPYJ2mOCQyUuKLcLQsdrMCpBPUi8qVE6+YuaJkozeA9NusTAw3hLr8Xe5EQ==",
|
"integrity": "sha1-wZyd+aAocC1nhhI4SmVSQExjbRU=",
|
||||||
"dev": true
|
"dev": true
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -4924,7 +4924,7 @@
|
|||||||
"npmlog": {
|
"npmlog": {
|
||||||
"version": "4.1.0",
|
"version": "4.1.0",
|
||||||
"resolved": "https://registry.npmjs.org/npmlog/-/npmlog-4.1.0.tgz",
|
"resolved": "https://registry.npmjs.org/npmlog/-/npmlog-4.1.0.tgz",
|
||||||
"integrity": "sha512-ocolIkZYZt8UveuiDS0yAkkIjid1o7lPG8cYm05yNYzBn8ykQtaiPMEGp8fY9tKdDgm8okpdKzkvu1y9hUYugA==",
|
"integrity": "sha1-3Fm+6F9k8A7UJO+yrweD3yXRwLU=",
|
||||||
"dev": true
|
"dev": true
|
||||||
},
|
},
|
||||||
"nth-check": {
|
"nth-check": {
|
||||||
@@ -5936,7 +5936,7 @@
|
|||||||
"glob": {
|
"glob": {
|
||||||
"version": "7.1.2",
|
"version": "7.1.2",
|
||||||
"resolved": "https://registry.npmjs.org/glob/-/glob-7.1.2.tgz",
|
"resolved": "https://registry.npmjs.org/glob/-/glob-7.1.2.tgz",
|
||||||
"integrity": "sha512-MJTUg1kjuLeQCJ+ccE4Vpa6kKVXkPYJ2mOCQyUuKLcLQsdrMCpBPUi8qVE6+YuaJkozeA9NusTAw3hLr8Xe5EQ==",
|
"integrity": "sha1-wZyd+aAocC1nhhI4SmVSQExjbRU=",
|
||||||
"dev": true
|
"dev": true
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -6002,7 +6002,7 @@
|
|||||||
"glob": {
|
"glob": {
|
||||||
"version": "7.1.2",
|
"version": "7.1.2",
|
||||||
"resolved": "https://registry.npmjs.org/glob/-/glob-7.1.2.tgz",
|
"resolved": "https://registry.npmjs.org/glob/-/glob-7.1.2.tgz",
|
||||||
"integrity": "sha512-MJTUg1kjuLeQCJ+ccE4Vpa6kKVXkPYJ2mOCQyUuKLcLQsdrMCpBPUi8qVE6+YuaJkozeA9NusTAw3hLr8Xe5EQ==",
|
"integrity": "sha1-wZyd+aAocC1nhhI4SmVSQExjbRU=",
|
||||||
"dev": true
|
"dev": true
|
||||||
},
|
},
|
||||||
"yargs": {
|
"yargs": {
|
||||||
@@ -6576,7 +6576,7 @@
|
|||||||
"glob": {
|
"glob": {
|
||||||
"version": "7.1.2",
|
"version": "7.1.2",
|
||||||
"resolved": "https://registry.npmjs.org/glob/-/glob-7.1.2.tgz",
|
"resolved": "https://registry.npmjs.org/glob/-/glob-7.1.2.tgz",
|
||||||
"integrity": "sha512-MJTUg1kjuLeQCJ+ccE4Vpa6kKVXkPYJ2mOCQyUuKLcLQsdrMCpBPUi8qVE6+YuaJkozeA9NusTAw3hLr8Xe5EQ==",
|
"integrity": "sha1-wZyd+aAocC1nhhI4SmVSQExjbRU=",
|
||||||
"dev": true
|
"dev": true
|
||||||
},
|
},
|
||||||
"source-map-support": {
|
"source-map-support": {
|
||||||
@@ -6880,7 +6880,7 @@
|
|||||||
"glob": {
|
"glob": {
|
||||||
"version": "7.1.2",
|
"version": "7.1.2",
|
||||||
"resolved": "https://registry.npmjs.org/glob/-/glob-7.1.2.tgz",
|
"resolved": "https://registry.npmjs.org/glob/-/glob-7.1.2.tgz",
|
||||||
"integrity": "sha512-MJTUg1kjuLeQCJ+ccE4Vpa6kKVXkPYJ2mOCQyUuKLcLQsdrMCpBPUi8qVE6+YuaJkozeA9NusTAw3hLr8Xe5EQ==",
|
"integrity": "sha1-wZyd+aAocC1nhhI4SmVSQExjbRU=",
|
||||||
"dev": true
|
"dev": true
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -7375,7 +7375,7 @@
|
|||||||
"wide-align": {
|
"wide-align": {
|
||||||
"version": "1.1.2",
|
"version": "1.1.2",
|
||||||
"resolved": "https://registry.npmjs.org/wide-align/-/wide-align-1.1.2.tgz",
|
"resolved": "https://registry.npmjs.org/wide-align/-/wide-align-1.1.2.tgz",
|
||||||
"integrity": "sha512-ijDLlyQ7s6x1JgCLur53osjm/UXUYD9+0PbYKrBsYisYXzCxN+HC3mYDNy/dWdmf3AwqwU3CXwDCvsNgGK1S0w==",
|
"integrity": "sha1-Vx4PGwYEY268DfwhsDObvjE0FxA=",
|
||||||
"dev": true
|
"dev": true
|
||||||
},
|
},
|
||||||
"widest-line": {
|
"widest-line": {
|
||||||
|
Reference in New Issue
Block a user