@backstage/plugin-catalog 1.3.1-next.1 → 1.4.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/CHANGELOG.md CHANGED
@@ -1,5 +1,166 @@
1
1
  # @backstage/plugin-catalog
2
2
 
3
+ ## 1.4.0
4
+
5
+ ### Minor Changes
6
+
7
+ - 97c46f2359: Add `spec.targets` (or `spec.target`) for Location entities at the `CatalogTable`.
8
+ - cf288221d1: Add `Location` target(s) to `AboutCard`.
9
+ - a274fe38b9: Add hidden title column to catalog and API table to enable filtering by title.
10
+
11
+ ### Patch Changes
12
+
13
+ - dcaf1cb418: Previously, the color of the Entity Context Menu (in the Entity Page Header) was hardcoded as `white`.
14
+
15
+ This was an issue for themes that use a header with a white background. By default, the color of the icon is now `theme.page.fontColor`.
16
+
17
+ It can now also be overridden in the theme, which is only necessary if the header title, subtitle and three-dots icon need to have different colors. For example:
18
+
19
+ ```typescript
20
+ export function createThemeOverrides(theme: BackstageTheme): Overrides {
21
+ return {
22
+ PluginCatalogEntityContextMenu: {
23
+ button: {
24
+ color: 'blue',
25
+ },
26
+ },
27
+ ...
28
+ },
29
+ ...
30
+ }
31
+ ```
32
+
33
+ - f1dcc6f3c6: Use entity type predicates from catalog-model
34
+ - 258057a4b9: Adding ability to customize the "unregister entity" menu item in the entity context menu on the entity page with options 'visible','hidden','disabled'.With this three new options, one can hide the "unregister entity" menu item from the list, disable or keep it enabled.
35
+
36
+ The boolean input for "unregister entity" will be deprecated later in favour of the above three options.
37
+
38
+ - 385389d23c: Updated to remove usage of the `bursts` object in the theme palette
39
+ - be26d95141: Added new `EntityProcessingStatusPicker` that will filter for entities with orphans and/or errors.
40
+
41
+ If you are using the default Catalog page this picker will be added automatically. For those who have customized their Catalog page you'll need to add this manually by doing something like this:
42
+
43
+ ```diff
44
+ ...
45
+ import {
46
+ CatalogFilterLayout,
47
+ EntityTypePicker,
48
+ UserListPicker,
49
+ EntityTagPicker
50
+ + EntityProcessingStatusPicker,
51
+ } from '@backstage/plugin-catalog-react';
52
+ ...
53
+ export const CustomCatalogPage = ({
54
+ columns,
55
+ actions,
56
+ initiallySelectedFilter = 'owned',
57
+ }: CatalogPageProps) => {
58
+ return (
59
+ ...
60
+ <EntityListProvider>
61
+ <CatalogFilterLayout>
62
+ <CatalogFilterLayout.Filters>
63
+ <EntityKindPicker initialFilter="component" hidden />
64
+ <EntityTypePicker />
65
+ <UserListPicker initialFilter={initiallySelectedFilter} />
66
+ <EntityTagPicker />
67
+ + <EntityProcessingStatusPicker />
68
+ <CatalogFilterLayout.Filters>
69
+ <CatalogFilterLayout.Content>
70
+ <CatalogTable columns={columns} actions={actions} />
71
+ </CatalogFilterLayout.Content>
72
+ </CatalogFilterLayout>
73
+ </EntityListProvider>
74
+ ...
75
+ };
76
+ ```
77
+
78
+ - Updated dependencies
79
+ - @backstage/core-components@0.10.0
80
+ - @backstage/catalog-model@1.1.0
81
+ - @backstage/plugin-search-react@1.0.0
82
+ - @backstage/plugin-search-common@1.0.0
83
+ - @backstage/core-plugin-api@1.0.4
84
+ - @backstage/catalog-client@1.0.4
85
+ - @backstage/integration-react@1.1.2
86
+ - @backstage/plugin-catalog-react@1.1.2
87
+ - @backstage/theme@0.2.16
88
+ - @backstage/errors@1.1.0
89
+ - @backstage/plugin-catalog-common@1.0.4
90
+
91
+ ## 1.4.0-next.3
92
+
93
+ ### Patch Changes
94
+
95
+ - Updated dependencies
96
+ - @backstage/core-plugin-api@1.0.4-next.0
97
+ - @backstage/core-components@0.10.0-next.3
98
+ - @backstage/catalog-client@1.0.4-next.2
99
+ - @backstage/integration-react@1.1.2-next.3
100
+ - @backstage/catalog-model@1.1.0-next.3
101
+ - @backstage/plugin-catalog-react@1.1.2-next.3
102
+ - @backstage/plugin-search-react@0.2.2-next.3
103
+
104
+ ## 1.4.0-next.2
105
+
106
+ ### Minor Changes
107
+
108
+ - a274fe38b9: Add hidden title column to catalog and API table to enable filtering by title.
109
+
110
+ ### Patch Changes
111
+
112
+ - 258057a4b9: Adding ability to customize the "unregister entity" menu item in the entity context menu on the entity page with options 'visible','hidden','disabled'.With this three new options, one can hide the "unregister entity" menu item from the list, disable or keep it enabled.
113
+
114
+ The boolean input for "unregister entity" will be deprecated later in favour of the above three options.
115
+
116
+ - 385389d23c: Updated to remove usage of the `bursts` object in the theme palette
117
+ - be26d95141: Added new `EntityProcessingStatusPicker` that will filter for entities with orphans and/or errors.
118
+
119
+ If you are using the default Catalog page this picker will be added automatically. For those who have customized their Catalog page you'll need to add this manually by doing something like this:
120
+
121
+ ```diff
122
+ ...
123
+ import {
124
+ CatalogFilterLayout,
125
+ EntityTypePicker,
126
+ UserListPicker,
127
+ EntityTagPicker
128
+ + EntityProcessingStatusPicker,
129
+ } from '@backstage/plugin-catalog-react';
130
+ ...
131
+ export const CustomCatalogPage = ({
132
+ columns,
133
+ actions,
134
+ initiallySelectedFilter = 'owned',
135
+ }: CatalogPageProps) => {
136
+ return (
137
+ ...
138
+ <EntityListProvider>
139
+ <CatalogFilterLayout>
140
+ <CatalogFilterLayout.Filters>
141
+ <EntityKindPicker initialFilter="component" hidden />
142
+ <EntityTypePicker />
143
+ <UserListPicker initialFilter={initiallySelectedFilter} />
144
+ <EntityTagPicker />
145
+ + <EntityProcessingStatusPicker />
146
+ <CatalogFilterLayout.Filters>
147
+ <CatalogFilterLayout.Content>
148
+ <CatalogTable columns={columns} actions={actions} />
149
+ </CatalogFilterLayout.Content>
150
+ </CatalogFilterLayout>
151
+ </EntityListProvider>
152
+ ...
153
+ };
154
+ ```
155
+
156
+ - Updated dependencies
157
+ - @backstage/core-components@0.10.0-next.2
158
+ - @backstage/catalog-model@1.1.0-next.2
159
+ - @backstage/plugin-search-react@0.2.2-next.2
160
+ - @backstage/theme@0.2.16-next.1
161
+ - @backstage/plugin-catalog-react@1.1.2-next.2
162
+ - @backstage/integration-react@1.1.2-next.2
163
+
3
164
  ## 1.3.1-next.1
4
165
 
5
166
  ### Patch Changes
@@ -1,4 +1,4 @@
1
- export { A as AboutCard, b as AboutContent, d as AboutField } from './index-8994757a.esm.js';
1
+ export { A as AboutCard, b as AboutContent, d as AboutField } from './index-b0b0b077.esm.js';
2
2
  import 'zen-observable';
3
3
  import '@backstage/catalog-model';
4
4
  import 'lodash';
@@ -11,6 +11,7 @@ import '@material-ui/icons/Cached';
11
11
  import '@material-ui/icons/Description';
12
12
  import '@material-ui/icons/Edit';
13
13
  import 'react';
14
+ import '@material-ui/icons/Language';
14
15
  import 'react-use/lib/useAsync';
15
16
  import '@backstage/plugin-search-react';
16
17
  import '@material-ui/icons/OpenInNew';
@@ -19,10 +20,10 @@ import '@material-ui/core/styles';
19
20
  import '@material-ui/icons/Star';
20
21
  import '@material-ui/lab';
21
22
  import 'react-router';
22
- import '@material-ui/icons/Cancel';
23
23
  import '@material-ui/icons/BugReport';
24
24
  import '@material-ui/icons/MoreVert';
25
25
  import '@backstage/plugin-catalog-common';
26
+ import '@material-ui/icons/Cancel';
26
27
  import '@backstage/errors';
27
28
  import '@backstage/catalog-client';
28
- //# sourceMappingURL=index-d9543433.esm.js.map
29
+ //# sourceMappingURL=index-10cb0abb.esm.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index-10cb0abb.esm.js","sources":[],"sourcesContent":[],"names":[],"mappings":";;;;;;;;;;;;;;;;;;;;;;;;;;;"}
@@ -2,8 +2,8 @@ import React from 'react';
2
2
  import { useOutlet } from 'react-router';
3
3
  import { PageWithHeader, Content, ContentHeader, CreateButton, SupportButton } from '@backstage/core-components';
4
4
  import { useApi, configApiRef, useRouteRef } from '@backstage/core-plugin-api';
5
- import { EntityListProvider, CatalogFilterLayout, EntityTypePicker, UserListPicker, EntityOwnerPicker, EntityLifecyclePicker, EntityTagPicker } from '@backstage/plugin-catalog-react';
6
- import { c as createComponentRouteRef, C as CatalogKindHeader, a as CatalogTable } from './index-8994757a.esm.js';
5
+ import { EntityListProvider, CatalogFilterLayout, EntityTypePicker, UserListPicker, EntityOwnerPicker, EntityLifecyclePicker, EntityTagPicker, EntityProcessingStatusPicker } from '@backstage/plugin-catalog-react';
6
+ import { c as createComponentRouteRef, C as CatalogKindHeader, a as CatalogTable } from './index-b0b0b077.esm.js';
7
7
  import 'zen-observable';
8
8
  import '@backstage/catalog-model';
9
9
  import 'lodash';
@@ -12,6 +12,7 @@ import '@material-ui/core';
12
12
  import '@material-ui/icons/Cached';
13
13
  import '@material-ui/icons/Description';
14
14
  import '@material-ui/icons/Edit';
15
+ import '@material-ui/icons/Language';
15
16
  import 'react-use/lib/useAsync';
16
17
  import '@backstage/plugin-search-react';
17
18
  import '@material-ui/icons/OpenInNew';
@@ -19,10 +20,10 @@ import '@material-ui/icons/StarBorder';
19
20
  import '@material-ui/core/styles';
20
21
  import '@material-ui/icons/Star';
21
22
  import '@material-ui/lab';
22
- import '@material-ui/icons/Cancel';
23
23
  import '@material-ui/icons/BugReport';
24
24
  import '@material-ui/icons/MoreVert';
25
25
  import '@backstage/plugin-catalog-common';
26
+ import '@material-ui/icons/Cancel';
26
27
  import '@backstage/errors';
27
28
  import '@backstage/catalog-client';
28
29
 
