Login.jsx 7.6KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209
  1. import React from 'react'
  2. import { connect } from 'react-redux'
  3. import { withRouter, Redirect } from 'react-router'
  4. import { translate } from 'react-i18next'
  5. import LoginLogo from '../component/Login/LoginLogo.jsx'
  6. import LoginLogoImg from '../img/logoTracimWhite.svg'
  7. import Card from '../component/common/Card/Card.jsx'
  8. import CardHeader from '../component/common/Card/CardHeader.jsx'
  9. import CardBody from '../component/common/Card/CardBody.jsx'
  10. import InputGroupText from '../component/common/Input/InputGroupText.jsx'
  11. import Button from '../component/common/Input/Button.jsx'
  12. import LoginBtnForgotPw from '../component/Login/LoginBtnForgotPw.jsx'
  13. import {
  14. newFlashMessage,
  15. setUserConnected,
  16. setWorkspaceList,
  17. setWorkspaceListIsOpenInSidebar,
  18. setContentTypeList,
  19. setAppList
  20. } from '../action-creator.sync.js'
  21. import {
  22. getAppList,
  23. getContentTypeList,
  24. getWorkspaceList,
  25. postUserLogin
  26. } from '../action-creator.async.js'
  27. import { setCookie, PAGE } from '../helper.js'
  28. import { Checkbox } from 'tracim_frontend_lib'
  29. class Login extends React.Component {
  30. constructor (props) {
  31. super(props)
  32. this.state = {
  33. inputLogin: {
  34. value: '',
  35. isInvalid: false
  36. },
  37. inputPassword: {
  38. value: '',
  39. isInvalid: false
  40. },
  41. inputRememberMe: false
  42. }
  43. }
  44. handleChangeLogin = e => this.setState({inputLogin: {...this.state.inputLogin, value: e.target.value}})
  45. handleChangePassword = e => this.setState({inputPassword: {...this.state.inputPassword, value: e.target.value}})
  46. handleChangeRememberMe = e => {
  47. e.preventDefault()
  48. e.stopPropagation()
  49. this.setState(prev => ({inputRememberMe: !prev.inputRememberMe}))
  50. }
  51. handleInputKeyPress = e => e.key === 'Enter' && this.handleClickSubmit()
  52. handleClickSubmit = async () => {
  53. const { history, dispatch, t } = this.props
  54. const { inputLogin, inputPassword, inputRememberMe } = this.state
  55. const fetchPostUserLogin = await dispatch(postUserLogin(inputLogin.value, inputPassword.value, inputRememberMe))
  56. if (fetchPostUserLogin.status === 200) {
  57. let userAuth = ''
  58. if (inputRememberMe) userAuth = setCookie(inputLogin.value, inputPassword.value, 365)
  59. else userAuth = setCookie(inputLogin.value, inputPassword.value)
  60. const loggedUser = {
  61. ...fetchPostUserLogin.json,
  62. auth: userAuth,
  63. logged: true
  64. }
  65. dispatch(setUserConnected(loggedUser))
  66. this.loadAppConfig(loggedUser)
  67. this.loadWorkspaceList(loggedUser)
  68. history.push(PAGE.WORKSPACE.ROOT)
  69. } else if (fetchPostUserLogin.status === 403) {
  70. dispatch(newFlashMessage(t('Email or password invalid'), 'danger'))
  71. }
  72. }
  73. // @FIXME Côme - 2018/08/22 - this function is duplicated from Tracim.jsx
  74. loadAppConfig = async user => {
  75. const { props } = this
  76. const fetchGetAppList = await props.dispatch(getAppList(user))
  77. if (fetchGetAppList.status === 200) props.dispatch(setAppList(fetchGetAppList.json))
  78. const fetchGetContentTypeList = await props.dispatch(getContentTypeList(user))
  79. if (fetchGetContentTypeList.status === 200) props.dispatch(setContentTypeList(fetchGetContentTypeList.json))
  80. }
  81. // @FIXME Côme - 2018/08/22 - this function is duplicated from Tracim.jsx
  82. loadWorkspaceList = async user => {
  83. const { props } = this
  84. const fetchGetWorkspaceList = await props.dispatch(getWorkspaceList(user))
  85. if (fetchGetWorkspaceList.status === 200) {
  86. props.dispatch(setWorkspaceList(fetchGetWorkspaceList.json))
  87. const idWorkspaceToOpen = (() =>
  88. props.match && props.match.params.idws !== undefined && !isNaN(props.match.params.idws)
  89. ? parseInt(props.match.params.idws)
  90. : fetchGetWorkspaceList.json[0].workspace_id
  91. )()
  92. props.dispatch(setWorkspaceListIsOpenInSidebar(idWorkspaceToOpen, true))
  93. }
  94. }
  95. render () {
  96. if (this.props.user.logged) return <Redirect to={{pathname: '/'}} />
  97. else {
  98. return (
  99. <section className='loginpage primaryColorBg'>
  100. <div className='container-fluid'>
  101. <LoginLogo customClass='loginpage__logo' logoSrc={LoginLogoImg} />
  102. <div className='row justify-content-center'>
  103. <div className='col-12 col-sm-11 col-md-8 col-lg-6 col-xl-4'>
  104. <Card customClass='loginpage__connection'>
  105. <CardHeader customClass='connection__header primaryColorBgLighten text-center'>{this.props.t('Connection')}</CardHeader>
  106. <CardBody formClass='connection__form'>
  107. <div>
  108. <InputGroupText
  109. parentClassName='connection__form__groupemail'
  110. customClass='mb-3 mt-4'
  111. icon='fa-envelope-open-o'
  112. type='email'
  113. placeHolder={this.props.t('Email Adress')}
  114. invalidMsg='Email invalide.'
  115. isInvalid={this.state.inputLogin.isInvalid}
  116. value={this.state.inputLogin.value}
  117. onChange={this.handleChangeLogin}
  118. onKeyPress={this.handleInputKeyPress}
  119. />
  120. <InputGroupText
  121. parentClassName='connection__form__groupepw'
  122. customClass=''
  123. icon='fa-lock'
  124. type='password'
  125. placeHolder={this.props.t('Password')}
  126. invalidMsg='Mot de passe invalide.'
  127. isInvalid={this.state.inputPassword.isInvalid}
  128. value={this.state.inputPassword.value}
  129. onChange={this.handleChangePassword}
  130. onKeyPress={this.handleInputKeyPress}
  131. />
  132. <div className='row align-items-center mt-4 mb-4'>
  133. <div className='col-12 col-sm-6 col-md-6 col-lg-6 col-xl-6'>
  134. <div className='connection__form__rememberme' onClick={this.handleChangeRememberMe}>
  135. <Checkbox
  136. name='inputRememberMe'
  137. checked={this.state.inputRememberMe}
  138. onClickCheckbox={() => {}}
  139. />
  140. Se souvenir de moi
  141. </div>
  142. <LoginBtnForgotPw
  143. customClass='connection__form__pwforgot'
  144. label={this.props.t('Forgotten password ?')}
  145. />
  146. </div>
  147. <div className='col-6 col-sm-6 col-md-6 col-lg-6 col-xl-6'>
  148. <Button
  149. htmlType='button'
  150. bootstrapType='primary'
  151. customClass='connection__form__btnsubmit ml-auto'
  152. label={this.props.t('Connection')}
  153. onClick={this.handleClickSubmit}
  154. />
  155. </div>
  156. </div>
  157. </div>
  158. </CardBody>
  159. </Card>
  160. </div>
  161. </div>
  162. </div>
  163. <footer className='loginpage__footer'>
  164. <div className='loginpage__footer__text d-flex align-items-center flex wrap'>
  165. copyright © 2013 - 2018 <a href='http://www.tracim.fr/' target='_blank' className='ml-3'>tracim.fr</a>
  166. </div>
  167. </footer>
  168. </section>
  169. )
  170. }
  171. }
  172. }
  173. const mapStateToProps = ({ user }) => ({ user })
  174. export default withRouter(connect(mapStateToProps)(translate()(Login)))