mirror of
https://github.com/elastic/kibana.git
synced 2025-04-24 09:48:58 -04:00
[Security Solution][Endpoint][Admin] Refactor policy details protections (#94970)
This commit is contained in:
parent
55e513364a
commit
3998a83871
10 changed files with 488 additions and 632 deletions
|
@ -120,6 +120,12 @@ export type RansomwareProtectionOSes = KeysByValueCriteria<
|
|||
{ ransomware: ProtectionFields }
|
||||
>;
|
||||
|
||||
export type PolicyProtection =
|
||||
| keyof Pick<UIPolicyConfig['windows'], 'malware' | 'ransomware'>
|
||||
| keyof Pick<UIPolicyConfig['mac'], 'malware'>;
|
||||
|
||||
export type MacPolicyProtection = keyof Pick<UIPolicyConfig['mac'], 'malware'>;
|
||||
|
||||
export interface GetPolicyListResponse extends GetPackagePoliciesResponse {
|
||||
items: PolicyData[];
|
||||
}
|
||||
|
|
|
@ -0,0 +1,91 @@
|
|||
/*
|
||||
* Copyright Elasticsearch B.V. and/or licensed to Elasticsearch B.V. under one
|
||||
* or more contributor license agreements. Licensed under the Elastic License
|
||||
* 2.0; you may not use this file except in compliance with the Elastic License
|
||||
* 2.0.
|
||||
*/
|
||||
|
||||
import React, { useCallback, useMemo } from 'react';
|
||||
import { useDispatch } from 'react-redux';
|
||||
import { cloneDeep } from 'lodash';
|
||||
import { htmlIdGenerator, EuiRadio } from '@elastic/eui';
|
||||
import {
|
||||
ImmutableArray,
|
||||
ProtectionModes,
|
||||
UIPolicyConfig,
|
||||
} from '../../../../../../../common/endpoint/types';
|
||||
import { MacPolicyProtection, PolicyProtection } from '../../../types';
|
||||
import { usePolicyDetailsSelector } from '../../policy_hooks';
|
||||
import { policyConfig } from '../../../store/policy_details/selectors';
|
||||
import { AppAction } from '../../../../../../common/store/actions';
|
||||
import { useLicense } from '../../../../../../common/hooks/use_license';
|
||||
|
||||
export const ProtectionRadio = React.memo(
|
||||
({
|
||||
protection,
|
||||
protectionMode,
|
||||
osList,
|
||||
label,
|
||||
}: {
|
||||
protection: PolicyProtection;
|
||||
protectionMode: ProtectionModes;
|
||||
osList: ImmutableArray<Partial<keyof UIPolicyConfig>>;
|
||||
label: string;
|
||||
}) => {
|
||||
const policyDetailsConfig = usePolicyDetailsSelector(policyConfig);
|
||||
const dispatch = useDispatch<(action: AppAction) => void>();
|
||||
const radioButtonId = useMemo(() => htmlIdGenerator()(), []);
|
||||
const selected = policyDetailsConfig && policyDetailsConfig.windows[protection].mode;
|
||||
const isPlatinumPlus = useLicense().isPlatinumPlus();
|
||||
|
||||
const handleRadioChange = useCallback(() => {
|
||||
if (policyDetailsConfig) {
|
||||
const newPayload = cloneDeep(policyDetailsConfig);
|
||||
for (const os of osList) {
|
||||
if (os === 'windows') {
|
||||
newPayload[os][protection].mode = protectionMode;
|
||||
} else if (os === 'mac') {
|
||||
newPayload[os][protection as MacPolicyProtection].mode = protectionMode;
|
||||
}
|
||||
if (isPlatinumPlus) {
|
||||
if (os === 'windows') {
|
||||
if (protectionMode === ProtectionModes.prevent) {
|
||||
newPayload[os].popup[protection].enabled = true;
|
||||
} else {
|
||||
newPayload[os].popup[protection].enabled = false;
|
||||
}
|
||||
} else if (os === 'mac') {
|
||||
if (protectionMode === ProtectionModes.prevent) {
|
||||
newPayload[os].popup[protection as MacPolicyProtection].enabled = true;
|
||||
} else {
|
||||
newPayload[os].popup[protection as MacPolicyProtection].enabled = false;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
dispatch({
|
||||
type: 'userChangedPolicyConfig',
|
||||
payload: { policyConfig: newPayload },
|
||||
});
|
||||
}
|
||||
}, [dispatch, protectionMode, policyDetailsConfig, isPlatinumPlus, osList, protection]);
|
||||
|
||||
/**
|
||||
* Passing an arbitrary id because EuiRadio
|
||||
* requires an id if label is passed
|
||||
*/
|
||||
|
||||
return (
|
||||
<EuiRadio
|
||||
className="policyDetailsProtectionRadio"
|
||||
label={label}
|
||||
id={radioButtonId}
|
||||
checked={selected === protectionMode}
|
||||
onChange={handleRadioChange}
|
||||
disabled={selected === ProtectionModes.off}
|
||||
/>
|
||||
);
|
||||
}
|
||||
);
|
||||
|
||||
ProtectionRadio.displayName = 'ProtectionRadio';
|
|
@ -0,0 +1,100 @@
|
|||
/*
|
||||
* Copyright Elasticsearch B.V. and/or licensed to Elasticsearch B.V. under one
|
||||
* or more contributor license agreements. Licensed under the Elastic License
|
||||
* 2.0; you may not use this file except in compliance with the Elastic License
|
||||
* 2.0.
|
||||
*/
|
||||
|
||||
import React, { useCallback } from 'react';
|
||||
import { useDispatch } from 'react-redux';
|
||||
import { i18n } from '@kbn/i18n';
|
||||
import { EuiSwitch } from '@elastic/eui';
|
||||
import { cloneDeep } from 'lodash';
|
||||
import { useLicense } from '../../../../../../common/hooks/use_license';
|
||||
import { policyConfig } from '../../../store/policy_details/selectors';
|
||||
import { usePolicyDetailsSelector } from '../../policy_hooks';
|
||||
import { AppAction } from '../../../../../../common/store/actions';
|
||||
import {
|
||||
ImmutableArray,
|
||||
ProtectionModes,
|
||||
UIPolicyConfig,
|
||||
} from '../../../../../../../common/endpoint/types';
|
||||
import { PolicyProtection, MacPolicyProtection } from '../../../types';
|
||||
|
||||
export const ProtectionSwitch = React.memo(
|
||||
({
|
||||
protection,
|
||||
osList,
|
||||
}: {
|
||||
protection: PolicyProtection;
|
||||
osList: ImmutableArray<Partial<keyof UIPolicyConfig>>;
|
||||
}) => {
|
||||
const policyDetailsConfig = usePolicyDetailsSelector(policyConfig);
|
||||
const isPlatinumPlus = useLicense().isPlatinumPlus();
|
||||
const dispatch = useDispatch<(action: AppAction) => void>();
|
||||
const selected = policyDetailsConfig && policyDetailsConfig.windows[protection].mode;
|
||||
|
||||
const handleSwitchChange = useCallback(
|
||||
(event) => {
|
||||
if (policyDetailsConfig) {
|
||||
const newPayload = cloneDeep(policyDetailsConfig);
|
||||
if (event.target.checked === false) {
|
||||
for (const os of osList) {
|
||||
if (os === 'windows') {
|
||||
newPayload[os][protection].mode = ProtectionModes.off;
|
||||
} else if (os === 'mac') {
|
||||
newPayload[os][protection as MacPolicyProtection].mode = ProtectionModes.off;
|
||||
}
|
||||
if (isPlatinumPlus) {
|
||||
if (os === 'windows') {
|
||||
newPayload[os].popup[protection].enabled = event.target.checked;
|
||||
} else if (os === 'mac') {
|
||||
newPayload[os].popup[protection as MacPolicyProtection].enabled =
|
||||
event.target.checked;
|
||||
}
|
||||
}
|
||||
}
|
||||
} else {
|
||||
for (const os of osList) {
|
||||
if (os === 'windows') {
|
||||
newPayload[os][protection].mode = ProtectionModes.prevent;
|
||||
} else if (os === 'mac') {
|
||||
newPayload[os][protection as MacPolicyProtection].mode = ProtectionModes.prevent;
|
||||
}
|
||||
if (isPlatinumPlus) {
|
||||
if (os === 'windows') {
|
||||
newPayload[os].popup[protection].enabled = event.target.checked;
|
||||
} else if (os === 'mac') {
|
||||
newPayload[os].popup[protection as MacPolicyProtection].enabled =
|
||||
event.target.checked;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
dispatch({
|
||||
type: 'userChangedPolicyConfig',
|
||||
payload: { policyConfig: newPayload },
|
||||
});
|
||||
}
|
||||
},
|
||||
[dispatch, policyDetailsConfig, isPlatinumPlus, protection, osList]
|
||||
);
|
||||
|
||||
return (
|
||||
<EuiSwitch
|
||||
label={i18n.translate('xpack.securitySolution.endpoint.policy.details.protectionsEnabled', {
|
||||
defaultMessage:
|
||||
'{protectionName} protections {mode, select, true {enabled} false {disabled}}',
|
||||
values: {
|
||||
protectionName: protection.charAt(0).toUpperCase() + protection.substring(1),
|
||||
mode: selected !== ProtectionModes.off,
|
||||
},
|
||||
})}
|
||||
checked={selected !== ProtectionModes.off}
|
||||
onChange={handleSwitchChange}
|
||||
/>
|
||||
);
|
||||
}
|
||||
);
|
||||
|
||||
ProtectionSwitch.displayName = 'ProtectionSwitch';
|
|
@ -0,0 +1,96 @@
|
|||
/*
|
||||
* Copyright Elasticsearch B.V. and/or licensed to Elasticsearch B.V. under one
|
||||
* or more contributor license agreements. Licensed under the Elastic License
|
||||
* 2.0; you may not use this file except in compliance with the Elastic License
|
||||
* 2.0.
|
||||
*/
|
||||
|
||||
import React, { useMemo } from 'react';
|
||||
import { i18n } from '@kbn/i18n';
|
||||
import { FormattedMessage } from '@kbn/i18n/react';
|
||||
import styled from 'styled-components';
|
||||
import { EuiSpacer, EuiFlexItem, EuiFlexGroup } from '@elastic/eui';
|
||||
import {
|
||||
Immutable,
|
||||
ImmutableArray,
|
||||
ProtectionModes,
|
||||
UIPolicyConfig,
|
||||
} from '../../../../../../../common/endpoint/types';
|
||||
import { PolicyProtection } from '../../../types';
|
||||
import { ConfigFormHeading } from '../../components/config_form';
|
||||
import { ProtectionRadio } from './protection_radio';
|
||||
|
||||
export const RadioFlexGroup = styled(EuiFlexGroup)`
|
||||
.no-right-margin-radio {
|
||||
margin-right: 0;
|
||||
}
|
||||
.no-horizontal-margin-radio {
|
||||
margin: ${(props) => props.theme.eui.ruleMargins.marginSmall} 0;
|
||||
}
|
||||
`;
|
||||
|
||||
export const RadioButtons = React.memo(
|
||||
({
|
||||
protection,
|
||||
osList,
|
||||
}: {
|
||||
protection: PolicyProtection;
|
||||
osList: ImmutableArray<Partial<keyof UIPolicyConfig>>;
|
||||
}) => {
|
||||
const radios: Immutable<
|
||||
Array<{
|
||||
id: ProtectionModes;
|
||||
label: string;
|
||||
}>
|
||||
> = useMemo(() => {
|
||||
return [
|
||||
{
|
||||
id: ProtectionModes.detect,
|
||||
label: i18n.translate('xpack.securitySolution.endpoint.policy.details.detect', {
|
||||
defaultMessage: 'Detect',
|
||||
}),
|
||||
},
|
||||
{
|
||||
id: ProtectionModes.prevent,
|
||||
label: i18n.translate('xpack.securitySolution.endpoint.policy.details.prevent', {
|
||||
defaultMessage: 'Prevent',
|
||||
}),
|
||||
},
|
||||
];
|
||||
}, []);
|
||||
|
||||
return (
|
||||
<>
|
||||
<ConfigFormHeading>
|
||||
<FormattedMessage
|
||||
id="xpack.securitySolution.endpoint.policyDetailsConfig.protectionLevel"
|
||||
defaultMessage="Protection Level"
|
||||
/>
|
||||
</ConfigFormHeading>
|
||||
<EuiSpacer size="xs" />
|
||||
<RadioFlexGroup>
|
||||
<EuiFlexItem className="no-right-margin-radio" grow={2}>
|
||||
<ProtectionRadio
|
||||
protection={protection}
|
||||
protectionMode={radios[0].id}
|
||||
osList={osList}
|
||||
key={{ protection } + radios[0].id}
|
||||
label={radios[0].label}
|
||||
/>
|
||||
</EuiFlexItem>
|
||||
<EuiFlexItem className="no-horizontal-margin-radio" grow={5}>
|
||||
<ProtectionRadio
|
||||
protection={protection}
|
||||
protectionMode={radios[1].id}
|
||||
osList={osList}
|
||||
key={{ protection } + radios[1].id}
|
||||
label={radios[1].label}
|
||||
/>
|
||||
</EuiFlexItem>
|
||||
</RadioFlexGroup>
|
||||
</>
|
||||
);
|
||||
}
|
||||
);
|
||||
|
||||
RadioButtons.displayName = 'RadioButtons';
|
|
@ -8,7 +8,7 @@
|
|||
import React from 'react';
|
||||
import { FormattedMessage } from '@kbn/i18n/react';
|
||||
import { EuiText } from '@elastic/eui';
|
||||
import { popupVersionsMap } from './popup_options_to_versions';
|
||||
import { popupVersionsMap } from '../protections/popup_options_to_versions';
|
||||
|
||||
export const SupportedVersionNotice = ({ optionName }: { optionName: string }) => {
|
||||
const version = popupVersionsMap.get(optionName);
|
|
@ -0,0 +1,170 @@
|
|||
/*
|
||||
* Copyright Elasticsearch B.V. and/or licensed to Elasticsearch B.V. under one
|
||||
* or more contributor license agreements. Licensed under the Elastic License
|
||||
* 2.0; you may not use this file except in compliance with the Elastic License
|
||||
* 2.0.
|
||||
*/
|
||||
|
||||
import React, { useCallback } from 'react';
|
||||
import { useDispatch } from 'react-redux';
|
||||
import { i18n } from '@kbn/i18n';
|
||||
import { FormattedMessage } from '@kbn/i18n/react';
|
||||
import { cloneDeep } from 'lodash';
|
||||
import {
|
||||
EuiSpacer,
|
||||
EuiFlexItem,
|
||||
EuiFlexGroup,
|
||||
EuiCheckbox,
|
||||
EuiIconTip,
|
||||
EuiText,
|
||||
EuiTextArea,
|
||||
} from '@elastic/eui';
|
||||
import {
|
||||
ImmutableArray,
|
||||
ProtectionModes,
|
||||
UIPolicyConfig,
|
||||
} from '../../../../../../../common/endpoint/types';
|
||||
import { PolicyProtection, MacPolicyProtection } from '../../../types';
|
||||
import { ConfigFormHeading } from '../../components/config_form';
|
||||
import { usePolicyDetailsSelector } from '../../policy_hooks';
|
||||
import { policyConfig } from '../../../store/policy_details/selectors';
|
||||
import { AppAction } from '../../../../../../common/store/actions';
|
||||
import { SupportedVersionNotice } from './supported_version';
|
||||
|
||||
export const UserNotification = React.memo(
|
||||
({
|
||||
protection,
|
||||
osList,
|
||||
}: {
|
||||
protection: PolicyProtection;
|
||||
osList: ImmutableArray<Partial<keyof UIPolicyConfig>>;
|
||||
}) => {
|
||||
const policyDetailsConfig = usePolicyDetailsSelector(policyConfig);
|
||||
const dispatch = useDispatch<(action: AppAction) => void>();
|
||||
const selected = policyDetailsConfig && policyDetailsConfig.windows[protection].mode;
|
||||
const userNotificationSelected =
|
||||
policyDetailsConfig && policyDetailsConfig.windows.popup[protection].enabled;
|
||||
const userNotificationMessage =
|
||||
policyDetailsConfig && policyDetailsConfig.windows.popup[protection].message;
|
||||
|
||||
const handleUserNotificationCheckbox = useCallback(
|
||||
(event) => {
|
||||
if (policyDetailsConfig) {
|
||||
const newPayload = cloneDeep(policyDetailsConfig);
|
||||
for (const os of osList) {
|
||||
if (os === 'windows') {
|
||||
newPayload[os].popup[protection].enabled = event.target.checked;
|
||||
} else if (os === 'mac') {
|
||||
newPayload[os].popup[protection as MacPolicyProtection].enabled =
|
||||
event.target.checked;
|
||||
}
|
||||
}
|
||||
dispatch({
|
||||
type: 'userChangedPolicyConfig',
|
||||
payload: { policyConfig: newPayload },
|
||||
});
|
||||
}
|
||||
},
|
||||
[policyDetailsConfig, dispatch, protection, osList]
|
||||
);
|
||||
|
||||
const handleCustomUserNotification = useCallback(
|
||||
(event) => {
|
||||
if (policyDetailsConfig) {
|
||||
const newPayload = cloneDeep(policyDetailsConfig);
|
||||
for (const os of osList) {
|
||||
if (os === 'windows') {
|
||||
newPayload[os].popup[protection].message = event.target.value;
|
||||
} else if (os === 'mac') {
|
||||
newPayload[os].popup[protection as MacPolicyProtection].message = event.target.value;
|
||||
}
|
||||
}
|
||||
dispatch({
|
||||
type: 'userChangedPolicyConfig',
|
||||
payload: { policyConfig: newPayload },
|
||||
});
|
||||
}
|
||||
},
|
||||
[policyDetailsConfig, dispatch, protection, osList]
|
||||
);
|
||||
|
||||
return (
|
||||
<>
|
||||
<EuiSpacer size="m" />
|
||||
<ConfigFormHeading>
|
||||
<FormattedMessage
|
||||
id="xpack.securitySolution.endpoint.policyDetailsConfig.userNotification"
|
||||
defaultMessage="User Notification"
|
||||
/>
|
||||
</ConfigFormHeading>
|
||||
<SupportedVersionNotice optionName={protection} />
|
||||
<EuiSpacer size="s" />
|
||||
<EuiCheckbox
|
||||
data-test-subj={`${protection}UserNotificationCheckbox`}
|
||||
id={`${protection}UserNotificationCheckbox}`}
|
||||
onChange={handleUserNotificationCheckbox}
|
||||
checked={userNotificationSelected}
|
||||
disabled={selected === ProtectionModes.off}
|
||||
label={i18n.translate('xpack.securitySolution.endpoint.policyDetail.notifyUser', {
|
||||
defaultMessage: 'Notify User',
|
||||
})}
|
||||
/>
|
||||
{userNotificationSelected && (
|
||||
<>
|
||||
<EuiSpacer size="s" />
|
||||
<EuiFlexGroup gutterSize="s">
|
||||
<EuiFlexItem grow={false}>
|
||||
<EuiText size="xs">
|
||||
<h4>
|
||||
<FormattedMessage
|
||||
id="xpack.securitySolution.endpoint.policyDetailsConfig.customizeUserNotification"
|
||||
defaultMessage="Customize notification message"
|
||||
/>
|
||||
</h4>
|
||||
</EuiText>
|
||||
</EuiFlexItem>
|
||||
<EuiFlexItem grow={false}>
|
||||
<EuiIconTip
|
||||
position="right"
|
||||
data-test-subj={`${protection}Tooltip`}
|
||||
content={
|
||||
<>
|
||||
<FormattedMessage
|
||||
id="xpack.securitySolution.endpoint.policyDetailsConfig.notifyUserTooltip.a"
|
||||
defaultMessage="Selecting the user notification option will display a notification to the host user when { protectionName } is prevented or detected."
|
||||
values={{
|
||||
protectionName: protection,
|
||||
}}
|
||||
/>
|
||||
<EuiSpacer size="m" />
|
||||
<FormattedMessage
|
||||
id="xpack.securitySolution.endpoint.policyDetailsConfig.notifyUserTooltip.b"
|
||||
defaultMessage="
|
||||
The user notification can be customized in the text box below. Bracketed tags can be used to dynamically populate the applicable action (such as prevented or detected) and the filename."
|
||||
/>
|
||||
</>
|
||||
}
|
||||
/>
|
||||
</EuiFlexItem>
|
||||
</EuiFlexGroup>
|
||||
<EuiSpacer size="xs" />
|
||||
<EuiTextArea
|
||||
placeholder={i18n.translate(
|
||||
'xpack.securitySolution.endpoint.policyDetails.userNotification.placeholder',
|
||||
{
|
||||
defaultMessage: 'Input your custom notification message',
|
||||
}
|
||||
)}
|
||||
value={userNotificationMessage}
|
||||
onChange={handleCustomUserNotification}
|
||||
fullWidth={true}
|
||||
data-test-subj={`${protection}UserNotificationCustomMessage`}
|
||||
/>
|
||||
</>
|
||||
)}
|
||||
</>
|
||||
);
|
||||
}
|
||||
);
|
||||
|
||||
UserNotification.displayName = 'UserNotification';
|
|
@ -5,333 +5,29 @@
|
|||
* 2.0.
|
||||
*/
|
||||
|
||||
import React, { useCallback, useMemo } from 'react';
|
||||
import { useDispatch } from 'react-redux';
|
||||
import React from 'react';
|
||||
import { i18n } from '@kbn/i18n';
|
||||
import { FormattedMessage } from '@kbn/i18n/react';
|
||||
import {
|
||||
EuiCallOut,
|
||||
EuiCheckbox,
|
||||
EuiRadio,
|
||||
EuiSpacer,
|
||||
EuiSwitch,
|
||||
EuiText,
|
||||
EuiTextArea,
|
||||
htmlIdGenerator,
|
||||
EuiFlexGroup,
|
||||
EuiFlexItem,
|
||||
EuiIconTip,
|
||||
} from '@elastic/eui';
|
||||
import { cloneDeep } from 'lodash';
|
||||
import styled from 'styled-components';
|
||||
import { EuiCallOut, EuiSpacer } from '@elastic/eui';
|
||||
import { APP_ID } from '../../../../../../../common/constants';
|
||||
import { SecurityPageName } from '../../../../../../app/types';
|
||||
import {
|
||||
Immutable,
|
||||
OperatingSystem,
|
||||
ProtectionModes,
|
||||
} from '../../../../../../../common/endpoint/types';
|
||||
import { Immutable, OperatingSystem } from '../../../../../../../common/endpoint/types';
|
||||
import { MalwareProtectionOSes, OS } from '../../../types';
|
||||
import { ConfigForm, ConfigFormHeading } from '../../components/config_form';
|
||||
import { policyConfig } from '../../../store/policy_details/selectors';
|
||||
import { usePolicyDetailsSelector } from '../../policy_hooks';
|
||||
import { ConfigForm } from '../../components/config_form';
|
||||
import { LinkToApp } from '../../../../../../common/components/endpoint/link_to_app';
|
||||
import { useLicense } from '../../../../../../common/hooks/use_license';
|
||||
import { AppAction } from '../../../../../../common/store/actions';
|
||||
import { SupportedVersionNotice } from './supported_version';
|
||||
|
||||
export const RadioFlexGroup = styled(EuiFlexGroup)`
|
||||
.no-right-margin-radio {
|
||||
margin-right: 0;
|
||||
}
|
||||
.no-horizontal-margin-radio {
|
||||
margin: ${(props) => props.theme.eui.ruleMargins.marginSmall} 0;
|
||||
}
|
||||
`;
|
||||
|
||||
const OSes: Immutable<MalwareProtectionOSes[]> = [OS.windows, OS.mac];
|
||||
const protection = 'malware';
|
||||
|
||||
const ProtectionRadio = React.memo(
|
||||
({ protectionMode, label }: { protectionMode: ProtectionModes; label: string }) => {
|
||||
const policyDetailsConfig = usePolicyDetailsSelector(policyConfig);
|
||||
const dispatch = useDispatch<(action: AppAction) => void>();
|
||||
const radioButtonId = useMemo(() => htmlIdGenerator()(), []);
|
||||
// currently just taking windows.malware, but both windows.malware and mac.malware should be the same value
|
||||
const selected = policyDetailsConfig && policyDetailsConfig.windows.malware.mode;
|
||||
const isPlatinumPlus = useLicense().isPlatinumPlus();
|
||||
|
||||
const handleRadioChange = useCallback(() => {
|
||||
if (policyDetailsConfig) {
|
||||
const newPayload = cloneDeep(policyDetailsConfig);
|
||||
for (const os of OSes) {
|
||||
newPayload[os][protection].mode = protectionMode;
|
||||
if (isPlatinumPlus) {
|
||||
if (protectionMode === ProtectionModes.prevent) {
|
||||
newPayload[os].popup[protection].enabled = true;
|
||||
} else {
|
||||
newPayload[os].popup[protection].enabled = false;
|
||||
}
|
||||
}
|
||||
}
|
||||
dispatch({
|
||||
type: 'userChangedPolicyConfig',
|
||||
payload: { policyConfig: newPayload },
|
||||
});
|
||||
}
|
||||
}, [dispatch, protectionMode, policyDetailsConfig, isPlatinumPlus]);
|
||||
|
||||
/**
|
||||
* Passing an arbitrary id because EuiRadio
|
||||
* requires an id if label is passed
|
||||
*/
|
||||
|
||||
return (
|
||||
<EuiRadio
|
||||
className="policyDetailsProtectionRadio"
|
||||
label={label}
|
||||
id={radioButtonId}
|
||||
checked={selected === protectionMode}
|
||||
onChange={handleRadioChange}
|
||||
disabled={selected === ProtectionModes.off}
|
||||
/>
|
||||
);
|
||||
}
|
||||
);
|
||||
|
||||
ProtectionRadio.displayName = 'ProtectionRadio';
|
||||
import { RadioButtons } from '../components/radio_buttons';
|
||||
import { UserNotification } from '../components/user_notification';
|
||||
import { ProtectionSwitch } from '../components/protection_switch';
|
||||
|
||||
/** The Malware Protections form for policy details
|
||||
* which will configure for all relevant OSes.
|
||||
*/
|
||||
export const MalwareProtections = React.memo(() => {
|
||||
const policyDetailsConfig = usePolicyDetailsSelector(policyConfig);
|
||||
const dispatch = useDispatch<(action: AppAction) => void>();
|
||||
// currently just taking windows.malware, but both windows.malware and mac.malware should be the same value
|
||||
const selected = policyDetailsConfig && policyDetailsConfig.windows.malware.mode;
|
||||
const userNotificationSelected =
|
||||
policyDetailsConfig && policyDetailsConfig.windows.popup.malware.enabled;
|
||||
const userNotificationMessage =
|
||||
policyDetailsConfig && policyDetailsConfig.windows.popup.malware.message;
|
||||
const OSes: Immutable<MalwareProtectionOSes[]> = [OS.windows, OS.mac];
|
||||
const protection = 'malware';
|
||||
const isPlatinumPlus = useLicense().isPlatinumPlus();
|
||||
|
||||
const radios: Immutable<
|
||||
Array<{
|
||||
id: ProtectionModes;
|
||||
label: string;
|
||||
protection: 'malware';
|
||||
}>
|
||||
> = useMemo(() => {
|
||||
return [
|
||||
{
|
||||
id: ProtectionModes.detect,
|
||||
label: i18n.translate('xpack.securitySolution.endpoint.policy.details.detect', {
|
||||
defaultMessage: 'Detect',
|
||||
}),
|
||||
protection: 'malware',
|
||||
},
|
||||
{
|
||||
id: ProtectionModes.prevent,
|
||||
label: i18n.translate('xpack.securitySolution.endpoint.policy.details.prevent', {
|
||||
defaultMessage: 'Prevent',
|
||||
}),
|
||||
protection: 'malware',
|
||||
},
|
||||
];
|
||||
}, []);
|
||||
|
||||
const handleSwitchChange = useCallback(
|
||||
(event) => {
|
||||
if (policyDetailsConfig) {
|
||||
const newPayload = cloneDeep(policyDetailsConfig);
|
||||
if (event.target.checked === false) {
|
||||
for (const os of OSes) {
|
||||
newPayload[os][protection].mode = ProtectionModes.off;
|
||||
if (isPlatinumPlus) {
|
||||
newPayload[os].popup[protection].enabled = event.target.checked;
|
||||
}
|
||||
}
|
||||
} else {
|
||||
for (const os of OSes) {
|
||||
newPayload[os][protection].mode = ProtectionModes.prevent;
|
||||
if (isPlatinumPlus) {
|
||||
newPayload[os].popup[protection].enabled = event.target.checked;
|
||||
}
|
||||
}
|
||||
}
|
||||
dispatch({
|
||||
type: 'userChangedPolicyConfig',
|
||||
payload: { policyConfig: newPayload },
|
||||
});
|
||||
}
|
||||
},
|
||||
[dispatch, policyDetailsConfig, isPlatinumPlus]
|
||||
);
|
||||
|
||||
const handleUserNotificationCheckbox = useCallback(
|
||||
(event) => {
|
||||
if (policyDetailsConfig) {
|
||||
const newPayload = cloneDeep(policyDetailsConfig);
|
||||
for (const os of OSes) {
|
||||
newPayload[os].popup[protection].enabled = event.target.checked;
|
||||
}
|
||||
dispatch({
|
||||
type: 'userChangedPolicyConfig',
|
||||
payload: { policyConfig: newPayload },
|
||||
});
|
||||
}
|
||||
},
|
||||
[policyDetailsConfig, dispatch]
|
||||
);
|
||||
|
||||
const handleCustomUserNotification = useCallback(
|
||||
(event) => {
|
||||
if (policyDetailsConfig) {
|
||||
const newPayload = cloneDeep(policyDetailsConfig);
|
||||
for (const os of OSes) {
|
||||
newPayload[os].popup[protection].message = event.target.value;
|
||||
}
|
||||
dispatch({
|
||||
type: 'userChangedPolicyConfig',
|
||||
payload: { policyConfig: newPayload },
|
||||
});
|
||||
}
|
||||
},
|
||||
[policyDetailsConfig, dispatch]
|
||||
);
|
||||
|
||||
const radioButtons = useMemo(() => {
|
||||
return (
|
||||
<>
|
||||
<ConfigFormHeading>
|
||||
<FormattedMessage
|
||||
id="xpack.securitySolution.endpoint.policyDetailsConfig.protectionLevel"
|
||||
defaultMessage="Protection Level"
|
||||
/>
|
||||
</ConfigFormHeading>
|
||||
<EuiSpacer size="xs" />
|
||||
<RadioFlexGroup>
|
||||
<EuiFlexItem className="no-right-margin-radio" grow={2}>
|
||||
<ProtectionRadio
|
||||
protectionMode={radios[0].id}
|
||||
key={radios[0].protection + radios[0].id}
|
||||
label={radios[0].label}
|
||||
/>
|
||||
</EuiFlexItem>
|
||||
<EuiFlexItem className="no-horizontal-margin-radio" grow={5}>
|
||||
<ProtectionRadio
|
||||
protectionMode={radios[1].id}
|
||||
key={radios[1].protection + radios[1].id}
|
||||
label={radios[1].label}
|
||||
/>
|
||||
</EuiFlexItem>
|
||||
</RadioFlexGroup>
|
||||
{isPlatinumPlus && (
|
||||
<>
|
||||
<EuiSpacer size="m" />
|
||||
<ConfigFormHeading>
|
||||
<FormattedMessage
|
||||
id="xpack.securitySolution.endpoint.policyDetailsConfig.userNotification"
|
||||
defaultMessage="User Notification"
|
||||
/>
|
||||
</ConfigFormHeading>
|
||||
<SupportedVersionNotice optionName="malware" />
|
||||
<EuiSpacer size="s" />
|
||||
<EuiCheckbox
|
||||
data-test-subj="malwareUserNotificationCheckbox"
|
||||
id="xpack.securitySolution.endpoint.policyDetail.malware.userNotification"
|
||||
onChange={handleUserNotificationCheckbox}
|
||||
checked={userNotificationSelected}
|
||||
disabled={selected === ProtectionModes.off}
|
||||
label={i18n.translate(
|
||||
'xpack.securitySolution.endpoint.policyDetail.malware.notifyUser',
|
||||
{
|
||||
defaultMessage: 'Notify User',
|
||||
}
|
||||
)}
|
||||
/>
|
||||
</>
|
||||
)}
|
||||
{isPlatinumPlus && userNotificationSelected && (
|
||||
<>
|
||||
<EuiSpacer size="s" />
|
||||
<EuiFlexGroup gutterSize="s">
|
||||
<EuiFlexItem grow={false}>
|
||||
<EuiText size="xs">
|
||||
<h4>
|
||||
<FormattedMessage
|
||||
id="xpack.securitySolution.endpoint.policyDetailsConfig.customizeUserNotification"
|
||||
defaultMessage="Customize notification message"
|
||||
/>
|
||||
</h4>
|
||||
</EuiText>
|
||||
</EuiFlexItem>
|
||||
<EuiFlexItem grow={false}>
|
||||
<EuiIconTip
|
||||
position="right"
|
||||
data-test-subj="malwareTooltip"
|
||||
content={
|
||||
<>
|
||||
<FormattedMessage
|
||||
id="xpack.securitySolution.endpoint.policyDetailsConfig.malware.notifyUserTooltip.a"
|
||||
defaultMessage="Selecting the user notification option will display a notification to the host user when malware is prevented or detected."
|
||||
/>
|
||||
<EuiSpacer size="m" />
|
||||
<FormattedMessage
|
||||
id="xpack.securitySolution.endpoint.policyDetailsConfig.malware.notifyUserTooltip.b"
|
||||
defaultMessage="
|
||||
The user notification can be customized in the text box below. Bracketed tags can be used to dynamically populate the applicable action (such as prevented or detected) and the filename."
|
||||
/>
|
||||
</>
|
||||
}
|
||||
/>
|
||||
</EuiFlexItem>
|
||||
</EuiFlexGroup>
|
||||
<EuiSpacer size="xs" />
|
||||
<EuiTextArea
|
||||
placeholder={i18n.translate(
|
||||
'xpack.securitySolution.endpoint.policyDetails.malware.userNotification.placeholder',
|
||||
{
|
||||
defaultMessage: 'Input your custom notification message',
|
||||
}
|
||||
)}
|
||||
value={userNotificationMessage}
|
||||
onChange={handleCustomUserNotification}
|
||||
fullWidth={true}
|
||||
data-test-subj="malwareUserNotificationCustomMessage"
|
||||
/>
|
||||
</>
|
||||
)}
|
||||
</>
|
||||
);
|
||||
}, [
|
||||
radios,
|
||||
selected,
|
||||
isPlatinumPlus,
|
||||
handleUserNotificationCheckbox,
|
||||
userNotificationSelected,
|
||||
userNotificationMessage,
|
||||
handleCustomUserNotification,
|
||||
]);
|
||||
|
||||
const protectionSwitch = useMemo(() => {
|
||||
return (
|
||||
<EuiSwitch
|
||||
label={i18n.translate(
|
||||
'xpack.securitySolution.endpoint.policy.details.malwareProtectionsEnabled',
|
||||
{
|
||||
defaultMessage: 'Malware protections {mode, select, true {enabled} false {disabled}}',
|
||||
values: {
|
||||
mode: selected !== ProtectionModes.off,
|
||||
},
|
||||
}
|
||||
)}
|
||||
checked={selected !== ProtectionModes.off}
|
||||
onChange={handleSwitchChange}
|
||||
/>
|
||||
);
|
||||
}, [handleSwitchChange, selected]);
|
||||
|
||||
return (
|
||||
<ConfigForm
|
||||
type={i18n.translate('xpack.securitySolution.endpoint.policy.details.malware', {
|
||||
|
@ -339,9 +35,10 @@ export const MalwareProtections = React.memo(() => {
|
|||
})}
|
||||
supportedOss={[OperatingSystem.WINDOWS, OperatingSystem.MAC]}
|
||||
dataTestSubj="malwareProtectionsForm"
|
||||
rightCorner={protectionSwitch}
|
||||
rightCorner={<ProtectionSwitch protection={protection} osList={OSes} />}
|
||||
>
|
||||
{radioButtons}
|
||||
<RadioButtons protection={protection} osList={OSes} />
|
||||
{isPlatinumPlus && <UserNotification protection={protection} osList={OSes} />}
|
||||
<EuiSpacer size="m" />
|
||||
<EuiCallOut iconType="iInCircle">
|
||||
<FormattedMessage
|
||||
|
|
|
@ -5,311 +5,26 @@
|
|||
* 2.0.
|
||||
*/
|
||||
|
||||
import React, { useCallback, useMemo } from 'react';
|
||||
import { useDispatch } from 'react-redux';
|
||||
import React from 'react';
|
||||
import { i18n } from '@kbn/i18n';
|
||||
import { FormattedMessage } from '@kbn/i18n/react';
|
||||
import {
|
||||
EuiCallOut,
|
||||
EuiCheckbox,
|
||||
EuiRadio,
|
||||
EuiSpacer,
|
||||
EuiSwitch,
|
||||
EuiText,
|
||||
EuiTextArea,
|
||||
htmlIdGenerator,
|
||||
EuiFlexGroup,
|
||||
EuiFlexItem,
|
||||
EuiIconTip,
|
||||
EuiCheckboxProps,
|
||||
EuiRadioProps,
|
||||
EuiSwitchProps,
|
||||
} from '@elastic/eui';
|
||||
import { cloneDeep } from 'lodash';
|
||||
import { EuiCallOut, EuiSpacer } from '@elastic/eui';
|
||||
import { APP_ID } from '../../../../../../../common/constants';
|
||||
import { SecurityPageName } from '../../../../../../app/types';
|
||||
import {
|
||||
Immutable,
|
||||
OperatingSystem,
|
||||
ProtectionModes,
|
||||
} from '../../../../../../../common/endpoint/types';
|
||||
import { Immutable, OperatingSystem } from '../../../../../../../common/endpoint/types';
|
||||
import { RansomwareProtectionOSes, OS } from '../../../types';
|
||||
import { ConfigForm, ConfigFormHeading } from '../../components/config_form';
|
||||
import { policyConfig } from '../../../store/policy_details/selectors';
|
||||
import { usePolicyDetailsSelector } from '../../policy_hooks';
|
||||
import { ConfigForm } from '../../components/config_form';
|
||||
import { LinkToApp } from '../../../../../../common/components/endpoint/link_to_app';
|
||||
import { AppAction } from '../../../../../../common/store/actions';
|
||||
import { SupportedVersionNotice } from './supported_version';
|
||||
import { RadioFlexGroup } from './malware';
|
||||
|
||||
const OSes: Immutable<RansomwareProtectionOSes[]> = [OS.windows];
|
||||
const protection = 'ransomware';
|
||||
|
||||
const ProtectionRadio = React.memo(
|
||||
({ protectionMode, label }: { protectionMode: ProtectionModes; label: string }) => {
|
||||
const policyDetailsConfig = usePolicyDetailsSelector(policyConfig);
|
||||
const dispatch = useDispatch<(action: AppAction) => void>();
|
||||
const radioButtonId = useMemo(() => htmlIdGenerator()(), []);
|
||||
const selected = policyDetailsConfig && policyDetailsConfig.windows.ransomware.mode;
|
||||
|
||||
const handleRadioChange: EuiRadioProps['onChange'] = useCallback(() => {
|
||||
if (policyDetailsConfig) {
|
||||
const newPayload = cloneDeep(policyDetailsConfig);
|
||||
for (const os of OSes) {
|
||||
newPayload[os][protection].mode = protectionMode;
|
||||
if (protectionMode === ProtectionModes.prevent) {
|
||||
newPayload[os].popup[protection].enabled = true;
|
||||
} else {
|
||||
newPayload[os].popup[protection].enabled = false;
|
||||
}
|
||||
}
|
||||
dispatch({
|
||||
type: 'userChangedPolicyConfig',
|
||||
payload: { policyConfig: newPayload },
|
||||
});
|
||||
}
|
||||
}, [dispatch, protectionMode, policyDetailsConfig]);
|
||||
|
||||
/**
|
||||
* Passing an arbitrary id because EuiRadio
|
||||
* requires an id if label is passed
|
||||
*/
|
||||
|
||||
return (
|
||||
<EuiRadio
|
||||
className="policyDetailsProtectionRadio"
|
||||
label={label}
|
||||
id={radioButtonId}
|
||||
checked={selected === protectionMode}
|
||||
onChange={handleRadioChange}
|
||||
disabled={selected === ProtectionModes.off}
|
||||
/>
|
||||
);
|
||||
}
|
||||
);
|
||||
|
||||
ProtectionRadio.displayName = 'ProtectionRadio';
|
||||
import { RadioButtons } from '../components/radio_buttons';
|
||||
import { UserNotification } from '../components/user_notification';
|
||||
import { ProtectionSwitch } from '../components/protection_switch';
|
||||
|
||||
/** The Ransomware Protections form for policy details
|
||||
* which will configure for all relevant OSes.
|
||||
*/
|
||||
export const Ransomware = React.memo(() => {
|
||||
const policyDetailsConfig = usePolicyDetailsSelector(policyConfig);
|
||||
const dispatch = useDispatch<(action: AppAction) => void>();
|
||||
const selected = policyDetailsConfig && policyDetailsConfig.windows.ransomware.mode;
|
||||
const userNotificationSelected =
|
||||
policyDetailsConfig && policyDetailsConfig.windows.popup.ransomware.enabled;
|
||||
const userNotificationMessage =
|
||||
policyDetailsConfig && policyDetailsConfig.windows.popup.ransomware.message;
|
||||
|
||||
const radios: Immutable<
|
||||
Array<{
|
||||
id: ProtectionModes;
|
||||
label: string;
|
||||
protection: 'ransomware';
|
||||
}>
|
||||
> = useMemo(() => {
|
||||
return [
|
||||
{
|
||||
id: ProtectionModes.detect,
|
||||
label: i18n.translate('xpack.securitySolution.endpoint.policy.details.detect', {
|
||||
defaultMessage: 'Detect',
|
||||
}),
|
||||
protection: 'ransomware',
|
||||
},
|
||||
{
|
||||
id: ProtectionModes.prevent,
|
||||
label: i18n.translate('xpack.securitySolution.endpoint.policy.details.prevent', {
|
||||
defaultMessage: 'Prevent',
|
||||
}),
|
||||
protection: 'ransomware',
|
||||
},
|
||||
];
|
||||
}, []);
|
||||
|
||||
const handleSwitchChange: EuiSwitchProps['onChange'] = useCallback(
|
||||
(event) => {
|
||||
if (policyDetailsConfig) {
|
||||
const newPayload = cloneDeep(policyDetailsConfig);
|
||||
if (event.target.checked === false) {
|
||||
for (const os of OSes) {
|
||||
newPayload[os][protection].mode = ProtectionModes.off;
|
||||
newPayload[os].popup[protection].enabled = event.target.checked;
|
||||
}
|
||||
} else {
|
||||
for (const os of OSes) {
|
||||
newPayload[os][protection].mode = ProtectionModes.prevent;
|
||||
newPayload[os].popup[protection].enabled = event.target.checked;
|
||||
}
|
||||
}
|
||||
dispatch({
|
||||
type: 'userChangedPolicyConfig',
|
||||
payload: { policyConfig: newPayload },
|
||||
});
|
||||
}
|
||||
},
|
||||
[dispatch, policyDetailsConfig]
|
||||
);
|
||||
|
||||
const handleUserNotificationCheckbox: EuiCheckboxProps['onChange'] = useCallback(
|
||||
(event) => {
|
||||
if (policyDetailsConfig) {
|
||||
const newPayload = cloneDeep(policyDetailsConfig);
|
||||
for (const os of OSes) {
|
||||
newPayload[os].popup[protection].enabled = event.target.checked;
|
||||
}
|
||||
dispatch({
|
||||
type: 'userChangedPolicyConfig',
|
||||
payload: { policyConfig: newPayload },
|
||||
});
|
||||
}
|
||||
},
|
||||
[policyDetailsConfig, dispatch]
|
||||
);
|
||||
|
||||
const handleCustomUserNotification = useCallback(
|
||||
(event) => {
|
||||
if (policyDetailsConfig) {
|
||||
const newPayload = cloneDeep(policyDetailsConfig);
|
||||
for (const os of OSes) {
|
||||
newPayload[os].popup[protection].message = event.target.value;
|
||||
}
|
||||
dispatch({
|
||||
type: 'userChangedPolicyConfig',
|
||||
payload: { policyConfig: newPayload },
|
||||
});
|
||||
}
|
||||
},
|
||||
[policyDetailsConfig, dispatch]
|
||||
);
|
||||
|
||||
const radioButtons = useMemo(() => {
|
||||
return (
|
||||
<>
|
||||
<ConfigFormHeading>
|
||||
<FormattedMessage
|
||||
id="xpack.securitySolution.endpoint.policyDetailsConfig.protectionLevel"
|
||||
defaultMessage="Protection Level"
|
||||
/>
|
||||
</ConfigFormHeading>
|
||||
<EuiSpacer size="xs" />
|
||||
<RadioFlexGroup>
|
||||
<EuiFlexItem className="no-right-margin-radio" grow={2}>
|
||||
<ProtectionRadio
|
||||
protectionMode={radios[0].id}
|
||||
key={radios[0].protection + radios[0].id}
|
||||
label={radios[0].label}
|
||||
/>
|
||||
</EuiFlexItem>
|
||||
<EuiFlexItem className="no-horizontal-margin-radio" grow={5}>
|
||||
<ProtectionRadio
|
||||
protectionMode={radios[1].id}
|
||||
key={radios[1].protection + radios[1].id}
|
||||
label={radios[1].label}
|
||||
/>
|
||||
</EuiFlexItem>
|
||||
</RadioFlexGroup>
|
||||
<EuiSpacer size="m" />
|
||||
<ConfigFormHeading>
|
||||
<FormattedMessage
|
||||
id="xpack.securitySolution.endpoint.policyDetailsConfig.userNotification"
|
||||
defaultMessage="User Notification"
|
||||
/>
|
||||
</ConfigFormHeading>
|
||||
<SupportedVersionNotice optionName="ransomware" />
|
||||
<EuiSpacer size="s" />
|
||||
<EuiCheckbox
|
||||
data-test-subj="ransomwareUserNotificationCheckbox"
|
||||
id="xpack.securitySolution.endpoint.policyDetail.ransomware.userNotification"
|
||||
onChange={handleUserNotificationCheckbox}
|
||||
checked={userNotificationSelected}
|
||||
disabled={selected === ProtectionModes.off}
|
||||
label={i18n.translate(
|
||||
'xpack.securitySolution.endpoint.policyDetail.ransomware.notifyUser',
|
||||
{
|
||||
defaultMessage: 'Notify User',
|
||||
}
|
||||
)}
|
||||
/>
|
||||
{userNotificationSelected && (
|
||||
<>
|
||||
<EuiSpacer size="s" />
|
||||
<EuiFlexGroup gutterSize="s">
|
||||
<EuiFlexItem grow={false}>
|
||||
<EuiText size="xs">
|
||||
<h4>
|
||||
<FormattedMessage
|
||||
id="xpack.securitySolution.endpoint.policyDetailsConfig.customizeUserNotification"
|
||||
defaultMessage="Customize notification message"
|
||||
/>
|
||||
</h4>
|
||||
</EuiText>
|
||||
</EuiFlexItem>
|
||||
<EuiFlexItem grow={false}>
|
||||
<EuiIconTip
|
||||
position="right"
|
||||
data-test-subj="ransomwareTooltip"
|
||||
content={
|
||||
<>
|
||||
<FormattedMessage
|
||||
id="xpack.securitySolution.endpoint.policyDetailsConfig.ransomware.notifyUserTooltip.a"
|
||||
defaultMessage="Selecting the user notification option will display a notification to the host user when ransomware is prevented or detected."
|
||||
/>
|
||||
<EuiSpacer size="m" />
|
||||
<FormattedMessage
|
||||
id="xpack.securitySolution.endpoint.policyDetailsConfig.ransomware.notifyUserTooltip.b"
|
||||
defaultMessage="
|
||||
The user notification can be customized in the text box below. Bracketed tags can be used to dynamically populate the applicable action (such as prevented or detected) and the filename."
|
||||
/>
|
||||
</>
|
||||
}
|
||||
/>
|
||||
</EuiFlexItem>
|
||||
</EuiFlexGroup>
|
||||
<EuiSpacer size="xs" />
|
||||
<EuiTextArea
|
||||
placeholder={i18n.translate(
|
||||
'xpack.securitySolution.endpoint.policyDetails.ransomware.userNotification.placeholder',
|
||||
{
|
||||
defaultMessage: 'Input your custom notification message',
|
||||
}
|
||||
)}
|
||||
value={userNotificationMessage}
|
||||
onChange={handleCustomUserNotification}
|
||||
fullWidth={true}
|
||||
data-test-subj="ransomwareUserNotificationCustomMessage"
|
||||
/>
|
||||
</>
|
||||
)}
|
||||
</>
|
||||
);
|
||||
}, [
|
||||
radios,
|
||||
selected,
|
||||
handleUserNotificationCheckbox,
|
||||
userNotificationSelected,
|
||||
userNotificationMessage,
|
||||
handleCustomUserNotification,
|
||||
]);
|
||||
|
||||
const protectionSwitch = useMemo(() => {
|
||||
return (
|
||||
<EuiSwitch
|
||||
label={i18n.translate(
|
||||
'xpack.securitySolution.endpoint.policy.details.ransomwareProtectionsEnabled',
|
||||
{
|
||||
defaultMessage:
|
||||
'Ransomware protections {mode, select, true {enabled} false {disabled}}',
|
||||
values: {
|
||||
mode: selected !== ProtectionModes.off,
|
||||
},
|
||||
}
|
||||
)}
|
||||
checked={selected !== ProtectionModes.off}
|
||||
onChange={handleSwitchChange}
|
||||
/>
|
||||
);
|
||||
}, [handleSwitchChange, selected]);
|
||||
const OSes: Immutable<RansomwareProtectionOSes[]> = [OS.windows];
|
||||
const protection = 'ransomware';
|
||||
|
||||
return (
|
||||
<ConfigForm
|
||||
|
@ -318,9 +33,10 @@ export const Ransomware = React.memo(() => {
|
|||
})}
|
||||
supportedOss={[OperatingSystem.WINDOWS]}
|
||||
dataTestSubj="ransomwareProtectionsForm"
|
||||
rightCorner={protectionSwitch}
|
||||
rightCorner={<ProtectionSwitch protection={protection} osList={OSes} />}
|
||||
>
|
||||
{radioButtons}
|
||||
<RadioButtons protection={protection} osList={OSes} />
|
||||
<UserNotification protection={protection} osList={OSes} />
|
||||
<EuiSpacer size="m" />
|
||||
<EuiCallOut iconType="iInCircle">
|
||||
<FormattedMessage
|
||||
|
|
|
@ -19609,12 +19609,10 @@
|
|||
"xpack.securitySolution.endpoint.policy.details.eventCollectionsEnabled": "{selected} / {total} 件のイベント収集が有効です",
|
||||
"xpack.securitySolution.endpoint.policy.details.lockedCard": "ランサムウェア保護をオンにするには、ライセンスをプラチナに更新するか、30日間の無料トライアルを開始するか、AWS、GCP、またはAzureで{cloudDeploymentLink}にサインアップしてください。",
|
||||
"xpack.securitySolution.endpoint.policy.details.malware": "マルウェア",
|
||||
"xpack.securitySolution.endpoint.policy.details.malwareProtectionsEnabled": "マルウェア保護{mode, select, true {有効} false {無効}}",
|
||||
"xpack.securitySolution.endpoint.policy.details.platinum": "プラチナ",
|
||||
"xpack.securitySolution.endpoint.policy.details.prevent": "防御",
|
||||
"xpack.securitySolution.endpoint.policy.details.protections": "保護",
|
||||
"xpack.securitySolution.endpoint.policy.details.ransomware": "ランサムウェア",
|
||||
"xpack.securitySolution.endpoint.policy.details.ransomwareProtectionsEnabled": "ランサムウェア保護{mode, select, true {有効} false {無効}}",
|
||||
"xpack.securitySolution.endpoint.policy.details.save": "保存",
|
||||
"xpack.securitySolution.endpoint.policy.details.settings": "設定",
|
||||
"xpack.securitySolution.endpoint.policy.details.updateConfirm.cancelButtonTitle": "キャンセル",
|
||||
|
@ -19626,15 +19624,11 @@
|
|||
"xpack.securitySolution.endpoint.policy.details.updateSuccessMessage": "統合{name}が更新されました。",
|
||||
"xpack.securitySolution.endpoint.policy.details.updateSuccessTitle": "成功!",
|
||||
"xpack.securitySolution.endpoint.policy.details.upgradeToPlatinum": "Elastic Platinum へのアップグレード",
|
||||
"xpack.securitySolution.endpoint.policyDetail.malware.notifyUser": "ユーザーに通知",
|
||||
"xpack.securitySolution.endpoint.policyDetail.ransomware.notifyUser": "ユーザーに通知",
|
||||
"xpack.securitySolution.endpoint.policyDetailOS": "オペレーティングシステム",
|
||||
"xpack.securitySolution.endpoint.policyDetails.agentsSummary.errorTitle": "エラー",
|
||||
"xpack.securitySolution.endpoint.policyDetails.agentsSummary.offlineTitle": "オフライン",
|
||||
"xpack.securitySolution.endpoint.policyDetails.agentsSummary.onlineTitle": "オンライン",
|
||||
"xpack.securitySolution.endpoint.policyDetails.agentsSummary.totalTitle": "エンドポイント",
|
||||
"xpack.securitySolution.endpoint.policyDetails.malware.userNotification.placeholder": "カスタム通知メッセージを入力",
|
||||
"xpack.securitySolution.endpoint.policyDetails.ransomware.userNotification.placeholder": "カスタム通知メッセージを入力",
|
||||
"xpack.securitySolution.endpoint.policyDetails.supportedVersion": "エージェントバージョン {version}",
|
||||
"xpack.securitySolution.endpoint.policyDetailsConfig.customizeUserNotification": "通知メッセージをカスタマイズ",
|
||||
"xpack.securitySolution.endpoint.policyDetailsConfig.eventingEvents": "イベント",
|
||||
|
@ -19644,11 +19638,7 @@
|
|||
"xpack.securitySolution.endpoint.policyDetailsConfig.mac.events.file": "ファイル",
|
||||
"xpack.securitySolution.endpoint.policyDetailsConfig.mac.events.network": "ネットワーク",
|
||||
"xpack.securitySolution.endpoint.policyDetailsConfig.mac.events.process": "プロセス",
|
||||
"xpack.securitySolution.endpoint.policyDetailsConfig.malware.notifyUserTooltip.a": "ユーザー通知オプションを選択すると、マルウェアが防御または検出されたときに、ホストユーザーに通知を表示します。",
|
||||
"xpack.securitySolution.endpoint.policyDetailsConfig.malware.notifyUserTooltip.b": " ユーザー通知は、以下のテキストボックスでカスタマイズできます。括弧内のタグを使用すると、該当するアクション (防御または検出など) とファイル名を動的に入力できます。",
|
||||
"xpack.securitySolution.endpoint.policyDetailsConfig.protectionLevel": "保護レベル",
|
||||
"xpack.securitySolution.endpoint.policyDetailsConfig.ransomware.notifyUserTooltip.a": "ユーザー通知オプションを選択すると、ランサムウェアが防御または検出されたときに、ホストユーザーに通知を表示します。",
|
||||
"xpack.securitySolution.endpoint.policyDetailsConfig.ransomware.notifyUserTooltip.b": " ユーザー通知は、以下のテキストボックスでカスタマイズできます。括弧内のタグを使用すると、該当するアクション (防御または検出など) とファイル名を動的に入力できます。",
|
||||
"xpack.securitySolution.endpoint.policyDetailsConfig.userNotification": "ユーザー通知",
|
||||
"xpack.securitySolution.endpoint.policyDetailsConfig.windows.events.dllDriverLoad": "DLL とドライバーの読み込み",
|
||||
"xpack.securitySolution.endpoint.policyDetailsConfig.windows.events.dns": "DNS",
|
||||
|
|
|
@ -19900,12 +19900,10 @@
|
|||
"xpack.securitySolution.endpoint.policy.details.eventCollectionsEnabled": "{selected} / {total} 个事件收集已启用",
|
||||
"xpack.securitySolution.endpoint.policy.details.lockedCard": "要打开勒索软件防护,必须将您的许可证升级到白金级、开始 30 天免费试用或在 AWS、GCP 或 Azure 中实施{cloudDeploymentLink}。",
|
||||
"xpack.securitySolution.endpoint.policy.details.malware": "恶意软件",
|
||||
"xpack.securitySolution.endpoint.policy.details.malwareProtectionsEnabled": "恶意软件防护{mode, select, true {已启用} false {已禁用}}",
|
||||
"xpack.securitySolution.endpoint.policy.details.platinum": "白金级",
|
||||
"xpack.securitySolution.endpoint.policy.details.prevent": "防御",
|
||||
"xpack.securitySolution.endpoint.policy.details.protections": "防护",
|
||||
"xpack.securitySolution.endpoint.policy.details.ransomware": "勒索软件",
|
||||
"xpack.securitySolution.endpoint.policy.details.ransomwareProtectionsEnabled": "勒索软件防护{mode, select, true {已启用} false {已禁用}}",
|
||||
"xpack.securitySolution.endpoint.policy.details.save": "保存",
|
||||
"xpack.securitySolution.endpoint.policy.details.settings": "设置",
|
||||
"xpack.securitySolution.endpoint.policy.details.updateConfirm.cancelButtonTitle": "取消",
|
||||
|
@ -19918,15 +19916,11 @@
|
|||
"xpack.securitySolution.endpoint.policy.details.updateSuccessMessage": "集成 {name} 已更新。",
|
||||
"xpack.securitySolution.endpoint.policy.details.updateSuccessTitle": "成功!",
|
||||
"xpack.securitySolution.endpoint.policy.details.upgradeToPlatinum": "升级到 Elastic 白金级",
|
||||
"xpack.securitySolution.endpoint.policyDetail.malware.notifyUser": "通知用户",
|
||||
"xpack.securitySolution.endpoint.policyDetail.ransomware.notifyUser": "通知用户",
|
||||
"xpack.securitySolution.endpoint.policyDetailOS": "操作系统",
|
||||
"xpack.securitySolution.endpoint.policyDetails.agentsSummary.errorTitle": "错误",
|
||||
"xpack.securitySolution.endpoint.policyDetails.agentsSummary.offlineTitle": "脱机",
|
||||
"xpack.securitySolution.endpoint.policyDetails.agentsSummary.onlineTitle": "联机",
|
||||
"xpack.securitySolution.endpoint.policyDetails.agentsSummary.totalTitle": "终端",
|
||||
"xpack.securitySolution.endpoint.policyDetails.malware.userNotification.placeholder": "输入您的定制通知消息",
|
||||
"xpack.securitySolution.endpoint.policyDetails.ransomware.userNotification.placeholder": "输入您的定制通知消息",
|
||||
"xpack.securitySolution.endpoint.policyDetails.supportedVersion": "代理版本 {version}",
|
||||
"xpack.securitySolution.endpoint.policyDetailsConfig.customizeUserNotification": "定制通知消息",
|
||||
"xpack.securitySolution.endpoint.policyDetailsConfig.eventingEvents": "事件",
|
||||
|
@ -19936,11 +19930,7 @@
|
|||
"xpack.securitySolution.endpoint.policyDetailsConfig.mac.events.file": "文件",
|
||||
"xpack.securitySolution.endpoint.policyDetailsConfig.mac.events.network": "网络",
|
||||
"xpack.securitySolution.endpoint.policyDetailsConfig.mac.events.process": "进程",
|
||||
"xpack.securitySolution.endpoint.policyDetailsConfig.malware.notifyUserTooltip.a": "选择用户通知选项后,在阻止或检测到恶意软件时将向主机用户显示通知。",
|
||||
"xpack.securitySolution.endpoint.policyDetailsConfig.malware.notifyUserTooltip.b": " 可在下方文本框中定制用户通知。括号中的标签可用于动态填充适用操作 (如已阻止或已检测) 和文件名。",
|
||||
"xpack.securitySolution.endpoint.policyDetailsConfig.protectionLevel": "防护级别",
|
||||
"xpack.securitySolution.endpoint.policyDetailsConfig.ransomware.notifyUserTooltip.a": "选择用户通知选项后,在阻止或检测到勒索软件时将向主机用户显示通知。",
|
||||
"xpack.securitySolution.endpoint.policyDetailsConfig.ransomware.notifyUserTooltip.b": " 可在下方文本框中定制用户通知。括号中的标签可用于动态填充适用操作 (如已阻止或已检测) 和文件名。",
|
||||
"xpack.securitySolution.endpoint.policyDetailsConfig.userNotification": "用户通知",
|
||||
"xpack.securitySolution.endpoint.policyDetailsConfig.windows.events.dllDriverLoad": "DLL 和驱动程序加载",
|
||||
"xpack.securitySolution.endpoint.policyDetailsConfig.windows.events.dns": "DNS",
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue