@backstage/plugin-techdocs 1.1.0 → 1.1.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,51 @@
1
1
  # @backstage/plugin-techdocs
2
2
 
3
+ ## 1.1.1-next.2
4
+
5
+ ### Patch Changes
6
+
7
+ - 52419be116: Create a menu in the sub header of documentation pages, it is responsible for rendering TechDocs addons that allow users to customize their reading experience.
8
+ - 1af133f779: Updated dependency `event-source-polyfill` to `1.0.26`.
9
+ - 2dcb2c9678: Loading SVGs correctly with `bota` with extended characters
10
+ - 3a74e203a8: Updated search result components to support rendering content with highlighted matched terms
11
+ - Updated dependencies
12
+ - @backstage/core-components@0.9.4-next.1
13
+ - @backstage/plugin-techdocs-react@0.1.1-next.2
14
+ - @backstage/config@1.0.1-next.0
15
+ - @backstage/plugin-search-react@0.2.0-next.2
16
+ - @backstage/plugin-search-common@0.3.4-next.0
17
+ - @backstage/plugin-catalog-react@1.1.0-next.2
18
+ - @backstage/catalog-model@1.0.2-next.0
19
+ - @backstage/core-plugin-api@1.0.2-next.1
20
+ - @backstage/integration@1.2.0-next.1
21
+ - @backstage/integration-react@1.1.0-next.2
22
+
23
+ ## 1.1.1-next.1
24
+
25
+ ### Patch Changes
26
+
27
+ - 52fddad92d: The `TechDocsStorageApi` and its associated ref are now exported by `@backstage/plugin-techdocs-react`. The API interface, ref, and types are now deprecated in `@backstage/plugin-techdocs` and will be removed in a future release.
28
+ - Updated dependencies
29
+ - @backstage/core-components@0.9.4-next.0
30
+ - @backstage/core-plugin-api@1.0.2-next.0
31
+ - @backstage/plugin-catalog-react@1.1.0-next.1
32
+ - @backstage/plugin-search-react@0.2.0-next.1
33
+ - @backstage/plugin-techdocs-react@0.1.1-next.1
34
+ - @backstage/integration-react@1.1.0-next.1
35
+
36
+ ## 1.1.1-next.0
37
+
38
+ ### Patch Changes
39
+
40
+ - a307a14be0: Removed dependency on `@backstage/core-app-api`.
41
+ - bed0d64ce9: Fixed bugs that prevented a 404 error from being shown when it should have been.
42
+ - Updated dependencies
43
+ - @backstage/integration@1.2.0-next.0
44
+ - @backstage/plugin-catalog-react@1.1.0-next.0
45
+ - @backstage/integration-react@1.1.0-next.0
46
+ - @backstage/plugin-search-react@0.1.1-next.0
47
+ - @backstage/plugin-techdocs-react@0.1.1-next.0
48
+
3
49
  ## 1.1.0
4
50
 
5
51
  ### Minor Changes
@@ -2,7 +2,7 @@ import React, { useState } from 'react';
2
2
  import useAsync from 'react-use/lib/useAsync';
3
3
  import { makeStyles } from '@material-ui/core';
4
4
  import { catalogApiRef, CATALOG_FILTER_EXISTS, useEntityOwnership } from '@backstage/plugin-catalog-react';
5
- import { T as TechDocsPageWrapper, D as DocsTable, a as DocsCardGrid } from './index-cb910cad.esm.js';
5
+ import { T as TechDocsPageWrapper, D as DocsTable, a as DocsCardGrid } from './index-c537b1f3.esm.js';
6
6
  import { Content, Progress, WarningPanel, CodeSnippet, HeaderTabs, ContentHeader, SupportButton } from '@backstage/core-components';
7
7
  import { useApi } from '@backstage/core-plugin-api';
8
8
  import '@backstage/errors';
@@ -11,7 +11,6 @@ import 'react-router-dom';
11
11
  import '@backstage/plugin-techdocs-react';
12
12
  import 'jss';
13
13
  import '@material-ui/styles';
14
- import 'react-text-truncate';
15
14
  import '@backstage/plugin-search-react';
16
15
  import '@material-ui/icons/Search';
17
16
  import '@material-ui/lab/Autocomplete';
@@ -31,12 +30,12 @@ import 'dompurify';
31
30
  import 'react-helmet';
32
31
  import '@material-ui/icons/Code';
33
32
  import '@backstage/catalog-model';
33
+ import '@material-ui/icons/Settings';
34
34
  import 'react-use/lib/useCopyToClipboard';
35
35
  import 'lodash';
36
36
  import '@material-ui/icons/Share';
37
37
  import '@material-ui/icons/Star';
38
38
  import '@material-ui/icons/StarBorder';
39
- import '@backstage/core-app-api';
40
39
 
