@backstage/plugin-catalog-react 1.4.1-next.0 → 1.4.1-next.2

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,44 @@
1
1
  # @backstage/plugin-catalog-react
2
2
 
3
+ ## 1.4.1-next.2
4
+
5
+ ### Patch Changes
6
+
7
+ - 81bee24c5de: Fixed bug in catalog filters where you could not click on the text to select a value.
8
+ - 2898b6c8d52: Minor type tweaks for TypeScript 5.0
9
+ - Updated dependencies
10
+ - @backstage/catalog-client@1.4.1-next.0
11
+ - @backstage/core-components@0.12.6-next.2
12
+ - @backstage/core-plugin-api@1.5.1-next.1
13
+ - @backstage/catalog-model@1.2.1
14
+ - @backstage/errors@1.1.5
15
+ - @backstage/integration@1.4.4-next.0
16
+ - @backstage/theme@0.2.19-next.0
17
+ - @backstage/types@1.0.2
18
+ - @backstage/version-bridge@1.0.4-next.0
19
+ - @backstage/plugin-catalog-common@1.0.13-next.0
20
+ - @backstage/plugin-permission-common@0.7.5-next.0
21
+ - @backstage/plugin-permission-react@0.4.12-next.1
22
+
23
+ ## 1.4.1-next.1
24
+
25
+ ### Patch Changes
26
+
27
+ - e0c6e8b9c3c: Update peer dependencies
28
+ - Updated dependencies
29
+ - @backstage/core-components@0.12.6-next.1
30
+ - @backstage/plugin-permission-common@0.7.5-next.0
31
+ - @backstage/core-plugin-api@1.5.1-next.0
32
+ - @backstage/plugin-permission-react@0.4.12-next.0
33
+ - @backstage/version-bridge@1.0.4-next.0
34
+ - @backstage/integration@1.4.4-next.0
35
+ - @backstage/theme@0.2.19-next.0
36
+ - @backstage/catalog-client@1.4.0
37
+ - @backstage/catalog-model@1.2.1
38
+ - @backstage/errors@1.1.5
39
+ - @backstage/types@1.0.2
40
+ - @backstage/plugin-catalog-common@1.0.13-next.0
41
+
3
42
  ## 1.4.1-next.0
4
43
 
5
44
  ### Patch Changes
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@backstage/plugin-catalog-react",
3
- "version": "1.4.1-next.0",
3
+ "version": "1.4.1-next.2",
4
4
  "main": "../dist/alpha.esm.js",
5
5
  "module": "../dist/alpha.esm.js",
6
6
  "types": "../dist/alpha.d.ts"
package/dist/alpha.esm.js CHANGED
@@ -1,20 +1,10 @@
1
- import { parseEntityRef, getCompoundEntityRef, stringifyEntityRef, RELATION_MEMBER_OF, RELATION_OWNED_BY } from '@backstage/catalog-model';
1
+ import { RELATION_MEMBER_OF, getCompoundEntityRef, stringifyEntityRef, RELATION_OWNED_BY } from '@backstage/catalog-model';
2
+ import { g as getEntityRelations, a as useAsyncEntity } from './esm/useEntity-de64059a.esm.js';
2
3
  import { usePermission } from '@backstage/plugin-permission-react';
3
4
  import '@backstage/core-plugin-api';
4
- import { createVersionedContext, useVersionedContext } from '@backstage/version-bridge';
5
+ import '@backstage/version-bridge';
5
6
  import 'react';
6
7
 
