Merge branch 'master' into feature/10453-add-custom-options-catalog-table
This commit is contained in:
@@ -22,7 +22,7 @@
|
||||
"clean": "backstage-cli package clean"
|
||||
},
|
||||
"dependencies": {
|
||||
"@backstage/backend-common": "^0.13.2-next.0",
|
||||
"@backstage/backend-common": "^0.13.2-next.1",
|
||||
"@backstage/config": "^1.0.0",
|
||||
"@types/express": "*",
|
||||
"express": "^4.17.1",
|
||||
@@ -33,7 +33,7 @@
|
||||
"yn": "^4.0.0"
|
||||
},
|
||||
"devDependencies": {
|
||||
"@backstage/cli": "^0.16.1-next.0",
|
||||
"@backstage/cli": "^0.17.0-next.1",
|
||||
"@types/http-proxy-middleware": "^0.19.3",
|
||||
"@types/supertest": "^2.0.8",
|
||||
"supertest": "^6.1.6",
|
||||
|
||||
@@ -27,8 +27,8 @@
|
||||
"@backstage/core-components": "^0.9.3-next.0",
|
||||
"@backstage/core-plugin-api": "^1.0.0",
|
||||
"@backstage/dev-utils": "^1.0.1-next.0",
|
||||
"@backstage/plugin-catalog-react": "^1.0.1-next.0",
|
||||
"@backstage/test-utils": "^1.0.1-next.0",
|
||||
"@backstage/plugin-catalog-react": "^1.0.1-next.1",
|
||||
"@backstage/test-utils": "^1.0.1-next.1",
|
||||
"@backstage/theme": "^0.2.15",
|
||||
"@material-ui/core": "^4.12.2",
|
||||
"@material-ui/icons": "^4.9.1",
|
||||
@@ -40,10 +40,10 @@
|
||||
"react": "^16.13.1 || ^17.0.0"
|
||||
},
|
||||
"devDependencies": {
|
||||
"@backstage/app-defaults": "^1.0.1-next.0",
|
||||
"@backstage/cli": "^0.16.1-next.0",
|
||||
"@backstage/app-defaults": "^1.0.1-next.1",
|
||||
"@backstage/cli": "^0.17.0-next.1",
|
||||
"@backstage/dev-utils": "^1.0.1-next.0",
|
||||
"@backstage/test-utils": "^1.0.1-next.0",
|
||||
"@backstage/test-utils": "^1.0.1-next.1",
|
||||
"@testing-library/jest-dom": "^5.10.1",
|
||||
"@testing-library/react": "^12.1.3",
|
||||
"@testing-library/user-event": "^13.1.8",
|
||||
|
||||
@@ -28,7 +28,7 @@
|
||||
"@backstage/catalog-model": "^1.0.1-next.0",
|
||||
"@backstage/core-components": "^0.9.3-next.0",
|
||||
"@backstage/core-plugin-api": "^1.0.0",
|
||||
"@backstage/plugin-catalog-react": "^1.0.1-next.0",
|
||||
"@backstage/plugin-catalog-react": "^1.0.1-next.1",
|
||||
"@backstage/theme": "^0.2.15",
|
||||
"@material-ui/core": "^4.12.2",
|
||||
"@material-ui/icons": "^4.9.1",
|
||||
@@ -40,10 +40,10 @@
|
||||
"react": "^16.13.1 || ^17.0.0"
|
||||
},
|
||||
"devDependencies": {
|
||||
"@backstage/cli": "^0.16.1-next.0",
|
||||
"@backstage/cli": "^0.17.0-next.1",
|
||||
"@backstage/core-app-api": "^1.0.1-next.0",
|
||||
"@backstage/dev-utils": "^1.0.1-next.0",
|
||||
"@backstage/test-utils": "^1.0.1-next.0",
|
||||
"@backstage/test-utils": "^1.0.1-next.1",
|
||||
"@testing-library/jest-dom": "^5.10.1",
|
||||
"@testing-library/react": "^12.1.3",
|
||||
"@testing-library/user-event": "^13.1.8",
|
||||
|
||||
@@ -38,10 +38,10 @@
|
||||
"react": "^16.13.1 || ^17.0.0"
|
||||
},
|
||||
"devDependencies": {
|
||||
"@backstage/cli": "^0.16.1-next.0",
|
||||
"@backstage/cli": "^0.17.0-next.1",
|
||||
"@backstage/core-app-api": "^1.0.1-next.0",
|
||||
"@backstage/dev-utils": "^1.0.1-next.0",
|
||||
"@backstage/test-utils": "^1.0.1-next.0",
|
||||
"@backstage/test-utils": "^1.0.1-next.1",
|
||||
"@testing-library/jest-dom": "^5.10.1",
|
||||
"@testing-library/react": "^12.1.3",
|
||||
"@testing-library/user-event": "^13.1.8",
|
||||
|
||||
+5
-5
@@ -220,7 +220,7 @@ describe('GoogleAnalytics', () => {
|
||||
});
|
||||
|
||||
// Wait for any/all promises involved to settle.
|
||||
await new Promise(resolve => setImmediate(resolve));
|
||||
await new Promise(resolve => setTimeout(resolve));
|
||||
|
||||
// A pageview should have been fired immediately.
|
||||
const [command, data] = ReactGA.testModeAPI.calls[1];
|
||||
@@ -251,7 +251,7 @@ describe('GoogleAnalytics', () => {
|
||||
});
|
||||
|
||||
// Wait for any/all promises involved to settle.
|
||||
await new Promise(resolve => setImmediate(resolve));
|
||||
await new Promise(resolve => setTimeout(resolve));
|
||||
|
||||
// A pageview should have been fired immediately.
|
||||
const [command, data] = ReactGA.testModeAPI.calls[1];
|
||||
@@ -290,7 +290,7 @@ describe('GoogleAnalytics', () => {
|
||||
});
|
||||
|
||||
// Wait for any/all promises involved to settle.
|
||||
await new Promise(resolve => setImmediate(resolve));
|
||||
await new Promise(resolve => setTimeout(resolve));
|
||||
|
||||
// User ID should have been set after the pageview.
|
||||
const [setCommand, setData] = ReactGA.testModeAPI.calls[2];
|
||||
@@ -318,7 +318,7 @@ describe('GoogleAnalytics', () => {
|
||||
});
|
||||
|
||||
// Wait for any/all promises involved to settle.
|
||||
await new Promise(resolve => setImmediate(resolve));
|
||||
await new Promise(resolve => setTimeout(resolve));
|
||||
|
||||
// A pageview should have been fired immediately.
|
||||
const [command, data] = ReactGA.testModeAPI.calls[1];
|
||||
@@ -369,7 +369,7 @@ describe('GoogleAnalytics', () => {
|
||||
});
|
||||
|
||||
// Wait for any/all promises involved to settle.
|
||||
await new Promise(resolve => setImmediate(resolve));
|
||||
await new Promise(resolve => setTimeout(resolve));
|
||||
|
||||
// User ID should have been set first.
|
||||
const [setCommand, setData] = ReactGA.testModeAPI.calls[1];
|
||||
|
||||
@@ -36,10 +36,10 @@
|
||||
"react": "^16.13.1 || ^17.0.0"
|
||||
},
|
||||
"devDependencies": {
|
||||
"@backstage/cli": "^0.16.1-next.0",
|
||||
"@backstage/cli": "^0.17.0-next.1",
|
||||
"@backstage/core-app-api": "^1.0.1-next.0",
|
||||
"@backstage/dev-utils": "^1.0.1-next.0",
|
||||
"@backstage/test-utils": "^1.0.1-next.0",
|
||||
"@backstage/test-utils": "^1.0.1-next.1",
|
||||
"@testing-library/jest-dom": "^5.10.1",
|
||||
"@testing-library/react": "^12.1.3",
|
||||
"@testing-library/user-event": "^13.1.8",
|
||||
|
||||
@@ -1,5 +1,13 @@
|
||||
# @backstage/plugin-api-docs
|
||||
|
||||
## 0.8.4-next.1
|
||||
|
||||
### Patch Changes
|
||||
|
||||
- Updated dependencies
|
||||
- @backstage/plugin-catalog-react@1.0.1-next.1
|
||||
- @backstage/plugin-catalog@1.1.0-next.1
|
||||
|
||||
## 0.8.4-next.0
|
||||
|
||||
### Patch Changes
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
{
|
||||
"name": "@backstage/plugin-api-docs",
|
||||
"description": "A Backstage plugin that helps represent API entities in the frontend",
|
||||
"version": "0.8.4-next.0",
|
||||
"version": "0.8.4-next.1",
|
||||
"main": "src/index.ts",
|
||||
"types": "src/index.ts",
|
||||
"license": "Apache-2.0",
|
||||
@@ -37,8 +37,8 @@
|
||||
"@backstage/catalog-model": "^1.0.1-next.0",
|
||||
"@backstage/core-components": "^0.9.3-next.0",
|
||||
"@backstage/core-plugin-api": "^1.0.0",
|
||||
"@backstage/plugin-catalog": "^1.0.1-next.0",
|
||||
"@backstage/plugin-catalog-react": "^1.0.1-next.0",
|
||||
"@backstage/plugin-catalog": "^1.1.0-next.1",
|
||||
"@backstage/plugin-catalog-react": "^1.0.1-next.1",
|
||||
"@backstage/theme": "^0.2.15",
|
||||
"@material-ui/core": "^4.12.2",
|
||||
"@material-ui/icons": "^4.9.1",
|
||||
@@ -56,10 +56,10 @@
|
||||
"react": "^16.13.1 || ^17.0.0"
|
||||
},
|
||||
"devDependencies": {
|
||||
"@backstage/cli": "^0.16.1-next.0",
|
||||
"@backstage/cli": "^0.17.0-next.1",
|
||||
"@backstage/core-app-api": "^1.0.1-next.0",
|
||||
"@backstage/dev-utils": "^1.0.1-next.0",
|
||||
"@backstage/test-utils": "^1.0.1-next.0",
|
||||
"@backstage/test-utils": "^1.0.1-next.1",
|
||||
"@testing-library/jest-dom": "^5.10.1",
|
||||
"@testing-library/react": "^12.1.3",
|
||||
"@testing-library/user-event": "^13.1.8",
|
||||
|
||||
@@ -33,7 +33,7 @@
|
||||
"clean": "backstage-cli package clean"
|
||||
},
|
||||
"dependencies": {
|
||||
"@backstage/backend-common": "^0.13.2-next.0",
|
||||
"@backstage/backend-common": "^0.13.2-next.1",
|
||||
"@backstage/config-loader": "^1.0.1-next.0",
|
||||
"@backstage/config": "^1.0.0",
|
||||
"@backstage/types": "^1.0.0",
|
||||
@@ -50,8 +50,8 @@
|
||||
"yn": "^4.0.0"
|
||||
},
|
||||
"devDependencies": {
|
||||
"@backstage/backend-test-utils": "^0.1.23-next.0",
|
||||
"@backstage/cli": "^0.16.1-next.0",
|
||||
"@backstage/backend-test-utils": "^0.1.23-next.1",
|
||||
"@backstage/cli": "^0.17.0-next.1",
|
||||
"@backstage/types": "^1.0.0",
|
||||
"@types/supertest": "^2.0.8",
|
||||
"mock-fs": "^5.1.0",
|
||||
|
||||
@@ -1,5 +1,13 @@
|
||||
# @backstage/plugin-auth-backend
|
||||
|
||||
## 0.13.0-next.1
|
||||
|
||||
### Patch Changes
|
||||
|
||||
- a45bce06e3: Handle trailing slashes on GitHub `enterpriseInstanceUrl` settings
|
||||
- Updated dependencies
|
||||
- @backstage/backend-common@0.13.2-next.1
|
||||
|
||||
## 0.13.0-next.0
|
||||
|
||||
### Minor Changes
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
{
|
||||
"name": "@backstage/plugin-auth-backend",
|
||||
"description": "A Backstage backend plugin that handles authentication",
|
||||
"version": "0.13.0-next.0",
|
||||
"version": "0.13.0-next.1",
|
||||
"main": "src/index.ts",
|
||||
"types": "src/index.ts",
|
||||
"license": "Apache-2.0",
|
||||
@@ -34,7 +34,7 @@
|
||||
},
|
||||
"dependencies": {
|
||||
"@backstage/plugin-auth-node": "^0.2.0-next.0",
|
||||
"@backstage/backend-common": "^0.13.2-next.0",
|
||||
"@backstage/backend-common": "^0.13.2-next.1",
|
||||
"@backstage/catalog-client": "^1.0.1-next.0",
|
||||
"@backstage/catalog-model": "^1.0.1-next.0",
|
||||
"@backstage/config": "^1.0.0",
|
||||
@@ -76,8 +76,8 @@
|
||||
"yn": "^4.0.0"
|
||||
},
|
||||
"devDependencies": {
|
||||
"@backstage/backend-test-utils": "^0.1.23-next.0",
|
||||
"@backstage/cli": "^0.16.1-next.0",
|
||||
"@backstage/backend-test-utils": "^0.1.23-next.1",
|
||||
"@backstage/cli": "^0.17.0-next.1",
|
||||
"@types/body-parser": "^1.19.0",
|
||||
"@types/cookie-parser": "^1.4.2",
|
||||
"@types/express-session": "^1.17.2",
|
||||
|
||||
@@ -44,6 +44,8 @@ jest.mock('@google-cloud/firestore', () => ({
|
||||
Firestore: jest.fn().mockImplementation(() => firestoreMock),
|
||||
}));
|
||||
|
||||
jest.useFakeTimers('legacy');
|
||||
|
||||
describe('FirestoreKeyStore', () => {
|
||||
const key = {
|
||||
kid: '123',
|
||||
@@ -69,11 +71,6 @@ describe('FirestoreKeyStore', () => {
|
||||
|
||||
beforeEach(() => {
|
||||
jest.clearAllMocks();
|
||||
jest.useFakeTimers();
|
||||
});
|
||||
|
||||
afterEach(() => {
|
||||
jest.useRealTimers();
|
||||
});
|
||||
|
||||
it('can create an instance without settings', async () => {
|
||||
|
||||
@@ -318,9 +318,9 @@ export const createGithubProvider = (
|
||||
OAuthEnvironmentHandler.mapConfig(config, envConfig => {
|
||||
const clientId = envConfig.getString('clientId');
|
||||
const clientSecret = envConfig.getString('clientSecret');
|
||||
const enterpriseInstanceUrl = envConfig.getOptionalString(
|
||||
'enterpriseInstanceUrl',
|
||||
);
|
||||
const enterpriseInstanceUrl = envConfig
|
||||
.getOptionalString('enterpriseInstanceUrl')
|
||||
?.replace(/\/$/, '');
|
||||
const customCallbackUrl = envConfig.getOptionalString('callbackUrl');
|
||||
const authorizationUrl = enterpriseInstanceUrl
|
||||
? `${enterpriseInstanceUrl}/login/oauth/authorize`
|
||||
|
||||
@@ -23,7 +23,7 @@
|
||||
"start": "backstage-cli package start"
|
||||
},
|
||||
"dependencies": {
|
||||
"@backstage/backend-common": "^0.13.2-next.0",
|
||||
"@backstage/backend-common": "^0.13.2-next.1",
|
||||
"@backstage/config": "^1.0.0",
|
||||
"@backstage/errors": "^1.0.0",
|
||||
"jose": "^1.27.1",
|
||||
@@ -31,7 +31,7 @@
|
||||
"winston": "^3.2.1"
|
||||
},
|
||||
"devDependencies": {
|
||||
"@backstage/cli": "^0.16.1-next.0",
|
||||
"@backstage/cli": "^0.17.0-next.1",
|
||||
"msw": "^0.35.0",
|
||||
"uuid": "^8.0.0"
|
||||
},
|
||||
|
||||
@@ -23,7 +23,7 @@
|
||||
"clean": "backstage-cli package clean"
|
||||
},
|
||||
"dependencies": {
|
||||
"@backstage/backend-common": "^0.13.2-next.0",
|
||||
"@backstage/backend-common": "^0.13.2-next.1",
|
||||
"@backstage/config": "^1.0.0",
|
||||
"@backstage/plugin-azure-devops-common": "^0.2.2",
|
||||
"@types/express": "^4.17.6",
|
||||
@@ -35,7 +35,7 @@
|
||||
"yn": "^4.0.0"
|
||||
},
|
||||
"devDependencies": {
|
||||
"@backstage/cli": "^0.16.1-next.0",
|
||||
"@backstage/cli": "^0.17.0-next.1",
|
||||
"@types/supertest": "^2.0.8",
|
||||
"supertest": "^6.1.6",
|
||||
"msw": "^0.35.0"
|
||||
|
||||
@@ -32,7 +32,7 @@
|
||||
"clean": "backstage-cli package clean"
|
||||
},
|
||||
"devDependencies": {
|
||||
"@backstage/cli": "^0.16.1-next.0"
|
||||
"@backstage/cli": "^0.17.0-next.1"
|
||||
},
|
||||
"files": [
|
||||
"dist"
|
||||
|
||||
@@ -35,7 +35,7 @@
|
||||
"@backstage/core-plugin-api": "^1.0.0",
|
||||
"@backstage/errors": "^1.0.0",
|
||||
"@backstage/plugin-azure-devops-common": "^0.2.2",
|
||||
"@backstage/plugin-catalog-react": "^1.0.1-next.0",
|
||||
"@backstage/plugin-catalog-react": "^1.0.1-next.1",
|
||||
"@backstage/theme": "^0.2.15",
|
||||
"@material-ui/core": "^4.12.2",
|
||||
"@material-ui/icons": "^4.9.1",
|
||||
@@ -49,10 +49,10 @@
|
||||
"react": "^16.13.1 || ^17.0.0"
|
||||
},
|
||||
"devDependencies": {
|
||||
"@backstage/cli": "^0.16.1-next.0",
|
||||
"@backstage/cli": "^0.17.0-next.1",
|
||||
"@backstage/core-app-api": "^1.0.1-next.0",
|
||||
"@backstage/dev-utils": "^1.0.1-next.0",
|
||||
"@backstage/test-utils": "^1.0.1-next.0",
|
||||
"@backstage/test-utils": "^1.0.1-next.1",
|
||||
"@testing-library/jest-dom": "^5.10.1",
|
||||
"@testing-library/react": "^12.1.3",
|
||||
"@testing-library/user-event": "^13.1.8",
|
||||
|
||||
@@ -1,5 +1,13 @@
|
||||
# @backstage/plugin-badges-backend
|
||||
|
||||
## 0.1.25-next.1
|
||||
|
||||
### Patch Changes
|
||||
|
||||
- 4c93fd36ee: allow overriding `DefaultBadgeBuilder.getMarkdownCode`
|
||||
- Updated dependencies
|
||||
- @backstage/backend-common@0.13.2-next.1
|
||||
|
||||
## 0.1.25-next.0
|
||||
|
||||
### Patch Changes
|
||||
|
||||
@@ -122,6 +122,8 @@ export class DefaultBadgeBuilder implements BadgeBuilder {
|
||||
createBadgeSvg(options: BadgeOptions): Promise<string>;
|
||||
// (undocumented)
|
||||
getBadges(): Promise<BadgeInfo[]>;
|
||||
// (undocumented)
|
||||
protected getMarkdownCode(params: Badge, badgeUrl: string): string;
|
||||
}
|
||||
|
||||
// Warning: (ae-missing-release-tag) "RouterOptions" is exported by the package, but it is missing a release tag (@alpha, @beta, @public, or @internal)
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
{
|
||||
"name": "@backstage/plugin-badges-backend",
|
||||
"description": "A Backstage backend plugin that generates README badges for your entities",
|
||||
"version": "0.1.25-next.0",
|
||||
"version": "0.1.25-next.1",
|
||||
"main": "src/index.ts",
|
||||
"types": "src/index.ts",
|
||||
"license": "Apache-2.0",
|
||||
@@ -34,7 +34,7 @@
|
||||
"clean": "backstage-cli package clean"
|
||||
},
|
||||
"dependencies": {
|
||||
"@backstage/backend-common": "^0.13.2-next.0",
|
||||
"@backstage/backend-common": "^0.13.2-next.1",
|
||||
"@backstage/catalog-client": "^1.0.1-next.0",
|
||||
"@backstage/catalog-model": "^1.0.1-next.0",
|
||||
"@backstage/config": "^1.0.0",
|
||||
@@ -48,7 +48,7 @@
|
||||
"yn": "^4.0.0"
|
||||
},
|
||||
"devDependencies": {
|
||||
"@backstage/cli": "^0.16.1-next.0",
|
||||
"@backstage/cli": "^0.17.0-next.1",
|
||||
"@types/supertest": "^2.0.8",
|
||||
"supertest": "^6.1.3"
|
||||
},
|
||||
|
||||
@@ -70,7 +70,7 @@ export class DefaultBadgeBuilder implements BadgeBuilder {
|
||||
}
|
||||
}
|
||||
|
||||
private getMarkdownCode(params: Badge, badgeUrl: string): string {
|
||||
protected getMarkdownCode(params: Badge, badgeUrl: string): string {
|
||||
let altText = `${params.label}: ${params.message}`;
|
||||
if (params.description && params.description !== params.label) {
|
||||
altText = `${params.description}, ${altText}`;
|
||||
|
||||
@@ -34,7 +34,7 @@
|
||||
"@backstage/core-components": "^0.9.3-next.0",
|
||||
"@backstage/core-plugin-api": "^1.0.0",
|
||||
"@backstage/errors": "^1.0.0",
|
||||
"@backstage/plugin-catalog-react": "^1.0.1-next.0",
|
||||
"@backstage/plugin-catalog-react": "^1.0.1-next.1",
|
||||
"@backstage/theme": "^0.2.15",
|
||||
"@material-ui/core": "^4.12.2",
|
||||
"@material-ui/icons": "^4.9.1",
|
||||
@@ -46,10 +46,10 @@
|
||||
"react": "^16.13.1 || ^17.0.0"
|
||||
},
|
||||
"devDependencies": {
|
||||
"@backstage/cli": "^0.16.1-next.0",
|
||||
"@backstage/cli": "^0.17.0-next.1",
|
||||
"@backstage/core-app-api": "^1.0.1-next.0",
|
||||
"@backstage/dev-utils": "^1.0.1-next.0",
|
||||
"@backstage/test-utils": "^1.0.1-next.0",
|
||||
"@backstage/test-utils": "^1.0.1-next.1",
|
||||
"@testing-library/jest-dom": "^5.10.1",
|
||||
"@testing-library/react": "^12.1.3",
|
||||
"@testing-library/user-event": "^13.1.8",
|
||||
|
||||
@@ -23,8 +23,8 @@
|
||||
"clean": "backstage-cli package clean"
|
||||
},
|
||||
"dependencies": {
|
||||
"@backstage/backend-common": "^0.13.2-next.0",
|
||||
"@backstage/backend-test-utils": "^0.1.23-next.0",
|
||||
"@backstage/backend-common": "^0.13.2-next.1",
|
||||
"@backstage/backend-test-utils": "^0.1.23-next.1",
|
||||
"@backstage/config": "^1.0.0",
|
||||
"@types/express": "^4.17.6",
|
||||
"express": "^4.17.1",
|
||||
@@ -34,7 +34,7 @@
|
||||
"yn": "^4.0.0"
|
||||
},
|
||||
"devDependencies": {
|
||||
"@backstage/cli": "^0.16.1-next.0"
|
||||
"@backstage/cli": "^0.17.0-next.1"
|
||||
},
|
||||
"files": [
|
||||
"dist",
|
||||
|
||||
@@ -1,5 +1,15 @@
|
||||
# @backstage/plugin-bazaar
|
||||
|
||||
## 0.1.19-next.1
|
||||
|
||||
### Patch Changes
|
||||
|
||||
- 69738379c7: Pass authorization header with Backstage token to backend requests.
|
||||
- Updated dependencies
|
||||
- @backstage/plugin-catalog-react@1.0.1-next.1
|
||||
- @backstage/cli@0.17.0-next.1
|
||||
- @backstage/plugin-catalog@1.1.0-next.1
|
||||
|
||||
## 0.1.19-next.0
|
||||
|
||||
### Patch Changes
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
{
|
||||
"name": "@backstage/plugin-bazaar",
|
||||
"version": "0.1.19-next.0",
|
||||
"version": "0.1.19-next.1",
|
||||
"main": "src/index.ts",
|
||||
"types": "src/index.ts",
|
||||
"license": "Apache-2.0",
|
||||
@@ -26,11 +26,11 @@
|
||||
"dependencies": {
|
||||
"@backstage/catalog-client": "^1.0.1-next.0",
|
||||
"@backstage/catalog-model": "^1.0.1-next.0",
|
||||
"@backstage/cli": "^0.16.1-next.0",
|
||||
"@backstage/cli": "^0.17.0-next.1",
|
||||
"@backstage/core-components": "^0.9.3-next.0",
|
||||
"@backstage/core-plugin-api": "^1.0.0",
|
||||
"@backstage/plugin-catalog": "^1.0.1-next.0",
|
||||
"@backstage/plugin-catalog-react": "^1.0.1-next.0",
|
||||
"@backstage/plugin-catalog": "^1.1.0-next.1",
|
||||
"@backstage/plugin-catalog-react": "^1.0.1-next.1",
|
||||
"@date-io/luxon": "1.x",
|
||||
"@material-ui/core": "^4.12.2",
|
||||
"@material-ui/icons": "^4.9.1",
|
||||
@@ -47,7 +47,7 @@
|
||||
"react": "^16.13.1 || ^17.0.0"
|
||||
},
|
||||
"devDependencies": {
|
||||
"@backstage/cli": "^0.16.1-next.0",
|
||||
"@backstage/cli": "^0.17.0-next.1",
|
||||
"@backstage/dev-utils": "^1.0.1-next.0",
|
||||
"@testing-library/jest-dom": "^5.10.1",
|
||||
"cross-fetch": "^3.1.5"
|
||||
|
||||
+36
-39
@@ -17,6 +17,7 @@
|
||||
import {
|
||||
createApiRef,
|
||||
DiscoveryApi,
|
||||
FetchApi,
|
||||
IdentityApi,
|
||||
} from '@backstage/core-plugin-api';
|
||||
|
||||
@@ -47,49 +48,53 @@ export interface BazaarApi {
|
||||
export class BazaarClient implements BazaarApi {
|
||||
private readonly identityApi: IdentityApi;
|
||||
private readonly discoveryApi: DiscoveryApi;
|
||||
private readonly fetchApi: FetchApi;
|
||||
|
||||
constructor(options: {
|
||||
identityApi: IdentityApi;
|
||||
discoveryApi: DiscoveryApi;
|
||||
fetchApi: FetchApi;
|
||||
}) {
|
||||
this.identityApi = options.identityApi;
|
||||
this.discoveryApi = options.discoveryApi;
|
||||
this.fetchApi = options.fetchApi;
|
||||
}
|
||||
|
||||
async updateProject(bazaarProject: any): Promise<any> {
|
||||
const baseUrl = await this.discoveryApi.getBaseUrl('bazaar');
|
||||
|
||||
return await fetch(`${baseUrl}/projects`, {
|
||||
method: 'PUT',
|
||||
headers: {
|
||||
Accept: 'application/json',
|
||||
'Content-Type': 'application/json',
|
||||
},
|
||||
body: JSON.stringify(bazaarProject),
|
||||
}).then(resp => resp.json());
|
||||
return await this.fetchApi
|
||||
.fetch(`${baseUrl}/projects`, {
|
||||
method: 'PUT',
|
||||
headers: {
|
||||
Accept: 'application/json',
|
||||
'Content-Type': 'application/json',
|
||||
},
|
||||
body: JSON.stringify(bazaarProject),
|
||||
})
|
||||
.then(resp => resp.json());
|
||||
}
|
||||
|
||||
async addProject(bazaarProject: any): Promise<any> {
|
||||
const baseUrl = await this.discoveryApi.getBaseUrl('bazaar');
|
||||
|
||||
return await fetch(`${baseUrl}/projects`, {
|
||||
method: 'POST',
|
||||
headers: {
|
||||
Accept: 'application/json',
|
||||
'Content-Type': 'application/json',
|
||||
},
|
||||
body: JSON.stringify(bazaarProject),
|
||||
}).then(resp => resp.json());
|
||||
return await this.fetchApi
|
||||
.fetch(`${baseUrl}/projects`, {
|
||||
method: 'POST',
|
||||
headers: {
|
||||
Accept: 'application/json',
|
||||
'Content-Type': 'application/json',
|
||||
},
|
||||
body: JSON.stringify(bazaarProject),
|
||||
})
|
||||
.then(resp => resp.json());
|
||||
}
|
||||
|
||||
async getProjectById(id: number): Promise<any> {
|
||||
const baseUrl = await this.discoveryApi.getBaseUrl('bazaar');
|
||||
|
||||
const response = await fetch(
|
||||
const response = await this.fetchApi.fetch(
|
||||
`${baseUrl}/projects/${encodeURIComponent(id)}`,
|
||||
{
|
||||
method: 'GET',
|
||||
},
|
||||
);
|
||||
|
||||
return response.ok ? response : null;
|
||||
@@ -98,11 +103,8 @@ export class BazaarClient implements BazaarApi {
|
||||
async getProjectByRef(entityRef: string): Promise<any> {
|
||||
const baseUrl = await this.discoveryApi.getBaseUrl('bazaar');
|
||||
|
||||
const response = await fetch(
|
||||
const response = await this.fetchApi.fetch(
|
||||
`${baseUrl}/projects/${encodeURIComponent(entityRef)}`,
|
||||
{
|
||||
method: 'GET',
|
||||
},
|
||||
);
|
||||
|
||||
return response.ok ? response : null;
|
||||
@@ -111,19 +113,16 @@ export class BazaarClient implements BazaarApi {
|
||||
async getMembers(id: number): Promise<any> {
|
||||
const baseUrl = await this.discoveryApi.getBaseUrl('bazaar');
|
||||
|
||||
return await fetch(
|
||||
`${baseUrl}/projects/${encodeURIComponent(id)}/members`,
|
||||
{
|
||||
method: 'GET',
|
||||
},
|
||||
).then(resp => resp.json());
|
||||
return await this.fetchApi
|
||||
.fetch(`${baseUrl}/projects/${encodeURIComponent(id)}/members`)
|
||||
.then(resp => resp.json());
|
||||
}
|
||||
|
||||
async addMember(id: number, userId: string): Promise<void> {
|
||||
const baseUrl = await this.discoveryApi.getBaseUrl('bazaar');
|
||||
const { picture } = await this.identityApi.getProfileInfo();
|
||||
|
||||
await fetch(
|
||||
await this.fetchApi.fetch(
|
||||
`${baseUrl}/projects/${encodeURIComponent(
|
||||
id,
|
||||
)}/member/${encodeURIComponent(userId)}`,
|
||||
@@ -141,28 +140,26 @@ export class BazaarClient implements BazaarApi {
|
||||
async deleteMember(id: number, userId: string): Promise<void> {
|
||||
const baseUrl = await this.discoveryApi.getBaseUrl('bazaar');
|
||||
|
||||
await fetch(
|
||||
await this.fetchApi.fetch(
|
||||
`${baseUrl}/projects/${encodeURIComponent(
|
||||
id,
|
||||
)}/member/${encodeURIComponent(userId)}`,
|
||||
{
|
||||
method: 'DELETE',
|
||||
},
|
||||
{ method: 'DELETE' },
|
||||
);
|
||||
}
|
||||
|
||||
async getProjects(): Promise<any> {
|
||||
const baseUrl = await this.discoveryApi.getBaseUrl('bazaar');
|
||||
|
||||
return await fetch(`${baseUrl}/projects`, {
|
||||
method: 'GET',
|
||||
}).then(resp => resp.json());
|
||||
return await this.fetchApi
|
||||
.fetch(`${baseUrl}/projects`)
|
||||
.then(resp => resp.json());
|
||||
}
|
||||
|
||||
async deleteProject(id: number): Promise<void> {
|
||||
const baseUrl = await this.discoveryApi.getBaseUrl('bazaar');
|
||||
|
||||
await fetch(`${baseUrl}/projects/${encodeURIComponent(id)}`, {
|
||||
await this.fetchApi.fetch(`${baseUrl}/projects/${encodeURIComponent(id)}`, {
|
||||
method: 'DELETE',
|
||||
});
|
||||
}
|
||||
|
||||
@@ -21,6 +21,7 @@ import {
|
||||
createRoutableExtension,
|
||||
identityApiRef,
|
||||
discoveryApiRef,
|
||||
fetchApiRef,
|
||||
} from '@backstage/core-plugin-api';
|
||||
import { bazaarApiRef, BazaarClient } from './api';
|
||||
|
||||
@@ -35,9 +36,10 @@ export const bazaarPlugin = createPlugin({
|
||||
deps: {
|
||||
identityApi: identityApiRef,
|
||||
discoveryApi: discoveryApiRef,
|
||||
fetchApi: fetchApiRef,
|
||||
},
|
||||
factory: ({ identityApi, discoveryApi }) =>
|
||||
new BazaarClient({ identityApi, discoveryApi }),
|
||||
factory: ({ identityApi, discoveryApi, fetchApi }) =>
|
||||
new BazaarClient({ identityApi, discoveryApi, fetchApi }),
|
||||
}),
|
||||
],
|
||||
});
|
||||
|
||||
@@ -27,7 +27,7 @@
|
||||
"@backstage/catalog-model": "^1.0.1-next.0",
|
||||
"@backstage/core-components": "^0.9.3-next.0",
|
||||
"@backstage/core-plugin-api": "^1.0.0",
|
||||
"@backstage/plugin-catalog-react": "^1.0.1-next.0",
|
||||
"@backstage/plugin-catalog-react": "^1.0.1-next.1",
|
||||
"@backstage/theme": "^0.2.15",
|
||||
"@material-ui/core": "^4.12.2",
|
||||
"@material-ui/icons": "^4.9.1",
|
||||
@@ -43,10 +43,10 @@
|
||||
"react": "^16.13.1 || ^17.0.0"
|
||||
},
|
||||
"devDependencies": {
|
||||
"@backstage/cli": "^0.16.1-next.0",
|
||||
"@backstage/cli": "^0.17.0-next.1",
|
||||
"@backstage/core-app-api": "^1.0.1-next.0",
|
||||
"@backstage/dev-utils": "^1.0.1-next.0",
|
||||
"@backstage/test-utils": "^1.0.1-next.0",
|
||||
"@backstage/test-utils": "^1.0.1-next.1",
|
||||
"@testing-library/jest-dom": "^5.10.1",
|
||||
"@testing-library/react": "^12.1.3",
|
||||
"@testing-library/user-event": "^13.1.8",
|
||||
|
||||
@@ -1,5 +1,13 @@
|
||||
# @backstage/plugin-catalog-backend-module-aws
|
||||
|
||||
## 0.1.4-next.1
|
||||
|
||||
### Patch Changes
|
||||
|
||||
- Updated dependencies
|
||||
- @backstage/plugin-catalog-backend@1.1.0-next.1
|
||||
- @backstage/backend-common@0.13.2-next.1
|
||||
|
||||
## 0.1.4-next.0
|
||||
|
||||
### Patch Changes
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
{
|
||||
"name": "@backstage/plugin-catalog-backend-module-aws",
|
||||
"description": "A Backstage catalog backend module that helps integrate towards AWS",
|
||||
"version": "0.1.4-next.0",
|
||||
"version": "0.1.4-next.1",
|
||||
"main": "src/index.ts",
|
||||
"types": "src/index.ts",
|
||||
"license": "Apache-2.0",
|
||||
@@ -33,11 +33,11 @@
|
||||
"start": "backstage-cli package start"
|
||||
},
|
||||
"dependencies": {
|
||||
"@backstage/backend-common": "^0.13.2-next.0",
|
||||
"@backstage/backend-common": "^0.13.2-next.1",
|
||||
"@backstage/catalog-model": "^1.0.1-next.0",
|
||||
"@backstage/config": "^1.0.0",
|
||||
"@backstage/errors": "^1.0.0",
|
||||
"@backstage/plugin-catalog-backend": "^1.0.1-next.0",
|
||||
"@backstage/plugin-catalog-backend": "^1.1.0-next.1",
|
||||
"@backstage/types": "^1.0.0",
|
||||
"aws-sdk": "^2.840.0",
|
||||
"lodash": "^4.17.21",
|
||||
@@ -45,7 +45,7 @@
|
||||
"winston": "^3.2.1"
|
||||
},
|
||||
"devDependencies": {
|
||||
"@backstage/cli": "^0.16.1-next.0",
|
||||
"@backstage/cli": "^0.17.0-next.1",
|
||||
"@types/lodash": "^4.14.151",
|
||||
"aws-sdk-mock": "^5.2.1",
|
||||
"yaml": "^1.9.2"
|
||||
|
||||
@@ -1,5 +1,14 @@
|
||||
# @backstage/plugin-catalog-backend-module-azure
|
||||
|
||||
## 0.1.2-next.1
|
||||
|
||||
### Patch Changes
|
||||
|
||||
- Updated dependencies
|
||||
- @backstage/plugin-catalog-backend@1.1.0-next.1
|
||||
- @backstage/integration@1.1.0-next.1
|
||||
- @backstage/backend-common@0.13.2-next.1
|
||||
|
||||
## 0.1.2-next.0
|
||||
|
||||
### Patch Changes
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
{
|
||||
"name": "@backstage/plugin-catalog-backend-module-azure",
|
||||
"description": "A Backstage catalog backend module that helps integrate towards Azure",
|
||||
"version": "0.1.2-next.0",
|
||||
"version": "0.1.2-next.1",
|
||||
"main": "src/index.ts",
|
||||
"types": "src/index.ts",
|
||||
"license": "Apache-2.0",
|
||||
@@ -33,12 +33,12 @@
|
||||
"start": "backstage-cli package start"
|
||||
},
|
||||
"dependencies": {
|
||||
"@backstage/backend-common": "^0.13.2-next.0",
|
||||
"@backstage/backend-common": "^0.13.2-next.1",
|
||||
"@backstage/catalog-model": "^1.0.1-next.0",
|
||||
"@backstage/config": "^1.0.0",
|
||||
"@backstage/errors": "^1.0.0",
|
||||
"@backstage/integration": "^1.0.1-next.0",
|
||||
"@backstage/plugin-catalog-backend": "^1.0.1-next.0",
|
||||
"@backstage/integration": "^1.1.0-next.1",
|
||||
"@backstage/plugin-catalog-backend": "^1.1.0-next.1",
|
||||
"@backstage/types": "^1.0.0",
|
||||
"lodash": "^4.17.21",
|
||||
"msw": "^0.35.0",
|
||||
@@ -46,8 +46,8 @@
|
||||
"winston": "^3.2.1"
|
||||
},
|
||||
"devDependencies": {
|
||||
"@backstage/backend-test-utils": "^0.1.23-next.0",
|
||||
"@backstage/cli": "^0.16.1-next.0",
|
||||
"@backstage/backend-test-utils": "^0.1.23-next.1",
|
||||
"@backstage/cli": "^0.17.0-next.1",
|
||||
"@types/lodash": "^4.14.151"
|
||||
},
|
||||
"files": [
|
||||
|
||||
@@ -1,5 +1,14 @@
|
||||
# @backstage/plugin-catalog-backend-module-bitbucket
|
||||
|
||||
## 0.1.2-next.1
|
||||
|
||||
### Patch Changes
|
||||
|
||||
- Updated dependencies
|
||||
- @backstage/plugin-catalog-backend@1.1.0-next.1
|
||||
- @backstage/integration@1.1.0-next.1
|
||||
- @backstage/backend-common@0.13.2-next.1
|
||||
|
||||
## 0.1.2-next.0
|
||||
|
||||
### Patch Changes
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
{
|
||||
"name": "@backstage/plugin-catalog-backend-module-bitbucket",
|
||||
"description": "A Backstage catalog backend module that helps integrate towards Bitbucket",
|
||||
"version": "0.1.2-next.0",
|
||||
"version": "0.1.2-next.1",
|
||||
"main": "src/index.ts",
|
||||
"types": "src/index.ts",
|
||||
"license": "Apache-2.0",
|
||||
@@ -33,12 +33,12 @@
|
||||
"start": "backstage-cli package start"
|
||||
},
|
||||
"dependencies": {
|
||||
"@backstage/backend-common": "^0.13.2-next.0",
|
||||
"@backstage/backend-common": "^0.13.2-next.1",
|
||||
"@backstage/catalog-model": "^1.0.1-next.0",
|
||||
"@backstage/config": "^1.0.0",
|
||||
"@backstage/errors": "^1.0.0",
|
||||
"@backstage/integration": "^1.0.1-next.0",
|
||||
"@backstage/plugin-catalog-backend": "^1.0.1-next.0",
|
||||
"@backstage/integration": "^1.1.0-next.1",
|
||||
"@backstage/plugin-catalog-backend": "^1.1.0-next.1",
|
||||
"@backstage/types": "^1.0.0",
|
||||
"lodash": "^4.17.21",
|
||||
"msw": "^0.35.0",
|
||||
@@ -46,8 +46,8 @@
|
||||
"winston": "^3.2.1"
|
||||
},
|
||||
"devDependencies": {
|
||||
"@backstage/backend-test-utils": "^0.1.23-next.0",
|
||||
"@backstage/cli": "^0.16.1-next.0",
|
||||
"@backstage/backend-test-utils": "^0.1.23-next.1",
|
||||
"@backstage/cli": "^0.17.0-next.1",
|
||||
"@types/lodash": "^4.14.151"
|
||||
},
|
||||
"files": [
|
||||
|
||||
@@ -1,5 +1,14 @@
|
||||
# @backstage/plugin-catalog-backend-module-github
|
||||
|
||||
## 0.1.2-next.1
|
||||
|
||||
### Patch Changes
|
||||
|
||||
- Updated dependencies
|
||||
- @backstage/plugin-catalog-backend@1.1.0-next.1
|
||||
- @backstage/integration@1.1.0-next.1
|
||||
- @backstage/backend-common@0.13.2-next.1
|
||||
|
||||
## 0.1.2-next.0
|
||||
|
||||
### Patch Changes
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
{
|
||||
"name": "@backstage/plugin-catalog-backend-module-github",
|
||||
"description": "A Backstage catalog backend module that helps integrate towards GitHub",
|
||||
"version": "0.1.2-next.0",
|
||||
"version": "0.1.2-next.1",
|
||||
"main": "src/index.ts",
|
||||
"types": "src/index.ts",
|
||||
"license": "Apache-2.0",
|
||||
@@ -33,12 +33,12 @@
|
||||
"start": "backstage-cli package start"
|
||||
},
|
||||
"dependencies": {
|
||||
"@backstage/backend-common": "^0.13.2-next.0",
|
||||
"@backstage/backend-common": "^0.13.2-next.1",
|
||||
"@backstage/catalog-model": "^1.0.1-next.0",
|
||||
"@backstage/config": "^1.0.0",
|
||||
"@backstage/errors": "^1.0.0",
|
||||
"@backstage/integration": "^1.0.1-next.0",
|
||||
"@backstage/plugin-catalog-backend": "^1.0.1-next.0",
|
||||
"@backstage/integration": "^1.1.0-next.1",
|
||||
"@backstage/plugin-catalog-backend": "^1.1.0-next.1",
|
||||
"@backstage/types": "^1.0.0",
|
||||
"@octokit/graphql": "^4.5.8",
|
||||
"lodash": "^4.17.21",
|
||||
@@ -47,8 +47,8 @@
|
||||
"winston": "^3.2.1"
|
||||
},
|
||||
"devDependencies": {
|
||||
"@backstage/backend-test-utils": "^0.1.23-next.0",
|
||||
"@backstage/cli": "^0.16.1-next.0",
|
||||
"@backstage/backend-test-utils": "^0.1.23-next.1",
|
||||
"@backstage/cli": "^0.17.0-next.1",
|
||||
"@types/lodash": "^4.14.151"
|
||||
},
|
||||
"files": [
|
||||
|
||||
@@ -1,5 +1,14 @@
|
||||
# @backstage/plugin-catalog-backend-module-gitlab
|
||||
|
||||
## 0.1.2-next.1
|
||||
|
||||
### Patch Changes
|
||||
|
||||
- Updated dependencies
|
||||
- @backstage/plugin-catalog-backend@1.1.0-next.1
|
||||
- @backstage/integration@1.1.0-next.1
|
||||
- @backstage/backend-common@0.13.2-next.1
|
||||
|
||||
## 0.1.2-next.0
|
||||
|
||||
### Patch Changes
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
{
|
||||
"name": "@backstage/plugin-catalog-backend-module-gitlab",
|
||||
"description": "A Backstage catalog backend module that helps integrate towards GitLab",
|
||||
"version": "0.1.2-next.0",
|
||||
"version": "0.1.2-next.1",
|
||||
"main": "src/index.ts",
|
||||
"types": "src/index.ts",
|
||||
"license": "Apache-2.0",
|
||||
@@ -33,12 +33,12 @@
|
||||
"start": "backstage-cli package start"
|
||||
},
|
||||
"dependencies": {
|
||||
"@backstage/backend-common": "^0.13.2-next.0",
|
||||
"@backstage/backend-common": "^0.13.2-next.1",
|
||||
"@backstage/catalog-model": "^1.0.1-next.0",
|
||||
"@backstage/config": "^1.0.0",
|
||||
"@backstage/errors": "^1.0.0",
|
||||
"@backstage/integration": "^1.0.1-next.0",
|
||||
"@backstage/plugin-catalog-backend": "^1.0.1-next.0",
|
||||
"@backstage/integration": "^1.1.0-next.1",
|
||||
"@backstage/plugin-catalog-backend": "^1.1.0-next.1",
|
||||
"@backstage/types": "^1.0.0",
|
||||
"lodash": "^4.17.21",
|
||||
"msw": "^0.35.0",
|
||||
@@ -46,8 +46,8 @@
|
||||
"winston": "^3.2.1"
|
||||
},
|
||||
"devDependencies": {
|
||||
"@backstage/backend-test-utils": "^0.1.23-next.0",
|
||||
"@backstage/cli": "^0.16.1-next.0",
|
||||
"@backstage/backend-test-utils": "^0.1.23-next.1",
|
||||
"@backstage/cli": "^0.17.0-next.1",
|
||||
"@types/lodash": "^4.14.151"
|
||||
},
|
||||
"files": [
|
||||
|
||||
@@ -1,5 +1,13 @@
|
||||
# @backstage/plugin-catalog-backend-module-ldap
|
||||
|
||||
## 0.4.2-next.1
|
||||
|
||||
### Patch Changes
|
||||
|
||||
- Updated dependencies
|
||||
- @backstage/plugin-catalog-backend@1.1.0-next.1
|
||||
- @backstage/backend-tasks@0.3.0-next.1
|
||||
|
||||
## 0.4.2-next.0
|
||||
|
||||
### Patch Changes
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
{
|
||||
"name": "@backstage/plugin-catalog-backend-module-ldap",
|
||||
"description": "A Backstage catalog backend module that helps integrate towards LDAP",
|
||||
"version": "0.4.2-next.0",
|
||||
"version": "0.4.2-next.1",
|
||||
"main": "src/index.ts",
|
||||
"types": "src/index.ts",
|
||||
"license": "Apache-2.0",
|
||||
@@ -33,11 +33,11 @@
|
||||
"start": "backstage-cli package start"
|
||||
},
|
||||
"dependencies": {
|
||||
"@backstage/backend-tasks": "^0.2.2-next.0",
|
||||
"@backstage/backend-tasks": "^0.3.0-next.1",
|
||||
"@backstage/catalog-model": "^1.0.1-next.0",
|
||||
"@backstage/config": "^1.0.0",
|
||||
"@backstage/errors": "^1.0.0",
|
||||
"@backstage/plugin-catalog-backend": "^1.0.1-next.0",
|
||||
"@backstage/plugin-catalog-backend": "^1.1.0-next.1",
|
||||
"@backstage/types": "^1.0.0",
|
||||
"@types/ldapjs": "^2.2.0",
|
||||
"ldapjs": "^2.2.0",
|
||||
@@ -46,7 +46,7 @@
|
||||
"winston": "^3.2.1"
|
||||
},
|
||||
"devDependencies": {
|
||||
"@backstage/cli": "^0.16.1-next.0",
|
||||
"@backstage/cli": "^0.17.0-next.1",
|
||||
"@types/lodash": "^4.14.151"
|
||||
},
|
||||
"files": [
|
||||
|
||||
@@ -1,5 +1,14 @@
|
||||
# @backstage/plugin-catalog-backend-module-msgraph
|
||||
|
||||
## 0.3.1-next.1
|
||||
|
||||
### Patch Changes
|
||||
|
||||
- 1691c6c5c2: Clarify that config locations that emit User and Group kinds now need to declare so in the `catalog.locations.[].rules`
|
||||
- Updated dependencies
|
||||
- @backstage/plugin-catalog-backend@1.1.0-next.1
|
||||
- @backstage/backend-tasks@0.3.0-next.1
|
||||
|
||||
## 0.3.1-next.0
|
||||
|
||||
### Patch Changes
|
||||
|
||||
@@ -141,8 +141,6 @@ catalog:
|
||||
locations:
|
||||
- type: microsoft-graph-org
|
||||
target: https://graph.microsoft.com/v1.0
|
||||
# If you catalog doesn't allow to import Group and User entities by
|
||||
# default, allow them here
|
||||
rules:
|
||||
- allow: [Group, User]
|
||||
…
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
{
|
||||
"name": "@backstage/plugin-catalog-backend-module-msgraph",
|
||||
"description": "A Backstage catalog backend module that helps integrate towards Microsoft Graph",
|
||||
"version": "0.3.1-next.0",
|
||||
"version": "0.3.1-next.1",
|
||||
"main": "src/index.ts",
|
||||
"types": "src/index.ts",
|
||||
"license": "Apache-2.0",
|
||||
@@ -34,10 +34,10 @@
|
||||
},
|
||||
"dependencies": {
|
||||
"@azure/msal-node": "^1.1.0",
|
||||
"@backstage/backend-tasks": "^0.2.2-next.0",
|
||||
"@backstage/backend-tasks": "^0.3.0-next.1",
|
||||
"@backstage/catalog-model": "^1.0.1-next.0",
|
||||
"@backstage/config": "^1.0.0",
|
||||
"@backstage/plugin-catalog-backend": "^1.0.1-next.0",
|
||||
"@backstage/plugin-catalog-backend": "^1.1.0-next.1",
|
||||
"@microsoft/microsoft-graph-types": "^2.6.0",
|
||||
"@types/node-fetch": "^2.5.12",
|
||||
"lodash": "^4.17.21",
|
||||
@@ -48,9 +48,9 @@
|
||||
"qs": "^6.9.4"
|
||||
},
|
||||
"devDependencies": {
|
||||
"@backstage/backend-common": "^0.13.2-next.0",
|
||||
"@backstage/backend-test-utils": "^0.1.23-next.0",
|
||||
"@backstage/cli": "^0.16.1-next.0",
|
||||
"@backstage/backend-common": "^0.13.2-next.1",
|
||||
"@backstage/backend-test-utils": "^0.1.23-next.1",
|
||||
"@backstage/cli": "^0.17.0-next.1",
|
||||
"@types/lodash": "^4.14.151",
|
||||
"msw": "^0.35.0"
|
||||
},
|
||||
|
||||
@@ -1,5 +1,56 @@
|
||||
# @backstage/plugin-catalog-backend
|
||||
|
||||
## 1.1.0-next.1
|
||||
|
||||
### Minor Changes
|
||||
|
||||
- 8012ac46a0: **BREAKING (alpha api):** Replace `createCatalogPolicyDecision` export with `createCatalogConditionalDecision`, which accepts a permission parameter of type `ResourcePermission<'catalog-entity'>` along with conditions. The permission passed is expected to be the handled permission in `PermissionPolicy#handle`, whose type must first be narrowed using methods like `isPermission` and `isResourcePermission`:
|
||||
|
||||
```typescript
|
||||
class TestPermissionPolicy implements PermissionPolicy {
|
||||
async handle(
|
||||
request: PolicyQuery<Permission>,
|
||||
_user?: BackstageIdentityResponse,
|
||||
): Promise<PolicyDecision> {
|
||||
if (
|
||||
// Narrow type of `request.permission` to `ResourcePermission<'catalog-entity'>
|
||||
isResourcePermission(request.permission, RESOURCE_TYPE_CATALOG_ENTITY)
|
||||
) {
|
||||
return createCatalogConditionalDecision(
|
||||
request.permission,
|
||||
catalogConditions.isEntityOwner(
|
||||
_user?.identity.ownershipEntityRefs ?? [],
|
||||
),
|
||||
);
|
||||
}
|
||||
|
||||
return {
|
||||
result: AuthorizeResult.ALLOW,
|
||||
};
|
||||
```
|
||||
|
||||
- 8012ac46a0: **BREAKING:** Mark CatalogBuilder#addPermissionRules as @alpha.
|
||||
- fb02d2d94d: export `locationSpecToLocationEntity`
|
||||
|
||||
### Patch Changes
|
||||
|
||||
- ada4446733: Specify type of `visibilityPermission` property on collators and collator factories.
|
||||
- 1691c6c5c2: Clarify that config locations that emit User and Group kinds now need to declare so in the `catalog.locations.[].rules`
|
||||
- 8012ac46a0: Handle changes to @alpha permission-related types.
|
||||
|
||||
- All exported permission rules and conditions now have a `resourceType`.
|
||||
- `createCatalogConditionalDecision` now expects supplied conditions to have the appropriate `resourceType`.
|
||||
- `createCatalogPermissionRule` now expects `resourceType` as part of the supplied rule object.
|
||||
- Introduce new `CatalogPermissionRule` convenience type.
|
||||
|
||||
- Updated dependencies
|
||||
- @backstage/integration@1.1.0-next.1
|
||||
- @backstage/plugin-permission-common@0.6.0-next.0
|
||||
- @backstage/plugin-permission-node@0.6.0-next.1
|
||||
- @backstage/plugin-catalog-common@1.0.1-next.1
|
||||
- @backstage/backend-common@0.13.2-next.1
|
||||
- @backstage/plugin-search-common@0.3.3-next.1
|
||||
|
||||
## 1.0.1-next.0
|
||||
|
||||
### Patch Changes
|
||||
@@ -1394,6 +1445,8 @@
|
||||
locations:
|
||||
- type: github-multi-org
|
||||
target: https://github.myorg.com
|
||||
rules:
|
||||
- allow: [User, Group]
|
||||
|
||||
processors:
|
||||
githubMultiOrg:
|
||||
|
||||
@@ -8,7 +8,7 @@
|
||||
import { CatalogApi } from '@backstage/catalog-client';
|
||||
import { CatalogEntityDocument } from '@backstage/plugin-catalog-common';
|
||||
import { CompoundEntityRef } from '@backstage/catalog-model';
|
||||
import { ConditionalPolicyDecision } from '@backstage/plugin-permission-node';
|
||||
import { ConditionalPolicyDecision } from '@backstage/plugin-permission-common';
|
||||
import { Conditions } from '@backstage/plugin-permission-node';
|
||||
import { Config } from '@backstage/config';
|
||||
import { DocumentCollatorFactory } from '@backstage/plugin-search-common';
|
||||
@@ -16,6 +16,7 @@ import { Entity } from '@backstage/catalog-model';
|
||||
import { EntityPolicy } from '@backstage/catalog-model';
|
||||
import { GetEntitiesRequest } from '@backstage/catalog-client';
|
||||
import { JsonValue } from '@backstage/types';
|
||||
import { LocationEntityV1alpha1 } from '@backstage/catalog-model';
|
||||
import { Logger } from 'winston';
|
||||
import { Permission } from '@backstage/plugin-permission-common';
|
||||
import { PermissionAuthorizer } from '@backstage/plugin-permission-common';
|
||||
@@ -25,6 +26,7 @@ import { PermissionRule } from '@backstage/plugin-permission-node';
|
||||
import { PluginDatabaseManager } from '@backstage/backend-common';
|
||||
import { PluginEndpointDiscovery } from '@backstage/backend-common';
|
||||
import { Readable } from 'stream';
|
||||
import { ResourcePermission } from '@backstage/plugin-permission-common';
|
||||
import { Router } from 'express';
|
||||
import { ScmIntegrationRegistry } from '@backstage/integration';
|
||||
import { TokenManager } from '@backstage/backend-common';
|
||||
@@ -109,13 +111,8 @@ export class BuiltinKindsEntityProcessor implements CatalogProcessor {
|
||||
export class CatalogBuilder {
|
||||
addEntityPolicy(...policies: EntityPolicy[]): CatalogBuilder;
|
||||
addEntityProvider(...providers: EntityProvider[]): CatalogBuilder;
|
||||
addPermissionRules(
|
||||
...permissionRules: PermissionRule<
|
||||
Entity,
|
||||
EntitiesSearchFilter,
|
||||
unknown[]
|
||||
>[]
|
||||
): void;
|
||||
// @alpha
|
||||
addPermissionRules(...permissionRules: CatalogPermissionRule[]): void;
|
||||
addProcessor(...processors: CatalogProcessor[]): CatalogBuilder;
|
||||
build(): Promise<{
|
||||
processingEngine: CatalogProcessingEngine;
|
||||
@@ -143,23 +140,37 @@ export const catalogConditions: Conditions<{
|
||||
hasAnnotation: PermissionRule<
|
||||
Entity,
|
||||
EntitiesSearchFilter,
|
||||
'catalog-entity',
|
||||
[annotation: string]
|
||||
>;
|
||||
hasLabel: PermissionRule<Entity, EntitiesSearchFilter, [label: string]>;
|
||||
hasLabel: PermissionRule<
|
||||
Entity,
|
||||
EntitiesSearchFilter,
|
||||
'catalog-entity',
|
||||
[label: string]
|
||||
>;
|
||||
hasMetadata: PermissionRule<
|
||||
Entity,
|
||||
EntitiesSearchFilter,
|
||||
'catalog-entity',
|
||||
[key: string, value?: string | undefined]
|
||||
>;
|
||||
hasSpec: PermissionRule<
|
||||
Entity,
|
||||
EntitiesSearchFilter,
|
||||
'catalog-entity',
|
||||
[key: string, value?: string | undefined]
|
||||
>;
|
||||
isEntityKind: PermissionRule<Entity, EntitiesSearchFilter, [kinds: string[]]>;
|
||||
isEntityKind: PermissionRule<
|
||||
Entity,
|
||||
EntitiesSearchFilter,
|
||||
'catalog-entity',
|
||||
[kinds: string[]]
|
||||
>;
|
||||
isEntityOwner: PermissionRule<
|
||||
Entity,
|
||||
EntitiesSearchFilter,
|
||||
'catalog-entity',
|
||||
[claims: string[]]
|
||||
>;
|
||||
}>;
|
||||
@@ -173,6 +184,10 @@ export type CatalogEnvironment = {
|
||||
permissions: PermissionAuthorizer;
|
||||
};
|
||||
|
||||
// @alpha
|
||||
export type CatalogPermissionRule<TParams extends unknown[] = unknown[]> =
|
||||
PermissionRule<Entity, EntitiesSearchFilter, 'catalog-entity', TParams>;
|
||||
|
||||
// @public (undocumented)
|
||||
export interface CatalogProcessingEngine {
|
||||
// (undocumented)
|
||||
@@ -277,14 +292,17 @@ export class CodeOwnersProcessor implements CatalogProcessor {
|
||||
}
|
||||
|
||||
// @alpha
|
||||
export const createCatalogPermissionRule: <TParams extends unknown[]>(
|
||||
rule: PermissionRule<Entity, EntitiesSearchFilter, TParams>,
|
||||
) => PermissionRule<Entity, EntitiesSearchFilter, TParams>;
|
||||
export const createCatalogConditionalDecision: (
|
||||
permission: ResourcePermission<'catalog-entity'>,
|
||||
conditions: PermissionCriteria<
|
||||
PermissionCondition<'catalog-entity', unknown[]>
|
||||
>,
|
||||
) => ConditionalPolicyDecision;
|
||||
|
||||
// @alpha
|
||||
export const createCatalogPolicyDecision: (
|
||||
conditions: PermissionCriteria<PermissionCondition<unknown[]>>,
|
||||
) => ConditionalPolicyDecision;
|
||||
export const createCatalogPermissionRule: <TParams extends unknown[]>(
|
||||
rule: PermissionRule<Entity, EntitiesSearchFilter, 'catalog-entity', TParams>,
|
||||
) => PermissionRule<Entity, EntitiesSearchFilter, 'catalog-entity', TParams>;
|
||||
|
||||
// @public
|
||||
export function createRandomProcessingInterval(options: {
|
||||
@@ -458,6 +476,12 @@ export type LocationSpec = {
|
||||
presence?: 'optional' | 'required';
|
||||
};
|
||||
|
||||
// @public (undocumented)
|
||||
export function locationSpecToLocationEntity(opts: {
|
||||
location: LocationSpec;
|
||||
parentEntity?: Entity;
|
||||
}): LocationEntityV1alpha1;
|
||||
|
||||
// @public (undocumented)
|
||||
export function parseEntityYaml(
|
||||
data: Buffer,
|
||||
@@ -469,23 +493,37 @@ export const permissionRules: {
|
||||
hasAnnotation: PermissionRule<
|
||||
Entity,
|
||||
EntitiesSearchFilter,
|
||||
'catalog-entity',
|
||||
[annotation: string]
|
||||
>;
|
||||
hasLabel: PermissionRule<Entity, EntitiesSearchFilter, [label: string]>;
|
||||
hasLabel: PermissionRule<
|
||||
Entity,
|
||||
EntitiesSearchFilter,
|
||||
'catalog-entity',
|
||||
[label: string]
|
||||
>;
|
||||
hasMetadata: PermissionRule<
|
||||
Entity,
|
||||
EntitiesSearchFilter,
|
||||
'catalog-entity',
|
||||
[key: string, value?: string | undefined]
|
||||
>;
|
||||
hasSpec: PermissionRule<
|
||||
Entity,
|
||||
EntitiesSearchFilter,
|
||||
'catalog-entity',
|
||||
[key: string, value?: string | undefined]
|
||||
>;
|
||||
isEntityKind: PermissionRule<Entity, EntitiesSearchFilter, [kinds: string[]]>;
|
||||
isEntityKind: PermissionRule<
|
||||
Entity,
|
||||
EntitiesSearchFilter,
|
||||
'catalog-entity',
|
||||
[kinds: string[]]
|
||||
>;
|
||||
isEntityOwner: PermissionRule<
|
||||
Entity,
|
||||
EntitiesSearchFilter,
|
||||
'catalog-entity',
|
||||
[claims: string[]]
|
||||
>;
|
||||
};
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
{
|
||||
"name": "@backstage/plugin-catalog-backend",
|
||||
"description": "The Backstage backend plugin that provides the Backstage catalog",
|
||||
"version": "1.0.1-next.0",
|
||||
"version": "1.1.0-next.1",
|
||||
"main": "src/index.ts",
|
||||
"types": "src/index.ts",
|
||||
"license": "Apache-2.0",
|
||||
@@ -34,17 +34,17 @@
|
||||
"clean": "backstage-cli package clean"
|
||||
},
|
||||
"dependencies": {
|
||||
"@backstage/backend-common": "^0.13.2-next.0",
|
||||
"@backstage/backend-common": "^0.13.2-next.1",
|
||||
"@backstage/catalog-client": "^1.0.1-next.0",
|
||||
"@backstage/catalog-model": "^1.0.1-next.0",
|
||||
"@backstage/config": "^1.0.0",
|
||||
"@backstage/errors": "^1.0.0",
|
||||
"@backstage/integration": "^1.0.1-next.0",
|
||||
"@backstage/plugin-catalog-common": "^1.0.1-next.0",
|
||||
"@backstage/plugin-permission-common": "^0.5.3",
|
||||
"@backstage/plugin-permission-node": "^0.5.6-next.0",
|
||||
"@backstage/integration": "^1.1.0-next.1",
|
||||
"@backstage/plugin-catalog-common": "^1.0.1-next.1",
|
||||
"@backstage/plugin-permission-common": "^0.6.0-next.0",
|
||||
"@backstage/plugin-permission-node": "^0.6.0-next.1",
|
||||
"@backstage/plugin-scaffolder-common": "^1.0.1-next.0",
|
||||
"@backstage/plugin-search-common": "^0.3.3-next.0",
|
||||
"@backstage/plugin-search-common": "^0.3.3-next.1",
|
||||
"@backstage/types": "^1.0.0",
|
||||
"@types/express": "^4.17.6",
|
||||
"codeowners-utils": "^1.0.2",
|
||||
@@ -68,9 +68,9 @@
|
||||
"zod": "^3.11.6"
|
||||
},
|
||||
"devDependencies": {
|
||||
"@backstage/backend-test-utils": "^0.1.23-next.0",
|
||||
"@backstage/cli": "^0.16.1-next.0",
|
||||
"@backstage/plugin-permission-common": "^0.5.3",
|
||||
"@backstage/backend-test-utils": "^0.1.23-next.1",
|
||||
"@backstage/cli": "^0.17.0-next.1",
|
||||
"@backstage/plugin-permission-common": "^0.6.0-next.0",
|
||||
"@backstage/plugin-search-backend-node": "0.5.3-next.0",
|
||||
"@types/core-js": "^2.5.4",
|
||||
"@types/git-url-parse": "^9.0.0",
|
||||
|
||||
@@ -24,7 +24,8 @@ export * from './api';
|
||||
export * from './catalog';
|
||||
export * from './ingestion';
|
||||
export * from './modules';
|
||||
export * from './search';
|
||||
export * from './processing';
|
||||
export * from './service';
|
||||
export * from './permissions';
|
||||
export * from './processing';
|
||||
export * from './search';
|
||||
export * from './service';
|
||||
export * from './util';
|
||||
|
||||
@@ -60,8 +60,10 @@ export class ConfigLocationEntityProvider implements EntityProvider {
|
||||
const type = location.getString('type');
|
||||
const target = location.getString('target');
|
||||
const entity = locationSpecToLocationEntity({
|
||||
type,
|
||||
target: type === 'file' ? path.resolve(target) : target,
|
||||
location: {
|
||||
type,
|
||||
target: type === 'file' ? path.resolve(target) : target,
|
||||
},
|
||||
});
|
||||
const locationKey = getEntityLocationRef(entity);
|
||||
return { entity, locationKey };
|
||||
|
||||
@@ -58,7 +58,7 @@ export class DefaultLocationStore implements LocationStore, EntityProvider {
|
||||
|
||||
return inner;
|
||||
});
|
||||
const entity = locationSpecToLocationEntity(location);
|
||||
const entity = locationSpecToLocationEntity({ location });
|
||||
await this.connection.applyMutation({
|
||||
type: 'delta',
|
||||
added: [{ entity, locationKey: getEntityLocationRef(entity) }],
|
||||
@@ -100,7 +100,7 @@ export class DefaultLocationStore implements LocationStore, EntityProvider {
|
||||
await tx<DbLocationsRow>('locations').where({ id }).del();
|
||||
return location;
|
||||
});
|
||||
const entity = locationSpecToLocationEntity(deleted);
|
||||
const entity = locationSpecToLocationEntity({ location: deleted });
|
||||
await this.connection.applyMutation({
|
||||
type: 'delta',
|
||||
added: [],
|
||||
@@ -122,7 +122,7 @@ export class DefaultLocationStore implements LocationStore, EntityProvider {
|
||||
const locations = await this.locations();
|
||||
|
||||
const entities = locations.map(location => {
|
||||
const entity = locationSpecToLocationEntity(location);
|
||||
const entity = locationSpecToLocationEntity({ location });
|
||||
return { entity, locationKey: getEntityLocationRef(entity) };
|
||||
});
|
||||
|
||||
|
||||
@@ -345,7 +345,7 @@ describe('PlaceholderProcessor', () => {
|
||||
},
|
||||
),
|
||||
).rejects.toThrow(
|
||||
'Placeholder $text could not form a URL out of ./a/b/catalog-info.yaml and ../c/catalog-info.yaml, TypeError: Invalid base URL: ./a/b/catalog-info.yaml',
|
||||
/^Placeholder \$text could not form a URL out of \.\/a\/b\/catalog-info\.yaml and \.\.\/c\/catalog-info\.yaml, TypeError \[ERR_INVALID_URL\]/,
|
||||
);
|
||||
|
||||
expect(read).not.toBeCalled();
|
||||
|
||||
@@ -18,41 +18,49 @@ import { RESOURCE_TYPE_CATALOG_ENTITY } from '@backstage/plugin-catalog-common';
|
||||
import { createConditionExports } from '@backstage/plugin-permission-node';
|
||||
import { permissionRules } from './rules';
|
||||
|
||||
const conditionExports = createConditionExports({
|
||||
const { conditions, createConditionalDecision } = createConditionExports({
|
||||
pluginId: 'catalog',
|
||||
resourceType: RESOURCE_TYPE_CATALOG_ENTITY,
|
||||
rules: permissionRules,
|
||||
});
|
||||
|
||||
/**
|
||||
* These conditions are used when creating conditional decisions that are returned
|
||||
* by authorization policies.
|
||||
* These conditions are used when creating conditional decisions for catalog
|
||||
* entities that are returned by authorization policies.
|
||||
*
|
||||
* @alpha
|
||||
*/
|
||||
export const catalogConditions = conditionExports.conditions;
|
||||
export const catalogConditions = conditions;
|
||||
|
||||
/**
|
||||
* `createCatalogPolicyDecision` can be used when authoring policies to create
|
||||
* conditional decisions.
|
||||
* `createCatalogConditionalDecision` can be used when authoring policies to
|
||||
* create conditional decisions. It requires a permission of type
|
||||
* `ResourcePermission<'catalog-entity'>` to be passed as the first parameter.
|
||||
* It's recommended that you use the provided `isResourcePermission` and
|
||||
* `isPermission` helper methods to narrow the type of the permission passed to
|
||||
* the handle method as shown below.
|
||||
*
|
||||
* ```
|
||||
* // MyAuthorizationPolicy.ts
|
||||
* ...
|
||||
* import { createCatalogPolicyDecision } from '@backstage/plugin-catalog-backend';
|
||||
* import { RESOURCE_TYPE_CATALOG_ENTITY } from '@backstage/plugin-catalog-common';
|
||||
*
|
||||
* class MyAuthorizationPolicy implements PermissionPolicy {
|
||||
* async handle(request, user) {
|
||||
* ...
|
||||
*
|
||||
* return createCatalogPolicyDecision({
|
||||
* anyOf: [...insert conditions here...],
|
||||
* });
|
||||
* }
|
||||
* if (isResourcePermission(request.permission, RESOURCE_TYPE_CATALOG_ENTITY)) {
|
||||
* return createCatalogConditionalDecision(
|
||||
* request.permission,
|
||||
* { anyOf: [...insert conditions here...] }
|
||||
* );
|
||||
* }
|
||||
*
|
||||
* ...
|
||||
* }
|
||||
* ```
|
||||
*
|
||||
* @alpha
|
||||
*/
|
||||
export const createCatalogPolicyDecision =
|
||||
conditionExports.createPolicyDecision;
|
||||
export const createCatalogConditionalDecision = createConditionalDecision;
|
||||
|
||||
@@ -16,6 +16,6 @@
|
||||
|
||||
export {
|
||||
catalogConditions,
|
||||
createCatalogPolicyDecision,
|
||||
createCatalogConditionalDecision,
|
||||
} from './conditionExports';
|
||||
export * from './rules';
|
||||
|
||||
@@ -16,12 +16,14 @@
|
||||
|
||||
import { get } from 'lodash';
|
||||
import { Entity } from '@backstage/catalog-model';
|
||||
import { RESOURCE_TYPE_CATALOG_ENTITY } from '@backstage/plugin-catalog-common';
|
||||
import { createCatalogPermissionRule } from './util';
|
||||
|
||||
export const createPropertyRule = (propertyType: 'metadata' | 'spec') =>
|
||||
createCatalogPermissionRule({
|
||||
name: `HAS_${propertyType.toUpperCase()}`,
|
||||
description: `Allow entities which have the specified ${propertyType} subfield.`,
|
||||
resourceType: RESOURCE_TYPE_CATALOG_ENTITY,
|
||||
apply: (resource: Entity, key: string, value?: string) => {
|
||||
const foundValue = get(resource[propertyType], key);
|
||||
if (value !== undefined) {
|
||||
|
||||
@@ -15,6 +15,7 @@
|
||||
*/
|
||||
|
||||
import { Entity } from '@backstage/catalog-model';
|
||||
import { RESOURCE_TYPE_CATALOG_ENTITY } from '@backstage/plugin-catalog-common';
|
||||
import { createCatalogPermissionRule } from './util';
|
||||
|
||||
/**
|
||||
@@ -27,6 +28,7 @@ export const hasAnnotation = createCatalogPermissionRule({
|
||||
name: 'HAS_ANNOTATION',
|
||||
description:
|
||||
'Allow entities which are annotated with the specified annotation',
|
||||
resourceType: RESOURCE_TYPE_CATALOG_ENTITY,
|
||||
apply: (resource: Entity, annotation: string) =>
|
||||
!!resource.metadata.annotations?.hasOwnProperty(annotation),
|
||||
toQuery: (annotation: string) => ({
|
||||
|
||||
@@ -15,6 +15,7 @@
|
||||
*/
|
||||
|
||||
import { Entity } from '@backstage/catalog-model';
|
||||
import { RESOURCE_TYPE_CATALOG_ENTITY } from '@backstage/plugin-catalog-common';
|
||||
import { createCatalogPermissionRule } from './util';
|
||||
|
||||
/**
|
||||
@@ -25,6 +26,7 @@ import { createCatalogPermissionRule } from './util';
|
||||
export const hasLabel = createCatalogPermissionRule({
|
||||
name: 'HAS_LABEL',
|
||||
description: 'Allow entities which have the specified label metadata.',
|
||||
resourceType: RESOURCE_TYPE_CATALOG_ENTITY,
|
||||
apply: (resource: Entity, label: string) =>
|
||||
!!resource.metadata.labels?.hasOwnProperty(label),
|
||||
toQuery: (label: string) => ({
|
||||
|
||||
@@ -36,4 +36,5 @@ export const permissionRules = {
|
||||
isEntityOwner,
|
||||
};
|
||||
|
||||
export type { CatalogPermissionRule } from './util';
|
||||
export { createCatalogPermissionRule } from './util';
|
||||
|
||||
@@ -14,6 +14,7 @@
|
||||
* limitations under the License.
|
||||
*/
|
||||
import { Entity } from '@backstage/catalog-model';
|
||||
import { RESOURCE_TYPE_CATALOG_ENTITY } from '@backstage/plugin-catalog-common';
|
||||
import { EntitiesSearchFilter } from '../../catalog/types';
|
||||
import { createCatalogPermissionRule } from './util';
|
||||
|
||||
@@ -25,6 +26,7 @@ import { createCatalogPermissionRule } from './util';
|
||||
export const isEntityKind = createCatalogPermissionRule({
|
||||
name: 'IS_ENTITY_KIND',
|
||||
description: 'Allow entities with the specified kind',
|
||||
resourceType: RESOURCE_TYPE_CATALOG_ENTITY,
|
||||
apply(resource: Entity, kinds: string[]) {
|
||||
const resourceKind = resource.kind.toLocaleLowerCase('en-US');
|
||||
return kinds.some(kind => kind.toLocaleLowerCase('en-US') === resourceKind);
|
||||
|
||||
@@ -15,6 +15,7 @@
|
||||
*/
|
||||
|
||||
import { Entity, RELATION_OWNED_BY } from '@backstage/catalog-model';
|
||||
import { RESOURCE_TYPE_CATALOG_ENTITY } from '@backstage/plugin-catalog-common';
|
||||
import { createCatalogPermissionRule } from './util';
|
||||
|
||||
/**
|
||||
@@ -26,6 +27,7 @@ import { createCatalogPermissionRule } from './util';
|
||||
export const isEntityOwner = createCatalogPermissionRule({
|
||||
name: 'IS_ENTITY_OWNER',
|
||||
description: 'Allow entities owned by the current user',
|
||||
resourceType: RESOURCE_TYPE_CATALOG_ENTITY,
|
||||
apply: (resource: Entity, claims: string[]) => {
|
||||
if (!resource.relations) {
|
||||
return false;
|
||||
|
||||
@@ -15,9 +15,23 @@
|
||||
*/
|
||||
|
||||
import { Entity } from '@backstage/catalog-model';
|
||||
import { makeCreatePermissionRule } from '@backstage/plugin-permission-node';
|
||||
import { RESOURCE_TYPE_CATALOG_ENTITY } from '@backstage/plugin-catalog-common';
|
||||
import {
|
||||
makeCreatePermissionRule,
|
||||
PermissionRule,
|
||||
} from '@backstage/plugin-permission-node';
|
||||
import { EntitiesSearchFilter } from '../../catalog/types';
|
||||
|
||||
/**
|
||||
* Convenience type for {@link @backstage/plugin-permission-node#PermissionRule}
|
||||
* instances with the correct resource type, resource, and filter to work with
|
||||
* the catalog.
|
||||
*
|
||||
* @alpha
|
||||
*/
|
||||
export type CatalogPermissionRule<TParams extends unknown[] = unknown[]> =
|
||||
PermissionRule<Entity, EntitiesSearchFilter, 'catalog-entity', TParams>;
|
||||
|
||||
/**
|
||||
* Helper function for creating correctly-typed
|
||||
* {@link @backstage/plugin-permission-node#PermissionRule}s for the
|
||||
@@ -27,5 +41,6 @@ import { EntitiesSearchFilter } from '../../catalog/types';
|
||||
*/
|
||||
export const createCatalogPermissionRule = makeCreatePermissionRule<
|
||||
Entity,
|
||||
EntitiesSearchFilter
|
||||
EntitiesSearchFilter,
|
||||
typeof RESOURCE_TYPE_CATALOG_ENTITY
|
||||
>();
|
||||
|
||||
@@ -106,10 +106,10 @@ export class ProcessorOutputCollector {
|
||||
|
||||
this.deferredEntities.push({ entity, locationKey: location });
|
||||
} else if (i.type === 'location') {
|
||||
const entity = locationSpecToLocationEntity(
|
||||
i.location,
|
||||
this.parentEntity,
|
||||
);
|
||||
const entity = locationSpecToLocationEntity({
|
||||
location: i.location,
|
||||
parentEntity: this.parentEntity,
|
||||
});
|
||||
const locationKey = getEntityLocationRef(entity);
|
||||
this.deferredEntities.push({ entity, locationKey });
|
||||
} else if (i.type === 'relation') {
|
||||
|
||||
@@ -33,6 +33,7 @@ import {
|
||||
catalogEntityReadPermission,
|
||||
CatalogEntityDocument,
|
||||
} from '@backstage/plugin-catalog-common';
|
||||
import { Permission } from '@backstage/plugin-permission-common';
|
||||
|
||||
/**
|
||||
* @public
|
||||
@@ -45,7 +46,8 @@ export class DefaultCatalogCollator {
|
||||
protected filter?: GetEntitiesRequest['filter'];
|
||||
protected readonly catalogClient: CatalogApi;
|
||||
public readonly type: string = 'software-catalog';
|
||||
public readonly visibilityPermission = catalogEntityReadPermission;
|
||||
public readonly visibilityPermission: Permission =
|
||||
catalogEntityReadPermission;
|
||||
protected tokenManager: TokenManager;
|
||||
|
||||
static fromConfig(
|
||||
|
||||
@@ -34,6 +34,7 @@ import {
|
||||
catalogEntityReadPermission,
|
||||
CatalogEntityDocument,
|
||||
} from '@backstage/plugin-catalog-common';
|
||||
import { Permission } from '@backstage/plugin-permission-common';
|
||||
import { Readable } from 'stream';
|
||||
|
||||
/** @public */
|
||||
@@ -49,7 +50,8 @@ export type DefaultCatalogCollatorFactoryOptions = {
|
||||
/** @public */
|
||||
export class DefaultCatalogCollatorFactory implements DocumentCollatorFactory {
|
||||
public readonly type: string = 'software-catalog';
|
||||
public readonly visibilityPermission = catalogEntityReadPermission;
|
||||
public readonly visibilityPermission: Permission =
|
||||
catalogEntityReadPermission;
|
||||
|
||||
private locationTemplate: string;
|
||||
private filter?: GetEntitiesRequest['filter'];
|
||||
|
||||
@@ -14,15 +14,11 @@
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
import { Entity } from '@backstage/catalog-model';
|
||||
import { NotAllowedError } from '@backstage/errors';
|
||||
import { AuthorizeResult } from '@backstage/plugin-permission-common';
|
||||
import {
|
||||
createConditionTransformer,
|
||||
PermissionRule,
|
||||
} from '@backstage/plugin-permission-node';
|
||||
import { EntitiesSearchFilter } from '../catalog/types';
|
||||
import { createConditionTransformer } from '@backstage/plugin-permission-node';
|
||||
import { isEntityKind } from '../permissions/rules/isEntityKind';
|
||||
import { CatalogPermissionRule } from '../permissions/rules';
|
||||
import { AuthorizedEntitiesCatalog } from './AuthorizedEntitiesCatalog';
|
||||
|
||||
describe('AuthorizedEntitiesCatalog', () => {
|
||||
@@ -36,9 +32,7 @@ describe('AuthorizedEntitiesCatalog', () => {
|
||||
authorize: jest.fn(),
|
||||
};
|
||||
|
||||
const createCatalog = (
|
||||
...rules: PermissionRule<Entity, EntitiesSearchFilter, unknown[]>[]
|
||||
) =>
|
||||
const createCatalog = (...rules: CatalogPermissionRule[]) =>
|
||||
new AuthorizedEntitiesCatalog(
|
||||
fakeCatalog,
|
||||
fakePermissionApi,
|
||||
|
||||
@@ -17,7 +17,6 @@
|
||||
import { PluginDatabaseManager, UrlReader } from '@backstage/backend-common';
|
||||
import {
|
||||
DefaultNamespaceEntityPolicy,
|
||||
Entity,
|
||||
EntityPolicies,
|
||||
EntityPolicy,
|
||||
FieldFormatEntityPolicy,
|
||||
@@ -32,7 +31,6 @@ import { ScmIntegrations } from '@backstage/integration';
|
||||
import { createHash } from 'crypto';
|
||||
import { Router } from 'express';
|
||||
import lodash, { keyBy } from 'lodash';
|
||||
import { EntitiesSearchFilter } from '../catalog';
|
||||
|
||||
import {
|
||||
CatalogProcessor,
|
||||
@@ -77,10 +75,12 @@ import { DefaultCatalogRulesEnforcer } from '../ingestion/CatalogRules';
|
||||
import { Config } from '@backstage/config';
|
||||
import { Logger } from 'winston';
|
||||
import { connectEntityProviders } from '../processing/connectEntityProviders';
|
||||
import { permissionRules as catalogPermissionRules } from '../permissions/rules';
|
||||
import {
|
||||
CatalogPermissionRule,
|
||||
permissionRules as catalogPermissionRules,
|
||||
} from '../permissions/rules';
|
||||
import { PermissionAuthorizer } from '@backstage/plugin-permission-common';
|
||||
import {
|
||||
PermissionRule,
|
||||
createConditionTransformer,
|
||||
createPermissionIntegrationRouter,
|
||||
} from '@backstage/plugin-permission-node';
|
||||
@@ -135,11 +135,7 @@ export class CatalogBuilder {
|
||||
maxSeconds: 150,
|
||||
});
|
||||
private locationAnalyzer: LocationAnalyzer | undefined = undefined;
|
||||
private permissionRules: PermissionRule<
|
||||
Entity,
|
||||
EntitiesSearchFilter,
|
||||
unknown[]
|
||||
>[];
|
||||
private permissionRules: CatalogPermissionRule[];
|
||||
|
||||
/**
|
||||
* Creates a catalog builder.
|
||||
@@ -339,14 +335,9 @@ export class CatalogBuilder {
|
||||
* {@link @backstage/plugin-permission-node#PermissionRule}.
|
||||
*
|
||||
* @param permissionRules - Additional permission rules
|
||||
* @alpha
|
||||
*/
|
||||
addPermissionRules(
|
||||
...permissionRules: PermissionRule<
|
||||
Entity,
|
||||
EntitiesSearchFilter,
|
||||
unknown[]
|
||||
>[]
|
||||
) {
|
||||
addPermissionRules(...permissionRules: CatalogPermissionRule[]) {
|
||||
this.permissionRules.push(...permissionRules);
|
||||
}
|
||||
|
||||
|
||||
@@ -26,7 +26,10 @@ import { LocationInput, LocationService, RefreshService } from './types';
|
||||
import { basicEntityFilter } from './request';
|
||||
import { createRouter } from './createRouter';
|
||||
import { AuthorizeResult } from '@backstage/plugin-permission-common';
|
||||
import { createPermissionIntegrationRouter } from '@backstage/plugin-permission-node';
|
||||
import {
|
||||
createPermissionIntegrationRouter,
|
||||
createPermissionRule,
|
||||
} from '@backstage/plugin-permission-node';
|
||||
import { RESOURCE_TYPE_CATALOG_ENTITY } from '@backstage/plugin-catalog-common';
|
||||
|
||||
describe('createRouter readonly disabled', () => {
|
||||
@@ -568,12 +571,13 @@ describe('NextRouter permissioning', () => {
|
||||
let app: express.Express;
|
||||
let refreshService: RefreshService;
|
||||
|
||||
const fakeRule = {
|
||||
const fakeRule = createPermissionRule({
|
||||
name: 'FAKE_RULE',
|
||||
description: 'fake rule',
|
||||
resourceType: RESOURCE_TYPE_CATALOG_ENTITY,
|
||||
apply: () => true,
|
||||
toQuery: () => ({ key: '', values: [] }),
|
||||
};
|
||||
});
|
||||
|
||||
beforeAll(async () => {
|
||||
entitiesCatalog = {
|
||||
@@ -631,7 +635,11 @@ describe('NextRouter permissioning', () => {
|
||||
id: '123',
|
||||
resourceType: 'catalog-entity',
|
||||
resourceRef: 'component:default/spidey-sense',
|
||||
conditions: { rule: 'FAKE_RULE', params: ['user:default/spiderman'] },
|
||||
conditions: {
|
||||
rule: 'FAKE_RULE',
|
||||
resourceType: 'catalog-entity',
|
||||
params: ['user:default/spiderman'],
|
||||
},
|
||||
},
|
||||
],
|
||||
};
|
||||
|
||||
@@ -32,10 +32,14 @@ export function locationSpecToMetadataName(location: LocationSpec) {
|
||||
return `generated-${hash}`;
|
||||
}
|
||||
|
||||
export function locationSpecToLocationEntity(
|
||||
location: LocationSpec,
|
||||
parentEntity?: Entity,
|
||||
): LocationEntityV1alpha1 {
|
||||
/** @public */
|
||||
export function locationSpecToLocationEntity(opts: {
|
||||
location: LocationSpec;
|
||||
parentEntity?: Entity;
|
||||
}): LocationEntityV1alpha1 {
|
||||
const location = opts.location;
|
||||
const parentEntity = opts.parentEntity;
|
||||
|
||||
let ownLocation: string;
|
||||
let originLocation: string;
|
||||
if (parentEntity) {
|
||||
|
||||
@@ -0,0 +1,17 @@
|
||||
/*
|
||||
* Copyright 2022 The Backstage Authors
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
export { locationSpecToLocationEntity } from './conversion';
|
||||
@@ -1,5 +1,15 @@
|
||||
# @backstage/plugin-catalog-common
|
||||
|
||||
## 1.0.1-next.1
|
||||
|
||||
### Patch Changes
|
||||
|
||||
- ada4446733: Use `createPermission` helper when creating permissions.
|
||||
- 8c8bee47f4: Add `@alpha` `CatalogEntityPermission` convenience type, available for import from `@backstage/plugin-catalog-common/alpha`.
|
||||
- Updated dependencies
|
||||
- @backstage/plugin-permission-common@0.6.0-next.0
|
||||
- @backstage/search-common@0.3.3-next.1
|
||||
|
||||
## 1.0.1-next.0
|
||||
|
||||
### Patch Changes
|
||||
|
||||
@@ -3,14 +3,15 @@
|
||||
> Do not edit this file. It is a report generated by [API Extractor](https://api-extractor.com/).
|
||||
|
||||
```ts
|
||||
import { BasicPermission } from '@backstage/plugin-permission-common';
|
||||
import { IndexableDocument } from '@backstage/search-common';
|
||||
import { Permission } from '@backstage/plugin-permission-common';
|
||||
import { ResourcePermission } from '@backstage/plugin-permission-common';
|
||||
|
||||
// @alpha
|
||||
export const catalogEntityCreatePermission: Permission;
|
||||
export const catalogEntityCreatePermission: BasicPermission;
|
||||
|
||||
// @alpha
|
||||
export const catalogEntityDeletePermission: Permission;
|
||||
export const catalogEntityDeletePermission: ResourcePermission<'catalog-entity'>;
|
||||
|
||||
// @public
|
||||
export interface CatalogEntityDocument extends IndexableDocument {
|
||||
@@ -29,19 +30,24 @@ export interface CatalogEntityDocument extends IndexableDocument {
|
||||
}
|
||||
|
||||
// @alpha
|
||||
export const catalogEntityReadPermission: Permission;
|
||||
export type CatalogEntityPermission = ResourcePermission<
|
||||
typeof RESOURCE_TYPE_CATALOG_ENTITY
|
||||
>;
|
||||
|
||||
// @alpha
|
||||
export const catalogEntityRefreshPermission: Permission;
|
||||
export const catalogEntityReadPermission: ResourcePermission<'catalog-entity'>;
|
||||
|
||||
// @alpha
|
||||
export const catalogLocationCreatePermission: Permission;
|
||||
export const catalogEntityRefreshPermission: ResourcePermission<'catalog-entity'>;
|
||||
|
||||
// @alpha
|
||||
export const catalogLocationDeletePermission: Permission;
|
||||
export const catalogLocationCreatePermission: BasicPermission;
|
||||
|
||||
// @alpha
|
||||
export const catalogLocationReadPermission: Permission;
|
||||
export const catalogLocationDeletePermission: BasicPermission;
|
||||
|
||||
// @alpha
|
||||
export const catalogLocationReadPermission: BasicPermission;
|
||||
|
||||
// @alpha
|
||||
export const RESOURCE_TYPE_CATALOG_ENTITY = 'catalog-entity';
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
{
|
||||
"name": "@backstage/plugin-catalog-common",
|
||||
"description": "Common functionalities for the catalog plugin",
|
||||
"version": "1.0.1-next.0",
|
||||
"version": "1.0.1-next.1",
|
||||
"main": "src/index.ts",
|
||||
"types": "src/index.ts",
|
||||
"license": "Apache-2.0",
|
||||
@@ -34,11 +34,11 @@
|
||||
"clean": "backstage-cli package clean"
|
||||
},
|
||||
"dependencies": {
|
||||
"@backstage/plugin-permission-common": "^0.5.3",
|
||||
"@backstage/search-common": "^0.3.3-next.0"
|
||||
"@backstage/plugin-permission-common": "^0.6.0-next.0",
|
||||
"@backstage/search-common": "^0.3.3-next.1"
|
||||
},
|
||||
"devDependencies": {
|
||||
"@backstage/cli": "^0.16.1-next.0"
|
||||
"@backstage/cli": "^0.17.0-next.1"
|
||||
},
|
||||
"files": [
|
||||
"dist",
|
||||
|
||||
@@ -31,5 +31,6 @@ export {
|
||||
catalogLocationCreatePermission,
|
||||
catalogLocationDeletePermission,
|
||||
} from './permissions';
|
||||
export type { CatalogEntityPermission } from './permissions';
|
||||
|
||||
export * from './search';
|
||||
|
||||
@@ -14,7 +14,10 @@
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
import { Permission } from '@backstage/plugin-permission-common';
|
||||
import {
|
||||
createPermission,
|
||||
ResourcePermission,
|
||||
} from '@backstage/plugin-permission-common';
|
||||
|
||||
/**
|
||||
* Permission resource type which corresponds to catalog entities.
|
||||
@@ -24,6 +27,15 @@ import { Permission } from '@backstage/plugin-permission-common';
|
||||
*/
|
||||
export const RESOURCE_TYPE_CATALOG_ENTITY = 'catalog-entity';
|
||||
|
||||
/**
|
||||
* Convenience type for catalog entity
|
||||
* {@link @backstage/plugin-permission-common#ResourcePermission}s.
|
||||
* @alpha
|
||||
*/
|
||||
export type CatalogEntityPermission = ResourcePermission<
|
||||
typeof RESOURCE_TYPE_CATALOG_ENTITY
|
||||
>;
|
||||
|
||||
/**
|
||||
* This permission is used to authorize actions that involve reading one or more
|
||||
* entities from the catalog.
|
||||
@@ -32,13 +44,13 @@ export const RESOURCE_TYPE_CATALOG_ENTITY = 'catalog-entity';
|
||||
* exist in the catalog — both in the frontend and in API responses.
|
||||
* @alpha
|
||||
*/
|
||||
export const catalogEntityReadPermission: Permission = {
|
||||
export const catalogEntityReadPermission = createPermission({
|
||||
name: 'catalog.entity.read',
|
||||
attributes: {
|
||||
action: 'read',
|
||||
},
|
||||
resourceType: RESOURCE_TYPE_CATALOG_ENTITY,
|
||||
};
|
||||
});
|
||||
|
||||
/**
|
||||
* This permission is used to authorize actions that involve creating a new
|
||||
@@ -46,38 +58,38 @@ export const catalogEntityReadPermission: Permission = {
|
||||
* catalog.
|
||||
* @alpha
|
||||
*/
|
||||
export const catalogEntityCreatePermission: Permission = {
|
||||
export const catalogEntityCreatePermission = createPermission({
|
||||
name: 'catalog.entity.create',
|
||||
attributes: {
|
||||
action: 'create',
|
||||
},
|
||||
};
|
||||
});
|
||||
|
||||
/**
|
||||
* This permission is used to designate actions that involve removing one or
|
||||
* more entities from the catalog.
|
||||
* @alpha
|
||||
*/
|
||||
export const catalogEntityDeletePermission: Permission = {
|
||||
export const catalogEntityDeletePermission = createPermission({
|
||||
name: 'catalog.entity.delete',
|
||||
attributes: {
|
||||
action: 'delete',
|
||||
},
|
||||
resourceType: RESOURCE_TYPE_CATALOG_ENTITY,
|
||||
};
|
||||
});
|
||||
|
||||
/**
|
||||
* This permission is used to designate refreshing one or more entities from the
|
||||
* catalog.
|
||||
* @alpha
|
||||
*/
|
||||
export const catalogEntityRefreshPermission: Permission = {
|
||||
export const catalogEntityRefreshPermission = createPermission({
|
||||
name: 'catalog.entity.refresh',
|
||||
attributes: {
|
||||
action: 'update',
|
||||
},
|
||||
resourceType: RESOURCE_TYPE_CATALOG_ENTITY,
|
||||
};
|
||||
});
|
||||
|
||||
/**
|
||||
* This permission is used to designate actions that involve reading one or more
|
||||
@@ -87,33 +99,33 @@ export const catalogEntityRefreshPermission: Permission = {
|
||||
* not exist in the catalog — both in the frontend and in API responses.
|
||||
* @alpha
|
||||
*/
|
||||
export const catalogLocationReadPermission: Permission = {
|
||||
export const catalogLocationReadPermission = createPermission({
|
||||
name: 'catalog.location.read',
|
||||
attributes: {
|
||||
action: 'read',
|
||||
},
|
||||
};
|
||||
});
|
||||
|
||||
/**
|
||||
* This permission is used to designate actions that involve creating catalog
|
||||
* locations.
|
||||
* @alpha
|
||||
*/
|
||||
export const catalogLocationCreatePermission: Permission = {
|
||||
export const catalogLocationCreatePermission = createPermission({
|
||||
name: 'catalog.location.create',
|
||||
attributes: {
|
||||
action: 'create',
|
||||
},
|
||||
};
|
||||
});
|
||||
|
||||
/**
|
||||
* This permission is used to designate actions that involve deleting locations
|
||||
* from the catalog.
|
||||
* @alpha
|
||||
*/
|
||||
export const catalogLocationDeletePermission: Permission = {
|
||||
export const catalogLocationDeletePermission = createPermission({
|
||||
name: 'catalog.location.delete',
|
||||
attributes: {
|
||||
action: 'delete',
|
||||
},
|
||||
};
|
||||
});
|
||||
|
||||
@@ -1,5 +1,13 @@
|
||||
# @backstage/plugin-catalog-graph
|
||||
|
||||
## 0.2.16-next.1
|
||||
|
||||
### Patch Changes
|
||||
|
||||
- 77800a32dd: Added renderNode and renderLabel property to EntityRelationsGraph to support customization using CustomNode and CustomLabel components
|
||||
- Updated dependencies
|
||||
- @backstage/plugin-catalog-react@1.0.1-next.1
|
||||
|
||||
## 0.2.16-next.0
|
||||
|
||||
### Patch Changes
|
||||
|
||||
@@ -128,6 +128,8 @@ export const EntityRelationsGraph: ({
|
||||
relationPairs,
|
||||
className,
|
||||
zoom,
|
||||
renderNode,
|
||||
renderLabel,
|
||||
}: {
|
||||
rootEntityNames: CompoundEntityRef | CompoundEntityRef[];
|
||||
maxDepth?: number | undefined;
|
||||
@@ -142,6 +144,10 @@ export const EntityRelationsGraph: ({
|
||||
relationPairs?: RelationPairs | undefined;
|
||||
className?: string | undefined;
|
||||
zoom?: 'disabled' | 'enabled' | 'enable-on-click' | undefined;
|
||||
renderNode?: DependencyGraphTypes.RenderNodeFunction<EntityNode> | undefined;
|
||||
renderLabel?:
|
||||
| DependencyGraphTypes.RenderLabelFunction<EntityEdge>
|
||||
| undefined;
|
||||
}) => JSX.Element;
|
||||
|
||||
// @public
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
{
|
||||
"name": "@backstage/plugin-catalog-graph",
|
||||
"version": "0.2.16-next.0",
|
||||
"version": "0.2.16-next.1",
|
||||
"main": "src/index.ts",
|
||||
"types": "src/index.ts",
|
||||
"license": "Apache-2.0",
|
||||
@@ -28,7 +28,7 @@
|
||||
"@backstage/catalog-model": "^1.0.1-next.0",
|
||||
"@backstage/core-components": "^0.9.3-next.0",
|
||||
"@backstage/core-plugin-api": "^1.0.0",
|
||||
"@backstage/plugin-catalog-react": "^1.0.1-next.0",
|
||||
"@backstage/plugin-catalog-react": "^1.0.1-next.1",
|
||||
"@backstage/theme": "^0.2.15",
|
||||
"@material-ui/core": "^4.12.2",
|
||||
"@material-ui/icons": "^4.9.1",
|
||||
@@ -45,11 +45,11 @@
|
||||
"react": "^16.13.1 || ^17.0.0"
|
||||
},
|
||||
"devDependencies": {
|
||||
"@backstage/cli": "^0.16.1-next.0",
|
||||
"@backstage/plugin-catalog": "^1.0.1-next.0",
|
||||
"@backstage/cli": "^0.17.0-next.1",
|
||||
"@backstage/plugin-catalog": "^1.1.0-next.1",
|
||||
"@backstage/core-app-api": "^1.0.1-next.0",
|
||||
"@backstage/dev-utils": "^1.0.1-next.0",
|
||||
"@backstage/test-utils": "^1.0.1-next.0",
|
||||
"@backstage/test-utils": "^1.0.1-next.1",
|
||||
"@testing-library/jest-dom": "^5.10.1",
|
||||
"@testing-library/react": "^12.1.3",
|
||||
"@testing-library/react-hooks": "^7.0.2",
|
||||
|
||||
+47
@@ -21,6 +21,7 @@ import {
|
||||
RELATION_OWNER_OF,
|
||||
RELATION_PART_OF,
|
||||
} from '@backstage/catalog-model';
|
||||
import { DependencyGraphTypes } from '@backstage/core-components';
|
||||
import { CatalogApi, catalogApiRef } from '@backstage/plugin-catalog-react';
|
||||
import { renderInTestApp, TestApiProvider } from '@backstage/test-utils';
|
||||
import userEvent from '@testing-library/user-event';
|
||||
@@ -30,6 +31,7 @@ import { EntityRelationsGraph } from './EntityRelationsGraph';
|
||||
describe('<EntityRelationsGraph/>', () => {
|
||||
let Wrapper: FunctionComponent;
|
||||
let catalog: jest.Mocked<CatalogApi>;
|
||||
const CUSTOM_TEST_ID = 'custom-test-id';
|
||||
|
||||
beforeAll(() => {
|
||||
Object.defineProperty(window.SVGElement.prototype, 'getBBox', {
|
||||
@@ -378,4 +380,49 @@ describe('<EntityRelationsGraph/>', () => {
|
||||
userEvent.click(await findByText('k:d/a1'));
|
||||
expect(onNodeClick).toBeCalledTimes(1);
|
||||
});
|
||||
|
||||
test('render custom node', async () => {
|
||||
const renderNode = (props: DependencyGraphTypes.RenderNodeProps) => (
|
||||
<g>
|
||||
<text>{props.node.id}</text>
|
||||
<circle data-testid={CUSTOM_TEST_ID} r={100} />
|
||||
</g>
|
||||
);
|
||||
|
||||
const { findAllByTestId, container } = await renderInTestApp(
|
||||
<Wrapper>
|
||||
<EntityRelationsGraph
|
||||
rootEntityNames={{ kind: 'b', namespace: 'd', name: 'c' }}
|
||||
renderNode={renderNode}
|
||||
/>
|
||||
</Wrapper>,
|
||||
);
|
||||
|
||||
const node = await findAllByTestId(CUSTOM_TEST_ID);
|
||||
expect(node[0]).toBeInTheDocument();
|
||||
expect(container.querySelector('circle')).toBeInTheDocument();
|
||||
});
|
||||
|
||||
test('render custom label', async () => {
|
||||
const renderLabel = (props: DependencyGraphTypes.RenderLabelProps) => (
|
||||
<g>
|
||||
<text>{`Test-Label${props.edge.label}`}</text>
|
||||
<circle data-testid={CUSTOM_TEST_ID} r={100} />
|
||||
</g>
|
||||
);
|
||||
|
||||
const { findAllByTestId, findAllByText, container } = await renderInTestApp(
|
||||
<Wrapper>
|
||||
<EntityRelationsGraph
|
||||
rootEntityNames={{ kind: 'b', namespace: 'd', name: 'c' }}
|
||||
renderLabel={renderLabel}
|
||||
/>
|
||||
</Wrapper>,
|
||||
);
|
||||
const node = await findAllByTestId(CUSTOM_TEST_ID);
|
||||
expect(node[0]).toBeInTheDocument();
|
||||
expect(container.querySelector('circle')).toBeInTheDocument();
|
||||
const labels = await findAllByText('Test-Labelvisible');
|
||||
expect(labels[0]).toBeInTheDocument();
|
||||
});
|
||||
});
|
||||
|
||||
@@ -28,7 +28,7 @@ import React, { MouseEvent, useEffect, useMemo } from 'react';
|
||||
import { CustomLabel } from './CustomLabel';
|
||||
import { CustomNode } from './CustomNode';
|
||||
import { ALL_RELATION_PAIRS, RelationPairs } from './relations';
|
||||
import { Direction, EntityNode } from './types';
|
||||
import { Direction, EntityEdge, EntityNode } from './types';
|
||||
import { useEntityRelationNodesAndEdges } from './useEntityRelationNodesAndEdges';
|
||||
|
||||
const useStyles = makeStyles(theme => ({
|
||||
@@ -79,6 +79,8 @@ export const EntityRelationsGraph = ({
|
||||
relationPairs = ALL_RELATION_PAIRS,
|
||||
className,
|
||||
zoom = 'enabled',
|
||||
renderNode,
|
||||
renderLabel,
|
||||
}: {
|
||||
rootEntityNames: CompoundEntityRef | CompoundEntityRef[];
|
||||
maxDepth?: number;
|
||||
@@ -91,6 +93,8 @@ export const EntityRelationsGraph = ({
|
||||
relationPairs?: RelationPairs;
|
||||
className?: string;
|
||||
zoom?: 'enabled' | 'disabled' | 'enable-on-click';
|
||||
renderNode?: DependencyGraphTypes.RenderNodeFunction<EntityNode>;
|
||||
renderLabel?: DependencyGraphTypes.RenderLabelFunction<EntityEdge>;
|
||||
}) => {
|
||||
const theme = useTheme();
|
||||
const classes = useStyles();
|
||||
@@ -127,8 +131,8 @@ export const EntityRelationsGraph = ({
|
||||
<DependencyGraph
|
||||
nodes={nodes}
|
||||
edges={edges}
|
||||
renderNode={CustomNode}
|
||||
renderLabel={CustomLabel}
|
||||
renderNode={renderNode || CustomNode}
|
||||
renderLabel={renderLabel || CustomLabel}
|
||||
direction={direction}
|
||||
className={classes.graph}
|
||||
paddingX={theme.spacing(4)}
|
||||
|
||||
@@ -46,8 +46,8 @@
|
||||
"winston": "^3.2.1"
|
||||
},
|
||||
"devDependencies": {
|
||||
"@backstage/cli": "^0.16.1-next.0",
|
||||
"@backstage/test-utils": "^1.0.1-next.0",
|
||||
"@backstage/cli": "^0.17.0-next.1",
|
||||
"@backstage/test-utils": "^1.0.1-next.1",
|
||||
"@graphql-codegen/cli": "^2.3.1",
|
||||
"@graphql-codegen/typescript": "^2.4.2",
|
||||
"@graphql-codegen/typescript-resolvers": "^2.4.3",
|
||||
|
||||
@@ -1,5 +1,14 @@
|
||||
# @backstage/plugin-catalog-import
|
||||
|
||||
## 0.8.7-next.1
|
||||
|
||||
### Patch Changes
|
||||
|
||||
- Updated dependencies
|
||||
- @backstage/integration@1.1.0-next.1
|
||||
- @backstage/plugin-catalog-react@1.0.1-next.1
|
||||
- @backstage/integration-react@1.0.1-next.1
|
||||
|
||||
## 0.8.7-next.0
|
||||
|
||||
### Patch Changes
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
{
|
||||
"name": "@backstage/plugin-catalog-import",
|
||||
"description": "A Backstage plugin the helps you import entities into your catalog",
|
||||
"version": "0.8.7-next.0",
|
||||
"version": "0.8.7-next.1",
|
||||
"main": "src/index.ts",
|
||||
"types": "src/index.ts",
|
||||
"license": "Apache-2.0",
|
||||
@@ -40,9 +40,9 @@
|
||||
"@backstage/config": "^1.0.0",
|
||||
"@backstage/core-plugin-api": "^1.0.0",
|
||||
"@backstage/errors": "^1.0.0",
|
||||
"@backstage/integration": "^1.0.1-next.0",
|
||||
"@backstage/integration-react": "^1.0.1-next.0",
|
||||
"@backstage/plugin-catalog-react": "^1.0.1-next.0",
|
||||
"@backstage/integration": "^1.1.0-next.1",
|
||||
"@backstage/integration-react": "^1.0.1-next.1",
|
||||
"@backstage/plugin-catalog-react": "^1.0.1-next.1",
|
||||
"@material-ui/core": "^4.12.2",
|
||||
"@material-ui/icons": "^4.9.1",
|
||||
"@material-ui/lab": "4.0.0-alpha.57",
|
||||
@@ -60,10 +60,10 @@
|
||||
"react": "^16.13.1 || ^17.0.0"
|
||||
},
|
||||
"devDependencies": {
|
||||
"@backstage/cli": "^0.16.1-next.0",
|
||||
"@backstage/cli": "^0.17.0-next.1",
|
||||
"@backstage/core-app-api": "^1.0.1-next.0",
|
||||
"@backstage/dev-utils": "^1.0.1-next.0",
|
||||
"@backstage/test-utils": "^1.0.1-next.0",
|
||||
"@backstage/test-utils": "^1.0.1-next.1",
|
||||
"@testing-library/jest-dom": "^5.10.1",
|
||||
"@testing-library/react": "^12.1.3",
|
||||
"@testing-library/react-hooks": "^7.0.2",
|
||||
|
||||
@@ -1,5 +1,22 @@
|
||||
# @backstage/plugin-catalog-react
|
||||
|
||||
## 1.0.1-next.1
|
||||
|
||||
### Patch Changes
|
||||
|
||||
- 0ffd88a90e: Prevent permissions with types other than `ResourcePermission<'catalog-entity'>` from being used with the `useEntityPermission` hook.
|
||||
- 4af82967f4: Decouple tags picker from backend entities
|
||||
|
||||
`EntityTagPicker` fetches all the tags independently and it doesn't require all the entities to be available client side.
|
||||
|
||||
- 37b04b5a5e: Removed broken link from Labels section of entity inspector.
|
||||
- 4431873583: Update `usePermission` usage.
|
||||
- Updated dependencies
|
||||
- @backstage/integration@1.1.0-next.1
|
||||
- @backstage/plugin-permission-react@0.4.0-next.0
|
||||
- @backstage/plugin-permission-common@0.6.0-next.0
|
||||
- @backstage/plugin-catalog-common@1.0.1-next.1
|
||||
|
||||
## 1.0.1-next.0
|
||||
|
||||
### Patch Changes
|
||||
|
||||
@@ -16,10 +16,10 @@ import { IconButton } from '@material-ui/core';
|
||||
import { LinkProps } from '@backstage/core-components';
|
||||
import { Observable } from '@backstage/types';
|
||||
import { Overrides } from '@material-ui/core/styles/overrides';
|
||||
import { Permission } from '@backstage/plugin-permission-common';
|
||||
import { PropsWithChildren } from 'react';
|
||||
import { default as React_2 } from 'react';
|
||||
import { ReactNode } from 'react';
|
||||
import { ResourcePermission } from '@backstage/plugin-permission-common';
|
||||
import { RouteRef } from '@backstage/core-plugin-api';
|
||||
import { ScmIntegrationRegistry } from '@backstage/integration';
|
||||
import { StyleRules } from '@material-ui/core/styles/withStyles';
|
||||
@@ -489,7 +489,9 @@ export function useEntityOwnership(): {
|
||||
};
|
||||
|
||||
// @alpha
|
||||
export function useEntityPermission(permission: Permission): {
|
||||
export function useEntityPermission(
|
||||
permission: ResourcePermission<'catalog-entity'>,
|
||||
): {
|
||||
loading: boolean;
|
||||
allowed: boolean;
|
||||
error?: Error;
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
{
|
||||
"name": "@backstage/plugin-catalog-react",
|
||||
"description": "A frontend library that helps other Backstage plugins interact with the catalog",
|
||||
"version": "1.0.1-next.0",
|
||||
"version": "1.0.1-next.1",
|
||||
"main": "src/index.ts",
|
||||
"types": "src/index.ts",
|
||||
"license": "Apache-2.0",
|
||||
@@ -39,9 +39,10 @@
|
||||
"@backstage/core-components": "^0.9.3-next.0",
|
||||
"@backstage/core-plugin-api": "^1.0.0",
|
||||
"@backstage/errors": "^1.0.0",
|
||||
"@backstage/integration": "^1.0.1-next.0",
|
||||
"@backstage/plugin-permission-common": "^0.5.3",
|
||||
"@backstage/plugin-permission-react": "^0.3.4",
|
||||
"@backstage/integration": "^1.1.0-next.1",
|
||||
"@backstage/plugin-catalog-common": "^1.0.1-next.1",
|
||||
"@backstage/plugin-permission-common": "^0.6.0-next.0",
|
||||
"@backstage/plugin-permission-react": "^0.4.0-next.0",
|
||||
"@backstage/theme": "^0.2.15",
|
||||
"@backstage/types": "^1.0.0",
|
||||
"@backstage/version-bridge": "^1.0.0",
|
||||
@@ -62,11 +63,11 @@
|
||||
"react": "^16.13.1 || ^17.0.0"
|
||||
},
|
||||
"devDependencies": {
|
||||
"@backstage/cli": "^0.16.1-next.0",
|
||||
"@backstage/cli": "^0.17.0-next.1",
|
||||
"@backstage/core-app-api": "^1.0.1-next.0",
|
||||
"@backstage/plugin-catalog-common": "^1.0.1-next.0",
|
||||
"@backstage/plugin-catalog-common": "^1.0.1-next.1",
|
||||
"@backstage/plugin-scaffolder-common": "^1.0.1-next.0",
|
||||
"@backstage/test-utils": "^1.0.1-next.0",
|
||||
"@backstage/test-utils": "^1.0.1-next.1",
|
||||
"@testing-library/jest-dom": "^5.10.1",
|
||||
"@testing-library/react": "^12.1.3",
|
||||
"@testing-library/react-hooks": "^7.0.2",
|
||||
|
||||
@@ -14,60 +14,49 @@
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
import { Entity } from '@backstage/catalog-model';
|
||||
import { fireEvent, render } from '@testing-library/react';
|
||||
import { fireEvent, render, waitFor } from '@testing-library/react';
|
||||
import React from 'react';
|
||||
import { MockEntityListContextProvider } from '../../testUtils/providers';
|
||||
import { EntityTagFilter } from '../../filters';
|
||||
import { EntityTagPicker } from './EntityTagPicker';
|
||||
import { TestApiProvider } from '@backstage/test-utils';
|
||||
import { catalogApiRef } from '../../api';
|
||||
import { CatalogApi } from '@backstage/catalog-client';
|
||||
|
||||
const taggedEntities: Entity[] = [
|
||||
{
|
||||
apiVersion: '1',
|
||||
kind: 'Component',
|
||||
metadata: {
|
||||
name: 'component-1',
|
||||
tags: ['tag4', 'tag1', 'tag2'],
|
||||
},
|
||||
},
|
||||
{
|
||||
apiVersion: '1',
|
||||
kind: 'Component',
|
||||
metadata: {
|
||||
name: 'component-2',
|
||||
tags: ['tag3', 'tag4'],
|
||||
},
|
||||
},
|
||||
];
|
||||
const tags = ['tag1', 'tag2', 'tag3', 'tag4'];
|
||||
|
||||
describe('<EntityTagPicker/>', () => {
|
||||
it('renders all tags', () => {
|
||||
const mockCatalogApiRef = {
|
||||
getEntityFacets: async () => ({
|
||||
facets: { 'metadata.tags': tags.map(value => ({ value })) },
|
||||
}),
|
||||
} as unknown as CatalogApi;
|
||||
|
||||
it('renders all tags', async () => {
|
||||
const rendered = render(
|
||||
<MockEntityListContextProvider
|
||||
value={{ entities: taggedEntities, backendEntities: taggedEntities }}
|
||||
>
|
||||
<EntityTagPicker />
|
||||
</MockEntityListContextProvider>,
|
||||
<TestApiProvider apis={[[catalogApiRef, mockCatalogApiRef]]}>
|
||||
<MockEntityListContextProvider value={{}}>
|
||||
<EntityTagPicker />
|
||||
</MockEntityListContextProvider>
|
||||
</TestApiProvider>,
|
||||
);
|
||||
expect(rendered.getByText('Tags')).toBeInTheDocument();
|
||||
await waitFor(() => expect(rendered.getByText('Tags')).toBeInTheDocument());
|
||||
|
||||
fireEvent.click(rendered.getByTestId('tag-picker-expand'));
|
||||
taggedEntities
|
||||
.flatMap(e => e.metadata.tags!)
|
||||
.forEach(tag => {
|
||||
expect(rendered.getByText(tag)).toBeInTheDocument();
|
||||
});
|
||||
tags.forEach(tag => {
|
||||
expect(rendered.getByText(tag)).toBeInTheDocument();
|
||||
});
|
||||
});
|
||||
|
||||
it('renders unique tags in alphabetical order', () => {
|
||||
it('renders unique tags in alphabetical order', async () => {
|
||||
const rendered = render(
|
||||
<MockEntityListContextProvider
|
||||
value={{ entities: taggedEntities, backendEntities: taggedEntities }}
|
||||
>
|
||||
<EntityTagPicker />
|
||||
</MockEntityListContextProvider>,
|
||||
<TestApiProvider apis={[[catalogApiRef, mockCatalogApiRef]]}>
|
||||
<MockEntityListContextProvider value={{}}>
|
||||
<EntityTagPicker />
|
||||
</MockEntityListContextProvider>
|
||||
</TestApiProvider>,
|
||||
);
|
||||
expect(rendered.getByText('Tags')).toBeInTheDocument();
|
||||
await waitFor(() => expect(rendered.getByText('Tags')).toBeInTheDocument());
|
||||
|
||||
fireEvent.click(rendered.getByTestId('tag-picker-expand'));
|
||||
|
||||
@@ -79,43 +68,47 @@ describe('<EntityTagPicker/>', () => {
|
||||
]);
|
||||
});
|
||||
|
||||
it('respects the query parameter filter value', () => {
|
||||
it('respects the query parameter filter value', async () => {
|
||||
const updateFilters = jest.fn();
|
||||
const queryParameters = { tags: ['tag3'] };
|
||||
render(
|
||||
<MockEntityListContextProvider
|
||||
value={{
|
||||
entities: taggedEntities,
|
||||
backendEntities: taggedEntities,
|
||||
updateFilters,
|
||||
queryParameters,
|
||||
}}
|
||||
>
|
||||
<EntityTagPicker />
|
||||
</MockEntityListContextProvider>,
|
||||
<TestApiProvider apis={[[catalogApiRef, mockCatalogApiRef]]}>
|
||||
<MockEntityListContextProvider
|
||||
value={{
|
||||
updateFilters,
|
||||
queryParameters,
|
||||
}}
|
||||
>
|
||||
<EntityTagPicker />
|
||||
</MockEntityListContextProvider>
|
||||
</TestApiProvider>,
|
||||
);
|
||||
|
||||
expect(updateFilters).toHaveBeenLastCalledWith({
|
||||
tags: new EntityTagFilter(['tag3']),
|
||||
});
|
||||
await waitFor(() =>
|
||||
expect(updateFilters).toHaveBeenLastCalledWith({
|
||||
tags: new EntityTagFilter(['tag3']),
|
||||
}),
|
||||
);
|
||||
});
|
||||
|
||||
it('adds tags to filters', () => {
|
||||
it('adds tags to filters', async () => {
|
||||
const updateFilters = jest.fn();
|
||||
const rendered = render(
|
||||
<MockEntityListContextProvider
|
||||
value={{
|
||||
entities: taggedEntities,
|
||||
backendEntities: taggedEntities,
|
||||
updateFilters,
|
||||
}}
|
||||
>
|
||||
<EntityTagPicker />
|
||||
</MockEntityListContextProvider>,
|
||||
<TestApiProvider apis={[[catalogApiRef, mockCatalogApiRef]]}>
|
||||
<MockEntityListContextProvider
|
||||
value={{
|
||||
updateFilters,
|
||||
}}
|
||||
>
|
||||
<EntityTagPicker />
|
||||
</MockEntityListContextProvider>
|
||||
</TestApiProvider>,
|
||||
);
|
||||
await waitFor(() =>
|
||||
expect(updateFilters).toHaveBeenLastCalledWith({
|
||||
tags: undefined,
|
||||
}),
|
||||
);
|
||||
expect(updateFilters).toHaveBeenLastCalledWith({
|
||||
tags: undefined,
|
||||
});
|
||||
|
||||
fireEvent.click(rendered.getByTestId('tag-picker-expand'));
|
||||
fireEvent.click(rendered.getByText('tag1'));
|
||||
@@ -124,23 +117,25 @@ describe('<EntityTagPicker/>', () => {
|
||||
});
|
||||
});
|
||||
|
||||
it('removes tags from filters', () => {
|
||||
it('removes tags from filters', async () => {
|
||||
const updateFilters = jest.fn();
|
||||
const rendered = render(
|
||||
<MockEntityListContextProvider
|
||||
value={{
|
||||
entities: taggedEntities,
|
||||
backendEntities: taggedEntities,
|
||||
updateFilters,
|
||||
filters: { tags: new EntityTagFilter(['tag1']) },
|
||||
}}
|
||||
>
|
||||
<EntityTagPicker />
|
||||
</MockEntityListContextProvider>,
|
||||
<TestApiProvider apis={[[catalogApiRef, mockCatalogApiRef]]}>
|
||||
<MockEntityListContextProvider
|
||||
value={{
|
||||
updateFilters,
|
||||
filters: { tags: new EntityTagFilter(['tag1']) },
|
||||
}}
|
||||
>
|
||||
<EntityTagPicker />
|
||||
</MockEntityListContextProvider>
|
||||
</TestApiProvider>,
|
||||
);
|
||||
await waitFor(() =>
|
||||
expect(updateFilters).toHaveBeenLastCalledWith({
|
||||
tags: new EntityTagFilter(['tag1']),
|
||||
}),
|
||||
);
|
||||
expect(updateFilters).toHaveBeenLastCalledWith({
|
||||
tags: new EntityTagFilter(['tag1']),
|
||||
});
|
||||
fireEvent.click(rendered.getByTestId('tag-picker-expand'));
|
||||
expect(rendered.getByLabelText('tag1')).toBeChecked();
|
||||
|
||||
@@ -150,30 +145,36 @@ describe('<EntityTagPicker/>', () => {
|
||||
});
|
||||
});
|
||||
|
||||
it('responds to external queryParameters changes', () => {
|
||||
it('responds to external queryParameters changes', async () => {
|
||||
const updateFilters = jest.fn();
|
||||
const rendered = render(
|
||||
<MockEntityListContextProvider
|
||||
value={{
|
||||
updateFilters,
|
||||
queryParameters: { tags: ['tag1'] },
|
||||
}}
|
||||
>
|
||||
<EntityTagPicker />
|
||||
</MockEntityListContextProvider>,
|
||||
<TestApiProvider apis={[[catalogApiRef, mockCatalogApiRef]]}>
|
||||
<MockEntityListContextProvider
|
||||
value={{
|
||||
updateFilters,
|
||||
queryParameters: { tags: ['tag1'] },
|
||||
}}
|
||||
>
|
||||
<EntityTagPicker />
|
||||
</MockEntityListContextProvider>
|
||||
</TestApiProvider>,
|
||||
);
|
||||
await waitFor(() =>
|
||||
expect(updateFilters).toHaveBeenLastCalledWith({
|
||||
tags: new EntityTagFilter(['tag1']),
|
||||
}),
|
||||
);
|
||||
expect(updateFilters).toHaveBeenLastCalledWith({
|
||||
tags: new EntityTagFilter(['tag1']),
|
||||
});
|
||||
rendered.rerender(
|
||||
<MockEntityListContextProvider
|
||||
value={{
|
||||
updateFilters,
|
||||
queryParameters: { tags: ['tag2'] },
|
||||
}}
|
||||
>
|
||||
<EntityTagPicker />
|
||||
</MockEntityListContextProvider>,
|
||||
<TestApiProvider apis={[[catalogApiRef, mockCatalogApiRef]]}>
|
||||
<MockEntityListContextProvider
|
||||
value={{
|
||||
updateFilters,
|
||||
queryParameters: { tags: ['tag2'] },
|
||||
}}
|
||||
>
|
||||
<EntityTagPicker />
|
||||
</MockEntityListContextProvider>
|
||||
</TestApiProvider>,
|
||||
);
|
||||
expect(updateFilters).toHaveBeenLastCalledWith({
|
||||
tags: new EntityTagFilter(['tag2']),
|
||||
|
||||
@@ -14,7 +14,6 @@
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
import { Entity } from '@backstage/catalog-model';
|
||||
import {
|
||||
Box,
|
||||
Checkbox,
|
||||
@@ -30,6 +29,9 @@ import { Autocomplete } from '@material-ui/lab';
|
||||
import React, { useEffect, useMemo, useState } from 'react';
|
||||
import { useEntityList } from '../../hooks/useEntityListProvider';
|
||||
import { EntityTagFilter } from '../../filters';
|
||||
import { useApi } from '@backstage/core-plugin-api';
|
||||
import useAsync from 'react-use/lib/useAsync';
|
||||
import { catalogApiRef } from '../../api';
|
||||
|
||||
/** @public */
|
||||
export type CatalogReactEntityTagPickerClassKey = 'input';
|
||||
@@ -49,8 +51,18 @@ const checkedIcon = <CheckBoxIcon fontSize="small" />;
|
||||
/** @public */
|
||||
export const EntityTagPicker = () => {
|
||||
const classes = useStyles();
|
||||
const { updateFilters, backendEntities, filters, queryParameters } =
|
||||
useEntityList();
|
||||
const { updateFilters, filters, queryParameters } = useEntityList();
|
||||
|
||||
const catalogApi = useApi(catalogApiRef);
|
||||
const { value: availableTags } = useAsync(async () => {
|
||||
const facet = 'metadata.tags';
|
||||
const { facets } = await catalogApi.getEntityFacets({
|
||||
facets: [facet],
|
||||
filter: filters.kind?.getCatalogFilters(),
|
||||
});
|
||||
|
||||
return facets[facet].map(({ value }) => value);
|
||||
}, [filters.kind]);
|
||||
|
||||
const queryParamTags = useMemo(
|
||||
() => [queryParameters.tags].flat().filter(Boolean) as string[],
|
||||
@@ -75,19 +87,7 @@ export const EntityTagPicker = () => {
|
||||
});
|
||||
}, [selectedTags, updateFilters]);
|
||||
|
||||
const availableTags = useMemo(
|
||||
() =>
|
||||
[
|
||||
...new Set(
|
||||
backendEntities
|
||||
.flatMap((e: Entity) => e.metadata.tags)
|
||||
.filter(Boolean) as string[],
|
||||
),
|
||||
].sort(),
|
||||
[backendEntities],
|
||||
);
|
||||
|
||||
if (!availableTags.length) return null;
|
||||
if (!availableTags?.length) return null;
|
||||
|
||||
return (
|
||||
<Box pb={1} pt={1}>
|
||||
|
||||
+1
-9
@@ -107,15 +107,7 @@ export function OverviewPage(props: { entity: AlphaEntity }) {
|
||||
</List>
|
||||
)}
|
||||
{!!Object.keys(metadata.labels || {}).length && (
|
||||
<List
|
||||
dense
|
||||
subheader={
|
||||
<ListSubheader>
|
||||
Labels
|
||||
<HelpIcon to="https://backstage.io/docs/features/software-catalog/well-known-labels" />
|
||||
</ListSubheader>
|
||||
}
|
||||
>
|
||||
<List dense subheader={<ListSubheader>Labels</ListSubheader>}>
|
||||
{Object.entries(metadata.labels!).map(entry => (
|
||||
<KeyValueListItem key={entry[0]} indent entry={entry} />
|
||||
))}
|
||||
|
||||
@@ -15,7 +15,7 @@
|
||||
*/
|
||||
|
||||
import { stringifyEntityRef } from '@backstage/catalog-model';
|
||||
import { Permission } from '@backstage/plugin-permission-common';
|
||||
import { ResourcePermission } from '@backstage/plugin-permission-common';
|
||||
import { usePermission } from '@backstage/plugin-permission-react';
|
||||
import { useAsyncEntity } from './useEntity';
|
||||
|
||||
@@ -23,14 +23,18 @@ import { useAsyncEntity } from './useEntity';
|
||||
* A thin wrapper around the
|
||||
* {@link @backstage/plugin-permission-react#usePermission} hook which uses the
|
||||
* current entity in context to make an authorization request for the given
|
||||
* permission.
|
||||
* {@link @backstage/plugin-catalog-common#CatalogEntityPermission}.
|
||||
*
|
||||
* Note: this hook blocks the permission request until the entity has loaded in
|
||||
* context. If you have the entityRef and need concurrent requests, use the
|
||||
* `usePermission` hook directly.
|
||||
* @alpha
|
||||
*/
|
||||
export function useEntityPermission(permission: Permission): {
|
||||
export function useEntityPermission(
|
||||
// TODO(joeporpeglia) Replace with `CatalogEntityPermission` when the issue described in
|
||||
// https://github.com/backstage/backstage/pull/10128 is fixed.
|
||||
permission: ResourcePermission<'catalog-entity'>,
|
||||
): {
|
||||
loading: boolean;
|
||||
allowed: boolean;
|
||||
error?: Error;
|
||||
@@ -44,10 +48,10 @@ export function useEntityPermission(permission: Permission): {
|
||||
allowed,
|
||||
loading: loadingPermission,
|
||||
error: permissionError,
|
||||
} = usePermission(
|
||||
} = usePermission({
|
||||
permission,
|
||||
entity ? stringifyEntityRef(entity) : undefined,
|
||||
);
|
||||
resourceRef: entity ? stringifyEntityRef(entity) : undefined,
|
||||
});
|
||||
|
||||
if (loadingEntity || loadingPermission) {
|
||||
return { loading: true, allowed: false };
|
||||
|
||||
@@ -1,5 +1,19 @@
|
||||
# @backstage/plugin-catalog
|
||||
|
||||
## 1.1.0-next.1
|
||||
|
||||
### Minor Changes
|
||||
|
||||
- bdc61b4002: Expose 'initalFilter' through initialKind prop on Catalog Page.
|
||||
|
||||
### Patch Changes
|
||||
|
||||
- Updated dependencies
|
||||
- @backstage/plugin-catalog-react@1.0.1-next.1
|
||||
- @backstage/plugin-catalog-common@1.0.1-next.1
|
||||
- @backstage/integration-react@1.0.1-next.1
|
||||
- @backstage/plugin-search-common@0.3.3-next.1
|
||||
|
||||
## 1.0.1-next.0
|
||||
|
||||
### Patch Changes
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
{
|
||||
"name": "@backstage/plugin-catalog",
|
||||
"description": "The Backstage plugin for browsing the Backstage catalog",
|
||||
"version": "1.0.1-next.0",
|
||||
"version": "1.1.0-next.1",
|
||||
"main": "src/index.ts",
|
||||
"types": "src/index.ts",
|
||||
"license": "Apache-2.0",
|
||||
@@ -39,10 +39,10 @@
|
||||
"@backstage/core-components": "^0.9.3-next.0",
|
||||
"@backstage/core-plugin-api": "^1.0.0",
|
||||
"@backstage/errors": "^1.0.0",
|
||||
"@backstage/integration-react": "^1.0.1-next.0",
|
||||
"@backstage/plugin-catalog-common": "^1.0.1-next.0",
|
||||
"@backstage/plugin-catalog-react": "^1.0.1-next.0",
|
||||
"@backstage/plugin-search-common": "^0.3.3-next.0",
|
||||
"@backstage/integration-react": "^1.0.1-next.1",
|
||||
"@backstage/plugin-catalog-common": "^1.0.1-next.1",
|
||||
"@backstage/plugin-catalog-react": "^1.0.1-next.1",
|
||||
"@backstage/plugin-search-common": "^0.3.3-next.1",
|
||||
"@backstage/theme": "^0.2.15",
|
||||
"@backstage/types": "^1.0.0",
|
||||
"@material-ui/core": "^4.12.2",
|
||||
@@ -60,11 +60,11 @@
|
||||
"react": "^16.13.1 || ^17.0.0"
|
||||
},
|
||||
"devDependencies": {
|
||||
"@backstage/cli": "^0.16.1-next.0",
|
||||
"@backstage/cli": "^0.17.0-next.1",
|
||||
"@backstage/core-app-api": "^1.0.1-next.0",
|
||||
"@backstage/dev-utils": "^1.0.1-next.0",
|
||||
"@backstage/plugin-permission-react": "^0.3.4",
|
||||
"@backstage/test-utils": "^1.0.1-next.0",
|
||||
"@backstage/plugin-permission-react": "^0.4.0-next.0",
|
||||
"@backstage/test-utils": "^1.0.1-next.1",
|
||||
"@testing-library/jest-dom": "^5.10.1",
|
||||
"@testing-library/react": "^12.1.3",
|
||||
"@testing-library/user-event": "^13.1.8",
|
||||
|
||||
@@ -38,7 +38,7 @@
|
||||
"@backstage/catalog-model": "^1.0.1-next.0",
|
||||
"@backstage/core-components": "^0.9.3-next.0",
|
||||
"@backstage/core-plugin-api": "^1.0.0",
|
||||
"@backstage/plugin-catalog-react": "^1.0.1-next.0",
|
||||
"@backstage/plugin-catalog-react": "^1.0.1-next.1",
|
||||
"@backstage/theme": "^0.2.15",
|
||||
"@material-ui/core": "^4.12.2",
|
||||
"@material-ui/icons": "^4.9.1",
|
||||
@@ -55,10 +55,10 @@
|
||||
"react": "^16.13.1 || ^17.0.0"
|
||||
},
|
||||
"devDependencies": {
|
||||
"@backstage/cli": "^0.16.1-next.0",
|
||||
"@backstage/cli": "^0.17.0-next.1",
|
||||
"@backstage/core-app-api": "^1.0.1-next.0",
|
||||
"@backstage/dev-utils": "^1.0.1-next.0",
|
||||
"@backstage/test-utils": "^1.0.1-next.0",
|
||||
"@backstage/test-utils": "^1.0.1-next.1",
|
||||
"@testing-library/jest-dom": "^5.10.1",
|
||||
"@testing-library/react": "^12.1.3",
|
||||
"@testing-library/user-event": "^13.1.8",
|
||||
|
||||
@@ -37,7 +37,7 @@
|
||||
"@backstage/catalog-model": "^1.0.1-next.0",
|
||||
"@backstage/core-components": "^0.9.3-next.0",
|
||||
"@backstage/core-plugin-api": "^1.0.0",
|
||||
"@backstage/plugin-catalog-react": "^1.0.1-next.0",
|
||||
"@backstage/plugin-catalog-react": "^1.0.1-next.1",
|
||||
"@backstage/theme": "^0.2.15",
|
||||
"@material-ui/core": "^4.12.2",
|
||||
"@material-ui/icons": "^4.9.1",
|
||||
@@ -52,10 +52,10 @@
|
||||
"react": "^16.13.1 || ^17.0.0"
|
||||
},
|
||||
"devDependencies": {
|
||||
"@backstage/cli": "^0.16.1-next.0",
|
||||
"@backstage/cli": "^0.17.0-next.1",
|
||||
"@backstage/core-app-api": "^1.0.1-next.0",
|
||||
"@backstage/dev-utils": "^1.0.1-next.0",
|
||||
"@backstage/test-utils": "^1.0.1-next.0",
|
||||
"@backstage/test-utils": "^1.0.1-next.1",
|
||||
"@testing-library/jest-dom": "^5.10.1",
|
||||
"@testing-library/react": "^12.1.3",
|
||||
"@testing-library/user-event": "^13.1.8",
|
||||
|
||||
@@ -26,7 +26,7 @@
|
||||
"@backstage/catalog-model": "^1.0.1-next.0",
|
||||
"@backstage/core-components": "^0.9.3-next.0",
|
||||
"@backstage/core-plugin-api": "^1.0.0",
|
||||
"@backstage/plugin-catalog-react": "^1.0.1-next.0",
|
||||
"@backstage/plugin-catalog-react": "^1.0.1-next.1",
|
||||
"@backstage/theme": "^0.2.15",
|
||||
"@material-ui/core": "^4.12.2",
|
||||
"@material-ui/icons": "^4.9.1",
|
||||
@@ -40,9 +40,9 @@
|
||||
"react": "^16.13.1 || ^17.0.0"
|
||||
},
|
||||
"devDependencies": {
|
||||
"@backstage/cli": "^0.16.1-next.0",
|
||||
"@backstage/cli": "^0.17.0-next.1",
|
||||
"@backstage/dev-utils": "^1.0.1-next.0",
|
||||
"@backstage/test-utils": "^1.0.1-next.0",
|
||||
"@backstage/test-utils": "^1.0.1-next.1",
|
||||
"@testing-library/jest-dom": "^5.10.1",
|
||||
"@testing-library/react": "^12.1.3",
|
||||
"@testing-library/user-event": "^13.1.8",
|
||||
|
||||
@@ -1,5 +1,13 @@
|
||||
# @backstage/plugin-code-coverage-backend
|
||||
|
||||
## 0.1.29-next.1
|
||||
|
||||
### Patch Changes
|
||||
|
||||
- Updated dependencies
|
||||
- @backstage/integration@1.1.0-next.1
|
||||
- @backstage/backend-common@0.13.2-next.1
|
||||
|
||||
## 0.1.29-next.0
|
||||
|
||||
### Patch Changes
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
{
|
||||
"name": "@backstage/plugin-code-coverage-backend",
|
||||
"description": "A Backstage backend plugin that helps you keep track of your code coverage",
|
||||
"version": "0.1.29-next.0",
|
||||
"version": "0.1.29-next.1",
|
||||
"main": "src/index.ts",
|
||||
"types": "src/index.ts",
|
||||
"license": "Apache-2.0",
|
||||
@@ -23,12 +23,12 @@
|
||||
"clean": "backstage-cli package clean"
|
||||
},
|
||||
"dependencies": {
|
||||
"@backstage/backend-common": "^0.13.2-next.0",
|
||||
"@backstage/backend-common": "^0.13.2-next.1",
|
||||
"@backstage/catalog-client": "^1.0.1-next.0",
|
||||
"@backstage/catalog-model": "^1.0.1-next.0",
|
||||
"@backstage/config": "^1.0.0",
|
||||
"@backstage/errors": "^1.0.0",
|
||||
"@backstage/integration": "^1.0.1-next.0",
|
||||
"@backstage/integration": "^1.1.0-next.1",
|
||||
"@types/express": "^4.17.6",
|
||||
"express": "^4.17.1",
|
||||
"express-promise-router": "^4.1.0",
|
||||
@@ -39,7 +39,7 @@
|
||||
"yn": "^4.0.0"
|
||||
},
|
||||
"devDependencies": {
|
||||
"@backstage/cli": "^0.16.1-next.0",
|
||||
"@backstage/cli": "^0.17.0-next.1",
|
||||
"@types/express-xml-bodyparser": "^0.3.2",
|
||||
"@types/supertest": "^2.0.8",
|
||||
"msw": "^0.35.0",
|
||||
|
||||
@@ -29,7 +29,7 @@
|
||||
"@backstage/core-components": "^0.9.3-next.0",
|
||||
"@backstage/core-plugin-api": "^1.0.0",
|
||||
"@backstage/errors": "^1.0.0",
|
||||
"@backstage/plugin-catalog-react": "^1.0.1-next.0",
|
||||
"@backstage/plugin-catalog-react": "^1.0.1-next.1",
|
||||
"@backstage/theme": "^0.2.15",
|
||||
"@material-ui/core": "^4.12.2",
|
||||
"@material-ui/icons": "^4.9.1",
|
||||
@@ -46,10 +46,10 @@
|
||||
"react": "^16.13.1 || ^17.0.0"
|
||||
},
|
||||
"devDependencies": {
|
||||
"@backstage/cli": "^0.16.1-next.0",
|
||||
"@backstage/cli": "^0.17.0-next.1",
|
||||
"@backstage/core-app-api": "^1.0.1-next.0",
|
||||
"@backstage/dev-utils": "^1.0.1-next.0",
|
||||
"@backstage/test-utils": "^1.0.1-next.0",
|
||||
"@backstage/test-utils": "^1.0.1-next.1",
|
||||
"@testing-library/jest-dom": "^5.10.1",
|
||||
"@testing-library/react": "^12.1.3",
|
||||
"@testing-library/user-event": "^13.1.8",
|
||||
|
||||
@@ -41,10 +41,10 @@
|
||||
"react": "^16.13.1 || ^17.0.0"
|
||||
},
|
||||
"devDependencies": {
|
||||
"@backstage/cli": "^0.16.1-next.0",
|
||||
"@backstage/cli": "^0.17.0-next.1",
|
||||
"@backstage/core-app-api": "^1.0.1-next.0",
|
||||
"@backstage/dev-utils": "^1.0.1-next.0",
|
||||
"@backstage/test-utils": "^1.0.1-next.0",
|
||||
"@backstage/test-utils": "^1.0.1-next.1",
|
||||
"@testing-library/jest-dom": "^5.10.1",
|
||||
"@testing-library/react": "^12.1.3",
|
||||
"@testing-library/user-event": "^13.1.8",
|
||||
|
||||
@@ -60,10 +60,10 @@
|
||||
"react": "^16.13.1 || ^17.0.0"
|
||||
},
|
||||
"devDependencies": {
|
||||
"@backstage/cli": "^0.16.1-next.0",
|
||||
"@backstage/cli": "^0.17.0-next.1",
|
||||
"@backstage/core-app-api": "^1.0.1-next.0",
|
||||
"@backstage/dev-utils": "^1.0.1-next.0",
|
||||
"@backstage/test-utils": "^1.0.1-next.0",
|
||||
"@backstage/test-utils": "^1.0.1-next.1",
|
||||
"@testing-library/jest-dom": "^5.10.1",
|
||||
"@testing-library/react": "^12.1.3",
|
||||
"@testing-library/user-event": "^13.1.8",
|
||||
|
||||
@@ -36,9 +36,9 @@
|
||||
"@backstage/core-plugin-api": "^1.0.0"
|
||||
},
|
||||
"devDependencies": {
|
||||
"@backstage/cli": "^0.16.1-next.0",
|
||||
"@backstage/cli": "^0.17.0-next.1",
|
||||
"@backstage/dev-utils": "^1.0.1-next.0",
|
||||
"@backstage/test-utils": "^1.0.1-next.0",
|
||||
"@backstage/test-utils": "^1.0.1-next.1",
|
||||
"@testing-library/jest-dom": "^5.10.1",
|
||||
"@testing-library/react": "^12.1.3",
|
||||
"@testing-library/user-event": "^13.1.8",
|
||||
|
||||
@@ -37,7 +37,7 @@
|
||||
"@backstage/catalog-model": "^1.0.1-next.0",
|
||||
"@backstage/core-components": "^0.9.3-next.0",
|
||||
"@backstage/core-plugin-api": "^1.0.0",
|
||||
"@backstage/plugin-catalog-react": "^1.0.1-next.0",
|
||||
"@backstage/plugin-catalog-react": "^1.0.1-next.1",
|
||||
"@backstage/plugin-explore-react": "^0.0.15",
|
||||
"@backstage/theme": "^0.2.15",
|
||||
"@material-ui/core": "^4.12.2",
|
||||
@@ -53,10 +53,10 @@
|
||||
"react": "^16.13.1 || ^17.0.0"
|
||||
},
|
||||
"devDependencies": {
|
||||
"@backstage/cli": "^0.16.1-next.0",
|
||||
"@backstage/cli": "^0.17.0-next.1",
|
||||
"@backstage/core-app-api": "^1.0.1-next.0",
|
||||
"@backstage/dev-utils": "^1.0.1-next.0",
|
||||
"@backstage/test-utils": "^1.0.1-next.0",
|
||||
"@backstage/test-utils": "^1.0.1-next.1",
|
||||
"@testing-library/jest-dom": "^5.10.1",
|
||||
"@testing-library/react": "^12.1.3",
|
||||
"@testing-library/user-event": "^13.1.8",
|
||||
|
||||
@@ -27,7 +27,7 @@
|
||||
"dependencies": {
|
||||
"@backstage/core-components": "^0.9.3-next.0",
|
||||
"@backstage/core-plugin-api": "^1.0.0",
|
||||
"@backstage/plugin-catalog-react": "^1.0.1-next.0",
|
||||
"@backstage/plugin-catalog-react": "^1.0.1-next.1",
|
||||
"@backstage/theme": "^0.2.15",
|
||||
"@material-ui/core": "^4.12.2",
|
||||
"@material-ui/icons": "^4.9.1",
|
||||
@@ -39,10 +39,10 @@
|
||||
"react": "^16.13.1 || ^17.0.0"
|
||||
},
|
||||
"devDependencies": {
|
||||
"@backstage/cli": "^0.16.1-next.0",
|
||||
"@backstage/cli": "^0.17.0-next.1",
|
||||
"@backstage/core-app-api": "^1.0.1-next.0",
|
||||
"@backstage/dev-utils": "^1.0.1-next.0",
|
||||
"@backstage/test-utils": "^1.0.1-next.0",
|
||||
"@backstage/test-utils": "^1.0.1-next.1",
|
||||
"@testing-library/jest-dom": "^5.10.1",
|
||||
"@testing-library/react": "^12.1.3",
|
||||
"@testing-library/user-event": "^13.1.8",
|
||||
|
||||
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user