Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

[CCR] Show remote cluster validation in CCR forms, and add edit follower index #28778

Merged
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
29 commits
Select commit Hold shift + click to select a range
298803d
[CCR] Advanced settings component
sebelga Jan 8, 2019
5d81b44
Remove preview active on toggle settings
sebelga Jan 8, 2019
0094099
Add client side validation of advanced settings form
sebelga Jan 9, 2019
a2f6bea
Move form entry row to separate component
sebelga Jan 9, 2019
842f88a
Add title to panel
sebelga Jan 9, 2019
5211cf5
Add i18n translation of advanced settings
sebelga Jan 9, 2019
dd9b8bf
Update Follower index form with toggle for advanced settings
sebelga Jan 10, 2019
4530329
Add server side serialisation for advanced settings
sebelga Jan 10, 2019
72c266b
Make code review changes
sebelga Jan 11, 2019
ae4762f
Merge branch 'feature/ccr' into feature/ccr_follower_advanced_settings
sebelga Jan 11, 2019
cb1467d
Merge branch 'feature/ccr' into feature/ccr_follower_advanced_settings
sebelga Jan 12, 2019
f6360ea
Fix test: mock constant dependency
sebelga Jan 13, 2019
5fdd053
Merge branch 'feature/ccr' into feature/ccr_follower_advanced_settings
sebelga Jan 14, 2019
9aaab0e
Add section to edit follower index
sebelga Jan 11, 2019
7c7eb75
Show confirm modal before updating follower index
sebelga Jan 11, 2019
958b77f
Add edit icon in table + update server endpoint to pause / resume
sebelga Jan 14, 2019
9d9a959
[CCR] Show remote cluster validation in follower index form & auto-fo…
sebelga Jan 15, 2019
f45553a
Merge remote-tracking branch 'upstream/feature/ccr' into feature/ccr_…
jen-huang Jan 17, 2019
3ae6be7
PR feedback, cleanup form sizes, add redirect to edit remote cluster
jen-huang Jan 17, 2019
df3107f
Fix routing, remove unused code, adjust auto follow pattern edit load…
jen-huang Jan 17, 2019
8d6293c
Merge remote-tracking branch 'upstream/feature/ccr_seb-temp-2' into f…
jen-huang Jan 18, 2019
da359c8
Adjust error messages and make remote cluster not found edit page the…
jen-huang Jan 18, 2019
e3c20a5
Merge remote-tracking branch 'upstream/feature/ccr' into feature/ccr_…
jen-huang Jan 18, 2019
91e9978
Fix functionality as result of merge
jen-huang Jan 18, 2019
c95982b
Fix validation, reorder actions, fix tests, and address feedback
jen-huang Jan 18, 2019
844df58
PR feedback and fix validation pt 2
jen-huang Jan 18, 2019
6082bf5
Adjust remote cluster validation
jen-huang Jan 19, 2019
8189efe
Fix i18n
jen-huang Jan 22, 2019
10c0a19
Fix api error not showing on add follower form
jen-huang Jan 22, 2019
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 2 additions & 0 deletions x-pack/plugins/cross_cluster_replication/public/app/app.js
Original file line number Diff line number Diff line change
Expand Up @@ -16,6 +16,7 @@ import {
AutoFollowPatternAdd,
AutoFollowPatternEdit,
FollowerIndexAdd,
FollowerIndexEdit,
} from './sections';