7
- function getEntityRelations(entity, relationType, filter) {
8
- var _a;
9
- let entityNames = ((_a = entity == null ? void 0 : entity.relations) == null ? void 0 : _a.filter((r) => r.type === relationType).map((r) => parseEntityRef(r.targetRef))) || [];
10
- if (filter == null ? void 0 : filter.kind) {
11
- entityNames = entityNames.filter(
12
- (e) => e.kind.toLocaleLowerCase("en-US") === filter.kind.toLocaleLowerCase("en-US")
13
- );
14
- }
15
- return entityNames;
16
- }
17
-
18
8
  function isOwnerOf(owner, entity) {
19
9
  const possibleOwners = new Set(
20
10
  [
@@ -33,24 +23,6 @@ function isOwnerOf(owner, entity) {
33
23
  return false;
34
24
  }
35
25
 
36
- createVersionedContext(
37
- "entity-context"
38
- );
39
- function useAsyncEntity() {
40
- const versionedHolder = useVersionedContext(
41
- "entity-context"
42
- );
43
- if (!versionedHolder) {
44
- throw new Error("Entity context is not available");
45
- }
46
- const value = versionedHolder.atVersion(1);
47
- if (!value) {
48
- throw new Error("EntityContext v1 not available");
49
- }
50
- const { entity, loading, error, refresh } = value;
51
- return { entity, loading, error, refresh };
52
- }
53
-
54
26
  function useEntityPermission(permission) {
55
27
  const {
56
28
  entity,
@@ -1 +1 @@
1
- {"version":3,"file":"alpha.esm.js","sources":["../src/utils/getEntityRelations.ts","../src/utils/isOwnerOf.ts","../src/hooks/useEntity.tsx","../src/hooks/useEntityPermission.ts"],"sourcesContent":["/*\n * Copyright 2020 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 Entity,\n CompoundEntityRef,\n parseEntityRef,\n} from '@backstage/catalog-model';\n\n// TODO(freben): This should be returning entity refs instead\n/**\n * Get the related entity references.\n *\n * @public\n */\nexport function getEntityRelations(\n entity: Entity | undefined,\n relationType: string,\n filter?: { kind: string },\n): CompoundEntityRef[] {\n let entityNames =\n entity?.relations\n ?.filter(r => r.type === relationType)\n .map(r => parseEntityRef(r.targetRef)) || [];\n\n if (filter?.kind) {\n entityNames = entityNames.filter(\n e =>\n e.kind.toLocaleLowerCase('en-US') ===\n filter.kind.toLocaleLowerCase('en-US'),\n );\n }\n\n return entityNames;\n}\n","/*\n * Copyright 2020 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 Entity,\n getCompoundEntityRef,\n RELATION_MEMBER_OF,\n RELATION_OWNED_BY,\n stringifyEntityRef,\n} from '@backstage/catalog-model';\nimport { getEntityRelations } from './getEntityRelations';\n\n/**\n * Returns true if the `owner` argument is a direct owner on the `entity` argument.\n *\n * @alpha\n * @remarks\n *\n * Note that this ownership is not the same as using the claims in the auth-resolver, it only will take into account ownership as expressed by direct entity relations.\n * It doesn't know anything about the additional groups that a user might belong to which the claims contain.\n */\nexport function isOwnerOf(owner: Entity, entity: Entity) {\n const possibleOwners = new Set(\n [\n ...getEntityRelations(owner, RELATION_MEMBER_OF, { kind: 'group' }),\n ...(owner ? [getCompoundEntityRef(owner)] : []),\n ].map(stringifyEntityRef),\n );\n\n const owners = getEntityRelations(entity, RELATION_OWNED_BY).map(\n stringifyEntityRef,\n );\n\n for (const ownerItem of owners) {\n if (possibleOwners.has(ownerItem)) {\n return true;\n }\n }\n\n return false;\n}\n","/*\n * Copyright 2020 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 */\nimport { Entity, stringifyEntityRef } from '@backstage/catalog-model';\nimport { AnalyticsContext } from '@backstage/core-plugin-api';\nimport {\n createVersionedContext,\n createVersionedValueMap,\n useVersionedContext,\n} from '@backstage/version-bridge';\nimport React, { ReactNode } from 'react';\n\n/** @public */\nexport type EntityLoadingStatus<TEntity extends Entity = Entity> = {\n entity?: TEntity;\n loading: boolean;\n error?: Error;\n refresh?: VoidFunction;\n};\n\n// This context has support for multiple concurrent versions of this package.\n// It is currently used in parallel with the old context in order to provide\n// a smooth transition, but will eventually be the only context we use.\nconst NewEntityContext = createVersionedContext<{ 1: EntityLoadingStatus }>(\n 'entity-context',\n);\n\n/**\n * Properties for the AsyncEntityProvider component.\n *\n * @public\n */\nexport interface AsyncEntityProviderProps {\n children: ReactNode;\n entity?: Entity;\n loading: boolean;\n error?: Error;\n refresh?: VoidFunction;\n}\n\n/**\n * Provides a loaded entity to be picked up by the `useEntity` hook.\n *\n * @public\n */\nexport const AsyncEntityProvider = (props: AsyncEntityProviderProps) => {\n const { children, entity, loading, error, refresh } = props;\n const value = { entity, loading, error, refresh };\n // We provide both the old and the new context, since\n // consumers might be doing things like `useContext(EntityContext)`\n return (\n <NewEntityContext.Provider value={createVersionedValueMap({ 1: value })}>\n <AnalyticsContext\n attributes={{\n ...(entity ? { entityRef: stringifyEntityRef(entity) } : undefined),\n }}\n >\n {children}\n </AnalyticsContext>\n </NewEntityContext.Provider>\n );\n};\n\n/**\n * Properties for the EntityProvider component.\n *\n * @public\n */\nexport interface EntityProviderProps {\n children: ReactNode;\n entity?: Entity;\n}\n\n/**\n * Provides an entity to be picked up by the `useEntity` hook.\n *\n * @public\n */\nexport const EntityProvider = (props: EntityProviderProps) => (\n <AsyncEntityProvider\n entity={props.entity}\n loading={!Boolean(props.entity)}\n error={undefined}\n refresh={undefined}\n children={props.children}\n />\n);\n\n/**\n * Grab the current entity from the context, throws if the entity has not yet been loaded\n * or is not available.\n *\n * @public\n */\nexport function useEntity<TEntity extends Entity = Entity>(): {\n entity: TEntity;\n} {\n const versionedHolder = useVersionedContext<{ 1: EntityLoadingStatus }>(\n 'entity-context',\n );\n\n if (!versionedHolder) {\n throw new Error('Entity context is not available');\n }\n\n const value = versionedHolder.atVersion(1);\n if (!value) {\n throw new Error('EntityContext v1 not available');\n }\n\n if (!value.entity) {\n throw new Error(\n 'useEntity hook is being called outside of an EntityLayout where the entity has not been loaded. If this is intentional, please use useAsyncEntity instead.',\n );\n }\n\n return { entity: value.entity as TEntity };\n}\n\n/**\n * Grab the current entity from the context, provides loading state and errors, and the ability to refresh.\n *\n * @public\n */\nexport function useAsyncEntity<\n TEntity extends Entity = Entity,\n>(): EntityLoadingStatus<TEntity> {\n const versionedHolder = useVersionedContext<{ 1: EntityLoadingStatus }>(\n 'entity-context',\n );\n\n if (!versionedHolder) {\n throw new Error('Entity context is not available');\n }\n const value = versionedHolder.atVersion(1);\n if (!value) {\n throw new Error('EntityContext v1 not available');\n }\n\n const { entity, loading, error, refresh } = value;\n return { entity: entity as TEntity, loading, error, refresh };\n}\n","/*\n * Copyright 2022 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 { stringifyEntityRef } from '@backstage/catalog-model';\nimport { ResourcePermission } from '@backstage/plugin-permission-common';\nimport { usePermission } from '@backstage/plugin-permission-react';\nimport { useAsyncEntity } from './useEntity';\n\n/**\n * A thin wrapper around the\n * {@link @backstage/plugin-permission-react#usePermission} hook which uses the\n * current entity in context to make an authorization request for the given\n * {@link @backstage/plugin-catalog-common#CatalogEntityPermission}.\n *\n * Note: this hook blocks the permission request until the entity has loaded in\n * context. If you have the entityRef and need concurrent requests, use the\n * `usePermission` hook directly.\n * @alpha\n */\nexport function useEntityPermission(\n // TODO(joeporpeglia) Replace with `CatalogEntityPermission` when the issue described in\n // https://github.com/backstage/backstage/pull/10128 is fixed.\n permission: ResourcePermission<'catalog-entity'>,\n): {\n loading: boolean;\n allowed: boolean;\n error?: Error;\n} {\n const {\n entity,\n loading: loadingEntity,\n error: entityError,\n } = useAsyncEntity();\n const {\n allowed,\n loading: loadingPermission,\n error: permissionError,\n } = usePermission({\n permission,\n resourceRef: entity ? stringifyEntityRef(entity) : undefined,\n });\n\n if (loadingEntity || loadingPermission) {\n return { loading: true, allowed: false };\n }\n if (entityError) {\n return { loading: false, allowed: false, error: entityError };\n }\n return { loading: false, allowed, error: permissionError };\n}\n"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"alpha.esm.js","sources":["../src/utils/isOwnerOf.ts","../src/hooks/useEntityPermission.ts"],"sourcesContent":["/*\n * Copyright 2020 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 Entity,\n getCompoundEntityRef,\n RELATION_MEMBER_OF,\n RELATION_OWNED_BY,\n stringifyEntityRef,\n} from '@backstage/catalog-model';\nimport { getEntityRelations } from './getEntityRelations';\n\n/**\n * Returns true if the `owner` argument is a direct owner on the `entity` argument.\n *\n * @alpha\n * @remarks\n *\n * Note that this ownership is not the same as using the claims in the auth-resolver, it only will take into account ownership as expressed by direct entity relations.\n * It doesn't know anything about the additional groups that a user might belong to which the claims contain.\n */\nexport function isOwnerOf(owner: Entity, entity: Entity) {\n const possibleOwners = new Set(\n [\n ...getEntityRelations(owner, RELATION_MEMBER_OF, { kind: 'group' }),\n ...(owner ? [getCompoundEntityRef(owner)] : []),\n ].map(stringifyEntityRef),\n );\n\n const owners = getEntityRelations(entity, RELATION_OWNED_BY).map(\n stringifyEntityRef,\n );\n\n for (const ownerItem of owners) {\n if (possibleOwners.has(ownerItem)) {\n return true;\n }\n }\n\n return false;\n}\n","/*\n * Copyright 2022 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 { stringifyEntityRef } from '@backstage/catalog-model';\nimport { ResourcePermission } from '@backstage/plugin-permission-common';\nimport { usePermission } from '@backstage/plugin-permission-react';\nimport { useAsyncEntity } from './useEntity';\n\n/**\n * A thin wrapper around the\n * {@link @backstage/plugin-permission-react#usePermission} hook which uses the\n * current entity in context to make an authorization request for the given\n * {@link @backstage/plugin-catalog-common#CatalogEntityPermission}.\n *\n * Note: this hook blocks the permission request until the entity has loaded in\n * context. If you have the entityRef and need concurrent requests, use the\n * `usePermission` hook directly.\n * @alpha\n */\nexport function useEntityPermission(\n // TODO(joeporpeglia) Replace with `CatalogEntityPermission` when the issue described in\n // https://github.com/backstage/backstage/pull/10128 is fixed.\n permission: ResourcePermission<'catalog-entity'>,\n): {\n loading: boolean;\n allowed: boolean;\n error?: Error;\n} {\n const {\n entity,\n loading: loadingEntity,\n error: entityError,\n } = useAsyncEntity();\n const {\n allowed,\n loading: loadingPermission,\n error: permissionError,\n } = usePermission({\n permission,\n resourceRef: entity ? stringifyEntityRef(entity) : undefined,\n });\n\n if (loadingEntity || loadingPermission) {\n return { loading: true, allowed: false };\n }\n if (entityError) {\n return { loading: false, allowed: false, error: entityError };\n }\n return { loading: false, allowed, error: permissionError };\n}\n"],"names":[],"mappings":";;;;;;;AAkCgB,SAAA,SAAA,CAAU,OAAe,MAAgB,EAAA;AACvD,EAAA,MAAM,iBAAiB,IAAI,GAAA;AAAA,IACzB;AAAA,MACE,GAAG,kBAAmB,CAAA,KAAA,EAAO,oBAAoB,EAAE,IAAA,EAAM,SAAS,CAAA;AAAA,MAClE,GAAI,KAAQ,GAAA,CAAC,qBAAqB,KAAK,CAAC,IAAI,EAAC;AAAA,KAC/C,CAAE,IAAI,kBAAkB,CAAA;AAAA,GAC1B,CAAA;AAEA,EAAA,MAAM,MAAS,GAAA,kBAAA,CAAmB,MAAQ,EAAA,iBAAiB,CAAE,CAAA,GAAA;AAAA,IAC3D,kBAAA;AAAA,GACF,CAAA;AAEA,EAAA,KAAA,MAAW,aAAa,MAAQ,EAAA;AAC9B,IAAI,IAAA,cAAA,CAAe,GAAI,CAAA,SAAS,CAAG,EAAA;AACjC,MAAO,OAAA,IAAA,CAAA;AAAA,KACT;AAAA,GACF;AAEA,EAAO,OAAA,KAAA,CAAA;AACT;;ACrBO,SAAS,oBAGd,UAKA,EAAA;AACA,EAAM,MAAA;AAAA,IACJ,MAAA;AAAA,IACA,OAAS,EAAA,aAAA;AAAA,IACT,KAAO,EAAA,WAAA;AAAA,MACL,cAAe,EAAA,CAAA;AACnB,EAAM,MAAA;AAAA,IACJ,OAAA;AAAA,IACA,OAAS,EAAA,iBAAA;AAAA,IACT,KAAO,EAAA,eAAA;AAAA,MACL,aAAc,CAAA;AAAA,IAChB,UAAA;AAAA,IACA,WAAa,EAAA,MAAA,GAAS,kBAAmB,CAAA,MAAM,CAAI,GAAA,KAAA,CAAA;AAAA,GACpD,CAAA,CAAA;AAED,EAAA,IAAI,iBAAiB,iBAAmB,EAAA;AACtC,IAAA,OAAO,EAAE,OAAA,EAAS,IAAM,EAAA,OAAA,EAAS,KAAM,EAAA,CAAA;AAAA,GACzC;AACA,EAAA,IAAI,WAAa,EAAA;AACf,IAAA,OAAO,EAAE,OAAS,EAAA,KAAA,EAAO,OAAS,EAAA,KAAA,EAAO,OAAO,WAAY,EAAA,CAAA;AAAA,GAC9D;AACA,EAAA,OAAO,EAAE,OAAA,EAAS,KAAO,EAAA,OAAA,EAAS,OAAO,eAAgB,EAAA,CAAA;AAC3D;;;;"}
@@ -0,0 +1,77 @@
1
+ import { parseEntityRef, stringifyEntityRef } from '@backstage/catalog-model';
2
+ import { AnalyticsContext } from '@backstage/core-plugin-api';
3
+ import { createVersionedContext, createVersionedValueMap, useVersionedContext } from '@backstage/version-bridge';
4
+ import React from 'react';
5
+
6
+ function getEntityRelations(entity, relationType, filter) {
7
+ var _a;
8
+ let entityNames = ((_a = entity == null ? void 0 : entity.relations) == null ? void 0 : _a.filter((r) => r.type === relationType).map((r) => parseEntityRef(r.targetRef))) || [];
9
+ if (filter == null ? void 0 : filter.kind) {
10
+ entityNames = entityNames.filter(
11
+ (e) => e.kind.toLocaleLowerCase("en-US") === filter.kind.toLocaleLowerCase("en-US")
12
+ );
13
+ }
14
+ return entityNames;
15
+ }
16
+
17
+ const NewEntityContext = createVersionedContext(
18
+ "entity-context"
19
+ );
20
+ const AsyncEntityProvider = (props) => {
21
+ const { children, entity, loading, error, refresh } = props;
22
+ const value = { entity, loading, error, refresh };
23
+ return /* @__PURE__ */ React.createElement(NewEntityContext.Provider, { value: createVersionedValueMap({ 1: value }) }, /* @__PURE__ */ React.createElement(
24
+ AnalyticsContext,
25
+ {
26
+ attributes: {
27
+ ...entity ? { entityRef: stringifyEntityRef(entity) } : void 0
28
+ }
29
+ },
30
+ children
31
+ ));
32
+ };
33
+ const EntityProvider = (props) => /* @__PURE__ */ React.createElement(
34
+ AsyncEntityProvider,
35
+ {
36
+ entity: props.entity,
37
+ loading: !Boolean(props.entity),
38
+ error: void 0,
39
+ refresh: void 0,
40
+ children: props.children
41
+ }
42
+ );
43
+ function useEntity() {
44
+ const versionedHolder = useVersionedContext(
45
+ "entity-context"
46
+ );
47
+ if (!versionedHolder) {
48
+ throw new Error("Entity context is not available");
49
+ }
50
+ const value = versionedHolder.atVersion(1);
51
+ if (!value) {
52
+ throw new Error("EntityContext v1 not available");
53
+ }
54
+ if (!value.entity) {
55
+ throw new Error(
56
+ "useEntity hook is being called outside of an EntityLayout where the entity has not been loaded. If this is intentional, please use useAsyncEntity instead."
57
+ );
58
+ }
59
+ return { entity: value.entity };
60
+ }
61
+ function useAsyncEntity() {
62
+ const versionedHolder = useVersionedContext(
63
+ "entity-context"
64
+ );
65
+ if (!versionedHolder) {
66
+ throw new Error("Entity context is not available");
67
+ }
68
+ const value = versionedHolder.atVersion(1);
69
+ if (!value) {
70
+ throw new Error("EntityContext v1 not available");
71
+ }
72
+ const { entity, loading, error, refresh } = value;
73
+ return { entity, loading, error, refresh };
74
+ }
75
+
76
+ export { AsyncEntityProvider as A, EntityProvider as E, useAsyncEntity as a, getEntityRelations as g, useEntity as u };
77
+ //# sourceMappingURL=useEntity-de64059a.esm.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"useEntity-de64059a.esm.js","sources":["../../src/utils/getEntityRelations.ts","../../src/hooks/useEntity.tsx"],"sourcesContent":["/*\n * Copyright 2020 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 Entity,\n CompoundEntityRef,\n parseEntityRef,\n} from '@backstage/catalog-model';\n\n// TODO(freben): This should be returning entity refs instead\n/**\n * Get the related entity references.\n *\n * @public\n */\nexport function getEntityRelations(\n entity: Entity | undefined,\n relationType: string,\n filter?: { kind: string },\n): CompoundEntityRef[] {\n let entityNames =\n entity?.relations\n ?.filter(r => r.type === relationType)\n .map(r => parseEntityRef(r.targetRef)) || [];\n\n if (filter?.kind) {\n entityNames = entityNames.filter(\n e =>\n e.kind.toLocaleLowerCase('en-US') ===\n filter.kind.toLocaleLowerCase('en-US'),\n );\n }\n\n return entityNames;\n}\n","/*\n * Copyright 2020 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 */\nimport { Entity, stringifyEntityRef } from '@backstage/catalog-model';\nimport { AnalyticsContext } from '@backstage/core-plugin-api';\nimport {\n createVersionedContext,\n createVersionedValueMap,\n useVersionedContext,\n} from '@backstage/version-bridge';\nimport React, { ReactNode } from 'react';\n\n/** @public */\nexport type EntityLoadingStatus<TEntity extends Entity = Entity> = {\n entity?: TEntity;\n loading: boolean;\n error?: Error;\n refresh?: VoidFunction;\n};\n\n// This context has support for multiple concurrent versions of this package.\n// It is currently used in parallel with the old context in order to provide\n// a smooth transition, but will eventually be the only context we use.\nconst NewEntityContext = createVersionedContext<{ 1: EntityLoadingStatus }>(\n 'entity-context',\n);\n\n/**\n * Properties for the AsyncEntityProvider component.\n *\n * @public\n */\nexport interface AsyncEntityProviderProps {\n children: ReactNode;\n entity?: Entity;\n loading: boolean;\n error?: Error;\n refresh?: VoidFunction;\n}\n\n/**\n * Provides a loaded entity to be picked up by the `useEntity` hook.\n *\n * @public\n */\nexport const AsyncEntityProvider = (props: AsyncEntityProviderProps) => {\n const { children, entity, loading, error, refresh } = props;\n const value = { entity, loading, error, refresh };\n // We provide both the old and the new context, since\n // consumers might be doing things like `useContext(EntityContext)`\n return (\n <NewEntityContext.Provider value={createVersionedValueMap({ 1: value })}>\n <AnalyticsContext\n attributes={{\n ...(entity ? { entityRef: stringifyEntityRef(entity) } : undefined),\n }}\n >\n {children}\n </AnalyticsContext>\n </NewEntityContext.Provider>\n );\n};\n\n/**\n * Properties for the EntityProvider component.\n *\n * @public\n */\nexport interface EntityProviderProps {\n children: ReactNode;\n entity?: Entity;\n}\n\n/**\n * Provides an entity to be picked up by the `useEntity` hook.\n *\n * @public\n */\nexport const EntityProvider = (props: EntityProviderProps) => (\n <AsyncEntityProvider\n entity={props.entity}\n loading={!Boolean(props.entity)}\n error={undefined}\n refresh={undefined}\n children={props.children}\n />\n);\n\n/**\n * Grab the current entity from the context, throws if the entity has not yet been loaded\n * or is not available.\n *\n * @public\n */\nexport function useEntity<TEntity extends Entity = Entity>(): {\n entity: TEntity;\n} {\n const versionedHolder = useVersionedContext<{ 1: EntityLoadingStatus }>(\n 'entity-context',\n );\n\n if (!versionedHolder) {\n throw new Error('Entity context is not available');\n }\n\n const value = versionedHolder.atVersion(1);\n if (!value) {\n throw new Error('EntityContext v1 not available');\n }\n\n if (!value.entity) {\n throw new Error(\n 'useEntity hook is being called outside of an EntityLayout where the entity has not been loaded. If this is intentional, please use useAsyncEntity instead.',\n );\n }\n\n return { entity: value.entity as TEntity };\n}\n\n/**\n * Grab the current entity from the context, provides loading state and errors, and the ability to refresh.\n *\n * @public\n */\nexport function useAsyncEntity<\n TEntity extends Entity = Entity,\n>(): EntityLoadingStatus<TEntity> {\n const versionedHolder = useVersionedContext<{ 1: EntityLoadingStatus }>(\n 'entity-context',\n );\n\n if (!versionedHolder) {\n throw new Error('Entity context is not available');\n }\n const value = versionedHolder.atVersion(1);\n if (!value) {\n throw new Error('EntityContext v1 not available');\n }\n\n const { entity, loading, error, refresh } = value;\n return { entity: entity as TEntity, loading, error, refresh };\n}\n"],"names":[],"mappings":"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"}
package/dist/index.d.ts CHANGED
@@ -87,14 +87,14 @@ interface EntityKindPickerProps {
87
87
  declare const EntityKindPicker: (props: EntityKindPickerProps) => JSX.Element | null;
88
88
 
89
89
  /** @public */
90
- declare type CatalogReactEntityLifecyclePickerClassKey = 'input';
90
+ type CatalogReactEntityLifecyclePickerClassKey = 'input';
91
91
  /** @public */
92
92
  declare const EntityLifecyclePicker: (props: {
93
93
  initialFilter?: string[];
94
94
  }) => JSX.Element | null;
95
95
 
96
96
  /** @public */
97
- declare type CatalogReactEntityOwnerPickerClassKey = 'input';
97
+ type CatalogReactEntityOwnerPickerClassKey = 'input';
98
98
  /** @public */
99
99
  declare const EntityOwnerPicker: () => JSX.Element | null;
100
100
 
@@ -103,7 +103,7 @@ declare const EntityOwnerPicker: () => JSX.Element | null;
103
103
  *
104
104
  * @public
105
105
  */
106
- declare type EntityRefLinkProps = {
106
+ type EntityRefLinkProps = {
107
107
  entityRef: Entity | CompoundEntityRef | string;
108
108
  defaultKind?: string;
109
109
  title?: string;
@@ -121,7 +121,7 @@ declare const EntityRefLink: (props: EntityRefLinkProps) => JSX.Element;
121
121
  *
122
122
  * @public
123
123
  */
124
- declare type EntityRefLinksProps<TRef extends string | CompoundEntityRef | Entity> = ({
124
+ type EntityRefLinksProps<TRef extends string | CompoundEntityRef | Entity> = ({
125
125
  defaultKind?: string;
126
126
  entityRefs: TRef[];
127
127
  fetchEntities?: false;
@@ -154,7 +154,7 @@ declare function humanizeEntityRef(entityRef: Entity | CompoundEntityRef, opts?:
154
154
  *
155
155
  * @public
156
156
  */
157
- declare type EntityPeekAheadPopoverProps = PropsWithChildren<{
157
+ type EntityPeekAheadPopoverProps = PropsWithChildren<{
158
158
  entityRef: string;
159
159
  delayTime?: number;
160
160
  }>;
@@ -166,7 +166,7 @@ declare type EntityPeekAheadPopoverProps = PropsWithChildren<{
166
166
  declare const EntityPeekAheadPopover: (props: EntityPeekAheadPopoverProps) => JSX.Element;
167
167
 
168
168
  /** @public */
169
- declare type CatalogReactEntitySearchBarClassKey = 'searchToolbar' | 'input';
169
+ type CatalogReactEntitySearchBarClassKey = 'searchToolbar' | 'input';
170
170
  /**
171
171
  * Renders search bar for filtering the entity list.
172
172
  * @public
@@ -238,9 +238,9 @@ declare const columnFactories: Readonly<{
238
238
  }>;
239
239
 
240
240
  /** @public */
241
- declare type CatalogReactEntityTagPickerClassKey = 'input';
241
+ type CatalogReactEntityTagPickerClassKey = 'input';
242
242
  /** @public */
243
- declare type EntityTagPickerProps = {
243
+ type EntityTagPickerProps = {
244
244
  showCounts?: boolean;
245
245
  };
246
246
  /** @public */
@@ -259,7 +259,7 @@ interface EntityTypePickerProps {
259
259
  declare const EntityTypePicker: (props: EntityTypePickerProps) => JSX.Element | null;
260
260
 
261
261
  /** @public */
262
- declare type FavoriteEntityProps = ComponentProps<typeof IconButton> & {
262
+ type FavoriteEntityProps = ComponentProps<typeof IconButton> & {
263
263
  entity: Entity;
264
264
  };
265
265
  /**
@@ -281,7 +281,7 @@ declare function InspectEntityDialog(props: {
281
281
  }): JSX.Element | null;
282
282
 
283
283
  /** @public */
284
- declare type UnregisterEntityDialogProps = {
284
+ type UnregisterEntityDialogProps = {
285
285
  open: boolean;
286
286
  onConfirm: () => any;
287
287
  onClose: () => any;
@@ -291,7 +291,7 @@ declare type UnregisterEntityDialogProps = {
291
291
  declare const UnregisterEntityDialog: (props: UnregisterEntityDialogProps) => JSX.Element;
292
292
 
293
293
  /** @public */
294
- declare type EntityFilter = {
294
+ type EntityFilter = {
295
295
  /**
296
296
  * Get filters to add to the catalog-backend request. These are a dot-delimited field with
297
297
  * value(s) to accept, extracted on the backend by parseEntityFilterParams. For example:
@@ -313,12 +313,12 @@ declare type EntityFilter = {
313
313
  toQueryValue?: () => string | string[];
314
314
  };
315
315
  /** @public */
316
- declare type UserListFilterKind = 'owned' | 'starred' | 'all';
316
+ type UserListFilterKind = 'owned' | 'starred' | 'all';
317
317
 
318
318
  /** @public */
319
- declare type CatalogReactUserListPickerClassKey = 'root' | 'title' | 'listIcon' | 'menuItem' | 'groupWrapper';
319
+ type CatalogReactUserListPickerClassKey = 'root' | 'title' | 'listIcon' | 'menuItem' | 'groupWrapper';
320
320
  /** @public */
321
- declare type UserListPickerProps = {
321
+ type UserListPickerProps = {
322
322
  initialFilter?: UserListFilterKind;
323
323
  availableFilters?: UserListFilterKind[];
324
324
  };
@@ -326,12 +326,12 @@ declare type UserListPickerProps = {
326
326
  declare const UserListPicker: (props: UserListPickerProps) => JSX.Element;
327
327
 
328
328
  /** @public */
329
- declare type CatalogReactEntityProcessingStatusPickerClassKey = 'input';
329
+ type CatalogReactEntityProcessingStatusPickerClassKey = 'input';
330
330
  /** @public */
331
331
  declare const EntityProcessingStatusPicker: () => JSX.Element;
332
332
 
333
333
  /** @public */
334
- declare type EntityLoadingStatus<TEntity extends Entity = Entity> = {
334
+ type EntityLoadingStatus<TEntity extends Entity = Entity> = {
335
335
  entity?: TEntity;
336
336
  loading: boolean;
337
337
  error?: Error;
@@ -479,7 +479,7 @@ declare class EntityErrorFilter implements EntityFilter {
479
479
  }
480
480
 
481
481
  /** @public */
482
- declare type DefaultEntityFilters = {
482
+ type DefaultEntityFilters = {
483
483
  kind?: EntityKindFilter;
484
484
  type?: EntityTypeFilter;
485
485
  user?: UserListFilter;
@@ -491,7 +491,7 @@ declare type DefaultEntityFilters = {
491
491
  error?: EntityErrorFilter;
492
492
  };
493
493
  /** @public */
494
- declare type EntityListContextProps<EntityFilters extends DefaultEntityFilters = DefaultEntityFilters> = {
494
+ type EntityListContextProps<EntityFilters extends DefaultEntityFilters = DefaultEntityFilters> = {
495
495
  /**
496
496
  * The currently registered filters, adhering to the shape of DefaultEntityFilters or an extension
497
497
  * of that default (to add custom filter types).
@@ -615,7 +615,7 @@ declare function MockEntityListContextProvider<T extends DefaultEntityFilters =
615
615
  }>): JSX.Element;
616
616
 
617
617
  /** @public */
618
- declare type CatalogReactComponentsNameToClassKey = {
618
+ type CatalogReactComponentsNameToClassKey = {
619
619
  CatalogReactUserListPicker: CatalogReactUserListPickerClassKey;
620
620
  CatalogReactEntityLifecyclePicker: CatalogReactEntityLifecyclePickerClassKey;
621
621
  CatalogReactEntitySearchBar: CatalogReactEntitySearchBarClassKey;
@@ -624,7 +624,7 @@ declare type CatalogReactComponentsNameToClassKey = {
624
624
  CatalogReactEntityProcessingStatusPicker: CatalogReactEntityProcessingStatusPickerClassKey;
625
625
  };
626
626
  /** @public */
627
- declare type BackstageOverrides = Overrides & {
627
+ type BackstageOverrides = Overrides & {
628
628
  [Name in keyof CatalogReactComponentsNameToClassKey]?: Partial<StyleRules<CatalogReactComponentsNameToClassKey[Name]>>;
629
629
  };
630
630
 
@@ -638,7 +638,7 @@ declare function getEntityRelations(entity: Entity | undefined, relationType: st
638
638
  }): CompoundEntityRef[];
639
639
 
640
640
  /** @public */
641
- declare type EntitySourceLocation = {
641
+ type EntitySourceLocation = {
642
642
  locationTargetUrl: string;
643
643
  integrationType?: string;
644
644
  };
package/dist/index.esm.js CHANGED
@@ -1,13 +1,15 @@
1
1
  export { CATALOG_FILTER_EXISTS } from '@backstage/catalog-client';
2
- import { createApiRef, createRouteRef, useRouteRef, useApi, AnalyticsContext, identityApiRef, alertApiRef, useApiHolder, useApp, configApiRef } from '@backstage/core-plugin-api';
2
+ import { createApiRef, createRouteRef, useRouteRef, useApi, identityApiRef, alertApiRef, useApiHolder, useApp, configApiRef } from '@backstage/core-plugin-api';
3
3
  import ObservableImpl from 'zen-observable';
4
4
  import React, { useState, forwardRef, createContext, useMemo, useCallback, useContext, useEffect, useRef, memo, useLayoutEffect, Fragment } from 'react';
5
5
  import { Grid, useMediaQuery, useTheme, Button, Drawer, Box, Typography, Tooltip, makeStyles, FormControlLabel, Checkbox, TextField, IconButton, Card, CardContent, Chip, CardActions, Toolbar, FormControl, Input, InputAdornment, withStyles, DialogContentText, ListItemText as ListItemText$1, ListSubheader as ListSubheader$1, ListItem, ListItemIcon, List, Dialog, DialogTitle, DialogContent, Tabs, Tab, DialogActions, Divider, MenuItem, ListItemSecondaryAction } from '@material-ui/core';
6
6
  import FilterListIcon from '@material-ui/icons/FilterList';
7
7
  import { Link, Progress, ErrorPanel, Select, ResponseErrorPanel, OverflowTooltip, Table, DependencyGraph, DependencyGraphTypes, CodeSnippet } from '@backstage/core-components';
8
8
  import { DEFAULT_NAMESPACE, parseEntityRef, ANNOTATION_SOURCE_LOCATION, parseLocationRef, RELATION_OWNED_BY, stringifyEntityRef, getCompoundEntityRef, isUserEntity, isGroupEntity, RELATION_PART_OF, ANNOTATION_LOCATION, ANNOTATION_ORIGIN_LOCATION } from '@backstage/catalog-model';
9
- import { getOrCreateGlobalSingleton, createVersionedContext, createVersionedValueMap, useVersionedContext } from '@backstage/version-bridge';
9
+ import { getOrCreateGlobalSingleton } from '@backstage/version-bridge';
10
10
  import useAsync from 'react-use/lib/useAsync';
11
+ import { g as getEntityRelations } from './esm/useEntity-de64059a.esm.js';
12
+ export { A as AsyncEntityProvider, E as EntityProvider, g as getEntityRelations, a as useAsyncEntity, u as useEntity } from './esm/useEntity-de64059a.esm.js';
11
13
  import _, { compact, isEqual, groupBy, chunk, debounce } from 'lodash';
12
14
  import qs from 'qs';
13
15
  import { useLocation, useNavigate } from 'react-router-dom';
@@ -204,10 +206,13 @@ function FetchedEntityRefLinks(props) {
204
206
  error
205
207
  } = useAsync(async () => {
206
208
  const refs = entityRefs.reduce((acc, current) => {
207
- return "metadata" in current ? acc : [...acc, parseEntityRef(current)];
209
+ if (typeof current === "object" && "metadata" in current) {
210
+ return acc;
211
+ }
212
+ return [...acc, parseEntityRef(current)];
208
213
  }, new Array());
209
214
  const pureEntities = entityRefs.filter(
210
- (ref) => "metadata" in ref
215
+ (ref) => typeof ref === "object" && "metadata" in ref
211
216
  );
212
217
  return refs.length > 0 ? [
213
218
  ...(await catalogApi.getEntities({
@@ -279,17 +284,6 @@ function reduceEntityFilters(filters) {
279
284
  );
280
285
  }
281
286
 
282
- function getEntityRelations(entity, relationType, filter) {
283
- var _a;
284
- let entityNames = ((_a = entity == null ? void 0 : entity.relations) == null ? void 0 : _a.filter((r) => r.type === relationType).map((r) => parseEntityRef(r.targetRef))) || [];
285
- if (filter == null ? void 0 : filter.kind) {
286
- entityNames = entityNames.filter(
287
- (e) => e.kind.toLocaleLowerCase("en-US") === filter.kind.toLocaleLowerCase("en-US")
288
- );
289
- }
290
- return entityNames;
291
- }
292
-
293
287
  function getEntitySourceLocation(entity, scmIntegrationsApi) {
294
288
  var _a;
295
289
  const sourceLocation = (_a = entity.metadata.annotations) == null ? void 0 : _a[ANNOTATION_SOURCE_LOCATION];
@@ -440,65 +434,6 @@ class EntityErrorFilter {
440
434
  }
441
435
  }
442
436
 
443
- const NewEntityContext = createVersionedContext(
444
- "entity-context"
445
- );
446
- const AsyncEntityProvider = (props) => {
447
- const { children, entity, loading, error, refresh } = props;
448
- const value = { entity, loading, error, refresh };
449
- return /* @__PURE__ */ React.createElement(NewEntityContext.Provider, { value: createVersionedValueMap({ 1: value }) }, /* @__PURE__ */ React.createElement(
450
- AnalyticsContext,
451
- {
452
- attributes: {
453
- ...entity ? { entityRef: stringifyEntityRef(entity) } : void 0
454
- }
455
- },
456
- children
457
- ));
458
- };
459
- const EntityProvider = (props) => /* @__PURE__ */ React.createElement(
460
- AsyncEntityProvider,
461
- {
462
- entity: props.entity,
463
- loading: !Boolean(props.entity),
464
- error: void 0,
465
- refresh: void 0,
466
- children: props.children
467
- }
468
- );
469
- function useEntity() {
470
- const versionedHolder = useVersionedContext(
471
- "entity-context"
472
- );
473
- if (!versionedHolder) {
474
- throw new Error("Entity context is not available");
475
- }
476
- const value = versionedHolder.atVersion(1);
477
- if (!value) {
478
- throw new Error("EntityContext v1 not available");
479
- }
480
- if (!value.entity) {
481
- throw new Error(
482
- "useEntity hook is being called outside of an EntityLayout where the entity has not been loaded. If this is intentional, please use useAsyncEntity instead."
483
- );
484
- }
485
- return { entity: value.entity };
486
- }
487
- function useAsyncEntity() {
488
- const versionedHolder = useVersionedContext(
489
- "entity-context"
490
- );
491
- if (!versionedHolder) {
492
- throw new Error("Entity context is not available");
493
- }
494
- const value = versionedHolder.atVersion(1);
495
- if (!value) {
496
- throw new Error("EntityContext v1 not available");
497
- }
498
- const { entity, loading, error, refresh } = value;
499
- return { entity, loading, error, refresh };
500
- }
501
-
502
437
  const EntityListContext = createContext(void 0);
503
438
  const EntityListProvider = (props) => {
504
439
  const isMounted = useMountedState();
@@ -984,6 +919,7 @@ const EntityLifecyclePicker = (props) => {
984
919
  checked: selected
985
920
  }
986
921
  ),
922
+ onClick: (event) => event.preventDefault(),
987
923
  label: option
988
924
  }
989
925
  ),
@@ -1070,6 +1006,7 @@ const EntityOwnerPicker = () => {
1070
1006
  checked: selected
1071
1007
  }
1072
1008
  ),
1009
+ onClick: (event) => event.preventDefault(),
1073
1010
  label: option
1074
1011
  }
1075
1012
  ),
@@ -1450,7 +1387,8 @@ const EntityAutocompletePickerOption = memo((props) => {
1450
1387
  FormControlLabel,
1451
1388
  {
1452
1389
  control: /* @__PURE__ */ React.createElement(OptionCheckbox, { selected }),
1453
- label
1390
+ label,
1391
+ onClick: (event) => event.preventDefault()
1454
1392
  }
1455
1393
  );
1456
1394
  });
@@ -1514,7 +1452,8 @@ function EntityAutocompletePicker(props) {
1514
1452
  [name]: shouldAddFilter ? new Filter(selectedOptions) : void 0
1515
1453
  });
1516
1454
  }, [name, shouldAddFilter, selectedOptions, Filter, updateFilters]);
1517
- if (filters[name] && !("values" in filters[name]) || !availableOptions.length) {
1455
+ const filter = filters[name];
1456
+ if (filter && typeof filter === "object" && !("values" in filter) || !availableOptions.length) {
1518
1457
  return null;
1519
1458
  }
1520
1459
  return /* @__PURE__ */ React.createElement(Box, { pb: 1, pt: 1 }, /* @__PURE__ */ React.createElement(Typography, { variant: "button", component: "label" }, label, /* @__PURE__ */ React.createElement(
@@ -2522,6 +2461,7 @@ const EntityProcessingStatusPicker = () => {
2522
2461
  checked: selected
2523
2462
  }
2524
2463
  ),
2464
+ onClick: (event) => event.preventDefault(),
2525
2465
  label: option
2526
2466
  }
2527
2467
  ),
@@ -2578,5 +2518,5 @@ function MockEntityListContextProvider(props) {
2578
2518
  return /* @__PURE__ */ React.createElement(EntityListContext.Provider, { value: resolvedValue }, children);
2579
2519
  }
2580
2520
 
2581
- export { AsyncEntityProvider, CatalogFilterLayout, EntityErrorFilter, EntityKindFilter, EntityKindPicker, EntityLifecycleFilter, EntityLifecyclePicker, EntityListContext, EntityListProvider, EntityOrphanFilter, EntityOwnerFilter, EntityOwnerPicker, EntityPeekAheadPopover, EntityProcessingStatusPicker, EntityProvider, EntityRefLink, EntityRefLinks, EntitySearchBar, EntityTable, EntityTagFilter, EntityTagPicker, EntityTextFilter, EntityTypeFilter, EntityTypePicker, FavoriteEntity, InspectEntityDialog, MockEntityListContextProvider, MockStarredEntitiesApi, UnregisterEntityDialog, UserListFilter, UserListPicker, catalogApiRef, columnFactories, entityRouteParams, entityRouteRef, getEntityRelations, getEntitySourceLocation, humanizeEntityRef, starredEntitiesApiRef, useAsyncEntity, useEntity, useEntityList, useEntityOwnership, useEntityTypeFilter, useRelatedEntities, useStarredEntities, useStarredEntity };
2521
+ export { CatalogFilterLayout, EntityErrorFilter, EntityKindFilter, EntityKindPicker, EntityLifecycleFilter, EntityLifecyclePicker, EntityListContext, EntityListProvider, EntityOrphanFilter, EntityOwnerFilter, EntityOwnerPicker, EntityPeekAheadPopover, EntityProcessingStatusPicker, EntityRefLink, EntityRefLinks, EntitySearchBar, EntityTable, EntityTagFilter, EntityTagPicker, EntityTextFilter, EntityTypeFilter, EntityTypePicker, FavoriteEntity, InspectEntityDialog, MockEntityListContextProvider, MockStarredEntitiesApi, UnregisterEntityDialog, UserListFilter, UserListPicker, catalogApiRef, columnFactories, entityRouteParams, entityRouteRef, getEntitySourceLocation, humanizeEntityRef, starredEntitiesApiRef, useEntityList, useEntityOwnership, useEntityTypeFilter, useRelatedEntities, useStarredEntities, useStarredEntity };
2582
2522
  //# sourceMappingURL=index.esm.js.map