diff --git a/packages/app/package.json b/packages/app/package.json index 814b671c95..ecbcaf4961 100644 --- a/packages/app/package.json +++ b/packages/app/package.json @@ -29,7 +29,7 @@ "@backstage/plugin-cloudbuild": "^0.3.6-next.1", "@backstage/plugin-code-coverage": "^0.1.33-next.1", "@backstage/plugin-cost-insights": "^0.11.28-next.1", - "@backstage/plugin-dynatrace": "^0.1.0", + "@backstage/plugin-dynatrace": "^0.0.0", "@backstage/plugin-explore": "^0.3.37-next.1", "@backstage/plugin-gcalendar": "^0.3.2-next.1", "@backstage/plugin-gcp-projects": "^0.3.25-next.1", diff --git a/plugins/dynatrace/package.json b/plugins/dynatrace/package.json index 5ff08529e6..570dfa1a40 100644 --- a/plugins/dynatrace/package.json +++ b/plugins/dynatrace/package.json @@ -1,6 +1,6 @@ { "name": "@backstage/plugin-dynatrace", - "version": "0.1.0", + "version": "0.0.0", "main": "src/index.ts", "types": "src/index.ts", "license": "Apache-2.0", diff --git a/plugins/dynatrace/src/api/DynatraceApi.ts b/plugins/dynatrace/src/api/DynatraceApi.ts index 40676e3d09..1865b20363 100644 --- a/plugins/dynatrace/src/api/DynatraceApi.ts +++ b/plugins/dynatrace/src/api/DynatraceApi.ts @@ -23,7 +23,7 @@ export type DynatraceEntity = { name: string; }; -export type Problem = { +export type DynatraceProblem = { problemId: string; impactLevel: string; status: string; @@ -35,8 +35,8 @@ export type Problem = { affectedEntities: Array; }; -export interface Problems { - problems: Array; +export interface DynatraceProblems { + problems: Array; } export const dynatraceApiRef = createApiRef({ @@ -44,5 +44,7 @@ export const dynatraceApiRef = createApiRef({ }); export type DynatraceApi = { - getProblems(dynatraceEntityId: string): Promise; + getDynatraceProblems( + dynatraceEntityId: string, + ): Promise; }; diff --git a/plugins/dynatrace/src/api/DynatraceClient.ts b/plugins/dynatrace/src/api/DynatraceClient.ts index 157e840749..ae352106d0 100644 --- a/plugins/dynatrace/src/api/DynatraceClient.ts +++ b/plugins/dynatrace/src/api/DynatraceClient.ts @@ -13,23 +13,30 @@ * See the License for the specific language governing permissions and * limitations under the License. */ -import fetch from 'cross-fetch'; -import { Problems, DynatraceApi } from './DynatraceApi'; -import { DiscoveryApi, IdentityApi } from '@backstage/core-plugin-api'; +import { DynatraceProblems, DynatraceApi } from './DynatraceApi'; +import { + DiscoveryApi, + IdentityApi, + FetchApi, +} from '@backstage/core-plugin-api'; export class DynatraceClient implements DynatraceApi { discoveryApi: DiscoveryApi; identityApi: IdentityApi; + fetchApi: FetchApi; constructor({ discoveryApi, identityApi, + fetchApi, }: { discoveryApi: DiscoveryApi; identityApi: IdentityApi; + fetchApi: FetchApi; }) { this.discoveryApi = discoveryApi; this.identityApi = identityApi; + this.fetchApi = fetchApi; } private async callApi( @@ -39,7 +46,7 @@ export class DynatraceClient implements DynatraceApi { const { token: idToken } = await this.identityApi.getCredentials(); const apiUrl = `${await this.discoveryApi.getBaseUrl('proxy')}/dynatrace`; - const response = await fetch( + const response = await this.fetchApi.fetch( `${apiUrl}/${path}?${new URLSearchParams(query).toString()}`, { headers: { @@ -54,7 +61,9 @@ export class DynatraceClient implements DynatraceApi { return undefined; } - async getProblems(dynatraceEntityId: string): Promise { + async getDynatraceProblems( + dynatraceEntityId: string, + ): Promise { if (!dynatraceEntityId) { return undefined; } diff --git a/plugins/dynatrace/src/api/index.ts b/plugins/dynatrace/src/api/index.ts index 3924f373b5..97e33c9281 100644 --- a/plugins/dynatrace/src/api/index.ts +++ b/plugins/dynatrace/src/api/index.ts @@ -13,6 +13,10 @@ * See the License for the specific language governing permissions and * limitations under the License. */ -export type { Problems, Problem, DynatraceEntity } from './DynatraceApi'; +export type { + DynatraceProblems, + DynatraceProblem, + DynatraceEntity, +} from './DynatraceApi'; export { dynatraceApiRef } from './DynatraceApi'; export { DynatraceClient } from './DynatraceClient'; diff --git a/plugins/dynatrace/src/components/Problems/ProblemStatus/ProblemStatus.tsx b/plugins/dynatrace/src/components/Problems/ProblemStatus/ProblemStatus.tsx index 5605be6e44..2ed861963a 100644 --- a/plugins/dynatrace/src/components/Problems/ProblemStatus/ProblemStatus.tsx +++ b/plugins/dynatrace/src/components/Problems/ProblemStatus/ProblemStatus.tsx @@ -14,10 +14,10 @@ * limitations under the License. */ import React from 'react'; -import { Problem } from '../../../api/DynatraceApi'; +import { DynatraceProblem } from '../../../api/DynatraceApi'; import { StatusError, StatusOK } from '@backstage/core-components'; -export const ProblemStatus = ({ status }: Partial) => { +export const ProblemStatus = ({ status }: Partial) => { switch (status?.toLocaleLowerCase()) { case 'open': return ( diff --git a/plugins/dynatrace/src/components/Problems/ProblemsList/ProblemsList.test.tsx b/plugins/dynatrace/src/components/Problems/ProblemsList/ProblemsList.test.tsx index dfeb311c33..1249f4e886 100644 --- a/plugins/dynatrace/src/components/Problems/ProblemsList/ProblemsList.test.tsx +++ b/plugins/dynatrace/src/components/Problems/ProblemsList/ProblemsList.test.tsx @@ -22,7 +22,7 @@ import { ApiProvider, ConfigReader } from '@backstage/core-app-api'; import { configApiRef } from '@backstage/core-plugin-api'; const mockDynatraceApi = { - getProblems: jest.fn(), + getDynatraceProblems: jest.fn(), }; const apis = TestApiRegistry.from( [dynatraceApiRef, mockDynatraceApi], @@ -31,7 +31,9 @@ const apis = TestApiRegistry.from( describe('ProblemStatus', () => { it('renders a table with problem data', async () => { - mockDynatraceApi.getProblems = jest.fn().mockResolvedValue({ problems }); + mockDynatraceApi.getDynatraceProblems = jest + .fn() + .mockResolvedValue({ problems }); const rendered = await renderInTestApp( @@ -40,7 +42,7 @@ describe('ProblemStatus', () => { expect(await rendered.findByText('example-service')).toBeInTheDocument(); }); it('renders "nothing to report :)" if no problems are found', async () => { - mockDynatraceApi.getProblems = jest.fn().mockResolvedValue({}); + mockDynatraceApi.getDynatraceProblems = jest.fn().mockResolvedValue({}); const rendered = await renderInTestApp( diff --git a/plugins/dynatrace/src/components/Problems/ProblemsList/ProblemsList.tsx b/plugins/dynatrace/src/components/Problems/ProblemsList/ProblemsList.tsx index b12b8fe41a..ac69abf93e 100644 --- a/plugins/dynatrace/src/components/Problems/ProblemsList/ProblemsList.tsx +++ b/plugins/dynatrace/src/components/Problems/ProblemsList/ProblemsList.tsx @@ -29,8 +29,7 @@ export const ProblemsList = (props: ProblemsListProps) => { const { dynatraceEntityId } = props; const dynatraceApi = useApi(dynatraceApiRef); const { value, loading, error } = useAsync(async () => { - const r = await dynatraceApi.getProblems(dynatraceEntityId); - return r; + return dynatraceApi.getDynatraceProblems(dynatraceEntityId); }, [dynatraceApi, dynatraceEntityId]); const problems = value?.problems; diff --git a/plugins/dynatrace/src/components/Problems/ProblemsTable/ProblemsTable.tsx b/plugins/dynatrace/src/components/Problems/ProblemsTable/ProblemsTable.tsx index ba1a2e19d9..8e3d330c37 100644 --- a/plugins/dynatrace/src/components/Problems/ProblemsTable/ProblemsTable.tsx +++ b/plugins/dynatrace/src/components/Problems/ProblemsTable/ProblemsTable.tsx @@ -15,14 +15,14 @@ */ import React from 'react'; import { Table, TableColumn } from '@backstage/core-components'; -import { Problem } from '../../../api/DynatraceApi'; +import { DynatraceProblem } from '../../../api/DynatraceApi'; import { ProblemStatus } from '../ProblemStatus'; import { configApiRef } from '@backstage/core-plugin-api'; import { useApi } from '@backstage/core-plugin-api'; import { Link } from '@material-ui/core'; type ProblemsTableProps = { - problems: Problem[]; + problems: DynatraceProblem[]; }; export const ProblemsTable = ({ problems }: ProblemsTableProps) => { @@ -32,7 +32,7 @@ export const ProblemsTable = ({ problems }: ProblemsTableProps) => { { title: 'Title', field: 'title', - render: (row: Partial) => ( + render: (row: Partial) => ( @@ -43,29 +43,32 @@ export const ProblemsTable = ({ problems }: ProblemsTableProps) => { { title: 'Status', field: 'status', - render: (row: Partial) => , + render: (row: Partial) => ( + + ), }, { title: 'Severity', field: 'severityLevel' }, { title: 'Root Cause', field: 'rootCauseEntity', - render: (row: Partial) => row.rootCauseEntity?.name, + render: (row: Partial) => row.rootCauseEntity?.name, }, { title: 'Affected', field: 'affectedEntities', - render: (row: Partial) => row.affectedEntities?.map(e => e.name), + render: (row: Partial) => + row.affectedEntities?.map(e => e.name), }, { title: 'Start Time', field: 'startTime', - render: (row: Partial) => + render: (row: Partial) => new Date(row.startTime || 0).toString(), }, { title: 'End Time', field: 'endTime', - render: (row: Partial) => + render: (row: Partial) => row.endTime === -1 ? 'ongoing' : new Date(row.endTime || 0).toString(), }, ]; diff --git a/plugins/dynatrace/src/plugin.ts b/plugins/dynatrace/src/plugin.ts index 74e5544341..2bf1353e13 100644 --- a/plugins/dynatrace/src/plugin.ts +++ b/plugins/dynatrace/src/plugin.ts @@ -19,6 +19,7 @@ import { createPlugin, discoveryApiRef, identityApiRef, + fetchApiRef, createRoutableExtension, } from '@backstage/core-plugin-api'; @@ -38,11 +39,13 @@ export const dynatracePlugin = createPlugin({ deps: { discoveryApi: discoveryApiRef, identityApi: identityApiRef, + fetchApi: fetchApiRef, }, - factory: ({ discoveryApi, identityApi }) => + factory: ({ discoveryApi, identityApi, fetchApi }) => new DynatraceClient({ discoveryApi, identityApi, + fetchApi, }), }), ],