+ client: add clients forms validation and cache findClients function

This commit is contained in:
Artem Baskal
2019-12-12 21:48:17 +03:00
parent cddf3ca01e
commit 2e493e0226
16 changed files with 187 additions and 162 deletions

View File

@@ -4,7 +4,7 @@ import { Field, reduxForm } from 'redux-form';
import { withNamespaces, Trans } from 'react-i18next';
import flow from 'lodash/flow';
import { renderField } from '../../../helpers/form';
import { renderInputField } from '../../../helpers/form';
import { RESPONSE_FILTER } from '../../../helpers/constants';
import Tooltip from '../../ui/Tooltip';
@@ -65,7 +65,7 @@ const Form = (props) => {
<Field
id="filter_question_type"
name="filter_question_type"
component={renderField}
component={renderInputField}
type="text"
className="form-control"
placeholder={t('type_table_header')}

View File

@@ -10,7 +10,9 @@ import Tabs from '../../ui/Tabs';
import Examples from '../Dns/Upstream/Examples';
import { toggleAllServices } from '../../../helpers/helpers';
import {
renderField,
required,
clientId,
renderInputField,
renderGroupField,
renderSelectField,
renderServiceField,
@@ -40,38 +42,30 @@ const settingsCheckboxes = [
placeholder: 'enforce_safe_search',
},
];
const validate = (values) => {
const errors = {};
const { name, ids } = values;
if (!name || !name.length) {
errors.name = i18n.t('form_error_required');
}
errors.name = required(name);
if (ids && ids.length) {
const idArrayErrors = [];
ids.forEach((id, idx) => {
if (!id || !id.length) {
idArrayErrors[idx] = i18n.t('form_error_required');
}
idArrayErrors[idx] = required(id) || clientId(id);
});
if (idArrayErrors.length) {
errors.ids = idArrayErrors;
}
}
return errors;
};
const renderFields = (placeholder, buttonTitle) =>
const renderFieldsWrapper = (placeholder, buttonTitle) =>
function cell(row) {
const {
fields,
meta: { error },
} = row;
return (
<div className="form__group">
{fields.map((ip, index) => (
@@ -84,6 +78,7 @@ const renderFields = (placeholder, buttonTitle) =>
placeholder={placeholder}
isActionAvailable={index !== 0}
removeField={() => fields.remove(index)}
normalize={data => data && data.trim()}
/>
</div>
))}
@@ -97,11 +92,13 @@ const renderFields = (placeholder, buttonTitle) =>
<use xlinkHref="#plus" />
</svg>
</button>
{error && <div className="error">{error}</div>}
</div>
);
};
// Should create function outside of component to prevent component re-renders
const renderFields = renderFieldsWrapper(i18n.t('form_enter_id'), i18n.t('form_add_id'));
let Form = (props) => {
const {
t,
@@ -126,10 +123,11 @@ let Form = (props) => {
<Field
id="name"
name="name"
component={renderField}
component={renderInputField}
type="text"
className="form-control"
placeholder={t('form_client_name')}
normalize={data => data && data.trim()}
/>
</div>
@@ -155,7 +153,7 @@ let Form = (props) => {
<div className="form__group">
<FieldArray
name="ids"
component={renderFields(t('form_enter_id'), t('form_add_id'))}
component={renderFields}
/>
</div>
</div>

View File

@@ -5,7 +5,7 @@ import { Field, reduxForm, formValueSelector } from 'redux-form';
import { Trans, withNamespaces } from 'react-i18next';
import flow from 'lodash/flow';
import { renderField, required, ipv4, isPositive, toNumber } from '../../../helpers/form';
import { renderInputField, required, ipv4, isPositive, toNumber } from '../../../helpers/form';
const renderInterfaces = (interfaces => (
Object.keys(interfaces).map((item) => {
@@ -116,8 +116,9 @@ let Form = (props) => {
<div className="form__group form__group--settings">
<label>{t('dhcp_form_gateway_input')}</label>
<Field
id="gateway_ip"
name="gateway_ip"
component={renderField}
component={renderInputField}
type="text"
className="form-control"
placeholder={t('dhcp_form_gateway_input')}
@@ -127,8 +128,9 @@ let Form = (props) => {
<div className="form__group form__group--settings">
<label>{t('dhcp_form_subnet_input')}</label>
<Field
id="subnet_mask"
name="subnet_mask"
component={renderField}
component={renderInputField}
type="text"
className="form-control"
placeholder={t('dhcp_form_subnet_input')}
@@ -144,8 +146,9 @@ let Form = (props) => {
</div>
<div className="col">
<Field
id="range_start"
name="range_start"
component={renderField}
component={renderInputField}
type="text"
className="form-control"
placeholder={t('dhcp_form_range_start')}
@@ -154,8 +157,9 @@ let Form = (props) => {
</div>
<div className="col">
<Field
id="range_end"
name="range_end"
component={renderField}
component={renderInputField}
type="text"
className="form-control"
placeholder={t('dhcp_form_range_end')}
@@ -168,7 +172,7 @@ let Form = (props) => {
<label>{t('dhcp_form_lease_title')}</label>
<Field
name="lease_duration"
component={renderField}
component={renderInputField}
type="number"
className="form-control"
placeholder={t('dhcp_form_lease_input')}

View File

@@ -4,7 +4,7 @@ import { Field, reduxForm } from 'redux-form';
import { Trans, withNamespaces } from 'react-i18next';
import flow from 'lodash/flow';
import { renderField, ipv4, mac, required } from '../../../../helpers/form';
import { renderInputField, ipv4, mac, required } from '../../../../helpers/form';
const Form = (props) => {
const {
@@ -24,7 +24,7 @@ const Form = (props) => {
<Field
id="mac"
name="mac"
component={renderField}
component={renderInputField}
type="text"
className="form-control"
placeholder={t('form_enter_mac')}
@@ -35,7 +35,7 @@ const Form = (props) => {
<Field
id="ip"
name="ip"
component={renderField}
component={renderInputField}
type="text"
className="form-control"
placeholder={t('form_enter_ip')}
@@ -46,7 +46,7 @@ const Form = (props) => {
<Field
id="hostname"
name="hostname"
component={renderField}
component={renderInputField}
type="text"
className="form-control"
placeholder={t('form_enter_hostname')}

View File

@@ -3,6 +3,7 @@ import PropTypes from 'prop-types';
import { Field, reduxForm } from 'redux-form';
import { Trans, withNamespaces } from 'react-i18next';
import flow from 'lodash/flow';
import { renderTextareaField } from '../../../../helpers/form';
const Form = (props) => {
const {
@@ -21,7 +22,7 @@ const Form = (props) => {
<Field
id="allowed_clients"
name="allowed_clients"
component="textarea"
component={renderTextareaField}
type="text"
className="form-control form-control--textarea"
disabled={processingSet}
@@ -37,7 +38,7 @@ const Form = (props) => {
<Field
id="disallowed_clients"
name="disallowed_clients"
component="textarea"
component={renderTextareaField}
type="text"
className="form-control form-control--textarea"
disabled={processingSet}
@@ -53,7 +54,7 @@ const Form = (props) => {
<Field
id="blocked_hosts"
name="blocked_hosts"
component="textarea"
component={renderTextareaField}
type="text"
className="form-control form-control--textarea"
disabled={processingSet}
@@ -81,6 +82,7 @@ Form.propTypes = {
initialValues: PropTypes.object.isRequired,
processingSet: PropTypes.bool.isRequired,
t: PropTypes.func.isRequired,
textarea: PropTypes.bool,
};
export default flow([withNamespaces(), reduxForm({ form: 'accessForm' })])(Form);

View File

@@ -4,7 +4,7 @@ import { Field, reduxForm } from 'redux-form';
import { Trans, withNamespaces } from 'react-i18next';
import flow from 'lodash/flow';
import { renderField, required, domain, answer } from '../../../../helpers/form';
import { renderInputField, required, domain, answer } from '../../../../helpers/form';
const Form = (props) => {
const {
@@ -24,7 +24,7 @@ const Form = (props) => {
<Field
id="domain"
name="domain"
component={renderField}
component={renderInputField}
type="text"
className="form-control"
placeholder={t('form_domain')}
@@ -35,7 +35,7 @@ const Form = (props) => {
<Field
id="answer"
name="answer"
component={renderField}
component={renderInputField}
type="text"
className="form-control"
placeholder={t('form_answer')}

View File

@@ -6,7 +6,7 @@ import { Trans, withNamespaces } from 'react-i18next';
import flow from 'lodash/flow';
import {
renderField,
renderInputField,
renderSelectField,
renderRadioField,
toNumber,
@@ -117,7 +117,7 @@ let Form = (props) => {
<Field
id="server_name"
name="server_name"
component={renderField}
component={renderInputField}
type="text"
className="form-control"
placeholder={t('encryption_server_enter')}
@@ -154,7 +154,7 @@ let Form = (props) => {
<Field
id="port_https"
name="port_https"
component={renderField}
component={renderInputField}
type="number"
className="form-control"
placeholder={t('encryption_https')}
@@ -176,7 +176,7 @@ let Form = (props) => {
<Field
id="port_dns_over_tls"
name="port_dns_over_tls"
component={renderField}
component={renderInputField}
type="number"
className="form-control"
placeholder={t('encryption_dot')}
@@ -252,7 +252,7 @@ let Form = (props) => {
<Field
id="certificate_path"
name="certificate_path"
component={renderField}
component={renderInputField}
type="text"
className="form-control"
placeholder={t('encryption_certificate_path')}
@@ -321,7 +321,7 @@ let Form = (props) => {
<Field
id="private_key_path"
name="private_key_path"
component={renderField}
component={renderInputField}
type="text"
className="form-control"
placeholder={t('encryption_private_key_path')}