@@ -49,7 +50,7 @@ function DefaultCatalogPage(props) {
49
50
  to: createComponentLink && createComponentLink()
50
51
  }), /* @__PURE__ */ React.createElement(SupportButton, null, "All your software catalog entities")), /* @__PURE__ */ React.createElement(CatalogFilterLayout, null, /* @__PURE__ */ React.createElement(CatalogFilterLayout.Filters, null, /* @__PURE__ */ React.createElement(EntityTypePicker, null), /* @__PURE__ */ React.createElement(UserListPicker, {
51
52
  initialFilter: initiallySelectedFilter
52
- }), /* @__PURE__ */ React.createElement(EntityOwnerPicker, null), /* @__PURE__ */ React.createElement(EntityLifecyclePicker, null), /* @__PURE__ */ React.createElement(EntityTagPicker, null)), /* @__PURE__ */ React.createElement(CatalogFilterLayout.Content, null, /* @__PURE__ */ React.createElement(CatalogTable, {
53
+ }), /* @__PURE__ */ React.createElement(EntityOwnerPicker, null), /* @__PURE__ */ React.createElement(EntityLifecyclePicker, null), /* @__PURE__ */ React.createElement(EntityTagPicker, null), /* @__PURE__ */ React.createElement(EntityProcessingStatusPicker, null)), /* @__PURE__ */ React.createElement(CatalogFilterLayout.Content, null, /* @__PURE__ */ React.createElement(CatalogTable, {
53
54
  columns,
54
55
  actions,
55
56
  tableOptions
@@ -64,4 +65,4 @@ function CatalogPage(props) {
64
65
  }
65
66
 
66
67
  export { CatalogPage, DefaultCatalogPage };
67
- //# sourceMappingURL=index-19f7244b.esm.js.map
68
+ //# sourceMappingURL=index-1a954f75.esm.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index-1a954f75.esm.js","sources":["../../src/components/CatalogPage/DefaultCatalogPage.tsx","../../src/components/CatalogPage/CatalogPage.tsx"],"sourcesContent":["/*\n * Copyright 2021 The Backstage Authors\n *\n * Licensed under the Apache License, Version 2.0 (the \"License\");\n * you may not use this file except in compliance with the License.\n * You may obtain a copy of the License at\n *\n * http://www.apache.org/licenses/LICENSE-2.0\n *\n * Unless required by applicable law or agreed to in writing, software\n * distributed under the License is distributed on an \"AS IS\" BASIS,\n * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n * See the License for the specific language governing permissions and\n * limitations under the License.\n */\n\nimport {\n Content,\n ContentHeader,\n CreateButton,\n PageWithHeader,\n SupportButton,\n TableColumn,\n TableProps,\n} from '@backstage/core-components';\nimport { configApiRef, useApi, useRouteRef } from '@backstage/core-plugin-api';\nimport {\n CatalogFilterLayout,\n EntityLifecyclePicker,\n EntityListProvider,\n EntityProcessingStatusPicker,\n EntityOwnerPicker,\n EntityTagPicker,\n EntityTypePicker,\n UserListFilterKind,\n UserListPicker,\n} from '@backstage/plugin-catalog-react';\nimport React from 'react';\nimport { createComponentRouteRef } from '../../routes';\nimport { CatalogTable, CatalogTableRow } from '../CatalogTable';\nimport { CatalogKindHeader } from '../CatalogKindHeader';\n\n/**\n * Props for root catalog pages.\n *\n * @public\n */\nexport interface DefaultCatalogPageProps {\n initiallySelectedFilter?: UserListFilterKind;\n columns?: TableColumn<CatalogTableRow>[];\n actions?: TableProps<CatalogTableRow>['actions'];\n initialKind?: string;\n tableOptions?: TableProps<CatalogTableRow>['options'];\n}\n\nexport function DefaultCatalogPage(props: DefaultCatalogPageProps) {\n const {\n columns,\n actions,\n initiallySelectedFilter = 'owned',\n initialKind = 'component',\n tableOptions = {},\n } = props;\n const orgName =\n useApi(configApiRef).getOptionalString('organization.name') ?? 'Backstage';\n const createComponentLink = useRouteRef(createComponentRouteRef);\n\n return (\n <PageWithHeader title={`${orgName} Catalog`} themeId=\"home\">\n <EntityListProvider>\n <Content>\n <ContentHeader\n titleComponent={<CatalogKindHeader initialFilter={initialKind} />}\n >\n <CreateButton\n title=\"Create Component\"\n to={createComponentLink && createComponentLink()}\n />\n <SupportButton>All your software catalog entities</SupportButton>\n </ContentHeader>\n <CatalogFilterLayout>\n <CatalogFilterLayout.Filters>\n <EntityTypePicker />\n <UserListPicker initialFilter={initiallySelectedFilter} />\n <EntityOwnerPicker />\n <EntityLifecyclePicker />\n <EntityTagPicker />\n <EntityProcessingStatusPicker />\n </CatalogFilterLayout.Filters>\n <CatalogFilterLayout.Content>\n <CatalogTable\n columns={columns}\n actions={actions}\n tableOptions={tableOptions}\n />\n </CatalogFilterLayout.Content>\n </CatalogFilterLayout>\n </Content>\n </EntityListProvider>\n </PageWithHeader>\n );\n}\n","/*\n * Copyright 2021 The Backstage Authors\n *\n * Licensed under the Apache License, Version 2.0 (the \"License\");\n * you may not use this file except in compliance with the License.\n * You may obtain a copy of the License at\n *\n * http://www.apache.org/licenses/LICENSE-2.0\n *\n * Unless required by applicable law or agreed to in writing, software\n * distributed under the License is distributed on an \"AS IS\" BASIS,\n * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n * See the License for the specific language governing permissions and\n * limitations under the License.\n */\n\nimport React from 'react';\nimport { useOutlet } from 'react-router';\nimport {\n DefaultCatalogPage,\n DefaultCatalogPageProps,\n} from './DefaultCatalogPage';\n\nexport function CatalogPage(props: DefaultCatalogPageProps) {\n const outlet = useOutlet();\n\n return outlet || <DefaultCatalogPage {...props} />;\n}\n"],"names":[],"mappings":";;;;;;;;;;;;;;;;;;;;;;;;;;;;;AAsBO,SAAS,kBAAkB,CAAC,KAAK,EAAE;AAC1C,EAAE,IAAI,EAAE,CAAC;AACT,EAAE,MAAM;AACR,IAAI,OAAO;AACX,IAAI,OAAO;AACX,IAAI,uBAAuB,GAAG,OAAO;AACrC,IAAI,WAAW,GAAG,WAAW;AAC7B,IAAI,YAAY,GAAG,EAAE;AACrB,GAAG,GAAG,KAAK,CAAC;AACZ,EAAE,MAAM,OAAO,GAAG,CAAC,EAAE,GAAG,MAAM,CAAC,YAAY,CAAC,CAAC,iBAAiB,CAAC,mBAAmB,CAAC,KAAK,IAAI,GAAG,EAAE,GAAG,WAAW,CAAC;AAChH,EAAE,MAAM,mBAAmB,GAAG,WAAW,CAAC,uBAAuB,CAAC,CAAC;AACnE,EAAE,uBAAuB,KAAK,CAAC,aAAa,CAAC,cAAc,EAAE;AAC7D,IAAI,KAAK,EAAE,CAAC,EAAE,OAAO,CAAC,QAAQ,CAAC;AAC/B,IAAI,OAAO,EAAE,MAAM;AACnB,GAAG,kBAAkB,KAAK,CAAC,aAAa,CAAC,kBAAkB,EAAE,IAAI,kBAAkB,KAAK,CAAC,aAAa,CAAC,OAAO,EAAE,IAAI,kBAAkB,KAAK,CAAC,aAAa,CAAC,aAAa,EAAE;AACzK,IAAI,cAAc,kBAAkB,KAAK,CAAC,aAAa,CAAC,iBAAiB,EAAE;AAC3E,MAAM,aAAa,EAAE,WAAW;AAChC,KAAK,CAAC;AACN,GAAG,kBAAkB,KAAK,CAAC,aAAa,CAAC,YAAY,EAAE;AACvD,IAAI,KAAK,EAAE,kBAAkB;AAC7B,IAAI,EAAE,EAAE,mBAAmB,IAAI,mBAAmB,EAAE;AACpD,GAAG,CAAC,kBAAkB,KAAK,CAAC,aAAa,CAAC,aAAa,EAAE,IAAI,EAAE,oCAAoC,CAAC,CAAC,kBAAkB,KAAK,CAAC,aAAa,CAAC,mBAAmB,EAAE,IAAI,kBAAkB,KAAK,CAAC,aAAa,CAAC,mBAAmB,CAAC,OAAO,EAAE,IAAI,kBAAkB,KAAK,CAAC,aAAa,CAAC,gBAAgB,EAAE,IAAI,CAAC,kBAAkB,KAAK,CAAC,aAAa,CAAC,cAAc,EAAE;AAC9V,IAAI,aAAa,EAAE,uBAAuB;AAC1C,GAAG,CAAC,kBAAkB,KAAK,CAAC,aAAa,CAAC,iBAAiB,EAAE,IAAI,CAAC,kBAAkB,KAAK,CAAC,aAAa,CAAC,qBAAqB,EAAE,IAAI,CAAC,kBAAkB,KAAK,CAAC,aAAa,CAAC,eAAe,EAAE,IAAI,CAAC,kBAAkB,KAAK,CAAC,aAAa,CAAC,4BAA4B,EAAE,IAAI,CAAC,CAAC,kBAAkB,KAAK,CAAC,aAAa,CAAC,mBAAmB,CAAC,OAAO,EAAE,IAAI,kBAAkB,KAAK,CAAC,aAAa,CAAC,YAAY,EAAE;AACrY,IAAI,OAAO;AACX,IAAI,OAAO;AACX,IAAI,YAAY;AAChB,GAAG,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;AACV;;AC7CO,SAAS,WAAW,CAAC,KAAK,EAAE;AACnC,EAAE,MAAM,MAAM,GAAG,SAAS,EAAE,CAAC;AAC7B,EAAE,OAAO,MAAM,oBAAoB,KAAK,CAAC,aAAa,CAAC,kBAAkB,EAAE;AAC3E,IAAI,GAAG,KAAK;AACZ,GAAG,CAAC,CAAC;AACL;;;;"}
@@ -1,15 +1,16 @@
1
1
  import ObservableImpl from 'zen-observable';
2
- import { stringifyEntityRef, RELATION_PART_OF, RELATION_OWNED_BY, ANNOTATION_EDIT_URL, DEFAULT_NAMESPACE, ANNOTATION_LOCATION, ANNOTATION_VIEW_URL } from '@backstage/catalog-model';
2
+ import { stringifyEntityRef, RELATION_PART_OF, RELATION_OWNED_BY, getEntitySourceLocation, ANNOTATION_EDIT_URL, DEFAULT_NAMESPACE, ANNOTATION_LOCATION, ANNOTATION_VIEW_URL } from '@backstage/catalog-model';
3
3
  import { isArray, isString, capitalize as capitalize$1 } from 'lodash';
4
4
  import { Link, HeaderIconLinkRow, OverflowTooltip, WarningPanel, CodeSnippet, Table, Page, Header, Progress, RoutedTabs, Content, HeaderLabel, ResponseErrorPanel } from '@backstage/core-components';
5
5
  import { createExternalRouteRef, createRouteRef, useElementFilter, useApi, alertApiRef, useRouteRef, useAnalytics, attachComponentData, useRouteRefParams, useApiHolder, createPlugin, createApiFactory, discoveryApiRef, fetchApiRef, storageApiRef, createRoutableExtension, createComponentExtension } from '@backstage/core-plugin-api';
6
6
  import { scmIntegrationsApiRef, ScmIntegrationIcon } from '@backstage/integration-react';
7
- import { getEntityRelations, EntityRefLinks, useEntity, catalogApiRef, getEntitySourceLocation, useEntityList, EntityKindFilter, humanizeEntityRef, EntityRefLink, useStarredEntities, useEntityPermission, entityRouteRef, useAsyncEntity, UnregisterEntityDialog, InspectEntityDialog, FavoriteEntity, CatalogFilterLayout, starredEntitiesApiRef } from '@backstage/plugin-catalog-react';
8
- import { makeStyles, Typography, Grid, Chip, Card, CardHeader, IconButton, Divider, CardContent, createStyles, capitalize, Select, InputBase, MenuItem, ListItem, ListItemIcon, ListItemText, Box, Popover, MenuList, Dialog, DialogTitle, DialogActions, Button } from '@material-ui/core';
7
+ import { getEntityRelations, EntityRefLinks, useEntity, catalogApiRef, getEntitySourceLocation as getEntitySourceLocation$1, useEntityList, EntityKindFilter, EntityRefLink, humanizeEntityRef, useStarredEntities, useEntityPermission, entityRouteRef, useAsyncEntity, UnregisterEntityDialog, InspectEntityDialog, FavoriteEntity, CatalogFilterLayout, starredEntitiesApiRef } from '@backstage/plugin-catalog-react';
8
+ import { makeStyles, Typography, Grid, Box, useMediaQuery, ImageList, ImageListItem, Chip, Card, CardHeader, IconButton, Divider, CardContent, createStyles, capitalize, Select, InputBase, MenuItem, ListItem, ListItemIcon, ListItemText, Popover, MenuList, Dialog, DialogTitle, DialogActions, Button } from '@material-ui/core';
9
9
  import CachedIcon from '@material-ui/icons/Cached';
10
10
  import DocsIcon from '@material-ui/icons/Description';
11
11
  import EditIcon from '@material-ui/icons/Edit';
12
12
  import React, { useCallback, useMemo, useState, useEffect } from 'react';
13
+ import LanguageIcon from '@material-ui/icons/Language';
13
14
  import useAsync from 'react-use/lib/useAsync';
14
15
  import { HighlightedSearchResultText } from '@backstage/plugin-search-react';
15
16
  import OpenInNew from '@material-ui/icons/OpenInNew';
@@ -18,10 +19,10 @@ import { withStyles, makeStyles as makeStyles$1 } from '@material-ui/core/styles
18
19
  import Star from '@material-ui/icons/Star';
19
20
  import { Alert } from '@material-ui/lab';
20
21
  import { useLocation, useNavigate } from 'react-router';
21
- import CancelIcon from '@material-ui/icons/Cancel';
22
22
  import BugReportIcon from '@material-ui/icons/BugReport';
23
23
  import MoreVert from '@material-ui/icons/MoreVert';
24
24
  import { catalogEntityDeletePermission } from '@backstage/plugin-catalog-common';
25
+ import CancelIcon from '@material-ui/icons/Cancel';
25
26
  import { assertError } from '@backstage/errors';
26
27
  import { ENTITY_STATUS_CATALOG_PROCESSING_TYPE, CatalogClient } from '@backstage/catalog-client';
27
28
 
@@ -94,7 +95,7 @@ const rootRouteRef = createRouteRef({
94
95
  id: "catalog"
95
96
  });
96
97
 
97
- const useStyles$5 = makeStyles((theme) => ({
98
+ const useStyles$6 = makeStyles((theme) => ({
98
99
  value: {
99
100
  fontWeight: "bold",
100
101
  overflow: "hidden",
@@ -113,7 +114,7 @@ const useStyles$5 = makeStyles((theme) => ({
113
114
  }));
114
115
  function AboutField(props) {
115
116
  const { label, value, gridSizes, children } = props;
116
- const classes = useStyles$5();
117
+ const classes = useStyles$6();
117
118
  const childElements = useElementFilter(children, (c) => c.getElements());
118
119
  const content = childElements.length > 0 ? childElements : /* @__PURE__ */ React.createElement(Typography, {
119
120
  variant: "body2",
@@ -128,13 +129,93 @@ function AboutField(props) {
128
129
  }, label), content);
129
130
  }
130
131
 
132
+ const useStyles$5 = makeStyles({
133
+ svgIcon: {
134
+ display: "inline-block",
135
+ "& svg": {
136
+ display: "inline-block",
137
+ fontSize: "inherit",
138
+ verticalAlign: "baseline"
139
+ }
140
+ }
141
+ });
142
+ function IconLink(props) {
143
+ const { href, text, Icon } = props;
144
+ const classes = useStyles$5();
145
+ return /* @__PURE__ */ React.createElement(Box, {
146
+ display: "flex"
147
+ }, /* @__PURE__ */ React.createElement(Box, {
148
+ mr: 1,
149
+ className: classes.svgIcon
150
+ }, /* @__PURE__ */ React.createElement(Typography, {
151
+ component: "div"
152
+ }, Icon ? /* @__PURE__ */ React.createElement(Icon, null) : /* @__PURE__ */ React.createElement(LanguageIcon, null))), /* @__PURE__ */ React.createElement(Box, {
153
+ flexGrow: "1"
154
+ }, /* @__PURE__ */ React.createElement(Link, {
155
+ to: href,
156
+ target: "_blank",
157
+ rel: "noopener"
158
+ }, text || href)));
159
+ }
160
+
161
+ const colDefaults = {
162
+ xs: 1,
163
+ sm: 1,
164
+ md: 1,
165
+ lg: 2,
166
+ xl: 3
167
+ };
168
+ function useDynamicColumns(cols) {
169
+ var _a, _b;
170
+ const matches = [
171
+ useMediaQuery((theme) => theme.breakpoints.up("xl")) ? "xl" : null,
172
+ useMediaQuery((theme) => theme.breakpoints.up("lg")) ? "lg" : null,
173
+ useMediaQuery((theme) => theme.breakpoints.up("md")) ? "md" : null,
174
+ useMediaQuery((theme) => theme.breakpoints.up("sm")) ? "sm" : null,
175
+ useMediaQuery((theme) => theme.breakpoints.up("xs")) ? "xs" : null
176
+ ];
177
+ let numOfCols = 1;
178
+ if (typeof cols === "number") {
179
+ numOfCols = cols;
180
+ } else {
181
+ const breakpoint = (_a = matches.find((k) => k !== null)) != null ? _a : "xs";
182
+ numOfCols = (_b = cols == null ? void 0 : cols[breakpoint]) != null ? _b : colDefaults[breakpoint];
183
+ }
184
+ return numOfCols;
185
+ }
186
+
187
+ function LinksGridList(props) {
188
+ const { items, cols = void 0 } = props;
189
+ const numOfCols = useDynamicColumns(cols);
190
+ return /* @__PURE__ */ React.createElement(ImageList, {
191
+ rowHeight: "auto",
192
+ cols: numOfCols
193
+ }, items.map(({ text, href, Icon }, i) => /* @__PURE__ */ React.createElement(ImageListItem, {
194
+ key: i
195
+ }, /* @__PURE__ */ React.createElement(IconLink, {
196
+ href,
197
+ text: text != null ? text : href,
198
+ Icon
199
+ }))));
200
+ }
201
+
131
202
  const useStyles$4 = makeStyles({
132
203
  description: {
133
204
  wordBreak: "break-word"
134
205
  }
135
206
  });
207
+ function getLocationTargetHref(target, type, entitySourceLocation) {
208
+ if (type === "url" || target.includes("://")) {
209
+ return target;
210
+ }
211
+ const srcLocationUrl = entitySourceLocation.type === "file" ? `file://${entitySourceLocation.target}` : entitySourceLocation.target;
212
+ if (type === "file" || entitySourceLocation.type === "file") {
213
+ return new URL(target, srcLocationUrl).href;
214
+ }
215
+ return srcLocationUrl;
216
+ }
136
217
  function AboutContent(props) {
137
- var _a, _b, _c, _d, _e, _f;
218
+ var _a, _b, _c, _d, _e, _f, _g, _h;
138
219
  const { entity } = props;
139
220
  const classes = useStyles$4();
140
221
  const isSystem = entity.kind.toLocaleLowerCase("en-US") === "system";
@@ -154,6 +235,12 @@ function AboutContent(props) {
154
235
  kind: "domain"
155
236
  });
156
237
  const ownedByRelations = getEntityRelations(entity, RELATION_OWNED_BY);
238
+ let entitySourceLocation;
239
+ try {
240
+ entitySourceLocation = getEntitySourceLocation(entity);
241
+ } catch (e) {
242
+ entitySourceLocation = void 0;
243
+ }
157
244
  return /* @__PURE__ */ React.createElement(Grid, {
158
245
  container: true
159
246
  }, /* @__PURE__ */ React.createElement(AboutField, {
@@ -207,7 +294,19 @@ function AboutContent(props) {
207
294
  key: t,
208
295
  size: "small",
209
296
  label: t
210
- }))));
297
+ }))), isLocation && (((_g = entity == null ? void 0 : entity.spec) == null ? void 0 : _g.targets) || ((_h = entity == null ? void 0 : entity.spec) == null ? void 0 : _h.target)) && /* @__PURE__ */ React.createElement(AboutField, {
298
+ label: "Targets",
299
+ gridSizes: { xs: 12 }
300
+ }, /* @__PURE__ */ React.createElement(LinksGridList, {
301
+ cols: 1,
302
+ items: (entity.spec.targets || [entity.spec.target]).map((target) => target).map((target) => {
303
+ var _a2;
304
+ return {
305
+ text: target,
306
+ href: getLocationTargetHref(target, ((_a2 = entity == null ? void 0 : entity.spec) == null ? void 0 : _a2.type) || "unknown", entitySourceLocation)
307
+ };
308
+ })
309
+ })));
211
310
  }
212
311
 
213
312
  const useStyles$3 = makeStyles({
@@ -238,7 +337,7 @@ function AboutCard(props) {
238
337
  const catalogApi = useApi(catalogApiRef);
239
338
  const alertApi = useApi(alertApiRef);
240
339
  const viewTechdocLink = useRouteRef(viewTechDocRouteRef);
241
- const entitySourceLocation = getEntitySourceLocation(entity, scmIntegrationsApi);
340
+ const entitySourceLocation = getEntitySourceLocation$1(entity, scmIntegrationsApi);
242
341
  const entityMetadataEditUrl = (_a = entity.metadata.annotations) == null ? void 0 : _a[ANNOTATION_EDIT_URL];
243
342
  const viewInSource = {
244
343
  label: "View Source",
@@ -452,11 +551,25 @@ const columnFactories = Object.freeze({
452
551
  })
453
552
  };
454
553
  },
554
+ createSpecTargetsColumn() {
555
+ return {
556
+ title: "Targets",
557
+ field: "entity.spec.targets",
558
+ render: ({ entity }) => {
559
+ var _a, _b;
560
+ return /* @__PURE__ */ React.createElement(React.Fragment, null, (((_a = entity == null ? void 0 : entity.spec) == null ? void 0 : _a.targets) || ((_b = entity == null ? void 0 : entity.spec) == null ? void 0 : _b.target)) && /* @__PURE__ */ React.createElement(OverflowTooltip, {
561
+ text: (entity.spec.targets || [entity.spec.target]).join(", "),
562
+ placement: "bottom-start"
563
+ }));
564
+ }
565
+ };
566
+ },
455
567
  createSpecTypeColumn() {
456
568
  return {
457
569
  title: "Type",
458
570
  field: "entity.spec.type",
459
- hidden: true
571
+ hidden: true,
572
+ width: "auto"
460
573
  };
461
574
  },
462
575
  createSpecLifecycleColumn() {
@@ -489,7 +602,16 @@ const columnFactories = Object.freeze({
489
602
  size: "small",
490
603
  variant: "outlined",
491
604
  style: { marginBottom: "0px" }
492
- })))
605
+ }))),
606
+ width: "auto"
607
+ };
608
+ },
609
+ createTitleColumn(options) {
610
+ return {
611
+ title: "Title",
612
+ field: "entity.metadata.title",
613
+ hidden: options == null ? void 0 : options.hidden,
614
+ searchable: true
493
615
  };
494
616
  }
