1<template> 2 <b-form class="login-form" novalidate @submit.prevent="login"> 3 <alert class="login-error mb-4" :show="authError" variant="danger"> 4 <p id="login-error-alert"> 5 {{ $t('pageLogin.alert.message') }} 6 </p> 7 </alert> 8 <b-form-group label-for="language" :label="$t('pageLogin.language')"> 9 <b-form-select 10 id="language" 11 v-model="$i18n.locale" 12 :options="languages" 13 data-test-id="login-select-language" 14 ></b-form-select> 15 </b-form-group> 16 <b-form-group label-for="username" :label="$t('pageLogin.username')"> 17 <b-form-input 18 id="username" 19 v-model="userInfo.username" 20 aria-describedby="login-error-alert username-required" 21 :state="getValidationState($v.userInfo.username)" 22 type="text" 23 autofocus="autofocus" 24 data-test-id="login-input-username" 25 @input="$v.userInfo.username.$touch()" 26 > 27 </b-form-input> 28 <b-form-invalid-feedback id="username-required" role="alert"> 29 <template v-if="!$v.userInfo.username.required"> 30 {{ $t('global.form.fieldRequired') }} 31 </template> 32 </b-form-invalid-feedback> 33 </b-form-group> 34 <div class="login-form__section mb-3"> 35 <label for="password">{{ $t('pageLogin.password') }}</label> 36 <input-password-toggle> 37 <b-form-input 38 id="password" 39 v-model="userInfo.password" 40 aria-describedby="login-error-alert password-required" 41 :state="getValidationState($v.userInfo.password)" 42 type="password" 43 data-test-id="login-input-password" 44 class="form-control-with-button" 45 @input="$v.userInfo.password.$touch()" 46 > 47 </b-form-input> 48 </input-password-toggle> 49 <b-form-invalid-feedback id="password-required" role="alert"> 50 <template v-if="!$v.userInfo.password.required"> 51 {{ $t('global.form.fieldRequired') }} 52 </template> 53 </b-form-invalid-feedback> 54 </div> 55 <b-button 56 class="mt-3" 57 type="submit" 58 variant="primary" 59 data-test-id="login-button-submit" 60 :disabled="disableSubmitButton" 61 >{{ $t('pageLogin.logIn') }}</b-button 62 > 63 </b-form> 64</template> 65 66<script> 67import { required } from 'vuelidate/lib/validators'; 68import VuelidateMixin from '@/components/Mixins/VuelidateMixin.js'; 69import i18n from '@/i18n'; 70import Alert from '@/components/Global/Alert'; 71import InputPasswordToggle from '@/components/Global/InputPasswordToggle'; 72 73export default { 74 name: 'Login', 75 components: { Alert, InputPasswordToggle }, 76 mixins: [VuelidateMixin], 77 data() { 78 return { 79 userInfo: { 80 username: null, 81 password: null, 82 }, 83 disableSubmitButton: false, 84 languages: [ 85 { 86 value: 'en-US', 87 text: 'English', 88 }, 89 { 90 value: 'es', 91 text: 'Español', 92 }, 93 { 94 value: 'ru-RU', 95 text: 'Русский', 96 }, 97 ], 98 }; 99 }, 100 computed: { 101 authError() { 102 return this.$store.getters['authentication/authError']; 103 }, 104 }, 105 validations: { 106 userInfo: { 107 username: { 108 required, 109 }, 110 password: { 111 required, 112 }, 113 }, 114 }, 115 methods: { 116 login: function () { 117 this.$v.$touch(); 118 if (this.$v.$invalid) return; 119 this.disableSubmitButton = true; 120 const username = this.userInfo.username; 121 const password = this.userInfo.password; 122 this.$store 123 .dispatch('authentication/login', { username, password }) 124 .then(() => { 125 localStorage.setItem('storedLanguage', i18n.locale); 126 localStorage.setItem('storedUsername', username); 127 this.$store.commit('global/setUsername', username); 128 this.$store.commit('global/setLanguagePreference', i18n.locale); 129 return this.$store.dispatch( 130 'authentication/checkPasswordChangeRequired', 131 username 132 ); 133 }) 134 .then((passwordChangeRequired) => { 135 if (passwordChangeRequired) { 136 this.$router.push('/change-password'); 137 } else { 138 this.$router.push('/'); 139 } 140 }) 141 .catch((error) => console.log(error)) 142 .finally(() => (this.disableSubmitButton = false)); 143 }, 144 }, 145}; 146</script> 147