Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 2 additions & 0 deletions .gitignore
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,8 @@
**/node_modules
**/dist
**/.DS_Store
**/integration-tests/results
**/test-results

# https://next.yarnpkg.com/getting-started/qa#which-files-should-be-gitignored
.pnp.*
Expand Down
5 changes: 3 additions & 2 deletions jest.config.ts
Original file line number Diff line number Diff line change
@@ -1,11 +1,12 @@
import type { InitialOptionsTsJest } from 'ts-jest';
import type { JestConfigWithTsJest } from 'ts-jest';

const config: InitialOptionsTsJest = {
const config: JestConfigWithTsJest = {
projects: [
'<rootDir>/packages/common',
'<rootDir>/packages/lib-core',
'<rootDir>/packages/lib-utils',
'<rootDir>/packages/lib-webpack',
'<rootDir>/packages/sample-app',
],

collectCoverage: true,
Expand Down
36 changes: 16 additions & 20 deletions package.json
Original file line number Diff line number Diff line change
Expand Up @@ -11,23 +11,21 @@
"run-samples": "yarn workspaces foreach -Api --include 'packages/sample-*' run http-server",
"lint": "yarn eslint packages",
"test": "yarn jest",
"test-component": "yarn sample-app-test-component",
"test-e2e": "start-server-and-test 'yarn run-samples' '127.0.0.1:9000|127.0.0.1:9001' 'yarn sample-app-test-e2e'",
"test-e2e": "yarn workspace @monorepo/sample-app run test-e2e-headless",
"eslint": "eslint --max-warnings 0 --ext .js,.jsx,.ts,.tsx --rulesdir ./packages/eslint-plugin-internal/src/runtime-rules",
"eslint-print-config": "yarn eslint --print-config",
"jest": "TZ=UTC jest --passWithNoTests",
"jest-print-config": "jest --showConfig",
"sample-app-install-cypress": "yarn workspace @monorepo/sample-app run cypress install",
"sample-app-test-component": "yarn workspace @monorepo/sample-app run cypress run --component",
"sample-app-test-e2e": "yarn workspace @monorepo/sample-app run cypress run --e2e",
"api-extractor": "api-extractor run --typescript-compiler-folder ./node_modules/typescript/lib",

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Note - when running e.g. (cd packages/lib-core ; yarn api-extractor) this has resulted in

--typescript-compiler-folder packages/lib-core/node_modules/typescript/lib

which does not exist, so we're using $PROJECT_CWD which always points to workspace root directory.

"api-extractor": "api-extractor run --typescript-compiler-folder $PROJECT_CWD/node_modules/typescript/lib",
"api-extractor-local": "yarn workspaces foreach -A --include 'packages/lib-*' run api-extractor-local"
},
"devDependencies": {
"@babel/core": "^7.18.6",
"@microsoft/api-documenter": "^7.19.24",
"@microsoft/api-extractor": "^7.33.6",
"@microsoft/api-documenter": "^7.30.5",
"@microsoft/api-extractor": "^7.58.7",
"@optimize-lodash/rollup-plugin": "^4.0.3",
"@playwright/browser-chromium": "^1.60.0",
"@playwright/test": "^1.60.0",
"@rollup/plugin-commonjs": "^21.0.2",
"@rollup/plugin-json": "^5.0.2",
"@rollup/plugin-node-resolve": "^13.1.1",
Expand All @@ -37,7 +35,7 @@
"@testing-library/react": "^16.3.2",
"@testing-library/user-event": "^14.6.1",
"@types/glob": "^7.2.0",
"@types/jest": "^27.5.2",
"@types/jest": "^29.5.0",
"@types/jest-axe": "^3.5.4",
"@types/lodash": "^4.14.192",
"@types/node": "^16.11.12",
Expand All @@ -46,8 +44,8 @@
"@types/react-dom": "^18.3.0",
"@types/semver": "^7.7.1",
"@types/uuid": "^8.3.4",
"@typescript-eslint/eslint-plugin": "^5.3.1",
"@typescript-eslint/parser": "^5.3.1",
"@typescript-eslint/eslint-plugin": "^5.62.0",
"@typescript-eslint/parser": "^5.62.0",
"babel-loader": "^8.2.5",
"eslint": "^8.57.1",
"eslint-config-airbnb": "^19.0.0",
Expand All @@ -64,33 +62,31 @@
"eslint-plugin-react-hooks": "^4.3.0",
"find-up": "^5.0.0",
"identity-obj-proxy": "^3.0.0",
"jest": "^27.5.1",
"jest-axe": "^6.0.0",
"jest": "^29.7.0",
"jest-axe": "^10.0.0",
"jest-environment-jsdom": "^29.7.0",
"jsonc-parser": "^3.2.0",
"lodash": "^4.17.23",
"minimatch": "^3.1.2",
"prettier": "^3.8.3",
"prettier-plugin-organize-imports": "^4.3.0",
"react": "^18.3.1",
"react-dom": "^18.3.1",
"react-redux": "^8.0.5",
"react-router": "^6.3.0",
"react-router-dom": "^6.3.0",
"redux": "^4.1.2",
"redux-thunk": "^2.4.1",
"rollup": "^2.61.1",
"rollup-plugin-analyzer": "^4.0.0",
"rollup-plugin-import-css": "^3.0.3",
"start-server-and-test": "^2.0.1",
"ts-jest": "^27.1.4",
"ts-node": "^10.7.0",
"ts-jest": "^29.4.0",
"ts-node": "^10.9.2",
"tslib": "^2.3.1",
"type-fest": "^2.18.0",
"typescript": "~4.4.4",
"typescript": "^5.9.3",
"webpack": "^5.100.0"
},
"dependenciesMeta": {
"cypress": {
"@playwright/browser-chromium": {
"built": true
}
},
Expand Down
4 changes: 2 additions & 2 deletions packages/common/jest.config.ts
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
import reactConfig from '@monorepo/common/jest/jest-config-react';
import type { InitialOptionsTsJest } from 'ts-jest';
import type { JestConfigWithTsJest } from 'ts-jest';

const config: InitialOptionsTsJest = {
const config: JestConfigWithTsJest = {
...reactConfig,
displayName: 'common',
};
Expand Down
8 changes: 5 additions & 3 deletions packages/common/jest/jest-config-base.ts
Original file line number Diff line number Diff line change
@@ -1,11 +1,13 @@
import type { InitialOptionsTsJest } from 'ts-jest';
import type { JestConfigWithTsJest } from 'ts-jest';

const config: InitialOptionsTsJest = {
const config: JestConfigWithTsJest = {
// https://kulshekhar.github.io/ts-jest/docs/getting-started/presets
preset: 'ts-jest/presets/js-with-ts',

testMatch: ['**/*.test.(js|jsx|ts|tsx)'],
transformIgnorePatterns: ['/node_modules/'],

// Allow transforming ESM-only packages like uuid
transformIgnorePatterns: ['/node_modules/(?!uuid/)'],

moduleFileExtensions: ['ts', 'tsx', 'js', 'jsx', 'json'],
moduleNameMapper: {
Expand Down
15 changes: 9 additions & 6 deletions packages/common/jest/jest-config-node.ts
Original file line number Diff line number Diff line change
@@ -1,15 +1,18 @@
import path from 'path';
import type { InitialOptionsTsJest } from 'ts-jest';
import type { JestConfigWithTsJest } from 'ts-jest';
import baseConfig from './jest-config-base';

const config: InitialOptionsTsJest = {
const config: JestConfigWithTsJest = {
...baseConfig,
testEnvironment: 'node',

globals: {
'ts-jest': {
tsconfig: path.resolve(__dirname, '../tsconfig-bases/lib-node-cjs.json'),
},
transform: {
'^.+\\.(jsx?|tsx?)$': [
'ts-jest',
{
tsconfig: path.resolve(__dirname, '../tsconfig-bases/lib-node-cjs.json'),
},
],
},
};

Expand Down
15 changes: 9 additions & 6 deletions packages/common/jest/jest-config-react.ts
Original file line number Diff line number Diff line change
@@ -1,8 +1,8 @@
import path from 'path';
import type { InitialOptionsTsJest } from 'ts-jest';
import type { JestConfigWithTsJest } from 'ts-jest';
import baseConfig from './jest-config-base';

const config: InitialOptionsTsJest = {
const config: JestConfigWithTsJest = {
...baseConfig,
testEnvironment: 'jsdom',

Expand All @@ -13,10 +13,13 @@ const config: InitialOptionsTsJest = {

setupFilesAfterEnv: [path.resolve(__dirname, 'setup-react.ts')],

globals: {
'ts-jest': {
tsconfig: path.resolve(__dirname, '../tsconfig-bases/lib-react-esm.json'),
},
transform: {
'^.+\\.(jsx?|tsx?)$': [
'ts-jest',
{
tsconfig: path.resolve(__dirname, '../tsconfig-bases/lib-react-esm.json'),
},
],
},
};

Expand Down
3 changes: 3 additions & 0 deletions packages/common/jest/setup-react.ts
Original file line number Diff line number Diff line change
@@ -1,9 +1,12 @@
// This adds custom Jest matchers for working with the DOM
// https://github.com/testing-library/jest-dom#custom-matchers
import '@testing-library/jest-dom';
import { configure } from '@testing-library/react';
import { toHaveNoViolations } from 'jest-axe';
import { noop } from 'lodash';

configure({ testIdAttribute: 'data-test-id' });

expect.extend(toHaveNoViolations);

jest.mock('react', () => ({
Expand Down
3 changes: 1 addition & 2 deletions packages/lib-api-types/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -31,7 +31,6 @@
"@types/js-yaml": "^4.0.9",
"@types/json-schema": "^7.0.15",
"js-yaml": "^4.1.1",
"json-schema-to-typescript": "^15.0.4",
"typescript": "^5.9.2"
"json-schema-to-typescript": "^15.0.4"
}
}
4 changes: 2 additions & 2 deletions packages/lib-core/jest.config.ts
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
import reactConfig from '@monorepo/common/jest/jest-config-react';
import type { InitialOptionsTsJest } from 'ts-jest';
import type { JestConfigWithTsJest } from 'ts-jest';

const config: InitialOptionsTsJest = {
const config: JestConfigWithTsJest = {
...reactConfig,
displayName: 'lib-core',
};
Expand Down
4 changes: 2 additions & 2 deletions packages/lib-utils/jest.config.ts
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
import reactConfig from '@monorepo/common/jest/jest-config-react';
import type { InitialOptionsTsJest } from 'ts-jest';
import type { JestConfigWithTsJest } from 'ts-jest';

const config: InitialOptionsTsJest = {
const config: JestConfigWithTsJest = {
...reactConfig,
displayName: 'lib-utils',
};
Expand Down
3 changes: 3 additions & 0 deletions packages/lib-utils/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -40,5 +40,8 @@
"pluralize": "^8.0.0",
"typesafe-actions": "^4.4.2",
"uuid": "^8.3.2"
},
"devDependencies": {
"react-redux": "^8.0.5"
}
}
2 changes: 1 addition & 1 deletion packages/lib-utils/src/k8s/hooks/use-model-types.ts
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,6 @@ import type {
export type UseK8sModel = (
// Use K8sGroupVersionKind type instead of K8sResourceKindReference. Support for type K8sResourceKindReference will be removed in a future release.
groupVersionKind: K8sResourceKindReference | K8sGroupVersionKind,
) => [K8sModelCommon, boolean];
) => [K8sModelCommon | undefined, boolean];

export type UseK8sModels = () => [{ [key: string]: K8sModelCommon }, boolean];
6 changes: 4 additions & 2 deletions packages/lib-utils/src/k8s/hooks/useK8sModel.ts
Original file line number Diff line number Diff line change
Expand Up @@ -14,7 +14,7 @@ import type { UseK8sModel } from './use-model-types';
export const getK8sModel = (
k8s: K8sState,
k8sGroupVersionKind: K8sResourceKindReference | K8sGroupVersionKind,
): K8sModelCommon => {
): K8sModelCommon | undefined => {
const kindReference = transformGroupVersionKindToReference(k8sGroupVersionKind);
return kindReference
? (k8s?.getIn(['RESOURCES', 'models', kindReference]) ??
Expand All @@ -36,6 +36,8 @@ export const getK8sModel = (
* ```
*/
export const useK8sModel: UseK8sModel = (k8sGroupVersionKind) => [
useSelector<SDKStoreState, K8sModelCommon>(({ k8s }) => getK8sModel(k8s, k8sGroupVersionKind)),
useSelector<SDKStoreState, K8sModelCommon | undefined>(({ k8s }) =>
getK8sModel(k8s, k8sGroupVersionKind),
),
useSelector<SDKStoreState, boolean>(({ k8s }) => k8s?.getIn(['RESOURCES', 'inFlight']) ?? false),
];
12 changes: 6 additions & 6 deletions packages/lib-utils/src/k8s/hooks/useK8sWatchResource.test.ts
Original file line number Diff line number Diff line change
Expand Up @@ -66,12 +66,12 @@ jest.mock('react-redux', () => ({
useSelector: jest.fn(),
}));

const useSelectorMock = jest.mocked(useSelector, false);
const useModelsLoadedMock = jest.mocked(useModelsLoaded, false);
const useDeepCompareMemoizeMock = jest.mocked(useDeepCompareMemoize, false);
const useK8sModelMock = jest.mocked(useK8sModel, false);
const getWatchDataMock = jest.mocked(getWatchData, false);
const getReduxDataMock = jest.mocked(getReduxData, false);
const useSelectorMock = jest.mocked(useSelector);
const useModelsLoadedMock = jest.mocked(useModelsLoaded);
const useDeepCompareMemoizeMock = jest.mocked(useDeepCompareMemoize);
const useK8sModelMock = jest.mocked(useK8sModel);
const getWatchDataMock = jest.mocked(getWatchData);
const getReduxDataMock = jest.mocked(getReduxData);

describe('useK8sWatchResource', () => {
beforeEach(() => {
Expand Down
10 changes: 5 additions & 5 deletions packages/lib-utils/src/k8s/hooks/useK8sWatchResources.test.ts
Original file line number Diff line number Diff line change
Expand Up @@ -64,11 +64,11 @@ jest.mock('./useModelsLoaded', () => ({ useModelsLoaded: jest.fn() }));

jest.mock('./useDeepCompareMemoize', () => ({ useDeepCompareMemoize: jest.fn() }));

const useSelectorMock = jest.mocked(useSelector, false);
const useModelsLoadedMock = jest.mocked(useModelsLoaded, false);
const useDeepCompareMemoizeMock = jest.mocked(useDeepCompareMemoize, false);
const getWatchDataMock = jest.mocked(getWatchData, false);
const getReduxDataMock = jest.mocked(getReduxData, false);
const useSelectorMock = jest.mocked(useSelector);
const useModelsLoadedMock = jest.mocked(useModelsLoaded);
const useDeepCompareMemoizeMock = jest.mocked(useDeepCompareMemoize);
const getWatchDataMock = jest.mocked(getWatchData);
const getReduxDataMock = jest.mocked(getReduxData);

describe('useK8sWatchResources', () => {
beforeEach(() => {
Expand Down
4 changes: 4 additions & 0 deletions packages/lib-utils/src/k8s/hooks/useK8sWatchResources.ts
Original file line number Diff line number Diff line change
Expand Up @@ -139,12 +139,16 @@ export const useK8sWatchResources = <R extends ResourcesObject>(
useEffect(() => {
const reduxIDKeys = Object.keys(reduxIDs || {});
reduxIDKeys.forEach((k) => {
// eslint-disable-next-line @typescript-eslint/ban-ts-comment
// @ts-expect-error
if (reduxIDs?.[k] && reduxIDs[k].action) {
dispatch(reduxIDs[k].action);
}
});
return () => {
reduxIDKeys.forEach((k) => {
// eslint-disable-next-line @typescript-eslint/ban-ts-comment
// @ts-expect-error
if (reduxIDs?.[k] && reduxIDs[k].action) {
dispatch(k8sActions.stopK8sWatch(reduxIDs[k].id));
}
Expand Down
4 changes: 2 additions & 2 deletions packages/lib-webpack/jest.config.ts
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
import nodeConfig from '@monorepo/common/jest/jest-config-node';
import type { InitialOptionsTsJest } from 'ts-jest';
import type { JestConfigWithTsJest } from 'ts-jest';

const config: InitialOptionsTsJest = {
const config: JestConfigWithTsJest = {
...nodeConfig,
displayName: 'lib-webpack',
};
Expand Down
24 changes: 0 additions & 24 deletions packages/sample-app/cypress.config.ts

This file was deleted.

34 changes: 34 additions & 0 deletions packages/sample-app/integration-tests/tests/app.spec.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,34 @@
import { test, expect } from '@playwright/test';

test.describe('Sample Plugin Host Application', () => {
test('Loads the sample plugin', async ({ page }) => {
await page.goto('/');

const table = page.getByTestId('plugin-table');
await expect(table.locator('tbody')).toContainText('No plugins detected');

const openButton = page.getByTestId('plugin-modal-open');
await expect(openButton).toHaveText('Load remote plugin');
await openButton.click();

const urlInput = page.getByTestId('plugin-modal-url');
await expect(urlInput).toHaveValue('http://localhost:9001/plugin-manifest.json');

const loadButton = page.getByTestId('plugin-modal-load');
await expect(loadButton).toBeEnabled();
await expect(loadButton).toHaveText('Load');
await loadButton.click();

await expect(table.locator('tbody')).not.toContainText('No plugins detected');

const rows = table.locator('tbody > tr');
await expect(rows).toHaveCount(1);

const row = rows.first();
await expect(row.locator('td[data-label="Name"]')).toContainText('sample-plugin');
await expect(row.locator('td[data-label="Version"]')).toContainText('1.2.3');
await expect(row.locator('td[data-label="Status"]')).toContainText('loaded');
await expect(row.locator('td[data-label="Extensions"]')).toContainText('2');
await expect(row.locator('td[data-label="Enabled"]')).toContainText('Yes');
});
});
Loading