UNPKG

ldx-widgets

Version:

widgets

229 lines (215 loc) 7.89 kB
(function() { var CheckboxInput, ENTER, MAX_PASSWORD_LENGTH, MIN_PASSWORD_LENGTH, PasswordInput, REMOVED_REQUIREMENTS, React, TextInput, _, div, h4, li, owasp, ref, span, ul; React = require('react'); _ = require('lodash'); owasp = require('owasp-password-strength-test'); TextInput = React.createFactory(require('./text_input')); CheckboxInput = React.createFactory(require('./checkbox_input')); ENTER = require('../constants/keyboard').ENTER; ref = React.DOM, div = ref.div, li = ref.li, h4 = ref.h4, ul = ref.ul, span = ref.span; MIN_PASSWORD_LENGTH = 6; MAX_PASSWORD_LENGTH = 15; REMOVED_REQUIREMENTS = [2, 6]; PasswordInput = React.createClass({ displayName: 'PasswordInput', propTypes: { onChange: React.PropTypes.func }, getInitialState: function() { var test; owasp.config({ minLength: MIN_PASSWORD_LENGTH, maxLength: MAX_PASSWORD_LENGTH, isPassphrase: false }); test = owasp.test(''); return { passwordTest: test, passwordRequirements: this.buildTestRequirements(test), currentPassword: null, confirmPassword: null }; }, getDefaultProps: function() { return { onChange: function() {}, inputColumnClass: 'col-3-12', requirementsColumnClass: 'col-3-12', confirmColumnClass: 'col-3-12', className: 'grid grid-pad', compact: false, focusOnMount: false }; }, isValid: function() { var confirm, current; current = this.refs.input.getValue(); if (this.refs.inputConfirm != null) { confirm = this.refs.inputConfirm.getValue(); } return (confirm != null ? confirm.length : void 0) && confirm === current && this.state.passwordTest.failedTests.length === 0; }, render: function() { var className, compact, confirmColumnClass, confirmField, confirmPassword, currentPassword, focusOnMount, inputColumnClass, isNewUser, passingTest, passwordErrors, passwordFailures, passwordRequirements, passwordTest, passwordsMatch, ref1, ref2, requirementsColumnClass, requirementsEls, resetPass; ref1 = this.props, isNewUser = ref1.isNewUser, resetPass = ref1.resetPass, focusOnMount = ref1.focusOnMount, inputColumnClass = ref1.inputColumnClass, requirementsColumnClass = ref1.requirementsColumnClass, confirmColumnClass = ref1.confirmColumnClass, className = ref1.className, compact = ref1.compact; ref2 = this.state, passwordTest = ref2.passwordTest, currentPassword = ref2.currentPassword, confirmPassword = ref2.confirmPassword, passwordRequirements = ref2.passwordRequirements; passwordsMatch = currentPassword === confirmPassword; passwordFailures = passwordTest.failedTests; passwordErrors = passwordTest.errors; passingTest = (passwordFailures != null ? passwordFailures.length : void 0) === 0; if (passwordFailures && passwordFailures.length === 0) { passingTest = true; } confirmField = TextInput({ key: 'inputConfirm', ref: 'inputConfirm', type: 'password', autoComplete: this.props.autoComplete, tabIndex: this.props.tabIndex, placeholder: t('Confirm Password'), onChange: this.testConfirmPassword, wrapperClass: compact ? 'password-confirm' : null, value: confirmPassword, onKeyUp: this.handleKeyUp, disabled: !passingTest }); requirementsEls = passwordRequirements.concat([ passingTest ? li({ key: 'passMatch', className: 'req-item' }, [ span({ key: 'match-icon', className: "icon-status " + (passwordsMatch ? 'success' : 'error') }), span({ key: 'match-text', className: 'req-text' }, t('Passwords match')) ]) : void 0 ]); return div({ className: className }, [ div({ key: 'inputs', className: inputColumnClass }, [ TextInput({ placeholder: t('Password'), ref: 'input', key: 'input', type: 'password', onChange: this.testCurrentPassword, tabIndex: this.props.tabIndex }), compact ? confirmField : void 0 ]), !compact ? div({ key: 'confirm', className: confirmColumnClass }, confirmField) : void 0, div({ key: 'requirements', className: requirementsColumnClass }, [ h4({ key: 'pass-req-header', className: 'password-reqs-header' }, (t('Password requirements')) + ":"), ul({ key: 'pass-reqs', className: 'password-reqs' }, requirementsEls) ]) ]); }, componentDidMount: function() { if (this.props.focusOnMount) { return this.refs.input.focus(); } }, getValue: function() { var confirmPassword, currentPassword, passingTest, passwordFailures, passwordTest, passwordsMatch, ref1; ref1 = this.state, passwordTest = ref1.passwordTest, currentPassword = ref1.currentPassword, confirmPassword = ref1.confirmPassword; passwordsMatch = currentPassword === confirmPassword; passwordFailures = passwordTest.failedTests; passingTest = (passwordFailures != null ? passwordFailures.length : void 0) === 0; if (!passwordsMatch || !passingTest) { return ''; } else { return confirmPassword; } }, handleKeyUp: function(e) { var base; if (e.keyCode !== ENTER) { return; } if (this.isValid()) { return typeof (base = this.props).handleKeyUp === "function" ? base.handleKeyUp() : void 0; } }, buildTestRequirements: function(test) { var errors, failedTestErrors, failedTests, i, index, key, len, passwordRequirements, req, status, val; failedTestErrors = { 0: t("At least __minLength__ characters", { minLength: MIN_PASSWORD_LENGTH }), 3: t("At least __count__ lowercase letter", { count: 1 }), 4: t("At least __count__ uppercase letter", { count: 1 }), 5: t("At least __count__ number", { count: 1 }) }; passwordRequirements = []; failedTests = test.failedTests, errors = test.errors; for (i = 0, len = REMOVED_REQUIREMENTS.length; i < len; i++) { req = REMOVED_REQUIREMENTS[i]; index = failedTests != null ? failedTests.indexOf(req) : void 0; if (index > -1) { failedTests.splice(index, 1); } if (index > -1) { errors.splice(index, 1); } } for (key in failedTestErrors) { val = failedTestErrors[key]; status = failedTests.indexOf(+key) > -1 ? 'error' : 'success'; passwordRequirements.push(li({ key: key, className: 'req-item' }, [ span({ key: 'status', className: "icon-status " + status }, null), span({ key: 'val', className: 'req-text' }, val) ])); } return passwordRequirements; }, testCurrentPassword: function(e) { var test, value; value = this.refs.input.getValue(); test = owasp.test(value); return this.setState({ passwordTest: test, currentPassword: value, passwordRequirements: this.buildTestRequirements(test) }); }, testConfirmPassword: function(e) { var value; value = this.refs.inputConfirm.getValue(); return this.setState({ confirmPassword: value }, function() { return this.props.onChange(); }); } }); module.exports = PasswordInput; }).call(this);