export class App extends Component {
Expand Down Expand Up @@ -54,6 +55,7 @@ export class App extends Component {
<Route exact path={`${BASE_PATH}/auto_follow_patterns/add`} component={AutoFollowPatternAdd} />
<Route exact path={`${BASE_PATH}/auto_follow_patterns/edit/:id`} component={AutoFollowPatternEdit} />
<Route exact path={`${BASE_PATH}/follower_indices/add`} component={FollowerIndexAdd} />
<Route exact path={`${BASE_PATH}/follower_indices/edit/:id`} component={FollowerIndexEdit} />
<Route exact path={`${BASE_PATH}/:section`} component={CrossClusterReplicationHome} />
</Switch>
</div>
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -26,32 +26,26 @@ import {
EuiSpacer,
EuiText,
EuiTitle,
EuiSuperSelect,
} from '@elastic/eui';

import { INDEX_PATTERN_ILLEGAL_CHARACTERS_VISIBLE } from 'ui/index_patterns';
import { INDEX_ILLEGAL_CHARACTERS_VISIBLE } from 'ui/indices';

import routing from '../services/routing';
import { extractQueryParams } from '../services/query_params';
import { getRemoteClusterName } from '../services/get_remote_cluster_name';
import { API_STATUS } from '../constants';
import { SectionError, AutoFollowPatternIndicesPreview } from './';
import { SectionError } from './section_error';
import { AutoFollowPatternIndicesPreview } from './auto_follow_pattern_indices_preview';
import { RemoteClustersFormField } from './remote_clusters_form_field';
import { validateAutoFollowPattern, validateLeaderIndexPattern } from '../services/auto_follow_pattern_validators';

const indexPatternIllegalCharacters = INDEX_PATTERN_ILLEGAL_CHARACTERS_VISIBLE.join(' ');
const indexNameIllegalCharacters = INDEX_ILLEGAL_CHARACTERS_VISIBLE.join(' ');

const getFirstConnectedCluster = (clusters) => {
for (let i = 0; i < clusters.length; i++) {
if (clusters[i].isConnected) {
return clusters[i];
}
}
return {};
};

const getEmptyAutoFollowPattern = (remoteClusters) => ({
const getEmptyAutoFollowPattern = (remoteClusterName = '') => ({
name: '',
remoteCluster: getFirstConnectedCluster(remoteClusters).name,
remoteCluster: remoteClusterName,
leaderIndexPatterns: [],
followIndexPatternPrefix: '',
followIndexPatternSuffix: '',
Expand All @@ -70,16 +64,19 @@ export class AutoFollowPatternFormUI extends PureComponent {
autoFollowPattern: PropTypes.object,
apiError: PropTypes.object,
apiStatus: PropTypes.string.isRequired,
remoteClusters: PropTypes.array.isRequired,
currentUrl: PropTypes.string.isRequired,
remoteClusters: PropTypes.array,
}

constructor(props) {
super(props);

const isNew = this.props.autoFollowPattern === undefined;

const { route: { location: { search } } } = routing.reactRouter;
const queryParams = extractQueryParams(search);
const remoteClusterName = getRemoteClusterName(this.props.remoteClusters, queryParams.cluster);
const autoFollowPattern = isNew
? getEmptyAutoFollowPattern(this.props.remoteClusters)
? getEmptyAutoFollowPattern(remoteClusterName)
: {
...this.props.autoFollowPattern,
};
Expand All @@ -101,9 +98,11 @@ export class AutoFollowPatternFormUI extends PureComponent {
}));

const errors = validateAutoFollowPattern(fields);
this.setState(({ fieldsErrors }) => updateFormErrors(errors, fieldsErrors));
this.onFieldsErrorChange(errors);
};

onFieldsErrorChange = (errors) => this.setState(({ fieldsErrors }) => updateFormErrors(errors, fieldsErrors));

onClusterChange = (remoteCluster) => {
this.onFieldsChange({ remoteCluster });
};
Expand Down Expand Up @@ -169,8 +168,8 @@ export class AutoFollowPatternFormUI extends PureComponent {

this.setState(({ fieldsErrors }) => updateFormErrors(errors, fieldsErrors));
} else {
this.setState(({ fieldsErrors, autoFollowPattern }) => {
const errors = validateAutoFollowPattern(autoFollowPattern);
this.setState(({ fieldsErrors, autoFollowPattern: { leaderIndexPatterns } }) => {
const errors = validateAutoFollowPattern({ leaderIndexPatterns });
return updateFormErrors(errors, fieldsErrors);
});
}
Expand All @@ -187,7 +186,7 @@ export class AutoFollowPatternFormUI extends PureComponent {
};

isFormValid() {
return Object.values(this.state.fieldsErrors).every(error => error === null);
return Object.values(this.state.fieldsErrors).every(error => error === undefined || error === null);
}

sendForm = () => {
Expand Down Expand Up @@ -293,12 +292,24 @@ export class AutoFollowPatternFormUI extends PureComponent {
* Remote Cluster
*/
const renderRemoteClusterField = () => {
const remoteClustersOptions = this.props.remoteClusters.map(({ name, isConnected }) => ({
value: name,
inputDisplay: isConnected ? name : `${name} (not connected)`,
disabled: !isConnected,
'data-test-subj': `option-${name}`
}));
const { remoteClusters, currentUrl } = this.props;

const errorMessages = {
noClusterFound: () => (<FormattedMessage
id="xpack.crossClusterReplication.autoFollowPatternForm.emptyRemoteClustersCallOutDescription"
defaultMessage="Auto-follow patterns capture indices on remote clusters. You must add a remote cluster."
/>),
remoteClusterNotConnectedNotEditable: () => (<FormattedMessage
id="xpack.crossClusterReplication.autoFollowPatternForm.currentRemoteClusterNotConnectedCallOutDescription"
defaultMessage="You need to connect it before editing this auto-follow pattern. Edit the remote cluster to
fix the problem."
/>),
remoteClusterDoesNotExist: () => (<FormattedMessage
id="xpack.crossClusterReplication.autoFollowPatternForm.currentRemoteClusterNotFoundCallOutDescription"
defaultMessage="It might have been removed. In order to edit this auto-follow pattern,
you need to add a remote cluster with the same name."
/>)
};

return (
<EuiDescribedFormGroup
Expand All @@ -320,32 +331,16 @@ export class AutoFollowPatternFormUI extends PureComponent {
)}
fullWidth
>
<EuiFormRow
label={(
<FormattedMessage
id="xpack.crossClusterReplication.autoFollowPatternForm.remoteCluster.fieldClusterLabel"
defaultMessage="Remote cluster"
/>
)}
fullWidth
>
<Fragment>
{ isNew && (
<EuiSuperSelect
options={remoteClustersOptions}
valueOfSelected={remoteCluster}
onChange={this.onClusterChange}
/>
)}
{ !isNew && (
<EuiFieldText
value={remoteCluster}
fullWidth
disabled={true}
/>
)}
</Fragment>
</EuiFormRow>
<RemoteClustersFormField
selected={remoteCluster ? remoteCluster : null}
remoteClusters={remoteClusters}
currentUrl={currentUrl}
isEditable={isNew}
areErrorsVisible={areErrorsVisible}
onChange={this.onClusterChange}
onError={(error) => this.onFieldsErrorChange({ remoteCluster: error })}
errorMessages={errorMessages}
/>
</EuiDescribedFormGroup>
);
};
Expand Down Expand Up @@ -435,9 +430,9 @@ export class AutoFollowPatternFormUI extends PureComponent {
};

/**
* Auto-follow pattern
* Auto-follow pattern prefix/suffix
*/
const renderAutoFollowPattern = () => {
const renderAutoFollowPatternPrefixSuffix = () => {
const isPrefixInvalid = areErrorsVisible && !!fieldsErrors.followIndexPatternPrefix;
const isSuffixInvalid = areErrorsVisible && !!fieldsErrors.followIndexPatternSuffix;

Expand Down Expand Up @@ -625,7 +620,7 @@ export class AutoFollowPatternFormUI extends PureComponent {
{renderAutoFollowPatternName()}
{renderRemoteClusterField()}
{renderLeaderIndexPatterns()}
{renderAutoFollowPattern()}
{renderAutoFollowPatternPrefixSuffix()}
</EuiForm>
{renderFormErrorWarning()}
<EuiSpacer size="l" />
Expand Down
Loading