From 2ae6333b1b6c004b1daa534cdab9418758593b02 Mon Sep 17 00:00:00 2001 From: Christos Nasikas Date: Fri, 1 Nov 2024 09:38:32 +0200 Subject: [PATCH] [ResponseOps][Cases] Make deprecated APIs internal in serverless (#198378) ## Summary Fixes: https://github.com/elastic/kibana/issues/198407 ### Checklist Delete any items that are not applicable to this PR. - [x] [Unit or functional tests](https://www.elastic.co/guide/en/kibana/master/development-tests.html) were updated or added to match the most common scenarios ### For maintainers - [x] This was checked for breaking API changes and was [labeled appropriately](https://www.elastic.co/guide/en/kibana/master/contributing.html#_add_your_labels) --- x-pack/plugins/cases/server/plugin.ts | 7 +- .../server/routes/api/cases/get_case.test.ts | 62 +++++++++++++ .../cases/server/routes/api/cases/get_case.ts | 92 ++++++++++--------- .../api/comments/get_all_comment.test.ts | 22 +++++ .../routes/api/comments/get_all_comment.ts | 75 +++++++-------- .../server/routes/api/get_external_routes.ts | 10 +- .../routes/api/stats/get_status.test.ts | 22 +++++ .../server/routes/api/stats/get_status.ts | 65 ++++++------- .../user_actions/get_all_user_actions.test.ts | 22 +++++ .../api/user_actions/get_all_user_actions.ts | 73 +++++++-------- .../common/lib/api/index.ts | 10 +- .../api_integration/services/svl_cases/api.ts | 14 +-- .../observability/cases/get_all_comments.ts | 45 +++++++++ .../cases/get_all_user_actions.ts | 45 +++++++++ .../observability/cases/get_case.ts | 19 +++- .../observability/cases/get_status.ts | 45 +++++++++ .../test_suites/observability/cases/index.ts | 3 + .../test_suites/security/cases/get_case.ts | 19 +++- 18 files changed, 481 insertions(+), 169 deletions(-) create mode 100644 x-pack/plugins/cases/server/routes/api/cases/get_case.test.ts create mode 100644 x-pack/plugins/cases/server/routes/api/comments/get_all_comment.test.ts create mode 100644 x-pack/plugins/cases/server/routes/api/stats/get_status.test.ts create mode 100644 x-pack/plugins/cases/server/routes/api/user_actions/get_all_user_actions.test.ts create mode 100644 x-pack/test_serverless/api_integration/test_suites/observability/cases/get_all_comments.ts create mode 100644 x-pack/test_serverless/api_integration/test_suites/observability/cases/get_all_user_actions.ts create mode 100644 x-pack/test_serverless/api_integration/test_suites/observability/cases/get_status.ts diff --git a/x-pack/plugins/cases/server/plugin.ts b/x-pack/plugins/cases/server/plugin.ts index fa172b48520a7..b40089ff75050 100644 --- a/x-pack/plugins/cases/server/plugin.ts +++ b/x-pack/plugins/cases/server/plugin.ts @@ -122,9 +122,14 @@ export class CasePlugin const router = core.http.createRouter(); const telemetryUsageCounter = plugins.usageCollection?.createUsageCounter(APP_ID); + const isServerless = plugins.cloud?.isServerlessEnabled; + registerRoutes({ router, - routes: [...getExternalRoutes(), ...getInternalRoutes(this.userProfileService)], + routes: [ + ...getExternalRoutes({ isServerless }), + ...getInternalRoutes(this.userProfileService), + ], logger: this.logger, kibanaVersion: this.kibanaVersion, telemetryUsageCounter, diff --git a/x-pack/plugins/cases/server/routes/api/cases/get_case.test.ts b/x-pack/plugins/cases/server/routes/api/cases/get_case.test.ts new file mode 100644 index 0000000000000..45ee5e8f47163 --- /dev/null +++ b/x-pack/plugins/cases/server/routes/api/cases/get_case.test.ts @@ -0,0 +1,62 @@ +/* + * 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 { createCasesClientMock } from '../../../client/mocks'; +import { getCaseRoute } from './get_case'; +import { httpServerMock, loggingSystemMock } from '@kbn/core/server/mocks'; + +describe('getCaseRoute', () => { + const casesClientMock = createCasesClientMock(); + const logger = loggingSystemMock.createLogger(); + const response = httpServerMock.createResponseFactory(); + const kibanaVersion = '8.17'; + const context = { cases: { getCasesClient: jest.fn().mockResolvedValue(casesClientMock) } }; + + it('throws a bad request if the includeComments is set in serverless', async () => { + const router = getCaseRoute({ isServerless: true }); + const request = httpServerMock.createKibanaRequest({ + path: '/api/cases/{case_id}/?includeComments=true', + query: { includeComments: true }, + params: { case_id: 'foo' }, + }); + + await expect( + // @ts-expect-error: no need to create the context + router.handler({ response, request, logger, kibanaVersion, context }) + ).rejects.toThrowErrorMatchingInlineSnapshot(` + "Failed to retrieve case in route case id: foo + include comments: true: Error: includeComments is not supported" + `); + }); + + it('does not throw a bad request if the includeComments is set in non-serverless', async () => { + const router = getCaseRoute({ isServerless: false }); + const request = httpServerMock.createKibanaRequest({ + path: '/api/cases/{case_id}/?includeComments=true', + query: { includeComments: true }, + params: { case_id: 'foo' }, + }); + + await expect( + // @ts-expect-error: no need to create the context + router.handler({ response, request, logger, kibanaVersion, context }) + ).resolves.not.toThrow(); + }); + + it('does not throw a bad request if the includeComments is not set in serverless', async () => { + const router = getCaseRoute({ isServerless: true }); + const request = httpServerMock.createKibanaRequest({ + path: '/api/cases/{case_id}', + params: { case_id: 'foo' }, + }); + + await expect( + // @ts-expect-error: no need to create the context + router.handler({ response, request, logger, kibanaVersion, context }) + ).resolves.not.toThrow(); + }); +}); diff --git a/x-pack/plugins/cases/server/routes/api/cases/get_case.ts b/x-pack/plugins/cases/server/routes/api/cases/get_case.ts index 831a7be129f70..158360ff7b23f 100644 --- a/x-pack/plugins/cases/server/routes/api/cases/get_case.ts +++ b/x-pack/plugins/cases/server/routes/api/cases/get_case.ts @@ -5,6 +5,7 @@ * 2.0. */ +import Boom from '@hapi/boom'; import { schema } from '@kbn/config-schema'; import type { caseApiV1 } from '../../../../common/types/api'; @@ -26,53 +27,58 @@ const params = { }), }; -export const getCaseRoute = createCasesRoute({ - method: 'get', - path: CASE_DETAILS_URL, - params, - routerOptions: { - access: 'public', - summary: `Get a case`, - tags: ['oas-tag:cases'], - }, - handler: async ({ context, request, response, logger, kibanaVersion }) => { - try { - const isIncludeCommentsParamProvidedByTheUser = - request.url.searchParams.has('includeComments'); +export const getCaseRoute = ({ isServerless }: { isServerless?: boolean }) => + createCasesRoute({ + method: 'get', + path: CASE_DETAILS_URL, + params, + routerOptions: { + access: 'public', + summary: `Get a case`, + tags: ['oas-tag:cases'], + }, + handler: async ({ context, request, response, logger, kibanaVersion }) => { + try { + const isIncludeCommentsParamProvidedByTheUser = + request.url.searchParams.has('includeComments'); - if (isIncludeCommentsParamProvidedByTheUser) { - logDeprecatedEndpoint( - logger, - request.headers, - `The query parameter 'includeComments' of the get case API '${CASE_DETAILS_URL}' is deprecated` - ); - } + if (isServerless && isIncludeCommentsParamProvidedByTheUser) { + throw Boom.badRequest('includeComments is not supported'); + } - const caseContext = await context.cases; - const casesClient = await caseContext.getCasesClient(); - const id = request.params.case_id; + if (isIncludeCommentsParamProvidedByTheUser) { + logDeprecatedEndpoint( + logger, + request.headers, + `The query parameter 'includeComments' of the get case API '${CASE_DETAILS_URL}' is deprecated` + ); + } - const res: caseDomainV1.Case = await casesClient.cases.get({ - id, - includeComments: request.query.includeComments, - }); + const caseContext = await context.cases; + const casesClient = await caseContext.getCasesClient(); + const id = request.params.case_id; - return response.ok({ - ...(isIncludeCommentsParamProvidedByTheUser && { - headers: { - ...getWarningHeader(kibanaVersion, 'Deprecated query parameter includeComments'), - }, - }), - body: res, - }); - } catch (error) { - throw createCaseError({ - message: `Failed to retrieve case in route case id: ${request.params.case_id} \ninclude comments: ${request.query.includeComments}: ${error}`, - error, - }); - } - }, -}); + const res: caseDomainV1.Case = await casesClient.cases.get({ + id, + includeComments: request.query.includeComments, + }); + + return response.ok({ + ...(isIncludeCommentsParamProvidedByTheUser && { + headers: { + ...getWarningHeader(kibanaVersion, 'Deprecated query parameter includeComments'), + }, + }), + body: res, + }); + } catch (error) { + throw createCaseError({ + message: `Failed to retrieve case in route case id: ${request.params.case_id} \ninclude comments: ${request.query.includeComments}: ${error}`, + error, + }); + } + }, + }); export const resolveCaseRoute = createCasesRoute({ method: 'get', diff --git a/x-pack/plugins/cases/server/routes/api/comments/get_all_comment.test.ts b/x-pack/plugins/cases/server/routes/api/comments/get_all_comment.test.ts new file mode 100644 index 0000000000000..9687e73d1f7c8 --- /dev/null +++ b/x-pack/plugins/cases/server/routes/api/comments/get_all_comment.test.ts @@ -0,0 +1,22 @@ +/* + * 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 { getAllCommentsRoute } from './get_all_comment'; + +describe('getAllCommentsRoute', () => { + it('marks the endpoint internal in serverless', async () => { + const router = getAllCommentsRoute({ isServerless: true }); + + expect(router.routerOptions?.access).toBe('internal'); + }); + + it('marks the endpoint public in non-serverless', async () => { + const router = getAllCommentsRoute({ isServerless: false }); + + expect(router.routerOptions?.access).toBe('public'); + }); +}); diff --git a/x-pack/plugins/cases/server/routes/api/comments/get_all_comment.ts b/x-pack/plugins/cases/server/routes/api/comments/get_all_comment.ts index 6e8ac79bffec9..0f84ed29dce29 100644 --- a/x-pack/plugins/cases/server/routes/api/comments/get_all_comment.ts +++ b/x-pack/plugins/cases/server/routes/api/comments/get_all_comment.ts @@ -15,41 +15,42 @@ import type { attachmentDomainV1 } from '../../../../common/types/domain'; /** * @deprecated since version 8.1.0 */ -export const getAllCommentsRoute = createCasesRoute({ - method: 'get', - path: CASE_COMMENTS_URL, - params: { - params: schema.object({ - case_id: schema.string(), - }), - }, - options: { - deprecated: true, - }, - routerOptions: { - access: 'public', - summary: `Gets all case comments`, - tags: ['oas-tag:cases'], - // description: 'You must have `read` privileges for the **Cases** feature in the **Management**, **Observability**, or **Security** section of the Kibana feature privileges, depending on the owner of the cases with the comments you\'re seeking.', - // @ts-expect-error TODO(https://github.com/elastic/kibana/issues/196095): Replace {RouteDeprecationInfo} - deprecated: true, - }, - handler: async ({ context, request, response }) => { - try { - const caseContext = await context.cases; - const client = await caseContext.getCasesClient(); - const res: attachmentDomainV1.Attachments = await client.attachments.getAll({ - caseID: request.params.case_id, - }); +export const getAllCommentsRoute = ({ isServerless }: { isServerless?: boolean }) => + createCasesRoute({ + method: 'get', + path: CASE_COMMENTS_URL, + params: { + params: schema.object({ + case_id: schema.string(), + }), + }, + options: { + deprecated: true, + }, + routerOptions: { + access: isServerless ? 'internal' : 'public', + summary: `Gets all case comments`, + tags: ['oas-tag:cases'], + // description: 'You must have `read` privileges for the **Cases** feature in the **Management**, **Observability**, or **Security** section of the Kibana feature privileges, depending on the owner of the cases with the comments you\'re seeking.', + // @ts-expect-error TODO(https://github.com/elastic/kibana/issues/196095): Replace {RouteDeprecationInfo} + deprecated: true, + }, + handler: async ({ context, request, response }) => { + try { + const caseContext = await context.cases; + const client = await caseContext.getCasesClient(); + const res: attachmentDomainV1.Attachments = await client.attachments.getAll({ + caseID: request.params.case_id, + }); - return response.ok({ - body: res, - }); - } catch (error) { - throw createCaseError({ - message: `Failed to get all comments in route case id: ${request.params.case_id}: ${error}`, - error, - }); - } - }, -}); + return response.ok({ + body: res, + }); + } catch (error) { + throw createCaseError({ + message: `Failed to get all comments in route case id: ${request.params.case_id}: ${error}`, + error, + }); + } + }, + }); diff --git a/x-pack/plugins/cases/server/routes/api/get_external_routes.ts b/x-pack/plugins/cases/server/routes/api/get_external_routes.ts index bd990deefbdfa..4412d0b695079 100644 --- a/x-pack/plugins/cases/server/routes/api/get_external_routes.ts +++ b/x-pack/plugins/cases/server/routes/api/get_external_routes.ts @@ -31,18 +31,18 @@ import { postCaseConfigureRoute } from './configure/post_configure'; import { getAllAlertsAttachedToCaseRoute } from './comments/get_alerts'; import { findUserActionsRoute } from './user_actions/find_user_actions'; -export const getExternalRoutes = () => +export const getExternalRoutes = ({ isServerless }: { isServerless?: boolean }) => [ deleteCaseRoute, findCaseRoute, - getCaseRoute, + getCaseRoute({ isServerless }), resolveCaseRoute, patchCaseRoute, postCaseRoute, pushCaseRoute, findUserActionsRoute, - getUserActionsRoute, - getStatusRoute, + getUserActionsRoute({ isServerless }), + getStatusRoute({ isServerless }), getCasesByAlertIdRoute, getReportersRoute, getTagsRoute, @@ -50,7 +50,7 @@ export const getExternalRoutes = () => deleteAllCommentsRoute, findCommentsRoute, getCommentRoute, - getAllCommentsRoute, + getAllCommentsRoute({ isServerless }), patchCommentRoute, postCommentRoute, getCaseConfigureRoute, diff --git a/x-pack/plugins/cases/server/routes/api/stats/get_status.test.ts b/x-pack/plugins/cases/server/routes/api/stats/get_status.test.ts new file mode 100644 index 0000000000000..9376a46b76808 --- /dev/null +++ b/x-pack/plugins/cases/server/routes/api/stats/get_status.test.ts @@ -0,0 +1,22 @@ +/* + * 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 { getStatusRoute } from './get_status'; + +describe('getStatusRoute', () => { + it('marks the endpoint internal in serverless', async () => { + const router = getStatusRoute({ isServerless: true }); + + expect(router.routerOptions?.access).toBe('internal'); + }); + + it('marks the endpoint public in non-serverless', async () => { + const router = getStatusRoute({ isServerless: false }); + + expect(router.routerOptions?.access).toBe('public'); + }); +}); diff --git a/x-pack/plugins/cases/server/routes/api/stats/get_status.ts b/x-pack/plugins/cases/server/routes/api/stats/get_status.ts index dce369e4a0f45..0889644f6a80a 100644 --- a/x-pack/plugins/cases/server/routes/api/stats/get_status.ts +++ b/x-pack/plugins/cases/server/routes/api/stats/get_status.ts @@ -15,37 +15,38 @@ import type { statsApiV1 } from '../../../../common/types/api'; /** * @deprecated since version 8.1.0 */ -export const getStatusRoute: CaseRoute = createCasesRoute({ - method: 'get', - path: CASE_STATUS_URL, - options: { deprecated: true }, - routerOptions: { - access: 'public', - summary: `Get case status summary`, - tags: ['oas-tag:cases'], - description: - 'Returns the number of cases that are open, closed, and in progress in the default space.', - // You must have `read` privileges for the **Cases** feature in the **Management**, **Observability**, or **Security** section of the Kibana feature privileges, depending on the owner of the cases you're seeking. - // @ts-expect-error TODO(https://github.com/elastic/kibana/issues/196095): Replace {RouteDeprecationInfo} - deprecated: true, - }, - handler: async ({ context, request, response }) => { - try { - const caseContext = await context.cases; - const client = await caseContext.getCasesClient(); +export const getStatusRoute = ({ isServerless }: { isServerless?: boolean }): CaseRoute => + createCasesRoute({ + method: 'get', + path: CASE_STATUS_URL, + options: { deprecated: true }, + routerOptions: { + access: isServerless ? 'internal' : 'public', + summary: `Get case status summary`, + tags: ['oas-tag:cases'], + description: + 'Returns the number of cases that are open, closed, and in progress in the default space.', + // You must have `read` privileges for the **Cases** feature in the **Management**, **Observability**, or **Security** section of the Kibana feature privileges, depending on the owner of the cases you're seeking. + // @ts-expect-error TODO(https://github.com/elastic/kibana/issues/196095): Replace {RouteDeprecationInfo} + deprecated: true, + }, + handler: async ({ context, request, response }) => { + try { + const caseContext = await context.cases; + const client = await caseContext.getCasesClient(); - const res: statsApiV1.CasesStatusResponse = await client.metrics.getStatusTotalsByType( - request.query as statsApiV1.CasesStatusRequest - ); + const res: statsApiV1.CasesStatusResponse = await client.metrics.getStatusTotalsByType( + request.query as statsApiV1.CasesStatusRequest + ); - return response.ok({ - body: res, - }); - } catch (error) { - throw createCaseError({ - message: `Failed to get status stats in route: ${error}`, - error, - }); - } - }, -}); + return response.ok({ + body: res, + }); + } catch (error) { + throw createCaseError({ + message: `Failed to get status stats in route: ${error}`, + error, + }); + } + }, + }); diff --git a/x-pack/plugins/cases/server/routes/api/user_actions/get_all_user_actions.test.ts b/x-pack/plugins/cases/server/routes/api/user_actions/get_all_user_actions.test.ts new file mode 100644 index 0000000000000..d99b90c29bbb4 --- /dev/null +++ b/x-pack/plugins/cases/server/routes/api/user_actions/get_all_user_actions.test.ts @@ -0,0 +1,22 @@ +/* + * 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 { getUserActionsRoute } from './get_all_user_actions'; + +describe('getUserActionsRoute', () => { + it('marks the endpoint internal in serverless', async () => { + const router = getUserActionsRoute({ isServerless: true }); + + expect(router.routerOptions?.access).toBe('internal'); + }); + + it('marks the endpoint public in non-serverless', async () => { + const router = getUserActionsRoute({ isServerless: false }); + + expect(router.routerOptions?.access).toBe('public'); + }); +}); diff --git a/x-pack/plugins/cases/server/routes/api/user_actions/get_all_user_actions.ts b/x-pack/plugins/cases/server/routes/api/user_actions/get_all_user_actions.ts index 17fe0dcdb9012..19d7f1f8956ac 100644 --- a/x-pack/plugins/cases/server/routes/api/user_actions/get_all_user_actions.ts +++ b/x-pack/plugins/cases/server/routes/api/user_actions/get_all_user_actions.ts @@ -15,41 +15,42 @@ import { createCasesRoute } from '../create_cases_route'; /** * @deprecated since version 8.1.0 */ -export const getUserActionsRoute = createCasesRoute({ - method: 'get', - path: CASE_USER_ACTIONS_URL, - params: { - params: schema.object({ - case_id: schema.string(), - }), - }, - options: { deprecated: true }, - routerOptions: { - access: 'public', - summary: 'Get case activity', - description: `Returns all user activity for a case.`, - // You must have `read` privileges for the **Cases** feature in the **Management**, **Observability**, or **Security** section of the Kibana feature privileges, depending on the owner of the case you're seeking. - tags: ['oas-tag:cases'], - // @ts-expect-error TODO(https://github.com/elastic/kibana/issues/196095): Replace {RouteDeprecationInfo} - deprecated: true, - }, - handler: async ({ context, request, response }) => { - try { - const caseContext = await context.cases; - const casesClient = await caseContext.getCasesClient(); - const caseId = request.params.case_id; +export const getUserActionsRoute = ({ isServerless }: { isServerless?: boolean }) => + createCasesRoute({ + method: 'get', + path: CASE_USER_ACTIONS_URL, + params: { + params: schema.object({ + case_id: schema.string(), + }), + }, + options: { deprecated: true }, + routerOptions: { + access: isServerless ? 'internal' : 'public', + summary: 'Get case activity', + description: `Returns all user activity for a case.`, + // You must have `read` privileges for the **Cases** feature in the **Management**, **Observability**, or **Security** section of the Kibana feature privileges, depending on the owner of the case you're seeking. + tags: ['oas-tag:cases'], + // @ts-expect-error TODO(https://github.com/elastic/kibana/issues/196095): Replace {RouteDeprecationInfo} + deprecated: true, + }, + handler: async ({ context, request, response }) => { + try { + const caseContext = await context.cases; + const casesClient = await caseContext.getCasesClient(); + const caseId = request.params.case_id; - const res: userActionApiV1.CaseUserActionsDeprecatedResponse = - await casesClient.userActions.getAll({ caseId }); + const res: userActionApiV1.CaseUserActionsDeprecatedResponse = + await casesClient.userActions.getAll({ caseId }); - return response.ok({ - body: res, - }); - } catch (error) { - throw createCaseError({ - message: `Failed to retrieve case user actions in route case id: ${request.params.case_id}: ${error}`, - error, - }); - } - }, -}); + return response.ok({ + body: res, + }); + } catch (error) { + throw createCaseError({ + message: `Failed to retrieve case user actions in route case id: ${request.params.case_id}: ${error}`, + error, + }); + } + }, + }); diff --git a/x-pack/test/cases_api_integration/common/lib/api/index.ts b/x-pack/test/cases_api_integration/common/lib/api/index.ts index ea0f66affdc35..59d91a388f6ea 100644 --- a/x-pack/test/cases_api_integration/common/lib/api/index.ts +++ b/x-pack/test/cases_api_integration/common/lib/api/index.ts @@ -460,7 +460,7 @@ export const getAllCasesStatuses = async ({ export const getCase = async ({ supertest, caseId, - includeComments = false, + includeComments, expectedHttpCode = 200, auth = { user: superUser, space: null }, }: { @@ -470,10 +470,12 @@ export const getCase = async ({ expectedHttpCode?: number; auth?: { user: User; space: string | null }; }): Promise => { + const basePath = `${getSpaceUrlPrefix(auth?.space)}${CASES_URL}/${caseId}`; + const path = + includeComments != null ? `${basePath}?includeComments=${includeComments}` : basePath; + const { body: theCase } = await supertest - .get( - `${getSpaceUrlPrefix(auth?.space)}${CASES_URL}/${caseId}?includeComments=${includeComments}` - ) + .get(path) .set('kbn-xsrf', 'true') .set('x-elastic-internal-origin', 'foo') .auth(auth.user.username, auth.user.password) diff --git a/x-pack/test_serverless/api_integration/services/svl_cases/api.ts b/x-pack/test_serverless/api_integration/services/svl_cases/api.ts index c01365861c2d3..6886c894c1110 100644 --- a/x-pack/test_serverless/api_integration/services/svl_cases/api.ts +++ b/x-pack/test_serverless/api_integration/services/svl_cases/api.ts @@ -159,22 +159,22 @@ export function SvlCasesApiServiceProvider({ getService }: FtrProviderContext) { { caseId, space = 'default', - includeComments = false, expectedHttpCode = 200, + includeComments, }: { caseId: string; space?: string; - includeComments?: boolean; expectedHttpCode?: number; + includeComments?: boolean; }, roleAuthc: RoleCredentials ): Promise { + const basePath = `${this.getSpaceUrlPrefix(space)}${CASES_URL}/${caseId}`; + const path = + includeComments != null ? `${basePath}?includeComments=${includeComments}` : basePath; + const { body: theCase } = await supertestWithoutAuth - .get( - `${this.getSpaceUrlPrefix( - space - )}${CASES_URL}/${caseId}?includeComments=${includeComments}` - ) + .get(path) .set(svlCommonApi.getInternalRequestHeader()) .set(roleAuthc.apiKeyHeader) .expect(expectedHttpCode); diff --git a/x-pack/test_serverless/api_integration/test_suites/observability/cases/get_all_comments.ts b/x-pack/test_serverless/api_integration/test_suites/observability/cases/get_all_comments.ts new file mode 100644 index 0000000000000..5672b084d465c --- /dev/null +++ b/x-pack/test_serverless/api_integration/test_suites/observability/cases/get_all_comments.ts @@ -0,0 +1,45 @@ +/* + * 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 { CASE_COMMENTS_URL } from '@kbn/cases-plugin/common/constants'; +import type { RoleCredentials } from '../../../../shared/services'; +import { FtrProviderContext } from '../../../ftr_provider_context'; + +export default ({ getService }: FtrProviderContext): void => { + const svlCases = getService('svlCases'); + const svlUserManager = getService('svlUserManager'); + const supertestWithoutAuth = getService('supertestWithoutAuth'); + const svlCommonApi = getService('svlCommonApi'); + + describe('get_all_comments', () => { + let roleAuthc: RoleCredentials; + + before(async () => { + roleAuthc = await svlUserManager.createM2mApiKeyWithRoleScope('admin'); + }); + + after(async () => { + await svlUserManager.invalidateM2mApiKeyWithRoleScope(roleAuthc); + }); + + afterEach(async () => { + await svlCases.api.deleteCases(); + }); + + it('should fetch the status correctly with internal request headers', async () => { + await supertestWithoutAuth + .get(CASE_COMMENTS_URL) + .set(svlCommonApi.getInternalRequestHeader()) + .set(roleAuthc.apiKeyHeader) + .expect(200); + }); + + it('should not fetch the status correctly with no internal request headers', async () => { + await supertestWithoutAuth.get(CASE_COMMENTS_URL).set(roleAuthc.apiKeyHeader).expect(400); + }); + }); +}; diff --git a/x-pack/test_serverless/api_integration/test_suites/observability/cases/get_all_user_actions.ts b/x-pack/test_serverless/api_integration/test_suites/observability/cases/get_all_user_actions.ts new file mode 100644 index 0000000000000..54221f23256c6 --- /dev/null +++ b/x-pack/test_serverless/api_integration/test_suites/observability/cases/get_all_user_actions.ts @@ -0,0 +1,45 @@ +/* + * 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 { CASE_USER_ACTIONS_URL } from '@kbn/cases-plugin/common/constants'; +import type { RoleCredentials } from '../../../../shared/services'; +import { FtrProviderContext } from '../../../ftr_provider_context'; + +export default ({ getService }: FtrProviderContext): void => { + const svlCases = getService('svlCases'); + const svlUserManager = getService('svlUserManager'); + const supertestWithoutAuth = getService('supertestWithoutAuth'); + const svlCommonApi = getService('svlCommonApi'); + + describe('get_all_user_actions', () => { + let roleAuthc: RoleCredentials; + + before(async () => { + roleAuthc = await svlUserManager.createM2mApiKeyWithRoleScope('admin'); + }); + + after(async () => { + await svlUserManager.invalidateM2mApiKeyWithRoleScope(roleAuthc); + }); + + afterEach(async () => { + await svlCases.api.deleteCases(); + }); + + it('should fetch the status correctly with internal request headers', async () => { + await supertestWithoutAuth + .get(CASE_USER_ACTIONS_URL) + .set(svlCommonApi.getInternalRequestHeader()) + .set(roleAuthc.apiKeyHeader) + .expect(200); + }); + + it('should not fetch the status correctly with no internal request headers', async () => { + await supertestWithoutAuth.get(CASE_USER_ACTIONS_URL).set(roleAuthc.apiKeyHeader).expect(400); + }); + }); +}; diff --git a/x-pack/test_serverless/api_integration/test_suites/observability/cases/get_case.ts b/x-pack/test_serverless/api_integration/test_suites/observability/cases/get_case.ts index 8b1cb4a2561fe..5e38b9153f611 100644 --- a/x-pack/test_serverless/api_integration/test_suites/observability/cases/get_case.ts +++ b/x-pack/test_serverless/api_integration/test_suites/observability/cases/get_case.ts @@ -36,7 +36,7 @@ export default ({ getService }: FtrProviderContext): void => { const theCase = await svlCases.api.getCase( { caseId: postedCase.id, - includeComments: true, + expectedHttpCode: 200, }, roleAuthc ); @@ -47,7 +47,22 @@ export default ({ getService }: FtrProviderContext): void => { expect(data).to.eql(expectedData); expect(createdBy).to.have.keys('full_name', 'email', 'username'); - expect(data.comments?.length).to.eql(0); + }); + + it('should throw a 400 if the query param includeComments is being used', async () => { + const postedCase = await svlCases.api.createCase( + svlCases.api.getPostCaseRequest('observability'), + roleAuthc + ); + + await svlCases.api.getCase( + { + caseId: postedCase.id, + includeComments: true, + expectedHttpCode: 400, + }, + roleAuthc + ); }); }); }; diff --git a/x-pack/test_serverless/api_integration/test_suites/observability/cases/get_status.ts b/x-pack/test_serverless/api_integration/test_suites/observability/cases/get_status.ts new file mode 100644 index 0000000000000..39527cb12f4ba --- /dev/null +++ b/x-pack/test_serverless/api_integration/test_suites/observability/cases/get_status.ts @@ -0,0 +1,45 @@ +/* + * 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 { CASE_STATUS_URL } from '@kbn/cases-plugin/common/constants'; +import type { RoleCredentials } from '../../../../shared/services'; +import { FtrProviderContext } from '../../../ftr_provider_context'; + +export default ({ getService }: FtrProviderContext): void => { + const svlCases = getService('svlCases'); + const svlUserManager = getService('svlUserManager'); + const supertestWithoutAuth = getService('supertestWithoutAuth'); + const svlCommonApi = getService('svlCommonApi'); + + describe('get_status', () => { + let roleAuthc: RoleCredentials; + + before(async () => { + roleAuthc = await svlUserManager.createM2mApiKeyWithRoleScope('admin'); + }); + + after(async () => { + await svlUserManager.invalidateM2mApiKeyWithRoleScope(roleAuthc); + }); + + afterEach(async () => { + await svlCases.api.deleteCases(); + }); + + it('should fetch the status correctly with internal request headers', async () => { + await supertestWithoutAuth + .get(CASE_STATUS_URL) + .set(svlCommonApi.getInternalRequestHeader()) + .set(roleAuthc.apiKeyHeader) + .expect(200); + }); + + it('should not fetch the status correctly with no internal request headers', async () => { + await supertestWithoutAuth.get(CASE_STATUS_URL).set(roleAuthc.apiKeyHeader).expect(400); + }); + }); +}; diff --git a/x-pack/test_serverless/api_integration/test_suites/observability/cases/index.ts b/x-pack/test_serverless/api_integration/test_suites/observability/cases/index.ts index 97e56b4220124..8a4ba7258b04d 100644 --- a/x-pack/test_serverless/api_integration/test_suites/observability/cases/index.ts +++ b/x-pack/test_serverless/api_integration/test_suites/observability/cases/index.ts @@ -12,5 +12,8 @@ export default function ({ loadTestFile }: FtrProviderContext) { loadTestFile(require.resolve('./get_case')); loadTestFile(require.resolve('./find_cases')); loadTestFile(require.resolve('./post_case')); + loadTestFile(require.resolve('./get_status')); + loadTestFile(require.resolve('./get_all_comments')); + loadTestFile(require.resolve('./get_all_user_actions')); }); } diff --git a/x-pack/test_serverless/api_integration/test_suites/security/cases/get_case.ts b/x-pack/test_serverless/api_integration/test_suites/security/cases/get_case.ts index 6886ade38ad78..052a1f9bf9d3a 100644 --- a/x-pack/test_serverless/api_integration/test_suites/security/cases/get_case.ts +++ b/x-pack/test_serverless/api_integration/test_suites/security/cases/get_case.ts @@ -31,7 +31,7 @@ export default ({ getService }: FtrProviderContext): void => { const theCase = await svlCases.api.getCase( { caseId: postedCase.id, - includeComments: true, + expectedHttpCode: 200, }, roleAuthc ); @@ -41,7 +41,22 @@ export default ({ getService }: FtrProviderContext): void => { const { created_by: _, ...expectedData } = svlCases.api.postCaseResp('securitySolution'); expect(data).to.eql(expectedData); expect(createdBy).to.have.keys('full_name', 'email', 'username'); - expect(data.comments?.length).to.eql(0); + }); + + it('should throw a 400 if the query param includeComments is being used', async () => { + const postedCase = await svlCases.api.createCase( + svlCases.api.getPostCaseRequest('securitySolution'), + roleAuthc + ); + + await svlCases.api.getCase( + { + caseId: postedCase.id, + includeComments: true, + expectedHttpCode: 400, + }, + roleAuthc + ); }); }); };