mirror of
https://github.com/elastic/kibana.git
synced 2025-04-23 09:19:04 -04:00
[Fleet] Ensure kibana assets are installed on policy space change (#215793)
This commit is contained in:
parent
115ec32eec
commit
bb78f8f5b8
17 changed files with 224 additions and 76 deletions
|
@ -27360,6 +27360,14 @@
|
|||
"properties": {
|
||||
"force": {
|
||||
"type": "boolean"
|
||||
},
|
||||
"space_ids": {
|
||||
"description": "When provided install assets in the specified spaces instead of the current space.",
|
||||
"items": {
|
||||
"type": "string"
|
||||
},
|
||||
"minItems": 1,
|
||||
"type": "array"
|
||||
}
|
||||
},
|
||||
"type": "object"
|
||||
|
|
|
@ -27360,6 +27360,14 @@
|
|||
"properties": {
|
||||
"force": {
|
||||
"type": "boolean"
|
||||
},
|
||||
"space_ids": {
|
||||
"description": "When provided install assets in the specified spaces instead of the current space.",
|
||||
"items": {
|
||||
"type": "string"
|
||||
},
|
||||
"minItems": 1,
|
||||
"type": "array"
|
||||
}
|
||||
},
|
||||
"type": "object"
|
||||
|
|
|
@ -25309,6 +25309,12 @@ paths:
|
|||
properties:
|
||||
force:
|
||||
type: boolean
|
||||
space_ids:
|
||||
description: When provided install assets in the specified spaces instead of the current space.
|
||||
items:
|
||||
type: string
|
||||
minItems: 1
|
||||
type: array
|
||||
responses:
|
||||
'200':
|
||||
content:
|
||||
|
|
|
@ -27513,6 +27513,12 @@ paths:
|
|||
properties:
|
||||
force:
|
||||
type: boolean
|
||||
space_ids:
|
||||
description: When provided install assets in the specified spaces instead of the current space.
|
||||
items:
|
||||
type: string
|
||||
minItems: 1
|
||||
type: array
|
||||
responses:
|
||||
'200':
|
||||
content:
|
||||
|
|
|
@ -34,7 +34,7 @@ import { validatePackagePolicy, validationHasErrors } from '../../../services';
|
|||
import { NotObscuredByBottomBar } from '..';
|
||||
import { StepConfigurePackagePolicy, StepDefinePackagePolicy } from '../../../components';
|
||||
import { prepareInputPackagePolicyDataset } from '../../../services/prepare_input_pkg_policy_dataset';
|
||||
import { ensurePackageKibanaAssetsInstalled } from '../../../services/ensure_kibana_assets_installed';
|
||||
import { ensurePackageKibanaAssetsInstalled } from '../../../../../../services/ensure_kibana_assets_installed';
|
||||
|
||||
const ExpandableAdvancedSettings: React.FC<{ children?: React.ReactNode }> = ({ children }) => {
|
||||
const [isShowingAdvanced, setIsShowingAdvanced] = useState<boolean>(false);
|
||||
|
|
|
@ -51,7 +51,7 @@ import {
|
|||
getCloudShellUrlFromPackagePolicy,
|
||||
} from '../../../../../../../components/cloud_security_posture/services';
|
||||
import { AGENTLESS_DISABLED_INPUTS } from '../../../../../../../../common/constants';
|
||||
import { ensurePackageKibanaAssetsInstalled } from '../../services/ensure_kibana_assets_installed';
|
||||
import { ensurePackageKibanaAssetsInstalled } from '../../../../../services/ensure_kibana_assets_installed';
|
||||
|
||||
import { useAgentless, useSetupTechnology } from './setup_technology';
|
||||
|
||||
|
|
|
@ -6,8 +6,9 @@
|
|||
*/
|
||||
|
||||
import React, { memo, useMemo, useState } from 'react';
|
||||
import deepEqual from 'fast-deep-equal';
|
||||
import styled from 'styled-components';
|
||||
import { pick } from 'lodash';
|
||||
import { pick, uniqBy } from 'lodash';
|
||||
import {
|
||||
EuiBottomBar,
|
||||
EuiFlexGroup,
|
||||
|
@ -21,12 +22,14 @@ import { FormattedMessage } from '@kbn/i18n-react';
|
|||
import { DEFAULT_SPACE_ID } from '@kbn/spaces-plugin/common';
|
||||
import { useHistory } from 'react-router-dom';
|
||||
|
||||
import { ensurePackageKibanaAssetsInstalled } from '../../../../../services/ensure_kibana_assets_installed';
|
||||
|
||||
import { useSpaceSettingsContext } from '../../../../../../../hooks/use_space_settings_context';
|
||||
import type { AgentPolicy } from '../../../../../types';
|
||||
import {
|
||||
useStartServices,
|
||||
useAuthz,
|
||||
sendUpdateAgentPolicy,
|
||||
sendUpdateAgentPolicyForRq,
|
||||
useConfig,
|
||||
sendGetAgentStatus,
|
||||
useAgentPolicyRefresh,
|
||||
|
@ -115,41 +118,54 @@ export const SettingsView = memo<{ agentPolicy: AgentPolicy }>(
|
|||
const submitUpdateAgentPolicy = async () => {
|
||||
setIsLoading(true);
|
||||
try {
|
||||
const { data, error } = await sendUpdateAgentPolicy(
|
||||
agentPolicy.id,
|
||||
pickAgentPolicyKeysToSend(agentPolicy)
|
||||
);
|
||||
if (data) {
|
||||
notifications.toasts.addSuccess(
|
||||
i18n.translate('xpack.fleet.editAgentPolicy.successNotificationTitle', {
|
||||
defaultMessage: "Successfully updated ''{name}'' settings",
|
||||
values: { name: agentPolicy.name },
|
||||
})
|
||||
const dataToSend = pickAgentPolicyKeysToSend(agentPolicy);
|
||||
await sendUpdateAgentPolicyForRq(agentPolicy.id, pickAgentPolicyKeysToSend(agentPolicy));
|
||||
|
||||
if (
|
||||
dataToSend.space_ids &&
|
||||
!deepEqual(originalAgentPolicy.space_ids, dataToSend.space_ids)
|
||||
) {
|
||||
const packages = uniqBy(
|
||||
originalAgentPolicy.package_policies
|
||||
?.map((pp) =>
|
||||
pp.package
|
||||
? { pkgName: pp.package.name, pkgVersion: pp.package.version }
|
||||
: undefined
|
||||
)
|
||||
.filter(
|
||||
(p): p is { pkgName: string; pkgVersion: string } => typeof p !== 'undefined'
|
||||
) ?? [],
|
||||
'pkgName'
|
||||
);
|
||||
if (
|
||||
agentPolicy.space_ids &&
|
||||
!agentPolicy.space_ids.includes(spaceId ?? DEFAULT_SPACE_ID)
|
||||
) {
|
||||
history.replace(getPath('policies_list'));
|
||||
} else {
|
||||
refreshAgentPolicy();
|
||||
setHasChanges(false);
|
||||
for (const { pkgName, pkgVersion } of packages) {
|
||||
await ensurePackageKibanaAssetsInstalled({
|
||||
spaceIds: dataToSend.space_ids,
|
||||
pkgName,
|
||||
pkgVersion,
|
||||
toasts: notifications.toasts,
|
||||
});
|
||||
}
|
||||
} else {
|
||||
notifications.toasts.addDanger(
|
||||
error
|
||||
? error.message
|
||||
: i18n.translate('xpack.fleet.editAgentPolicy.errorNotificationTitle', {
|
||||
defaultMessage: 'Unable to update agent policy',
|
||||
})
|
||||
);
|
||||
}
|
||||
} catch (e) {
|
||||
notifications.toasts.addDanger(
|
||||
i18n.translate('xpack.fleet.editAgentPolicy.errorNotificationTitle', {
|
||||
defaultMessage: 'Unable to update agent policy',
|
||||
|
||||
notifications.toasts.addSuccess(
|
||||
i18n.translate('xpack.fleet.editAgentPolicy.successNotificationTitle', {
|
||||
defaultMessage: "Successfully updated ''{name}'' settings",
|
||||
values: { name: agentPolicy.name },
|
||||
})
|
||||
);
|
||||
|
||||
if (agentPolicy.space_ids && !agentPolicy.space_ids.includes(spaceId ?? DEFAULT_SPACE_ID)) {
|
||||
history.replace(getPath('policies_list'));
|
||||
} else {
|
||||
refreshAgentPolicy();
|
||||
setHasChanges(false);
|
||||
}
|
||||
} catch (error) {
|
||||
notifications.toasts.addError(error, {
|
||||
title: i18n.translate('xpack.fleet.editAgentPolicy.errorNotificationTitle', {
|
||||
defaultMessage: 'Unable to update agent policy',
|
||||
}),
|
||||
});
|
||||
}
|
||||
setIsLoading(false);
|
||||
};
|
||||
|
|
|
@ -7,14 +7,11 @@
|
|||
|
||||
import { toastsServiceMock } from '@kbn/core-notifications-browser-mocks/src/toasts_service.mock';
|
||||
|
||||
import {
|
||||
sendGetPackageInfoByKeyForRq,
|
||||
sendInstallKibanaAssetsForRq,
|
||||
} from '../../../../../../hooks';
|
||||
import { sendGetPackageInfoByKeyForRq, sendInstallKibanaAssetsForRq } from '../../../hooks';
|
||||
|
||||
import { ensurePackageKibanaAssetsInstalled } from './ensure_kibana_assets_installed';
|
||||
|
||||
jest.mock('../../../../../../hooks');
|
||||
jest.mock('../../../hooks');
|
||||
|
||||
describe('ensurePackageKibanaAssetsInstalled', () => {
|
||||
beforeEach(() => {
|
||||
|
@ -48,6 +45,35 @@ describe('ensurePackageKibanaAssetsInstalled', () => {
|
|||
expect(toasts.addSuccess).toBeCalled();
|
||||
});
|
||||
|
||||
it('install assets in multiple space if not installed', async () => {
|
||||
jest.mocked(sendGetPackageInfoByKeyForRq).mockResolvedValue({
|
||||
item: {
|
||||
installationInfo: {
|
||||
name: 'nginx',
|
||||
version: '1.25.1',
|
||||
installed_kibana_space_id: 'default',
|
||||
},
|
||||
},
|
||||
} as any);
|
||||
|
||||
const toasts = toastsServiceMock.createStartContract();
|
||||
|
||||
await ensurePackageKibanaAssetsInstalled({
|
||||
spaceIds: ['default', 'test1', 'test2'],
|
||||
pkgName: 'nginx',
|
||||
pkgVersion: '1.25.1',
|
||||
toasts,
|
||||
});
|
||||
|
||||
expect(sendInstallKibanaAssetsForRq).toBeCalledWith({
|
||||
pkgName: 'nginx',
|
||||
pkgVersion: '1.25.1',
|
||||
spaceIds: ['test1', 'test2'],
|
||||
});
|
||||
|
||||
expect(toasts.addSuccess).toBeCalled();
|
||||
});
|
||||
|
||||
it('does nothing if assets are already installed', async () => {
|
||||
jest.mocked(sendGetPackageInfoByKeyForRq).mockResolvedValue({
|
||||
item: {
|
|
@ -9,22 +9,18 @@ import type { IToasts } from '@kbn/core/public';
|
|||
import { i18n } from '@kbn/i18n';
|
||||
import { DEFAULT_SPACE_ID } from '@kbn/spaces-plugin/common';
|
||||
|
||||
import {
|
||||
sendGetPackageInfoByKeyForRq,
|
||||
sendInstallKibanaAssetsForRq,
|
||||
} from '../../../../../../hooks';
|
||||
import { sendGetPackageInfoByKeyForRq, sendInstallKibanaAssetsForRq } from '../../../hooks';
|
||||
|
||||
export async function ensurePackageKibanaAssetsInstalled({
|
||||
currentSpaceId,
|
||||
pkgName,
|
||||
pkgVersion,
|
||||
toasts,
|
||||
...rest
|
||||
}: {
|
||||
currentSpaceId: string;
|
||||
pkgName: string;
|
||||
pkgVersion: string;
|
||||
toasts: IToasts;
|
||||
}) {
|
||||
} & ({ currentSpaceId: string } | { spaceIds: string[] })) {
|
||||
try {
|
||||
const packageInfo = await sendGetPackageInfoByKeyForRq(pkgName, pkgVersion, {
|
||||
prerelease: true,
|
||||
|
@ -40,21 +36,43 @@ export async function ensurePackageKibanaAssetsInstalled({
|
|||
installationInfo.installed_kibana_space_id ?? DEFAULT_SPACE_ID,
|
||||
...Object.keys(installationInfo.additional_spaces_installed_kibana ?? {}),
|
||||
];
|
||||
if (!kibanaAssetsSpaces.includes(currentSpaceId)) {
|
||||
|
||||
if ('currentSpaceId' in rest) {
|
||||
if (kibanaAssetsSpaces.includes(rest.currentSpaceId)) {
|
||||
return;
|
||||
}
|
||||
await sendInstallKibanaAssetsForRq({
|
||||
pkgName: installationInfo.name,
|
||||
pkgVersion: installationInfo.version,
|
||||
});
|
||||
toasts.addSuccess(
|
||||
i18n.translate('xpack.fleet.installKibanaAssets.successNotificationTitle', {
|
||||
defaultMessage: 'Successfully installed kibana assets',
|
||||
})
|
||||
} else {
|
||||
const missingSpaceIds = rest.spaceIds.filter(
|
||||
(spaceId) => !kibanaAssetsSpaces.includes(spaceId)
|
||||
);
|
||||
if (!missingSpaceIds.length) {
|
||||
return;
|
||||
}
|
||||
await sendInstallKibanaAssetsForRq({
|
||||
pkgName: installationInfo.name,
|
||||
pkgVersion: installationInfo.version,
|
||||
spaceIds: missingSpaceIds,
|
||||
});
|
||||
}
|
||||
toasts.addSuccess(
|
||||
i18n.translate('xpack.fleet.installKibanaAssets.successNotificationTitle', {
|
||||
defaultMessage: 'Successfully installed kibana assets for {pkgName}',
|
||||
values: {
|
||||
pkgName: installationInfo.name,
|
||||
},
|
||||
})
|
||||
);
|
||||
} catch (err) {
|
||||
toasts.addError(err, {
|
||||
title: i18n.translate('xpack.fleet.installKibanaAssets.errorNotificationTitle', {
|
||||
defaultMessage: 'Unable to install kibana assets',
|
||||
defaultMessage: 'Unable to install kibana assets for {pkgName}',
|
||||
values: {
|
||||
pkgName,
|
||||
},
|
||||
}),
|
||||
});
|
||||
}
|
|
@ -184,6 +184,9 @@ export const sendCreateAgentPolicy = (
|
|||
});
|
||||
};
|
||||
|
||||
/**
|
||||
* @deprecated use sendUpdateAgentPolicyForRq instead
|
||||
*/
|
||||
export const sendUpdateAgentPolicy = (
|
||||
agentPolicyId: string,
|
||||
body: UpdateAgentPolicyRequest['body']
|
||||
|
|
|
@ -339,6 +339,7 @@ interface UpdatePackageArgs {
|
|||
interface InstallKibanaAssetsArgs {
|
||||
pkgName: string;
|
||||
pkgVersion: string;
|
||||
spaceIds?: string[];
|
||||
}
|
||||
|
||||
export const useUpdatePackageMutation = () => {
|
||||
|
@ -365,11 +366,16 @@ export const useInstallKibanaAssetsMutation = () => {
|
|||
});
|
||||
};
|
||||
|
||||
export const sendInstallKibanaAssetsForRq = ({ pkgName, pkgVersion }: InstallKibanaAssetsArgs) =>
|
||||
export const sendInstallKibanaAssetsForRq = ({
|
||||
pkgName,
|
||||
pkgVersion,
|
||||
spaceIds,
|
||||
}: InstallKibanaAssetsArgs) =>
|
||||
sendRequestForRq({
|
||||
path: epmRouteService.getInstallKibanaAssetsPath(pkgName, pkgVersion),
|
||||
method: 'post',
|
||||
version: API_VERSIONS.public.v1,
|
||||
body: spaceIds ? { space_ids: spaceIds } : undefined,
|
||||
});
|
||||
|
||||
export const sendUpdatePackage = (
|
||||
|
|
|
@ -5,9 +5,10 @@
|
|||
* 2.0.
|
||||
*/
|
||||
|
||||
import type { KibanaRequest } from '@kbn/core/server';
|
||||
import type { TypeOf } from '@kbn/config-schema';
|
||||
|
||||
import { FleetNotFoundError } from '../../errors';
|
||||
import { FleetError, FleetNotFoundError } from '../../errors';
|
||||
import { appContextService } from '../../services';
|
||||
import {
|
||||
deleteKibanaAssetsAndReferencesForSpace,
|
||||
|
@ -24,6 +25,21 @@ import type {
|
|||
} from '../../types';
|
||||
import { createArchiveIteratorFromMap } from '../../services/epm/archive/archive_iterator';
|
||||
|
||||
export async function checkIntegrationsAllPrivilegesForSpaces(
|
||||
request: KibanaRequest,
|
||||
spaceIds: string[]
|
||||
) {
|
||||
const security = appContextService.getSecurity();
|
||||
const res = await security.authz.checkPrivilegesWithRequest(request).atSpaces(spaceIds, {
|
||||
kibana: [security.authz.actions.api.get(`integrations-all`)],
|
||||
});
|
||||
if (!res.hasAllRequested) {
|
||||
throw new FleetError(
|
||||
`No enough permissions to install assets in spaces ${spaceIds.join(', ')}`
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
export const installPackageKibanaAssetsHandler: FleetRequestHandler<
|
||||
TypeOf<typeof InstallKibanaAssetsRequestSchema.params>,
|
||||
undefined,
|
||||
|
@ -35,6 +51,10 @@ export const installPackageKibanaAssetsHandler: FleetRequestHandler<
|
|||
const spaceId = fleetContext.spaceId;
|
||||
const { pkgName, pkgVersion } = request.params;
|
||||
|
||||
if (request.body?.space_ids) {
|
||||
await checkIntegrationsAllPrivilegesForSpaces(request, request.body?.space_ids);
|
||||
}
|
||||
|
||||
const installedPkgWithAssets = await getInstalledPackageWithAssets({
|
||||
savedObjectsClient,
|
||||
pkgName,
|
||||
|
@ -56,21 +76,25 @@ export const installPackageKibanaAssetsHandler: FleetRequestHandler<
|
|||
|
||||
const { packageInfo } = installedPkgWithAssets;
|
||||
|
||||
await installKibanaAssetsAndReferences({
|
||||
savedObjectsClient,
|
||||
logger,
|
||||
pkgName,
|
||||
pkgTitle: packageInfo.title,
|
||||
installAsAdditionalSpace: true,
|
||||
spaceId,
|
||||
assetTags: installedPkgWithAssets.packageInfo?.asset_tags,
|
||||
installedPkg: installation,
|
||||
packageInstallContext: {
|
||||
packageInfo,
|
||||
paths: installedPkgWithAssets.paths,
|
||||
archiveIterator: createArchiveIteratorFromMap(installedPkgWithAssets.assetsMap),
|
||||
},
|
||||
});
|
||||
const spaceIds = request.body?.space_ids ?? [spaceId];
|
||||
|
||||
for (const spaceToInstallId of spaceIds) {
|
||||
await installKibanaAssetsAndReferences({
|
||||
savedObjectsClient: appContextService.getInternalUserSOClientForSpaceId(spaceToInstallId),
|
||||
logger,
|
||||
pkgName,
|
||||
pkgTitle: packageInfo.title,
|
||||
installAsAdditionalSpace: true,
|
||||
spaceId: spaceToInstallId,
|
||||
assetTags: installedPkgWithAssets.packageInfo?.asset_tags,
|
||||
installedPkg: installation,
|
||||
packageInstallContext: {
|
||||
packageInfo,
|
||||
paths: installedPkgWithAssets.paths,
|
||||
archiveIterator: createArchiveIteratorFromMap(installedPkgWithAssets.assetsMap),
|
||||
},
|
||||
});
|
||||
}
|
||||
|
||||
return response.ok({ body: { success: true } });
|
||||
};
|
||||
|
|
|
@ -345,7 +345,7 @@ export async function deleteKibanaAssetsAndReferencesForSpace({
|
|||
);
|
||||
}
|
||||
await deleteKibanaSavedObjectsAssets({ installedPkg, spaceId });
|
||||
await saveKibanaAssetsRefs(savedObjectsClient, pkgName, [], true);
|
||||
await saveKibanaAssetsRefs(savedObjectsClient, pkgName, null, true);
|
||||
}
|
||||
|
||||
const kibanaAssetTypes = Object.values(KibanaAssetType);
|
||||
|
|
|
@ -1199,7 +1199,7 @@ export const kibanaAssetsToAssetsRef = (
|
|||
export const saveKibanaAssetsRefs = async (
|
||||
savedObjectsClient: SavedObjectsClientContract,
|
||||
pkgName: string,
|
||||
assetRefs: KibanaAssetReference[],
|
||||
assetRefs: KibanaAssetReference[] | null,
|
||||
saveAsAdditionnalSpace = false
|
||||
) => {
|
||||
auditLoggingService.writeCustomSoAuditLog({
|
||||
|
@ -1236,11 +1236,11 @@ export const saveKibanaAssetsRefs = async (
|
|||
installation?.attributes?.additional_spaces_installed_kibana ?? {},
|
||||
spaceId
|
||||
),
|
||||
...(assetRefs.length > 0 ? { [spaceId]: assetRefs } : {}),
|
||||
...(assetRefs !== null ? { [spaceId]: assetRefs } : {}),
|
||||
},
|
||||
}
|
||||
: {
|
||||
installed_kibana: assetRefs,
|
||||
installed_kibana: assetRefs !== null ? assetRefs : [],
|
||||
},
|
||||
{ refresh: false }
|
||||
);
|
||||
|
@ -1248,7 +1248,7 @@ export const saveKibanaAssetsRefs = async (
|
|||
{ retries: 20 } // Use a number of retries higher than the number of es asset update operations
|
||||
);
|
||||
|
||||
return assetRefs;
|
||||
return assetRefs !== null ? assetRefs : [];
|
||||
};
|
||||
|
||||
export async function ensurePackagesCompletedInstall(
|
||||
|
|
|
@ -591,10 +591,18 @@ export const InstallKibanaAssetsRequestSchema = {
|
|||
pkgName: schema.string(),
|
||||
pkgVersion: schema.string(),
|
||||
}),
|
||||
// body is deprecated on delete request
|
||||
body: schema.nullable(
|
||||
schema.object({
|
||||
force: schema.maybe(schema.boolean()),
|
||||
space_ids: schema.maybe(
|
||||
schema.arrayOf(schema.string(), {
|
||||
minSize: 1,
|
||||
meta: {
|
||||
description:
|
||||
'When provided install assets in the specified spaces instead of the current space.',
|
||||
},
|
||||
})
|
||||
),
|
||||
})
|
||||
),
|
||||
};
|
||||
|
|
|
@ -482,7 +482,7 @@ export class SpaceTestApiClient {
|
|||
return res;
|
||||
}
|
||||
async installPackageKibanaAssets(
|
||||
{ pkgName, pkgVersion }: { pkgName: string; pkgVersion: string },
|
||||
{ pkgName, pkgVersion, spaceIds }: { pkgName: string; pkgVersion: string; spaceIds?: string[] },
|
||||
spaceId?: string
|
||||
) {
|
||||
const { body: res } = await this.supertest
|
||||
|
@ -490,6 +490,7 @@ export class SpaceTestApiClient {
|
|||
`${this.getBaseUrl(spaceId)}/api/fleet/epm/packages/${pkgName}/${pkgVersion}/kibana_assets`
|
||||
)
|
||||
.set('kbn-xsrf', 'xxxx')
|
||||
.send(spaceIds ? { space_ids: spaceIds } : {})
|
||||
.expect(200);
|
||||
|
||||
return res;
|
||||
|
|
|
@ -145,6 +145,24 @@ export default function (providerContext: FtrProviderContext) {
|
|||
Object.keys(res.item.installationInfo?.additional_spaces_installed_kibana ?? {})
|
||||
).eql([]);
|
||||
});
|
||||
|
||||
it('should allow to install kibana in another space from the default space', async () => {
|
||||
await apiClient.installPackageKibanaAssets({
|
||||
pkgName: 'nginx',
|
||||
pkgVersion: '1.20.0',
|
||||
spaceIds: [TEST_SPACE_1],
|
||||
});
|
||||
|
||||
const res = await apiClient.getPackage({ pkgName: 'nginx', pkgVersion: '1.20.0' });
|
||||
if (!('installationInfo' in res.item)) {
|
||||
throw new Error('not installed');
|
||||
}
|
||||
|
||||
expect(res.item.installationInfo?.installed_kibana_space_id).eql('default');
|
||||
expect(
|
||||
Object.keys(res.item.installationInfo?.additional_spaces_installed_kibana ?? {})
|
||||
).eql([TEST_SPACE_1]);
|
||||
});
|
||||
});
|
||||
|
||||
describe('with package installed in test space', () => {
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue