diff --git a/x-pack/packages/kbn-cloud-security-posture-common/README.md b/x-pack/packages/kbn-cloud-security-posture-common/README.md
index bafaa51be0d82c..2fc159d9c4cac5 100644
--- a/x-pack/packages/kbn-cloud-security-posture-common/README.md
+++ b/x-pack/packages/kbn-cloud-security-posture-common/README.md
@@ -1 +1,9 @@
-FILL THIS IN LATER
\ No newline at end of file
+# @kbn/cloud-security-posture-common
+
+This package provides common code consumed in both the browser, i.e. the
+`packages/cloud-security-posture` package and `plugins/cloud_security_posture` plugin, and on the server, i.e. the
+`plugins/cloud_security_posture` plugin.
+
+## Maintainers
+
+Maintained by the Cloud Security Posture Team
\ No newline at end of file
diff --git a/x-pack/packages/kbn-cloud-security-posture-common/utils/helpers.ts b/x-pack/packages/kbn-cloud-security-posture-common/utils/helpers.ts
index e64d281a447754..be97ef8947b8f0 100644
--- a/x-pack/packages/kbn-cloud-security-posture-common/utils/helpers.ts
+++ b/x-pack/packages/kbn-cloud-security-posture-common/utils/helpers.ts
@@ -5,13 +5,16 @@
* 2.0.
*/
import { QueryDslQueryContainer } from '@kbn/data-views-plugin/common/types';
+import { i18n } from '@kbn/i18n';
import { CspBenchmarkRulesStates } from '../types/latest';
export const extractErrorMessage = (e: unknown, defaultMessage = 'Unknown Error'): string => {
if (e instanceof Error) return e.message;
if (typeof e === 'string') return e;
- return defaultMessage; // TODO: i18n
+ return i18n.translate('xpack.csp.findings.errorMessage.default', {
+ defaultMessage,
+ });
};
export const buildMutedRulesFilter = (
diff --git a/x-pack/packages/kbn-cloud-security-posture/README.md b/x-pack/packages/kbn-cloud-security-posture/README.md
index bafaa51be0d82c..38a875dda54abf 100644
--- a/x-pack/packages/kbn-cloud-security-posture/README.md
+++ b/x-pack/packages/kbn-cloud-security-posture/README.md
@@ -1 +1,9 @@
-FILL THIS IN LATER
\ No newline at end of file
+# @kbn/cloud-security-posture
+
+This package includes
+- Hooks that's used on Flyout component that's used in Alerts page on Security Solution Plugins as well as components on CSP plugin
+- Utilities and types thats used for the Hooks above as well as in CSP plugins
+
+## Maintainers
+
+Maintained by the Cloud Security Posture Team
\ No newline at end of file
diff --git a/x-pack/plugins/security_solution/public/flyout/entity_details/shared/components/insight_entity/misconfigurations_overview.tsx b/x-pack/plugins/security_solution/public/flyout/entity_details/shared/components/insight_entity/misconfigurations_overview.tsx
index 7903ccc15e90a5..2c533971fcb75f 100644
--- a/x-pack/plugins/security_solution/public/flyout/entity_details/shared/components/insight_entity/misconfigurations_overview.tsx
+++ b/x-pack/plugins/security_solution/public/flyout/entity_details/shared/components/insight_entity/misconfigurations_overview.tsx
@@ -5,33 +5,37 @@
* 2.0.
*/
-import React from 'react';
+import React, { useCallback } from 'react';
import { css } from '@emotion/react';
import { EuiFlexGroup, EuiFlexItem, EuiText, useEuiTheme } from '@elastic/eui';
import { FormattedMessage } from '@kbn/i18n-react';
import { DistributionBar } from '@kbn/security-solution-distribution-bar';
import { useMisconfigurationPreview } from '@kbn/cloud-security-posture';
import { euiThemeVars } from '@kbn/ui-theme';
+import { i18n } from '@kbn/i18n';
import { ExpandablePanel } from '../../../../shared/components/expandable_panel';
export const MisconfigurationsOverview = ({ hostName }: { hostName: string }) => {
- const queryHostName = {
- bool: {
- must: [],
- filter: [
- {
- bool: {
- should: [{ term: { 'host.name': { value: `${hostName}` } } }],
- minimum_should_match: 1,
+ const queryHostName = useCallback(() => {
+ return {
+ bool: {
+ must: [],
+ filter: [
+ {
+ bool: {
+ should: [{ term: { 'host.name': { value: `${hostName}` } } }],
+ minimum_should_match: 1,
+ },
},
- },
- ],
- should: [],
- must_not: [],
- },
- };
+ ],
+ should: [],
+ must_not: [],
+ },
+ };
+ }, [hostName]);
+
const { data } = useMisconfigurationPreview({
- query: queryHostName,
+ query: queryHostName(),
sort: [],
enabled: true,
pageSize: 1,
@@ -44,18 +48,91 @@ export const MisconfigurationsOverview = ({ hostName }: { hostName: string }) =>
if (passedFindingsStats === 0 && failedFindingsStats === 0) return [];
return [
{
- key: 'Passed findings',
+ key: i18n.translate(
+ 'xpack.securitySolution.flyout.right.insights.misconfigurations.passedFindingsText',
+ {
+ defaultMessage: 'Passed findings',
+ }
+ ),
count: passedFindingsStats,
color: euiThemeVars.euiColorSuccess,
},
{
- key: 'Failed findings',
+ key: i18n.translate(
+ 'xpack.securitySolution.flyout.right.insights.misconfigurations.failedFindingsText',
+ {
+ defaultMessage: 'Failed findings',
+ }
+ ),
count: failedFindingsStats,
color: euiThemeVars.euiColorVis9,
},
];
};
+ const MisconfigurationEmptyState = () => {
+ return (
+
+
+
+
+
+
+
+
+
+
+
+
+ );
+ };
+
+ const MisconfigurationPreviewScore = () => {
+ return (
+
+
+
+
+ {`${Math.round((passedFindings / (passedFindings + failedFindings)) * 100)}%`}
+
+
+
+
+
+
+
+
+
+ );
+ };
+
return (
/>
),
- // Commented this out until we have the expanded flyout
+ // TODO: Uncomment when we have the expanded flyout
// iconType: 'arrowStart',
}}
data-test-subj={'securitySolutionFlyoutInsightsMisconfigurations'}
>
{passedFindings === 0 && failedFindings === 0 ? (
-
-
-
-
- {'-'}
-
-
-
-
-
-
-
-
-
+
) : (
-
-
-
-
- {`${Math.round((passedFindings / (passedFindings + failedFindings)) * 100)}%`}
-
-
-
-
-
-
-
-
-
+
)}
diff --git a/x-pack/test/security_solution_cypress/cypress/tasks/api_calls/rules.ts b/x-pack/test/security_solution_cypress/cypress/tasks/api_calls/rules.ts
index 008fc92bd02248..be63a66f9a5317 100644
--- a/x-pack/test/security_solution_cypress/cypress/tasks/api_calls/rules.ts
+++ b/x-pack/test/security_solution_cypress/cypress/tasks/api_calls/rules.ts
@@ -138,3 +138,16 @@ export const enableRules = ({ names, ids }: EnableRulesParameters): Cypress.Chai
failOnStatusCode: false,
});
};
+
+export const createFindings = (
+ rule: RuleCreateProps
+): Cypress.Chainable> => {
+ return cy.currentSpace().then((spaceId) =>
+ rootRequest({
+ method: 'POST',
+ url: spaceId ? getSpaceUrl(spaceId, DETECTION_ENGINE_RULES_URL) : DETECTION_ENGINE_RULES_URL,
+ body: rule,
+ failOnStatusCode: false,
+ })
+ );
+};