495
617
  });
@@ -507,6 +629,7 @@ const CatalogTable = (props) => {
507
629
  const defaultColumns = useMemo(() => {
508
630
  var _a2;
509
631
  return [
632
+ columnFactories.createTitleColumn({ hidden: true }),
510
633
  columnFactories.createNameColumn({ defaultKind: (_a2 = filters.kind) == null ? void 0 : _a2.value }),
511
634
  ...createEntitySpecificColumns(),
512
635
  columnFactories.createMetadataDescriptionColumn(),
@@ -521,9 +644,13 @@ const CatalogTable = (props) => {
521
644
  case "system":
522
645
  return [columnFactories.createOwnerColumn()];
523
646
  case "group":
524
- case "location":
525
647
  case "template":
526
648
  return [columnFactories.createSpecTypeColumn()];
649
+ case "location":
650
+ return [
651
+ columnFactories.createSpecTypeColumn(),
652
+ columnFactories.createSpecTargetsColumn()
653
+ ];
527
654
  default:
528
655
  return [
529
656
  columnFactories.createSystemColumn(),
@@ -642,15 +769,41 @@ const CatalogTable = (props) => {
642
769
  };
643
770
  CatalogTable.columns = columnFactories;
644
771
 
772
+ function UnregisterEntity(props) {
773
+ var _a;
774
+ const {
775
+ unregisterEntityOptions,
776
+ isUnregisterAllowed,
777
+ onUnregisterEntity,
778
+ onClose
779
+ } = props;
780
+ const isBoolean = typeof (unregisterEntityOptions == null ? void 0 : unregisterEntityOptions.disableUnregister) === "boolean";
781
+ const isDisabled = (_a = !isUnregisterAllowed || (isBoolean ? !!(unregisterEntityOptions == null ? void 0 : unregisterEntityOptions.disableUnregister) : (unregisterEntityOptions == null ? void 0 : unregisterEntityOptions.disableUnregister) === "disable")) != null ? _a : false;
782
+ let unregisterButton = /* @__PURE__ */ React.createElement(React.Fragment, null);
783
+ if ((unregisterEntityOptions == null ? void 0 : unregisterEntityOptions.disableUnregister) !== "hidden") {
784
+ unregisterButton = /* @__PURE__ */ React.createElement(MenuItem, {
785
+ onClick: () => {
786
+ onClose();
787
+ onUnregisterEntity();
788
+ },
789
+ disabled: isDisabled
790
+ }, /* @__PURE__ */ React.createElement(ListItemIcon, null, /* @__PURE__ */ React.createElement(CancelIcon, {
791
+ fontSize: "small"
792
+ })), /* @__PURE__ */ React.createElement(ListItemText, {
793
+ primary: "Unregister entity"
794
+ }));
795
+ }
796
+ return /* @__PURE__ */ React.createElement(React.Fragment, null, unregisterButton);
797
+ }
798
+
645
799
  const useStyles = makeStyles$1((theme) => {
646
800
  return {
647
801
  button: {
648
- color: theme.palette.bursts.fontColor
802
+ color: theme.page.fontColor
649
803
  }
650
804
  };
651
805
  }, { name: "PluginCatalogEntityContextMenu" });
652
806
  function EntityContextMenu(props) {
653
- var _a;
654
807
  const {
655
808
  UNSTABLE_extraContextMenuItems,
656
809
  UNSTABLE_contextMenuOptions,
@@ -660,6 +813,7 @@ function EntityContextMenu(props) {
660
813
  const [anchorEl, setAnchorEl] = useState();
661
814
  const classes = useStyles();
662
815
  const unregisterPermission = useEntityPermission(catalogEntityDeletePermission);
816
+ const isAllowed = unregisterPermission.allowed;
663
817
  const onOpen = (event) => {
664
818
  setAnchorEl(event.currentTarget);
665
819
  };
@@ -682,7 +836,6 @@ function EntityContextMenu(props) {
682
836
  key: "the divider is here!"
683
837
  })
684
838
  ];
685
- const disableUnregister = (_a = !unregisterPermission.allowed || (UNSTABLE_contextMenuOptions == null ? void 0 : UNSTABLE_contextMenuOptions.disableUnregister)) != null ? _a : false;
686
839
  return /* @__PURE__ */ React.createElement(React.Fragment, null, /* @__PURE__ */ React.createElement(IconButton, {
687
840
  "aria-label": "more",
688
841
  "aria-controls": "long-menu",
@@ -700,17 +853,12 @@ function EntityContextMenu(props) {
700
853
  anchorOrigin: { vertical: "bottom", horizontal: "right" },
701
854
  transformOrigin: { vertical: "top", horizontal: "right" },
702
855
  "aria-labelledby": "long-menu"
703
- }, /* @__PURE__ */ React.createElement(MenuList, null, extraItems, /* @__PURE__ */ React.createElement(MenuItem, {
704
- onClick: () => {
705
- onClose();
706
- onUnregisterEntity();
707
- },
708
- disabled: disableUnregister
709
- }, /* @__PURE__ */ React.createElement(ListItemIcon, null, /* @__PURE__ */ React.createElement(CancelIcon, {
710
- fontSize: "small"
711
- })), /* @__PURE__ */ React.createElement(ListItemText, {
712
- primary: "Unregister entity"
713
- })), /* @__PURE__ */ React.createElement(MenuItem, {
856
+ }, /* @__PURE__ */ React.createElement(MenuList, null, extraItems, /* @__PURE__ */ React.createElement(UnregisterEntity, {
857
+ unregisterEntityOptions: UNSTABLE_contextMenuOptions,
858
+ isUnregisterAllowed: isAllowed,
859
+ onUnregisterEntity,
860
+ onClose
861
+ }), /* @__PURE__ */ React.createElement(MenuItem, {
714
862
  onClick: () => {
715
863
  onClose();
716
864
  onInspectEntity();
@@ -1078,7 +1226,7 @@ const catalogPlugin = createPlugin({
1078
1226
  });
1079
1227
  const CatalogIndexPage = catalogPlugin.provide(createRoutableExtension({
1080
1228
  name: "CatalogIndexPage",
1081
- component: () => import('./index-19f7244b.esm.js').then((m) => m.CatalogPage),
1229
+ component: () => import('./index-1a954f75.esm.js').then((m) => m.CatalogPage),
1082
1230
  mountPoint: rootRouteRef
1083
1231
  }));
1084
1232
  const CatalogEntityPage = catalogPlugin.provide(createRoutableExtension({
@@ -1089,13 +1237,13 @@ const CatalogEntityPage = catalogPlugin.provide(createRoutableExtension({
1089
1237
  const EntityAboutCard = catalogPlugin.provide(createComponentExtension({
1090
1238
  name: "EntityAboutCard",
1091
1239
  component: {
1092
- lazy: () => import('./index-d9543433.esm.js').then((m) => m.AboutCard)
1240
+ lazy: () => import('./index-10cb0abb.esm.js').then((m) => m.AboutCard)
1093
1241
  }
1094
1242
  }));
1095
1243
  const EntityLinksCard = catalogPlugin.provide(createComponentExtension({
1096
1244
  name: "EntityLinksCard",
1097
1245
  component: {
1098
- lazy: () => import('./index-896aeac9.esm.js').then((m) => m.EntityLinksCard)
1246
+ lazy: () => import('./index-c6279600.esm.js').then((m) => m.EntityLinksCard)
1099
1247
  }
1100
1248
  }));
1101
1249
  const EntityHasSystemsCard = catalogPlugin.provide(createComponentExtension({
@@ -1147,5 +1295,5 @@ const RelatedEntitiesCard = catalogPlugin.provide(createComponentExtension({
1147
1295
  }
1148
1296
  }));
1149
1297
 
1150
- export { AboutCard as A, EntityListContainer as B, CatalogKindHeader as C, DefaultStarredEntitiesApi as D, EntityAboutCard as E, FilteredEntityLayout as F, RelatedEntitiesCard as R, CatalogTable as a, AboutContent as b, createComponentRouteRef as c, AboutField as d, CatalogEntityPage as e, CatalogIndexPage as f, catalogPlugin as g, EntityDependencyOfComponentsCard as h, EntityDependsOnComponentsCard as i, EntityDependsOnResourcesCard as j, EntityHasComponentsCard as k, EntityHasResourcesCard as l, EntityHasSubcomponentsCard as m, EntityHasSystemsCard as n, EntityLinksCard as o, CatalogSearchResultListItem as p, EntityLayout as q, EntityOrphanWarning as r, isOrphan as s, EntityProcessingErrorsPanel as t, hasCatalogProcessingErrors as u, EntitySwitch as v, isKind as w, isNamespace as x, isComponentType as y, FilterContainer as z };
1151
- //# sourceMappingURL=index-8994757a.esm.js.map
1298
+ export { AboutCard as A, EntityListContainer as B, CatalogKindHeader as C, DefaultStarredEntitiesApi as D, EntityAboutCard as E, FilteredEntityLayout as F, LinksGridList as L, RelatedEntitiesCard as R, CatalogTable as a, AboutContent as b, createComponentRouteRef as c, AboutField as d, CatalogEntityPage as e, CatalogIndexPage as f, catalogPlugin as g, EntityDependencyOfComponentsCard as h, EntityDependsOnComponentsCard as i, EntityDependsOnResourcesCard as j, EntityHasComponentsCard as k, EntityHasResourcesCard as l, EntityHasSubcomponentsCard as m, EntityHasSystemsCard as n, EntityLinksCard as o, CatalogSearchResultListItem as p, EntityLayout as q, EntityOrphanWarning as r, isOrphan as s, EntityProcessingErrorsPanel as t, hasCatalogProcessingErrors as u, EntitySwitch as v, isKind as w, isNamespace as x, isComponentType as y, FilterContainer as z };
1299
+ //# sourceMappingURL=index-b0b0b077.esm.js.map