Skip to content

Commit

Permalink
[8.15] [Fleet] Disable selecting standalone instructions for user wit…
Browse files Browse the repository at this point in the history
…hout agent policies READ permissions (elastic#187517) (elastic#187605)

# Backport

This will backport the following commits from `main` to `8.15`:
- [[Fleet] Disable selecting standalone instructions for user without
agent policies READ permissions
(elastic#187517)](elastic#187517)

<!--- Backport version: 9.4.3 -->

### Questions ?
Please refer to the [Backport tool
documentation](https://github.com/sqren/backport)

<!--BACKPORT [{"author":{"name":"Nicolas
Chaulet","email":"[email protected]"},"sourceCommit":{"committedDate":"2024-07-04T13:45:20Z","message":"[Fleet]
Disable selecting standalone instructions for user without agent
policies READ permissions
(elastic#187517)","sha":"c27ca409a4fcfa4a16e44558ab1302fa26f7f3b8","branchLabelMapping":{"^v8.15.0$":"main","^v(\\d+).(\\d+).\\d+$":"$1.$2"}},"sourcePullRequest":{"labels":["release_note:skip","Team:Fleet","backport:prev-minor","v8.15.0","v8.16.0"],"title":"[Fleet]
Disable selecting standalone instructions for user without agent
policies READ
permissions","number":187517,"url":"https://github.com/elastic/kibana/pull/187517","mergeCommit":{"message":"[Fleet]
Disable selecting standalone instructions for user without agent
policies READ permissions
(elastic#187517)","sha":"c27ca409a4fcfa4a16e44558ab1302fa26f7f3b8"}},"sourceBranch":"main","suggestedTargetBranches":[],"targetPullRequestStates":[{"branch":"main","label":"v8.15.0","branchLabelMappingKey":"^v8.15.0$","isSourceBranch":true,"state":"MERGED","url":"https://github.com/elastic/kibana/pull/187517","number":187517,"mergeCommit":{"message":"[Fleet]
Disable selecting standalone instructions for user without agent
policies READ permissions
(elastic#187517)","sha":"c27ca409a4fcfa4a16e44558ab1302fa26f7f3b8"}},{"branch":"8.16","label":"v8.16.0","branchLabelMappingKey":"^v(\\d+).(\\d+).\\d+$","isSourceBranch":false,"state":"NOT_CREATED"}]}]
BACKPORT-->

Co-authored-by: Nicolas Chaulet <[email protected]>
  • Loading branch information
kibanamachine and nchaulet authored Jul 4, 2024
1 parent c616ed3 commit 2f4f5ff
Show file tree
Hide file tree
Showing 4 changed files with 55 additions and 19 deletions.
3 changes: 1 addition & 2 deletions x-pack/plugins/fleet/common/authz.ts
Original file line number Diff line number Diff line change
Expand Up @@ -144,8 +144,7 @@ export const calculateAuthz = ({
// These are currently used by Fleet Server setup
setup: fleet.all || fleet.setup,
readEnrollmentTokens: (fleet.all || fleet.setup || fleet.agents?.all) ?? false,
readAgentPolicies:
(fleet.all || fleet.read || fleet.setup || fleet.agentPolicies?.read) ?? false,
readAgentPolicies: (fleet.all || fleet.setup) ?? false,
};

return {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -14,14 +14,16 @@ import type { RenderResult } from '@testing-library/react';
import { createFleetTestRendererMock } from '../../mock';
import type { AgentPolicy } from '../../../common';
import { sendGetOneAgentPolicy } from '../../hooks/use_request';
import { useAgentEnrollmentFlyoutData, useFleetServerStandalone } from '../../hooks';
import { useAgentEnrollmentFlyoutData, useAuthz, useFleetServerStandalone } from '../../hooks';

import { useAdvancedForm } from '../../applications/fleet/components/fleet_server_instructions/hooks';
import { useFleetServerUnhealthy } from '../../applications/fleet/sections/agents/hooks/use_fleet_server_unhealthy';

import type { FlyOutProps } from './types';
import { AgentEnrollmentFlyout } from '.';

jest.mock('../../hooks/use_authz');

const render = (props?: Partial<FlyOutProps>) => {
cleanup();
const renderer = createFleetTestRendererMock();
Expand All @@ -47,6 +49,11 @@ describe('<AgentEnrollmentFlyout />', () => {
let results: RenderResult;

beforeEach(async () => {
jest.mocked(useAuthz).mockReturnValue({
fleet: {
readAgentPolicies: true,
},
} as any);
jest.mocked(useFleetServerStandalone).mockReturnValue({ isFleetServerStandalone: false });

(useFleetServerUnhealthy as jest.Mock).mockReturnValue({
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -28,6 +28,7 @@ import {
useFleetStatus,
useAgentEnrollmentFlyoutData,
useFleetServerHostsForPolicy,
useAuthz,
} from '../../hooks';
import { FLEET_SERVER_PACKAGE, MAX_FLYOUT_WIDTH } from '../../constants';
import type { PackagePolicy, AgentPolicy } from '../../types';
Expand Down Expand Up @@ -61,6 +62,8 @@ export const AgentEnrollmentFlyout: React.FunctionComponent<FlyOutProps> = ({
return policies.find((p) => p.id === id);
};

const authz = useAuthz();

const fleetStatus = useFleetStatus();
const { docLinks } = useStartServices();

Expand Down Expand Up @@ -172,6 +175,8 @@ export const AgentEnrollmentFlyout: React.FunctionComponent<FlyOutProps> = ({
data-test-subj="standaloneTab"
isSelected={mode === 'standalone'}
onClick={() => setMode('standalone')}
// Standalone need read access to agent policies
disabled={!authz.fleet.readAgentPolicies}
>
<FormattedMessage
id="xpack.fleet.agentEnrollment.enrollStandaloneTabLabel"
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -6,14 +6,34 @@
*/

import React from 'react';
import { EuiRadioGroup } from '@elastic/eui';
import { EuiRadioGroup, EuiToolTip } from '@elastic/eui';
import { FormattedMessage } from '@kbn/i18n-react';
import { i18n } from '@kbn/i18n';

import type { EuiContainedStepProps } from '@elastic/eui/src/components/steps/steps';

import { useAuthz } from '../../../hooks';
import type { FlyoutMode } from '../types';

const PermissionWrapper: React.FunctionComponent<{
showTooltip: boolean;
}> = ({ children, showTooltip }) => {
return showTooltip && children ? (
<EuiToolTip
content={
<FormattedMessage
id="xpack.fleet.agentFlyout.standaloneMissingPermissions"
defaultMessage="Read access to Agent Policies is required to see the standalone instructions."
/>
}
>
{children as React.ReactElement}
</EuiToolTip>
) : (
<>{children}</>
);
};

export const InstallationModeSelectionStep = ({
selectedPolicyId,
mode,
Expand All @@ -23,6 +43,7 @@ export const InstallationModeSelectionStep = ({
mode: FlyoutMode;
setMode: (v: FlyoutMode) => void;
}): EuiContainedStepProps => {
const authz = useAuthz();
// radio id has to be unique so that the component works even if appears twice in DOM
const radioSuffix = 'installation_mode_agent_selection';

Expand Down Expand Up @@ -63,22 +84,26 @@ export const InstallationModeSelectionStep = ({
},
{
id: `standalone_${radioSuffix}`,
// Disabled if no agentPolicies read permission
disabled: !authz.fleet.readAgentPolicies,
label: (
<FormattedMessage
data-test-subj="agentFlyoutStandaloneRadioButtons"
id="xpack.fleet.agentFlyout.standaloneRadioOption"
defaultMessage="{standaloneMessage} – Run an Elastic Agent standalone to configure and update the agent manually on the host where the agent is installed."
values={{
standaloneMessage: (
<strong>
<FormattedMessage
id="xpack.fleet.agentFlyout.standaloneMessage"
defaultMessage="Run standalone"
/>
</strong>
),
}}
/>
<PermissionWrapper showTooltip={!authz.fleet.readAgentPolicies}>
<FormattedMessage
data-test-subj="agentFlyoutStandaloneRadioButtons"
id="xpack.fleet.agentFlyout.standaloneRadioOption"
defaultMessage="{standaloneMessage} – Run an Elastic Agent standalone to configure and update the agent manually on the host where the agent is installed."
values={{
standaloneMessage: (
<strong>
<FormattedMessage
id="xpack.fleet.agentFlyout.standaloneMessage"
defaultMessage="Run standalone"
/>
</strong>
),
}}
/>
</PermissionWrapper>
),
},
]}
Expand Down

0 comments on commit 2f4f5ff

Please sign in to comment.