41
40
  const panels = {
42
41
  DocsTable,
@@ -133,4 +132,4 @@ const TechDocsCustomHome = (props) => {
133
132
  };
134
133
 
135
134
  export { TechDocsCustomHome };
136
- //# sourceMappingURL=TechDocsCustomHome-4046b545.esm.js.map
135
+ //# sourceMappingURL=TechDocsCustomHome-b77adc6d.esm.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"TechDocsCustomHome-4046b545.esm.js","sources":["../../src/home/components/TechDocsCustomHome.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 React, { useState } from 'react';\nimport useAsync from 'react-use/lib/useAsync';\nimport { makeStyles } from '@material-ui/core';\nimport { CSSProperties } from '@material-ui/styles';\nimport {\n CATALOG_FILTER_EXISTS,\n catalogApiRef,\n CatalogApi,\n useEntityOwnership,\n} from '@backstage/plugin-catalog-react';\nimport { Entity } from '@backstage/catalog-model';\nimport { DocsTable } from './Tables';\nimport { DocsCardGrid } from './Grids';\nimport { TechDocsPageWrapper } from './TechDocsPageWrapper';\n\nimport {\n CodeSnippet,\n Content,\n HeaderTabs,\n Progress,\n WarningPanel,\n SupportButton,\n ContentHeader,\n} from '@backstage/core-components';\nimport { useApi } from '@backstage/core-plugin-api';\n\nconst panels = {\n DocsTable: DocsTable,\n DocsCardGrid: DocsCardGrid,\n};\n\n/**\n * Available panel types\n *\n * @public\n */\nexport type PanelType = 'DocsCardGrid' | 'DocsTable';\n\n/**\n * Type representing a TechDocsCustomHome panel.\n *\n * @public\n */\nexport interface PanelConfig {\n title: string;\n description: string;\n panelType: PanelType;\n panelCSS?: CSSProperties;\n filterPredicate: ((entity: Entity) => boolean) | string;\n}\n\n/**\n * Type representing a TechDocsCustomHome tab.\n *\n * @public\n */\nexport interface TabConfig {\n label: string;\n panels: PanelConfig[];\n}\n\n/**\n * Type representing a list of TechDocsCustomHome tabs.\n *\n * @public\n */\nexport type TabsConfig = TabConfig[];\n\nconst CustomPanel = ({\n config,\n entities,\n index,\n}: {\n config: PanelConfig;\n entities: Entity[];\n index: number;\n}) => {\n const useStyles = makeStyles({\n panelContainer: {\n marginBottom: '2rem',\n ...(config.panelCSS ? config.panelCSS : {}),\n },\n });\n const classes = useStyles();\n const { loading: loadingOwnership, isOwnedEntity } = useEntityOwnership();\n\n const Panel = panels[config.panelType];\n\n const shownEntities = entities.filter(entity => {\n if (config.filterPredicate === 'ownedByUser') {\n if (loadingOwnership) {\n return false;\n }\n return isOwnedEntity(entity);\n }\n\n return (\n typeof config.filterPredicate === 'function' &&\n config.filterPredicate(entity)\n );\n });\n\n return (\n <>\n <ContentHeader title={config.title} description={config.description}>\n {index === 0 ? (\n <SupportButton>\n Discover documentation in your ecosystem.\n </SupportButton>\n ) : null}\n </ContentHeader>\n <div className={classes.panelContainer}>\n <Panel data-testid=\"techdocs-custom-panel\" entities={shownEntities} />\n </div>\n </>\n );\n};\n\n/**\n * Props for {@link TechDocsCustomHome}\n *\n * @public\n */\nexport type TechDocsCustomHomeProps = {\n tabsConfig: TabsConfig;\n};\n\nexport const TechDocsCustomHome = (props: TechDocsCustomHomeProps) => {\n const { tabsConfig } = props;\n const [selectedTab, setSelectedTab] = useState<number>(0);\n const catalogApi: CatalogApi = useApi(catalogApiRef);\n\n const {\n value: entities,\n loading,\n error,\n } = useAsync(async () => {\n const response = await catalogApi.getEntities({\n filter: {\n 'metadata.annotations.backstage.io/techdocs-ref': CATALOG_FILTER_EXISTS,\n },\n fields: [\n 'apiVersion',\n 'kind',\n 'metadata',\n 'relations',\n 'spec.owner',\n 'spec.type',\n ],\n });\n return response.items.filter((entity: Entity) => {\n return !!entity.metadata.annotations?.['backstage.io/techdocs-ref'];\n });\n });\n\n const currentTabConfig = tabsConfig[selectedTab];\n\n if (loading) {\n return (\n <TechDocsPageWrapper>\n <Content>\n <Progress />\n </Content>\n </TechDocsPageWrapper>\n );\n }\n\n if (error) {\n return (\n <TechDocsPageWrapper>\n <Content>\n <WarningPanel\n severity=\"error\"\n title=\"Could not load available documentation.\"\n >\n <CodeSnippet language=\"text\" text={error.toString()} />\n </WarningPanel>\n </Content>\n </TechDocsPageWrapper>\n );\n }\n\n return (\n <TechDocsPageWrapper>\n <HeaderTabs\n selectedIndex={selectedTab}\n onChange={index => setSelectedTab(index)}\n tabs={tabsConfig.map(({ label }, index) => ({\n id: index.toString(),\n label,\n }))}\n />\n <Content data-testid=\"techdocs-content\">\n {currentTabConfig.panels.map((config, index) => (\n <CustomPanel\n key={index}\n config={config}\n entities={!!entities ? entities : []}\n index={index}\n />\n ))}\n </Content>\n </TechDocsPageWrapper>\n );\n};\n"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"TechDocsCustomHome-b77adc6d.esm.js","sources":["../../src/home/components/TechDocsCustomHome.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 React, { useState } from 'react';\nimport useAsync from 'react-use/lib/useAsync';\nimport { makeStyles } from '@material-ui/core';\nimport { CSSProperties } from '@material-ui/styles';\nimport {\n CATALOG_FILTER_EXISTS,\n catalogApiRef,\n CatalogApi,\n useEntityOwnership,\n} from '@backstage/plugin-catalog-react';\nimport { Entity } from '@backstage/catalog-model';\nimport { DocsTable } from './Tables';\nimport { DocsCardGrid } from './Grids';\nimport { TechDocsPageWrapper } from './TechDocsPageWrapper';\n\nimport {\n CodeSnippet,\n Content,\n HeaderTabs,\n Progress,\n WarningPanel,\n SupportButton,\n ContentHeader,\n} from '@backstage/core-components';\nimport { useApi } from '@backstage/core-plugin-api';\n\nconst panels = {\n DocsTable: DocsTable,\n DocsCardGrid: DocsCardGrid,\n};\n\n/**\n * Available panel types\n *\n * @public\n */\nexport type PanelType = 'DocsCardGrid' | 'DocsTable';\n\n/**\n * Type representing a TechDocsCustomHome panel.\n *\n * @public\n */\nexport interface PanelConfig {\n title: string;\n description: string;\n panelType: PanelType;\n panelCSS?: CSSProperties;\n filterPredicate: ((entity: Entity) => boolean) | string;\n}\n\n/**\n * Type representing a TechDocsCustomHome tab.\n *\n * @public\n */\nexport interface TabConfig {\n label: string;\n panels: PanelConfig[];\n}\n\n/**\n * Type representing a list of TechDocsCustomHome tabs.\n *\n * @public\n */\nexport type TabsConfig = TabConfig[];\n\nconst CustomPanel = ({\n config,\n entities,\n index,\n}: {\n config: PanelConfig;\n entities: Entity[];\n index: number;\n}) => {\n const useStyles = makeStyles({\n panelContainer: {\n marginBottom: '2rem',\n ...(config.panelCSS ? config.panelCSS : {}),\n },\n });\n const classes = useStyles();\n const { loading: loadingOwnership, isOwnedEntity } = useEntityOwnership();\n\n const Panel = panels[config.panelType];\n\n const shownEntities = entities.filter(entity => {\n if (config.filterPredicate === 'ownedByUser') {\n if (loadingOwnership) {\n return false;\n }\n return isOwnedEntity(entity);\n }\n\n return (\n typeof config.filterPredicate === 'function' &&\n config.filterPredicate(entity)\n );\n });\n\n return (\n <>\n <ContentHeader title={config.title} description={config.description}>\n {index === 0 ? (\n <SupportButton>\n Discover documentation in your ecosystem.\n </SupportButton>\n ) : null}\n </ContentHeader>\n <div className={classes.panelContainer}>\n <Panel data-testid=\"techdocs-custom-panel\" entities={shownEntities} />\n </div>\n </>\n );\n};\n\n/**\n * Props for {@link TechDocsCustomHome}\n *\n * @public\n */\nexport type TechDocsCustomHomeProps = {\n tabsConfig: TabsConfig;\n};\n\nexport const TechDocsCustomHome = (props: TechDocsCustomHomeProps) => {\n const { tabsConfig } = props;\n const [selectedTab, setSelectedTab] = useState<number>(0);\n const catalogApi: CatalogApi = useApi(catalogApiRef);\n\n const {\n value: entities,\n loading,\n error,\n } = useAsync(async () => {\n const response = await catalogApi.getEntities({\n filter: {\n 'metadata.annotations.backstage.io/techdocs-ref': CATALOG_FILTER_EXISTS,\n },\n fields: [\n 'apiVersion',\n 'kind',\n 'metadata',\n 'relations',\n 'spec.owner',\n 'spec.type',\n ],\n });\n return response.items.filter((entity: Entity) => {\n return !!entity.metadata.annotations?.['backstage.io/techdocs-ref'];\n });\n });\n\n const currentTabConfig = tabsConfig[selectedTab];\n\n if (loading) {\n return (\n <TechDocsPageWrapper>\n <Content>\n <Progress />\n </Content>\n </TechDocsPageWrapper>\n );\n }\n\n if (error) {\n return (\n <TechDocsPageWrapper>\n <Content>\n <WarningPanel\n severity=\"error\"\n title=\"Could not load available documentation.\"\n >\n <CodeSnippet language=\"text\" text={error.toString()} />\n </WarningPanel>\n </Content>\n </TechDocsPageWrapper>\n );\n }\n\n return (\n <TechDocsPageWrapper>\n <HeaderTabs\n selectedIndex={selectedTab}\n onChange={index => setSelectedTab(index)}\n tabs={tabsConfig.map(({ label }, index) => ({\n id: index.toString(),\n label,\n }))}\n />\n <Content data-testid=\"techdocs-content\">\n {currentTabConfig.panels.map((config, index) => (\n <CustomPanel\n key={index}\n config={config}\n entities={!!entities ? entities : []}\n index={index}\n />\n ))}\n </Content>\n </TechDocsPageWrapper>\n );\n};\n"],"names":[],"mappings":"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"}
@@ -1,4 +1,4 @@
1
- export { c as TechDocsReaderLayout, b as TechDocsReaderPage } from './index-cb910cad.esm.js';
1
+ export { c as TechDocsReaderLayout, b as TechDocsReaderPage } from './index-c537b1f3.esm.js';
2
2
  import '@backstage/core-plugin-api';
3
3
  import '@backstage/errors';
4
4
  import 'event-source-polyfill';
@@ -9,7 +9,6 @@ import '@backstage/plugin-techdocs-react';
9
9
  import 'jss';
10
10
  import '@material-ui/core';
11
11
  import '@material-ui/styles';
12
- import 'react-text-truncate';
13
12
  import '@backstage/plugin-search-react';
14
13
  import '@material-ui/icons/Search';
15
14
  import '@material-ui/lab/Autocomplete';
@@ -31,10 +30,10 @@ import 'react-helmet';
31
30
  import '@material-ui/icons/Code';
32
31
  import '@backstage/plugin-catalog-react';
33
32
  import '@backstage/catalog-model';
33
+ import '@material-ui/icons/Settings';
34
34
  import 'react-use/lib/useCopyToClipboard';
35
35
  import 'lodash';
36
36
  import '@material-ui/icons/Share';
37
37
  import '@material-ui/icons/Star';
38
38
  import '@material-ui/icons/StarBorder';
39
- import '@backstage/core-app-api';
40
- //# sourceMappingURL=index-64eda4c3.esm.js.map
39
+ //# sourceMappingURL=index-52f21300.esm.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index-52f21300.esm.js","sources":[],"sourcesContent":[],"names":[],"mappings":";;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;"}
@@ -4,12 +4,11 @@ import { EventSourcePolyfill } from 'event-source-polyfill';
4
4
  import React, { useState, useEffect, useReducer, useRef, useMemo, createContext, useContext, useCallback, Children } from 'react';
5
5
  import { useParams, useNavigate as useNavigate$1, useOutlet, Routes, Route } from 'react-router-dom';
6
6
  import { Link, LogViewer, ErrorPage, Progress, SidebarPinStateContext, Content, HeaderLabel, Header, Page, ItemCardGrid, ItemCardHeader, Button as Button$1, WarningPanel, CodeSnippet, SubvalueCell, Table, EmptyState, PageWithHeader, ContentHeader, SupportButton, MissingAnnotationEmptyState } from '@backstage/core-components';
7
- import { useTechDocsReaderPage, useTechDocsAddons, TechDocsAddonLocations, TECHDOCS_ADDONS_WRAPPER_KEY, TechDocsReaderPageProvider } from '@backstage/plugin-techdocs-react';
7
+ import { techdocsStorageApiRef as techdocsStorageApiRef$1, useTechDocsReaderPage, useTechDocsAddons, TechDocsAddonLocations, TECHDOCS_ADDONS_WRAPPER_KEY, TechDocsReaderPageProvider, techdocsApiRef as techdocsApiRef$1 } from '@backstage/plugin-techdocs-react';
8
8
  import { create } from 'jss';
9
- import { makeStyles, ListItemText, ListItem, Divider, TextField, InputAdornment, IconButton, CircularProgress, createStyles, Button, Drawer, Grid, Typography, withStyles, Tooltip, ThemeProvider, SvgIcon, useTheme, Portal, Toolbar, Box, Card, CardMedia, CardContent, CardActions } from '@material-ui/core';
9
+ import { makeStyles, ListItemText, ListItem, Divider, TextField, InputAdornment, IconButton, CircularProgress, createStyles, Button, Drawer, Grid, Typography, withStyles, Tooltip, ThemeProvider, SvgIcon, useTheme, Portal, Toolbar, Box, Menu, Card, CardMedia, CardContent, CardActions } from '@material-ui/core';
10
10
  import { jssPreset, StylesProvider, withStyles as withStyles$1 } from '@material-ui/styles';
11
- import TextTruncate from 'react-text-truncate';
12
- import { SearchContextProvider, useSearch } from '@backstage/plugin-search-react';
11
+ import { HighlightedSearchResultText, SearchContextProvider, useSearch } from '@backstage/plugin-search-react';
13
12
  import SearchIcon from '@material-ui/icons/Search';
14
13
  import Autocomplete from '@material-ui/lab/Autocomplete';
15
14
  import { useNavigate, useOutlet as useOutlet$1 } from 'react-router';
@@ -30,12 +29,12 @@ import Helmet from 'react-helmet';
30
29
  import CodeIcon from '@material-ui/icons/Code';
31
30
  import { getEntityRelations, EntityRefLink, EntityRefLinks, useEntityList, humanizeEntityRef, useStarredEntities, CATALOG_FILTER_EXISTS, EntityListProvider, CatalogFilterLayout, UserListPicker, EntityOwnerPicker, EntityTagPicker, useEntity } from '@backstage/plugin-catalog-react';
32
31
  import { RELATION_OWNED_BY, getCompoundEntityRef } from '@backstage/catalog-model';
32
+ import SettingsIcon from '@material-ui/icons/Settings';
33
33
  import useCopyToClipboard from 'react-use/lib/useCopyToClipboard';
34
34
  import { capitalize } from 'lodash';
35
35
  import ShareIcon from '@material-ui/icons/Share';
36
36
  import Star from '@material-ui/icons/Star';
37
37
  import StarBorder from '@material-ui/icons/StarBorder';
38
- import { FlatRoutes } from '@backstage/core-app-api';
39
38
 
40
39
  const techdocsStorageApiRef = createApiRef({
41
40
  id: "plugin.techdocs.storageservice"
@@ -166,6 +165,7 @@ const useStyles$4 = makeStyles({
166
165
  const TechDocsSearchResultListItem = (props) => {
167
166
  const {
168
167
  result,
168
+ highlight,
169
169
  lineClamp = 5,
170
170
  asListItem = true,
171
171
  asLink = true,
@@ -173,17 +173,37 @@ const TechDocsSearchResultListItem = (props) => {
173
173
  } = props;
174
174
  const classes = useStyles$4();
175
175
  const TextItem = () => {
176
- var _a;
176
+ const resultTitle = (highlight == null ? void 0 : highlight.fields.title) ? /* @__PURE__ */ React.createElement(HighlightedSearchResultText, {
177
+ text: highlight.fields.title,
178
+ preTag: highlight.preTag,
179
+ postTag: highlight.postTag
180
+ }) : result.title;
181
+ const entityTitle = (highlight == null ? void 0 : highlight.fields.entityTitle) ? /* @__PURE__ */ React.createElement(HighlightedSearchResultText, {
182
+ text: highlight.fields.entityTitle,
183
+ preTag: highlight.preTag,
184
+ postTag: highlight.postTag
185
+ }) : result.entityTitle;
186
+ const resultName = (highlight == null ? void 0 : highlight.fields.name) ? /* @__PURE__ */ React.createElement(HighlightedSearchResultText, {
187
+ text: highlight.fields.name,
188
+ preTag: highlight.preTag,
189
+ postTag: highlight.postTag
190
+ }) : result.name;
177
191
  return /* @__PURE__ */ React.createElement(ListItemText, {
178
192
  className: classes.itemText,
179
193
  primaryTypographyProps: { variant: "h6" },
180
- primary: title ? title : `${result.title} | ${(_a = result.entityTitle) != null ? _a : result.name} docs`,
181
- secondary: /* @__PURE__ */ React.createElement(TextTruncate, {
182
- line: lineClamp,
183
- truncateText: "\u2026",
184
- text: result.text,
185
- element: "span"
186
- })
194
+ primary: title ? title : /* @__PURE__ */ React.createElement(React.Fragment, null, resultTitle, " | ", entityTitle != null ? entityTitle : resultName, " docs"),
195
+ secondary: /* @__PURE__ */ React.createElement("span", {
196
+ style: {
197
+ display: "-webkit-box",
198
+ WebkitBoxOrient: "vertical",
199
+ WebkitLineClamp: lineClamp,
200
+ overflow: "hidden"
201
+ }
202
+ }, (highlight == null ? void 0 : highlight.fields.text) ? /* @__PURE__ */ React.createElement(HighlightedSearchResultText, {
203
+ text: highlight.fields.text,
204
+ preTag: highlight.preTag,
205
+ postTag: highlight.postTag
206
+ }) : result.text)
187
207
  });
188
208
  };
189
209
  const LinkWrapper = ({ children }) => asLink ? /* @__PURE__ */ React.createElement(Link, {
@@ -270,12 +290,13 @@ const TechDocsSearchBar = (props) => {
270
290
  noOptionsText: "No results found",
271
291
  value: null,
272
292
  options,
273
- renderOption: ({ document }) => /* @__PURE__ */ React.createElement(TechDocsSearchResultListItem, {
293
+ renderOption: ({ document, highlight }) => /* @__PURE__ */ React.createElement(TechDocsSearchResultListItem, {
274
294
  result: document,
275
295
  lineClamp: 3,
276
296
  asListItem: false,
277
297
  asLink: false,
278
- title: document.title
298
+ title: document.title,
299
+ highlight
279
300
  }),
280
301
  loading,
281
302
  renderInput: (params) => /* @__PURE__ */ React.createElement(TextField, {
@@ -551,7 +572,7 @@ function useReaderState(kind, namespace, name, path) {
551
572
  contentLoading: true,
552
573
  buildLog: []
553
574
  });
554
- const techdocsStorageApi = useApi(techdocsStorageApiRef);
575
+ const techdocsStorageApi = useApi(techdocsStorageApiRef$1);
555
576
  const { retry: contentReload } = useAsyncRetry(async () => {
556
577
  dispatch({ type: "contentLoading" });
557
578
  try {
@@ -665,7 +686,7 @@ const addBaseUrl = ({
665
686
  try {
666
687
  const svg = await fetch(newValue, { credentials: "include" });
667
688
  const svgContent = await svg.text();
668
- elem.setAttribute(attributeName, `data:image/svg+xml;base64,${btoa(svgContent)}`);
689
+ elem.setAttribute(attributeName, `data:image/svg+xml;base64,${btoa(unescape(encodeURIComponent(svgContent)))}`);
669
690
  } catch (e) {
670
691
  elem.setAttribute("alt", `Error: ${elemAttribute}`);
671
692
  }
@@ -688,6 +709,7 @@ const addBaseUrl = ({
688
709
 
689
710
  const addGitFeedbackLink = (scmIntegrationsApi) => {
690
711
  return (dom) => {
712
+ var _a;
691
713
  const sourceAnchor = dom.querySelector('[title="Edit this page"]');
692
714
  if (!sourceAnchor || !sourceAnchor.href) {
693
715
  return dom;
@@ -697,7 +719,7 @@ const addGitFeedbackLink = (scmIntegrationsApi) => {
697
719
  if ((integration == null ? void 0 : integration.type) !== "github" && (integration == null ? void 0 : integration.type) !== "gitlab") {
698
720
  return dom;
699
721
  }
700
- const title = dom.querySelector("article>h1").childNodes[0].textContent;
722
+ const title = ((_a = dom.querySelector("article>h1")) == null ? void 0 : _a.childNodes[0].textContent) || "";
701
723
  const issueTitle = encodeURIComponent(`Documentation Feedback: ${title}`);
702
724
  const issueDesc = encodeURIComponent(`Page source:
703
725
  ${sourceAnchor.href}
@@ -983,7 +1005,7 @@ const headings = ["h1", "h2", "h3", "h4", "h5", "h6"];
983
1005
  const useTechDocsReaderDom = (entityRef) => {
984
1006
  const navigate = useNavigate$1();
985
1007
  const theme = useTheme();
986
- const techdocsStorageApi = useApi(techdocsStorageApiRef);
1008
+ const techdocsStorageApi = useApi(techdocsStorageApiRef$1);
987
1009
  const scmIntegrationsApi = useApi(scmIntegrationsApiRef);
988
1010
  const techdocsSanitizer = useApi(configApiRef);
989
1011
  const { namespace, kind, name } = entityRef;
@@ -1604,7 +1626,12 @@ const TechDocsReaderPageContent = withTechDocsReaderProvider((props) => {
1604
1626
  const { withSearch = true, onReady } = props;
1605
1627
  const classes = useStyles$1();
1606
1628
  const addons = useTechDocsAddons();
1607
- const { entityRef, shadowRoot, setShadowRoot } = useTechDocsReaderPage();
1629
+ const {
1630
+ entityMetadata: { value: entityMetadata, loading: entityMetadataLoading },
1631
+ entityRef,
1632
+ shadowRoot,
1633
+ setShadowRoot
1634
+ } = useTechDocsReaderPage();
1608
1635
  const dom = useTechDocsReaderDom(entityRef);
1609
1636
  const [jss, setJss] = useState(create({
1610
1637
  ...jssPreset(),
@@ -1633,8 +1660,18 @@ const TechDocsReaderPageContent = withTechDocsReaderProvider((props) => {
1633
1660
  primarySidebarElement == null ? void 0 : primarySidebarElement.prepend(primarySidebarAddonLocation);
1634
1661
  const secondarySidebarAddonLocation = document.createElement("div");
1635
1662
  secondarySidebarElement == null ? void 0 : secondarySidebarElement.prepend(secondarySidebarAddonLocation);
1663
+ if (entityMetadataLoading === false && !entityMetadata)
1664
+ return /* @__PURE__ */ React.createElement(ErrorPage, {
1665
+ status: "404",
1666
+ statusMessage: "PAGE NOT FOUND"
1667
+ });
1636
1668
  if (!dom) {
1637
- return /* @__PURE__ */ React.createElement(Content, null, /* @__PURE__ */ React.createElement(Progress, null));
1669
+ return /* @__PURE__ */ React.createElement(Content, null, /* @__PURE__ */ React.createElement(Grid, {
1670
+ container: true
1671
+ }, /* @__PURE__ */ React.createElement(Grid, {
1672
+ xs: 12,
1673
+ item: true
1674
+ }, /* @__PURE__ */ React.createElement(TechDocsStateIndicator, null))));
1638
1675
  }
1639
1676
  return /* @__PURE__ */ React.createElement(Content, null, /* @__PURE__ */ React.createElement(Grid, {
1640
1677
  container: true
@@ -1692,8 +1729,8 @@ const TechDocsReaderPageHeader = (props) => {
1692
1729
  subtitle,
1693
1730
  setSubtitle,
1694
1731
  entityRef,
1695
- metadata: { value: metadata },
1696
- entityMetadata: { value: entityMetadata }
1732
+ metadata: { value: metadata, loading: metadataLoading },
1733
+ entityMetadata: { value: entityMetadata, loading: entityMetadataLoading }
1697
1734
  } = useTechDocsReaderPage();
1698
1735
  useEffect(() => {
1699
1736
  if (!metadata)
@@ -1743,6 +1780,10 @@ const TechDocsReaderPageHeader = (props) => {
1743
1780
  style: { marginTop: "-25px", fill: "#fff" }
1744
1781
  }))
1745
1782
  }) : null);
1783
+ const noEntMetadata = !entityMetadataLoading && entityMetadata === void 0;
1784
+ const noTdMetadata = !metadataLoading && metadata === void 0;
1785
+ if (noEntMetadata || noTdMetadata)
1786
+ return null;
1746
1787
  return /* @__PURE__ */ React.createElement(Header, {
1747
1788
  type: "Documentation",
1748
1789
  typeLink: docsRootLink,
@@ -1765,19 +1806,46 @@ const TechDocsReaderPageSubheader = ({
1765
1806
  toolbarProps
1766
1807
  }) => {
1767
1808
  const classes = useStyles();
1809
+ const [anchorEl, setAnchorEl] = useState(null);
1810
+ const handleClick = useCallback((event) => {
1811
+ setAnchorEl(event.currentTarget);
1812
+ }, []);
1813
+ const handleClose = useCallback(() => {
1814
+ setAnchorEl(null);
1815
+ }, []);
1816
+ const {
1817
+ entityMetadata: { value: entityMetadata, loading: entityMetadataLoading }
1818
+ } = useTechDocsReaderPage();
1768
1819
  const addons = useTechDocsAddons();
1769
1820
  const subheaderAddons = addons.renderComponentsByLocation(TechDocsAddonLocations.Subheader);
1770
- if (!subheaderAddons)
1821
+ const settingsAddons = addons.renderComponentsByLocation(TechDocsAddonLocations.Settings);
1822
+ if (!subheaderAddons && !settingsAddons)
1823
+ return null;
1824
+ if (entityMetadataLoading === false && !entityMetadata)
1771
1825
  return null;
1772
1826
  return /* @__PURE__ */ React.createElement(Toolbar, {
1773
1827
  classes,
1774
1828
  ...toolbarProps
1775
- }, subheaderAddons && /* @__PURE__ */ React.createElement(Box, {
1829
+ }, /* @__PURE__ */ React.createElement(Box, {
1776
1830
  display: "flex",
1777
1831
  justifyContent: "flex-end",
1778
1832
  width: "100%",
1779
1833
  flexWrap: "wrap"
1780
- }, subheaderAddons));
1834
+ }, subheaderAddons, settingsAddons ? /* @__PURE__ */ React.createElement(React.Fragment, null, /* @__PURE__ */ React.createElement(Tooltip, {
1835
+ title: "Settings"
1836
+ }, /* @__PURE__ */ React.createElement(IconButton, {
1837
+ "aria-controls": "tech-docs-reader-page-settings",
1838
+ "aria-haspopup": "true",
1839
+ onClick: handleClick
1840
+ }, /* @__PURE__ */ React.createElement(SettingsIcon, null))), /* @__PURE__ */ React.createElement(Menu, {
1841
+ id: "tech-docs-reader-page-settings",
1842
+ getContentAnchorEl: null,
1843
+ anchorEl,
1844
+ anchorOrigin: { vertical: "bottom", horizontal: "right" },
1845
+ open: Boolean(anchorEl),
1846
+ onClose: handleClose,
1847
+ keepMounted: true
1848
+ }, settingsAddons)) : null));
1781
1849
  };
1782
1850
 
1783
1851
  const TechDocsReaderLayout = ({
@@ -2068,7 +2136,7 @@ const techdocsPlugin = createPlugin({
2068
2136
  id: "techdocs",
2069
2137
  apis: [
2070
2138
  createApiFactory({
2071
- api: techdocsStorageApiRef,
2139
+ api: techdocsStorageApiRef$1,
2072
2140
  deps: {
2073
2141
  configApi: configApiRef,
2074
2142
  discoveryApi: discoveryApiRef,
@@ -2083,7 +2151,7 @@ const techdocsPlugin = createPlugin({
2083
2151
  })
2084
2152
  }),
2085
2153
  createApiFactory({
2086
- api: techdocsApiRef,
2154
+ api: techdocsApiRef$1,
2087
2155
  deps: {
2088
2156
  configApi: configApiRef,
2089
2157
  discoveryApi: discoveryApiRef,
@@ -2114,7 +2182,7 @@ const EntityTechdocsContent = techdocsPlugin.provide(createRoutableExtension({
2114
2182
  }));
2115
2183
  const TechDocsCustomHome = techdocsPlugin.provide(createRoutableExtension({
2116
2184
  name: "TechDocsCustomHome",
2117
- component: () => import('./TechDocsCustomHome-4046b545.esm.js').then((m) => m.TechDocsCustomHome),
2185
+ component: () => import('./TechDocsCustomHome-b77adc6d.esm.js').then((m) => m.TechDocsCustomHome),
2118
2186
  mountPoint: rootRouteRef
2119
2187
  }));
2120
2188
  const TechDocsIndexPage$2 = techdocsPlugin.provide(createRoutableExtension({
@@ -2124,7 +2192,7 @@ const TechDocsIndexPage$2 = techdocsPlugin.provide(createRoutableExtension({
2124
2192
  }));
2125
2193
  const TechDocsReaderPage = techdocsPlugin.provide(createRoutableExtension({
2126
2194
  name: "TechDocsReaderPage",
2127
- component: () => import('./index-64eda4c3.esm.js').then((m) => m.TechDocsReaderPage),
2195
+ component: () => import('./index-52f21300.esm.js').then((m) => m.TechDocsReaderPage),
2128
2196
  mountPoint: rootDocsRouteRef
2129
2197
  }));
2130
2198
 
@@ -2171,8 +2239,7 @@ const EmbeddedDocsRouter = (props) => {
2171
2239
  annotation: TECHDOCS_ANNOTATION
2172
2240
  });
2173
2241
  }
2174
- return /* @__PURE__ */ React.createElement(FlatRoutes, null, /* @__PURE__ */ React.createElement(Route, {
2175
- path: "/*",
2242
+ return /* @__PURE__ */ React.createElement(Routes, null, /* @__PURE__ */ React.createElement(Route, {
2176
2243
  element: /* @__PURE__ */ React.createElement(EntityPageDocs, {
2177
2244
  entity
2178
2245
  })
@@ -2187,4 +2254,4 @@ var Router$1 = /*#__PURE__*/Object.freeze({
2187
2254
  });
2188
2255
 
2189
2256
  export { isTechDocsAvailable as A, Router as B, EmbeddedDocsRouter as C, DocsTable as D, EntityTechdocsContent as E, Reader as R, TechDocsPageWrapper as T, DocsCardGrid as a, TechDocsReaderPage$1 as b, TechDocsReaderLayout as c, TechDocsCustomHome as d, TechDocsIndexPage$2 as e, TechdocsPage as f, TechDocsReaderPage as g, techdocsStorageApiRef as h, techdocsApiRef as i, TechDocsClient as j, TechDocsStorageClient as k, TechDocsReaderPageHeader as l, TechDocsReaderPageContent as m, TechDocsReaderProvider as n, useTechDocsReaderDom as o, TechDocsReaderPageSubheader as p, TechDocsStateIndicator as q, TechDocsSearchResultListItem as r, TechDocsSearch as s, techdocsPlugin as t, useTechDocsReader as u, EntityListDocsGrid as v, withTechDocsReaderProvider as w, EntityListDocsTable as x, DefaultTechDocsHome as y, TechDocsPicker as z };
2190
- //# sourceMappingURL=index-cb910cad.esm.js.map
2257
+ //# sourceMappingURL=index-c537b1f3.esm.js.map