From 8693a913dec637a16bd2d9451d5b924f3b9d1bbe Mon Sep 17 00:00:00 2001 From: Hayden Spitzley Date: Thu, 25 May 2023 13:10:53 -0400 Subject: [PATCH 01/65] feat: allow making isLocationMatch use exact match in query string matcher Signed-off-by: Hayden Spitzley --- .../src/layout/Sidebar/SidebarSubmenuItem.tsx | 7 ++--- .../src/layout/Sidebar/utils.test.ts | 26 +++++++++++++++++++ .../src/layout/Sidebar/utils.ts | 10 +++++-- 3 files changed, 38 insertions(+), 5 deletions(-) diff --git a/packages/core-components/src/layout/Sidebar/SidebarSubmenuItem.tsx b/packages/core-components/src/layout/Sidebar/SidebarSubmenuItem.tsx index b08647d335..7ec0a40624 100644 --- a/packages/core-components/src/layout/Sidebar/SidebarSubmenuItem.tsx +++ b/packages/core-components/src/layout/Sidebar/SidebarSubmenuItem.tsx @@ -130,6 +130,7 @@ export type SidebarSubmenuItemProps = { to?: string; icon?: IconComponent; dropdownItems?: SidebarSubmenuItemDropdownItem[]; + exact?: boolean; }; /** @@ -138,7 +139,7 @@ export type SidebarSubmenuItemProps = { * @public */ export const SidebarSubmenuItem = (props: SidebarSubmenuItemProps) => { - const { title, subtitle, to, icon: Icon, dropdownItems } = props; + const { title, subtitle, to, icon: Icon, dropdownItems, exact } = props; const classes = useStyles(); const { setIsHoveredOn } = useContext(SidebarItemWithSubmenuContext); const closeSubmenu = () => { @@ -146,7 +147,7 @@ export const SidebarSubmenuItem = (props: SidebarSubmenuItemProps) => { }; const toLocation = useResolvedPath(to ?? ''); const currentLocation = useLocation(); - let isActive = isLocationMatch(currentLocation, toLocation); + let isActive = isLocationMatch(currentLocation, toLocation, exact || false); const [showDropDown, setShowDropDown] = useState(false); const handleClickDropdown = () => { @@ -155,7 +156,7 @@ export const SidebarSubmenuItem = (props: SidebarSubmenuItemProps) => { if (dropdownItems !== undefined) { dropdownItems.some(item => { const resolvedPath = resolvePath(item.to); - isActive = isLocationMatch(currentLocation, resolvedPath); + isActive = isLocationMatch(currentLocation, resolvedPath, exact || false); return isActive; }); return ( diff --git a/packages/core-components/src/layout/Sidebar/utils.test.ts b/packages/core-components/src/layout/Sidebar/utils.test.ts index b08dcda0fc..976108a63d 100644 --- a/packages/core-components/src/layout/Sidebar/utils.test.ts +++ b/packages/core-components/src/layout/Sidebar/utils.test.ts @@ -95,4 +95,30 @@ describe('isLocationMatching', () => { toLocation = { pathname: '/catalog', search: '', hash: '' }; expect(isLocationMatch(currentLocation, toLocation)).toBe(true); }); + + describe('exact matching', () => { + it('return false when target query parameters are subset of current location query parameters', async () => { + currentLocation = { + pathname: '/catalog', + search: '?x=foo&y=bar', + state: null, + hash: '', + key: '', + }; + toLocation = { pathname: '/catalog', search: '?x=foo', hash: '' }; + expect(isLocationMatch(currentLocation, toLocation, true)).toBe(false); + }); + + it('return true when target query parameters are exact match with current location query parameters', async () => { + currentLocation = { + pathname: '/catalog', + search: '?x=foo&y=bar', + state: null, + hash: '', + key: '', + }; + toLocation = { pathname: '/catalog', search: '?y=bar&x=foo', hash: '' }; + expect(isLocationMatch(currentLocation, toLocation, true)).toBe(true); + }); + }); }); diff --git a/packages/core-components/src/layout/Sidebar/utils.ts b/packages/core-components/src/layout/Sidebar/utils.ts index 1afebe796d..5dba73f4cd 100644 --- a/packages/core-components/src/layout/Sidebar/utils.ts +++ b/packages/core-components/src/layout/Sidebar/utils.ts @@ -18,7 +18,11 @@ import { Location, Path } from 'history'; import { isEqual, isMatch } from 'lodash'; import qs from 'qs'; -export function isLocationMatch(currentLocation: Location, toLocation: Path) { +export function isLocationMatch( + currentLocation: Location, + toLocation: Path, + exact: boolean = false, +) { const toDecodedSearch = new URLSearchParams(toLocation.search).toString(); const toQueryParameters = qs.parse(toDecodedSearch); @@ -27,9 +31,11 @@ export function isLocationMatch(currentLocation: Location, toLocation: Path) { ).toString(); const currentQueryParameters = qs.parse(currentDecodedSearch); + const queryStringMatcher = exact ? isEqual : isMatch; + const matching = isEqual(toLocation.pathname, currentLocation.pathname) && - isMatch(currentQueryParameters, toQueryParameters); + queryStringMatcher(currentQueryParameters, toQueryParameters); return matching; } From c1f1eebe36d55746cf95ab5ca1098c1458d893bc Mon Sep 17 00:00:00 2001 From: Maapteh Date: Mon, 29 May 2023 13:56:51 +0200 Subject: [PATCH 02/65] fix: start with some printable containers Signed-off-by: Maapteh --- packages/core-components/src/layout/Page/Page.tsx | 5 +++++ packages/core-components/src/layout/Sidebar/Bar.tsx | 3 +++ .../core-components/src/layout/Sidebar/MobileSidebar.tsx | 3 +++ packages/core-components/src/layout/Sidebar/Page.tsx | 4 ++++ 4 files changed, 15 insertions(+) diff --git a/packages/core-components/src/layout/Page/Page.tsx b/packages/core-components/src/layout/Page/Page.tsx index 00988c475b..e388e0366a 100644 --- a/packages/core-components/src/layout/Page/Page.tsx +++ b/packages/core-components/src/layout/Page/Page.tsx @@ -33,6 +33,11 @@ const useStyles = makeStyles( [theme.breakpoints.down('xs')]: { height: '100%', }, + '@media print': { + display: 'block', + height: 'auto', + overflowY: 'inherit', + }, }, }), { name: 'BackstagePage' }, diff --git a/packages/core-components/src/layout/Sidebar/Bar.tsx b/packages/core-components/src/layout/Sidebar/Bar.tsx index 815d6bc0d6..8cb43ba007 100644 --- a/packages/core-components/src/layout/Sidebar/Bar.tsx +++ b/packages/core-components/src/layout/Sidebar/Bar.tsx @@ -63,6 +63,9 @@ const useStyles = makeStyles( '&::-webkit-scrollbar': { display: 'none', }, + '@media print': { + display: 'none', + }, }, drawerWidth: props => ({ width: props.sidebarConfig.drawerWidthClosed, diff --git a/packages/core-components/src/layout/Sidebar/MobileSidebar.tsx b/packages/core-components/src/layout/Sidebar/MobileSidebar.tsx index 9000c2f10b..bf96703613 100644 --- a/packages/core-components/src/layout/Sidebar/MobileSidebar.tsx +++ b/packages/core-components/src/layout/Sidebar/MobileSidebar.tsx @@ -72,6 +72,9 @@ const useStyles = makeStyles( zIndex: theme.zIndex.snackbar, // SidebarDivider color borderTop: '1px solid #383838', + '@media print': { + display: 'none', + }, }, overlay: props => ({ diff --git a/packages/core-components/src/layout/Sidebar/Page.tsx b/packages/core-components/src/layout/Sidebar/Page.tsx index 5f660547d1..09935867b3 100644 --- a/packages/core-components/src/layout/Sidebar/Page.tsx +++ b/packages/core-components/src/layout/Sidebar/Page.tsx @@ -51,6 +51,10 @@ const useStyles = makeStyles< [theme.breakpoints.down('xs')]: { paddingBottom: props => props.sidebarConfig.mobileSidebarHeight, }, + '@media print': { + paddingLeft: '0px !important', + paddingBottom: '0px !important', + }, }, content: { zIndex: 0, From 36bedda8da9a3485d264f70c701ccea664911bb1 Mon Sep 17 00:00:00 2001 From: Maapteh Date: Mon, 29 May 2023 14:22:28 +0200 Subject: [PATCH 03/65] -s fix: each container not breaked in start... Signed-off-by: Maapteh --- packages/core-components/src/layout/InfoCard/InfoCard.tsx | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/packages/core-components/src/layout/InfoCard/InfoCard.tsx b/packages/core-components/src/layout/InfoCard/InfoCard.tsx index 3d8d0f3bb0..3034ce1cf2 100644 --- a/packages/core-components/src/layout/InfoCard/InfoCard.tsx +++ b/packages/core-components/src/layout/InfoCard/InfoCard.tsx @@ -92,6 +92,10 @@ const VARIANT_STYLES = { flexDirection: 'column', height: 'calc(100% - 10px)', // for pages without content header marginBottom: '10px', + breakInside: 'avoid', + '@media print': { + height: 'auto', + }, }, }, cardContent: { From e33beb1f2a8ef53bfc18339630eecf9c2ced45bb Mon Sep 17 00:00:00 2001 From: Maapteh Date: Mon, 29 May 2023 14:40:16 +0200 Subject: [PATCH 04/65] add changelog Signed-off-by: Maapteh --- .changeset/smart-ads-rush.md | 5 +++++ 1 file changed, 5 insertions(+) create mode 100644 .changeset/smart-ads-rush.md diff --git a/.changeset/smart-ads-rush.md b/.changeset/smart-ads-rush.md new file mode 100644 index 0000000000..4f7cad0d49 --- /dev/null +++ b/.changeset/smart-ads-rush.md @@ -0,0 +1,5 @@ +--- +'@backstage/core-components': patch +--- + +Make the documentation pages printable (also handy for exporting to pdf when go-green) From 69db3a7e9427da205342e33d81ef755e5620d730 Mon Sep 17 00:00:00 2001 From: Maapteh Date: Mon, 29 May 2023 20:13:43 +0200 Subject: [PATCH 05/65] review Signed-off-by: Maapteh --- .changeset/smart-ads-rush.md | 2 +- packages/core-components/src/layout/Sidebar/Page.tsx | 3 +-- 2 files changed, 2 insertions(+), 3 deletions(-) diff --git a/.changeset/smart-ads-rush.md b/.changeset/smart-ads-rush.md index 4f7cad0d49..45ed2ff593 100644 --- a/.changeset/smart-ads-rush.md +++ b/.changeset/smart-ads-rush.md @@ -2,4 +2,4 @@ '@backstage/core-components': patch --- -Make the documentation pages printable (also handy for exporting to pdf when go-green) +Make the documentation pages printable (also handy for exporting to PDF) diff --git a/packages/core-components/src/layout/Sidebar/Page.tsx b/packages/core-components/src/layout/Sidebar/Page.tsx index 09935867b3..c0107256e1 100644 --- a/packages/core-components/src/layout/Sidebar/Page.tsx +++ b/packages/core-components/src/layout/Sidebar/Page.tsx @@ -52,8 +52,7 @@ const useStyles = makeStyles< paddingBottom: props => props.sidebarConfig.mobileSidebarHeight, }, '@media print': { - paddingLeft: '0px !important', - paddingBottom: '0px !important', + padding: '0px !important', }, }, content: { From f242762235ac2c0bf27498e7f782a50b3d75a994 Mon Sep 17 00:00:00 2001 From: Maapteh Date: Mon, 29 May 2023 20:16:08 +0200 Subject: [PATCH 06/65] review Signed-off-by: Maapteh --- packages/core-components/src/layout/InfoCard/InfoCard.tsx | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/packages/core-components/src/layout/InfoCard/InfoCard.tsx b/packages/core-components/src/layout/InfoCard/InfoCard.tsx index 3034ce1cf2..c80e71b609 100644 --- a/packages/core-components/src/layout/InfoCard/InfoCard.tsx +++ b/packages/core-components/src/layout/InfoCard/InfoCard.tsx @@ -92,7 +92,7 @@ const VARIANT_STYLES = { flexDirection: 'column', height: 'calc(100% - 10px)', // for pages without content header marginBottom: '10px', - breakInside: 'avoid', + breakInside: 'avoid-page', '@media print': { height: 'auto', }, From 485c49192b2544d05a51ad29e7fe6ddee0403007 Mon Sep 17 00:00:00 2001 From: Hayden Spitzley Date: Tue, 30 May 2023 09:01:58 -0400 Subject: [PATCH 07/65] remove fallback value and update api report Signed-off-by: Hayden Spitzley --- packages/core-components/api-report.md | 1 + .../core-components/src/layout/Sidebar/SidebarSubmenuItem.tsx | 4 ++-- 2 files changed, 3 insertions(+), 2 deletions(-) diff --git a/packages/core-components/api-report.md b/packages/core-components/api-report.md index 9f4aca1dcf..df34abdd03 100644 --- a/packages/core-components/api-report.md +++ b/packages/core-components/api-report.md @@ -1087,6 +1087,7 @@ export type SidebarSubmenuItemProps = { to?: string; icon?: IconComponent; dropdownItems?: SidebarSubmenuItemDropdownItem[]; + exact?: boolean; }; // @public diff --git a/packages/core-components/src/layout/Sidebar/SidebarSubmenuItem.tsx b/packages/core-components/src/layout/Sidebar/SidebarSubmenuItem.tsx index 7ec0a40624..d05ee23636 100644 --- a/packages/core-components/src/layout/Sidebar/SidebarSubmenuItem.tsx +++ b/packages/core-components/src/layout/Sidebar/SidebarSubmenuItem.tsx @@ -147,7 +147,7 @@ export const SidebarSubmenuItem = (props: SidebarSubmenuItemProps) => { }; const toLocation = useResolvedPath(to ?? ''); const currentLocation = useLocation(); - let isActive = isLocationMatch(currentLocation, toLocation, exact || false); + let isActive = isLocationMatch(currentLocation, toLocation, exact); const [showDropDown, setShowDropDown] = useState(false); const handleClickDropdown = () => { @@ -156,7 +156,7 @@ export const SidebarSubmenuItem = (props: SidebarSubmenuItemProps) => { if (dropdownItems !== undefined) { dropdownItems.some(item => { const resolvedPath = resolvePath(item.to); - isActive = isLocationMatch(currentLocation, resolvedPath, exact || false); + isActive = isLocationMatch(currentLocation, resolvedPath, exact); return isActive; }); return ( From 66ae4d8ca380104da66c08e1c86aeb8a444c3efe Mon Sep 17 00:00:00 2001 From: Hayden Spitzley Date: Tue, 30 May 2023 09:48:50 -0400 Subject: [PATCH 08/65] add changeset Signed-off-by: Hayden Spitzley --- .changeset/perfect-donkeys-cry.md | 5 +++++ 1 file changed, 5 insertions(+) create mode 100644 .changeset/perfect-donkeys-cry.md diff --git a/.changeset/perfect-donkeys-cry.md b/.changeset/perfect-donkeys-cry.md new file mode 100644 index 0000000000..83eafe69ca --- /dev/null +++ b/.changeset/perfect-donkeys-cry.md @@ -0,0 +1,5 @@ +--- +'@backstage/core-components': patch +--- + +Add option to require exact matching for isLocationMatch From 7493e042757efc83b45a192c8b58eedf530289a3 Mon Sep 17 00:00:00 2001 From: Maapteh Date: Tue, 30 May 2023 17:33:12 +0200 Subject: [PATCH 09/65] can not run techdocs maybe this is it.. Signed-off-by: Maapteh --- .../src/reader/transformers/styles/rules/layout.ts | 10 ++++++++++ 1 file changed, 10 insertions(+) diff --git a/plugins/techdocs/src/reader/transformers/styles/rules/layout.ts b/plugins/techdocs/src/reader/transformers/styles/rules/layout.ts index c5e69e6084..24adabfcec 100644 --- a/plugins/techdocs/src/reader/transformers/styles/rules/layout.ts +++ b/plugins/techdocs/src/reader/transformers/styles/rules/layout.ts @@ -227,4 +227,14 @@ export default ({ theme, sidebar }: RuleOptions) => ` width: 12.1rem; } } + + +@media print { + .md-sidebar { + display: none; + } + .md-content { + margin: 0; + } +} `; From 4e15516aaf6364ed20592009a4d9636decb746fb Mon Sep 17 00:00:00 2001 From: Maapteh Date: Tue, 30 May 2023 17:38:10 +0200 Subject: [PATCH 10/65] only able to run e2e fixture documentation Signed-off-by: Maapteh --- .../techdocs/src/reader/transformers/styles/rules/layout.ts | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/plugins/techdocs/src/reader/transformers/styles/rules/layout.ts b/plugins/techdocs/src/reader/transformers/styles/rules/layout.ts index 24adabfcec..4ab90e91e1 100644 --- a/plugins/techdocs/src/reader/transformers/styles/rules/layout.ts +++ b/plugins/techdocs/src/reader/transformers/styles/rules/layout.ts @@ -230,11 +230,14 @@ export default ({ theme, sidebar }: RuleOptions) => ` @media print { - .md-sidebar { + .md-sidebar, + #toggle-sidebar { display: none; } .md-content { margin: 0; + width: 100%; + max-width: 100%; } } `; From c695c3b5eaec1b4b3f3ed22caa755aaf4b310eb3 Mon Sep 17 00:00:00 2001 From: Maapteh Date: Tue, 30 May 2023 17:39:46 +0200 Subject: [PATCH 11/65] only able to run e2e fixture documentation Signed-off-by: Maapteh --- .changeset/smart-ads-rush.md | 1 + 1 file changed, 1 insertion(+) diff --git a/.changeset/smart-ads-rush.md b/.changeset/smart-ads-rush.md index 45ed2ff593..369e5ab25b 100644 --- a/.changeset/smart-ads-rush.md +++ b/.changeset/smart-ads-rush.md @@ -1,5 +1,6 @@ --- '@backstage/core-components': patch +'@backstage/plugin-techdocs': patch --- Make the documentation pages printable (also handy for exporting to PDF) From 42132761151a3d90c588a9cd127838fca2456018 Mon Sep 17 00:00:00 2001 From: Maapteh Date: Tue, 30 May 2023 17:44:05 +0200 Subject: [PATCH 12/65] only able to run e2e fixture documentation Signed-off-by: Maapteh --- .../TechDocsReaderPageContent/TechDocsReaderPageContent.tsx | 3 +++ .../TechDocsReaderPageSubheader.tsx | 3 +++ 2 files changed, 6 insertions(+) diff --git a/plugins/techdocs/src/reader/components/TechDocsReaderPageContent/TechDocsReaderPageContent.tsx b/plugins/techdocs/src/reader/components/TechDocsReaderPageContent/TechDocsReaderPageContent.tsx index 000a1ba275..1e5459fc9d 100644 --- a/plugins/techdocs/src/reader/components/TechDocsReaderPageContent/TechDocsReaderPageContent.tsx +++ b/plugins/techdocs/src/reader/components/TechDocsReaderPageContent/TechDocsReaderPageContent.tsx @@ -39,6 +39,9 @@ const useStyles = makeStyles({ width: 'calc(100% - 34.4rem)', margin: '0 auto', }, + '@media print': { + display: 'none', + }, }, }); diff --git a/plugins/techdocs/src/reader/components/TechDocsReaderPageSubheader/TechDocsReaderPageSubheader.tsx b/plugins/techdocs/src/reader/components/TechDocsReaderPageSubheader/TechDocsReaderPageSubheader.tsx index f3612aa46e..85f04655fd 100644 --- a/plugins/techdocs/src/reader/components/TechDocsReaderPageSubheader/TechDocsReaderPageSubheader.tsx +++ b/plugins/techdocs/src/reader/components/TechDocsReaderPageSubheader/TechDocsReaderPageSubheader.tsx @@ -39,6 +39,9 @@ const useStyles = makeStyles(theme => ({ flexDirection: 'column', minHeight: 'auto', padding: theme.spacing(3, 3, 0), + '@media print': { + display: 'none', + }, }, })); From c0806fe2b2e93f335264e411dd5b748fd195828a Mon Sep 17 00:00:00 2001 From: Maapteh Date: Tue, 30 May 2023 17:49:42 +0200 Subject: [PATCH 13/65] only able to run e2e fixture documentation Signed-off-by: Maapteh --- plugins/techdocs/src/reader/transformers/styles/rules/layout.ts | 1 + 1 file changed, 1 insertion(+) diff --git a/plugins/techdocs/src/reader/transformers/styles/rules/layout.ts b/plugins/techdocs/src/reader/transformers/styles/rules/layout.ts index 4ab90e91e1..cce6af7d6f 100644 --- a/plugins/techdocs/src/reader/transformers/styles/rules/layout.ts +++ b/plugins/techdocs/src/reader/transformers/styles/rules/layout.ts @@ -234,6 +234,7 @@ export default ({ theme, sidebar }: RuleOptions) => ` #toggle-sidebar { display: none; } + .md-content { margin: 0; width: 100%; From 54acb45982e566cb320381846de24883af102c0e Mon Sep 17 00:00:00 2001 From: npiyush97 Date: Wed, 31 May 2023 19:26:21 +0530 Subject: [PATCH 14/65] fix #18035 Signed-off-by: npiyush97 --- .../src/providers/GitlabOrgDiscoveryEntityProvider.ts | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/plugins/catalog-backend-module-gitlab/src/providers/GitlabOrgDiscoveryEntityProvider.ts b/plugins/catalog-backend-module-gitlab/src/providers/GitlabOrgDiscoveryEntityProvider.ts index 1fe607afbb..59de3ac30b 100644 --- a/plugins/catalog-backend-module-gitlab/src/providers/GitlabOrgDiscoveryEntityProvider.ts +++ b/plugins/catalog-backend-module-gitlab/src/providers/GitlabOrgDiscoveryEntityProvider.ts @@ -320,7 +320,7 @@ export class GitlabOrgDiscoveryEntityProvider implements EntityProvider { spec: { profile: { displayName: user.name, - picture: user.avatar_url, + picture: user.avatar_url || undefined, }, memberOf: [], }, From a83cb4e5624efea58abce2899ac06fb7a1a22269 Mon Sep 17 00:00:00 2001 From: "renovate[bot]" <29139614+renovate[bot]@users.noreply.github.com> Date: Wed, 31 May 2023 14:01:49 +0000 Subject: [PATCH 15/65] chore(deps): update dependency xml2js to ^0.6.0 Signed-off-by: renovate[bot] <29139614+renovate[bot]@users.noreply.github.com> --- .changeset/renovate-de04315.md | 5 +++++ plugins/code-coverage-backend/package.json | 2 +- yarn.lock | 10 +++++----- 3 files changed, 11 insertions(+), 6 deletions(-) create mode 100644 .changeset/renovate-de04315.md diff --git a/.changeset/renovate-de04315.md b/.changeset/renovate-de04315.md new file mode 100644 index 0000000000..9b8f5bd72c --- /dev/null +++ b/.changeset/renovate-de04315.md @@ -0,0 +1,5 @@ +--- +'@backstage/plugin-code-coverage-backend': patch +--- + +Updated dependency `xml2js` to `^0.6.0`. diff --git a/plugins/code-coverage-backend/package.json b/plugins/code-coverage-backend/package.json index d9857e7b7c..b965e2914f 100644 --- a/plugins/code-coverage-backend/package.json +++ b/plugins/code-coverage-backend/package.json @@ -44,7 +44,7 @@ "@types/supertest": "^2.0.8", "msw": "^1.0.0", "supertest": "^6.1.6", - "xml2js": "^0.5.0" + "xml2js": "^0.6.0" }, "files": [ "dist", diff --git a/yarn.lock b/yarn.lock index bb25e3b9ed..6a9a8f6b0d 100644 --- a/yarn.lock +++ b/yarn.lock @@ -6225,7 +6225,7 @@ __metadata: supertest: ^6.1.6 uuid: ^8.3.2 winston: ^3.2.1 - xml2js: ^0.5.0 + xml2js: ^0.6.0 yn: ^4.0.0 languageName: unknown linkType: soft @@ -41677,13 +41677,13 @@ __metadata: languageName: node linkType: hard -"xml2js@npm:^0.5.0": - version: 0.5.0 - resolution: "xml2js@npm:0.5.0" +"xml2js@npm:^0.6.0": + version: 0.6.0 + resolution: "xml2js@npm:0.6.0" dependencies: sax: ">=0.6.0" xmlbuilder: ~11.0.0 - checksum: 1aa71d62e5bc2d89138e3929b9ea46459157727759cbc62ef99484b778641c0cd21fb637696c052d901a22f82d092a3e740a16b4ce218e81ac59b933535124ea + checksum: 437f353fd66d367bf158e9555a0625df9965d944e499728a5c6bc92a54a2763179b144f14b7e1c725040f56bbd22b0fa6cfcb09ec4faf39c45ce01efe631f40b languageName: node linkType: hard From 12cb15e563c7fd18b7d94bee3c46b43be6bebc7a Mon Sep 17 00:00:00 2001 From: "renovate[bot]" <29139614+renovate[bot]@users.noreply.github.com> Date: Wed, 31 May 2023 15:09:32 +0000 Subject: [PATCH 16/65] fix(deps): update docusaurus monorepo to v0.0.0-5591 Signed-off-by: renovate[bot] <29139614+renovate[bot]@users.noreply.github.com> --- microsite/package.json | 8 +- microsite/yarn.lock | 380 ++++++++++++++++++++--------------------- 2 files changed, 194 insertions(+), 194 deletions(-) diff --git a/microsite/package.json b/microsite/package.json index 93e1689a92..720179093a 100644 --- a/microsite/package.json +++ b/microsite/package.json @@ -17,7 +17,7 @@ "docusaurus": "docusaurus" }, "devDependencies": { - "@docusaurus/module-type-aliases": "0.0.0-5589", + "@docusaurus/module-type-aliases": "0.0.0-5591", "@spotify/prettier-config": "^14.0.0", "@tsconfig/docusaurus": "^1.0.6", "@types/luxon": "^3.0.0", @@ -29,9 +29,9 @@ }, "prettier": "@spotify/prettier-config", "dependencies": { - "@docusaurus/core": "0.0.0-5589", - "@docusaurus/plugin-client-redirects": "0.0.0-5589", - "@docusaurus/preset-classic": "0.0.0-5589", + "@docusaurus/core": "0.0.0-5591", + "@docusaurus/plugin-client-redirects": "0.0.0-5591", + "@docusaurus/preset-classic": "0.0.0-5591", "@swc/core": "^1.3.46", "clsx": "^1.1.1", "docusaurus-plugin-sass": "^0.2.3", diff --git a/microsite/yarn.lock b/microsite/yarn.lock index e480859f65..12dbfd970c 100644 --- a/microsite/yarn.lock +++ b/microsite/yarn.lock @@ -1620,9 +1620,9 @@ __metadata: languageName: node linkType: hard -"@docusaurus/core@npm:0.0.0-5589": - version: 0.0.0-5589 - resolution: "@docusaurus/core@npm:0.0.0-5589" +"@docusaurus/core@npm:0.0.0-5591": + version: 0.0.0-5591 + resolution: "@docusaurus/core@npm:0.0.0-5591" dependencies: "@babel/core": ^7.20.12 "@babel/generator": ^7.21.1 @@ -1634,13 +1634,13 @@ __metadata: "@babel/runtime": ^7.21.0 "@babel/runtime-corejs3": ^7.21.0 "@babel/traverse": ^7.21.2 - "@docusaurus/cssnano-preset": 0.0.0-5589 - "@docusaurus/logger": 0.0.0-5589 - "@docusaurus/mdx-loader": 0.0.0-5589 + "@docusaurus/cssnano-preset": 0.0.0-5591 + "@docusaurus/logger": 0.0.0-5591 + "@docusaurus/mdx-loader": 0.0.0-5591 "@docusaurus/react-loadable": 5.5.2 - "@docusaurus/utils": 0.0.0-5589 - "@docusaurus/utils-common": 0.0.0-5589 - "@docusaurus/utils-validation": 0.0.0-5589 + "@docusaurus/utils": 0.0.0-5591 + "@docusaurus/utils-common": 0.0.0-5591 + "@docusaurus/utils-validation": 0.0.0-5591 "@slorber/static-site-generator-webpack-plugin": ^4.0.7 "@svgr/webpack": ^6.5.1 autoprefixer: ^10.4.13 @@ -1700,41 +1700,41 @@ __metadata: react-dom: ^16.8.4 || ^17.0.0 bin: docusaurus: bin/docusaurus.mjs - checksum: 40bcd07232d6dab372c01a78baf4467cde41d034819a282893e3e1eaaa1d237c3c764bba34e69d256369554d4ea4677a5ce657c4de50ba547960b3987659c6cf + checksum: 95dc10c721c1ec9b4912b772fc21f7ed79a4d27e3ab50c5acf30a86609ac8c4b544639fa6590705a3fac82ed72d3ae9b4b197d2db432d1af45d55b21bace6994 languageName: node linkType: hard -"@docusaurus/cssnano-preset@npm:0.0.0-5589": - version: 0.0.0-5589 - resolution: "@docusaurus/cssnano-preset@npm:0.0.0-5589" +"@docusaurus/cssnano-preset@npm:0.0.0-5591": + version: 0.0.0-5591 + resolution: "@docusaurus/cssnano-preset@npm:0.0.0-5591" dependencies: cssnano-preset-advanced: ^5.3.10 postcss: ^8.4.21 postcss-sort-media-queries: ^4.3.0 tslib: ^2.5.0 - checksum: 443f481e9bcf2fc39f244f55d78fc02b73206b5bdecf2ff0df12113924ec993fb16fcb5f9d53f51054c043541eac08b42a9107a69d91d3e5fad1582b54b2a26e + checksum: 256397caffd2c3d993b8a1e37b9a4f02b8baf4d78ff86df368e47d8e61c5933fc1258e26edac5a1823db0472896196e6a88f16f85cc81834f6a5edb04dfb4bf9 languageName: node linkType: hard -"@docusaurus/logger@npm:0.0.0-5589": - version: 0.0.0-5589 - resolution: "@docusaurus/logger@npm:0.0.0-5589" +"@docusaurus/logger@npm:0.0.0-5591": + version: 0.0.0-5591 + resolution: "@docusaurus/logger@npm:0.0.0-5591" dependencies: chalk: ^4.1.2 tslib: ^2.5.0 - checksum: 6eb23b03d2448b2df4c0c36bf7ca94619dd5875efa40ce42543d781d79b0ffd099a3782cf61ab893bf6df3d541a13b6934a7bcbc8c9b0e8b031d803e4f665fd1 + checksum: 0a59f232fec86170e9fbdca3f6bf7805ed0a38f1c83ff96aabdeb310c1de357c89db540e55d007086f76da701d0ffe89b283959856668894e8e2bae983f141b4 languageName: node linkType: hard -"@docusaurus/mdx-loader@npm:0.0.0-5589": - version: 0.0.0-5589 - resolution: "@docusaurus/mdx-loader@npm:0.0.0-5589" +"@docusaurus/mdx-loader@npm:0.0.0-5591": + version: 0.0.0-5591 + resolution: "@docusaurus/mdx-loader@npm:0.0.0-5591" dependencies: "@babel/parser": ^7.21.2 "@babel/traverse": ^7.21.2 - "@docusaurus/logger": 0.0.0-5589 - "@docusaurus/utils": 0.0.0-5589 - "@docusaurus/utils-validation": 0.0.0-5589 + "@docusaurus/logger": 0.0.0-5591 + "@docusaurus/utils": 0.0.0-5591 + "@docusaurus/utils-validation": 0.0.0-5591 "@mdx-js/mdx": ^2.1.5 escape-html: ^1.0.3 estree-util-value-to-estree: ^2.1.0 @@ -1758,16 +1758,16 @@ __metadata: peerDependencies: react: ^16.8.4 || ^17.0.0 react-dom: ^16.8.4 || ^17.0.0 - checksum: ac79ed203c98fad4303cb9e8e1e6c9ba3e1db04d42920f80057cf91579fcbe49d58dc13f2833e6ee99ad0d48dafecfd43fc9614f017a984d8d969778ceb8f8e4 + checksum: 919c5f0a0d815674bbf8777ba4ce758d26bb13f046e772d11b7f688b183a31d58bb9ba55d8a484f181996ea16f9f967529337ab98bc62b9d6c806d4dde374d15 languageName: node linkType: hard -"@docusaurus/module-type-aliases@npm:0.0.0-5589": - version: 0.0.0-5589 - resolution: "@docusaurus/module-type-aliases@npm:0.0.0-5589" +"@docusaurus/module-type-aliases@npm:0.0.0-5591": + version: 0.0.0-5591 + resolution: "@docusaurus/module-type-aliases@npm:0.0.0-5591" dependencies: "@docusaurus/react-loadable": 5.5.2 - "@docusaurus/types": 0.0.0-5589 + "@docusaurus/types": 0.0.0-5591 "@types/history": ^4.7.11 "@types/react": "*" "@types/react-router-config": "*" @@ -1777,19 +1777,19 @@ __metadata: peerDependencies: react: "*" react-dom: "*" - checksum: bef9472765002f863e6d1fe66f522246d02b3a6a59ab9fcbf1b700ed6bdef54b22a9c3ed14faf41999c03238fa682eb2a3e8d018a409007f61c8df4d4c691af9 + checksum: 9009e4f6edbfd274b42f5a0c2821c90606103404ec7df9e916940799ee8e810605549178d6a3e7ad6531554402d60a3db822268c88ddbff119a5c10f85f833d4 languageName: node linkType: hard -"@docusaurus/plugin-client-redirects@npm:0.0.0-5589": - version: 0.0.0-5589 - resolution: "@docusaurus/plugin-client-redirects@npm:0.0.0-5589" +"@docusaurus/plugin-client-redirects@npm:0.0.0-5591": + version: 0.0.0-5591 + resolution: "@docusaurus/plugin-client-redirects@npm:0.0.0-5591" dependencies: - "@docusaurus/core": 0.0.0-5589 - "@docusaurus/logger": 0.0.0-5589 - "@docusaurus/utils": 0.0.0-5589 - "@docusaurus/utils-common": 0.0.0-5589 - "@docusaurus/utils-validation": 0.0.0-5589 + "@docusaurus/core": 0.0.0-5591 + "@docusaurus/logger": 0.0.0-5591 + "@docusaurus/utils": 0.0.0-5591 + "@docusaurus/utils-common": 0.0.0-5591 + "@docusaurus/utils-validation": 0.0.0-5591 eta: ^2.0.1 fs-extra: ^11.1.0 lodash: ^4.17.21 @@ -1797,21 +1797,21 @@ __metadata: peerDependencies: react: ^16.8.4 || ^17.0.0 react-dom: ^16.8.4 || ^17.0.0 - checksum: 267a4081f79f0399266a1baf3ff4337b64d269f01d522e81ecb181cc8a5034844a8e49cb0c608420da0a2459ed88979764e7c2a9766b48010e9b7e775860f0c6 + checksum: 9e06448d280e3642fbe6ae02586c430c1245410e225a6f14f35c815d9cf13734b8793266267777b0f49eef968cd30d8247542b4521f3bdde0d5bebbfdd4a757c languageName: node linkType: hard -"@docusaurus/plugin-content-blog@npm:0.0.0-5589": - version: 0.0.0-5589 - resolution: "@docusaurus/plugin-content-blog@npm:0.0.0-5589" +"@docusaurus/plugin-content-blog@npm:0.0.0-5591": + version: 0.0.0-5591 + resolution: "@docusaurus/plugin-content-blog@npm:0.0.0-5591" dependencies: - "@docusaurus/core": 0.0.0-5589 - "@docusaurus/logger": 0.0.0-5589 - "@docusaurus/mdx-loader": 0.0.0-5589 - "@docusaurus/types": 0.0.0-5589 - "@docusaurus/utils": 0.0.0-5589 - "@docusaurus/utils-common": 0.0.0-5589 - "@docusaurus/utils-validation": 0.0.0-5589 + "@docusaurus/core": 0.0.0-5591 + "@docusaurus/logger": 0.0.0-5591 + "@docusaurus/mdx-loader": 0.0.0-5591 + "@docusaurus/types": 0.0.0-5591 + "@docusaurus/utils": 0.0.0-5591 + "@docusaurus/utils-common": 0.0.0-5591 + "@docusaurus/utils-validation": 0.0.0-5591 cheerio: ^1.0.0-rc.12 feed: ^4.2.2 fs-extra: ^11.1.0 @@ -1824,21 +1824,21 @@ __metadata: peerDependencies: react: ^16.8.4 || ^17.0.0 react-dom: ^16.8.4 || ^17.0.0 - checksum: 17c4d9e901f0dc60d7d81311ff8892a27ac27e0ef0c9e326b3a9e977eb5fe6f43177b6b1b6e6f9772fde42138b57de9edb2eb83ff0449832ab0b4d9fa86c28c6 + checksum: 61014344725c5bb003b1ef0e460d9287501f69d7a475b1650ddaffdd5a1609db244f766b1b0a2188f4db1a68f0ddd4dfd3ac6abcd20ed17446fa6294e35bea96 languageName: node linkType: hard -"@docusaurus/plugin-content-docs@npm:0.0.0-5589": - version: 0.0.0-5589 - resolution: "@docusaurus/plugin-content-docs@npm:0.0.0-5589" +"@docusaurus/plugin-content-docs@npm:0.0.0-5591": + version: 0.0.0-5591 + resolution: "@docusaurus/plugin-content-docs@npm:0.0.0-5591" dependencies: - "@docusaurus/core": 0.0.0-5589 - "@docusaurus/logger": 0.0.0-5589 - "@docusaurus/mdx-loader": 0.0.0-5589 - "@docusaurus/module-type-aliases": 0.0.0-5589 - "@docusaurus/types": 0.0.0-5589 - "@docusaurus/utils": 0.0.0-5589 - "@docusaurus/utils-validation": 0.0.0-5589 + "@docusaurus/core": 0.0.0-5591 + "@docusaurus/logger": 0.0.0-5591 + "@docusaurus/mdx-loader": 0.0.0-5591 + "@docusaurus/module-type-aliases": 0.0.0-5591 + "@docusaurus/types": 0.0.0-5591 + "@docusaurus/utils": 0.0.0-5591 + "@docusaurus/utils-validation": 0.0.0-5591 "@types/react-router-config": ^5.0.6 combine-promises: ^1.1.0 fs-extra: ^11.1.0 @@ -1851,133 +1851,133 @@ __metadata: peerDependencies: react: ^16.8.4 || ^17.0.0 react-dom: ^16.8.4 || ^17.0.0 - checksum: 9eb9caa230bc47409123d862570682b9a55213a9bbe84c91eed2a30fb6a07e25a333142105e3d86324f2765680beb5237db2ce94504f62d8d100e39987fa01a3 + checksum: 837fa1d6a0e5238ec8d9422a7de2da19380059edfd50946243bbc93f43f813336cd220a2f521e1efc99261218ab3cccaaf64c0977bdbaa14ed09f95924347476 languageName: node linkType: hard -"@docusaurus/plugin-content-pages@npm:0.0.0-5589": - version: 0.0.0-5589 - resolution: "@docusaurus/plugin-content-pages@npm:0.0.0-5589" +"@docusaurus/plugin-content-pages@npm:0.0.0-5591": + version: 0.0.0-5591 + resolution: "@docusaurus/plugin-content-pages@npm:0.0.0-5591" dependencies: - "@docusaurus/core": 0.0.0-5589 - "@docusaurus/mdx-loader": 0.0.0-5589 - "@docusaurus/types": 0.0.0-5589 - "@docusaurus/utils": 0.0.0-5589 - "@docusaurus/utils-validation": 0.0.0-5589 + "@docusaurus/core": 0.0.0-5591 + "@docusaurus/mdx-loader": 0.0.0-5591 + "@docusaurus/types": 0.0.0-5591 + "@docusaurus/utils": 0.0.0-5591 + "@docusaurus/utils-validation": 0.0.0-5591 fs-extra: ^11.1.0 tslib: ^2.5.0 webpack: ^5.76.0 peerDependencies: react: ^16.8.4 || ^17.0.0 react-dom: ^16.8.4 || ^17.0.0 - checksum: 5b0270bc661ce6758bb0e5f6d4196d2a5d713f164b86e2e51d233f748a8be69f93587c64bec4685436d085888c9d5a153cd7826f95c4d05cf259e266184ec05c + checksum: 74bfbc522fc60d0830b47a0100a0afd66d21d290047432414e9bd94db21d61805b883fc155f6c9ee965023f6153d7fb09b9219386f9140cda52540c40028942f languageName: node linkType: hard -"@docusaurus/plugin-debug@npm:0.0.0-5589": - version: 0.0.0-5589 - resolution: "@docusaurus/plugin-debug@npm:0.0.0-5589" +"@docusaurus/plugin-debug@npm:0.0.0-5591": + version: 0.0.0-5591 + resolution: "@docusaurus/plugin-debug@npm:0.0.0-5591" dependencies: - "@docusaurus/core": 0.0.0-5589 - "@docusaurus/types": 0.0.0-5589 - "@docusaurus/utils": 0.0.0-5589 + "@docusaurus/core": 0.0.0-5591 + "@docusaurus/types": 0.0.0-5591 + "@docusaurus/utils": 0.0.0-5591 fs-extra: ^11.1.0 react-json-view: ^1.21.3 tslib: ^2.5.0 peerDependencies: react: ^16.8.4 || ^17.0.0 react-dom: ^16.8.4 || ^17.0.0 - checksum: 3e23a2c443a2dbb69679356f1cfbb23982dca3f5c1e0c8fbf4897e978a0968cd09db8b4d51e63337bda42085a4baf8e1ea0b2bb349c976759a56788ccfa9c84b + checksum: f42bc6e5139e9aff99eab24a506f74fd9b0ef3baecf46fadb0596ead8167d58c4ba92b86a9e665d00bedaccbfeb7c483c02ef4f1c5de49cc966e457e624c0b45 languageName: node linkType: hard -"@docusaurus/plugin-google-analytics@npm:0.0.0-5589": - version: 0.0.0-5589 - resolution: "@docusaurus/plugin-google-analytics@npm:0.0.0-5589" +"@docusaurus/plugin-google-analytics@npm:0.0.0-5591": + version: 0.0.0-5591 + resolution: "@docusaurus/plugin-google-analytics@npm:0.0.0-5591" dependencies: - "@docusaurus/core": 0.0.0-5589 - "@docusaurus/types": 0.0.0-5589 - "@docusaurus/utils-validation": 0.0.0-5589 + "@docusaurus/core": 0.0.0-5591 + "@docusaurus/types": 0.0.0-5591 + "@docusaurus/utils-validation": 0.0.0-5591 tslib: ^2.5.0 peerDependencies: react: ^16.8.4 || ^17.0.0 react-dom: ^16.8.4 || ^17.0.0 - checksum: cf0332dccf1ebd7f7df4665af10caf6953817e2fcb84d44579a70181ecc8741fb0cad20e0f6b586b92099868b68e667cedf929f7ef41175e86b1252a27236c16 + checksum: 7c8b9bdb182b0eff01d6f85eb01cc6ffeb3325cb0c154187230328484669f346fa998dfa25bc474f9b03551c6351a2da76f31d68f2c7ce742382d579a32e89e7 languageName: node linkType: hard -"@docusaurus/plugin-google-gtag@npm:0.0.0-5589": - version: 0.0.0-5589 - resolution: "@docusaurus/plugin-google-gtag@npm:0.0.0-5589" +"@docusaurus/plugin-google-gtag@npm:0.0.0-5591": + version: 0.0.0-5591 + resolution: "@docusaurus/plugin-google-gtag@npm:0.0.0-5591" dependencies: - "@docusaurus/core": 0.0.0-5589 - "@docusaurus/types": 0.0.0-5589 - "@docusaurus/utils-validation": 0.0.0-5589 + "@docusaurus/core": 0.0.0-5591 + "@docusaurus/types": 0.0.0-5591 + "@docusaurus/utils-validation": 0.0.0-5591 "@types/gtag.js": ^0.0.12 tslib: ^2.5.0 peerDependencies: react: ^16.8.4 || ^17.0.0 react-dom: ^16.8.4 || ^17.0.0 - checksum: 2ff3f1f12c0a9e4d41df79f1074ea4507002d63fe99820dd3c9fd4da332a0868f4c3099e52975c7c1b55e8888293d57c50c42132dad15b6a14bd5df1407e9254 + checksum: 38daa81f7d499c819bf6221a9ba36d71e10f98f2c2e6b5adbcfcfbfc3f54e32df8315c98f381c9107f40ebe7aa9f7074dd16de6f925501f712dae73de3272133 languageName: node linkType: hard -"@docusaurus/plugin-google-tag-manager@npm:0.0.0-5589": - version: 0.0.0-5589 - resolution: "@docusaurus/plugin-google-tag-manager@npm:0.0.0-5589" +"@docusaurus/plugin-google-tag-manager@npm:0.0.0-5591": + version: 0.0.0-5591 + resolution: "@docusaurus/plugin-google-tag-manager@npm:0.0.0-5591" dependencies: - "@docusaurus/core": 0.0.0-5589 - "@docusaurus/types": 0.0.0-5589 - "@docusaurus/utils-validation": 0.0.0-5589 + "@docusaurus/core": 0.0.0-5591 + "@docusaurus/types": 0.0.0-5591 + "@docusaurus/utils-validation": 0.0.0-5591 tslib: ^2.5.0 peerDependencies: react: ^16.8.4 || ^17.0.0 react-dom: ^16.8.4 || ^17.0.0 - checksum: 102e162b2cf4779236dabd3e7a37347408a8b03891cb32d58ce99e0665a21d308bf1439952932be791662c06158fc07a4f0d6ada70df378b514e7d7a08cd841c + checksum: afc7e93de44fbee69183e285fc429cc406c184e28a8b8f3f774ee33d88a1edf6c12449bf3ad731d36b475b3915b5692925bd2cb48127ab92402cde6ff4442584 languageName: node linkType: hard -"@docusaurus/plugin-sitemap@npm:0.0.0-5589": - version: 0.0.0-5589 - resolution: "@docusaurus/plugin-sitemap@npm:0.0.0-5589" +"@docusaurus/plugin-sitemap@npm:0.0.0-5591": + version: 0.0.0-5591 + resolution: "@docusaurus/plugin-sitemap@npm:0.0.0-5591" dependencies: - "@docusaurus/core": 0.0.0-5589 - "@docusaurus/logger": 0.0.0-5589 - "@docusaurus/types": 0.0.0-5589 - "@docusaurus/utils": 0.0.0-5589 - "@docusaurus/utils-common": 0.0.0-5589 - "@docusaurus/utils-validation": 0.0.0-5589 + "@docusaurus/core": 0.0.0-5591 + "@docusaurus/logger": 0.0.0-5591 + "@docusaurus/types": 0.0.0-5591 + "@docusaurus/utils": 0.0.0-5591 + "@docusaurus/utils-common": 0.0.0-5591 + "@docusaurus/utils-validation": 0.0.0-5591 fs-extra: ^11.1.0 sitemap: ^7.1.1 tslib: ^2.5.0 peerDependencies: react: ^16.8.4 || ^17.0.0 react-dom: ^16.8.4 || ^17.0.0 - checksum: ede57edea1b058ed29dd9ebb60d959384b96411ef78473c855f1aeddc835d6dc191472ed31d187f586ddc623a3c7f85943c45e514fc2b5f0d11c29c31588a3c6 + checksum: cf9b5397699e3f7ff4d3fef175dfdfa66820ffd40a4892991634423331d19849da8f0d78bc453b5e964ff25a9705d4ad1e9dd0dcdc27b8520c6108594c491fc1 languageName: node linkType: hard -"@docusaurus/preset-classic@npm:0.0.0-5589": - version: 0.0.0-5589 - resolution: "@docusaurus/preset-classic@npm:0.0.0-5589" +"@docusaurus/preset-classic@npm:0.0.0-5591": + version: 0.0.0-5591 + resolution: "@docusaurus/preset-classic@npm:0.0.0-5591" dependencies: - "@docusaurus/core": 0.0.0-5589 - "@docusaurus/plugin-content-blog": 0.0.0-5589 - "@docusaurus/plugin-content-docs": 0.0.0-5589 - "@docusaurus/plugin-content-pages": 0.0.0-5589 - "@docusaurus/plugin-debug": 0.0.0-5589 - "@docusaurus/plugin-google-analytics": 0.0.0-5589 - "@docusaurus/plugin-google-gtag": 0.0.0-5589 - "@docusaurus/plugin-google-tag-manager": 0.0.0-5589 - "@docusaurus/plugin-sitemap": 0.0.0-5589 - "@docusaurus/theme-classic": 0.0.0-5589 - "@docusaurus/theme-common": 0.0.0-5589 - "@docusaurus/theme-search-algolia": 0.0.0-5589 - "@docusaurus/types": 0.0.0-5589 + "@docusaurus/core": 0.0.0-5591 + "@docusaurus/plugin-content-blog": 0.0.0-5591 + "@docusaurus/plugin-content-docs": 0.0.0-5591 + "@docusaurus/plugin-content-pages": 0.0.0-5591 + "@docusaurus/plugin-debug": 0.0.0-5591 + "@docusaurus/plugin-google-analytics": 0.0.0-5591 + "@docusaurus/plugin-google-gtag": 0.0.0-5591 + "@docusaurus/plugin-google-tag-manager": 0.0.0-5591 + "@docusaurus/plugin-sitemap": 0.0.0-5591 + "@docusaurus/theme-classic": 0.0.0-5591 + "@docusaurus/theme-common": 0.0.0-5591 + "@docusaurus/theme-search-algolia": 0.0.0-5591 + "@docusaurus/types": 0.0.0-5591 peerDependencies: react: ^16.8.4 || ^17.0.0 react-dom: ^16.8.4 || ^17.0.0 - checksum: 6fa034cd92ec2b58a6313c527b810bfbc60262f09b29f4139f18708f8522495711b1bcc2b7c997de93fd4ee49a916df29be9ab2ffc012e7b0680a808f5db7ca6 + checksum: 3e613a95622482510f3fdad017ceabcdf0d25d82560af665b536803d4fb746cd4e849fbe02304f60099a3e09845003bb433bedeb1b3fcde13b93522e775350f1 languageName: node linkType: hard @@ -1993,22 +1993,22 @@ __metadata: languageName: node linkType: hard -"@docusaurus/theme-classic@npm:0.0.0-5589": - version: 0.0.0-5589 - resolution: "@docusaurus/theme-classic@npm:0.0.0-5589" +"@docusaurus/theme-classic@npm:0.0.0-5591": + version: 0.0.0-5591 + resolution: "@docusaurus/theme-classic@npm:0.0.0-5591" dependencies: - "@docusaurus/core": 0.0.0-5589 - "@docusaurus/mdx-loader": 0.0.0-5589 - "@docusaurus/module-type-aliases": 0.0.0-5589 - "@docusaurus/plugin-content-blog": 0.0.0-5589 - "@docusaurus/plugin-content-docs": 0.0.0-5589 - "@docusaurus/plugin-content-pages": 0.0.0-5589 - "@docusaurus/theme-common": 0.0.0-5589 - "@docusaurus/theme-translations": 0.0.0-5589 - "@docusaurus/types": 0.0.0-5589 - "@docusaurus/utils": 0.0.0-5589 - "@docusaurus/utils-common": 0.0.0-5589 - "@docusaurus/utils-validation": 0.0.0-5589 + "@docusaurus/core": 0.0.0-5591 + "@docusaurus/mdx-loader": 0.0.0-5591 + "@docusaurus/module-type-aliases": 0.0.0-5591 + "@docusaurus/plugin-content-blog": 0.0.0-5591 + "@docusaurus/plugin-content-docs": 0.0.0-5591 + "@docusaurus/plugin-content-pages": 0.0.0-5591 + "@docusaurus/theme-common": 0.0.0-5591 + "@docusaurus/theme-translations": 0.0.0-5591 + "@docusaurus/types": 0.0.0-5591 + "@docusaurus/utils": 0.0.0-5591 + "@docusaurus/utils-common": 0.0.0-5591 + "@docusaurus/utils-validation": 0.0.0-5591 "@mdx-js/react": ^2.1.5 clsx: ^1.2.1 copy-text-to-clipboard: ^3.0.1 @@ -2025,21 +2025,21 @@ __metadata: peerDependencies: react: ^16.8.4 || ^17.0.0 react-dom: ^16.8.4 || ^17.0.0 - checksum: b44c934db76bda6ddcf2240c543392a1a299630af24a1edef9c73fd8085db8e92eb89546c0baf82f7c567e92adddaa1d8811b16bdb079cfd8aaf651b128a497e + checksum: 1bcfdb13c932e02dbd292b9a3215fff039dbf317f0cedf3d88aa365e15d5a2653f23c3e284930d33263bc6bf2887578140affa752c146a2395acb75818db64bf languageName: node linkType: hard -"@docusaurus/theme-common@npm:0.0.0-5589": - version: 0.0.0-5589 - resolution: "@docusaurus/theme-common@npm:0.0.0-5589" +"@docusaurus/theme-common@npm:0.0.0-5591": + version: 0.0.0-5591 + resolution: "@docusaurus/theme-common@npm:0.0.0-5591" dependencies: - "@docusaurus/mdx-loader": 0.0.0-5589 - "@docusaurus/module-type-aliases": 0.0.0-5589 - "@docusaurus/plugin-content-blog": 0.0.0-5589 - "@docusaurus/plugin-content-docs": 0.0.0-5589 - "@docusaurus/plugin-content-pages": 0.0.0-5589 - "@docusaurus/utils": 0.0.0-5589 - "@docusaurus/utils-common": 0.0.0-5589 + "@docusaurus/mdx-loader": 0.0.0-5591 + "@docusaurus/module-type-aliases": 0.0.0-5591 + "@docusaurus/plugin-content-blog": 0.0.0-5591 + "@docusaurus/plugin-content-docs": 0.0.0-5591 + "@docusaurus/plugin-content-pages": 0.0.0-5591 + "@docusaurus/utils": 0.0.0-5591 + "@docusaurus/utils-common": 0.0.0-5591 "@types/history": ^4.7.11 "@types/react": "*" "@types/react-router-config": "*" @@ -2052,22 +2052,22 @@ __metadata: peerDependencies: react: ^16.8.4 || ^17.0.0 react-dom: ^16.8.4 || ^17.0.0 - checksum: 52388d72d714aa67514367f59d8cb16fcea3790b7f1c3d7a7743ff826dea40ecece3d14edf7a57a7c93d960f93d300ce121cc4a162d44cab194d4129ca411b6b + checksum: bd941e6eac23310748aa70a35c41ad6e9123ea93ed0b872d6beb3313df847827dc5490000cc443d83d31157841cbf4d58fc2f844c743b3cf2fe6ccc7d1507deb languageName: node linkType: hard -"@docusaurus/theme-search-algolia@npm:0.0.0-5589": - version: 0.0.0-5589 - resolution: "@docusaurus/theme-search-algolia@npm:0.0.0-5589" +"@docusaurus/theme-search-algolia@npm:0.0.0-5591": + version: 0.0.0-5591 + resolution: "@docusaurus/theme-search-algolia@npm:0.0.0-5591" dependencies: "@docsearch/react": ^3.3.3 - "@docusaurus/core": 0.0.0-5589 - "@docusaurus/logger": 0.0.0-5589 - "@docusaurus/plugin-content-docs": 0.0.0-5589 - "@docusaurus/theme-common": 0.0.0-5589 - "@docusaurus/theme-translations": 0.0.0-5589 - "@docusaurus/utils": 0.0.0-5589 - "@docusaurus/utils-validation": 0.0.0-5589 + "@docusaurus/core": 0.0.0-5591 + "@docusaurus/logger": 0.0.0-5591 + "@docusaurus/plugin-content-docs": 0.0.0-5591 + "@docusaurus/theme-common": 0.0.0-5591 + "@docusaurus/theme-translations": 0.0.0-5591 + "@docusaurus/utils": 0.0.0-5591 + "@docusaurus/utils-validation": 0.0.0-5591 algoliasearch: ^4.15.0 algoliasearch-helper: ^3.12.0 clsx: ^1.2.1 @@ -2079,23 +2079,23 @@ __metadata: peerDependencies: react: ^16.8.4 || ^17.0.0 react-dom: ^16.8.4 || ^17.0.0 - checksum: 28275b24dd80357349678b5e48e141d1de8bc976774f51e4e6811c5b6b0867cc691f7662949fbbe8f18d62f5405768cdce1b745795f05b091fb42178ed44c2f4 + checksum: 7493eb67c7ba056aee42880006cd0587d81e05f81177f93d6f57f43f9af12cd2c9e6bed7b804c19a66fa6f192c5b6ccbbf9e16f923a48abe6c6a6a72d65bd5c1 languageName: node linkType: hard -"@docusaurus/theme-translations@npm:0.0.0-5589": - version: 0.0.0-5589 - resolution: "@docusaurus/theme-translations@npm:0.0.0-5589" +"@docusaurus/theme-translations@npm:0.0.0-5591": + version: 0.0.0-5591 + resolution: "@docusaurus/theme-translations@npm:0.0.0-5591" dependencies: fs-extra: ^11.1.0 tslib: ^2.5.0 - checksum: 1183cb59d7f9d742d525d81351343df74df08ff9e9a0a7e20bac6c3cf7974a2e92f8541b053eb12bfa282125ea1895d2a052651f2207f58fea072884f4abefeb + checksum: 6dd8647d1db2a97c77f3aa0d5f6935bad21df97f26d20d0a08916717335f50e72193c2bd7417043c9fb5fb4d9c19140f1408c854df5ef92ff6210bcc8e55f917 languageName: node linkType: hard -"@docusaurus/types@npm:0.0.0-5589": - version: 0.0.0-5589 - resolution: "@docusaurus/types@npm:0.0.0-5589" +"@docusaurus/types@npm:0.0.0-5591": + version: 0.0.0-5591 + resolution: "@docusaurus/types@npm:0.0.0-5591" dependencies: "@types/history": ^4.7.11 "@types/react": "*" @@ -2108,13 +2108,13 @@ __metadata: peerDependencies: react: ^16.8.4 || ^17.0.0 react-dom: ^16.8.4 || ^17.0.0 - checksum: bbd1b3176fff19109e093f542577a2126018665d6097cd77c312906ccf5d238aa8d4499d3f70eecac7777bd40c2afbecad7a0822399aafa1cf26b093ff49a38c + checksum: 6ea7a688f7cef509e0f3b5ab2a9bb9fb0841ffd033d82438b989a70344655a7420b456f5172be9aa13740316212970e4d9d3bc355eb5fd4c9b27c635baeb149a languageName: node linkType: hard -"@docusaurus/utils-common@npm:0.0.0-5589": - version: 0.0.0-5589 - resolution: "@docusaurus/utils-common@npm:0.0.0-5589" +"@docusaurus/utils-common@npm:0.0.0-5591": + version: 0.0.0-5591 + resolution: "@docusaurus/utils-common@npm:0.0.0-5591" dependencies: tslib: ^2.5.0 peerDependencies: @@ -2122,28 +2122,28 @@ __metadata: peerDependenciesMeta: "@docusaurus/types": optional: true - checksum: 6e9bc8e74d50cc4eb3a908e5ac9d83c31527731da122b8a0c3bab04ffda3ac90f898af5957fe81daba5d6fa5554628eedade5f0ebcc8b7b665dfbb2e21e797c9 + checksum: 6c21dac13338854bfaebef0a98b1c76a95f29cc16ae6cd43fac0734dbc16cec0df058339af7ebb6ca3dc3cd2ad2a21f4bbff221c9cf7ae5012a88bfc4b28f4d9 languageName: node linkType: hard -"@docusaurus/utils-validation@npm:0.0.0-5589": - version: 0.0.0-5589 - resolution: "@docusaurus/utils-validation@npm:0.0.0-5589" +"@docusaurus/utils-validation@npm:0.0.0-5591": + version: 0.0.0-5591 + resolution: "@docusaurus/utils-validation@npm:0.0.0-5591" dependencies: - "@docusaurus/logger": 0.0.0-5589 - "@docusaurus/utils": 0.0.0-5589 + "@docusaurus/logger": 0.0.0-5591 + "@docusaurus/utils": 0.0.0-5591 joi: ^17.8.3 js-yaml: ^4.1.0 tslib: ^2.5.0 - checksum: 3a76d9eecf155044aab6648bbcb9ff42468856e8ebe1f1f43f8a993214bc26d8f5c5f059c98bf22f5e3e1370cba491bc909124e0f1317be9b3515e3b09f9c8ad + checksum: 987acdce5ae5ce4c5bd78258201809889209d7293b063eb38888637452c80ecff72d12d84a7ce7fc49f52d61ca2a79c61006f3562b4180e379a1777b9d76493a languageName: node linkType: hard -"@docusaurus/utils@npm:0.0.0-5589": - version: 0.0.0-5589 - resolution: "@docusaurus/utils@npm:0.0.0-5589" +"@docusaurus/utils@npm:0.0.0-5591": + version: 0.0.0-5591 + resolution: "@docusaurus/utils@npm:0.0.0-5591" dependencies: - "@docusaurus/logger": 0.0.0-5589 + "@docusaurus/logger": 0.0.0-5591 "@svgr/webpack": ^6.5.1 escape-string-regexp: ^4.0.0 file-loader: ^6.2.0 @@ -2164,7 +2164,7 @@ __metadata: peerDependenciesMeta: "@docusaurus/types": optional: true - checksum: d745a4a2f01a77d533af48fd72ca4eacec0b4852b2a230aac2f326e8a5adeb7152759d25569d7aedba1cd520842897136d4c03aaa943b9e1e33479f09006deb5 + checksum: 287d991f7a1924df744ed3a5c0d505a5b903b8bd43df39aac3c45fcc139639fb5b7827d12e4e00787126ad216006483723390141eb283ab733e4b6de819f5cd5 languageName: node linkType: hard @@ -3752,10 +3752,10 @@ __metadata: version: 0.0.0-use.local resolution: "backstage-microsite@workspace:." dependencies: - "@docusaurus/core": 0.0.0-5589 - "@docusaurus/module-type-aliases": 0.0.0-5589 - "@docusaurus/plugin-client-redirects": 0.0.0-5589 - "@docusaurus/preset-classic": 0.0.0-5589 + "@docusaurus/core": 0.0.0-5591 + "@docusaurus/module-type-aliases": 0.0.0-5591 + "@docusaurus/plugin-client-redirects": 0.0.0-5591 + "@docusaurus/preset-classic": 0.0.0-5591 "@spotify/prettier-config": ^14.0.0 "@swc/core": ^1.3.46 "@tsconfig/docusaurus": ^1.0.6 From 43dc492bc4392c49364ad8a99eb8db5c3e4d0b0c Mon Sep 17 00:00:00 2001 From: Eric Peterson Date: Wed, 31 May 2023 18:40:00 +0200 Subject: [PATCH 17/65] Document URL Reader export-ignore limitations Signed-off-by: Eric Peterson --- docs/features/techdocs/troubleshooting.md | 21 +++++++++++++++++---- docs/plugins/url-reader.md | 10 ++++++++++ 2 files changed, 27 insertions(+), 4 deletions(-) diff --git a/docs/features/techdocs/troubleshooting.md b/docs/features/techdocs/troubleshooting.md index d8b413be5c..3f0daba101 100644 --- a/docs/features/techdocs/troubleshooting.md +++ b/docs/features/techdocs/troubleshooting.md @@ -5,11 +5,24 @@ sidebar_label: Troubleshooting description: Troubleshooting for TechDocs --- -## Failure to clone +## Documentation not found when generating -TechDocs will fail to clone your docs if you have a git config which overrides -the `https` protocol with `ssh` or something else. Make sure to remove your git -config locally when you try TechDocs. +This may happen if you have TechDocs set up using the "out-of-the-box" +configuration, wherein documentation is built dynamically by the TechDocs +backend, and your TechDocs files are being pulled from a git-based source +control management system (e.g. GitHub, BitBucket, etc). + +If you experience this, check that TechDocs-related files (e.g. markdown, +assets, or the `mkdocs.yml` file) are not matched by an `export-ignore` +attribute in a `.gitattributes` file in the relevant repository. + +TechDocs' backend is not able to see such files, and therefore may generate +partial (or no) TechDocs as a result. + +You'll need to reconsider how you distribute tar archives based on your source +code (and how you prevent internal documentation from being included in those +archives). Alternatively, you could consider switching to the "recommended" +TechDocs architecture (documentation generated and published in CI/CD). ## MkDocs Build Errors diff --git a/docs/plugins/url-reader.md b/docs/plugins/url-reader.md index fa9c341543..c8ff18952c 100644 --- a/docs/plugins/url-reader.md +++ b/docs/plugins/url-reader.md @@ -106,6 +106,16 @@ directly be used with a URL. Some example usages - Catalog using the `search` method to find files for a location URL containing a glob pattern. +Note that URL Readers which target git-based version control systems may, under +the hood, leverage the ability to create tar archives based on a specific git +commit-ish. A consequence of this is that files and directories configured with +[the `export-ignore` attribute](https://git-scm.com/docs/gitattributes#_creating_an_archive) +via `.gitattributes` will not be visible to the URL reader when using the +`readTree` or `search` methods. + +Be aware of this limitation and ensure that end-users of your plugin are also +aware via, for example, documentation. + ## Writing a new URL Reader If the available URL Readers are not sufficient for your use case and you want From 0eede913b7d9d1705944af875b32fc00ba9731e0 Mon Sep 17 00:00:00 2001 From: Hayden Spitzley <105455169+hspitzley-czi@users.noreply.github.com> Date: Thu, 1 Jun 2023 09:22:13 -0400 Subject: [PATCH 18/65] Update .changeset/perfect-donkeys-cry.md Co-authored-by: Patrik Oldsberg Signed-off-by: Hayden Spitzley <105455169+hspitzley-czi@users.noreply.github.com> --- .changeset/perfect-donkeys-cry.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/.changeset/perfect-donkeys-cry.md b/.changeset/perfect-donkeys-cry.md index 83eafe69ca..744dc19d64 100644 --- a/.changeset/perfect-donkeys-cry.md +++ b/.changeset/perfect-donkeys-cry.md @@ -2,4 +2,4 @@ '@backstage/core-components': patch --- -Add option to require exact matching for isLocationMatch +Added `exact` prop to `SidebarSubmenuItem` which causes it to only highlight if the current location is an exact match. From d68692aee97ed33f4d4d12b0b36bdb497c006dbb Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Fredrik=20Adel=C3=B6w?= Date: Thu, 1 Jun 2023 17:15:33 +0200 Subject: [PATCH 19/65] Make useRelatedEntities use getEntitiesByRefs under the hood MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Signed-off-by: Fredrik Adelöw --- .changeset/mean-insects-hope.md | 5 ++ plugins/catalog-react/api-report.md | 2 +- .../src/hooks/useRelatedEntities.test.tsx | 84 +++++++++++++++++++ .../src/hooks/useRelatedEntities.ts | 77 +++++------------ 4 files changed, 110 insertions(+), 58 deletions(-) create mode 100644 .changeset/mean-insects-hope.md create mode 100644 plugins/catalog-react/src/hooks/useRelatedEntities.test.tsx diff --git a/.changeset/mean-insects-hope.md b/.changeset/mean-insects-hope.md new file mode 100644 index 0000000000..0a71a9c1ee --- /dev/null +++ b/.changeset/mean-insects-hope.md @@ -0,0 +1,5 @@ +--- +'@backstage/plugin-catalog-react': patch +--- + +Make `useRelatedEntities` use `getEntitiesByRefs` under the hood diff --git a/plugins/catalog-react/api-report.md b/plugins/catalog-react/api-report.md index 90bddecd71..2fab514de1 100644 --- a/plugins/catalog-react/api-report.md +++ b/plugins/catalog-react/api-report.md @@ -555,7 +555,7 @@ export function useEntityTypeFilter(): { setSelectedTypes: (types: string[]) => void; }; -// @public (undocumented) +// @public export function useRelatedEntities( entity: Entity, relationFilter: { diff --git a/plugins/catalog-react/src/hooks/useRelatedEntities.test.tsx b/plugins/catalog-react/src/hooks/useRelatedEntities.test.tsx new file mode 100644 index 0000000000..0d415274e0 --- /dev/null +++ b/plugins/catalog-react/src/hooks/useRelatedEntities.test.tsx @@ -0,0 +1,84 @@ +/* + * Copyright 2023 The Backstage Authors + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +import { Entity } from '@backstage/catalog-model'; +import { TestApiProvider } from '@backstage/test-utils'; +import { WrapperComponent, renderHook } from '@testing-library/react-hooks'; +import React from 'react'; +import { catalogApiRef } from '../api'; +import { useRelatedEntities } from './useRelatedEntities'; + +describe('useRelatedEntities', () => { + afterEach(() => { + jest.resetAllMocks(); + }); + + const entity: Entity = { + apiVersion: 'backstage.io/v1alpha1', + kind: 'Component', + metadata: { name: 'test' }, + relations: [ + { + type: 'ownedBy', + targetRef: 'group:default/the-owners-1', + }, + { + type: 'ownedBy', + targetRef: 'group:default/the-owners-2', + }, + { + type: 'partOf', + targetRef: 'component:default/larger-thing', + }, + ], + }; + + const catalogApi = { + getEntitiesByRefs: jest.fn(), + }; + + const wrapper: WrapperComponent<{}> = ({ children }) => { + return ( + + {children} + + ); + }; + + it('filters and requests entities', async () => { + catalogApi.getEntitiesByRefs.mockResolvedValueOnce({ + items: [entity, null], // one of them doesn't exist + }); + + const rendered = renderHook( + () => useRelatedEntities(entity, { type: 'ownedby', kind: 'grOUP' }), + { wrapper }, + ); + + expect(rendered.result.current).toEqual({ loading: true }); + + await rendered.waitForValueToChange(() => rendered.result.current.loading); + + expect(catalogApi.getEntitiesByRefs).toHaveBeenCalledWith({ + entityRefs: ['group:default/the-owners-1', 'group:default/the-owners-2'], + }); + + expect(rendered.result.current).toEqual({ + loading: false, + entities: [entity], // filtered out the null + }); + }); +}); diff --git a/plugins/catalog-react/src/hooks/useRelatedEntities.ts b/plugins/catalog-react/src/hooks/useRelatedEntities.ts index 4cf5690ac3..7ec0a13d53 100644 --- a/plugins/catalog-react/src/hooks/useRelatedEntities.ts +++ b/plugins/catalog-react/src/hooks/useRelatedEntities.ts @@ -13,15 +13,18 @@ * See the License for the specific language governing permissions and * limitations under the License. */ + import { Entity, parseEntityRef } from '@backstage/catalog-model'; import { useApi } from '@backstage/core-plugin-api'; -import { chunk, groupBy } from 'lodash'; import useAsync from 'react-use/lib/useAsync'; import { catalogApiRef } from '../api'; -const BATCH_SIZE = 20; - -/** @public */ +/** + * Fetches all entities that appear in the entity's relations, optionally + * filtered by relation type and kind. + * + * @public + */ export function useRelatedEntities( entity: Entity, relationFilter: { type?: string; kind?: string }, @@ -32,70 +35,30 @@ export function useRelatedEntities( } { const filterByTypeLower = relationFilter?.type?.toLocaleLowerCase('en-US'); const filterByKindLower = relationFilter?.kind?.toLocaleLowerCase('en-US'); - const catalogApi = useApi(catalogApiRef); + const { loading, value: entities, error, } = useAsync(async () => { - const relations = entity.relations - ?.map(r => ({ type: r.type, target: parseEntityRef(r.targetRef) })) - .filter( - r => - (!filterByTypeLower || - r.type.toLocaleLowerCase('en-US') === filterByTypeLower) && - (!filterByKindLower || r.target.kind === filterByKindLower), - ); + const relations = entity.relations?.filter( + r => + (!filterByTypeLower || + r.type.toLocaleLowerCase('en-US') === filterByTypeLower) && + (!filterByKindLower || + parseEntityRef(r.targetRef).kind === filterByKindLower), + ); - if (!relations) { + if (!relations?.length) { return []; } - // Group the relations by kind and namespace to reduce the size of the request query string. - // Without this grouping, the kind and namespace would need to be specified for each relation, e.g. - // `filter=kind=component,namespace=default,name=example1&filter=kind=component,namespace=default,name=example2` - // with grouping, we can generate a query a string like - // `filter=kind=component,namespace=default,name=example1,example2` - const relationsByKindAndNamespace = Object.values( - groupBy(relations, ({ target }) => { - return `${target.kind}:${target.namespace}`.toLocaleLowerCase('en-US'); - }), - ); + const { items } = await catalogApi.getEntitiesByRefs({ + entityRefs: relations.map(r => r.targetRef), + }); - // Split the names within each group into batches to further reduce the query string length. - const batchedRelationsByKindAndNamespace: { - kind: string; - namespace: string; - nameBatches: string[][]; - }[] = []; - for (const rs of relationsByKindAndNamespace) { - batchedRelationsByKindAndNamespace.push({ - // All relations in a group have the same kind and namespace, so its arbitrary which we pick - kind: rs[0].target.kind, - namespace: rs[0].target.namespace, - nameBatches: chunk( - rs.map(r => r.target.name), - BATCH_SIZE, - ), - }); - } - - const results = await Promise.all( - batchedRelationsByKindAndNamespace.flatMap(rs => { - return rs.nameBatches.map(names => { - return catalogApi.getEntities({ - filter: { - kind: rs.kind, - 'metadata.namespace': rs.namespace, - 'metadata.name': names, - }, - }); - }); - }), - ); - - return results.flatMap(r => r.items); + return items.filter((x): x is Entity => Boolean(x)); }, [entity, filterByTypeLower, filterByKindLower]); return { From 5ecc3d7865f81e6989064d4543c1f9eca56d980f Mon Sep 17 00:00:00 2001 From: Carlos Esteban Lopez Date: Thu, 1 Jun 2023 16:37:40 -0500 Subject: [PATCH 20/65] fix(catalog-import): Fix stepper component order. Signed-off-by: Carlos Esteban Lopez --- .../components/DefaultImportPage/DefaultImportPage.tsx | 10 +++++----- 1 file changed, 5 insertions(+), 5 deletions(-) diff --git a/plugins/catalog-import/src/components/DefaultImportPage/DefaultImportPage.tsx b/plugins/catalog-import/src/components/DefaultImportPage/DefaultImportPage.tsx index 30cce9603a..f0c9d3c33a 100644 --- a/plugins/catalog-import/src/components/DefaultImportPage/DefaultImportPage.tsx +++ b/plugins/catalog-import/src/components/DefaultImportPage/DefaultImportPage.tsx @@ -47,14 +47,14 @@ export const DefaultImportPage = () => { - - - - - + + + + + From 309d2973adb4ef526fc0bd58508caefe19b2a029 Mon Sep 17 00:00:00 2001 From: Carlos Esteban Lopez Date: Thu, 1 Jun 2023 16:45:09 -0500 Subject: [PATCH 21/65] fix(catalog-import): Add changeset Signed-off-by: Carlos Esteban Lopez --- .changeset/cold-pillows-mix.md | 5 +++++ 1 file changed, 5 insertions(+) create mode 100644 .changeset/cold-pillows-mix.md diff --git a/.changeset/cold-pillows-mix.md b/.changeset/cold-pillows-mix.md new file mode 100644 index 0000000000..12dc9422aa --- /dev/null +++ b/.changeset/cold-pillows-mix.md @@ -0,0 +1,5 @@ +--- +'@backstage/plugin-catalog-import': patch +--- + +Swap `ImportStepper` and `InfoCard` order to fix tab order in `catalog-import`. From 1aecd7e3811c27841ef849a4c35f94f156b1d111 Mon Sep 17 00:00:00 2001 From: Carlos Esteban Lopez Date: Thu, 1 Jun 2023 17:24:36 -0500 Subject: [PATCH 22/65] fix(catalog-import): Use media queries to sort content order Signed-off-by: Carlos Esteban Lopez --- .../DefaultImportPage/DefaultImportPage.tsx | 22 ++++++++++++------- 1 file changed, 14 insertions(+), 8 deletions(-) diff --git a/plugins/catalog-import/src/components/DefaultImportPage/DefaultImportPage.tsx b/plugins/catalog-import/src/components/DefaultImportPage/DefaultImportPage.tsx index f0c9d3c33a..c777953808 100644 --- a/plugins/catalog-import/src/components/DefaultImportPage/DefaultImportPage.tsx +++ b/plugins/catalog-import/src/components/DefaultImportPage/DefaultImportPage.tsx @@ -22,7 +22,7 @@ import { SupportButton, } from '@backstage/core-components'; import { configApiRef, useApi } from '@backstage/core-plugin-api'; -import { Grid } from '@material-ui/core'; +import { Grid, useMediaQuery, useTheme } from '@material-ui/core'; import React from 'react'; import { ImportInfoCard } from '../ImportInfoCard'; import { ImportStepper } from '../ImportStepper'; @@ -33,9 +33,21 @@ import { ImportStepper } from '../ImportStepper'; * @public */ export const DefaultImportPage = () => { + const theme = useTheme(); const configApi = useApi(configApiRef); + const isMobile = useMediaQuery(theme.breakpoints.down('sm')); const appTitle = configApi.getOptional('app.title') || 'Backstage'; + const contentItems = [ + + + , + + + + , + ]; + return (
@@ -48,13 +60,7 @@ export const DefaultImportPage = () => { - - - - - - - + {isMobile ? contentItems : contentItems.reverse()} From 47b01e4c5315fce331a114a1ccda06badd883f98 Mon Sep 17 00:00:00 2001 From: Carlos Esteban Lopez Date: Thu, 1 Jun 2023 19:45:34 -0500 Subject: [PATCH 23/65] fix(catalog): EntityContextMenu now focus visible the first element. Signed-off-by: Carlos Esteban Lopez --- .changeset/warm-hornets-fetch.md | 5 +++++ .../src/components/EntityContextMenu/EntityContextMenu.tsx | 2 +- 2 files changed, 6 insertions(+), 1 deletion(-) create mode 100644 .changeset/warm-hornets-fetch.md diff --git a/.changeset/warm-hornets-fetch.md b/.changeset/warm-hornets-fetch.md new file mode 100644 index 0000000000..eb84a72f0a --- /dev/null +++ b/.changeset/warm-hornets-fetch.md @@ -0,0 +1,5 @@ +--- +'@backstage/plugin-catalog': patch +--- + +Keyboard navigation to open EntityContextMenu now focus visible the first element. diff --git a/plugins/catalog/src/components/EntityContextMenu/EntityContextMenu.tsx b/plugins/catalog/src/components/EntityContextMenu/EntityContextMenu.tsx index 1961fe6cac..5e6e8ff3a9 100644 --- a/plugins/catalog/src/components/EntityContextMenu/EntityContextMenu.tsx +++ b/plugins/catalog/src/components/EntityContextMenu/EntityContextMenu.tsx @@ -142,7 +142,7 @@ export function EntityContextMenu(props: EntityContextMenuProps) { transformOrigin={{ vertical: 'top', horizontal: 'right' }} aria-labelledby="long-menu" > - + {extraItems} Date: Fri, 2 Jun 2023 12:30:25 +0530 Subject: [PATCH 24/65] fix-18035 Signed-off-by: npiyush97 --- .changeset/gorgeous-timers-act.md | 5 ++ .../GitlabOrgDiscoveryEntityProvider.test.ts | 67 +++++++++++++++++++ .../GitlabOrgDiscoveryEntityProvider.ts | 2 +- 3 files changed, 73 insertions(+), 1 deletion(-) create mode 100644 .changeset/gorgeous-timers-act.md diff --git a/.changeset/gorgeous-timers-act.md b/.changeset/gorgeous-timers-act.md new file mode 100644 index 0000000000..25b6b0f1f0 --- /dev/null +++ b/.changeset/gorgeous-timers-act.md @@ -0,0 +1,5 @@ +--- +'@backstage/plugin-catalog-backend-module-gitlab': minor +--- + +added test if user does not have name or profile picture,variable default to undefined diff --git a/plugins/catalog-backend-module-gitlab/src/providers/GitlabOrgDiscoveryEntityProvider.test.ts b/plugins/catalog-backend-module-gitlab/src/providers/GitlabOrgDiscoveryEntityProvider.test.ts index 3d6ff0a91a..e29cdccc04 100644 --- a/plugins/catalog-backend-module-gitlab/src/providers/GitlabOrgDiscoveryEntityProvider.test.ts +++ b/plugins/catalog-backend-module-gitlab/src/providers/GitlabOrgDiscoveryEntityProvider.test.ts @@ -264,6 +264,48 @@ describe('GitlabOrgDiscoveryEntityProvider', () => { is_admin: false, note: '', }, + { + id: 2, + username: 'test2', + name: '', + state: 'active', + avatar_url: '', + web_url: 'https://gitlab.example/test2', + created_at: '2023-01-19T07:27:03.333Z', + bio: '', + location: null, + public_email: null, + skype: '', + linkedin: '', + twitter: '', + website_url: '', + organization: null, + job_title: '', + pronouns: null, + bot: false, + work_information: null, + followers: 0, + following: 0, + is_followed: false, + local_time: null, + last_sign_in_at: '2023-01-19T07:27:49.601Z', + confirmed_at: '2023-01-19T07:27:02.905Z', + last_activity_on: '2023-01-19', + email: 'test@example.com', + theme_id: 1, + color_scheme_id: 1, + projects_limit: 100000, + current_sign_in_at: '2023-01-19T09:09:10.676Z', + identities: [], + can_create_group: true, + can_create_project: true, + two_factor_enabled: false, + external: false, + private_profile: false, + commit_email: 'test@example.com', + is_admin: false, + note: '', + }, ]; return res(ctx.json(response)); }), @@ -374,6 +416,31 @@ describe('GitlabOrgDiscoveryEntityProvider', () => { }, locationKey: 'GitlabOrgDiscoveryEntityProvider:test-id', }, + { + entity: { + apiVersion: 'backstage.io/v1alpha1', + kind: 'User', + metadata: { + annotations: { + 'backstage.io/managed-by-location': + 'url:https://test-gitlab/test2', + 'backstage.io/managed-by-origin-location': + 'url:https://test-gitlab/test2', + 'test-gitlab/user-login': 'https://gitlab.example/test2', + }, + name: 'test2', + }, + spec: { + memberOf: [], + profile: { + displayName: undefined, + email: 'test@example.com', + picture: undefined, + }, + }, + }, + locationKey: 'GitlabOrgDiscoveryEntityProvider:test-id', + }, { entity: { apiVersion: 'backstage.io/v1alpha1', diff --git a/plugins/catalog-backend-module-gitlab/src/providers/GitlabOrgDiscoveryEntityProvider.ts b/plugins/catalog-backend-module-gitlab/src/providers/GitlabOrgDiscoveryEntityProvider.ts index 59de3ac30b..02c036f27a 100644 --- a/plugins/catalog-backend-module-gitlab/src/providers/GitlabOrgDiscoveryEntityProvider.ts +++ b/plugins/catalog-backend-module-gitlab/src/providers/GitlabOrgDiscoveryEntityProvider.ts @@ -319,7 +319,7 @@ export class GitlabOrgDiscoveryEntityProvider implements EntityProvider { }, spec: { profile: { - displayName: user.name, + displayName: user.name || undefined, picture: user.avatar_url || undefined, }, memberOf: [], From 229aac606406ab9a3ec86ab169c4f6df5fec6971 Mon Sep 17 00:00:00 2001 From: PIYUSH NEGI <43876655+npiyush97@users.noreply.github.com> Date: Fri, 2 Jun 2023 13:43:19 +0530 Subject: [PATCH 25/65] Update .changeset/gorgeous-timers-act.md Co-authored-by: Johan Haals Signed-off-by: PIYUSH NEGI <43876655+npiyush97@users.noreply.github.com> --- .changeset/gorgeous-timers-act.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/.changeset/gorgeous-timers-act.md b/.changeset/gorgeous-timers-act.md index 25b6b0f1f0..fd70548d5c 100644 --- a/.changeset/gorgeous-timers-act.md +++ b/.changeset/gorgeous-timers-act.md @@ -1,5 +1,5 @@ --- -'@backstage/plugin-catalog-backend-module-gitlab': minor +'@backstage/plugin-catalog-backend-module-gitlab': patch --- added test if user does not have name or profile picture,variable default to undefined From e354048b093666697e8965f42720e0856a8c7b78 Mon Sep 17 00:00:00 2001 From: PIYUSH NEGI <43876655+npiyush97@users.noreply.github.com> Date: Fri, 2 Jun 2023 13:43:36 +0530 Subject: [PATCH 26/65] Update .changeset/gorgeous-timers-act.md Co-authored-by: Johan Haals Signed-off-by: PIYUSH NEGI <43876655+npiyush97@users.noreply.github.com> --- .changeset/gorgeous-timers-act.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/.changeset/gorgeous-timers-act.md b/.changeset/gorgeous-timers-act.md index fd70548d5c..130ed5085f 100644 --- a/.changeset/gorgeous-timers-act.md +++ b/.changeset/gorgeous-timers-act.md @@ -2,4 +2,4 @@ '@backstage/plugin-catalog-backend-module-gitlab': patch --- -added test if user does not have name or profile picture,variable default to undefined +Fixed bug that caused ingestion errors when a user's name or profile picture is undefined. From 8afb3dcf0a937f388114cd2c9ee39e1d72c9f049 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Fredrik=20Adel=C3=B6w?= Date: Fri, 2 Jun 2023 14:04:41 +0200 Subject: [PATCH 27/65] fix tests MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Signed-off-by: Fredrik Adelöw --- .../src/components/ApisCards/ConsumedApisCard.test.tsx | 9 ++------- .../src/components/ApisCards/HasApisCard.test.tsx | 9 ++------- .../src/components/ApisCards/ProvidedApisCard.test.tsx | 9 ++------- .../ComponentsCards/ConsumingComponentsCard.test.tsx | 9 ++------- .../ComponentsCards/ProvidingComponentsCard.test.tsx | 9 ++------- .../DependencyOfComponentsCard.test.tsx | 8 +++++--- .../DependsOnComponentsCard.test.tsx | 8 +++++--- .../DependsOnResourcesCard.test.tsx | 8 +++++--- .../HasComponentsCard/HasComponentsCard.test.tsx | 8 +++++--- .../HasResourcesCard/HasResourcesCard.test.tsx | 8 +++++--- .../HasSubcomponentsCard/HasSubcomponentsCard.test.tsx | 8 +++++--- .../components/HasSystemsCard/HasSystemsCard.test.tsx | 8 +++++--- 12 files changed, 45 insertions(+), 56 deletions(-) diff --git a/plugins/api-docs/src/components/ApisCards/ConsumedApisCard.test.tsx b/plugins/api-docs/src/components/ApisCards/ConsumedApisCard.test.tsx index ea51d3989d..d664ce78e8 100644 --- a/plugins/api-docs/src/components/ApisCards/ConsumedApisCard.test.tsx +++ b/plugins/api-docs/src/components/ApisCards/ConsumedApisCard.test.tsx @@ -32,12 +32,7 @@ describe('', () => { getApiDefinitionWidget: jest.fn(), } as any; const catalogApi: jest.Mocked = { - getLocationById: jest.fn(), - getEntityByName: jest.fn(), - getEntities: jest.fn(), - addLocation: jest.fn(), - getLocationByRef: jest.fn(), - removeEntityByUid: jest.fn(), + getEntitiesByRefs: jest.fn(), } as any; let Wrapper: React.ComponentType>; @@ -99,7 +94,7 @@ describe('', () => { }, ], }; - catalogApi.getEntities.mockResolvedValue({ + catalogApi.getEntitiesByRefs.mockResolvedValue({ items: [ { apiVersion: 'v1', diff --git a/plugins/api-docs/src/components/ApisCards/HasApisCard.test.tsx b/plugins/api-docs/src/components/ApisCards/HasApisCard.test.tsx index 6ab55c5c66..169311d0c8 100644 --- a/plugins/api-docs/src/components/ApisCards/HasApisCard.test.tsx +++ b/plugins/api-docs/src/components/ApisCards/HasApisCard.test.tsx @@ -32,12 +32,7 @@ describe('', () => { getApiDefinitionWidget: jest.fn(), } as any; const catalogApi: jest.Mocked = { - getLocationById: jest.fn(), - getEntityByName: jest.fn(), - getEntities: jest.fn(), - addLocation: jest.fn(), - getLocationByRef: jest.fn(), - removeEntityByUid: jest.fn(), + getEntitiesByRefs: jest.fn(), } as any; let Wrapper: React.ComponentType>; @@ -99,7 +94,7 @@ describe('', () => { }, ], }; - catalogApi.getEntities.mockResolvedValue({ + catalogApi.getEntitiesByRefs.mockResolvedValue({ items: [ { apiVersion: 'v1', diff --git a/plugins/api-docs/src/components/ApisCards/ProvidedApisCard.test.tsx b/plugins/api-docs/src/components/ApisCards/ProvidedApisCard.test.tsx index 5f69e90f9f..3dbc4edd63 100644 --- a/plugins/api-docs/src/components/ApisCards/ProvidedApisCard.test.tsx +++ b/plugins/api-docs/src/components/ApisCards/ProvidedApisCard.test.tsx @@ -32,12 +32,7 @@ describe('', () => { getApiDefinitionWidget: jest.fn(), } as any; const catalogApi: jest.Mocked = { - getLocationById: jest.fn(), - getEntityByName: jest.fn(), - getEntities: jest.fn(), - addLocation: jest.fn(), - getLocationByRef: jest.fn(), - removeEntityByUid: jest.fn(), + getEntitiesByRefs: jest.fn(), } as any; let Wrapper: React.ComponentType>; @@ -99,7 +94,7 @@ describe('', () => { }, ], }; - catalogApi.getEntities.mockResolvedValue({ + catalogApi.getEntitiesByRefs.mockResolvedValue({ items: [ { apiVersion: 'v1', diff --git a/plugins/api-docs/src/components/ComponentsCards/ConsumingComponentsCard.test.tsx b/plugins/api-docs/src/components/ComponentsCards/ConsumingComponentsCard.test.tsx index f7a18cf671..20a60562b0 100644 --- a/plugins/api-docs/src/components/ComponentsCards/ConsumingComponentsCard.test.tsx +++ b/plugins/api-docs/src/components/ComponentsCards/ConsumingComponentsCard.test.tsx @@ -28,12 +28,7 @@ import { ConsumingComponentsCard } from './ConsumingComponentsCard'; describe('', () => { const catalogApi: jest.Mocked = { - getLocationById: jest.fn(), - getEntityByName: jest.fn(), - getEntities: jest.fn(), - addLocation: jest.fn(), - getLocationByRef: jest.fn(), - removeEntityByUid: jest.fn(), + getEntitiesByRefs: jest.fn(), } as any; let Wrapper: React.ComponentType>; @@ -102,7 +97,7 @@ describe('', () => { }, ], }; - catalogApi.getEntities.mockResolvedValue({ + catalogApi.getEntitiesByRefs.mockResolvedValue({ items: [ { apiVersion: 'v1', diff --git a/plugins/api-docs/src/components/ComponentsCards/ProvidingComponentsCard.test.tsx b/plugins/api-docs/src/components/ComponentsCards/ProvidingComponentsCard.test.tsx index 8b003bf2e2..0801d7103a 100644 --- a/plugins/api-docs/src/components/ComponentsCards/ProvidingComponentsCard.test.tsx +++ b/plugins/api-docs/src/components/ComponentsCards/ProvidingComponentsCard.test.tsx @@ -28,12 +28,7 @@ import { ProvidingComponentsCard } from './ProvidingComponentsCard'; describe('', () => { const catalogApi: jest.Mocked = { - getLocationById: jest.fn(), - getEntityByName: jest.fn(), - getEntities: jest.fn(), - addLocation: jest.fn(), - getLocationByRef: jest.fn(), - removeEntityByUid: jest.fn(), + getEntitiesByRefs: jest.fn(), } as any; let Wrapper: React.ComponentType>; @@ -102,7 +97,7 @@ describe('', () => { }, ], }; - catalogApi.getEntities.mockResolvedValue({ + catalogApi.getEntitiesByRefs.mockResolvedValue({ items: [ { apiVersion: 'v1', diff --git a/plugins/catalog/src/components/DependencyOfComponentsCard/DependencyOfComponentsCard.test.tsx b/plugins/catalog/src/components/DependencyOfComponentsCard/DependencyOfComponentsCard.test.tsx index e5900d75e0..0ebda6e64d 100644 --- a/plugins/catalog/src/components/DependencyOfComponentsCard/DependencyOfComponentsCard.test.tsx +++ b/plugins/catalog/src/components/DependencyOfComponentsCard/DependencyOfComponentsCard.test.tsx @@ -27,12 +27,14 @@ import React from 'react'; import { DependencyOfComponentsCard } from './DependencyOfComponentsCard'; describe('', () => { - const getEntities: jest.MockedFunction = jest.fn(); + const getEntitiesByRefs: jest.MockedFunction< + CatalogApi['getEntitiesByRefs'] + > = jest.fn(); let Wrapper: React.ComponentType>; beforeEach(() => { Wrapper = ({ children }: { children?: React.ReactNode }) => ( - + {children} ); @@ -85,7 +87,7 @@ describe('', () => { }, ], }; - getEntities.mockResolvedValue({ + getEntitiesByRefs.mockResolvedValue({ items: [ { apiVersion: 'v1', diff --git a/plugins/catalog/src/components/DependsOnComponentsCard/DependsOnComponentsCard.test.tsx b/plugins/catalog/src/components/DependsOnComponentsCard/DependsOnComponentsCard.test.tsx index 9255ee4f36..ee8931143f 100644 --- a/plugins/catalog/src/components/DependsOnComponentsCard/DependsOnComponentsCard.test.tsx +++ b/plugins/catalog/src/components/DependsOnComponentsCard/DependsOnComponentsCard.test.tsx @@ -27,12 +27,14 @@ import React from 'react'; import { DependsOnComponentsCard } from './DependsOnComponentsCard'; describe('', () => { - const getEntities: jest.MockedFunction = jest.fn(); + const getEntitiesByRefs: jest.MockedFunction< + CatalogApi['getEntitiesByRefs'] + > = jest.fn(); let Wrapper: React.ComponentType>; beforeEach(() => { Wrapper = ({ children }: { children?: React.ReactNode }) => ( - + {children} ); @@ -85,7 +87,7 @@ describe('', () => { }, ], }; - getEntities.mockResolvedValue({ + getEntitiesByRefs.mockResolvedValue({ items: [ { apiVersion: 'v1', diff --git a/plugins/catalog/src/components/DependsOnResourcesCard/DependsOnResourcesCard.test.tsx b/plugins/catalog/src/components/DependsOnResourcesCard/DependsOnResourcesCard.test.tsx index 3b0d7dcff3..0e760f9155 100644 --- a/plugins/catalog/src/components/DependsOnResourcesCard/DependsOnResourcesCard.test.tsx +++ b/plugins/catalog/src/components/DependsOnResourcesCard/DependsOnResourcesCard.test.tsx @@ -27,12 +27,14 @@ import React from 'react'; import { DependsOnResourcesCard } from './DependsOnResourcesCard'; describe('', () => { - const getEntities: jest.MockedFunction = jest.fn(); + const getEntitiesByRefs: jest.MockedFunction< + CatalogApi['getEntitiesByRefs'] + > = jest.fn(); let Wrapper: React.ComponentType>; beforeEach(() => { Wrapper = ({ children }: { children?: React.ReactNode }) => ( - + {children} ); @@ -85,7 +87,7 @@ describe('', () => { }, ], }; - getEntities.mockResolvedValue({ + getEntitiesByRefs.mockResolvedValue({ items: [ { apiVersion: 'v1', diff --git a/plugins/catalog/src/components/HasComponentsCard/HasComponentsCard.test.tsx b/plugins/catalog/src/components/HasComponentsCard/HasComponentsCard.test.tsx index 3651421797..67c3f6b650 100644 --- a/plugins/catalog/src/components/HasComponentsCard/HasComponentsCard.test.tsx +++ b/plugins/catalog/src/components/HasComponentsCard/HasComponentsCard.test.tsx @@ -27,12 +27,14 @@ import React from 'react'; import { HasComponentsCard } from './HasComponentsCard'; describe('', () => { - const getEntities: jest.MockedFunction = jest.fn(); + const getEntitiesByRefs: jest.MockedFunction< + CatalogApi['getEntitiesByRefs'] + > = jest.fn(); let Wrapper: React.ComponentType>; beforeEach(() => { Wrapper = ({ children }: { children?: React.ReactNode }) => ( - + {children} ); @@ -85,7 +87,7 @@ describe('', () => { }, ], }; - getEntities.mockResolvedValue({ + getEntitiesByRefs.mockResolvedValue({ items: [ { apiVersion: 'v1', diff --git a/plugins/catalog/src/components/HasResourcesCard/HasResourcesCard.test.tsx b/plugins/catalog/src/components/HasResourcesCard/HasResourcesCard.test.tsx index 4bf6524a9c..d78d307c96 100644 --- a/plugins/catalog/src/components/HasResourcesCard/HasResourcesCard.test.tsx +++ b/plugins/catalog/src/components/HasResourcesCard/HasResourcesCard.test.tsx @@ -27,12 +27,14 @@ import React from 'react'; import { HasResourcesCard } from './HasResourcesCard'; describe('', () => { - const getEntities: jest.MockedFunction = jest.fn(); + const getEntitiesByRefs: jest.MockedFunction< + CatalogApi['getEntitiesByRefs'] + > = jest.fn(); let Wrapper: React.ComponentType>; beforeEach(() => { Wrapper = ({ children }: { children?: React.ReactNode }) => ( - + {children} ); @@ -80,7 +82,7 @@ describe('', () => { }, ], }; - getEntities.mockResolvedValue({ + getEntitiesByRefs.mockResolvedValue({ items: [ { apiVersion: 'v1', diff --git a/plugins/catalog/src/components/HasSubcomponentsCard/HasSubcomponentsCard.test.tsx b/plugins/catalog/src/components/HasSubcomponentsCard/HasSubcomponentsCard.test.tsx index 97e69e93d1..713313b7c6 100644 --- a/plugins/catalog/src/components/HasSubcomponentsCard/HasSubcomponentsCard.test.tsx +++ b/plugins/catalog/src/components/HasSubcomponentsCard/HasSubcomponentsCard.test.tsx @@ -27,12 +27,14 @@ import React from 'react'; import { HasSubcomponentsCard } from './HasSubcomponentsCard'; describe('', () => { - const getEntities: jest.MockedFunction = jest.fn(); + const getEntitiesByRefs: jest.MockedFunction< + CatalogApi['getEntitiesByRefs'] + > = jest.fn(); let Wrapper: React.ComponentType>; beforeEach(() => { Wrapper = ({ children }: { children?: React.ReactNode }) => ( - + {children} ); @@ -85,7 +87,7 @@ describe('', () => { }, ], }; - getEntities.mockResolvedValue({ + getEntitiesByRefs.mockResolvedValue({ items: [ { apiVersion: 'v1', diff --git a/plugins/catalog/src/components/HasSystemsCard/HasSystemsCard.test.tsx b/plugins/catalog/src/components/HasSystemsCard/HasSystemsCard.test.tsx index 224e0c6703..9844708f85 100644 --- a/plugins/catalog/src/components/HasSystemsCard/HasSystemsCard.test.tsx +++ b/plugins/catalog/src/components/HasSystemsCard/HasSystemsCard.test.tsx @@ -27,12 +27,14 @@ import React from 'react'; import { HasSystemsCard } from './HasSystemsCard'; describe('', () => { - const getEntities: jest.MockedFunction = jest.fn(); + const getEntitiesByRefs: jest.MockedFunction< + CatalogApi['getEntitiesByRefs'] + > = jest.fn(); let Wrapper: React.ComponentType>; beforeEach(() => { Wrapper = ({ children }: { children?: React.ReactNode }) => ( - + {children} ); @@ -85,7 +87,7 @@ describe('', () => { }, ], }; - getEntities.mockResolvedValue({ + getEntitiesByRefs.mockResolvedValue({ items: [ { apiVersion: 'v1', From d0f5b0c886c2a554892514c6bf15e576adaa711f Mon Sep 17 00:00:00 2001 From: mingfu Date: Fri, 2 Jun 2023 21:31:46 +0800 Subject: [PATCH 28/65] set the expiration time for the oidc idToken Signed-off-by: mingfu --- .changeset/nice-peaches-reflect.md | 5 ++++ .../auth-backend/src/lib/session/constants.ts | 19 ++++++++++++ plugins/auth-backend/src/lib/session/index.ts | 17 +++++++++++ .../src/providers/github/provider.ts | 4 +-- .../src/providers/microsoft/provider.ts | 3 +- .../src/providers/oidc/provider.ts | 30 ++++++++++++------- plugins/auth-backend/src/service/router.ts | 3 +- 7 files changed, 64 insertions(+), 17 deletions(-) create mode 100644 .changeset/nice-peaches-reflect.md create mode 100644 plugins/auth-backend/src/lib/session/constants.ts create mode 100644 plugins/auth-backend/src/lib/session/index.ts diff --git a/.changeset/nice-peaches-reflect.md b/.changeset/nice-peaches-reflect.md new file mode 100644 index 0000000000..45c9f0ed6f --- /dev/null +++ b/.changeset/nice-peaches-reflect.md @@ -0,0 +1,5 @@ +--- +'@backstage/plugin-auth-backend': patch +--- + +Set the expiration time of oidc `idToken` to be less than backstage session expiration time. diff --git a/plugins/auth-backend/src/lib/session/constants.ts b/plugins/auth-backend/src/lib/session/constants.ts new file mode 100644 index 0000000000..0d14987ab2 --- /dev/null +++ b/plugins/auth-backend/src/lib/session/constants.ts @@ -0,0 +1,19 @@ +/* + * Copyright 2023 The Backstage Authors + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +// BACKSTAGE_SESSION_EXPIRATION the default session expiration time +// TODO: find a less hard-coded way to access this, perhaps by reading it from the configuration. +export const BACKSTAGE_SESSION_EXPIRATION = 3600; diff --git a/plugins/auth-backend/src/lib/session/index.ts b/plugins/auth-backend/src/lib/session/index.ts new file mode 100644 index 0000000000..306d483ae0 --- /dev/null +++ b/plugins/auth-backend/src/lib/session/index.ts @@ -0,0 +1,17 @@ +/* + * Copyright 2023 The Backstage Authors + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +export { BACKSTAGE_SESSION_EXPIRATION } from './constants'; diff --git a/plugins/auth-backend/src/providers/github/provider.ts b/plugins/auth-backend/src/providers/github/provider.ts index 7571b4a327..11a71ca018 100644 --- a/plugins/auth-backend/src/providers/github/provider.ts +++ b/plugins/auth-backend/src/providers/github/provider.ts @@ -42,12 +42,10 @@ import { OAuthRefreshRequest, } from '../../lib/oauth'; import { createAuthProviderIntegration } from '../createAuthProviderIntegration'; +import { BACKSTAGE_SESSION_EXPIRATION } from '../../lib/session'; const ACCESS_TOKEN_PREFIX = 'access-token.'; -// TODO(Rugvip): Auth providers need a way to access this in a less hardcoded way -const BACKSTAGE_SESSION_EXPIRATION = 3600; - type PrivateInfo = { refreshToken?: string; }; diff --git a/plugins/auth-backend/src/providers/microsoft/provider.ts b/plugins/auth-backend/src/providers/microsoft/provider.ts index 5d02b7ef61..bc581f6d10 100644 --- a/plugins/auth-backend/src/providers/microsoft/provider.ts +++ b/plugins/auth-backend/src/providers/microsoft/provider.ts @@ -51,8 +51,7 @@ import { Logger } from 'winston'; import fetch from 'node-fetch'; import { decodeJwt } from 'jose'; import { Profile as PassportProfile } from 'passport'; - -const BACKSTAGE_SESSION_EXPIRATION = 3600; +import { BACKSTAGE_SESSION_EXPIRATION } from '../../lib/session'; type PrivateInfo = { refreshToken: string; diff --git a/plugins/auth-backend/src/providers/oidc/provider.ts b/plugins/auth-backend/src/providers/oidc/provider.ts index a5196f0930..ed59611f21 100644 --- a/plugins/auth-backend/src/providers/oidc/provider.ts +++ b/plugins/auth-backend/src/providers/oidc/provider.ts @@ -48,6 +48,7 @@ import { commonByEmailLocalPartResolver, commonByEmailResolver, } from '../resolvers'; +import { BACKSTAGE_SESSION_EXPIRATION } from '../../lib/session'; type PrivateInfo = { refreshToken?: string; @@ -179,17 +180,15 @@ export class OidcAuthProvider implements OAuthHandlers { // Then populate the profile with it private async handleResult(result: OidcAuthResult): Promise { const { profile } = await this.authHandler(result, this.resolverContext); - const response: OAuthResponse = { - providerInfo: { - idToken: result.tokenset.id_token, - accessToken: result.tokenset.access_token!, - scope: result.tokenset.scope!, - expiresInSeconds: result.tokenset.expires_in, - }, - profile, - }; + + const expiresInSeconds = + result.tokenset.expires_in === undefined + ? BACKSTAGE_SESSION_EXPIRATION + : Math.min(result.tokenset.expires_in, BACKSTAGE_SESSION_EXPIRATION); + + let backstageIdentity = undefined; if (this.signInResolver) { - response.backstageIdentity = await this.signInResolver( + backstageIdentity = await this.signInResolver( { result, profile, @@ -198,7 +197,16 @@ export class OidcAuthProvider implements OAuthHandlers { ); } - return response; + return { + backstageIdentity, + providerInfo: { + idToken: result.tokenset.id_token, + accessToken: result.tokenset.access_token!, + scope: result.tokenset.scope!, + expiresInSeconds, + }, + profile, + }; } } diff --git a/plugins/auth-backend/src/service/router.ts b/plugins/auth-backend/src/service/router.ts index 2996ff68be..fa8dd95727 100644 --- a/plugins/auth-backend/src/service/router.ts +++ b/plugins/auth-backend/src/service/router.ts @@ -37,6 +37,7 @@ import passport from 'passport'; import { Minimatch } from 'minimatch'; import { CatalogAuthResolverContext } from '../lib/resolvers'; import { AuthDatabase } from '../database/AuthDatabase'; +import { BACKSTAGE_SESSION_EXPIRATION } from '../lib/session'; /** @public */ export type ProviderFactories = { [s: string]: AuthProviderFactory }; @@ -77,7 +78,7 @@ export async function createRouter( logger, database: authDb, }); - const keyDurationSeconds = 3600; + const keyDurationSeconds = BACKSTAGE_SESSION_EXPIRATION; const tokenIssuer = new TokenFactory({ issuer: authUrl, From 2a7bca7c705160448dc38cf799d924bb5e16eb9f Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Fredrik=20Adel=C3=B6w?= Date: Fri, 2 Jun 2023 16:29:15 +0200 Subject: [PATCH 29/65] update entity ref docs to remove illegal usages MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Signed-off-by: Fredrik Adelöw --- docs/features/software-catalog/references.md | 37 ++++++-------------- 1 file changed, 11 insertions(+), 26 deletions(-) diff --git a/docs/features/software-catalog/references.md b/docs/features/software-catalog/references.md index d347035950..6e0304b2e8 100644 --- a/docs/features/software-catalog/references.md +++ b/docs/features/software-catalog/references.md @@ -23,8 +23,7 @@ compound reference structure. ## String References -This is the most common alternative, that should be used in almost all -circumstances. +This is the most common alternative, that is used in almost all circumstances. The string is on the form `[:][/]`, that is, it is composed of between one and three parts in this specific order, without any @@ -75,30 +74,16 @@ essentially expand to `api:external-systems/petstore`, `api:internal/streetlights`, and `api:external-systems/hello-world`. We expect there to exist three API kind entities in the catalog matching those references. +Note that the remarks above in regards to shortening (leaving out kind and/or +namespace) _only_ apply for the entity input YAML data. In protocols, storage +systems, or when referring to entities externally, the entity ref always +consists of all three parts. + ## Compound References This is a more verbose version of a reference, where each part of the -kind-namespace-name triplet is expressed as a field in a structure. This format -can be used where necessary, such as if either of the three elements contains -colons or forward slashes. Avoid using it where possible, since it is harder to -read and write for humans. - -```yaml -# Example: -apiVersion: backstage.io/v1alpha1 -kind: Component -metadata: - name: petstore - description: Petstore -spec: - type: service - lifecycle: experimental - owner: - kind: Group - name: aegis-imports/pet-managers -``` - -In this example, the `spec.owner` has been broken apart since the name was -complex. The kind happened to be written with an uppercase letter G, which also -works. The namespace was left out just like in the string version above, which -is handled identically. +kind-namespace-name triplet is expressed as a field in an object. You may see +this structure used in Backstage code, but it should normally not be used in any +form of protocol or between plugins and/or external systems. For those cases, +instead prefer to use the string form which has clearer semantics and can be +transported more easily since it's just a string. From 1948845861b0950576da5dd32093f6773e198f5d Mon Sep 17 00:00:00 2001 From: Andrew Ochsner Date: Fri, 2 Jun 2023 10:04:07 -0500 Subject: [PATCH 30/65] add github:environment:create and github:deployKey:create Signed-off-by: Andrew Ochsner --- .changeset/strange-dolls-decide.md | 5 + docs/integrations/github/github-apps.md | 1 + plugins/scaffolder-backend/api-report.md | 44 +++ .../actions/builtin/createBuiltinActions.ts | 8 + .../builtin/github/githubDeployKey.test.ts | 112 ++++++++ .../actions/builtin/github/githubDeployKey.ts | 157 +++++++++++ .../builtin/github/githubEnvironment.test.ts | 258 ++++++++++++++++++ .../builtin/github/githubEnvironment.ts | 200 ++++++++++++++ .../actions/builtin/github/helpers.ts | 4 +- .../actions/builtin/github/index.ts | 2 + 10 files changed, 789 insertions(+), 2 deletions(-) create mode 100644 .changeset/strange-dolls-decide.md create mode 100644 plugins/scaffolder-backend/src/scaffolder/actions/builtin/github/githubDeployKey.test.ts create mode 100644 plugins/scaffolder-backend/src/scaffolder/actions/builtin/github/githubDeployKey.ts create mode 100644 plugins/scaffolder-backend/src/scaffolder/actions/builtin/github/githubEnvironment.test.ts create mode 100644 plugins/scaffolder-backend/src/scaffolder/actions/builtin/github/githubEnvironment.ts diff --git a/.changeset/strange-dolls-decide.md b/.changeset/strange-dolls-decide.md new file mode 100644 index 0000000000..97dc99d2c9 --- /dev/null +++ b/.changeset/strange-dolls-decide.md @@ -0,0 +1,5 @@ +--- +'@backstage/plugin-scaffolder-backend': minor +--- + +Added `github:deployKey:create` and `github:environment:create` scaffolder actions. You will need to add `read/write` permissions to your GITHUB_TOKEN and/or Github Backstage App for Repository `Administration` (for deploy key functionality) and `Environments` (for Environment functionality) diff --git a/docs/integrations/github/github-apps.md b/docs/integrations/github/github-apps.md index 3cad69f56d..cc84704799 100644 --- a/docs/integrations/github/github-apps.md +++ b/docs/integrations/github/github-apps.md @@ -138,3 +138,4 @@ integration: - `Commit statuses`: `Read-only` - `Variables`: `Read & write` (if templates include GitHub Action Repository Variables) - `Secrets`: `Read & write` (if templates include GitHub Action Repository Secrets) + - `Environments`: `Read & write` (if templates include GitHub Environments) diff --git a/plugins/scaffolder-backend/api-report.md b/plugins/scaffolder-backend/api-report.md index 5e18ad15bf..86fadbacb0 100644 --- a/plugins/scaffolder-backend/api-report.md +++ b/plugins/scaffolder-backend/api-report.md @@ -211,6 +211,50 @@ export function createGithubActionsDispatchAction(options: { JsonObject >; +// @public +export function createGithubDeployKeyAction(options: { + integrations: ScmIntegrationRegistry; +}): TemplateAction_2< + { + repoUrl: string; + publicKey: string; + privateKey: string; + deployKeyName: string; + privateKeySecretName?: string | undefined; + token?: string | undefined; + }, + JsonObject +>; + +// @public +export function createGithubEnvironmentAction(options: { + integrations: ScmIntegrationRegistry; +}): TemplateAction_2< + { + repoUrl: string; + name: string; + deploymentBranchPolicy?: + | { + protected_branches: boolean; + custom_branch_policies: boolean; + } + | undefined; + customBranchPolicyNames?: string[] | undefined; + environmentVariables?: + | { + [key: string]: string; + } + | undefined; + secrets?: + | { + [key: string]: string; + } + | undefined; + token?: string | undefined; + }, + JsonObject +>; + // @public export function createGithubIssuesLabelAction(options: { integrations: ScmIntegrationRegistry; diff --git a/plugins/scaffolder-backend/src/scaffolder/actions/builtin/createBuiltinActions.ts b/plugins/scaffolder-backend/src/scaffolder/actions/builtin/createBuiltinActions.ts index 747b5cdaed..f5ea23f26f 100644 --- a/plugins/scaffolder-backend/src/scaffolder/actions/builtin/createBuiltinActions.ts +++ b/plugins/scaffolder-backend/src/scaffolder/actions/builtin/createBuiltinActions.ts @@ -42,6 +42,8 @@ import { } from './filesystem'; import { createGithubActionsDispatchAction, + createGithubDeployKeyAction, + createGithubEnvironmentAction, createGithubIssuesLabelAction, createGithubRepoCreateAction, createGithubRepoPushAction, @@ -194,6 +196,12 @@ export const createBuiltinActions = ( config, githubCredentialsProvider, }), + createGithubEnvironmentAction({ + integrations, + }), + createGithubDeployKeyAction({ + integrations, + }), ]; return actions as TemplateAction[]; diff --git a/plugins/scaffolder-backend/src/scaffolder/actions/builtin/github/githubDeployKey.test.ts b/plugins/scaffolder-backend/src/scaffolder/actions/builtin/github/githubDeployKey.test.ts new file mode 100644 index 0000000000..4df9294ff5 --- /dev/null +++ b/plugins/scaffolder-backend/src/scaffolder/actions/builtin/github/githubDeployKey.test.ts @@ -0,0 +1,112 @@ +/* + * Copyright 2021 The Backstage Authors + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +import { PassThrough } from 'stream'; +import { createGithubDeployKeyAction } from './githubDeployKey'; +import { getVoidLogger } from '@backstage/backend-common'; +import { TemplateAction } from '@backstage/plugin-scaffolder-node'; +import { ConfigReader } from '@backstage/config'; +import { ScmIntegrations } from '@backstage/integration'; + +const mockOctokit = { + rest: { + actions: { + getRepoPublicKey: jest.fn(), + createOrUpdateRepoSecret: jest.fn(), + }, + repos: { + createDeployKey: jest.fn(), + }, + }, +}; +jest.mock('octokit', () => ({ + Octokit: class { + constructor() { + return mockOctokit; + } + }, +})); + +const publicKey = '2Sg8iYjAxxmI2LvUXpJjkYrMxURPc8r+dB7TJyvvcCU='; + +describe('github:deployKey:create', () => { + const config = new ConfigReader({ + integrations: { + github: [ + { host: 'github.com', token: 'tokenlols' }, + { host: 'ghe.github.com' }, + ], + }, + }); + + const integrations = ScmIntegrations.fromConfig(config); + let action: TemplateAction; + + const mockContext = { + input: { + repoUrl: 'github.com?repo=repository&owner=owner', + publicKey: 'pubkey', + privateKey: 'privkey', + deployKeyName: 'Push Tags', + }, + workspacePath: 'lol', + logger: getVoidLogger(), + logStream: new PassThrough(), + output: jest.fn(), + createTemporaryDirectory: jest.fn(), + }; + + beforeEach(() => { + jest.resetAllMocks(); + + action = createGithubDeployKeyAction({ + integrations, + }); + }); + + it('should work happy path', async () => { + mockOctokit.rest.actions.getRepoPublicKey.mockResolvedValue({ + data: { + key: publicKey, + key_id: 'keyid', + }, + }); + + await action.handler(mockContext); + + expect(mockOctokit.rest.repos.createDeployKey).toHaveBeenCalledWith({ + owner: 'owner', + repo: 'repository', + title: 'Push Tags', + key: 'pubkey', + }); + + expect( + mockOctokit.rest.actions.createOrUpdateRepoSecret, + ).toHaveBeenCalledWith({ + owner: 'owner', + repo: 'repository', + secret_name: 'PUSH_TAGS_PRIVATE_KEY', + key_id: 'keyid', + encrypted_value: expect.any(String), + }); + + expect(mockContext.output).toHaveBeenCalledWith( + 'privateKeySecretName', + 'PUSH_TAGS_PRIVATE_KEY', + ); + }); +}); diff --git a/plugins/scaffolder-backend/src/scaffolder/actions/builtin/github/githubDeployKey.ts b/plugins/scaffolder-backend/src/scaffolder/actions/builtin/github/githubDeployKey.ts new file mode 100644 index 0000000000..6ad646a89c --- /dev/null +++ b/plugins/scaffolder-backend/src/scaffolder/actions/builtin/github/githubDeployKey.ts @@ -0,0 +1,157 @@ +/* + * Copyright 2021 The Backstage Authors + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +import { InputError } from '@backstage/errors'; +import { createTemplateAction } from '@backstage/plugin-scaffolder-node'; +import { ScmIntegrationRegistry } from '@backstage/integration'; +import { parseRepoUrl } from '../publish/util'; +import { getOctokitOptions } from './helpers'; +import { Octokit } from 'octokit'; +import Sodium from 'libsodium-wrappers'; + +/** + * Creates an `github:deployKey:create` Scaffolder action that creates a Deploy Key + * + * @public + */ +export function createGithubDeployKeyAction(options: { + integrations: ScmIntegrationRegistry; +}) { + const { integrations } = options; + // For more information on how to define custom actions, see + // https://backstage.io/docs/features/software-templates/writing-custom-actions + return createTemplateAction<{ + repoUrl: string; + publicKey: string; + privateKey: string; + deployKeyName: string; + privateKeySecretName?: string; + token?: string; + }>({ + id: 'github:deployKey:create', + description: 'Creates and stores Deploy Keys', + schema: { + input: { + type: 'object', + required: ['repoUrl', 'publicKey', 'privateKey', 'deployKeyName'], + properties: { + repoUrl: { + title: 'Repository Location', + description: `Accepts the format 'github.com?repo=reponame&owner=owner' where 'reponame' is the new repository name and 'owner' is an organization or username`, + type: 'string', + }, + publicKey: { + title: 'SSH Public Key', + description: `Generated from ssh-keygen. Begins with 'ssh-rsa', 'ecdsa-sha2-nistp256', 'ecdsa-sha2-nistp384', 'ecdsa-sha2-nistp521', 'ssh-ed25519', 'sk-ecdsa-sha2-nistp256@openssh.com', or 'sk-ssh-ed25519@openssh.com'.`, + type: 'string', + }, + privateKey: { + title: 'SSH Private Key', + description: `SSH Private Key generated from ssh-keygen`, + type: 'string', + }, + deployKeyName: { + title: 'Deploy Key Name', + description: `Name of the Deploy Key`, + type: 'string', + }, + privateKeySecretName: { + title: 'Private Key GitHub Secret Name', + description: `Name of the GitHub Secret to store the private key related to the Deploy Key. Defaults to: 'KEY_NAME_PRIVATE_KEY' where 'KEY_NAME' is the name of the Deploy Key`, + type: 'string', + }, + token: { + title: 'Authentication Token', + type: 'string', + description: 'The token to use for authorization to GitHub', + }, + }, + }, + output: { + type: 'object', + properties: { + privateKeySecretName: { + title: 'The GitHub Action Repo Secret Name for the Private Key', + type: 'string', + }, + }, + }, + }, + async handler(ctx) { + const { + repoUrl, + publicKey, + privateKey, + deployKeyName, + privateKeySecretName = `${deployKeyName + .split(' ') + .join('_') + .toLocaleUpperCase('en-US')}_PRIVATE_KEY`, + token: providedToken, + } = ctx.input; + + const octokitOptions = await getOctokitOptions({ + integrations, + token: providedToken, + repoUrl: repoUrl, + }); + + const { owner, repo } = parseRepoUrl(repoUrl, integrations); + + if (!owner) { + throw new InputError(`No owner provided for repo ${repoUrl}`); + } + + const client = new Octokit(octokitOptions); + + await client.rest.repos.createDeployKey({ + owner: owner, + repo: repo, + title: deployKeyName, + key: publicKey, + }); + const publicKeyResponse = await client.rest.actions.getRepoPublicKey({ + owner: owner, + repo: repo, + }); + + await Sodium.ready; + const binaryKey = Sodium.from_base64( + publicKeyResponse.data.key, + Sodium.base64_variants.ORIGINAL, + ); + const binarySecret = Sodium.from_string(privateKey); + const encryptedBinarySecret = Sodium.crypto_box_seal( + binarySecret, + binaryKey, + ); + const encryptedBase64Secret = Sodium.to_base64( + encryptedBinarySecret, + Sodium.base64_variants.ORIGINAL, + ); + + await client.rest.actions.createOrUpdateRepoSecret({ + owner: owner, + repo: repo, + secret_name: privateKeySecretName, + encrypted_value: encryptedBase64Secret, + key_id: publicKeyResponse.data.key_id, + }); + + ctx.output('privateKeySecretName', privateKeySecretName); + }, + }); +} diff --git a/plugins/scaffolder-backend/src/scaffolder/actions/builtin/github/githubEnvironment.test.ts b/plugins/scaffolder-backend/src/scaffolder/actions/builtin/github/githubEnvironment.test.ts new file mode 100644 index 0000000000..d158bc122e --- /dev/null +++ b/plugins/scaffolder-backend/src/scaffolder/actions/builtin/github/githubEnvironment.test.ts @@ -0,0 +1,258 @@ +/* + * Copyright 2021 The Backstage Authors + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +import { PassThrough } from 'stream'; +import { createGithubEnvironmentAction } from './githubEnvironment'; +import { getVoidLogger } from '@backstage/backend-common'; +import { TemplateAction } from '@backstage/plugin-scaffolder-node'; +import { ConfigReader } from '@backstage/config'; +import { ScmIntegrations } from '@backstage/integration'; + +const mockOctokit = { + rest: { + actions: { + getRepoPublicKey: jest.fn(), + createEnvironmentVariable: jest.fn(), + createOrUpdateEnvironmentSecret: jest.fn(), + }, + repos: { + createDeploymentBranchPolicy: jest.fn(), + createOrUpdateEnvironment: jest.fn(), + get: jest.fn(), + }, + }, +}; +jest.mock('octokit', () => ({ + Octokit: class { + constructor() { + return mockOctokit; + } + }, +})); + +const publicKey = '2Sg8iYjAxxmI2LvUXpJjkYrMxURPc8r+dB7TJyvvcCU='; + +describe('github:environment:create', () => { + const config = new ConfigReader({ + integrations: { + github: [ + { host: 'github.com', token: 'tokenlols' }, + { host: 'ghe.github.com' }, + ], + }, + }); + + const integrations = ScmIntegrations.fromConfig(config); + let action: TemplateAction; + + const mockContext = { + input: { + repoUrl: 'github.com?repo=repository&owner=owner', + name: 'envname', + }, + workspacePath: 'lol', + logger: getVoidLogger(), + logStream: new PassThrough(), + output: jest.fn(), + createTemporaryDirectory: jest.fn(), + }; + + beforeEach(() => { + mockOctokit.rest.actions.getRepoPublicKey.mockResolvedValue({ + data: { + key: publicKey, + key_id: 'keyid', + }, + }); + mockOctokit.rest.repos.get.mockResolvedValue({ + data: { + id: 'repoid', + }, + }); + + action = createGithubEnvironmentAction({ + integrations, + }); + }); + + afterEach(jest.resetAllMocks); + + it('should work happy path', async () => { + await action.handler(mockContext); + + expect( + mockOctokit.rest.repos.createOrUpdateEnvironment, + ).toHaveBeenCalledWith({ + owner: 'owner', + repo: 'repository', + environment_name: 'envname', + deployment_branch_policy: null, + }); + }); + + it('should work specify deploymentBranchPolicy protected', async () => { + await action.handler({ + ...mockContext, + input: { + ...mockContext.input, + deploymentBranchPolicy: { + protected_branches: true, + custom_branch_policies: false, + }, + }, + }); + + expect( + mockOctokit.rest.repos.createOrUpdateEnvironment, + ).toHaveBeenCalledWith({ + owner: 'owner', + repo: 'repository', + environment_name: 'envname', + deployment_branch_policy: { + protected_branches: true, + custom_branch_policies: false, + }, + }); + }); + it('should work specify deploymentBranchPolicy custom', async () => { + await action.handler({ + ...mockContext, + input: { + ...mockContext.input, + deploymentBranchPolicy: { + protected_branches: false, + custom_branch_policies: true, + }, + customBranchPolicyNames: ['main', '*.*.*'], + }, + }); + + expect( + mockOctokit.rest.repos.createOrUpdateEnvironment, + ).toHaveBeenCalledWith({ + owner: 'owner', + repo: 'repository', + environment_name: 'envname', + deployment_branch_policy: { + protected_branches: false, + custom_branch_policies: true, + }, + }); + + expect( + mockOctokit.rest.repos.createDeploymentBranchPolicy, + ).toHaveBeenCalledWith({ + owner: 'owner', + repo: 'repository', + environment_name: 'envname', + name: 'main', + }); + expect( + mockOctokit.rest.repos.createDeploymentBranchPolicy, + ).toHaveBeenCalledWith({ + owner: 'owner', + repo: 'repository', + environment_name: 'envname', + name: '*.*.*', + }); + }); + + it('should work specify environment variables', async () => { + await action.handler({ + ...mockContext, + input: { + ...mockContext.input, + environmentVariables: { + key1: 'val1', + key2: 'val2', + }, + }, + }); + + expect( + mockOctokit.rest.repos.createOrUpdateEnvironment, + ).toHaveBeenCalledWith({ + owner: 'owner', + repo: 'repository', + environment_name: 'envname', + deployment_branch_policy: null, + }); + + expect( + mockOctokit.rest.actions.createEnvironmentVariable, + ).toHaveBeenCalledTimes(2); + expect( + mockOctokit.rest.actions.createEnvironmentVariable, + ).toHaveBeenCalledWith({ + repository_id: 'repoid', + environment_name: 'envname', + name: 'key1', + value: 'val1', + }); + expect( + mockOctokit.rest.actions.createEnvironmentVariable, + ).toHaveBeenCalledWith({ + repository_id: 'repoid', + environment_name: 'envname', + name: 'key2', + value: 'val2', + }); + }); + + it('should work specify secrets', async () => { + await action.handler({ + ...mockContext, + input: { + ...mockContext.input, + secrets: { + key1: 'val1', + key2: 'val2', + }, + }, + }); + + expect( + mockOctokit.rest.repos.createOrUpdateEnvironment, + ).toHaveBeenCalledWith({ + owner: 'owner', + repo: 'repository', + environment_name: 'envname', + deployment_branch_policy: null, + }); + + expect( + mockOctokit.rest.actions.createOrUpdateEnvironmentSecret, + ).toHaveBeenCalledTimes(2); + expect( + mockOctokit.rest.actions.createOrUpdateEnvironmentSecret, + ).toHaveBeenCalledWith({ + repository_id: 'repoid', + environment_name: 'envname', + secret_name: 'key1', + key_id: 'keyid', + encrypted_value: expect.any(String), + }); + expect( + mockOctokit.rest.actions.createOrUpdateEnvironmentSecret, + ).toHaveBeenCalledWith({ + repository_id: 'repoid', + environment_name: 'envname', + secret_name: 'key2', + key_id: 'keyid', + encrypted_value: expect.any(String), + }); + }); +}); diff --git a/plugins/scaffolder-backend/src/scaffolder/actions/builtin/github/githubEnvironment.ts b/plugins/scaffolder-backend/src/scaffolder/actions/builtin/github/githubEnvironment.ts new file mode 100644 index 0000000000..04b33ed259 --- /dev/null +++ b/plugins/scaffolder-backend/src/scaffolder/actions/builtin/github/githubEnvironment.ts @@ -0,0 +1,200 @@ +/* + * Copyright 2021 The Backstage Authors + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +import { InputError } from '@backstage/errors'; +import { createTemplateAction } from '@backstage/plugin-scaffolder-node'; +import { ScmIntegrationRegistry } from '@backstage/integration'; +import { parseRepoUrl } from '../publish/util'; +import { getOctokitOptions } from './helpers'; +import { Octokit } from 'octokit'; +import Sodium from 'libsodium-wrappers'; + +/** + * Creates an `github:environment:create` Scaffolder action that creates a Github Environment. + * + * @public + */ +export function createGithubEnvironmentAction(options: { + integrations: ScmIntegrationRegistry; +}) { + const { integrations } = options; + // For more information on how to define custom actions, see + // https://backstage.io/docs/features/software-templates/writing-custom-actions + return createTemplateAction<{ + repoUrl: string; + name: string; + deploymentBranchPolicy?: { + protected_branches: boolean; + custom_branch_policies: boolean; + }; + customBranchPolicyNames?: string[]; + environmentVariables?: { [key: string]: string }; + secrets?: { [key: string]: string }; + token?: string; + }>({ + id: 'github:environment:create', + description: 'Creates Deployment Environments', + schema: { + input: { + type: 'object', + required: ['repoUrl', 'name'], + properties: { + repoUrl: { + title: 'Repository Location', + description: `Accepts the format 'github.com?repo=reponame&owner=owner' where 'reponame' is the new repository name and 'owner' is an organization or username`, + type: 'string', + }, + name: { + title: 'Environment Name', + description: `Name of the deployment environment to create`, + type: 'string', + }, + deploymentBranchPolicy: { + title: 'Deployment Branch Policy', + description: `The type of deployment branch policy for this environment. To allow all branches to deploy, set to null.`, + type: 'object', + required: ['protected_branches', 'custom_branch_policies'], + properties: { + protected_branches: { + title: 'Protected Branches', + description: `Whether only branches with branch protection rules can deploy to this environment. If protected_branches is true, custom_branch_policies must be false; if protected_branches is false, custom_branch_policies must be true.`, + type: 'boolean', + }, + custom_branch_policies: { + title: 'Custom Branch Policies', + description: `Whether only branches that match the specified name patterns can deploy to this environment. If custom_branch_policies is true, protected_branches must be false; if custom_branch_policies is false, protected_branches must be true.`, + type: 'boolean', + }, + }, + }, + customBranchPolicyNames: { + title: 'Custom Branch Policy Name', + description: `The name pattern that branches must match in order to deploy to the environment. + + Wildcard characters will not match /. For example, to match branches that begin with release/ and contain an additional single slash, use release/*/*. For more information about pattern matching syntax, see the Ruby File.fnmatch documentation.`, + type: 'array', + items: { + type: 'string', + }, + }, + environmentVariables: { + title: 'Environment Variables', + description: `Environment variables attached to the deployment environment`, + type: 'object', + }, + secrets: { + title: 'Deployment Secrets', + description: `Secrets attached to the deployment environment`, + type: 'object', + }, + token: { + title: 'Authentication Token', + type: 'string', + description: 'The token to use for authorization to GitHub', + }, + }, + }, + }, + async handler(ctx) { + const { + repoUrl, + name, + deploymentBranchPolicy, + customBranchPolicyNames, + environmentVariables, + secrets, + token: providedToken, + } = ctx.input; + + const octokitOptions = await getOctokitOptions({ + integrations, + token: providedToken, + repoUrl: repoUrl, + }); + + const { owner, repo } = parseRepoUrl(repoUrl, integrations); + + if (!owner) { + throw new InputError(`No owner provided for repo ${repoUrl}`); + } + + const client = new Octokit(octokitOptions); + const repository = await client.rest.repos.get({ + owner: owner, + repo: repo, + }); + + await client.rest.repos.createOrUpdateEnvironment({ + owner: owner, + repo: repo, + environment_name: name, + deployment_branch_policy: deploymentBranchPolicy ?? null, + }); + + if (customBranchPolicyNames) { + for (const item of customBranchPolicyNames) { + await client.rest.repos.createDeploymentBranchPolicy({ + owner: owner, + repo: repo, + environment_name: name, + name: item, + }); + } + } + + for (const [key, value] of Object.entries(environmentVariables ?? {})) { + await client.rest.actions.createEnvironmentVariable({ + repository_id: repository.data.id, + environment_name: name, + name: key, + value, + }); + } + + if (secrets) { + const publicKeyResponse = await client.rest.actions.getRepoPublicKey({ + owner: owner, + repo: repo, + }); + + await Sodium.ready; + const binaryKey = Sodium.from_base64( + publicKeyResponse.data.key, + Sodium.base64_variants.ORIGINAL, + ); + for (const [key, value] of Object.entries(secrets)) { + const binarySecret = Sodium.from_string(value); + const encryptedBinarySecret = Sodium.crypto_box_seal( + binarySecret, + binaryKey, + ); + const encryptedBase64Secret = Sodium.to_base64( + encryptedBinarySecret, + Sodium.base64_variants.ORIGINAL, + ); + + await client.rest.actions.createOrUpdateEnvironmentSecret({ + repository_id: repository.data.id, + environment_name: name, + secret_name: key, + encrypted_value: encryptedBase64Secret, + key_id: publicKeyResponse.data.key_id, + }); + } + } + }, + }); +} diff --git a/plugins/scaffolder-backend/src/scaffolder/actions/builtin/github/helpers.ts b/plugins/scaffolder-backend/src/scaffolder/actions/builtin/github/helpers.ts index dc1b4eb91c..edef7cec5c 100644 --- a/plugins/scaffolder-backend/src/scaffolder/actions/builtin/github/helpers.ts +++ b/plugins/scaffolder-backend/src/scaffolder/actions/builtin/github/helpers.ts @@ -98,7 +98,7 @@ export async function createGithubRepoWithCollaboratorsAndTopics( client: Octokit, repo: string, owner: string, - repoVisibility: 'private' | 'internal' | 'public', + repoVisibility: 'private' | 'internal' | 'public' | undefined, description: string | undefined, homepage: string | undefined, deleteBranchOnMerge: boolean, @@ -149,7 +149,7 @@ export async function createGithubRepoWithCollaboratorsAndTopics( name: repo, org: owner, private: repoVisibility === 'private', - // @ts-ignore + // @ts-ignore https://github.com/octokit/types.ts/issues/522 visibility: repoVisibility, description: description, delete_branch_on_merge: deleteBranchOnMerge, diff --git a/plugins/scaffolder-backend/src/scaffolder/actions/builtin/github/index.ts b/plugins/scaffolder-backend/src/scaffolder/actions/builtin/github/index.ts index 6746aef37e..ecc8ce59f2 100644 --- a/plugins/scaffolder-backend/src/scaffolder/actions/builtin/github/index.ts +++ b/plugins/scaffolder-backend/src/scaffolder/actions/builtin/github/index.ts @@ -19,3 +19,5 @@ export { createGithubIssuesLabelAction } from './githubIssuesLabel'; export { createGithubRepoCreateAction } from './githubRepoCreate'; export { createGithubRepoPushAction } from './githubRepoPush'; export { createGithubWebhookAction } from './githubWebhook'; +export { createGithubDeployKeyAction } from './githubDeployKey'; +export { createGithubEnvironmentAction } from './githubEnvironment'; From c5fe9177fa72acd514c44911a0e798c2321f7677 Mon Sep 17 00:00:00 2001 From: djamaile Date: Fri, 2 Jun 2023 17:52:33 +0200 Subject: [PATCH 31/65] Add blog about backstage deploy Signed-off-by: djamaile --- .../2023-05-06-backstage-deploy-alpha.mdx | 77 ++++++++++++++++++ .../2023-05-06/Welcome-Backstage-Deploy.png | Bin 0 -> 122242 bytes 2 files changed, 77 insertions(+) create mode 100644 microsite/blog/2023-05-06-backstage-deploy-alpha.mdx create mode 100644 microsite/blog/assets/2023-05-06/Welcome-Backstage-Deploy.png diff --git a/microsite/blog/2023-05-06-backstage-deploy-alpha.mdx b/microsite/blog/2023-05-06-backstage-deploy-alpha.mdx new file mode 100644 index 0000000000..ead9eb5f29 --- /dev/null +++ b/microsite/blog/2023-05-06-backstage-deploy-alpha.mdx @@ -0,0 +1,77 @@ +--- +title: "Welcome: Backstage Deploy CLI (Alpha)" +author: Djamaile Rahamat, Spotify +authorURL: https://github.com/djamaile +authorImageURL: https://avatars.githubusercontent.com/u/15789670?v=4 +--- + +_This blog post is co-authored by Emma White ([@ewhite1997](https://github.com/ewhite1997)), Spotify._ + +![Backstage Deploy banner](assets/2023-05-06/Welcome-Backstage-Deploy.png) + +TL;DR: Backstage released a new CLI earlier this year as part of a [new Backstage project](https://github.com/backstage/backstage-deploy). This new capability allows early adopters to deploy their Backstage proof of concept faster than before. In this blog, you’ll learn a little bit more about the Deploy CLI and how you can get started with it. + +{/* truncate */} + + +## Why Backstage Deploy + +We’ve heard from Backstage adopters that before reaching widespread adoption at their organizations, teams test out a Backstage proof of concept (POC). To create the POC, teams scaffold an instance, set up the catalog, and change the UI to suit their company’s branding. Once these milestones are completed, there's just one last step before showing off the awesomeness of a Backstage POC internally... deploying the Backstage POC from a local machine to the cloud. This final step often introduces a lot of questions that attempt to determine the easiest and fastest way to do that. + +Let’s say you’re at this last step: your POC is ready for deployment, but you have some lingering questions. + +For example: +- What Dockerfile should you use? +- Should the POC be deployed on Kubernetes? +- How do you deploy the POC on my cloud provider? + +To address these questions and reduce friction from deploying a POC, we built a [new CLI](https://github.com/backstage/backstage-deploy). The CLI is simply called `deploy` and is invokable with `npx`. With this new CLI, you can generate a Dockerfile and deploy a Backstage instance onto a preferred cloud provider. While the package’s infrastructure is built to support all cloud providers, currently the CLI only offers an AWS implementation. In the future, we plan to add additional cloud providers to the package and [welcome any contributions](https://github.com/backstage/backstage/blob/6996b3338d678efc03307112524060e9dc2ad769/CONTRIBUTING.md) extending the suite of cloud provider implementations! + +**So, what about Kubernetes?** Since the CLI is designed specifically for the POC phase, we believe that Kubernetes isn’t the right fit – as Kubernetes is better suited for production workloads. So, we explored lightweight, container-based solutions, and landed on [Amazon Lightsail](https://docs.aws.amazon.com/lightsail/index.html) as a hosting service for the POC. +Amazon Lightsail supports [lightweight container](https://lightsail.aws.amazon.com/ls/docs/en_us/articles/amazon-lightsail-container-services) deployments [at a low cost](https://aws.amazon.com/lightsail/pricing/), and has a [free trial for new users](https://aws.amazon.com/lightsail/pricing/?loc=ft#AWS_Free_Tier)! Given Lightsail’s ease of use and affordability, we recommend using Lightsail over Kubernetes to test out your Backstage POC. + +With the Dockerfile and Kubernetes questions answered, we just have to address how to actually deploy the POC. And that is where the new CLI comes in. + +## Get started with Deploy CLI + +It's now time to put the Deploy CLI into action and deploy a Backstage POC. The following steps guide you through the deployment process. + +Deploy CLI makes use of [Pulumi](https://www.pulumi.com/docs/) which is an infrastructure-as-code tool that helps provision resources in the cloud. Before you get started, ensure you have the [Pulumi CLI](https://www.pulumi.com/docs/cli/) and [AWS CLI](https://docs.aws.amazon.com/cli/latest/userguide/getting-started-install.html) installed on your local machine. + +You can find the step-by-step installation documentation for Pulumi under the [Deployment section](https://backstage.io/docs/deployment/pulumi/aws). + +But we summarize the steps to deploy your POC here. You can invoke the the CLI you can use the following command: + +```bash +$ npx backstage-deploy aws --create-dockerfile +Starting Pulumi +successfully initialized stack +installing aws plugin... +plugins installed +setting up config +refreshing stack... +Refreshing (backstage): + +Instance will live at: +https://backstage-container-service.xxx.us-east-1.cs.amazonlightsail.com/ +``` + +Once you kick off the command it will create a Dockerfile for you in the root and Pulumi will start provisioning resources in AWS. +Pulumi will then create a container based deployment in Amazon Lightsail. + +After you’re done with the POC, it’s easy to delete the AWS resources you provisioned and save you costs within AWS. You can do so with the following command: + +```bash +$ npx backstage-deploy aws --destroy +``` +## Looking ahead + +As mentioned earlier in this blog, we released the Backstage Deploy CLI with an AWS implementation only. In the next few months, we are excited to collect feedback from our end users to understand how the AWS implementation works. With those learnings, we plan to iterate on the Deploy CLI and build out implementations for other cloud providers. Of course, contributions are always welcome! + +So, please try this new CLI out and let us know what you think on [Discord](https://discord.com/channels/687207715902193673/995973463208644678)! + +Useful links: + +- [Deploy docs](https://backstage.io/docs/deployment/pulumi/aws) +- [Pulumi docs](https://www.pulumi.com/docs/) +- [#deployment](https://discord.com/channels/687207715902193673/995973463208644678) channel in Discord diff --git a/microsite/blog/assets/2023-05-06/Welcome-Backstage-Deploy.png b/microsite/blog/assets/2023-05-06/Welcome-Backstage-Deploy.png new file mode 100644 index 0000000000000000000000000000000000000000..403f12f2bba4c637b91badff692c0ec42658530f GIT binary patch literal 122242 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 Date: Sat, 3 Jun 2023 12:50:55 +0000 Subject: [PATCH 32/65] fix(deps): update dependency @swc/core to v1.3.62 Signed-off-by: renovate[bot] <29139614+renovate[bot]@users.noreply.github.com> --- microsite/yarn.lock | 86 ++++++++++++++++++++++----------------------- storybook/yarn.lock | 86 ++++++++++++++++++++++----------------------- yarn.lock | 86 ++++++++++++++++++++++----------------------- 3 files changed, 129 insertions(+), 129 deletions(-) diff --git a/microsite/yarn.lock b/microsite/yarn.lock index e480859f65..de336151a8 100644 --- a/microsite/yarn.lock +++ b/microsite/yarn.lock @@ -2604,90 +2604,90 @@ __metadata: languageName: node linkType: hard -"@swc/core-darwin-arm64@npm:1.3.59": - version: 1.3.59 - resolution: "@swc/core-darwin-arm64@npm:1.3.59" +"@swc/core-darwin-arm64@npm:1.3.62": + version: 1.3.62 + resolution: "@swc/core-darwin-arm64@npm:1.3.62" conditions: os=darwin & cpu=arm64 languageName: node linkType: hard -"@swc/core-darwin-x64@npm:1.3.59": - version: 1.3.59 - resolution: "@swc/core-darwin-x64@npm:1.3.59" +"@swc/core-darwin-x64@npm:1.3.62": + version: 1.3.62 + resolution: "@swc/core-darwin-x64@npm:1.3.62" conditions: os=darwin & cpu=x64 languageName: node linkType: hard -"@swc/core-linux-arm-gnueabihf@npm:1.3.59": - version: 1.3.59 - resolution: "@swc/core-linux-arm-gnueabihf@npm:1.3.59" +"@swc/core-linux-arm-gnueabihf@npm:1.3.62": + version: 1.3.62 + resolution: "@swc/core-linux-arm-gnueabihf@npm:1.3.62" conditions: os=linux & cpu=arm languageName: node linkType: hard -"@swc/core-linux-arm64-gnu@npm:1.3.59": - version: 1.3.59 - resolution: "@swc/core-linux-arm64-gnu@npm:1.3.59" +"@swc/core-linux-arm64-gnu@npm:1.3.62": + version: 1.3.62 + resolution: "@swc/core-linux-arm64-gnu@npm:1.3.62" conditions: os=linux & cpu=arm64 & libc=glibc languageName: node linkType: hard -"@swc/core-linux-arm64-musl@npm:1.3.59": - version: 1.3.59 - resolution: "@swc/core-linux-arm64-musl@npm:1.3.59" +"@swc/core-linux-arm64-musl@npm:1.3.62": + version: 1.3.62 + resolution: "@swc/core-linux-arm64-musl@npm:1.3.62" conditions: os=linux & cpu=arm64 & libc=musl languageName: node linkType: hard -"@swc/core-linux-x64-gnu@npm:1.3.59": - version: 1.3.59 - resolution: "@swc/core-linux-x64-gnu@npm:1.3.59" +"@swc/core-linux-x64-gnu@npm:1.3.62": + version: 1.3.62 + resolution: "@swc/core-linux-x64-gnu@npm:1.3.62" conditions: os=linux & cpu=x64 & libc=glibc languageName: node linkType: hard -"@swc/core-linux-x64-musl@npm:1.3.59": - version: 1.3.59 - resolution: "@swc/core-linux-x64-musl@npm:1.3.59" +"@swc/core-linux-x64-musl@npm:1.3.62": + version: 1.3.62 + resolution: "@swc/core-linux-x64-musl@npm:1.3.62" conditions: os=linux & cpu=x64 & libc=musl languageName: node linkType: hard -"@swc/core-win32-arm64-msvc@npm:1.3.59": - version: 1.3.59 - resolution: "@swc/core-win32-arm64-msvc@npm:1.3.59" +"@swc/core-win32-arm64-msvc@npm:1.3.62": + version: 1.3.62 + resolution: "@swc/core-win32-arm64-msvc@npm:1.3.62" conditions: os=win32 & cpu=arm64 languageName: node linkType: hard -"@swc/core-win32-ia32-msvc@npm:1.3.59": - version: 1.3.59 - resolution: "@swc/core-win32-ia32-msvc@npm:1.3.59" +"@swc/core-win32-ia32-msvc@npm:1.3.62": + version: 1.3.62 + resolution: "@swc/core-win32-ia32-msvc@npm:1.3.62" conditions: os=win32 & cpu=ia32 languageName: node linkType: hard -"@swc/core-win32-x64-msvc@npm:1.3.59": - version: 1.3.59 - resolution: "@swc/core-win32-x64-msvc@npm:1.3.59" +"@swc/core-win32-x64-msvc@npm:1.3.62": + version: 1.3.62 + resolution: "@swc/core-win32-x64-msvc@npm:1.3.62" conditions: os=win32 & cpu=x64 languageName: node linkType: hard "@swc/core@npm:^1.3.46": - version: 1.3.59 - resolution: "@swc/core@npm:1.3.59" + version: 1.3.62 + resolution: "@swc/core@npm:1.3.62" dependencies: - "@swc/core-darwin-arm64": 1.3.59 - "@swc/core-darwin-x64": 1.3.59 - "@swc/core-linux-arm-gnueabihf": 1.3.59 - "@swc/core-linux-arm64-gnu": 1.3.59 - "@swc/core-linux-arm64-musl": 1.3.59 - "@swc/core-linux-x64-gnu": 1.3.59 - "@swc/core-linux-x64-musl": 1.3.59 - "@swc/core-win32-arm64-msvc": 1.3.59 - "@swc/core-win32-ia32-msvc": 1.3.59 - "@swc/core-win32-x64-msvc": 1.3.59 + "@swc/core-darwin-arm64": 1.3.62 + "@swc/core-darwin-x64": 1.3.62 + "@swc/core-linux-arm-gnueabihf": 1.3.62 + "@swc/core-linux-arm64-gnu": 1.3.62 + "@swc/core-linux-arm64-musl": 1.3.62 + "@swc/core-linux-x64-gnu": 1.3.62 + "@swc/core-linux-x64-musl": 1.3.62 + "@swc/core-win32-arm64-msvc": 1.3.62 + "@swc/core-win32-ia32-msvc": 1.3.62 + "@swc/core-win32-x64-msvc": 1.3.62 peerDependencies: "@swc/helpers": ^0.5.0 dependenciesMeta: @@ -2714,7 +2714,7 @@ __metadata: peerDependenciesMeta: "@swc/helpers": optional: true - checksum: 0283f39cf49cd12a6dc7062ef9ea4fa93e1a4f622ce46903a09605219f4f47ed5ad03925c6146d09ffe6ee02a89bb14e3c82eb86b4c60ecce4985ea6e078ffcf + checksum: a7a0d9ffdb8a2b0050e0ff89fdb86fe189d9bcb7f91cb6847f1bfe3e2b520a87ea2e83692dfd80b6d541fb5addb2194769484516b8ca6d3c62ad80f1c79a9368 languageName: node linkType: hard diff --git a/storybook/yarn.lock b/storybook/yarn.lock index 81b855f297..91ad8fd083 100644 --- a/storybook/yarn.lock +++ b/storybook/yarn.lock @@ -2943,90 +2943,90 @@ __metadata: languageName: node linkType: hard -"@swc/core-darwin-arm64@npm:1.3.59": - version: 1.3.59 - resolution: "@swc/core-darwin-arm64@npm:1.3.59" +"@swc/core-darwin-arm64@npm:1.3.62": + version: 1.3.62 + resolution: "@swc/core-darwin-arm64@npm:1.3.62" conditions: os=darwin & cpu=arm64 languageName: node linkType: hard -"@swc/core-darwin-x64@npm:1.3.59": - version: 1.3.59 - resolution: "@swc/core-darwin-x64@npm:1.3.59" +"@swc/core-darwin-x64@npm:1.3.62": + version: 1.3.62 + resolution: "@swc/core-darwin-x64@npm:1.3.62" conditions: os=darwin & cpu=x64 languageName: node linkType: hard -"@swc/core-linux-arm-gnueabihf@npm:1.3.59": - version: 1.3.59 - resolution: "@swc/core-linux-arm-gnueabihf@npm:1.3.59" +"@swc/core-linux-arm-gnueabihf@npm:1.3.62": + version: 1.3.62 + resolution: "@swc/core-linux-arm-gnueabihf@npm:1.3.62" conditions: os=linux & cpu=arm languageName: node linkType: hard -"@swc/core-linux-arm64-gnu@npm:1.3.59": - version: 1.3.59 - resolution: "@swc/core-linux-arm64-gnu@npm:1.3.59" +"@swc/core-linux-arm64-gnu@npm:1.3.62": + version: 1.3.62 + resolution: "@swc/core-linux-arm64-gnu@npm:1.3.62" conditions: os=linux & cpu=arm64 & libc=glibc languageName: node linkType: hard -"@swc/core-linux-arm64-musl@npm:1.3.59": - version: 1.3.59 - resolution: "@swc/core-linux-arm64-musl@npm:1.3.59" +"@swc/core-linux-arm64-musl@npm:1.3.62": + version: 1.3.62 + resolution: "@swc/core-linux-arm64-musl@npm:1.3.62" conditions: os=linux & cpu=arm64 & libc=musl languageName: node linkType: hard -"@swc/core-linux-x64-gnu@npm:1.3.59": - version: 1.3.59 - resolution: "@swc/core-linux-x64-gnu@npm:1.3.59" +"@swc/core-linux-x64-gnu@npm:1.3.62": + version: 1.3.62 + resolution: "@swc/core-linux-x64-gnu@npm:1.3.62" conditions: os=linux & cpu=x64 & libc=glibc languageName: node linkType: hard -"@swc/core-linux-x64-musl@npm:1.3.59": - version: 1.3.59 - resolution: "@swc/core-linux-x64-musl@npm:1.3.59" +"@swc/core-linux-x64-musl@npm:1.3.62": + version: 1.3.62 + resolution: "@swc/core-linux-x64-musl@npm:1.3.62" conditions: os=linux & cpu=x64 & libc=musl languageName: node linkType: hard -"@swc/core-win32-arm64-msvc@npm:1.3.59": - version: 1.3.59 - resolution: "@swc/core-win32-arm64-msvc@npm:1.3.59" +"@swc/core-win32-arm64-msvc@npm:1.3.62": + version: 1.3.62 + resolution: "@swc/core-win32-arm64-msvc@npm:1.3.62" conditions: os=win32 & cpu=arm64 languageName: node linkType: hard -"@swc/core-win32-ia32-msvc@npm:1.3.59": - version: 1.3.59 - resolution: "@swc/core-win32-ia32-msvc@npm:1.3.59" +"@swc/core-win32-ia32-msvc@npm:1.3.62": + version: 1.3.62 + resolution: "@swc/core-win32-ia32-msvc@npm:1.3.62" conditions: os=win32 & cpu=ia32 languageName: node linkType: hard -"@swc/core-win32-x64-msvc@npm:1.3.59": - version: 1.3.59 - resolution: "@swc/core-win32-x64-msvc@npm:1.3.59" +"@swc/core-win32-x64-msvc@npm:1.3.62": + version: 1.3.62 + resolution: "@swc/core-win32-x64-msvc@npm:1.3.62" conditions: os=win32 & cpu=x64 languageName: node linkType: hard "@swc/core@npm:^1.3.46": - version: 1.3.59 - resolution: "@swc/core@npm:1.3.59" + version: 1.3.62 + resolution: "@swc/core@npm:1.3.62" dependencies: - "@swc/core-darwin-arm64": 1.3.59 - "@swc/core-darwin-x64": 1.3.59 - "@swc/core-linux-arm-gnueabihf": 1.3.59 - "@swc/core-linux-arm64-gnu": 1.3.59 - "@swc/core-linux-arm64-musl": 1.3.59 - "@swc/core-linux-x64-gnu": 1.3.59 - "@swc/core-linux-x64-musl": 1.3.59 - "@swc/core-win32-arm64-msvc": 1.3.59 - "@swc/core-win32-ia32-msvc": 1.3.59 - "@swc/core-win32-x64-msvc": 1.3.59 + "@swc/core-darwin-arm64": 1.3.62 + "@swc/core-darwin-x64": 1.3.62 + "@swc/core-linux-arm-gnueabihf": 1.3.62 + "@swc/core-linux-arm64-gnu": 1.3.62 + "@swc/core-linux-arm64-musl": 1.3.62 + "@swc/core-linux-x64-gnu": 1.3.62 + "@swc/core-linux-x64-musl": 1.3.62 + "@swc/core-win32-arm64-msvc": 1.3.62 + "@swc/core-win32-ia32-msvc": 1.3.62 + "@swc/core-win32-x64-msvc": 1.3.62 peerDependencies: "@swc/helpers": ^0.5.0 dependenciesMeta: @@ -3053,7 +3053,7 @@ __metadata: peerDependenciesMeta: "@swc/helpers": optional: true - checksum: 0283f39cf49cd12a6dc7062ef9ea4fa93e1a4f622ce46903a09605219f4f47ed5ad03925c6146d09ffe6ee02a89bb14e3c82eb86b4c60ecce4985ea6e078ffcf + checksum: a7a0d9ffdb8a2b0050e0ff89fdb86fe189d9bcb7f91cb6847f1bfe3e2b520a87ea2e83692dfd80b6d541fb5addb2194769484516b8ca6d3c62ad80f1c79a9368 languageName: node linkType: hard diff --git a/yarn.lock b/yarn.lock index bb25e3b9ed..a8593c125c 100644 --- a/yarn.lock +++ b/yarn.lock @@ -15575,90 +15575,90 @@ __metadata: languageName: node linkType: hard -"@swc/core-darwin-arm64@npm:1.3.59": - version: 1.3.59 - resolution: "@swc/core-darwin-arm64@npm:1.3.59" +"@swc/core-darwin-arm64@npm:1.3.62": + version: 1.3.62 + resolution: "@swc/core-darwin-arm64@npm:1.3.62" conditions: os=darwin & cpu=arm64 languageName: node linkType: hard -"@swc/core-darwin-x64@npm:1.3.59": - version: 1.3.59 - resolution: "@swc/core-darwin-x64@npm:1.3.59" +"@swc/core-darwin-x64@npm:1.3.62": + version: 1.3.62 + resolution: "@swc/core-darwin-x64@npm:1.3.62" conditions: os=darwin & cpu=x64 languageName: node linkType: hard -"@swc/core-linux-arm-gnueabihf@npm:1.3.59": - version: 1.3.59 - resolution: "@swc/core-linux-arm-gnueabihf@npm:1.3.59" +"@swc/core-linux-arm-gnueabihf@npm:1.3.62": + version: 1.3.62 + resolution: "@swc/core-linux-arm-gnueabihf@npm:1.3.62" conditions: os=linux & cpu=arm languageName: node linkType: hard -"@swc/core-linux-arm64-gnu@npm:1.3.59": - version: 1.3.59 - resolution: "@swc/core-linux-arm64-gnu@npm:1.3.59" +"@swc/core-linux-arm64-gnu@npm:1.3.62": + version: 1.3.62 + resolution: "@swc/core-linux-arm64-gnu@npm:1.3.62" conditions: os=linux & cpu=arm64 & libc=glibc languageName: node linkType: hard -"@swc/core-linux-arm64-musl@npm:1.3.59": - version: 1.3.59 - resolution: "@swc/core-linux-arm64-musl@npm:1.3.59" +"@swc/core-linux-arm64-musl@npm:1.3.62": + version: 1.3.62 + resolution: "@swc/core-linux-arm64-musl@npm:1.3.62" conditions: os=linux & cpu=arm64 & libc=musl languageName: node linkType: hard -"@swc/core-linux-x64-gnu@npm:1.3.59": - version: 1.3.59 - resolution: "@swc/core-linux-x64-gnu@npm:1.3.59" +"@swc/core-linux-x64-gnu@npm:1.3.62": + version: 1.3.62 + resolution: "@swc/core-linux-x64-gnu@npm:1.3.62" conditions: os=linux & cpu=x64 & libc=glibc languageName: node linkType: hard -"@swc/core-linux-x64-musl@npm:1.3.59": - version: 1.3.59 - resolution: "@swc/core-linux-x64-musl@npm:1.3.59" +"@swc/core-linux-x64-musl@npm:1.3.62": + version: 1.3.62 + resolution: "@swc/core-linux-x64-musl@npm:1.3.62" conditions: os=linux & cpu=x64 & libc=musl languageName: node linkType: hard -"@swc/core-win32-arm64-msvc@npm:1.3.59": - version: 1.3.59 - resolution: "@swc/core-win32-arm64-msvc@npm:1.3.59" +"@swc/core-win32-arm64-msvc@npm:1.3.62": + version: 1.3.62 + resolution: "@swc/core-win32-arm64-msvc@npm:1.3.62" conditions: os=win32 & cpu=arm64 languageName: node linkType: hard -"@swc/core-win32-ia32-msvc@npm:1.3.59": - version: 1.3.59 - resolution: "@swc/core-win32-ia32-msvc@npm:1.3.59" +"@swc/core-win32-ia32-msvc@npm:1.3.62": + version: 1.3.62 + resolution: "@swc/core-win32-ia32-msvc@npm:1.3.62" conditions: os=win32 & cpu=ia32 languageName: node linkType: hard -"@swc/core-win32-x64-msvc@npm:1.3.59": - version: 1.3.59 - resolution: "@swc/core-win32-x64-msvc@npm:1.3.59" +"@swc/core-win32-x64-msvc@npm:1.3.62": + version: 1.3.62 + resolution: "@swc/core-win32-x64-msvc@npm:1.3.62" conditions: os=win32 & cpu=x64 languageName: node linkType: hard "@swc/core@npm:^1.3.46": - version: 1.3.59 - resolution: "@swc/core@npm:1.3.59" + version: 1.3.62 + resolution: "@swc/core@npm:1.3.62" dependencies: - "@swc/core-darwin-arm64": 1.3.59 - "@swc/core-darwin-x64": 1.3.59 - "@swc/core-linux-arm-gnueabihf": 1.3.59 - "@swc/core-linux-arm64-gnu": 1.3.59 - "@swc/core-linux-arm64-musl": 1.3.59 - "@swc/core-linux-x64-gnu": 1.3.59 - "@swc/core-linux-x64-musl": 1.3.59 - "@swc/core-win32-arm64-msvc": 1.3.59 - "@swc/core-win32-ia32-msvc": 1.3.59 - "@swc/core-win32-x64-msvc": 1.3.59 + "@swc/core-darwin-arm64": 1.3.62 + "@swc/core-darwin-x64": 1.3.62 + "@swc/core-linux-arm-gnueabihf": 1.3.62 + "@swc/core-linux-arm64-gnu": 1.3.62 + "@swc/core-linux-arm64-musl": 1.3.62 + "@swc/core-linux-x64-gnu": 1.3.62 + "@swc/core-linux-x64-musl": 1.3.62 + "@swc/core-win32-arm64-msvc": 1.3.62 + "@swc/core-win32-ia32-msvc": 1.3.62 + "@swc/core-win32-x64-msvc": 1.3.62 peerDependencies: "@swc/helpers": ^0.5.0 dependenciesMeta: @@ -15685,7 +15685,7 @@ __metadata: peerDependenciesMeta: "@swc/helpers": optional: true - checksum: 0283f39cf49cd12a6dc7062ef9ea4fa93e1a4f622ce46903a09605219f4f47ed5ad03925c6146d09ffe6ee02a89bb14e3c82eb86b4c60ecce4985ea6e078ffcf + checksum: a7a0d9ffdb8a2b0050e0ff89fdb86fe189d9bcb7f91cb6847f1bfe3e2b520a87ea2e83692dfd80b6d541fb5addb2194769484516b8ca6d3c62ad80f1c79a9368 languageName: node linkType: hard From a84c759bb607fa721e24e21cf7616e14c28e978b Mon Sep 17 00:00:00 2001 From: "renovate[bot]" <29139614+renovate[bot]@users.noreply.github.com> Date: Mon, 5 Jun 2023 02:39:38 +0000 Subject: [PATCH 33/65] chore(deps): update dependency @frsource/cypress-plugin-visual-regression-diff to v3.3.6 Signed-off-by: renovate[bot] <29139614+renovate[bot]@users.noreply.github.com> --- yarn.lock | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/yarn.lock b/yarn.lock index bb25e3b9ed..d0d1cbeea2 100644 --- a/yarn.lock +++ b/yarn.lock @@ -11160,8 +11160,8 @@ __metadata: linkType: hard "@frsource/cypress-plugin-visual-regression-diff@npm:^3.2.8": - version: 3.3.1 - resolution: "@frsource/cypress-plugin-visual-regression-diff@npm:3.3.1" + version: 3.3.6 + resolution: "@frsource/cypress-plugin-visual-regression-diff@npm:3.3.6" dependencies: "@frsource/base64": 1.0.14 glob: 8.0.3 @@ -11172,7 +11172,7 @@ __metadata: sharp: 0.31.2 peerDependencies: cypress: ">=4.5.0" - checksum: fae1e9de89fcc0f75a71dd7cc78cb870fa4d0989a0dd2e1084eec2fdc95f9ff503a124f05ea88f87b52c3d03463a79e96439e5620a6c0f24ac39135c81af9edc + checksum: d4cacc040c64221948b1974a3f0ee0820f404715fe0b2723e508ec0d8f45748a8f434e9d42b7dfe20999eae4ddf22e872a5e876ed901a04e51ebe8930fcfb5e8 languageName: node linkType: hard From d48578cd66f4b8f92a09556178e163a219b0643e Mon Sep 17 00:00:00 2001 From: "renovate[bot]" <29139614+renovate[bot]@users.noreply.github.com> Date: Mon, 5 Jun 2023 03:24:15 +0000 Subject: [PATCH 34/65] fix(deps): update dependency @apollo/client to v3.7.15 Signed-off-by: renovate[bot] <29139614+renovate[bot]@users.noreply.github.com> --- yarn.lock | 17 +++++++++++++---- 1 file changed, 13 insertions(+), 4 deletions(-) diff --git a/yarn.lock b/yarn.lock index d0d1cbeea2..a0dd348701 100644 --- a/yarn.lock +++ b/yarn.lock @@ -85,13 +85,13 @@ __metadata: linkType: hard "@apollo/client@npm:^3.0.0": - version: 3.7.14 - resolution: "@apollo/client@npm:3.7.14" + version: 3.7.15 + resolution: "@apollo/client@npm:3.7.15" dependencies: "@graphql-typed-document-node/core": ^3.1.1 "@wry/context": ^0.7.0 "@wry/equality": ^0.5.0 - "@wry/trie": ^0.3.0 + "@wry/trie": ^0.4.0 graphql-tag: ^2.12.6 hoist-non-react-statics: ^3.3.2 optimism: ^0.16.2 @@ -116,7 +116,7 @@ __metadata: optional: true subscriptions-transport-ws: optional: true - checksum: eaa8af74450fee4d4761d25fb8fe752788517b27ebb46a51b6496950c5b73f48b6ba3e4f3474b6e4a4f310916dc3fcf079306c35f16d4284b96c7fdbb8539fde + checksum: a33e56847dfb7d6176ffb3cd4d3ff2c548826ce51280a6c8f70e3d75daf9d3a287e79bf3d86ea0b16e39218c90d8a7b4f528eb340055387cf9137705970c0f59 languageName: node linkType: hard @@ -18413,6 +18413,15 @@ __metadata: languageName: node linkType: hard +"@wry/trie@npm:^0.4.0": + version: 0.4.3 + resolution: "@wry/trie@npm:0.4.3" + dependencies: + tslib: ^2.3.0 + checksum: 106e021125cfafd22250a6631a0438a6a3debae7bd73f6db87fe42aa0757fe67693db0dfbe200ae1f60ba608c3e09ddb8a4e2b3527d56ed0a7e02aa0ee4c94e1 + languageName: node + linkType: hard + "@xmldom/xmldom@npm:^0.7.0, @xmldom/xmldom@npm:^0.7.5, @xmldom/xmldom@npm:^0.7.6": version: 0.7.9 resolution: "@xmldom/xmldom@npm:0.7.9" From 0900dc2b34631fac63164317c1e8018569bb1078 Mon Sep 17 00:00:00 2001 From: "renovate[bot]" <29139614+renovate[bot]@users.noreply.github.com> Date: Mon, 5 Jun 2023 04:00:44 +0000 Subject: [PATCH 35/65] fix(deps): update dependency @google-cloud/firestore to v6.6.1 Signed-off-by: renovate[bot] <29139614+renovate[bot]@users.noreply.github.com> --- yarn.lock | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/yarn.lock b/yarn.lock index a0dd348701..b6ac70dcc7 100644 --- a/yarn.lock +++ b/yarn.lock @@ -11243,14 +11243,14 @@ __metadata: linkType: hard "@google-cloud/firestore@npm:^6.0.0": - version: 6.6.0 - resolution: "@google-cloud/firestore@npm:6.6.0" + version: 6.6.1 + resolution: "@google-cloud/firestore@npm:6.6.1" dependencies: fast-deep-equal: ^3.1.1 functional-red-black-tree: ^1.0.1 google-gax: ^3.5.7 protobufjs: ^7.0.0 - checksum: a3f6e9998159fae81d1a78371dc5d0d2a5b6b4e8e685ed5bf7a5a66c7b4b36beef010c6d38a77131c76ca4cbf6b9be352ac0dd39a9a9d286e931e8c9eaa95456 + checksum: 9f3838e07d74da34ba4cf322efd3f82e3b8f5b330ae01c0e51d717aacafe2a84caa2869989bbff87fe020086f5b8591baaaf8c643dc93c20fd3f6f2adfd67a24 languageName: node linkType: hard From 83c1639be6da4c58e3f1ec4dd31a56a3668acd02 Mon Sep 17 00:00:00 2001 From: "renovate[bot]" <29139614+renovate[bot]@users.noreply.github.com> Date: Mon, 5 Jun 2023 04:36:26 +0000 Subject: [PATCH 36/65] chore(deps): update dependency @frsource/cypress-plugin-visual-regression-diff to v3.3.7 Signed-off-by: renovate[bot] <29139614+renovate[bot]@users.noreply.github.com> --- yarn.lock | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/yarn.lock b/yarn.lock index b6ac70dcc7..15e1d53133 100644 --- a/yarn.lock +++ b/yarn.lock @@ -11160,8 +11160,8 @@ __metadata: linkType: hard "@frsource/cypress-plugin-visual-regression-diff@npm:^3.2.8": - version: 3.3.6 - resolution: "@frsource/cypress-plugin-visual-regression-diff@npm:3.3.6" + version: 3.3.7 + resolution: "@frsource/cypress-plugin-visual-regression-diff@npm:3.3.7" dependencies: "@frsource/base64": 1.0.14 glob: 8.0.3 @@ -11172,7 +11172,7 @@ __metadata: sharp: 0.31.2 peerDependencies: cypress: ">=4.5.0" - checksum: d4cacc040c64221948b1974a3f0ee0820f404715fe0b2723e508ec0d8f45748a8f434e9d42b7dfe20999eae4ddf22e872a5e876ed901a04e51ebe8930fcfb5e8 + checksum: 8521afd0627525d3523307c56eb74b5ca7cce45835cce22e20f9864066f2493efba209165bfce33c00271f0ffa71e6b0a98f43e20614f92a9f529bbc95876c66 languageName: node linkType: hard From 31da41e5850077e1588777e6a6aa5e1aba344e11 Mon Sep 17 00:00:00 2001 From: "renovate[bot]" <29139614+renovate[bot]@users.noreply.github.com> Date: Mon, 5 Jun 2023 05:11:41 +0000 Subject: [PATCH 37/65] chore(deps): update dependency eslint to v8.42.0 Signed-off-by: renovate[bot] <29139614+renovate[bot]@users.noreply.github.com> --- yarn.lock | 26 +++++++++++++------------- 1 file changed, 13 insertions(+), 13 deletions(-) diff --git a/yarn.lock b/yarn.lock index 15e1d53133..9b7dc1f57b 100644 --- a/yarn.lock +++ b/yarn.lock @@ -11086,10 +11086,10 @@ __metadata: languageName: node linkType: hard -"@eslint/js@npm:8.41.0": - version: 8.41.0 - resolution: "@eslint/js@npm:8.41.0" - checksum: af013d70fe8d0429cdf5cd8b5dcc6fc384ed026c1eccb0cfe30f5849b968ab91645111373fd1b83282b38955b1bdfbe667c1a7dbda3b06cae753521223cad775 +"@eslint/js@npm:8.42.0": + version: 8.42.0 + resolution: "@eslint/js@npm:8.42.0" + checksum: 750558843ac458f7da666122083ee05306fc087ecc1e5b21e7e14e23885775af6c55bcc92283dff1862b7b0d8863ec676c0f18c7faf1219c722fe91a8ece56b6 languageName: node linkType: hard @@ -12122,14 +12122,14 @@ __metadata: languageName: node linkType: hard -"@humanwhocodes/config-array@npm:^0.11.8": - version: 0.11.8 - resolution: "@humanwhocodes/config-array@npm:0.11.8" +"@humanwhocodes/config-array@npm:^0.11.10": + version: 0.11.10 + resolution: "@humanwhocodes/config-array@npm:0.11.10" dependencies: "@humanwhocodes/object-schema": ^1.2.1 debug: ^4.1.1 minimatch: ^3.0.5 - checksum: 0fd6b3c54f1674ce0a224df09b9c2f9846d20b9e54fabae1281ecfc04f2e6ad69bf19e1d6af6a28f88e8aa3990168b6cb9e1ef755868c3256a630605ec2cb1d3 + checksum: 1b1302e2403d0e35bc43e66d67a2b36b0ad1119efc704b5faff68c41f791a052355b010fb2d27ef022670f550de24cd6d08d5ecf0821c16326b7dcd0ee5d5d8a languageName: node linkType: hard @@ -24245,14 +24245,14 @@ __metadata: linkType: hard "eslint@npm:^8.33.0, eslint@npm:^8.6.0": - version: 8.41.0 - resolution: "eslint@npm:8.41.0" + version: 8.42.0 + resolution: "eslint@npm:8.42.0" dependencies: "@eslint-community/eslint-utils": ^4.2.0 "@eslint-community/regexpp": ^4.4.0 "@eslint/eslintrc": ^2.0.3 - "@eslint/js": 8.41.0 - "@humanwhocodes/config-array": ^0.11.8 + "@eslint/js": 8.42.0 + "@humanwhocodes/config-array": ^0.11.10 "@humanwhocodes/module-importer": ^1.0.1 "@nodelib/fs.walk": ^1.2.8 ajv: ^6.10.0 @@ -24289,7 +24289,7 @@ __metadata: text-table: ^0.2.0 bin: eslint: bin/eslint.js - checksum: 09979a6f8451dcc508a7005b6670845c8a518376280b3fd96657a406b8b6ef29d0e480d1ba11b4eb48da93d607e0c55c9b877676fe089d09973ec152354e23b2 + checksum: 07105397b5f2ff4064b983b8971e8c379ec04b1dfcc9d918976b3e00377189000161dac991d82ba14f8759e466091b8c71146f602930ca810c290ee3fcb3faf0 languageName: node linkType: hard From f09ff5c3fb1706918ec4dc0a3233416bd91f829c Mon Sep 17 00:00:00 2001 From: "renovate[bot]" <29139614+renovate[bot]@users.noreply.github.com> Date: Mon, 5 Jun 2023 05:52:07 +0000 Subject: [PATCH 38/65] chore(deps): update dependency webpack to v5.85.0 Signed-off-by: renovate[bot] <29139614+renovate[bot]@users.noreply.github.com> --- storybook/yarn.lock | 6 +++--- yarn.lock | 6 +++--- 2 files changed, 6 insertions(+), 6 deletions(-) diff --git a/storybook/yarn.lock b/storybook/yarn.lock index 81b855f297..da1088ddd5 100644 --- a/storybook/yarn.lock +++ b/storybook/yarn.lock @@ -11863,8 +11863,8 @@ __metadata: linkType: hard "webpack@npm:^5.73.0": - version: 5.84.1 - resolution: "webpack@npm:5.84.1" + version: 5.85.0 + resolution: "webpack@npm:5.85.0" dependencies: "@types/eslint-scope": ^3.7.3 "@types/estree": ^1.0.0 @@ -11895,7 +11895,7 @@ __metadata: optional: true bin: webpack: bin/webpack.js - checksum: 646b645df5badf2dac2ddd0193c9e9a177d51283d18f918eead36a0cdf7b750c4111d9ac11d9825c1334cbd0a6fb8f82628fbfb90d0066f927265dd11b47b192 + checksum: b013be9fbc7f6810d1f229f570c70710ddbc7290f817411acffe4214b2b6c783a041ab1f2005d9e1109f4ab21c136f0f8d8c067a5fb64f20a82dcbc1ee0d3f42 languageName: node linkType: hard diff --git a/yarn.lock b/yarn.lock index 9b7dc1f57b..e8e83ff349 100644 --- a/yarn.lock +++ b/yarn.lock @@ -41224,8 +41224,8 @@ __metadata: linkType: hard "webpack@npm:^5, webpack@npm:^5.70.0": - version: 5.84.1 - resolution: "webpack@npm:5.84.1" + version: 5.85.0 + resolution: "webpack@npm:5.85.0" dependencies: "@types/eslint-scope": ^3.7.3 "@types/estree": ^1.0.0 @@ -41256,7 +41256,7 @@ __metadata: optional: true bin: webpack: bin/webpack.js - checksum: 646b645df5badf2dac2ddd0193c9e9a177d51283d18f918eead36a0cdf7b750c4111d9ac11d9825c1334cbd0a6fb8f82628fbfb90d0066f927265dd11b47b192 + checksum: b013be9fbc7f6810d1f229f570c70710ddbc7290f817411acffe4214b2b6c783a041ab1f2005d9e1109f4ab21c136f0f8d8c067a5fb64f20a82dcbc1ee0d3f42 languageName: node linkType: hard From 84b0e47373db5b51b99862bd29f5ecef159a0c61 Mon Sep 17 00:00:00 2001 From: mingfu Date: Mon, 5 Jun 2023 15:08:19 +0800 Subject: [PATCH 39/65] chore: Add `TargetBranchName` variable and output for the `publish:gitlab:merge-request` and `publish:github:pull-request` s'cascaffolder actions. Signed-off-by: mingfu --- .changeset/fifty-shirts-brush.md | 5 + plugins/scaffolder-backend/api-report.md | 5 + .../builtin/publish/githubPullRequest.test.ts | 92 +++++++++++++++++++ .../builtin/publish/githubPullRequest.ts | 24 ++++- .../publish/gitlabMergeRequest.test.ts | 51 ++++++++++ .../builtin/publish/gitlabMergeRequest.ts | 28 ++++-- 6 files changed, 197 insertions(+), 8 deletions(-) create mode 100644 .changeset/fifty-shirts-brush.md diff --git a/.changeset/fifty-shirts-brush.md b/.changeset/fifty-shirts-brush.md new file mode 100644 index 0000000000..98cd7b885c --- /dev/null +++ b/.changeset/fifty-shirts-brush.md @@ -0,0 +1,5 @@ +--- +'@backstage/plugin-scaffolder-backend': minor +--- + +Add `TargetBranchName` variable and output for the `publish:gitlab:merge-request` and `publish:github:pull-request` s'cascaffolder actions. diff --git a/plugins/scaffolder-backend/api-report.md b/plugins/scaffolder-backend/api-report.md index 5e18ad15bf..0e686c31f3 100644 --- a/plugins/scaffolder-backend/api-report.md +++ b/plugins/scaffolder-backend/api-report.md @@ -584,6 +584,7 @@ export const createPublishGithubPullRequestAction: ( { title: string; branchName: string; + targetBranchName?: string | undefined; description: string; repoUrl: string; draft?: boolean | undefined; @@ -626,6 +627,7 @@ export const createPublishGitlabMergeRequestAction: (options: { title: string; description: string; branchName: string; + targetBranchName?: string | undefined; sourcePath?: string | undefined; targetPath?: string | undefined; token?: string | undefined; @@ -772,6 +774,9 @@ export type OctokitWithPullRequestPluginClient = Octokit & { data: { html_url: string; number: number; + base: { + ref: string; + }; }; } | null>; }; diff --git a/plugins/scaffolder-backend/src/scaffolder/actions/builtin/publish/githubPullRequest.test.ts b/plugins/scaffolder-backend/src/scaffolder/actions/builtin/publish/githubPullRequest.test.ts index 7750277728..82f8d22aea 100644 --- a/plugins/scaffolder-backend/src/scaffolder/actions/builtin/publish/githubPullRequest.test.ts +++ b/plugins/scaffolder-backend/src/scaffolder/actions/builtin/publish/githubPullRequest.test.ts @@ -62,6 +62,9 @@ describe('createPublishGithubPullRequestAction', () => { data: { html_url: 'https://github.com/myorg/myrepo/pull/123', number: 123, + base: { + ref: 'main', + }, }, }; }), @@ -90,6 +93,94 @@ describe('createPublishGithubPullRequestAction', () => { jest.resetAllMocks(); }); + describe('with targetBranchName', () => { + let input: GithubPullRequestActionInput; + let ctx: ActionContext; + + beforeEach(() => { + fakeClient = { + createPullRequest: jest.fn(async (_: any) => { + return { + url: 'https://api.github.com/myorg/myrepo/pull/123', + headers: {}, + status: 201, + data: { + html_url: 'https://github.com/myorg/myrepo/pull/123', + number: 123, + base: { + ref: 'test', + }, + }, + }; + }), + rest: { + pulls: { + requestReviewers: jest.fn(async (_: any) => ({ data: {} })), + }, + }, + }; + + input = { + repoUrl: 'github.com?owner=myorg&repo=myrepo', + title: 'Create my new app', + branchName: 'new-app', + targetBranchName: 'test', + description: 'This PR is really good', + draft: true, + }; + + mockFs({ + [workspacePath]: { 'file.txt': 'Hello there!' }, + }); + + ctx = { + createTemporaryDirectory: jest.fn(), + output: jest.fn(), + logger: getRootLogger(), + logStream: new Writable(), + input, + workspacePath, + }; + }); + + it('creates a pull request', async () => { + await instance.handler(ctx); + + expect(fakeClient.createPullRequest).toHaveBeenCalledWith({ + owner: 'myorg', + repo: 'myrepo', + title: 'Create my new app', + head: 'new-app', + base: 'test', + body: 'This PR is really good', + draft: true, + changes: [ + { + commit: 'Create my new app', + files: { + 'file.txt': { + content: Buffer.from('Hello there!').toString('base64'), + encoding: 'base64', + mode: '100644', + }, + }, + }, + ], + }); + }); + + it('creates outputs for the pull request url and number', async () => { + await instance.handler(ctx); + + expect(ctx.output).toHaveBeenCalledWith('targetBranchName', 'test'); + expect(ctx.output).toHaveBeenCalledWith( + 'remoteUrl', + 'https://github.com/myorg/myrepo/pull/123', + ); + expect(ctx.output).toHaveBeenCalledWith('pullRequestNumber', 123); + }); + }); + describe('with no sourcePath', () => { let input: GithubPullRequestActionInput; let ctx: ActionContext; @@ -145,6 +236,7 @@ describe('createPublishGithubPullRequestAction', () => { it('creates outputs for the pull request url and number', async () => { await instance.handler(ctx); + expect(ctx.output).toHaveBeenCalledWith('targetBranchName', 'main'); expect(ctx.output).toHaveBeenCalledWith( 'remoteUrl', 'https://github.com/myorg/myrepo/pull/123', diff --git a/plugins/scaffolder-backend/src/scaffolder/actions/builtin/publish/githubPullRequest.ts b/plugins/scaffolder-backend/src/scaffolder/actions/builtin/publish/githubPullRequest.ts index 6706ad9c06..167fedc88e 100644 --- a/plugins/scaffolder-backend/src/scaffolder/actions/builtin/publish/githubPullRequest.ts +++ b/plugins/scaffolder-backend/src/scaffolder/actions/builtin/publish/githubPullRequest.ts @@ -42,6 +42,9 @@ export type OctokitWithPullRequestPluginClient = Octokit & { data: { html_url: string; number: number; + base: { + ref: string; + }; }; } | null>; }; @@ -128,6 +131,7 @@ export const createPublishGithubPullRequestAction = ( return createTemplateAction<{ title: string; branchName: string; + targetBranchName?: string; description: string; repoUrl: string; draft?: boolean; @@ -154,6 +158,11 @@ export const createPublishGithubPullRequestAction = ( title: 'Branch Name', description: 'The name for the branch', }, + targetBranchName: { + type: 'string', + title: 'Target Branch Name', + description: 'The target branch name of the merge request', + }, title: { type: 'string', title: 'Pull Request Name', @@ -214,6 +223,10 @@ export const createPublishGithubPullRequestAction = ( required: ['remoteUrl'], type: 'object', properties: { + targetBranchName: { + title: 'Target branch name of the merge request', + type: 'string', + }, remoteUrl: { type: 'string', title: 'Pull Request URL', @@ -231,6 +244,7 @@ export const createPublishGithubPullRequestAction = ( const { repoUrl, branchName, + targetBranchName, title, description, draft, @@ -298,7 +312,7 @@ export const createPublishGithubPullRequestAction = ( ); try { - const response = await client.createPullRequest({ + const createOptions: createPullRequest.Options = { owner, repo, title, @@ -311,7 +325,11 @@ export const createPublishGithubPullRequestAction = ( body: description, head: branchName, draft, - }); + }; + if (targetBranchName) { + createOptions.base = targetBranchName; + } + const response = await client.createPullRequest(createOptions); if (!response) { throw new GithubResponseError('null response from Github'); @@ -329,6 +347,8 @@ export const createPublishGithubPullRequestAction = ( ); } + const targetBranch = response.data.base.ref; + ctx.output('targetBranchName', targetBranch); ctx.output('remoteUrl', response.data.html_url); ctx.output('pullRequestNumber', pullRequestNumber); } catch (e) { diff --git a/plugins/scaffolder-backend/src/scaffolder/actions/builtin/publish/gitlabMergeRequest.test.ts b/plugins/scaffolder-backend/src/scaffolder/actions/builtin/publish/gitlabMergeRequest.test.ts index c3d0fe58f1..afb93b348a 100644 --- a/plugins/scaffolder-backend/src/scaffolder/actions/builtin/publish/gitlabMergeRequest.test.ts +++ b/plugins/scaffolder-backend/src/scaffolder/actions/builtin/publish/gitlabMergeRequest.test.ts @@ -101,6 +101,49 @@ describe('createGitLabMergeRequest', () => { mockFs.restore(); }); + describe('createGitLabMergeRequestWithSpecifiedTargetBranch', () => { + it('removeSourceBranch is false by default when not passed in options', async () => { + const input = { + repoUrl: 'gitlab.com?repo=repo&owner=owner', + title: 'Create my new MR', + branchName: 'new-mr', + targetBranchName: 'test', + description: 'This MR is really good', + targetPath: 'Subdirectory', + }; + mockFs({ + [workspacePath]: { + source: { 'foo.txt': 'Hello there!' }, + irrelevant: { 'bar.txt': 'Nothing to see here' }, + }, + }); + const ctx = { + createTemporaryDirectory: jest.fn(), + output: jest.fn(), + logger: getRootLogger(), + logStream: new Writable(), + input, + workspacePath, + }; + await instance.handler(ctx); + + expect(mockGitlabClient.Projects.show).not.toHaveBeenCalled(); + expect(mockGitlabClient.Branches.create).toHaveBeenCalledWith( + 'owner/repo', + 'new-mr', + 'test', + ); + expect(mockGitlabClient.MergeRequests.create).toHaveBeenCalledWith( + 'owner/repo', + 'new-mr', + 'test', + 'Create my new MR', + { description: 'This MR is really good', removeSourceBranch: false }, + ); + expect(ctx.output).toHaveBeenCalledWith('targetBranchName', 'test'); + }); + }); + describe('createGitLabMergeRequestWithoutRemoveBranch', () => { it('removeSourceBranch is false by default when not passed in options', async () => { const input = { @@ -126,6 +169,12 @@ describe('createGitLabMergeRequest', () => { }; await instance.handler(ctx); + expect(mockGitlabClient.Projects.show).toHaveBeenCalledWith('owner/repo'); + expect(mockGitlabClient.Branches.create).toHaveBeenCalledWith( + 'owner/repo', + 'new-mr', + 'main', + ); expect(mockGitlabClient.MergeRequests.create).toHaveBeenCalledWith( 'owner/repo', 'new-mr', @@ -133,6 +182,8 @@ describe('createGitLabMergeRequest', () => { 'Create my new MR', { description: 'This MR is really good', removeSourceBranch: false }, ); + + expect(ctx.output).toHaveBeenCalledWith('targetBranchName', 'main'); }); }); diff --git a/plugins/scaffolder-backend/src/scaffolder/actions/builtin/publish/gitlabMergeRequest.ts b/plugins/scaffolder-backend/src/scaffolder/actions/builtin/publish/gitlabMergeRequest.ts index 3dfe0cff5c..8abb53288c 100644 --- a/plugins/scaffolder-backend/src/scaffolder/actions/builtin/publish/gitlabMergeRequest.ts +++ b/plugins/scaffolder-backend/src/scaffolder/actions/builtin/publish/gitlabMergeRequest.ts @@ -39,6 +39,7 @@ export const createPublishGitlabMergeRequestAction = (options: { title: string; description: string; branchName: string; + targetBranchName?: string; sourcePath?: string; targetPath?: string; token?: string; @@ -77,8 +78,13 @@ export const createPublishGitlabMergeRequestAction = (options: { }, branchName: { type: 'string', - title: 'Destination Branch name', - description: 'The description of the merge request', + title: 'Source Branch Name', + description: 'The source branch name of the merge request', + }, + targetBranchName: { + type: 'string', + title: 'Target Branch Name', + description: 'The target branch name of the merge request', }, sourcePath: { type: 'string', @@ -119,6 +125,10 @@ export const createPublishGitlabMergeRequestAction = (options: { output: { type: 'object', properties: { + targetBranchName: { + title: 'Target branch name of the merge request', + type: 'string', + }, projectid: { title: 'Gitlab Project id/Name(slug)', type: 'string', @@ -139,6 +149,7 @@ export const createPublishGitlabMergeRequestAction = (options: { const { assignee, branchName, + targetBranchName, description, repoUrl, removeSourceBranch, @@ -211,12 +222,16 @@ export const createPublishGitlabMergeRequestAction = (options: { execute_filemode: file.executable, })); - const projects = await api.Projects.show(repoID); + let targetBranch = targetBranchName; + if (!targetBranch) { + const projects = await api.Projects.show(repoID); - const { default_branch: defaultBranch } = projects; + const { default_branch: defaultBranch } = projects; + targetBranch = defaultBranch!; + } try { - await api.Branches.create(repoID, branchName, String(defaultBranch)); + await api.Branches.create(repoID, branchName, String(targetBranch)); } catch (e) { throw new InputError( `The branch creation failed. Please check that your repo does not already contain a branch named '${branchName}'. ${e}`, @@ -235,7 +250,7 @@ export const createPublishGitlabMergeRequestAction = (options: { const mergeRequestUrl = await api.MergeRequests.create( repoID, branchName, - String(defaultBranch), + String(targetBranch), title, { description, @@ -246,6 +261,7 @@ export const createPublishGitlabMergeRequestAction = (options: { return mergeRequest.web_url; }); ctx.output('projectid', repoID); + ctx.output('targetBranchName', targetBranch); ctx.output('projectPath', repoID); ctx.output('mergeRequestUrl', mergeRequestUrl); } catch (e) { From 3f066509a9d6d2c1d73172614bdb32f28e63e6e1 Mon Sep 17 00:00:00 2001 From: "renovate[bot]" <29139614+renovate[bot]@users.noreply.github.com> Date: Mon, 5 Jun 2023 08:37:57 +0000 Subject: [PATCH 40/65] fix(deps): update aws-sdk-js-v3 monorepo to v3.342.0 Signed-off-by: renovate[bot] <29139614+renovate[bot]@users.noreply.github.com> --- yarn.lock | 1333 +++++++++++++++++++++++++++-------------------------- 1 file changed, 667 insertions(+), 666 deletions(-) diff --git a/yarn.lock b/yarn.lock index f7b450b985..6822f8f118 100644 --- a/yarn.lock +++ b/yarn.lock @@ -531,13 +531,13 @@ __metadata: languageName: node linkType: hard -"@aws-sdk/abort-controller@npm:3.338.0, @aws-sdk/abort-controller@npm:^3.310.0": - version: 3.338.0 - resolution: "@aws-sdk/abort-controller@npm:3.338.0" +"@aws-sdk/abort-controller@npm:3.342.0, @aws-sdk/abort-controller@npm:^3.310.0": + version: 3.342.0 + resolution: "@aws-sdk/abort-controller@npm:3.342.0" dependencies: - "@aws-sdk/types": 3.338.0 + "@aws-sdk/types": 3.342.0 tslib: ^2.5.0 - checksum: e86ceabc2c03a3bf5d97759e1109bc9f13479566278cd3601c614ed7056d58618bd8a2b637e6302491e23d872ffefba42d9dd81ff8142f9801aaca0e7ecb3c83 + checksum: 5681ba5f943c1843b841a16290f9a093d01a75f16fc2348ae140a1b83ecdae983696f5f59936cd91f33eb8f76701b9f4dae11ad68f6d29c785327767a6564057 languageName: node linkType: hard @@ -550,628 +550,628 @@ __metadata: languageName: node linkType: hard -"@aws-sdk/client-cognito-identity@npm:3.338.0": - version: 3.338.0 - resolution: "@aws-sdk/client-cognito-identity@npm:3.338.0" +"@aws-sdk/client-cognito-identity@npm:3.345.0": + version: 3.345.0 + resolution: "@aws-sdk/client-cognito-identity@npm:3.345.0" dependencies: "@aws-crypto/sha256-browser": 3.0.0 "@aws-crypto/sha256-js": 3.0.0 - "@aws-sdk/client-sts": 3.338.0 - "@aws-sdk/config-resolver": 3.338.0 - "@aws-sdk/credential-provider-node": 3.338.0 - "@aws-sdk/fetch-http-handler": 3.338.0 - "@aws-sdk/hash-node": 3.338.0 - "@aws-sdk/invalid-dependency": 3.338.0 - "@aws-sdk/middleware-content-length": 3.338.0 - "@aws-sdk/middleware-endpoint": 3.338.0 - "@aws-sdk/middleware-host-header": 3.338.0 - "@aws-sdk/middleware-logger": 3.338.0 - "@aws-sdk/middleware-recursion-detection": 3.338.0 - "@aws-sdk/middleware-retry": 3.338.0 - "@aws-sdk/middleware-serde": 3.338.0 - "@aws-sdk/middleware-signing": 3.338.0 - "@aws-sdk/middleware-stack": 3.338.0 - "@aws-sdk/middleware-user-agent": 3.338.0 - "@aws-sdk/node-config-provider": 3.338.0 - "@aws-sdk/node-http-handler": 3.338.0 - "@aws-sdk/smithy-client": 3.338.0 - "@aws-sdk/types": 3.338.0 - "@aws-sdk/url-parser": 3.338.0 + "@aws-sdk/client-sts": 3.345.0 + "@aws-sdk/config-resolver": 3.342.0 + "@aws-sdk/credential-provider-node": 3.345.0 + "@aws-sdk/fetch-http-handler": 3.342.0 + "@aws-sdk/hash-node": 3.344.0 + "@aws-sdk/invalid-dependency": 3.342.0 + "@aws-sdk/middleware-content-length": 3.342.0 + "@aws-sdk/middleware-endpoint": 3.344.0 + "@aws-sdk/middleware-host-header": 3.342.0 + "@aws-sdk/middleware-logger": 3.342.0 + "@aws-sdk/middleware-recursion-detection": 3.342.0 + "@aws-sdk/middleware-retry": 3.342.0 + "@aws-sdk/middleware-serde": 3.342.0 + "@aws-sdk/middleware-signing": 3.342.0 + "@aws-sdk/middleware-stack": 3.342.0 + "@aws-sdk/middleware-user-agent": 3.345.0 + "@aws-sdk/node-config-provider": 3.342.0 + "@aws-sdk/node-http-handler": 3.344.0 + "@aws-sdk/smithy-client": 3.342.0 + "@aws-sdk/types": 3.342.0 + "@aws-sdk/url-parser": 3.342.0 "@aws-sdk/util-base64": 3.310.0 "@aws-sdk/util-body-length-browser": 3.310.0 "@aws-sdk/util-body-length-node": 3.310.0 - "@aws-sdk/util-defaults-mode-browser": 3.338.0 - "@aws-sdk/util-defaults-mode-node": 3.338.0 - "@aws-sdk/util-endpoints": 3.338.0 - "@aws-sdk/util-retry": 3.338.0 - "@aws-sdk/util-user-agent-browser": 3.338.0 - "@aws-sdk/util-user-agent-node": 3.338.0 + "@aws-sdk/util-defaults-mode-browser": 3.342.0 + "@aws-sdk/util-defaults-mode-node": 3.342.0 + "@aws-sdk/util-endpoints": 3.342.0 + "@aws-sdk/util-retry": 3.342.0 + "@aws-sdk/util-user-agent-browser": 3.345.0 + "@aws-sdk/util-user-agent-node": 3.345.0 "@aws-sdk/util-utf8": 3.310.0 "@smithy/protocol-http": ^1.0.1 "@smithy/types": ^1.0.0 tslib: ^2.5.0 - checksum: d560eb2ca9b764d899e012bddfed31d7f283811b5d408eb66b99daa42dfea1077d1eba4bb0edcb8e1068ed18f1ea5fb65b0027a04b4bce935739976665c378a5 + checksum: 7dead889b689a3e4bd0c911008cafc8f362bf09377b0590f1d467a47819ca8f3185b4fe786f6b81cd0df68a5010a4ca092e4e8edc18491f71460745d0b9604d7 languageName: node linkType: hard "@aws-sdk/client-eks@npm:^3.310.0": - version: 3.338.0 - resolution: "@aws-sdk/client-eks@npm:3.338.0" + version: 3.345.0 + resolution: "@aws-sdk/client-eks@npm:3.345.0" dependencies: "@aws-crypto/sha256-browser": 3.0.0 "@aws-crypto/sha256-js": 3.0.0 - "@aws-sdk/client-sts": 3.338.0 - "@aws-sdk/config-resolver": 3.338.0 - "@aws-sdk/credential-provider-node": 3.338.0 - "@aws-sdk/fetch-http-handler": 3.338.0 - "@aws-sdk/hash-node": 3.338.0 - "@aws-sdk/invalid-dependency": 3.338.0 - "@aws-sdk/middleware-content-length": 3.338.0 - "@aws-sdk/middleware-endpoint": 3.338.0 - "@aws-sdk/middleware-host-header": 3.338.0 - "@aws-sdk/middleware-logger": 3.338.0 - "@aws-sdk/middleware-recursion-detection": 3.338.0 - "@aws-sdk/middleware-retry": 3.338.0 - "@aws-sdk/middleware-serde": 3.338.0 - "@aws-sdk/middleware-signing": 3.338.0 - "@aws-sdk/middleware-stack": 3.338.0 - "@aws-sdk/middleware-user-agent": 3.338.0 - "@aws-sdk/node-config-provider": 3.338.0 - "@aws-sdk/node-http-handler": 3.338.0 - "@aws-sdk/smithy-client": 3.338.0 - "@aws-sdk/types": 3.338.0 - "@aws-sdk/url-parser": 3.338.0 + "@aws-sdk/client-sts": 3.345.0 + "@aws-sdk/config-resolver": 3.342.0 + "@aws-sdk/credential-provider-node": 3.345.0 + "@aws-sdk/fetch-http-handler": 3.342.0 + "@aws-sdk/hash-node": 3.344.0 + "@aws-sdk/invalid-dependency": 3.342.0 + "@aws-sdk/middleware-content-length": 3.342.0 + "@aws-sdk/middleware-endpoint": 3.344.0 + "@aws-sdk/middleware-host-header": 3.342.0 + "@aws-sdk/middleware-logger": 3.342.0 + "@aws-sdk/middleware-recursion-detection": 3.342.0 + "@aws-sdk/middleware-retry": 3.342.0 + "@aws-sdk/middleware-serde": 3.342.0 + "@aws-sdk/middleware-signing": 3.342.0 + "@aws-sdk/middleware-stack": 3.342.0 + "@aws-sdk/middleware-user-agent": 3.345.0 + "@aws-sdk/node-config-provider": 3.342.0 + "@aws-sdk/node-http-handler": 3.344.0 + "@aws-sdk/smithy-client": 3.342.0 + "@aws-sdk/types": 3.342.0 + "@aws-sdk/url-parser": 3.342.0 "@aws-sdk/util-base64": 3.310.0 "@aws-sdk/util-body-length-browser": 3.310.0 "@aws-sdk/util-body-length-node": 3.310.0 - "@aws-sdk/util-defaults-mode-browser": 3.338.0 - "@aws-sdk/util-defaults-mode-node": 3.338.0 - "@aws-sdk/util-endpoints": 3.338.0 - "@aws-sdk/util-retry": 3.338.0 - "@aws-sdk/util-user-agent-browser": 3.338.0 - "@aws-sdk/util-user-agent-node": 3.338.0 + "@aws-sdk/util-defaults-mode-browser": 3.342.0 + "@aws-sdk/util-defaults-mode-node": 3.342.0 + "@aws-sdk/util-endpoints": 3.342.0 + "@aws-sdk/util-retry": 3.342.0 + "@aws-sdk/util-user-agent-browser": 3.345.0 + "@aws-sdk/util-user-agent-node": 3.345.0 "@aws-sdk/util-utf8": 3.310.0 - "@aws-sdk/util-waiter": 3.338.0 + "@aws-sdk/util-waiter": 3.342.0 "@smithy/protocol-http": ^1.0.1 "@smithy/types": ^1.0.0 tslib: ^2.5.0 uuid: ^8.3.2 - checksum: a3e6dfb9b437e58417774b47e7c3eeabc7e6d301bb856516eb2438be72e83f06094703d00076be3534cbcf4dae6201523ab52f51ca0bf11416103a4dd13e2eee + checksum: 5d3488054155e05afe3cc700cd8156cfaa17098b869a240f596e12b64f0b3714f95ae41f4a8f19c91951eaa7ba1a5e7ab47d8eb7f69c982728f3cff594cc1417 languageName: node linkType: hard "@aws-sdk/client-organizations@npm:^3.310.0": - version: 3.338.0 - resolution: "@aws-sdk/client-organizations@npm:3.338.0" + version: 3.345.0 + resolution: "@aws-sdk/client-organizations@npm:3.345.0" dependencies: "@aws-crypto/sha256-browser": 3.0.0 "@aws-crypto/sha256-js": 3.0.0 - "@aws-sdk/client-sts": 3.338.0 - "@aws-sdk/config-resolver": 3.338.0 - "@aws-sdk/credential-provider-node": 3.338.0 - "@aws-sdk/fetch-http-handler": 3.338.0 - "@aws-sdk/hash-node": 3.338.0 - "@aws-sdk/invalid-dependency": 3.338.0 - "@aws-sdk/middleware-content-length": 3.338.0 - "@aws-sdk/middleware-endpoint": 3.338.0 - "@aws-sdk/middleware-host-header": 3.338.0 - "@aws-sdk/middleware-logger": 3.338.0 - "@aws-sdk/middleware-recursion-detection": 3.338.0 - "@aws-sdk/middleware-retry": 3.338.0 - "@aws-sdk/middleware-serde": 3.338.0 - "@aws-sdk/middleware-signing": 3.338.0 - "@aws-sdk/middleware-stack": 3.338.0 - "@aws-sdk/middleware-user-agent": 3.338.0 - "@aws-sdk/node-config-provider": 3.338.0 - "@aws-sdk/node-http-handler": 3.338.0 - "@aws-sdk/smithy-client": 3.338.0 - "@aws-sdk/types": 3.338.0 - "@aws-sdk/url-parser": 3.338.0 + "@aws-sdk/client-sts": 3.345.0 + "@aws-sdk/config-resolver": 3.342.0 + "@aws-sdk/credential-provider-node": 3.345.0 + "@aws-sdk/fetch-http-handler": 3.342.0 + "@aws-sdk/hash-node": 3.344.0 + "@aws-sdk/invalid-dependency": 3.342.0 + "@aws-sdk/middleware-content-length": 3.342.0 + "@aws-sdk/middleware-endpoint": 3.344.0 + "@aws-sdk/middleware-host-header": 3.342.0 + "@aws-sdk/middleware-logger": 3.342.0 + "@aws-sdk/middleware-recursion-detection": 3.342.0 + "@aws-sdk/middleware-retry": 3.342.0 + "@aws-sdk/middleware-serde": 3.342.0 + "@aws-sdk/middleware-signing": 3.342.0 + "@aws-sdk/middleware-stack": 3.342.0 + "@aws-sdk/middleware-user-agent": 3.345.0 + "@aws-sdk/node-config-provider": 3.342.0 + "@aws-sdk/node-http-handler": 3.344.0 + "@aws-sdk/smithy-client": 3.342.0 + "@aws-sdk/types": 3.342.0 + "@aws-sdk/url-parser": 3.342.0 "@aws-sdk/util-base64": 3.310.0 "@aws-sdk/util-body-length-browser": 3.310.0 "@aws-sdk/util-body-length-node": 3.310.0 - "@aws-sdk/util-defaults-mode-browser": 3.338.0 - "@aws-sdk/util-defaults-mode-node": 3.338.0 - "@aws-sdk/util-endpoints": 3.338.0 - "@aws-sdk/util-retry": 3.338.0 - "@aws-sdk/util-user-agent-browser": 3.338.0 - "@aws-sdk/util-user-agent-node": 3.338.0 + "@aws-sdk/util-defaults-mode-browser": 3.342.0 + "@aws-sdk/util-defaults-mode-node": 3.342.0 + "@aws-sdk/util-endpoints": 3.342.0 + "@aws-sdk/util-retry": 3.342.0 + "@aws-sdk/util-user-agent-browser": 3.345.0 + "@aws-sdk/util-user-agent-node": 3.345.0 "@aws-sdk/util-utf8": 3.310.0 "@smithy/protocol-http": ^1.0.1 "@smithy/types": ^1.0.0 tslib: ^2.5.0 - checksum: 58b712b0d515ac22ce010b98f2c2fe21a5e49c65f16121998fe7dc1008ca43e7cdab576bd096c25509882732b42ef1d629db8cf43bc49f27caea56a7d1f6fa6d + checksum: 2a50e58cdcac75cd6b4bc5ca8b985feadc8de100db9a12e1820189a22098b983695dbba7927f7ab8dc48bbb1d6210d33006cf9712f275d1afa10b61a4923e7f7 languageName: node linkType: hard "@aws-sdk/client-s3@npm:^3.310.0": - version: 3.338.0 - resolution: "@aws-sdk/client-s3@npm:3.338.0" + version: 3.345.0 + resolution: "@aws-sdk/client-s3@npm:3.345.0" dependencies: "@aws-crypto/sha1-browser": 3.0.0 "@aws-crypto/sha256-browser": 3.0.0 "@aws-crypto/sha256-js": 3.0.0 - "@aws-sdk/client-sts": 3.338.0 - "@aws-sdk/config-resolver": 3.338.0 - "@aws-sdk/credential-provider-node": 3.338.0 - "@aws-sdk/eventstream-serde-browser": 3.338.0 - "@aws-sdk/eventstream-serde-config-resolver": 3.338.0 - "@aws-sdk/eventstream-serde-node": 3.338.0 - "@aws-sdk/fetch-http-handler": 3.338.0 - "@aws-sdk/hash-blob-browser": 3.338.0 - "@aws-sdk/hash-node": 3.338.0 - "@aws-sdk/hash-stream-node": 3.338.0 - "@aws-sdk/invalid-dependency": 3.338.0 - "@aws-sdk/md5-js": 3.338.0 - "@aws-sdk/middleware-bucket-endpoint": 3.338.0 - "@aws-sdk/middleware-content-length": 3.338.0 - "@aws-sdk/middleware-endpoint": 3.338.0 - "@aws-sdk/middleware-expect-continue": 3.338.0 - "@aws-sdk/middleware-flexible-checksums": 3.338.0 - "@aws-sdk/middleware-host-header": 3.338.0 - "@aws-sdk/middleware-location-constraint": 3.338.0 - "@aws-sdk/middleware-logger": 3.338.0 - "@aws-sdk/middleware-recursion-detection": 3.338.0 - "@aws-sdk/middleware-retry": 3.338.0 - "@aws-sdk/middleware-sdk-s3": 3.338.0 - "@aws-sdk/middleware-serde": 3.338.0 - "@aws-sdk/middleware-signing": 3.338.0 - "@aws-sdk/middleware-ssec": 3.338.0 - "@aws-sdk/middleware-stack": 3.338.0 - "@aws-sdk/middleware-user-agent": 3.338.0 - "@aws-sdk/node-config-provider": 3.338.0 - "@aws-sdk/node-http-handler": 3.338.0 - "@aws-sdk/signature-v4-multi-region": 3.338.0 - "@aws-sdk/smithy-client": 3.338.0 - "@aws-sdk/types": 3.338.0 - "@aws-sdk/url-parser": 3.338.0 + "@aws-sdk/client-sts": 3.345.0 + "@aws-sdk/config-resolver": 3.342.0 + "@aws-sdk/credential-provider-node": 3.345.0 + "@aws-sdk/eventstream-serde-browser": 3.342.0 + "@aws-sdk/eventstream-serde-config-resolver": 3.342.0 + "@aws-sdk/eventstream-serde-node": 3.342.0 + "@aws-sdk/fetch-http-handler": 3.342.0 + "@aws-sdk/hash-blob-browser": 3.342.0 + "@aws-sdk/hash-node": 3.344.0 + "@aws-sdk/hash-stream-node": 3.342.0 + "@aws-sdk/invalid-dependency": 3.342.0 + "@aws-sdk/md5-js": 3.342.0 + "@aws-sdk/middleware-bucket-endpoint": 3.342.0 + "@aws-sdk/middleware-content-length": 3.342.0 + "@aws-sdk/middleware-endpoint": 3.344.0 + "@aws-sdk/middleware-expect-continue": 3.342.0 + "@aws-sdk/middleware-flexible-checksums": 3.342.0 + "@aws-sdk/middleware-host-header": 3.342.0 + "@aws-sdk/middleware-location-constraint": 3.342.0 + "@aws-sdk/middleware-logger": 3.342.0 + "@aws-sdk/middleware-recursion-detection": 3.342.0 + "@aws-sdk/middleware-retry": 3.342.0 + "@aws-sdk/middleware-sdk-s3": 3.342.0 + "@aws-sdk/middleware-serde": 3.342.0 + "@aws-sdk/middleware-signing": 3.342.0 + "@aws-sdk/middleware-ssec": 3.342.0 + "@aws-sdk/middleware-stack": 3.342.0 + "@aws-sdk/middleware-user-agent": 3.345.0 + "@aws-sdk/node-config-provider": 3.342.0 + "@aws-sdk/node-http-handler": 3.344.0 + "@aws-sdk/signature-v4-multi-region": 3.344.0 + "@aws-sdk/smithy-client": 3.342.0 + "@aws-sdk/types": 3.342.0 + "@aws-sdk/url-parser": 3.342.0 "@aws-sdk/util-base64": 3.310.0 "@aws-sdk/util-body-length-browser": 3.310.0 "@aws-sdk/util-body-length-node": 3.310.0 - "@aws-sdk/util-defaults-mode-browser": 3.338.0 - "@aws-sdk/util-defaults-mode-node": 3.338.0 - "@aws-sdk/util-endpoints": 3.338.0 - "@aws-sdk/util-retry": 3.338.0 - "@aws-sdk/util-stream-browser": 3.338.0 - "@aws-sdk/util-stream-node": 3.338.0 - "@aws-sdk/util-user-agent-browser": 3.338.0 - "@aws-sdk/util-user-agent-node": 3.338.0 + "@aws-sdk/util-defaults-mode-browser": 3.342.0 + "@aws-sdk/util-defaults-mode-node": 3.342.0 + "@aws-sdk/util-endpoints": 3.342.0 + "@aws-sdk/util-retry": 3.342.0 + "@aws-sdk/util-stream-browser": 3.342.0 + "@aws-sdk/util-stream-node": 3.344.0 + "@aws-sdk/util-user-agent-browser": 3.345.0 + "@aws-sdk/util-user-agent-node": 3.345.0 "@aws-sdk/util-utf8": 3.310.0 - "@aws-sdk/util-waiter": 3.338.0 + "@aws-sdk/util-waiter": 3.342.0 "@aws-sdk/xml-builder": 3.310.0 "@smithy/protocol-http": ^1.0.1 "@smithy/types": ^1.0.0 fast-xml-parser: 4.1.2 tslib: ^2.5.0 - checksum: f9f6e3c78e382fd595eb624e58d5c296aaadc5f5f378d802daeaaee2abb8803d6fcce88fdcc8a0d693effbc915e2b87554a39cde47a5a3b21074f71396548454 + checksum: 586a4067378e3e8a276608d247b7d0d2a74039ab1f7990750f8fb961689e1bb07a6faf1b4f7ae57e63195bf15a497f8dacd50a388367825de52cdbecefd420ca languageName: node linkType: hard "@aws-sdk/client-sqs@npm:^3.310.0": - version: 3.338.0 - resolution: "@aws-sdk/client-sqs@npm:3.338.0" + version: 3.345.0 + resolution: "@aws-sdk/client-sqs@npm:3.345.0" dependencies: "@aws-crypto/sha256-browser": 3.0.0 "@aws-crypto/sha256-js": 3.0.0 - "@aws-sdk/client-sts": 3.338.0 - "@aws-sdk/config-resolver": 3.338.0 - "@aws-sdk/credential-provider-node": 3.338.0 - "@aws-sdk/fetch-http-handler": 3.338.0 - "@aws-sdk/hash-node": 3.338.0 - "@aws-sdk/invalid-dependency": 3.338.0 - "@aws-sdk/md5-js": 3.338.0 - "@aws-sdk/middleware-content-length": 3.338.0 - "@aws-sdk/middleware-endpoint": 3.338.0 - "@aws-sdk/middleware-host-header": 3.338.0 - "@aws-sdk/middleware-logger": 3.338.0 - "@aws-sdk/middleware-recursion-detection": 3.338.0 - "@aws-sdk/middleware-retry": 3.338.0 - "@aws-sdk/middleware-sdk-sqs": 3.338.0 - "@aws-sdk/middleware-serde": 3.338.0 - "@aws-sdk/middleware-signing": 3.338.0 - "@aws-sdk/middleware-stack": 3.338.0 - "@aws-sdk/middleware-user-agent": 3.338.0 - "@aws-sdk/node-config-provider": 3.338.0 - "@aws-sdk/node-http-handler": 3.338.0 - "@aws-sdk/smithy-client": 3.338.0 - "@aws-sdk/types": 3.338.0 - "@aws-sdk/url-parser": 3.338.0 + "@aws-sdk/client-sts": 3.345.0 + "@aws-sdk/config-resolver": 3.342.0 + "@aws-sdk/credential-provider-node": 3.345.0 + "@aws-sdk/fetch-http-handler": 3.342.0 + "@aws-sdk/hash-node": 3.344.0 + "@aws-sdk/invalid-dependency": 3.342.0 + "@aws-sdk/md5-js": 3.342.0 + "@aws-sdk/middleware-content-length": 3.342.0 + "@aws-sdk/middleware-endpoint": 3.344.0 + "@aws-sdk/middleware-host-header": 3.342.0 + "@aws-sdk/middleware-logger": 3.342.0 + "@aws-sdk/middleware-recursion-detection": 3.342.0 + "@aws-sdk/middleware-retry": 3.342.0 + "@aws-sdk/middleware-sdk-sqs": 3.342.0 + "@aws-sdk/middleware-serde": 3.342.0 + "@aws-sdk/middleware-signing": 3.342.0 + "@aws-sdk/middleware-stack": 3.342.0 + "@aws-sdk/middleware-user-agent": 3.345.0 + "@aws-sdk/node-config-provider": 3.342.0 + "@aws-sdk/node-http-handler": 3.344.0 + "@aws-sdk/smithy-client": 3.342.0 + "@aws-sdk/types": 3.342.0 + "@aws-sdk/url-parser": 3.342.0 "@aws-sdk/util-base64": 3.310.0 "@aws-sdk/util-body-length-browser": 3.310.0 "@aws-sdk/util-body-length-node": 3.310.0 - "@aws-sdk/util-defaults-mode-browser": 3.338.0 - "@aws-sdk/util-defaults-mode-node": 3.338.0 - "@aws-sdk/util-endpoints": 3.338.0 - "@aws-sdk/util-retry": 3.338.0 - "@aws-sdk/util-user-agent-browser": 3.338.0 - "@aws-sdk/util-user-agent-node": 3.338.0 + "@aws-sdk/util-defaults-mode-browser": 3.342.0 + "@aws-sdk/util-defaults-mode-node": 3.342.0 + "@aws-sdk/util-endpoints": 3.342.0 + "@aws-sdk/util-retry": 3.342.0 + "@aws-sdk/util-user-agent-browser": 3.345.0 + "@aws-sdk/util-user-agent-node": 3.345.0 "@aws-sdk/util-utf8": 3.310.0 "@smithy/protocol-http": ^1.0.1 "@smithy/types": ^1.0.0 fast-xml-parser: 4.1.2 tslib: ^2.5.0 - checksum: 50912c1b0dfc42e1a0c1aac22bef1be7ea8879484b6b13aa8a753f2da5a435d1d08b33013b34bab73fb6e290816a80ea2808e465844873bcaa627ef347a6d848 + checksum: f6a8cd2a1437d43596c4b1a2e63bedb7215bdda96ccf1820f8ae18a42b9ceaade239b0a335a4fb34c65f635a6d65b827907085aebb1ae7f18702f944659840f8 languageName: node linkType: hard -"@aws-sdk/client-sso-oidc@npm:3.338.0": - version: 3.338.0 - resolution: "@aws-sdk/client-sso-oidc@npm:3.338.0" +"@aws-sdk/client-sso-oidc@npm:3.345.0": + version: 3.345.0 + resolution: "@aws-sdk/client-sso-oidc@npm:3.345.0" dependencies: "@aws-crypto/sha256-browser": 3.0.0 "@aws-crypto/sha256-js": 3.0.0 - "@aws-sdk/config-resolver": 3.338.0 - "@aws-sdk/fetch-http-handler": 3.338.0 - "@aws-sdk/hash-node": 3.338.0 - "@aws-sdk/invalid-dependency": 3.338.0 - "@aws-sdk/middleware-content-length": 3.338.0 - "@aws-sdk/middleware-endpoint": 3.338.0 - "@aws-sdk/middleware-host-header": 3.338.0 - "@aws-sdk/middleware-logger": 3.338.0 - "@aws-sdk/middleware-recursion-detection": 3.338.0 - "@aws-sdk/middleware-retry": 3.338.0 - "@aws-sdk/middleware-serde": 3.338.0 - "@aws-sdk/middleware-stack": 3.338.0 - "@aws-sdk/middleware-user-agent": 3.338.0 - "@aws-sdk/node-config-provider": 3.338.0 - "@aws-sdk/node-http-handler": 3.338.0 - "@aws-sdk/smithy-client": 3.338.0 - "@aws-sdk/types": 3.338.0 - "@aws-sdk/url-parser": 3.338.0 + "@aws-sdk/config-resolver": 3.342.0 + "@aws-sdk/fetch-http-handler": 3.342.0 + "@aws-sdk/hash-node": 3.344.0 + "@aws-sdk/invalid-dependency": 3.342.0 + "@aws-sdk/middleware-content-length": 3.342.0 + "@aws-sdk/middleware-endpoint": 3.344.0 + "@aws-sdk/middleware-host-header": 3.342.0 + "@aws-sdk/middleware-logger": 3.342.0 + "@aws-sdk/middleware-recursion-detection": 3.342.0 + "@aws-sdk/middleware-retry": 3.342.0 + "@aws-sdk/middleware-serde": 3.342.0 + "@aws-sdk/middleware-stack": 3.342.0 + "@aws-sdk/middleware-user-agent": 3.345.0 + "@aws-sdk/node-config-provider": 3.342.0 + "@aws-sdk/node-http-handler": 3.344.0 + "@aws-sdk/smithy-client": 3.342.0 + "@aws-sdk/types": 3.342.0 + "@aws-sdk/url-parser": 3.342.0 "@aws-sdk/util-base64": 3.310.0 "@aws-sdk/util-body-length-browser": 3.310.0 "@aws-sdk/util-body-length-node": 3.310.0 - "@aws-sdk/util-defaults-mode-browser": 3.338.0 - "@aws-sdk/util-defaults-mode-node": 3.338.0 - "@aws-sdk/util-endpoints": 3.338.0 - "@aws-sdk/util-retry": 3.338.0 - "@aws-sdk/util-user-agent-browser": 3.338.0 - "@aws-sdk/util-user-agent-node": 3.338.0 + "@aws-sdk/util-defaults-mode-browser": 3.342.0 + "@aws-sdk/util-defaults-mode-node": 3.342.0 + "@aws-sdk/util-endpoints": 3.342.0 + "@aws-sdk/util-retry": 3.342.0 + "@aws-sdk/util-user-agent-browser": 3.345.0 + "@aws-sdk/util-user-agent-node": 3.345.0 "@aws-sdk/util-utf8": 3.310.0 "@smithy/protocol-http": ^1.0.1 "@smithy/types": ^1.0.0 tslib: ^2.5.0 - checksum: bd4d42db2ccbb4e045fc22a59e40c93ddd8a718cc51cddedf7bb5aedf46c5668a548cccd39fb01f495d0076f68fa0a3b0f45f1f0fff1002828680a8127aa32a3 + checksum: 6241236088ad895f87cb1c0c5bcb176cfa20613097d99308dc513cea8f0b10efcab05b4a2d4f22819ca2c4ec8aee384c566e72e4177eb65cdd87136a650f1062 languageName: node linkType: hard -"@aws-sdk/client-sso@npm:3.338.0": - version: 3.338.0 - resolution: "@aws-sdk/client-sso@npm:3.338.0" +"@aws-sdk/client-sso@npm:3.345.0": + version: 3.345.0 + resolution: "@aws-sdk/client-sso@npm:3.345.0" dependencies: "@aws-crypto/sha256-browser": 3.0.0 "@aws-crypto/sha256-js": 3.0.0 - "@aws-sdk/config-resolver": 3.338.0 - "@aws-sdk/fetch-http-handler": 3.338.0 - "@aws-sdk/hash-node": 3.338.0 - "@aws-sdk/invalid-dependency": 3.338.0 - "@aws-sdk/middleware-content-length": 3.338.0 - "@aws-sdk/middleware-endpoint": 3.338.0 - "@aws-sdk/middleware-host-header": 3.338.0 - "@aws-sdk/middleware-logger": 3.338.0 - "@aws-sdk/middleware-recursion-detection": 3.338.0 - "@aws-sdk/middleware-retry": 3.338.0 - "@aws-sdk/middleware-serde": 3.338.0 - "@aws-sdk/middleware-stack": 3.338.0 - "@aws-sdk/middleware-user-agent": 3.338.0 - "@aws-sdk/node-config-provider": 3.338.0 - "@aws-sdk/node-http-handler": 3.338.0 - "@aws-sdk/smithy-client": 3.338.0 - "@aws-sdk/types": 3.338.0 - "@aws-sdk/url-parser": 3.338.0 + "@aws-sdk/config-resolver": 3.342.0 + "@aws-sdk/fetch-http-handler": 3.342.0 + "@aws-sdk/hash-node": 3.344.0 + "@aws-sdk/invalid-dependency": 3.342.0 + "@aws-sdk/middleware-content-length": 3.342.0 + "@aws-sdk/middleware-endpoint": 3.344.0 + "@aws-sdk/middleware-host-header": 3.342.0 + "@aws-sdk/middleware-logger": 3.342.0 + "@aws-sdk/middleware-recursion-detection": 3.342.0 + "@aws-sdk/middleware-retry": 3.342.0 + "@aws-sdk/middleware-serde": 3.342.0 + "@aws-sdk/middleware-stack": 3.342.0 + "@aws-sdk/middleware-user-agent": 3.345.0 + "@aws-sdk/node-config-provider": 3.342.0 + "@aws-sdk/node-http-handler": 3.344.0 + "@aws-sdk/smithy-client": 3.342.0 + "@aws-sdk/types": 3.342.0 + "@aws-sdk/url-parser": 3.342.0 "@aws-sdk/util-base64": 3.310.0 "@aws-sdk/util-body-length-browser": 3.310.0 "@aws-sdk/util-body-length-node": 3.310.0 - "@aws-sdk/util-defaults-mode-browser": 3.338.0 - "@aws-sdk/util-defaults-mode-node": 3.338.0 - "@aws-sdk/util-endpoints": 3.338.0 - "@aws-sdk/util-retry": 3.338.0 - "@aws-sdk/util-user-agent-browser": 3.338.0 - "@aws-sdk/util-user-agent-node": 3.338.0 + "@aws-sdk/util-defaults-mode-browser": 3.342.0 + "@aws-sdk/util-defaults-mode-node": 3.342.0 + "@aws-sdk/util-endpoints": 3.342.0 + "@aws-sdk/util-retry": 3.342.0 + "@aws-sdk/util-user-agent-browser": 3.345.0 + "@aws-sdk/util-user-agent-node": 3.345.0 "@aws-sdk/util-utf8": 3.310.0 "@smithy/protocol-http": ^1.0.1 "@smithy/types": ^1.0.0 tslib: ^2.5.0 - checksum: c4980aff00184a4dc70ac20862b2705a2eff570776c5be8dc014620d69f20d12c19e6feb08d11db14e1b21a38040813997bdd09f02f478e2e95037c483367690 + checksum: 6ecbb35aeaa928ca1c4a57e72d677eeba40bdbd97131e9b860ef658886840f07335593841117287fa62551ad9d2c655bb5abdb05909a46ff81ed8a2c6441f421 languageName: node linkType: hard -"@aws-sdk/client-sts@npm:3.338.0, @aws-sdk/client-sts@npm:^3.310.0": - version: 3.338.0 - resolution: "@aws-sdk/client-sts@npm:3.338.0" +"@aws-sdk/client-sts@npm:3.345.0, @aws-sdk/client-sts@npm:^3.310.0": + version: 3.345.0 + resolution: "@aws-sdk/client-sts@npm:3.345.0" dependencies: "@aws-crypto/sha256-browser": 3.0.0 "@aws-crypto/sha256-js": 3.0.0 - "@aws-sdk/config-resolver": 3.338.0 - "@aws-sdk/credential-provider-node": 3.338.0 - "@aws-sdk/fetch-http-handler": 3.338.0 - "@aws-sdk/hash-node": 3.338.0 - "@aws-sdk/invalid-dependency": 3.338.0 - "@aws-sdk/middleware-content-length": 3.338.0 - "@aws-sdk/middleware-endpoint": 3.338.0 - "@aws-sdk/middleware-host-header": 3.338.0 - "@aws-sdk/middleware-logger": 3.338.0 - "@aws-sdk/middleware-recursion-detection": 3.338.0 - "@aws-sdk/middleware-retry": 3.338.0 - "@aws-sdk/middleware-sdk-sts": 3.338.0 - "@aws-sdk/middleware-serde": 3.338.0 - "@aws-sdk/middleware-signing": 3.338.0 - "@aws-sdk/middleware-stack": 3.338.0 - "@aws-sdk/middleware-user-agent": 3.338.0 - "@aws-sdk/node-config-provider": 3.338.0 - "@aws-sdk/node-http-handler": 3.338.0 - "@aws-sdk/smithy-client": 3.338.0 - "@aws-sdk/types": 3.338.0 - "@aws-sdk/url-parser": 3.338.0 + "@aws-sdk/config-resolver": 3.342.0 + "@aws-sdk/credential-provider-node": 3.345.0 + "@aws-sdk/fetch-http-handler": 3.342.0 + "@aws-sdk/hash-node": 3.344.0 + "@aws-sdk/invalid-dependency": 3.342.0 + "@aws-sdk/middleware-content-length": 3.342.0 + "@aws-sdk/middleware-endpoint": 3.344.0 + "@aws-sdk/middleware-host-header": 3.342.0 + "@aws-sdk/middleware-logger": 3.342.0 + "@aws-sdk/middleware-recursion-detection": 3.342.0 + "@aws-sdk/middleware-retry": 3.342.0 + "@aws-sdk/middleware-sdk-sts": 3.342.0 + "@aws-sdk/middleware-serde": 3.342.0 + "@aws-sdk/middleware-signing": 3.342.0 + "@aws-sdk/middleware-stack": 3.342.0 + "@aws-sdk/middleware-user-agent": 3.345.0 + "@aws-sdk/node-config-provider": 3.342.0 + "@aws-sdk/node-http-handler": 3.344.0 + "@aws-sdk/smithy-client": 3.342.0 + "@aws-sdk/types": 3.342.0 + "@aws-sdk/url-parser": 3.342.0 "@aws-sdk/util-base64": 3.310.0 "@aws-sdk/util-body-length-browser": 3.310.0 "@aws-sdk/util-body-length-node": 3.310.0 - "@aws-sdk/util-defaults-mode-browser": 3.338.0 - "@aws-sdk/util-defaults-mode-node": 3.338.0 - "@aws-sdk/util-endpoints": 3.338.0 - "@aws-sdk/util-retry": 3.338.0 - "@aws-sdk/util-user-agent-browser": 3.338.0 - "@aws-sdk/util-user-agent-node": 3.338.0 + "@aws-sdk/util-defaults-mode-browser": 3.342.0 + "@aws-sdk/util-defaults-mode-node": 3.342.0 + "@aws-sdk/util-endpoints": 3.342.0 + "@aws-sdk/util-retry": 3.342.0 + "@aws-sdk/util-user-agent-browser": 3.345.0 + "@aws-sdk/util-user-agent-node": 3.345.0 "@aws-sdk/util-utf8": 3.310.0 "@smithy/protocol-http": ^1.0.1 "@smithy/types": ^1.0.0 fast-xml-parser: 4.1.2 tslib: ^2.5.0 - checksum: 879004560b0f92c9c7708e3ee574ea5822e0015d7e469edd07cf374e2a72924a50184086c00d31506ed44c80c209c5af5680ae00187aa0ff36352265ef0ecdf3 + checksum: 46dd7929a56e6126f750cde095569375aa12fe321ce1d71ea9749e0de6878e45f983e6db141dc3d804745324b810ddc8a512ff1afa4d3c8cd6d00823bc9dd857 languageName: node linkType: hard -"@aws-sdk/config-resolver@npm:3.338.0": - version: 3.338.0 - resolution: "@aws-sdk/config-resolver@npm:3.338.0" +"@aws-sdk/config-resolver@npm:3.342.0": + version: 3.342.0 + resolution: "@aws-sdk/config-resolver@npm:3.342.0" dependencies: - "@aws-sdk/types": 3.338.0 + "@aws-sdk/types": 3.342.0 "@aws-sdk/util-config-provider": 3.310.0 - "@aws-sdk/util-middleware": 3.338.0 + "@aws-sdk/util-middleware": 3.342.0 tslib: ^2.5.0 - checksum: d9b204555405869474ad6e37db6797ab0e829b0e6598fe3aa75022acb19eaaf95d011844396b7abf33a01af24eeb6fe67283f4c3a33aa7abd5e4f651dd964ffa + checksum: 61ac05c7e1999151b883280055655d59377675a1174c59c08d137f44d481facc0d7a2c612224f329b4fb97b8ff89636376ff03ab4d53b0cc44e0310134991e00 languageName: node linkType: hard -"@aws-sdk/credential-provider-cognito-identity@npm:3.338.0": - version: 3.338.0 - resolution: "@aws-sdk/credential-provider-cognito-identity@npm:3.338.0" +"@aws-sdk/credential-provider-cognito-identity@npm:3.345.0": + version: 3.345.0 + resolution: "@aws-sdk/credential-provider-cognito-identity@npm:3.345.0" dependencies: - "@aws-sdk/client-cognito-identity": 3.338.0 - "@aws-sdk/property-provider": 3.338.0 - "@aws-sdk/types": 3.338.0 + "@aws-sdk/client-cognito-identity": 3.345.0 + "@aws-sdk/property-provider": 3.342.0 + "@aws-sdk/types": 3.342.0 tslib: ^2.5.0 - checksum: bdd8af7416e467a2abf21a09069797e2acf0f61b8475635b51aff395e10da323d964ba963f020669eed69bc20c0524e8eec5c804d07cc2d89c121d636b564804 + checksum: 11ba057d43d1e36d0da8ca4281c381b5059e8c21a309ef4fb910ac44fa02cd8cdcde32a189b07aff7ddaaff1820be0c539010bd5a8644b339e3eda16e14f5a2f languageName: node linkType: hard -"@aws-sdk/credential-provider-env@npm:3.338.0": - version: 3.338.0 - resolution: "@aws-sdk/credential-provider-env@npm:3.338.0" +"@aws-sdk/credential-provider-env@npm:3.342.0": + version: 3.342.0 + resolution: "@aws-sdk/credential-provider-env@npm:3.342.0" dependencies: - "@aws-sdk/property-provider": 3.338.0 - "@aws-sdk/types": 3.338.0 + "@aws-sdk/property-provider": 3.342.0 + "@aws-sdk/types": 3.342.0 tslib: ^2.5.0 - checksum: b28e2ad7850b88ea050a3859d262ce42be09423aa56c9da645407835f669874e8a7ee0c71b4176b86dcf00676641d1bcd3f4c4620dcafde505af399dc271c7b1 + checksum: 086bde1f5388877e029ba381d44b342dccac2751e1de8a89db301d09f5e36c29bf7bffcb1e2cf66f3935077e22e061eeb35c0c62b587d1763cfdfebfe39e2392 languageName: node linkType: hard -"@aws-sdk/credential-provider-imds@npm:3.338.0": - version: 3.338.0 - resolution: "@aws-sdk/credential-provider-imds@npm:3.338.0" +"@aws-sdk/credential-provider-imds@npm:3.342.0": + version: 3.342.0 + resolution: "@aws-sdk/credential-provider-imds@npm:3.342.0" dependencies: - "@aws-sdk/node-config-provider": 3.338.0 - "@aws-sdk/property-provider": 3.338.0 - "@aws-sdk/types": 3.338.0 - "@aws-sdk/url-parser": 3.338.0 + "@aws-sdk/node-config-provider": 3.342.0 + "@aws-sdk/property-provider": 3.342.0 + "@aws-sdk/types": 3.342.0 + "@aws-sdk/url-parser": 3.342.0 tslib: ^2.5.0 - checksum: 4db0137b7a6a1825957b1f0d9744aa5b1ca369cfa39d00ea120e8c5b08a3d904cd1970a96be8ba852b92d1dd271827469def3c08f09ed898a2e8d7ac15b90874 + checksum: ea6341c9c1c98d164d1cf5f1643c701ef76fa0353659079046045e808964f7f0dfe911c827932ec72182b57781c3cfaaa970a2759657444c0a877b609e93c047 languageName: node linkType: hard -"@aws-sdk/credential-provider-ini@npm:3.338.0": - version: 3.338.0 - resolution: "@aws-sdk/credential-provider-ini@npm:3.338.0" +"@aws-sdk/credential-provider-ini@npm:3.345.0": + version: 3.345.0 + resolution: "@aws-sdk/credential-provider-ini@npm:3.345.0" dependencies: - "@aws-sdk/credential-provider-env": 3.338.0 - "@aws-sdk/credential-provider-imds": 3.338.0 - "@aws-sdk/credential-provider-process": 3.338.0 - "@aws-sdk/credential-provider-sso": 3.338.0 - "@aws-sdk/credential-provider-web-identity": 3.338.0 - "@aws-sdk/property-provider": 3.338.0 - "@aws-sdk/shared-ini-file-loader": 3.338.0 - "@aws-sdk/types": 3.338.0 + "@aws-sdk/credential-provider-env": 3.342.0 + "@aws-sdk/credential-provider-imds": 3.342.0 + "@aws-sdk/credential-provider-process": 3.342.0 + "@aws-sdk/credential-provider-sso": 3.345.0 + "@aws-sdk/credential-provider-web-identity": 3.342.0 + "@aws-sdk/property-provider": 3.342.0 + "@aws-sdk/shared-ini-file-loader": 3.342.0 + "@aws-sdk/types": 3.342.0 tslib: ^2.5.0 - checksum: cfef6a065b69c53ea2b5de81d05b9b37de26441ae813b9d11aa2985a18caa564938058ef527e0c5e10f27fd1d910c0e16f86681f6880e96dffef379e8751eb6d + checksum: 126aa2ea79b3079802a5ce3b97b2ba24351c662fe0bf66c8f07f47463c88be27a63a76d79f95ab60e04eb74fab07fa11ecc7f3826085612ad663ef809bcbcfbf languageName: node linkType: hard -"@aws-sdk/credential-provider-node@npm:3.338.0, @aws-sdk/credential-provider-node@npm:^3.310.0": - version: 3.338.0 - resolution: "@aws-sdk/credential-provider-node@npm:3.338.0" +"@aws-sdk/credential-provider-node@npm:3.345.0, @aws-sdk/credential-provider-node@npm:^3.310.0": + version: 3.345.0 + resolution: "@aws-sdk/credential-provider-node@npm:3.345.0" dependencies: - "@aws-sdk/credential-provider-env": 3.338.0 - "@aws-sdk/credential-provider-imds": 3.338.0 - "@aws-sdk/credential-provider-ini": 3.338.0 - "@aws-sdk/credential-provider-process": 3.338.0 - "@aws-sdk/credential-provider-sso": 3.338.0 - "@aws-sdk/credential-provider-web-identity": 3.338.0 - "@aws-sdk/property-provider": 3.338.0 - "@aws-sdk/shared-ini-file-loader": 3.338.0 - "@aws-sdk/types": 3.338.0 + "@aws-sdk/credential-provider-env": 3.342.0 + "@aws-sdk/credential-provider-imds": 3.342.0 + "@aws-sdk/credential-provider-ini": 3.345.0 + "@aws-sdk/credential-provider-process": 3.342.0 + "@aws-sdk/credential-provider-sso": 3.345.0 + "@aws-sdk/credential-provider-web-identity": 3.342.0 + "@aws-sdk/property-provider": 3.342.0 + "@aws-sdk/shared-ini-file-loader": 3.342.0 + "@aws-sdk/types": 3.342.0 tslib: ^2.5.0 - checksum: 871d1cd910a97aba33eb82053d7fd9f1cd126d31460a3622174e1ce85588d3d26e1c6f76a1a2e689e41aeba3dc748dd23b1d92af33a2b621c7b6afefaaf2559c + checksum: b869e25f8559eb6476841aeb6d297fb6be360029bcbabc594edc2573b2afc1293dd1895d2f61a6995ee96fea5cd9770297d4bd40f7af252e7e277358116b431b languageName: node linkType: hard -"@aws-sdk/credential-provider-process@npm:3.338.0": - version: 3.338.0 - resolution: "@aws-sdk/credential-provider-process@npm:3.338.0" +"@aws-sdk/credential-provider-process@npm:3.342.0": + version: 3.342.0 + resolution: "@aws-sdk/credential-provider-process@npm:3.342.0" dependencies: - "@aws-sdk/property-provider": 3.338.0 - "@aws-sdk/shared-ini-file-loader": 3.338.0 - "@aws-sdk/types": 3.338.0 + "@aws-sdk/property-provider": 3.342.0 + "@aws-sdk/shared-ini-file-loader": 3.342.0 + "@aws-sdk/types": 3.342.0 tslib: ^2.5.0 - checksum: 5af4d43e7dc5d85f9833dbe65e190ad23b9f360eb681484779106a435a9af08b0a75e42f71c637c4c7ab4443c7f5e3d896af7d4a7ac7971eab42aec426018279 + checksum: 87936656e9a838971b610ed811fc658ba0b8359f9a87b2d8a4a1f1d8efb47f46c6a5d44f57f282473c6eea3db36f24ce28fb862c6680f96987dfb8792347f7a7 languageName: node linkType: hard -"@aws-sdk/credential-provider-sso@npm:3.338.0": - version: 3.338.0 - resolution: "@aws-sdk/credential-provider-sso@npm:3.338.0" +"@aws-sdk/credential-provider-sso@npm:3.345.0": + version: 3.345.0 + resolution: "@aws-sdk/credential-provider-sso@npm:3.345.0" dependencies: - "@aws-sdk/client-sso": 3.338.0 - "@aws-sdk/property-provider": 3.338.0 - "@aws-sdk/shared-ini-file-loader": 3.338.0 - "@aws-sdk/token-providers": 3.338.0 - "@aws-sdk/types": 3.338.0 + "@aws-sdk/client-sso": 3.345.0 + "@aws-sdk/property-provider": 3.342.0 + "@aws-sdk/shared-ini-file-loader": 3.342.0 + "@aws-sdk/token-providers": 3.345.0 + "@aws-sdk/types": 3.342.0 tslib: ^2.5.0 - checksum: 35fe15cede3777e3c30770c460ba96c7aa80f4856ef80ab6bcc6788f955ea1c1f745248d53f4c5eda17774e42066a5f23f3c71fa7a0e312cc3235044dde022fa + checksum: 0a7e42c44cb3b5da25c70c17ffbe532aa3edf0995692c137f1072c6cb247efa6557fac64913617a201b518fc57ac6a896240e1af9fa1aee1a63459c5ec5fafce languageName: node linkType: hard -"@aws-sdk/credential-provider-web-identity@npm:3.338.0": - version: 3.338.0 - resolution: "@aws-sdk/credential-provider-web-identity@npm:3.338.0" +"@aws-sdk/credential-provider-web-identity@npm:3.342.0": + version: 3.342.0 + resolution: "@aws-sdk/credential-provider-web-identity@npm:3.342.0" dependencies: - "@aws-sdk/property-provider": 3.338.0 - "@aws-sdk/types": 3.338.0 + "@aws-sdk/property-provider": 3.342.0 + "@aws-sdk/types": 3.342.0 tslib: ^2.5.0 - checksum: aa61393398ff0d06ee83a727f8d967aa7585a28482a6423947f2bce86b8163bd97d2d6420a126e5ad1d5d00aa5bcb3128492412f0d7dfca128179f0600000183 + checksum: 19de3af2ee63e9bf9ff88d60c7add38d65b91df043e92281b4ea3caf91184ae9e94d2c890c8a2e38650cfec2d9976d3b03b750e6b3003ea510ae8965e2701452 languageName: node linkType: hard "@aws-sdk/credential-providers@npm:^3.310.0": - version: 3.338.0 - resolution: "@aws-sdk/credential-providers@npm:3.338.0" + version: 3.345.0 + resolution: "@aws-sdk/credential-providers@npm:3.345.0" dependencies: - "@aws-sdk/client-cognito-identity": 3.338.0 - "@aws-sdk/client-sso": 3.338.0 - "@aws-sdk/client-sts": 3.338.0 - "@aws-sdk/credential-provider-cognito-identity": 3.338.0 - "@aws-sdk/credential-provider-env": 3.338.0 - "@aws-sdk/credential-provider-imds": 3.338.0 - "@aws-sdk/credential-provider-ini": 3.338.0 - "@aws-sdk/credential-provider-node": 3.338.0 - "@aws-sdk/credential-provider-process": 3.338.0 - "@aws-sdk/credential-provider-sso": 3.338.0 - "@aws-sdk/credential-provider-web-identity": 3.338.0 - "@aws-sdk/property-provider": 3.338.0 - "@aws-sdk/types": 3.338.0 + "@aws-sdk/client-cognito-identity": 3.345.0 + "@aws-sdk/client-sso": 3.345.0 + "@aws-sdk/client-sts": 3.345.0 + "@aws-sdk/credential-provider-cognito-identity": 3.345.0 + "@aws-sdk/credential-provider-env": 3.342.0 + "@aws-sdk/credential-provider-imds": 3.342.0 + "@aws-sdk/credential-provider-ini": 3.345.0 + "@aws-sdk/credential-provider-node": 3.345.0 + "@aws-sdk/credential-provider-process": 3.342.0 + "@aws-sdk/credential-provider-sso": 3.345.0 + "@aws-sdk/credential-provider-web-identity": 3.342.0 + "@aws-sdk/property-provider": 3.342.0 + "@aws-sdk/types": 3.342.0 tslib: ^2.5.0 - checksum: 3001b8c829d1624ffb3ab75284bfced8e9c2d991032eae1369713bb190847019dd0061728b705a6e98c9bd152db3174c2df772b437bf0f1ca69f3554d4826835 + checksum: 7b9860d2a374216601e1195db3ae51c44f17c9d1329afb84d2090e3180c61c4f2fe5d56e21168357cd10b48b410ab48441d8fac97b9a899b043715d652f47cf6 languageName: node linkType: hard -"@aws-sdk/eventstream-codec@npm:3.338.0": - version: 3.338.0 - resolution: "@aws-sdk/eventstream-codec@npm:3.338.0" +"@aws-sdk/eventstream-codec@npm:3.342.0": + version: 3.342.0 + resolution: "@aws-sdk/eventstream-codec@npm:3.342.0" dependencies: "@aws-crypto/crc32": 3.0.0 - "@aws-sdk/types": 3.338.0 + "@aws-sdk/types": 3.342.0 "@aws-sdk/util-hex-encoding": 3.310.0 tslib: ^2.5.0 - checksum: 6fe39c223c6c95b7e8491fd4835abe9a43e37f78dd595b619337be2083be7af77730834f2f0509745a9b9678a13b0ee0a9021913bfef48ed357b54d42e1f6113 + checksum: 2922d430c6de801e584ff86bc8ee96eb055dbd2509b786c695c8e2f6029e5969d23ab6f815526a81460cbef9b8bf83ed70977855bbfba374e8daaf3043c88431 languageName: node linkType: hard -"@aws-sdk/eventstream-serde-browser@npm:3.338.0": - version: 3.338.0 - resolution: "@aws-sdk/eventstream-serde-browser@npm:3.338.0" +"@aws-sdk/eventstream-serde-browser@npm:3.342.0": + version: 3.342.0 + resolution: "@aws-sdk/eventstream-serde-browser@npm:3.342.0" dependencies: - "@aws-sdk/eventstream-serde-universal": 3.338.0 - "@aws-sdk/types": 3.338.0 + "@aws-sdk/eventstream-serde-universal": 3.342.0 + "@aws-sdk/types": 3.342.0 tslib: ^2.5.0 - checksum: d565058ffb42d60e870a2bce36495a595de8b706e85b3a4bbc5ec5a63c57b2b8716f7ced83ed7a5a231b13becf7a28979720d85810d45ab7eafb45a9fa7a43d6 + checksum: 47ded9d3674207946a611ee3f12f7173386ede8d1e60537b1a4782a491ac782e3251fed0096465d307ed0e9597c9d6ace3a7a709b485cd1af8b47abaadfa8006 languageName: node linkType: hard -"@aws-sdk/eventstream-serde-config-resolver@npm:3.338.0": - version: 3.338.0 - resolution: "@aws-sdk/eventstream-serde-config-resolver@npm:3.338.0" +"@aws-sdk/eventstream-serde-config-resolver@npm:3.342.0": + version: 3.342.0 + resolution: "@aws-sdk/eventstream-serde-config-resolver@npm:3.342.0" dependencies: - "@aws-sdk/types": 3.338.0 + "@aws-sdk/types": 3.342.0 tslib: ^2.5.0 - checksum: 0535397aa3ce6e655fffbad71b68a42dd1bbf2f8d6fb895108972f38756525a5fa5e033ed25b251e0a74610506c139baadca07719f98254dc75a9c7cdacdb7d0 + checksum: c7bac1de5aeedae2393d43d63b87865b9b25b25f56bdd0aeb081490da01b4aa8caecc36a1ded6205b811a8986d7b5a3dd9858eab808c4ccf0f37552d32fffb83 languageName: node linkType: hard -"@aws-sdk/eventstream-serde-node@npm:3.338.0": - version: 3.338.0 - resolution: "@aws-sdk/eventstream-serde-node@npm:3.338.0" +"@aws-sdk/eventstream-serde-node@npm:3.342.0": + version: 3.342.0 + resolution: "@aws-sdk/eventstream-serde-node@npm:3.342.0" dependencies: - "@aws-sdk/eventstream-serde-universal": 3.338.0 - "@aws-sdk/types": 3.338.0 + "@aws-sdk/eventstream-serde-universal": 3.342.0 + "@aws-sdk/types": 3.342.0 tslib: ^2.5.0 - checksum: 3804f61d220105122dbd1ad7e20a453f7278ff70927ec0fd941a48c07fb0233af5a6ba29b6cbfd34ea4cd76c2ac639b51d166d0a7e5bd4bc0d7fa7c4930ee0e1 + checksum: 32683ca9a1aaf531bcd27d94f4d5e80d4955dfe426c9d71d60f0a03fdd5ffebd07c44bb4eb5bf1c4302b270abe37c0e8f361aadf77c67ff50b9eac4eef020f70 languageName: node linkType: hard -"@aws-sdk/eventstream-serde-universal@npm:3.338.0": - version: 3.338.0 - resolution: "@aws-sdk/eventstream-serde-universal@npm:3.338.0" +"@aws-sdk/eventstream-serde-universal@npm:3.342.0": + version: 3.342.0 + resolution: "@aws-sdk/eventstream-serde-universal@npm:3.342.0" dependencies: - "@aws-sdk/eventstream-codec": 3.338.0 - "@aws-sdk/types": 3.338.0 + "@aws-sdk/eventstream-codec": 3.342.0 + "@aws-sdk/types": 3.342.0 tslib: ^2.5.0 - checksum: a105442ca33e1eec1091f64c8433a2715e613a963bf9ffc905f1cf5867add67062b43c900651b3decf302098fdcbd95c845688baf1d33e41b8024acec5414f44 + checksum: c7a53aacf39596a98882488d547eb65fd7e40ac56b68f5a2eb0db8a08437c44ad98c75929a2c477b0a26e5ac4ebf3d1bfd712cf31f9d6f379dc00ef2738afe74 languageName: node linkType: hard -"@aws-sdk/fetch-http-handler@npm:3.338.0": - version: 3.338.0 - resolution: "@aws-sdk/fetch-http-handler@npm:3.338.0" +"@aws-sdk/fetch-http-handler@npm:3.342.0": + version: 3.342.0 + resolution: "@aws-sdk/fetch-http-handler@npm:3.342.0" dependencies: - "@aws-sdk/protocol-http": 3.338.0 - "@aws-sdk/querystring-builder": 3.338.0 - "@aws-sdk/types": 3.338.0 + "@aws-sdk/protocol-http": 3.342.0 + "@aws-sdk/querystring-builder": 3.342.0 + "@aws-sdk/types": 3.342.0 "@aws-sdk/util-base64": 3.310.0 tslib: ^2.5.0 - checksum: db96ad7a62373df8c394105f0618a9c01d9ddafaa2665f87f08c595f4b0bdc5d0388c44770d6e06268e6dda6944ff43fb5f2f15212209027439af6b3225dc4e3 + checksum: da02fd9ff17e5fefaee3f2a070e13ad105b7bdd194a9e591299b04af556da01024dc8da2c41ef84be0435b68e8f32d88dd67b175c322983d3ed6b1ee5a2b8231 languageName: node linkType: hard -"@aws-sdk/hash-blob-browser@npm:3.338.0": - version: 3.338.0 - resolution: "@aws-sdk/hash-blob-browser@npm:3.338.0" +"@aws-sdk/hash-blob-browser@npm:3.342.0": + version: 3.342.0 + resolution: "@aws-sdk/hash-blob-browser@npm:3.342.0" dependencies: "@aws-sdk/chunked-blob-reader": 3.310.0 - "@aws-sdk/types": 3.338.0 + "@aws-sdk/types": 3.342.0 tslib: ^2.5.0 - checksum: 089efa923647c4c7b62fa1ff590c93044bdb9864a250c96a3bc1fa812add2b87b7e52b750076d4e1d416cd17a69b99ec233d87b8a829ce35896458c3b160969a + checksum: ebc4e8773e90a8fcf23e04661c91bdcb32b8c05a570ec8572858b9540d8898490401f20b9611a6e8a1c6e520bea499c212874f31810b494b4c348883c93be2cb languageName: node linkType: hard -"@aws-sdk/hash-node@npm:3.338.0": - version: 3.338.0 - resolution: "@aws-sdk/hash-node@npm:3.338.0" +"@aws-sdk/hash-node@npm:3.344.0": + version: 3.344.0 + resolution: "@aws-sdk/hash-node@npm:3.344.0" dependencies: - "@aws-sdk/types": 3.338.0 + "@aws-sdk/types": 3.342.0 "@aws-sdk/util-buffer-from": 3.310.0 "@aws-sdk/util-utf8": 3.310.0 tslib: ^2.5.0 - checksum: f45f263fbdd636e882ddca5a34b7f636c0416b77151dd53c61c91fc6048cd3a505b54bc390d5f31a161b72baeeb36358fbc6d0a710dabfa05d64b4c9ee89e05e + checksum: 361d96625d39c43a5c1873e4a549014eaeed56a2c1d3c4fa46047610cba9542252f4df5760f802ac268f29fbe1c863d70dbd298b5d0c0ed2dff26073adff9b8f languageName: node linkType: hard -"@aws-sdk/hash-stream-node@npm:3.338.0": - version: 3.338.0 - resolution: "@aws-sdk/hash-stream-node@npm:3.338.0" +"@aws-sdk/hash-stream-node@npm:3.342.0": + version: 3.342.0 + resolution: "@aws-sdk/hash-stream-node@npm:3.342.0" dependencies: - "@aws-sdk/types": 3.338.0 + "@aws-sdk/types": 3.342.0 "@aws-sdk/util-utf8": 3.310.0 tslib: ^2.5.0 - checksum: 429c3b9358965d173553ffdb47e4b3a8fa9da6148c640ee9559bc36fd14dd97e71e0d9464ebf4ecd1e0445251055e6212365525eec985c05a72e4b13416e5354 + checksum: 812a1c3987219af25073e8cc6bd304b85ea84e170e14b3dcc63c04b2b0b9c35c4b15c6c1194b67872cf113b3307a691d1c27583d0b457717c3abcb22e3c29c5d languageName: node linkType: hard -"@aws-sdk/invalid-dependency@npm:3.338.0": - version: 3.338.0 - resolution: "@aws-sdk/invalid-dependency@npm:3.338.0" +"@aws-sdk/invalid-dependency@npm:3.342.0": + version: 3.342.0 + resolution: "@aws-sdk/invalid-dependency@npm:3.342.0" dependencies: - "@aws-sdk/types": 3.338.0 + "@aws-sdk/types": 3.342.0 tslib: ^2.5.0 - checksum: d240b2dab9a3ec46537429ad2e857dfde18d31f345bb30527739cfcf42cbb91d5b77c6d8caf751317506aa5e5912d8dc8be3684714d8a266cec91ab34a90c70a + checksum: 58694fa950beae12bc780687d4dc43bf93bf5764f89c02935fb143d47532ebf8102da854f27aae767399fe507ca76513c625c05cb181935e0579fb35641e2f65 languageName: node linkType: hard @@ -1185,11 +1185,11 @@ __metadata: linkType: hard "@aws-sdk/lib-storage@npm:^3.310.0": - version: 3.338.0 - resolution: "@aws-sdk/lib-storage@npm:3.338.0" + version: 3.345.0 + resolution: "@aws-sdk/lib-storage@npm:3.345.0" dependencies: - "@aws-sdk/middleware-endpoint": 3.338.0 - "@aws-sdk/smithy-client": 3.338.0 + "@aws-sdk/middleware-endpoint": 3.344.0 + "@aws-sdk/smithy-client": 3.342.0 buffer: 5.6.0 events: 3.3.0 stream-browserify: 3.0.0 @@ -1197,387 +1197,388 @@ __metadata: peerDependencies: "@aws-sdk/abort-controller": ^3.0.0 "@aws-sdk/client-s3": ^3.0.0 - checksum: 642322da53789d7bc2f2965d2da6626e85a4fe65480e8665e287ee21e92ea3d6711a958e4b8dd3b22f61d6fcc547b8194edf5e98aa6bca2919ad874a96d0bdc8 + checksum: 1bece781ac04a3f7e12a0b1831d645f9077416f526dea47f93ca3997d997d154c79951392d2e56006823dd70e99b6d996548a51153d4d506ac33d6937b088791 languageName: node linkType: hard -"@aws-sdk/md5-js@npm:3.338.0": - version: 3.338.0 - resolution: "@aws-sdk/md5-js@npm:3.338.0" +"@aws-sdk/md5-js@npm:3.342.0": + version: 3.342.0 + resolution: "@aws-sdk/md5-js@npm:3.342.0" dependencies: - "@aws-sdk/types": 3.338.0 + "@aws-sdk/types": 3.342.0 "@aws-sdk/util-utf8": 3.310.0 tslib: ^2.5.0 - checksum: 851376107748918c92f66ef2c087dc562c9684f0dd93ad84e5454aa8a87244e31c8ab639fa06a1561cf0b6fa38110256c8228abe403d821c6aef4e22e2c3a7bc + checksum: 750dcbac2ce6cb4ec0dc05bf6ee5827b79fea14e64f2826cd20421c1b9460e7d9afe7bf7c7ac48e7b9478d2be00138f5e9127a5f1e9fba398e488318efcd4e10 languageName: node linkType: hard -"@aws-sdk/middleware-bucket-endpoint@npm:3.338.0": - version: 3.338.0 - resolution: "@aws-sdk/middleware-bucket-endpoint@npm:3.338.0" +"@aws-sdk/middleware-bucket-endpoint@npm:3.342.0": + version: 3.342.0 + resolution: "@aws-sdk/middleware-bucket-endpoint@npm:3.342.0" dependencies: - "@aws-sdk/protocol-http": 3.338.0 - "@aws-sdk/types": 3.338.0 + "@aws-sdk/protocol-http": 3.342.0 + "@aws-sdk/types": 3.342.0 "@aws-sdk/util-arn-parser": 3.310.0 "@aws-sdk/util-config-provider": 3.310.0 tslib: ^2.5.0 - checksum: 76acf178b8502b7dc91a59eca0a9a0217428d2d340ca8b24d20e577eec499e1c661c8af9ff8ac3ff8c6d57a86fa360a921d4f23df1f01eee9e23756059a34b62 + checksum: b3d436234049b38af9e0215354787e5262cd5337ef6e4dccd4363fe040b7be82720717270f0803ff3832b0af24abba547df1c1c83e572e8ac82270561d09527a languageName: node linkType: hard -"@aws-sdk/middleware-content-length@npm:3.338.0": - version: 3.338.0 - resolution: "@aws-sdk/middleware-content-length@npm:3.338.0" +"@aws-sdk/middleware-content-length@npm:3.342.0": + version: 3.342.0 + resolution: "@aws-sdk/middleware-content-length@npm:3.342.0" dependencies: - "@aws-sdk/protocol-http": 3.338.0 - "@aws-sdk/types": 3.338.0 + "@aws-sdk/protocol-http": 3.342.0 + "@aws-sdk/types": 3.342.0 tslib: ^2.5.0 - checksum: bc789ae025923de7f876b5a8e906ea05b662e67b8ce2311fa69bcfe0b6df3e7ca76c0d388db5050ee43cc04c97d5d6f2419aff992920f13896a7bf1a33e8332d + checksum: 397d211c6497b104457702581b3c8b29afd8dfbc6b07ca49f6c6d57375cb389cfa2c0675af447e635b81843f51382aa550882175d07a8c8c0bf707be7c125b59 languageName: node linkType: hard -"@aws-sdk/middleware-endpoint@npm:3.338.0, @aws-sdk/middleware-endpoint@npm:^3.310.0": - version: 3.338.0 - resolution: "@aws-sdk/middleware-endpoint@npm:3.338.0" +"@aws-sdk/middleware-endpoint@npm:3.344.0, @aws-sdk/middleware-endpoint@npm:^3.310.0": + version: 3.344.0 + resolution: "@aws-sdk/middleware-endpoint@npm:3.344.0" dependencies: - "@aws-sdk/middleware-serde": 3.338.0 - "@aws-sdk/types": 3.338.0 - "@aws-sdk/url-parser": 3.338.0 - "@aws-sdk/util-middleware": 3.338.0 + "@aws-sdk/middleware-serde": 3.342.0 + "@aws-sdk/types": 3.342.0 + "@aws-sdk/url-parser": 3.342.0 + "@aws-sdk/util-middleware": 3.342.0 tslib: ^2.5.0 - checksum: 265eef36686f7b849dce34eb5ccd55379af7b09f749bded039b4d6a6c020fd5ff602a00c2a41c134c821e82c4fef70136d78e5d4767dacbf79bfaefa1b07eb08 + checksum: 74c8b14104ce6283214d7bb5ce83dc95ccf3e9aec627cb13ee58237d85717d3ed84bffb1d97ba8510e9b154486007cde14a18b0b04592b29ffe4ca19bbcbb46f languageName: node linkType: hard -"@aws-sdk/middleware-expect-continue@npm:3.338.0": - version: 3.338.0 - resolution: "@aws-sdk/middleware-expect-continue@npm:3.338.0" +"@aws-sdk/middleware-expect-continue@npm:3.342.0": + version: 3.342.0 + resolution: "@aws-sdk/middleware-expect-continue@npm:3.342.0" dependencies: - "@aws-sdk/protocol-http": 3.338.0 - "@aws-sdk/types": 3.338.0 + "@aws-sdk/protocol-http": 3.342.0 + "@aws-sdk/types": 3.342.0 tslib: ^2.5.0 - checksum: bff8e22e2313458340cf8512dfa0152e683319155bfc63869cca30efedc5062be6a33fb85098230c90dfd835c6f02c27aa96383350247f14b75e2d111606b1e5 + checksum: aaca4517e61c87775079f7eb673c9474ecd426ca0cbcb8bf891a560518f363de91d0f9ede352d59ec1b1644a789db7a13d79c9ace6e848fc7fc365456dc53309 languageName: node linkType: hard -"@aws-sdk/middleware-flexible-checksums@npm:3.338.0": - version: 3.338.0 - resolution: "@aws-sdk/middleware-flexible-checksums@npm:3.338.0" +"@aws-sdk/middleware-flexible-checksums@npm:3.342.0": + version: 3.342.0 + resolution: "@aws-sdk/middleware-flexible-checksums@npm:3.342.0" dependencies: "@aws-crypto/crc32": 3.0.0 "@aws-crypto/crc32c": 3.0.0 "@aws-sdk/is-array-buffer": 3.310.0 - "@aws-sdk/protocol-http": 3.338.0 - "@aws-sdk/types": 3.338.0 + "@aws-sdk/protocol-http": 3.342.0 + "@aws-sdk/types": 3.342.0 "@aws-sdk/util-utf8": 3.310.0 tslib: ^2.5.0 - checksum: 6427816c22184976a0cb1b4c2e0740ab66f632da69f67e5bbb8888ed858f53b865e9e44a13f820d1c81d89b676fd9accbac0afb64378f739da9cd918926afc38 + checksum: 31c6a3a01a64420765af3bb5b94f7b096412ad01b746a77b2391dafe9482e2d0b88d01d10be9f4103449c872ddf7411c29434956970112641b0c9fe0227087bc languageName: node linkType: hard -"@aws-sdk/middleware-host-header@npm:3.338.0": - version: 3.338.0 - resolution: "@aws-sdk/middleware-host-header@npm:3.338.0" +"@aws-sdk/middleware-host-header@npm:3.342.0": + version: 3.342.0 + resolution: "@aws-sdk/middleware-host-header@npm:3.342.0" dependencies: - "@aws-sdk/protocol-http": 3.338.0 - "@aws-sdk/types": 3.338.0 + "@aws-sdk/protocol-http": 3.342.0 + "@aws-sdk/types": 3.342.0 tslib: ^2.5.0 - checksum: 7ff51a9453bb1dcf93f37bb9c04d84e13be429caa8f65d332e0e9963ca58ad5af6bc5c93110d7e0fb9fab1bb97c7dd7df6df267ffe4ba916c90a72dc6e4ba256 + checksum: eb26b492a2674baabedd96b5ce8152f5f0dab901931b5ae4ef15ad53e59d6967f58c68afe7e7ac53b183d818cc1b5640fd27e7b74b5ecbf7377783d18a35317b languageName: node linkType: hard -"@aws-sdk/middleware-location-constraint@npm:3.338.0": - version: 3.338.0 - resolution: "@aws-sdk/middleware-location-constraint@npm:3.338.0" +"@aws-sdk/middleware-location-constraint@npm:3.342.0": + version: 3.342.0 + resolution: "@aws-sdk/middleware-location-constraint@npm:3.342.0" dependencies: - "@aws-sdk/types": 3.338.0 + "@aws-sdk/types": 3.342.0 tslib: ^2.5.0 - checksum: 1306d5d6c919990492b9c2869197875d189edbfe83f7f9e1df5ac705c3deb8a42446f812ac5ac6968f4d3ae5f6962953bc8273bc7173a1cb1c9376024d84d8c5 + checksum: 7fea65c01b47c7c4b971a6446a1d439d0d914aa160b61ca8aba1ff7ad244d487056a7fd022b9d9a06722d225ef69f08b1994f9ddf9d5eb20f7f66515db5ca040 languageName: node linkType: hard -"@aws-sdk/middleware-logger@npm:3.338.0": - version: 3.338.0 - resolution: "@aws-sdk/middleware-logger@npm:3.338.0" +"@aws-sdk/middleware-logger@npm:3.342.0": + version: 3.342.0 + resolution: "@aws-sdk/middleware-logger@npm:3.342.0" dependencies: - "@aws-sdk/types": 3.338.0 + "@aws-sdk/types": 3.342.0 tslib: ^2.5.0 - checksum: 9c4a3e3656fe17a99eca5312c4aefe2031e33239c700de8efeae66be0d0636ad585701714b9832f783be143ebea602534db246dfbe8c90e6b1d325a71b64fa7e + checksum: bada09358137c161d781021336ea988d423f8db067c1eea2942ed7664fdb9ce852a9ee17d3da63a4f3678ff27e789996110848e7043963b771e78505f5cb693e languageName: node linkType: hard -"@aws-sdk/middleware-recursion-detection@npm:3.338.0": - version: 3.338.0 - resolution: "@aws-sdk/middleware-recursion-detection@npm:3.338.0" +"@aws-sdk/middleware-recursion-detection@npm:3.342.0": + version: 3.342.0 + resolution: "@aws-sdk/middleware-recursion-detection@npm:3.342.0" dependencies: - "@aws-sdk/protocol-http": 3.338.0 - "@aws-sdk/types": 3.338.0 + "@aws-sdk/protocol-http": 3.342.0 + "@aws-sdk/types": 3.342.0 tslib: ^2.5.0 - checksum: 9dddbabf6bf96808583b26a9af06af51fb8f5478d89a93954a60cbcbe5d2dbc3f9f3621b19f38491bc96096b121f446c138c37ab1b1be8a643efcd5ff983d3f1 + checksum: 4871056c3a8e3c9de17f59f946bfdcad85a5ee9f16cf96914fc0dfe6e2aa9e850e688dc4cfcb908eee0afe9591b6092b3dfb7d3bc3c1fac25f6cd4c6c83ac4d3 languageName: node linkType: hard -"@aws-sdk/middleware-retry@npm:3.338.0": - version: 3.338.0 - resolution: "@aws-sdk/middleware-retry@npm:3.338.0" +"@aws-sdk/middleware-retry@npm:3.342.0": + version: 3.342.0 + resolution: "@aws-sdk/middleware-retry@npm:3.342.0" dependencies: - "@aws-sdk/protocol-http": 3.338.0 - "@aws-sdk/service-error-classification": 3.338.0 - "@aws-sdk/types": 3.338.0 - "@aws-sdk/util-middleware": 3.338.0 - "@aws-sdk/util-retry": 3.338.0 + "@aws-sdk/protocol-http": 3.342.0 + "@aws-sdk/service-error-classification": 3.342.0 + "@aws-sdk/types": 3.342.0 + "@aws-sdk/util-middleware": 3.342.0 + "@aws-sdk/util-retry": 3.342.0 tslib: ^2.5.0 uuid: ^8.3.2 - checksum: 186d82e32df9dbfe62c90e545847dd74e79088b897c470d9dd753c51d4a6e6006a981734d4c0076ea2ec5155448ccf4bf65c517c6a907ac64b12c48da172dfb3 + checksum: 066268ccab655680b75865c8c47beb19f269d5b3bc14d85c4f6c53af9a4fac50f9b7c2f7bc0ca93fcb4b3f9bbb5d14b89c21bf855504e90b9a86cd370d4f8e0b languageName: node linkType: hard -"@aws-sdk/middleware-sdk-s3@npm:3.338.0": - version: 3.338.0 - resolution: "@aws-sdk/middleware-sdk-s3@npm:3.338.0" +"@aws-sdk/middleware-sdk-s3@npm:3.342.0": + version: 3.342.0 + resolution: "@aws-sdk/middleware-sdk-s3@npm:3.342.0" dependencies: - "@aws-sdk/protocol-http": 3.338.0 - "@aws-sdk/types": 3.338.0 + "@aws-sdk/protocol-http": 3.342.0 + "@aws-sdk/types": 3.342.0 "@aws-sdk/util-arn-parser": 3.310.0 tslib: ^2.5.0 - checksum: a1c7e35b106ab2f12bb700add3dd82afc304f6ea7fdeb69ac9b4192cc049e2e51cd1580740471f6aaaa3aaf83f870fc0873955e3554b6f3dda5c2bd8df42de31 + checksum: 5bf9789bc3e745ac754829d1e0dc6bb6fef7659cacfa38d41bd97df2b5357dbc5429defdb32e6b7fe0e27bc75ed9f04ebb1e42045b5a77e7f132f923d8287ccb languageName: node linkType: hard -"@aws-sdk/middleware-sdk-sqs@npm:3.338.0": - version: 3.338.0 - resolution: "@aws-sdk/middleware-sdk-sqs@npm:3.338.0" +"@aws-sdk/middleware-sdk-sqs@npm:3.342.0": + version: 3.342.0 + resolution: "@aws-sdk/middleware-sdk-sqs@npm:3.342.0" dependencies: - "@aws-sdk/types": 3.338.0 + "@aws-sdk/types": 3.342.0 "@aws-sdk/util-hex-encoding": 3.310.0 "@aws-sdk/util-utf8": 3.310.0 tslib: ^2.5.0 - checksum: 609eb416099bb38c7ce459f73129e51d29804690749e3fbfe665c28b0fca61d885ad45cba852bc9b0545915d65dcded09cdf2a49a9da2e1168bff29c58be9a0a + checksum: 450d44dd0b66da4137a7c2cf96c0a5de88c40b0dd8281cddc90d7ea42ee54c8690243ae95584273de1c5d591149ca0f34c4da575467b01c85479395c3f7fa9cd languageName: node linkType: hard -"@aws-sdk/middleware-sdk-sts@npm:3.338.0": - version: 3.338.0 - resolution: "@aws-sdk/middleware-sdk-sts@npm:3.338.0" +"@aws-sdk/middleware-sdk-sts@npm:3.342.0": + version: 3.342.0 + resolution: "@aws-sdk/middleware-sdk-sts@npm:3.342.0" dependencies: - "@aws-sdk/middleware-signing": 3.338.0 - "@aws-sdk/types": 3.338.0 + "@aws-sdk/middleware-signing": 3.342.0 + "@aws-sdk/types": 3.342.0 tslib: ^2.5.0 - checksum: 359cd0b7b47ac97a8ba5fa8dd290d8940515fa8ca0068b9e645f0d4d99fe6679a3086b5b01765b83a20982a81410d8ae4a50ede5e97917af4ee269fca2dd987f + checksum: 404e122a0d2d9ed6530a57fbd576f9085781bf57476cafd57ef048a49120cb7bcc24849d5337c5b7578f3bf1ba1825cb6282bdf13545e12dac26611b841f67a0 languageName: node linkType: hard -"@aws-sdk/middleware-serde@npm:3.338.0": - version: 3.338.0 - resolution: "@aws-sdk/middleware-serde@npm:3.338.0" +"@aws-sdk/middleware-serde@npm:3.342.0": + version: 3.342.0 + resolution: "@aws-sdk/middleware-serde@npm:3.342.0" dependencies: - "@aws-sdk/types": 3.338.0 + "@aws-sdk/types": 3.342.0 tslib: ^2.5.0 - checksum: f4317c734e1a27001278723bdfe71aadb63d50f1a60b44d0662c12ca5499f32b7208122bb65dd8f2ba809edfc2e333853f463dbeaee7c85e1214e5814875cfba + checksum: 10bff04ba1e31b9a7da311bd509459ad6a45f78aca817c0c436f9b2cde1f5f439a1f089d29cb741141815b9a0bee8a680efa25d5a9e900a079a415acf3cd8602 languageName: node linkType: hard -"@aws-sdk/middleware-signing@npm:3.338.0": - version: 3.338.0 - resolution: "@aws-sdk/middleware-signing@npm:3.338.0" +"@aws-sdk/middleware-signing@npm:3.342.0": + version: 3.342.0 + resolution: "@aws-sdk/middleware-signing@npm:3.342.0" dependencies: - "@aws-sdk/property-provider": 3.338.0 - "@aws-sdk/protocol-http": 3.338.0 - "@aws-sdk/signature-v4": 3.338.0 - "@aws-sdk/types": 3.338.0 - "@aws-sdk/util-middleware": 3.338.0 + "@aws-sdk/property-provider": 3.342.0 + "@aws-sdk/protocol-http": 3.342.0 + "@aws-sdk/signature-v4": 3.342.0 + "@aws-sdk/types": 3.342.0 + "@aws-sdk/util-middleware": 3.342.0 tslib: ^2.5.0 - checksum: e53478186e0ac9b1a6c8834659716b851afaced1cfdbf99681800ae2fd9e3124573f188ae258d00cda612afbec15dbb613b88567ee604ad3b69c92b1e47f225a + checksum: d07d718331d63732a4ad55bf580eb20375622f86fe05db3eecc874936e754c16a681951c00d206c30e9a4af84dd31805a72de55d0c67fe80b859c91d192342d5 languageName: node linkType: hard -"@aws-sdk/middleware-ssec@npm:3.338.0": - version: 3.338.0 - resolution: "@aws-sdk/middleware-ssec@npm:3.338.0" +"@aws-sdk/middleware-ssec@npm:3.342.0": + version: 3.342.0 + resolution: "@aws-sdk/middleware-ssec@npm:3.342.0" dependencies: - "@aws-sdk/types": 3.338.0 + "@aws-sdk/types": 3.342.0 tslib: ^2.5.0 - checksum: 7136d65756f319ae6f051a021c8ca345e01b9ccbbf6ae33a42bc6510a452904bc20e8ef5f0631adde6f6b91ee11615916dd4f69033944ffc549d47892ac9bd30 + checksum: 4c85be245737ee4f36b609bb9ba6add5d0c53238694e1772a4a05abebe3f6db5b853230021d8ce592c824c1dc23b84c06d2dd70b32d1ebf9cb17dbc059f5b368 languageName: node linkType: hard -"@aws-sdk/middleware-stack@npm:3.338.0": - version: 3.338.0 - resolution: "@aws-sdk/middleware-stack@npm:3.338.0" +"@aws-sdk/middleware-stack@npm:3.342.0": + version: 3.342.0 + resolution: "@aws-sdk/middleware-stack@npm:3.342.0" dependencies: tslib: ^2.5.0 - checksum: f73b04a9f9e3b33a19f0d4c56877248df4016003dda3a4237374bdfe8c1c4358b69894754110a9989ba131dab5ec1fa03de68c50cbe10a399e290da96b5b8d06 + checksum: 8cd077f7e60f9ceb57eba0f0766e5784ced7bb959dfeebb4491a948006052da1d1a99a98795146a80424b00f3f6874f85bdb94419a1e1d510227f739886f90a2 languageName: node linkType: hard -"@aws-sdk/middleware-user-agent@npm:3.338.0": - version: 3.338.0 - resolution: "@aws-sdk/middleware-user-agent@npm:3.338.0" +"@aws-sdk/middleware-user-agent@npm:3.345.0": + version: 3.345.0 + resolution: "@aws-sdk/middleware-user-agent@npm:3.345.0" dependencies: - "@aws-sdk/protocol-http": 3.338.0 - "@aws-sdk/types": 3.338.0 - "@aws-sdk/util-endpoints": 3.338.0 + "@aws-sdk/protocol-http": 3.342.0 + "@aws-sdk/types": 3.342.0 + "@aws-sdk/util-endpoints": 3.342.0 tslib: ^2.5.0 - checksum: 6b3dce2a4ec82121d13f57f2a426d42380e8198a4a891f89fdaee0698f3b9c8c7f7d08242d0f8b762f7d9515ef44e8beb79b79a96a9e890901cbfc484932bae3 + checksum: c2e057bbf31e6365d351dbfb007dbaebda8fc5fb5194e1314b32e474c103b09756eb5fdcbd15f5eb6a9e6e80a19a16136ad4111d63685430f93039ff6edab76a languageName: node linkType: hard -"@aws-sdk/node-config-provider@npm:3.338.0": - version: 3.338.0 - resolution: "@aws-sdk/node-config-provider@npm:3.338.0" +"@aws-sdk/node-config-provider@npm:3.342.0": + version: 3.342.0 + resolution: "@aws-sdk/node-config-provider@npm:3.342.0" dependencies: - "@aws-sdk/property-provider": 3.338.0 - "@aws-sdk/shared-ini-file-loader": 3.338.0 - "@aws-sdk/types": 3.338.0 + "@aws-sdk/property-provider": 3.342.0 + "@aws-sdk/shared-ini-file-loader": 3.342.0 + "@aws-sdk/types": 3.342.0 tslib: ^2.5.0 - checksum: e81d311321b582b94d7349f2e225b1be74d7a7b7f6d4d3834de5fb9d80a7861e7cede791d088c613008dcdc00f77dfec23301794756c61452308841d73b9ac1c + checksum: b52f42d898e42683493fbda9a50437529bbfbc46d0b12deddbdd0976f05a278a9303de2abe01573c86cf423d37b88881097c7c543c695ab5495e58be99119bfa languageName: node linkType: hard -"@aws-sdk/node-http-handler@npm:3.338.0, @aws-sdk/node-http-handler@npm:^3.310.0": - version: 3.338.0 - resolution: "@aws-sdk/node-http-handler@npm:3.338.0" +"@aws-sdk/node-http-handler@npm:3.344.0, @aws-sdk/node-http-handler@npm:^3.310.0": + version: 3.344.0 + resolution: "@aws-sdk/node-http-handler@npm:3.344.0" dependencies: - "@aws-sdk/abort-controller": 3.338.0 - "@aws-sdk/protocol-http": 3.338.0 - "@aws-sdk/querystring-builder": 3.338.0 - "@aws-sdk/types": 3.338.0 + "@aws-sdk/abort-controller": 3.342.0 + "@aws-sdk/protocol-http": 3.342.0 + "@aws-sdk/querystring-builder": 3.342.0 + "@aws-sdk/types": 3.342.0 tslib: ^2.5.0 - checksum: 238d573256eed3d7311e9aff92e072fb53486d054516045c443e6218841742e64ce02993fdaeda79cdd081d2d80011261010e0cdf9d63b267aebb86f9ec48a1e + checksum: 268ad90f1adfd20a33b61542b1c7c03528dee4dd9eaa07e42120c5c6e2e165c8e9b05e2356410600d5ef62d1e316885d13de81b0c257eb5500a82903abe05a69 languageName: node linkType: hard -"@aws-sdk/property-provider@npm:3.338.0": - version: 3.338.0 - resolution: "@aws-sdk/property-provider@npm:3.338.0" +"@aws-sdk/property-provider@npm:3.342.0": + version: 3.342.0 + resolution: "@aws-sdk/property-provider@npm:3.342.0" dependencies: - "@aws-sdk/types": 3.338.0 + "@aws-sdk/types": 3.342.0 tslib: ^2.5.0 - checksum: 938bd8c29254c24a74f0d505e58a214743a46c7880dc13a24d851fa5fc9871ba7043ff3305da484c9a9660dee305733d508448b7d06728e2ae694151fdaf5ec7 + checksum: 22a1d5f1883627e431e0523650877447ad8ebe57e39d1e798ee7870f7dcc0fe8013b958621b30373b5362326e3eafc00716eefe4f42b0d8f435968698d1694d6 languageName: node linkType: hard -"@aws-sdk/protocol-http@npm:3.338.0": - version: 3.338.0 - resolution: "@aws-sdk/protocol-http@npm:3.338.0" +"@aws-sdk/protocol-http@npm:3.342.0": + version: 3.342.0 + resolution: "@aws-sdk/protocol-http@npm:3.342.0" dependencies: - "@aws-sdk/types": 3.338.0 + "@aws-sdk/types": 3.342.0 tslib: ^2.5.0 - checksum: a5f87ba4876fb9d4294bfa82aa3da21a7386b4d8725d152f79441b099ef3f865c302dea1df691b23884c95f457671b0837f2aea98381e35cbcc8395796dee412 + checksum: f6910fa4880780d224cb5f78eb501cbc900a51b33be4727e734f2ea63e3bbdc7d581bf53e77ba3fa3a569055ba261750d0623e5c95b5ad510d11b4959166b00d languageName: node linkType: hard -"@aws-sdk/querystring-builder@npm:3.338.0": - version: 3.338.0 - resolution: "@aws-sdk/querystring-builder@npm:3.338.0" +"@aws-sdk/querystring-builder@npm:3.342.0": + version: 3.342.0 + resolution: "@aws-sdk/querystring-builder@npm:3.342.0" dependencies: - "@aws-sdk/types": 3.338.0 + "@aws-sdk/types": 3.342.0 "@aws-sdk/util-uri-escape": 3.310.0 tslib: ^2.5.0 - checksum: d9df52be103420f51b3d4ffa7a6d59825416f520421e4f1c4b95cb55d60d45eb12364dbc434bee1a3c7f1563268bf82b06c365324a79005f340b0abc9554143b + checksum: 801e5b4230024fa08244b78b96a96df62f1bbe681b3e3eb4694d4fa21bf59e732547d63a1636cc14cc5feb5e8d854497acea15cd826cbe68ea89abc6933f84fa languageName: node linkType: hard -"@aws-sdk/querystring-parser@npm:3.338.0": - version: 3.338.0 - resolution: "@aws-sdk/querystring-parser@npm:3.338.0" +"@aws-sdk/querystring-parser@npm:3.342.0": + version: 3.342.0 + resolution: "@aws-sdk/querystring-parser@npm:3.342.0" dependencies: - "@aws-sdk/types": 3.338.0 + "@aws-sdk/types": 3.342.0 tslib: ^2.5.0 - checksum: 8645c79cb27d8a63c3637a9ebf9d97ce603b1c4f114e849ca995432479871a3bc37b1084b2e593d48178dc609f9e3a2535a6b0e44052e62b1cd47966890bd0bd + checksum: 248b5b855eed52957cf3d2113ce57205723ecf1f378d211c79eb6209e68d8c4994c537bc4ff40695496f69b5337359d8de63825978e7570aa2e9cc76222c9e95 languageName: node linkType: hard -"@aws-sdk/service-error-classification@npm:3.338.0": - version: 3.338.0 - resolution: "@aws-sdk/service-error-classification@npm:3.338.0" - checksum: 5760007eaa6bd105524fce230a030072c44149ea381451a1c7706e7bc5bb44aa512b40fb14b569b1063dc70b2275f0618fc0e82bbcaf1cecdb74c59a92ba4557 +"@aws-sdk/service-error-classification@npm:3.342.0": + version: 3.342.0 + resolution: "@aws-sdk/service-error-classification@npm:3.342.0" + checksum: c7cf32ac7eb745db8e54ce1cd66618b10e321f814e406944b46692ea3b76778e43a90c9c9febfaed05049a426526e0820385d71d9868f227e23cb1dc5c719b48 languageName: node linkType: hard -"@aws-sdk/shared-ini-file-loader@npm:3.338.0": - version: 3.338.0 - resolution: "@aws-sdk/shared-ini-file-loader@npm:3.338.0" +"@aws-sdk/shared-ini-file-loader@npm:3.342.0": + version: 3.342.0 + resolution: "@aws-sdk/shared-ini-file-loader@npm:3.342.0" dependencies: - "@aws-sdk/types": 3.338.0 + "@aws-sdk/types": 3.342.0 tslib: ^2.5.0 - checksum: c50eb70ae5d5a47ac67c12dc0d00c29ae4e6179cabadeda2e5e1f0c3cc36f379ea8f0a55d04d600ad523597a5e8961571d3fea3fab93882496cd0567f80420d5 + checksum: 252c1f2f75a7bc2c135e8a1da5d6cf27353a5fdc5d57b9440b0546cece3b27d498621d07a100e741ff2037df9423e8cd9225f65bb89537da9cb01bb4711a4cb9 languageName: node linkType: hard -"@aws-sdk/signature-v4-multi-region@npm:3.338.0": - version: 3.338.0 - resolution: "@aws-sdk/signature-v4-multi-region@npm:3.338.0" +"@aws-sdk/signature-v4-multi-region@npm:3.344.0": + version: 3.344.0 + resolution: "@aws-sdk/signature-v4-multi-region@npm:3.344.0" dependencies: - "@aws-sdk/protocol-http": 3.338.0 - "@aws-sdk/signature-v4": 3.338.0 - "@aws-sdk/types": 3.338.0 + "@aws-sdk/protocol-http": 3.342.0 + "@aws-sdk/signature-v4": 3.342.0 + "@aws-sdk/types": 3.342.0 tslib: ^2.5.0 peerDependencies: "@aws-sdk/signature-v4-crt": ^3.118.0 peerDependenciesMeta: "@aws-sdk/signature-v4-crt": optional: true - checksum: 28f94ed3ee46a96d1f1e62ecfb71f22a6d2be9059b2230afa29753e4a5687d76bcafd9eb1394bd0730aaa6bc94e24d6d9100b0e7b4d39d45ccae09f15b993444 + checksum: d8adf704643bd50a99f6f812e989677152b6d8ae4f39ecae959b0cd9446fdb06f10911ea8fd30793743af4c3f642f3986b122c206ff016de2a009da8c3b466fd languageName: node linkType: hard -"@aws-sdk/signature-v4@npm:3.338.0, @aws-sdk/signature-v4@npm:^3.310.0": - version: 3.338.0 - resolution: "@aws-sdk/signature-v4@npm:3.338.0" +"@aws-sdk/signature-v4@npm:3.342.0, @aws-sdk/signature-v4@npm:^3.310.0": + version: 3.342.0 + resolution: "@aws-sdk/signature-v4@npm:3.342.0" dependencies: + "@aws-sdk/eventstream-codec": 3.342.0 "@aws-sdk/is-array-buffer": 3.310.0 - "@aws-sdk/types": 3.338.0 + "@aws-sdk/types": 3.342.0 "@aws-sdk/util-hex-encoding": 3.310.0 - "@aws-sdk/util-middleware": 3.338.0 + "@aws-sdk/util-middleware": 3.342.0 "@aws-sdk/util-uri-escape": 3.310.0 "@aws-sdk/util-utf8": 3.310.0 tslib: ^2.5.0 - checksum: 9d024ad98a84beb9f3d5e66bd68cc93a47b78eb50e00ab4d3ac4bcad34d2e7e4b05053b21d36645e69550c532ccceca38b1b65af7d68da3b7197900c427303ed + checksum: ab251dc6ad546beb1129abbd9dfdf8637da82cf54e14dd7cff9e026d62a428d511065a36604609963a028c2a04140d4c96746e3d3da50a441f0baf5d431a7fa8 languageName: node linkType: hard -"@aws-sdk/smithy-client@npm:3.338.0": - version: 3.338.0 - resolution: "@aws-sdk/smithy-client@npm:3.338.0" +"@aws-sdk/smithy-client@npm:3.342.0": + version: 3.342.0 + resolution: "@aws-sdk/smithy-client@npm:3.342.0" dependencies: - "@aws-sdk/middleware-stack": 3.338.0 - "@aws-sdk/types": 3.338.0 + "@aws-sdk/middleware-stack": 3.342.0 + "@aws-sdk/types": 3.342.0 tslib: ^2.5.0 - checksum: 7c2bc4b7fcfe94dd3bb3068947c9ab3d0bf563790f7981f8af312f20f3b43364c7a691019ca53229e81a639379e3d3db5a0f38b846940aba180f6170c2a7a2b9 + checksum: af79f4ec9bce5cda76154839f5f2ce24268cc4ec8f496aa5b9a8ff632f88675dc7015363cd57b397691df4de417cc05d706cf7b0c6ae02c686d42e95f204133d languageName: node linkType: hard -"@aws-sdk/token-providers@npm:3.338.0": - version: 3.338.0 - resolution: "@aws-sdk/token-providers@npm:3.338.0" +"@aws-sdk/token-providers@npm:3.345.0": + version: 3.345.0 + resolution: "@aws-sdk/token-providers@npm:3.345.0" dependencies: - "@aws-sdk/client-sso-oidc": 3.338.0 - "@aws-sdk/property-provider": 3.338.0 - "@aws-sdk/shared-ini-file-loader": 3.338.0 - "@aws-sdk/types": 3.338.0 + "@aws-sdk/client-sso-oidc": 3.345.0 + "@aws-sdk/property-provider": 3.342.0 + "@aws-sdk/shared-ini-file-loader": 3.342.0 + "@aws-sdk/types": 3.342.0 tslib: ^2.5.0 - checksum: 49b58c59ea372ccf80739925a84f5dcfde9c74fb194fd171bd4c2c3d80576ab4e6c33a7612bba697f588135edb1fb9bb26e88363e256d9c038eb469013a5fa71 + checksum: d9d7d446cdec152e60087e1bac5f123ccb8555b1f4802ed10a522f60eaa716785882fa650fe67ac24bcb153eba2c104a19784b2b4408541ba6e9cfe5e68a5d83 languageName: node linkType: hard -"@aws-sdk/types@npm:3.338.0, @aws-sdk/types@npm:^3.222.0, @aws-sdk/types@npm:^3.310.0": - version: 3.338.0 - resolution: "@aws-sdk/types@npm:3.338.0" +"@aws-sdk/types@npm:3.342.0, @aws-sdk/types@npm:^3.222.0, @aws-sdk/types@npm:^3.310.0": + version: 3.342.0 + resolution: "@aws-sdk/types@npm:3.342.0" dependencies: tslib: ^2.5.0 - checksum: c20619ef22c460c34926c053522163a2b8f4825fd8288dcfefec80ce2d526ab1e0417064dd533739a6037eb1abd16bc035a4be932d9eeec80a05483ec5183140 + checksum: c9ec0873304548696deb604fcc4fcdacb726c9e03a65cdb4e9d8643a24ddf83ea32aa9d85b801406670526ca210131d5a8842d3674c73757c03ca5329ed2d13a languageName: node linkType: hard -"@aws-sdk/url-parser@npm:3.338.0": - version: 3.338.0 - resolution: "@aws-sdk/url-parser@npm:3.338.0" +"@aws-sdk/url-parser@npm:3.342.0": + version: 3.342.0 + resolution: "@aws-sdk/url-parser@npm:3.342.0" dependencies: - "@aws-sdk/querystring-parser": 3.338.0 - "@aws-sdk/types": 3.338.0 + "@aws-sdk/querystring-parser": 3.342.0 + "@aws-sdk/types": 3.342.0 tslib: ^2.5.0 - checksum: c25a26196c6ee5f745bcb684d2b1c85051d913332682a5aa25635b4d4a858178c870639b6cd33c89f0cc456b9a65db48c90f039f7ac07f62963c9fa39fa7b4fe + checksum: d5c1b23cc3f110ac2acc47c7777911d362bf674ba5226b82b8f8c73c25e45bc56ad5060169821af88890d8d9cc02963d0af0e7574f9a283fc6987f7f8672f7bf languageName: node linkType: hard @@ -1637,39 +1638,39 @@ __metadata: languageName: node linkType: hard -"@aws-sdk/util-defaults-mode-browser@npm:3.338.0": - version: 3.338.0 - resolution: "@aws-sdk/util-defaults-mode-browser@npm:3.338.0" +"@aws-sdk/util-defaults-mode-browser@npm:3.342.0": + version: 3.342.0 + resolution: "@aws-sdk/util-defaults-mode-browser@npm:3.342.0" dependencies: - "@aws-sdk/property-provider": 3.338.0 - "@aws-sdk/types": 3.338.0 + "@aws-sdk/property-provider": 3.342.0 + "@aws-sdk/types": 3.342.0 bowser: ^2.11.0 tslib: ^2.5.0 - checksum: 07e06c0256097979743b0a81d09d69c1f678e6386f9543c1bc9d150b11f3d3c89ea729a5c8f1b99c32326ee60e23ebc7e9d1a985b920c4b2301eb53488e5faa6 + checksum: 96ff9723313dd331679e311f2e534914e4348b9729c19dce666c766e19a847eaea293d55bfbbda00c42eef127a5816aa6501cc4882be49c24470ab0285e3bff1 languageName: node linkType: hard -"@aws-sdk/util-defaults-mode-node@npm:3.338.0": - version: 3.338.0 - resolution: "@aws-sdk/util-defaults-mode-node@npm:3.338.0" +"@aws-sdk/util-defaults-mode-node@npm:3.342.0": + version: 3.342.0 + resolution: "@aws-sdk/util-defaults-mode-node@npm:3.342.0" dependencies: - "@aws-sdk/config-resolver": 3.338.0 - "@aws-sdk/credential-provider-imds": 3.338.0 - "@aws-sdk/node-config-provider": 3.338.0 - "@aws-sdk/property-provider": 3.338.0 - "@aws-sdk/types": 3.338.0 + "@aws-sdk/config-resolver": 3.342.0 + "@aws-sdk/credential-provider-imds": 3.342.0 + "@aws-sdk/node-config-provider": 3.342.0 + "@aws-sdk/property-provider": 3.342.0 + "@aws-sdk/types": 3.342.0 tslib: ^2.5.0 - checksum: 1829f7c5035049c43173e78e843b6feaf0acc46b94803e12827985b5b881ca1e8a091072106b3573bb400e7ad80fa7579364d0783e69db6c560cdf49cda0f759 + checksum: b255d8039e56b6ad4264bc2615a995804e3cf565ee36876f05491fbd795f5e0c3c4af3bd7e42c00d08cc68311694e60942a363fa2db6a4228447827d9f36455a languageName: node linkType: hard -"@aws-sdk/util-endpoints@npm:3.338.0": - version: 3.338.0 - resolution: "@aws-sdk/util-endpoints@npm:3.338.0" +"@aws-sdk/util-endpoints@npm:3.342.0": + version: 3.342.0 + resolution: "@aws-sdk/util-endpoints@npm:3.342.0" dependencies: - "@aws-sdk/types": 3.338.0 + "@aws-sdk/types": 3.342.0 tslib: ^2.5.0 - checksum: 8c70bcaae2636089b15e6891a31c4c4a19e59d5c945e17ff9a6ffcfce96a9db4dad28df7c7755920a4a670acdd3858a92a95b3d16b74191d8400807dafb6ba75 + checksum: eb9443651d620ff6fd13b2e2cd7cf85f9e40672d385e12d63502bc903e5cd1e6887142d6ca4e2f9fd56cc07cbf1777bf0a356a0dc62143104bbe35352add7003 languageName: node linkType: hard @@ -1691,48 +1692,48 @@ __metadata: languageName: node linkType: hard -"@aws-sdk/util-middleware@npm:3.338.0": - version: 3.338.0 - resolution: "@aws-sdk/util-middleware@npm:3.338.0" +"@aws-sdk/util-middleware@npm:3.342.0": + version: 3.342.0 + resolution: "@aws-sdk/util-middleware@npm:3.342.0" dependencies: tslib: ^2.5.0 - checksum: 971338a469dcb709fb7eac2f796fa8db033e614645cd35100327c39f48b66b9faba68560afdd8a88a39b9ace714390b1a6ddb1c8265a98729ae877e3a01ad2cd + checksum: b668e04eff6e54b3d2e1f410d1b18244fc1aecb9c6d231f95971c6798393c5a00e139cbd30da08f82226af9ea96addb3a8d96a2612e2e338975495d03c100426 languageName: node linkType: hard -"@aws-sdk/util-retry@npm:3.338.0": - version: 3.338.0 - resolution: "@aws-sdk/util-retry@npm:3.338.0" +"@aws-sdk/util-retry@npm:3.342.0": + version: 3.342.0 + resolution: "@aws-sdk/util-retry@npm:3.342.0" dependencies: - "@aws-sdk/service-error-classification": 3.338.0 + "@aws-sdk/service-error-classification": 3.342.0 tslib: ^2.5.0 - checksum: 37310fae814faab60351629c9e59a6a06bc2bed5bd296ef5016e1c4e94e4ba9daa892898473690f157f32f91eb70669061a14d3f8cabdc0bc65293496cdfb6c0 + checksum: 89f730fcf8dce43e6d426fd2d00b48eca1d8935ecc2ee7f07cc93d18cff82bc50a29f6ff536b2f570ed604f4df3044e53e82d84a5cdf37f08ccc0e43e4c9ff87 languageName: node linkType: hard -"@aws-sdk/util-stream-browser@npm:3.338.0": - version: 3.338.0 - resolution: "@aws-sdk/util-stream-browser@npm:3.338.0" +"@aws-sdk/util-stream-browser@npm:3.342.0": + version: 3.342.0 + resolution: "@aws-sdk/util-stream-browser@npm:3.342.0" dependencies: - "@aws-sdk/fetch-http-handler": 3.338.0 - "@aws-sdk/types": 3.338.0 + "@aws-sdk/fetch-http-handler": 3.342.0 + "@aws-sdk/types": 3.342.0 "@aws-sdk/util-base64": 3.310.0 "@aws-sdk/util-hex-encoding": 3.310.0 "@aws-sdk/util-utf8": 3.310.0 tslib: ^2.5.0 - checksum: 0a0cfb601737411e04aa06a502dad8be306e6dafa7d153ba1d446353348d72c844f12571622bc9926175c38121d332027ffaa01ed61090689be0e3cb79aefa08 + checksum: 5d6e6cda660001c82abcddc002a164db79ae69da92d6d7b94ad57a09a2147c32d21deb59973e4bad787a2faca831fd0e2f58f4f619e4e953a591ee7c02dafe44 languageName: node linkType: hard -"@aws-sdk/util-stream-node@npm:3.338.0, @aws-sdk/util-stream-node@npm:^3.310.0": - version: 3.338.0 - resolution: "@aws-sdk/util-stream-node@npm:3.338.0" +"@aws-sdk/util-stream-node@npm:3.344.0, @aws-sdk/util-stream-node@npm:^3.310.0": + version: 3.344.0 + resolution: "@aws-sdk/util-stream-node@npm:3.344.0" dependencies: - "@aws-sdk/node-http-handler": 3.338.0 - "@aws-sdk/types": 3.338.0 + "@aws-sdk/node-http-handler": 3.344.0 + "@aws-sdk/types": 3.342.0 "@aws-sdk/util-buffer-from": 3.310.0 tslib: ^2.5.0 - checksum: 8ab278d971800ec121dda964c65b9be43f58142bf29306fdd292d393f8de5197a59960d4452e8806be01f141343c6d4730484907cb1f6538af547ae58a00c10f + checksum: 9cdfcf50742078d22c7ba52e09e6ce4d1b41610be5658a1154dcf04ca020583596d5a6525025d639a08e83531580e54ad9de3a0e4b03d3eb43aca6fc18a1d440 languageName: node linkType: hard @@ -1745,30 +1746,30 @@ __metadata: languageName: node linkType: hard -"@aws-sdk/util-user-agent-browser@npm:3.338.0": - version: 3.338.0 - resolution: "@aws-sdk/util-user-agent-browser@npm:3.338.0" +"@aws-sdk/util-user-agent-browser@npm:3.345.0": + version: 3.345.0 + resolution: "@aws-sdk/util-user-agent-browser@npm:3.345.0" dependencies: - "@aws-sdk/types": 3.338.0 + "@aws-sdk/types": 3.342.0 bowser: ^2.11.0 tslib: ^2.5.0 - checksum: cea19aebcbc67e943ecfd34a7db53e94060021b1a7b8d79dd39496c42b9991ed80dc46dd42dd2eb4b52d3ce519e07686936cf3c2abd159f807a579c87b1ce1ba + checksum: fcab0d5789aea04ec6f5d2ecdb09ab976de7404e3ed9c0fc553caf098bb823c1c969b1215e15f65f8ad545722334b9e5b172670d817e412e053d96d7a0859cb7 languageName: node linkType: hard -"@aws-sdk/util-user-agent-node@npm:3.338.0": - version: 3.338.0 - resolution: "@aws-sdk/util-user-agent-node@npm:3.338.0" +"@aws-sdk/util-user-agent-node@npm:3.345.0": + version: 3.345.0 + resolution: "@aws-sdk/util-user-agent-node@npm:3.345.0" dependencies: - "@aws-sdk/node-config-provider": 3.338.0 - "@aws-sdk/types": 3.338.0 + "@aws-sdk/node-config-provider": 3.342.0 + "@aws-sdk/types": 3.342.0 tslib: ^2.5.0 peerDependencies: aws-crt: ">=1.0.0" peerDependenciesMeta: aws-crt: optional: true - checksum: dade43fc3218d7828f0f9d3f12c208211b3bae5ccc6018805d49e1a6886d54403d2133856503a76230b7e066e792a8e63ca894368b3e841fb8252e0290282580 + checksum: d4b24bed46b40a92a54b48d5b67f55e3573d4dcaf1908c99fd26c72515a910f45259dd4811605a45733b78a7eba49b950766622a3407cc40bba31ba2817319d2 languageName: node linkType: hard @@ -1791,14 +1792,14 @@ __metadata: languageName: node linkType: hard -"@aws-sdk/util-waiter@npm:3.338.0": - version: 3.338.0 - resolution: "@aws-sdk/util-waiter@npm:3.338.0" +"@aws-sdk/util-waiter@npm:3.342.0": + version: 3.342.0 + resolution: "@aws-sdk/util-waiter@npm:3.342.0" dependencies: - "@aws-sdk/abort-controller": 3.338.0 - "@aws-sdk/types": 3.338.0 + "@aws-sdk/abort-controller": 3.342.0 + "@aws-sdk/types": 3.342.0 tslib: ^2.5.0 - checksum: dda7038d1e7d62a8cc7f30523d1a755e5cc5c6c1cd821236a1f16adb16e87146a69260b23061c198a437e4b3a0a0e706b9f23fc592cc9dbd44276b588ba8100c + checksum: b3f5f3747ffb8bd8323cf57043ec8ed8a2633257deb8113ff9da1cd882a61770ef1d7066e14cfd577c6e83d9de3f24188ab7eb140be951c76260cba05d5bbe70 languageName: node linkType: hard From 229b3efcbcd9884fad70c05eeb24ed03d8e81564 Mon Sep 17 00:00:00 2001 From: Djam Date: Mon, 5 Jun 2023 10:44:18 +0200 Subject: [PATCH 41/65] Update 2023-05-06-backstage-deploy-alpha.mdx Signed-off-by: Djam --- microsite/blog/2023-05-06-backstage-deploy-alpha.mdx | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/microsite/blog/2023-05-06-backstage-deploy-alpha.mdx b/microsite/blog/2023-05-06-backstage-deploy-alpha.mdx index ead9eb5f29..422ba63f3b 100644 --- a/microsite/blog/2023-05-06-backstage-deploy-alpha.mdx +++ b/microsite/blog/2023-05-06-backstage-deploy-alpha.mdx @@ -72,6 +72,6 @@ So, please try this new CLI out and let us know what you think on [Discord](http Useful links: -- [Deploy docs](https://backstage.io/docs/deployment/pulumi/aws) +- [Deploy docs](https://backstage.io/docs/deployment/pulumi/aws-lightsail) - [Pulumi docs](https://www.pulumi.com/docs/) - [#deployment](https://discord.com/channels/687207715902193673/995973463208644678) channel in Discord From 30e0021ffa210b84edf9e7af6b32ca6f462b1cad Mon Sep 17 00:00:00 2001 From: "renovate[bot]" <29139614+renovate[bot]@users.noreply.github.com> Date: Mon, 5 Jun 2023 08:51:52 +0000 Subject: [PATCH 42/65] fix(deps): update dependency @codemirror/view to v6.13.0 Signed-off-by: renovate[bot] <29139614+renovate[bot]@users.noreply.github.com> --- yarn.lock | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/yarn.lock b/yarn.lock index af5096fae1..ba56991048 100644 --- a/yarn.lock +++ b/yarn.lock @@ -10389,13 +10389,13 @@ __metadata: linkType: hard "@codemirror/view@npm:^6.0.0": - version: 6.12.0 - resolution: "@codemirror/view@npm:6.12.0" + version: 6.13.0 + resolution: "@codemirror/view@npm:6.13.0" dependencies: "@codemirror/state": ^6.1.4 style-mod: ^4.0.0 w3c-keyname: ^2.2.4 - checksum: 512cbc9c05ac2cfa738cdf7aac711847b44e24ff5869f31839a9fcc11da6a512448fa9bc980535d55b897de80d49e744336a2724ca1fe3dae8bfcb31e339fe64 + checksum: 3c4713eba5cf54afd9cf92f42295f7a9b42f4041ad9c17fc3dbbeebeb94f95fe3b2bd5377265ceed71a070d5b2472bae2fbb5013254c7e85fe5e1e3b5c807d79 languageName: node linkType: hard From 58c2f1921504dffc6ab8667e857271ffe65d20f7 Mon Sep 17 00:00:00 2001 From: "renovate[bot]" <29139614+renovate[bot]@users.noreply.github.com> Date: Mon, 5 Jun 2023 09:31:58 +0000 Subject: [PATCH 43/65] chore(deps): update dependency @frsource/cypress-plugin-visual-regression-diff to v3.3.8 Signed-off-by: renovate[bot] <29139614+renovate[bot]@users.noreply.github.com> --- yarn.lock | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/yarn.lock b/yarn.lock index ce01a922c0..c11775cb1c 100644 --- a/yarn.lock +++ b/yarn.lock @@ -11161,8 +11161,8 @@ __metadata: linkType: hard "@frsource/cypress-plugin-visual-regression-diff@npm:^3.2.8": - version: 3.3.7 - resolution: "@frsource/cypress-plugin-visual-regression-diff@npm:3.3.7" + version: 3.3.8 + resolution: "@frsource/cypress-plugin-visual-regression-diff@npm:3.3.8" dependencies: "@frsource/base64": 1.0.14 glob: 8.0.3 @@ -11173,7 +11173,7 @@ __metadata: sharp: 0.31.2 peerDependencies: cypress: ">=4.5.0" - checksum: 8521afd0627525d3523307c56eb74b5ca7cce45835cce22e20f9864066f2493efba209165bfce33c00271f0ffa71e6b0a98f43e20614f92a9f529bbc95876c66 + checksum: 657cd8f4343da939677ae8db611445846eed21176fd2494617050ac267aed7665ce1b084aba0ce774170f7113a7bd79af41b3207e457af28a212e46b07f4783d languageName: node linkType: hard From 91ff06bf500d281874742df17e64fae056853d20 Mon Sep 17 00:00:00 2001 From: blam Date: Mon, 5 Jun 2023 12:08:10 +0200 Subject: [PATCH 44/65] chore: bump rjsf deps Signed-off-by: blam --- plugins/home-react/package.json | 2 +- plugins/home/package.json | 8 +-- plugins/scaffolder-react/package.json | 8 +-- plugins/scaffolder/package.json | 4 +- yarn.lock | 82 +++++++++++++++++++++++---- 5 files changed, 81 insertions(+), 23 deletions(-) diff --git a/plugins/home-react/package.json b/plugins/home-react/package.json index f0569f10bd..75cc90f554 100644 --- a/plugins/home-react/package.json +++ b/plugins/home-react/package.json @@ -37,7 +37,7 @@ "@backstage/core-plugin-api": "workspace:^", "@material-ui/core": "^4.12.2", "@material-ui/icons": "^4.9.1", - "@rjsf/utils": "5.6.0" + "@rjsf/utils": "5.7.3" }, "peerDependencies": { "react": "^16.13.1 || ^17.0.0", diff --git a/plugins/home/package.json b/plugins/home/package.json index d645209715..c445295f34 100644 --- a/plugins/home/package.json +++ b/plugins/home/package.json @@ -43,10 +43,10 @@ "@material-ui/core": "^4.12.2", "@material-ui/icons": "^4.9.1", "@material-ui/lab": "4.0.0-alpha.61", - "@rjsf/core-v5": "npm:@rjsf/core@5.6.0", - "@rjsf/material-ui": "5.6.0", - "@rjsf/utils": "5.6.0", - "@rjsf/validator-ajv8": "5.6.0", + "@rjsf/core-v5": "npm:@rjsf/core@5.7.3", + "@rjsf/material-ui": "5.7.3", + "@rjsf/utils": "5.7.3", + "@rjsf/validator-ajv8": "5.7.3", "@types/react": "^16.13.1 || ^17.0.0", "lodash": "^4.17.21", "react-grid-layout": "^1.3.4", diff --git a/plugins/scaffolder-react/package.json b/plugins/scaffolder-react/package.json index 870cf14a07..d6c5432ee1 100644 --- a/plugins/scaffolder-react/package.json +++ b/plugins/scaffolder-react/package.json @@ -60,11 +60,11 @@ "@material-ui/lab": "4.0.0-alpha.61", "@react-hookz/web": "^20.0.0", "@rjsf/core": "^3.2.1", - "@rjsf/core-v5": "npm:@rjsf/core@5.6.0", + "@rjsf/core-v5": "npm:@rjsf/core@5.7.3", "@rjsf/material-ui": "^3.2.1", - "@rjsf/material-ui-v5": "npm:@rjsf/material-ui@5.6.0", - "@rjsf/utils": "5.6.0", - "@rjsf/validator-ajv8": "5.6.0", + "@rjsf/material-ui-v5": "npm:@rjsf/material-ui@5.7.3", + "@rjsf/utils": "5.7.3", + "@rjsf/validator-ajv8": "5.7.3", "@types/json-schema": "^7.0.9", "@types/react": "^16.13.1 || ^17.0.0", "classnames": "^2.2.6", diff --git a/plugins/scaffolder/package.json b/plugins/scaffolder/package.json index de8d3d87ee..e32fac79cd 100644 --- a/plugins/scaffolder/package.json +++ b/plugins/scaffolder/package.json @@ -69,8 +69,8 @@ "@react-hookz/web": "^20.0.0", "@rjsf/core": "^3.2.1", "@rjsf/material-ui": "^3.2.1", - "@rjsf/utils": "5.6.0", - "@rjsf/validator-ajv8": "5.6.0", + "@rjsf/utils": "5.7.3", + "@rjsf/validator-ajv8": "5.7.3", "@types/react": "^16.13.1 || ^17.0.0", "@uiw/react-codemirror": "^4.9.3", "classnames": "^2.2.6", diff --git a/yarn.lock b/yarn.lock index f6f62edc05..e0f1d613ad 100644 --- a/yarn.lock +++ b/yarn.lock @@ -7334,7 +7334,7 @@ __metadata: "@backstage/test-utils": "workspace:^" "@material-ui/core": ^4.12.2 "@material-ui/icons": ^4.9.1 - "@rjsf/utils": 5.6.0 + "@rjsf/utils": 5.7.3 "@testing-library/dom": ^8.0.0 "@testing-library/jest-dom": ^5.10.1 "@testing-library/react": ^12.1.3 @@ -7400,10 +7400,10 @@ __metadata: "@material-ui/core": ^4.12.2 "@material-ui/icons": ^4.9.1 "@material-ui/lab": 4.0.0-alpha.61 - "@rjsf/core-v5": "npm:@rjsf/core@5.6.0" - "@rjsf/material-ui": 5.6.0 - "@rjsf/utils": 5.6.0 - "@rjsf/validator-ajv8": 5.6.0 + "@rjsf/core-v5": "npm:@rjsf/core@5.7.3" + "@rjsf/material-ui": 5.7.3 + "@rjsf/utils": 5.7.3 + "@rjsf/validator-ajv8": 5.7.3 "@testing-library/dom": ^8.0.0 "@testing-library/jest-dom": ^5.10.1 "@testing-library/react": ^12.1.3 @@ -8681,11 +8681,11 @@ __metadata: "@material-ui/lab": 4.0.0-alpha.61 "@react-hookz/web": ^20.0.0 "@rjsf/core": ^3.2.1 - "@rjsf/core-v5": "npm:@rjsf/core@5.6.0" + "@rjsf/core-v5": "npm:@rjsf/core@5.7.3" "@rjsf/material-ui": ^3.2.1 - "@rjsf/material-ui-v5": "npm:@rjsf/material-ui@5.6.0" - "@rjsf/utils": 5.6.0 - "@rjsf/validator-ajv8": 5.6.0 + "@rjsf/material-ui-v5": "npm:@rjsf/material-ui@5.7.3" + "@rjsf/utils": 5.7.3 + "@rjsf/validator-ajv8": 5.7.3 "@testing-library/dom": ^8.0.0 "@testing-library/jest-dom": ^5.10.1 "@testing-library/react": ^12.1.3 @@ -8748,8 +8748,8 @@ __metadata: "@react-hookz/web": ^20.0.0 "@rjsf/core": ^3.2.1 "@rjsf/material-ui": ^3.2.1 - "@rjsf/utils": 5.6.0 - "@rjsf/validator-ajv8": 5.6.0 + "@rjsf/utils": 5.7.3 + "@rjsf/validator-ajv8": 5.7.3 "@testing-library/dom": ^8.0.0 "@testing-library/jest-dom": ^5.10.1 "@testing-library/react": ^12.1.3 @@ -14500,6 +14500,22 @@ __metadata: languageName: node linkType: hard +"@rjsf/core-v5@npm:@rjsf/core@5.7.3": + version: 5.7.3 + resolution: "@rjsf/core@npm:5.7.3" + dependencies: + lodash: ^4.17.21 + lodash-es: ^4.17.21 + markdown-to-jsx: ^7.2.0 + nanoid: ^3.3.6 + prop-types: ^15.8.1 + peerDependencies: + "@rjsf/utils": 5.7.x + react: ^16.14.0 || >=17 + checksum: bdae474fd0a6d4d8fd625ef74384a90624860841e1426b516358365a960d5627a98a1a159a6ddc59cc84659dd768ac7bba126d459c83c4f1d78acd8ad8d98f19 + languageName: node + linkType: hard + "@rjsf/core@npm:^3.2.1": version: 3.2.1 resolution: "@rjsf/core@npm:3.2.1" @@ -14519,7 +14535,20 @@ __metadata: languageName: node linkType: hard -"@rjsf/material-ui-v5@npm:@rjsf/material-ui@5.6.0, @rjsf/material-ui@npm:5.6.0": +"@rjsf/material-ui-v5@npm:@rjsf/material-ui@5.7.3, @rjsf/material-ui@npm:5.7.3": + version: 5.7.3 + resolution: "@rjsf/material-ui@npm:5.7.3" + peerDependencies: + "@material-ui/core": ^4.12.3 + "@material-ui/icons": ^4.11.2 + "@rjsf/core": 5.7.x + "@rjsf/utils": 5.7.x + react: ^16.14.0 || >=17 + checksum: 96ff2a0227b6810efd8b9e36e7e956f1e753c9cecd78215e79e9487af6276da70ee25b8c9d4678241afb85cf5ade31c3591d39659cdeda3cd52ccb6a1ada1d17 + languageName: node + linkType: hard + +"@rjsf/material-ui@npm:5.6.0": version: 5.6.0 resolution: "@rjsf/material-ui@npm:5.6.0" peerDependencies: @@ -14559,6 +14588,21 @@ __metadata: languageName: node linkType: hard +"@rjsf/utils@npm:5.7.3": + version: 5.7.3 + resolution: "@rjsf/utils@npm:5.7.3" + dependencies: + json-schema-merge-allof: ^0.8.1 + jsonpointer: ^5.0.1 + lodash: ^4.17.21 + lodash-es: ^4.17.21 + react-is: ^18.2.0 + peerDependencies: + react: ^16.14.0 || >=17 + checksum: 30ceab80a98a33076eef3c680d079ca90bb7023d40524776fa6cce79f0dc21a5eeaec63fa786e3775b60ccee27f993d030b340d6704c3c4d23515f9d046d4354 + languageName: node + linkType: hard + "@rjsf/validator-ajv8@npm:5.6.0": version: 5.6.0 resolution: "@rjsf/validator-ajv8@npm:5.6.0" @@ -14573,6 +14617,20 @@ __metadata: languageName: node linkType: hard +"@rjsf/validator-ajv8@npm:5.7.3": + version: 5.7.3 + resolution: "@rjsf/validator-ajv8@npm:5.7.3" + dependencies: + ajv: ^8.12.0 + ajv-formats: ^2.1.1 + lodash: ^4.17.21 + lodash-es: ^4.17.21 + peerDependencies: + "@rjsf/utils": 5.7.x + checksum: 0b2ab4bf718c761a8b990f4a3894ad10af2f3d473c425dd4fdf2f1bec6d15a363ac9a012215f0cc4d9fecb0a6cf12bc4e13fd20fa782975e5c0b1e254ef8939e + languageName: node + linkType: hard + "@roadiehq/backstage-plugin-buildkite@npm:^2.0.8": version: 2.1.9 resolution: "@roadiehq/backstage-plugin-buildkite@npm:2.1.9" From 2ff94da135a4af95fdcbfc547e9ef16eca339937 Mon Sep 17 00:00:00 2001 From: blam Date: Mon, 5 Jun 2023 12:09:12 +0200 Subject: [PATCH 45/65] chore: added changeset Signed-off-by: blam --- .changeset/tiny-hounds-cross.md | 8 ++++++++ 1 file changed, 8 insertions(+) create mode 100644 .changeset/tiny-hounds-cross.md diff --git a/.changeset/tiny-hounds-cross.md b/.changeset/tiny-hounds-cross.md new file mode 100644 index 0000000000..822538423f --- /dev/null +++ b/.changeset/tiny-hounds-cross.md @@ -0,0 +1,8 @@ +--- +'@backstage/plugin-scaffolder-react': patch +'@backstage/plugin-home-react': patch +'@backstage/plugin-scaffolder': patch +'@backstage/plugin-home': patch +--- + +bump `rjsf` dependencies to 5.7.3 From 4c49f403a7cfe16b6d0f4dd4873a143559e495e0 Mon Sep 17 00:00:00 2001 From: djamaile Date: Mon, 5 Jun 2023 12:14:47 +0200 Subject: [PATCH 46/65] chore: run prettier Signed-off-by: djamaile --- .../2023-05-06-backstage-deploy-alpha.mdx | 29 ++++++++++--------- 1 file changed, 15 insertions(+), 14 deletions(-) diff --git a/microsite/blog/2023-05-06-backstage-deploy-alpha.mdx b/microsite/blog/2023-05-06-backstage-deploy-alpha.mdx index 422ba63f3b..5c4c3d2164 100644 --- a/microsite/blog/2023-05-06-backstage-deploy-alpha.mdx +++ b/microsite/blog/2023-05-06-backstage-deploy-alpha.mdx @@ -1,5 +1,5 @@ --- -title: "Welcome: Backstage Deploy CLI (Alpha)" +title: 'Welcome: Backstage Deploy CLI (Alpha)' author: Djamaile Rahamat, Spotify authorURL: https://github.com/djamaile authorImageURL: https://avatars.githubusercontent.com/u/15789670?v=4 @@ -9,36 +9,36 @@ _This blog post is co-authored by Emma White ([@ewhite1997](https://github.com/e ![Backstage Deploy banner](assets/2023-05-06/Welcome-Backstage-Deploy.png) -TL;DR: Backstage released a new CLI earlier this year as part of a [new Backstage project](https://github.com/backstage/backstage-deploy). This new capability allows early adopters to deploy their Backstage proof of concept faster than before. In this blog, you’ll learn a little bit more about the Deploy CLI and how you can get started with it. +TL;DR: Backstage released a new CLI earlier this year as part of a [new Backstage project](https://github.com/backstage/backstage-deploy). This new capability allows early adopters to deploy their Backstage proof of concept faster than before. In this blog, you’ll learn a little bit more about the Deploy CLI and how you can get started with it. {/* truncate */} +## Why Backstage Deploy -## Why Backstage Deploy +We’ve heard from Backstage adopters that before reaching widespread adoption at their organizations, teams test out a Backstage proof of concept (POC). To create the POC, teams scaffold an instance, set up the catalog, and change the UI to suit their company’s branding. Once these milestones are completed, there's just one last step before showing off the awesomeness of a Backstage POC internally... deploying the Backstage POC from a local machine to the cloud. This final step often introduces a lot of questions that attempt to determine the easiest and fastest way to do that. -We’ve heard from Backstage adopters that before reaching widespread adoption at their organizations, teams test out a Backstage proof of concept (POC). To create the POC, teams scaffold an instance, set up the catalog, and change the UI to suit their company’s branding. Once these milestones are completed, there's just one last step before showing off the awesomeness of a Backstage POC internally... deploying the Backstage POC from a local machine to the cloud. This final step often introduces a lot of questions that attempt to determine the easiest and fastest way to do that. - -Let’s say you’re at this last step: your POC is ready for deployment, but you have some lingering questions. +Let’s say you’re at this last step: your POC is ready for deployment, but you have some lingering questions. For example: + - What Dockerfile should you use? - Should the POC be deployed on Kubernetes? -- How do you deploy the POC on my cloud provider? +- How do you deploy the POC on my cloud provider? -To address these questions and reduce friction from deploying a POC, we built a [new CLI](https://github.com/backstage/backstage-deploy). The CLI is simply called `deploy` and is invokable with `npx`. With this new CLI, you can generate a Dockerfile and deploy a Backstage instance onto a preferred cloud provider. While the package’s infrastructure is built to support all cloud providers, currently the CLI only offers an AWS implementation. In the future, we plan to add additional cloud providers to the package and [welcome any contributions](https://github.com/backstage/backstage/blob/6996b3338d678efc03307112524060e9dc2ad769/CONTRIBUTING.md) extending the suite of cloud provider implementations! +To address these questions and reduce friction from deploying a POC, we built a [new CLI](https://github.com/backstage/backstage-deploy). The CLI is simply called `deploy` and is invokable with `npx`. With this new CLI, you can generate a Dockerfile and deploy a Backstage instance onto a preferred cloud provider. While the package’s infrastructure is built to support all cloud providers, currently the CLI only offers an AWS implementation. In the future, we plan to add additional cloud providers to the package and [welcome any contributions](https://github.com/backstage/backstage/blob/6996b3338d678efc03307112524060e9dc2ad769/CONTRIBUTING.md) extending the suite of cloud provider implementations! **So, what about Kubernetes?** Since the CLI is designed specifically for the POC phase, we believe that Kubernetes isn’t the right fit – as Kubernetes is better suited for production workloads. So, we explored lightweight, container-based solutions, and landed on [Amazon Lightsail](https://docs.aws.amazon.com/lightsail/index.html) as a hosting service for the POC. -Amazon Lightsail supports [lightweight container](https://lightsail.aws.amazon.com/ls/docs/en_us/articles/amazon-lightsail-container-services) deployments [at a low cost](https://aws.amazon.com/lightsail/pricing/), and has a [free trial for new users](https://aws.amazon.com/lightsail/pricing/?loc=ft#AWS_Free_Tier)! Given Lightsail’s ease of use and affordability, we recommend using Lightsail over Kubernetes to test out your Backstage POC. +Amazon Lightsail supports [lightweight container](https://lightsail.aws.amazon.com/ls/docs/en_us/articles/amazon-lightsail-container-services) deployments [at a low cost](https://aws.amazon.com/lightsail/pricing/), and has a [free trial for new users](https://aws.amazon.com/lightsail/pricing/?loc=ft#AWS_Free_Tier)! Given Lightsail’s ease of use and affordability, we recommend using Lightsail over Kubernetes to test out your Backstage POC. -With the Dockerfile and Kubernetes questions answered, we just have to address how to actually deploy the POC. And that is where the new CLI comes in. +With the Dockerfile and Kubernetes questions answered, we just have to address how to actually deploy the POC. And that is where the new CLI comes in. ## Get started with Deploy CLI It's now time to put the Deploy CLI into action and deploy a Backstage POC. The following steps guide you through the deployment process. -Deploy CLI makes use of [Pulumi](https://www.pulumi.com/docs/) which is an infrastructure-as-code tool that helps provision resources in the cloud. Before you get started, ensure you have the [Pulumi CLI](https://www.pulumi.com/docs/cli/) and [AWS CLI](https://docs.aws.amazon.com/cli/latest/userguide/getting-started-install.html) installed on your local machine. +Deploy CLI makes use of [Pulumi](https://www.pulumi.com/docs/) which is an infrastructure-as-code tool that helps provision resources in the cloud. Before you get started, ensure you have the [Pulumi CLI](https://www.pulumi.com/docs/cli/) and [AWS CLI](https://docs.aws.amazon.com/cli/latest/userguide/getting-started-install.html) installed on your local machine. -You can find the step-by-step installation documentation for Pulumi under the [Deployment section](https://backstage.io/docs/deployment/pulumi/aws). +You can find the step-by-step installation documentation for Pulumi under the [Deployment section](https://backstage.io/docs/deployment/pulumi/aws). But we summarize the steps to deploy your POC here. You can invoke the the CLI you can use the following command: @@ -59,14 +59,15 @@ https://backstage-container-service.xxx.us-east-1.cs.amazonlightsail.com/ Once you kick off the command it will create a Dockerfile for you in the root and Pulumi will start provisioning resources in AWS. Pulumi will then create a container based deployment in Amazon Lightsail. -After you’re done with the POC, it’s easy to delete the AWS resources you provisioned and save you costs within AWS. You can do so with the following command: +After you’re done with the POC, it’s easy to delete the AWS resources you provisioned and save you costs within AWS. You can do so with the following command: ```bash $ npx backstage-deploy aws --destroy ``` + ## Looking ahead -As mentioned earlier in this blog, we released the Backstage Deploy CLI with an AWS implementation only. In the next few months, we are excited to collect feedback from our end users to understand how the AWS implementation works. With those learnings, we plan to iterate on the Deploy CLI and build out implementations for other cloud providers. Of course, contributions are always welcome! +As mentioned earlier in this blog, we released the Backstage Deploy CLI with an AWS implementation only. In the next few months, we are excited to collect feedback from our end users to understand how the AWS implementation works. With those learnings, we plan to iterate on the Deploy CLI and build out implementations for other cloud providers. Of course, contributions are always welcome! So, please try this new CLI out and let us know what you think on [Discord](https://discord.com/channels/687207715902193673/995973463208644678)! From bbfec5fd0487c71082872f3800629742c6d2c1cf Mon Sep 17 00:00:00 2001 From: "renovate[bot]" <29139614+renovate[bot]@users.noreply.github.com> Date: Mon, 5 Jun 2023 10:14:54 +0000 Subject: [PATCH 47/65] fix(deps): update dependency @keyv/redis to v2.6.0 Signed-off-by: renovate[bot] <29139614+renovate[bot]@users.noreply.github.com> --- yarn.lock | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/yarn.lock b/yarn.lock index 5485295a0c..a41e836690 100644 --- a/yarn.lock +++ b/yarn.lock @@ -12680,11 +12680,11 @@ __metadata: linkType: hard "@keyv/redis@npm:^2.5.3": - version: 2.5.8 - resolution: "@keyv/redis@npm:2.5.8" + version: 2.6.0 + resolution: "@keyv/redis@npm:2.6.0" dependencies: ioredis: ^5.3.2 - checksum: 1050c4997b62e701112b48e5375c4e53a5e49454c1621fbb00b1c2272e55a575f9ace49c5179800f73e6f07ce247a4cf6e1260a6713ad1392fd8f8825079771f + checksum: f3e5dc086d0406cd2d12b8660eceef76124b56bbefe204bf152ceb4de536d6370fd60667cd4982936590e1084055a8368c406302c39be492fc45d632b3c06dba languageName: node linkType: hard From f2a38a783559569c16e389da7a6f4146c4556f64 Mon Sep 17 00:00:00 2001 From: "renovate[bot]" <29139614+renovate[bot]@users.noreply.github.com> Date: Mon, 5 Jun 2023 10:15:26 +0000 Subject: [PATCH 48/65] fix(deps): update dependency @rollup/plugin-yaml to v4.1.0 Signed-off-by: renovate[bot] <29139614+renovate[bot]@users.noreply.github.com> --- yarn.lock | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/yarn.lock b/yarn.lock index 5485295a0c..9831b21164 100644 --- a/yarn.lock +++ b/yarn.lock @@ -14730,8 +14730,8 @@ __metadata: linkType: hard "@rollup/plugin-yaml@npm:^4.0.0": - version: 4.0.1 - resolution: "@rollup/plugin-yaml@npm:4.0.1" + version: 4.1.0 + resolution: "@rollup/plugin-yaml@npm:4.1.0" dependencies: "@rollup/pluginutils": ^5.0.1 js-yaml: ^4.1.0 @@ -14741,7 +14741,7 @@ __metadata: peerDependenciesMeta: rollup: optional: true - checksum: d48e248a9acd3110c889d745562e03e5a16e5861838c6b6d92701e59c0d4a24af374ee7bd81db0ab8e6d021cdb925c05bd7d30149e4e9a0fce4d899170a78857 + checksum: e8dcfbb6032ebd493e3cf1f3fcc7ee7e50509e3848a283ab21c743ec59b65b587d3755f744c7135f49db97aee1fc7eee818375519f293e7227e278ccf9d8b3dc languageName: node linkType: hard From 7b8abaf5a8695787118cf08afffbaf254f6d0974 Mon Sep 17 00:00:00 2001 From: "renovate[bot]" <29139614+renovate[bot]@users.noreply.github.com> Date: Mon, 5 Jun 2023 12:08:50 +0000 Subject: [PATCH 49/65] fix(deps): update dependency @tanstack/react-query to v4.29.12 Signed-off-by: renovate[bot] <29139614+renovate[bot]@users.noreply.github.com> --- yarn.lock | 16 ++++++++-------- 1 file changed, 8 insertions(+), 8 deletions(-) diff --git a/yarn.lock b/yarn.lock index 68c2699de5..2a25a00335 100644 --- a/yarn.lock +++ b/yarn.lock @@ -15778,18 +15778,18 @@ __metadata: languageName: node linkType: hard -"@tanstack/query-core@npm:4.27.0": - version: 4.27.0 - resolution: "@tanstack/query-core@npm:4.27.0" - checksum: 914b4f01ac75632f4603b650e9105f64c739b79250baf76aad16cee216f7bad6060c04eda0c70838fe61a5f6c17883e19fcc3075b2433a906539da95ce785796 +"@tanstack/query-core@npm:4.29.11": + version: 4.29.11 + resolution: "@tanstack/query-core@npm:4.29.11" + checksum: 2a17223f34e99e17d564a15206668eb79324da72e630a47cf41690f92fb091a8669bdc89e9ab1b0d8f0e3e8f579529cfb0aa6f10b4fc58ea81cc7e5caede9229 languageName: node linkType: hard "@tanstack/react-query@npm:^4.1.3": - version: 4.28.0 - resolution: "@tanstack/react-query@npm:4.28.0" + version: 4.29.12 + resolution: "@tanstack/react-query@npm:4.29.12" dependencies: - "@tanstack/query-core": 4.27.0 + "@tanstack/query-core": 4.29.11 use-sync-external-store: ^1.2.0 peerDependencies: react: ^16.8.0 || ^17.0.0 || ^18.0.0 @@ -15800,7 +15800,7 @@ __metadata: optional: true react-native: optional: true - checksum: 7baa70d22b55cfa22f8a1d92ba9f8379c5436ee81fce3f0e7df4a8c29bb26bfef4a83759cf10f752b40ae2940099fcce88ce91a773240f4999ae91136980c6e3 + checksum: aea231af648688c5eafdbbda0667034221cca8b77e00690ab54950b7cc0296d14646931aee44fc5f18d5ce4d683b5d234b053eed5c0a5c340bbbacdab873a70b languageName: node linkType: hard From 8f6b60bca12040f77e1881260f5b42787d3393df Mon Sep 17 00:00:00 2001 From: "renovate[bot]" <29139614+renovate[bot]@users.noreply.github.com> Date: Mon, 5 Jun 2023 12:09:22 +0000 Subject: [PATCH 50/65] fix(deps): update dependency @uiw/react-codemirror to v4.21.0 Signed-off-by: renovate[bot] <29139614+renovate[bot]@users.noreply.github.com> --- yarn.lock | 16 ++++++++-------- 1 file changed, 8 insertions(+), 8 deletions(-) diff --git a/yarn.lock b/yarn.lock index 68c2699de5..1e15151df4 100644 --- a/yarn.lock +++ b/yarn.lock @@ -18181,9 +18181,9 @@ __metadata: languageName: node linkType: hard -"@uiw/codemirror-extensions-basic-setup@npm:4.19.16": - version: 4.19.16 - resolution: "@uiw/codemirror-extensions-basic-setup@npm:4.19.16" +"@uiw/codemirror-extensions-basic-setup@npm:4.21.0": + version: 4.21.0 + resolution: "@uiw/codemirror-extensions-basic-setup@npm:4.21.0" dependencies: "@codemirror/autocomplete": ^6.0.0 "@codemirror/commands": ^6.0.0 @@ -18200,19 +18200,19 @@ __metadata: "@codemirror/search": ">=6.0.0" "@codemirror/state": ">=6.0.0" "@codemirror/view": ">=6.0.0" - checksum: e5263f19e1ca838ac9cc7c0ab03d4d1ca2453ff306e17d354b0772954c14cfaa146b0a00ed2d5690f5687aeafdd5f2f5587efc573ffb5714bd77f6af46444f74 + checksum: 9b39f219cbbe00653a295ad05b6125c5b960f0343dfd68e1d9e0f97d4fba023bccb43915647ac3a9cbbb9e9ff54ffb9addfe3114aa22038952e1e1e59e3ab418 languageName: node linkType: hard "@uiw/react-codemirror@npm:^4.9.3": - version: 4.19.16 - resolution: "@uiw/react-codemirror@npm:4.19.16" + version: 4.21.0 + resolution: "@uiw/react-codemirror@npm:4.21.0" dependencies: "@babel/runtime": ^7.18.6 "@codemirror/commands": ^6.1.0 "@codemirror/state": ^6.1.1 "@codemirror/theme-one-dark": ^6.0.0 - "@uiw/codemirror-extensions-basic-setup": 4.19.16 + "@uiw/codemirror-extensions-basic-setup": 4.21.0 codemirror: ^6.0.0 peerDependencies: "@babel/runtime": ">=7.11.0" @@ -18222,7 +18222,7 @@ __metadata: codemirror: ">=6.0.0" react: ">=16.8.0" react-dom: ">=16.8.0" - checksum: 0625a544eb53ff1236e75dc4c81400285bf4dfdacd5c9c71129066f7decb7e902c97f756c6edc854d44b586ad4b0d3d303df065429532df9085c5f6b1adbad80 + checksum: 783a9b4fd3fc655d8a15fd7847ad36a3eb65cb88ac268622adf9cc93e55bc42a4f5a59cf288fc6ef05763dc090b7f5d21468633a7ead519a89a50d8db7bd4c8f languageName: node linkType: hard From 3fbeeae1bbc1baf785d73668da522f36afd3f834 Mon Sep 17 00:00:00 2001 From: "renovate[bot]" <29139614+renovate[bot]@users.noreply.github.com> Date: Mon, 5 Jun 2023 13:11:47 +0000 Subject: [PATCH 51/65] fix(deps): update dependency core-js to v3.30.2 Signed-off-by: renovate[bot] <29139614+renovate[bot]@users.noreply.github.com> --- yarn.lock | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/yarn.lock b/yarn.lock index cc84346c1a..688f5de26a 100644 --- a/yarn.lock +++ b/yarn.lock @@ -21629,9 +21629,9 @@ __metadata: linkType: hard "core-js@npm:^3.6.5": - version: 3.29.1 - resolution: "core-js@npm:3.29.1" - checksum: b38446dbfcfd3887b3d4922990da487e2c95044cb4c5717aaf95e786a4c6b218f05c056c7ed6c699169b9794a49fec890e402659d54661fc56965a0eb717e7bd + version: 3.30.2 + resolution: "core-js@npm:3.30.2" + checksum: 73d47e2b9d9f502800973982d08e995bbf04832e20b04e04be31dd7607247158271315e9328788a2408190e291c7ffbefad141167b1e57dea9f983e1e723541e languageName: node linkType: hard From 141b7d3fe78faf6046040ae665965765d48ea248 Mon Sep 17 00:00:00 2001 From: "renovate[bot]" <29139614+renovate[bot]@users.noreply.github.com> Date: Mon, 5 Jun 2023 13:12:20 +0000 Subject: [PATCH 52/65] fix(deps): update dependency cronstrue to v2.27.0 Signed-off-by: renovate[bot] <29139614+renovate[bot]@users.noreply.github.com> --- yarn.lock | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/yarn.lock b/yarn.lock index cc84346c1a..26538bcc8d 100644 --- a/yarn.lock +++ b/yarn.lock @@ -21783,11 +21783,11 @@ __metadata: linkType: hard "cronstrue@npm:^2.2.0": - version: 2.24.0 - resolution: "cronstrue@npm:2.24.0" + version: 2.27.0 + resolution: "cronstrue@npm:2.27.0" bin: cronstrue: bin/cli.js - checksum: 2c7d4cfe43bec7b57b1824772641271bb5f5ed0209336ea53796f97b17966dd95cf15ae890f7c2494f639ba489d225bfb882950cda0ec7e5453fa7bf236842dd + checksum: 310d933c4448896519c203a434dc1ede7029967df941e810f02bafb62146045c16df4987edde344d757bafb6d45f63c9ecb7385df19b985ca91486f4efa6ff7b languageName: node linkType: hard From e74df57b2cfbd102fde38c16293b402e317a4483 Mon Sep 17 00:00:00 2001 From: "renovate[bot]" <29139614+renovate[bot]@users.noreply.github.com> Date: Mon, 5 Jun 2023 14:12:38 +0000 Subject: [PATCH 53/65] fix(deps): update dependency css-loader to v6.8.1 Signed-off-by: renovate[bot] <29139614+renovate[bot]@users.noreply.github.com> --- yarn.lock | 16 ++++++++-------- 1 file changed, 8 insertions(+), 8 deletions(-) diff --git a/yarn.lock b/yarn.lock index 5786798323..97c01b6054 100644 --- a/yarn.lock +++ b/yarn.lock @@ -21924,20 +21924,20 @@ __metadata: linkType: hard "css-loader@npm:^6.5.1": - version: 6.7.4 - resolution: "css-loader@npm:6.7.4" + version: 6.8.1 + resolution: "css-loader@npm:6.8.1" dependencies: icss-utils: ^5.1.0 postcss: ^8.4.21 postcss-modules-extract-imports: ^3.0.0 - postcss-modules-local-by-default: ^4.0.1 + postcss-modules-local-by-default: ^4.0.3 postcss-modules-scope: ^3.0.0 postcss-modules-values: ^4.0.0 postcss-value-parser: ^4.2.0 semver: ^7.3.8 peerDependencies: webpack: ^5.0.0 - checksum: 6021fa9e375d767b9675e295c1513f2ee4ae04f76d9de69a75b8446e05f6e02b2170407ea72939925b788dcd5aa308527f6b41be3870dc1f4b0bfff8d2532c6e + checksum: 7c1784247bdbe76dc5c55fb1ac84f1d4177a74c47259942c9cfdb7a8e6baef11967a0bc85ac285f26bd26d5059decb848af8154a03fdb4f4894f41212f45eef3 languageName: node linkType: hard @@ -34495,16 +34495,16 @@ __metadata: languageName: node linkType: hard -"postcss-modules-local-by-default@npm:^4.0.0, postcss-modules-local-by-default@npm:^4.0.1": - version: 4.0.1 - resolution: "postcss-modules-local-by-default@npm:4.0.1" +"postcss-modules-local-by-default@npm:^4.0.0, postcss-modules-local-by-default@npm:^4.0.3": + version: 4.0.3 + resolution: "postcss-modules-local-by-default@npm:4.0.3" dependencies: icss-utils: ^5.0.0 postcss-selector-parser: ^6.0.2 postcss-value-parser: ^4.1.0 peerDependencies: postcss: ^8.1.0 - checksum: 1a95eb8bc54a363a77dbd77a0a88f500e7937ecbed5903becef9362eace28de406e6fdf62640126c22964678370e87eb10481eea2703702772935b4515603bfd + checksum: 2f8083687f3d6067885f8863dd32dbbb4f779cfcc7e52c17abede9311d84faf6d3ed8760e7c54c6380281732ae1f78e5e56a28baf3c271b33f450a11c9e30485 languageName: node linkType: hard From 243b79bac2e4278fd955854195122c71fafc2a02 Mon Sep 17 00:00:00 2001 From: "renovate[bot]" <29139614+renovate[bot]@users.noreply.github.com> Date: Mon, 5 Jun 2023 14:13:11 +0000 Subject: [PATCH 54/65] fix(deps): update dependency elastic-builder to v2.19.0 Signed-off-by: renovate[bot] <29139614+renovate[bot]@users.noreply.github.com> --- yarn.lock | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/yarn.lock b/yarn.lock index 5786798323..5fd85b1da1 100644 --- a/yarn.lock +++ b/yarn.lock @@ -23291,8 +23291,8 @@ __metadata: linkType: hard "elastic-builder@npm:^2.16.0": - version: 2.18.1 - resolution: "elastic-builder@npm:2.18.1" + version: 2.19.0 + resolution: "elastic-builder@npm:2.19.0" dependencies: lodash.has: ^4.5.2 lodash.hasin: ^4.5.2 @@ -23302,7 +23302,7 @@ __metadata: lodash.isobject: ^3.0.2 lodash.isstring: ^4.0.1 lodash.omit: ^4.5.0 - checksum: 54093daadc1fc3666ac8eef0a268267761e92a3fbb524e51936cf944ceeaeb231a269fc8ae9fb902ca41c976c76c0c037da692a34577d705da301ed727bd8e07 + checksum: 14c3a2e2a76f44425dfff4c57e16f077553845976422cb35c35d235e1ea59942b86c379e516828e8390e3c53360a564ff94ee3aa961a5f2fb791da7e5e97012c languageName: node linkType: hard From 54c1d95bdd2065a4298987af9276c337cab652b0 Mon Sep 17 00:00:00 2001 From: "renovate[bot]" <29139614+renovate[bot]@users.noreply.github.com> Date: Mon, 5 Jun 2023 15:12:33 +0000 Subject: [PATCH 55/65] fix(deps): update dependency @uiw/react-codemirror to v4.21.1 Signed-off-by: renovate[bot] <29139614+renovate[bot]@users.noreply.github.com> --- yarn.lock | 16 ++++++++-------- 1 file changed, 8 insertions(+), 8 deletions(-) diff --git a/yarn.lock b/yarn.lock index 5052893de4..50c2bb2d5b 100644 --- a/yarn.lock +++ b/yarn.lock @@ -18181,9 +18181,9 @@ __metadata: languageName: node linkType: hard -"@uiw/codemirror-extensions-basic-setup@npm:4.21.0": - version: 4.21.0 - resolution: "@uiw/codemirror-extensions-basic-setup@npm:4.21.0" +"@uiw/codemirror-extensions-basic-setup@npm:4.21.1": + version: 4.21.1 + resolution: "@uiw/codemirror-extensions-basic-setup@npm:4.21.1" dependencies: "@codemirror/autocomplete": ^6.0.0 "@codemirror/commands": ^6.0.0 @@ -18200,19 +18200,19 @@ __metadata: "@codemirror/search": ">=6.0.0" "@codemirror/state": ">=6.0.0" "@codemirror/view": ">=6.0.0" - checksum: 9b39f219cbbe00653a295ad05b6125c5b960f0343dfd68e1d9e0f97d4fba023bccb43915647ac3a9cbbb9e9ff54ffb9addfe3114aa22038952e1e1e59e3ab418 + checksum: ac1f90f9396b5542bd30222c513354e6756972c455931e4a48327ceaadb4c0c9fa0763a87c6d166ee3cfe45941cb348661f6ee4672f71fd67e8708e73231095b languageName: node linkType: hard "@uiw/react-codemirror@npm:^4.9.3": - version: 4.21.0 - resolution: "@uiw/react-codemirror@npm:4.21.0" + version: 4.21.1 + resolution: "@uiw/react-codemirror@npm:4.21.1" dependencies: "@babel/runtime": ^7.18.6 "@codemirror/commands": ^6.1.0 "@codemirror/state": ^6.1.1 "@codemirror/theme-one-dark": ^6.0.0 - "@uiw/codemirror-extensions-basic-setup": 4.21.0 + "@uiw/codemirror-extensions-basic-setup": 4.21.1 codemirror: ^6.0.0 peerDependencies: "@babel/runtime": ">=7.11.0" @@ -18222,7 +18222,7 @@ __metadata: codemirror: ">=6.0.0" react: ">=16.8.0" react-dom: ">=16.8.0" - checksum: 783a9b4fd3fc655d8a15fd7847ad36a3eb65cb88ac268622adf9cc93e55bc42a4f5a59cf288fc6ef05763dc090b7f5d21468633a7ead519a89a50d8db7bd4c8f + checksum: 359848cad18ae9a70d9767e07f9f520459b0794f32b9558ec442db92ea83f392a5f0b0fcab56804328e18bf4d1371a18ef2eaa5847c5e94603ff9a2dc1123a26 languageName: node linkType: hard From 5c4267337fcbe12f6e301e0161a14caa1bf82ef9 Mon Sep 17 00:00:00 2001 From: Djam Date: Mon, 5 Jun 2023 17:52:21 +0200 Subject: [PATCH 56/65] Update 2023-05-06-backstage-deploy-alpha.mdx Signed-off-by: Djam --- microsite/blog/2023-05-06-backstage-deploy-alpha.mdx | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/microsite/blog/2023-05-06-backstage-deploy-alpha.mdx b/microsite/blog/2023-05-06-backstage-deploy-alpha.mdx index 5c4c3d2164..cc0f3ee1a9 100644 --- a/microsite/blog/2023-05-06-backstage-deploy-alpha.mdx +++ b/microsite/blog/2023-05-06-backstage-deploy-alpha.mdx @@ -73,6 +73,6 @@ So, please try this new CLI out and let us know what you think on [Discord](http Useful links: -- [Deploy docs](https://backstage.io/docs/deployment/pulumi/aws-lightsail) +- [Backstage Deploy](https://github.com/backstage/backstage-deploy) - [Pulumi docs](https://www.pulumi.com/docs/) - [#deployment](https://discord.com/channels/687207715902193673/995973463208644678) channel in Discord From 7dd8fa7aab2e240440e0e03d58396c681a3cf880 Mon Sep 17 00:00:00 2001 From: "renovate[bot]" <29139614+renovate[bot]@users.noreply.github.com> Date: Mon, 5 Jun 2023 16:08:10 +0000 Subject: [PATCH 57/65] fix(deps): update dependency @google-cloud/storage to v6.11.0 Signed-off-by: renovate[bot] <29139614+renovate[bot]@users.noreply.github.com> --- yarn.lock | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/yarn.lock b/yarn.lock index 50c2bb2d5b..0d8f98d807 100644 --- a/yarn.lock +++ b/yarn.lock @@ -11280,8 +11280,8 @@ __metadata: linkType: hard "@google-cloud/storage@npm:^6.0.0": - version: 6.10.1 - resolution: "@google-cloud/storage@npm:6.10.1" + version: 6.11.0 + resolution: "@google-cloud/storage@npm:6.11.0" dependencies: "@google-cloud/paginator": ^3.0.7 "@google-cloud/projectify": ^3.0.0 @@ -11300,7 +11300,7 @@ __metadata: retry-request: ^5.0.0 teeny-request: ^8.0.0 uuid: ^8.0.0 - checksum: 8908500e3057456ccac5cca17224807898a5c51c0423dec336e802ed0bc0785be7658b0050f848102a2f9207dbf3fb2649f6cc8e515c49fce3a134a8f158ecea + checksum: 4183c0ad3b271e0c22b3aa01e9942590ae64b984efa142a787b96379baaf4c05a2ebdbb6015c8ea189951df251d57f4f35c6a28b920922828cc89d3e4147d1a1 languageName: node linkType: hard From 024e9554f2f1b1b7f12193987b9ddaf0d9084fd6 Mon Sep 17 00:00:00 2001 From: "renovate[bot]" <29139614+renovate[bot]@users.noreply.github.com> Date: Mon, 5 Jun 2023 16:08:45 +0000 Subject: [PATCH 58/65] fix(deps): update dependency eslint-plugin-deprecation to v1.4.1 Signed-off-by: renovate[bot] <29139614+renovate[bot]@users.noreply.github.com> --- yarn.lock | 129 ++++++++++++++---------------------------------------- 1 file changed, 34 insertions(+), 95 deletions(-) diff --git a/yarn.lock b/yarn.lock index 50c2bb2d5b..ce636d7b04 100644 --- a/yarn.lock +++ b/yarn.lock @@ -17960,22 +17960,6 @@ __metadata: languageName: node linkType: hard -"@typescript-eslint/experimental-utils@npm:^5.0.0": - version: 5.9.0 - resolution: "@typescript-eslint/experimental-utils@npm:5.9.0" - dependencies: - "@types/json-schema": ^7.0.9 - "@typescript-eslint/scope-manager": 5.9.0 - "@typescript-eslint/types": 5.9.0 - "@typescript-eslint/typescript-estree": 5.9.0 - eslint-scope: ^5.1.1 - eslint-utils: ^3.0.0 - peerDependencies: - eslint: ^6.0.0 || ^7.0.0 || ^8.0.0 - checksum: 731b27840642b644e65f4ae321ed47e973ffadacd1aa24a19b02b4b298b5bcfbfa16c2d3d034e87a08c3c45f942c5b974f7619cb143eb23fb950f37418dce791 - languageName: node - linkType: hard - "@typescript-eslint/parser@npm:^5.9.0": version: 5.53.0 resolution: "@typescript-eslint/parser@npm:5.53.0" @@ -18003,23 +17987,13 @@ __metadata: languageName: node linkType: hard -"@typescript-eslint/scope-manager@npm:5.58.0": - version: 5.58.0 - resolution: "@typescript-eslint/scope-manager@npm:5.58.0" +"@typescript-eslint/scope-manager@npm:5.59.8": + version: 5.59.8 + resolution: "@typescript-eslint/scope-manager@npm:5.59.8" dependencies: - "@typescript-eslint/types": 5.58.0 - "@typescript-eslint/visitor-keys": 5.58.0 - checksum: f0d3df5cc3c461fe63ef89ad886b53c239cc7c1d9061d83d8a9d9c8e087e5501eac84bebff8a954728c17ccea191f235686373d54d2b8b6370af2bcf2b18e062 - languageName: node - linkType: hard - -"@typescript-eslint/scope-manager@npm:5.9.0": - version: 5.9.0 - resolution: "@typescript-eslint/scope-manager@npm:5.9.0" - dependencies: - "@typescript-eslint/types": 5.9.0 - "@typescript-eslint/visitor-keys": 5.9.0 - checksum: 46e7ab0cef558e7faf1aa8d122a265e196566c0073292f5b2f9cede1f63f52860be8e4ef90251c15e0922339c15852584cb5337382035baff87f1203c0c8d1b5 + "@typescript-eslint/types": 5.59.8 + "@typescript-eslint/visitor-keys": 5.59.8 + checksum: e1e810ee991cfeb433330b04ee949bb6784abe4dbdb7d9480aa7a7536671b4fec914b7803edf662516c8ecb1b31dcff126797f9923270a529c26e2b00b0ea96f languageName: node linkType: hard @@ -18047,17 +18021,10 @@ __metadata: languageName: node linkType: hard -"@typescript-eslint/types@npm:5.58.0": - version: 5.58.0 - resolution: "@typescript-eslint/types@npm:5.58.0" - checksum: 8622a73d73220c4a7111537825f488c0271272032a1d4e129dc722bc6e8b3ec84f64469b2ca3b8dae7da3a9c18953ce1449af51f5f757dad60835eb579ad1d2c - languageName: node - linkType: hard - -"@typescript-eslint/types@npm:5.9.0": - version: 5.9.0 - resolution: "@typescript-eslint/types@npm:5.9.0" - checksum: 7c4e142600aec266b41418dab1d0cee8cace980b6990692df6522de6eab6705bf515aef36180e4a38c62acb10c92fb474269ac6856a4266d6b035068cd83fad3 +"@typescript-eslint/types@npm:5.59.8": + version: 5.59.8 + resolution: "@typescript-eslint/types@npm:5.59.8" + checksum: 559473d5601c849eb0da1874a2ac67c753480beed484ad6f6cda62fa6023273f2c3005c7f2864d9c2afb7c6356412d0d304b57db10c53597207f18a7f6cd4f18 languageName: node linkType: hard @@ -18079,12 +18046,12 @@ __metadata: languageName: node linkType: hard -"@typescript-eslint/typescript-estree@npm:5.58.0": - version: 5.58.0 - resolution: "@typescript-eslint/typescript-estree@npm:5.58.0" +"@typescript-eslint/typescript-estree@npm:5.59.8": + version: 5.59.8 + resolution: "@typescript-eslint/typescript-estree@npm:5.59.8" dependencies: - "@typescript-eslint/types": 5.58.0 - "@typescript-eslint/visitor-keys": 5.58.0 + "@typescript-eslint/types": 5.59.8 + "@typescript-eslint/visitor-keys": 5.59.8 debug: ^4.3.4 globby: ^11.1.0 is-glob: ^4.0.3 @@ -18093,25 +18060,7 @@ __metadata: peerDependenciesMeta: typescript: optional: true - checksum: 51b668ec858db0c040a71dff526273945cee4ba5a9b240528d503d02526685882d900cf071c6636a4d9061ed3fd4a7274f7f1a23fba55c4b48b143344b4009c7 - languageName: node - linkType: hard - -"@typescript-eslint/typescript-estree@npm:5.9.0": - version: 5.9.0 - resolution: "@typescript-eslint/typescript-estree@npm:5.9.0" - dependencies: - "@typescript-eslint/types": 5.9.0 - "@typescript-eslint/visitor-keys": 5.9.0 - debug: ^4.3.2 - globby: ^11.0.4 - is-glob: ^4.0.3 - semver: ^7.3.5 - tsutils: ^3.21.0 - peerDependenciesMeta: - typescript: - optional: true - checksum: 71e3f720e335fb08e66950d32b723484aa4d1f4a3163e82259f4be2d11091545070c2e71472be470403cb6f82bf1abe84fa89c1d0b1d47adc8550b3f70aabfb5 + checksum: d93371cc866f573a6a1ddc0eb10d498a8e59f36763a99ce21da0737fff2b4c942eef1587216aad273f8d896ebc0b19003677cba63a27d2646aa2c087638963eb languageName: node linkType: hard @@ -18133,21 +18082,21 @@ __metadata: languageName: node linkType: hard -"@typescript-eslint/utils@npm:^5.10.0, @typescript-eslint/utils@npm:^5.58.0": - version: 5.58.0 - resolution: "@typescript-eslint/utils@npm:5.58.0" +"@typescript-eslint/utils@npm:^5.10.0, @typescript-eslint/utils@npm:^5.57.0, @typescript-eslint/utils@npm:^5.58.0": + version: 5.59.8 + resolution: "@typescript-eslint/utils@npm:5.59.8" dependencies: "@eslint-community/eslint-utils": ^4.2.0 "@types/json-schema": ^7.0.9 "@types/semver": ^7.3.12 - "@typescript-eslint/scope-manager": 5.58.0 - "@typescript-eslint/types": 5.58.0 - "@typescript-eslint/typescript-estree": 5.58.0 + "@typescript-eslint/scope-manager": 5.59.8 + "@typescript-eslint/types": 5.59.8 + "@typescript-eslint/typescript-estree": 5.59.8 eslint-scope: ^5.1.1 semver: ^7.3.7 peerDependencies: eslint: ^6.0.0 || ^7.0.0 || ^8.0.0 - checksum: c618ae67963ecf96b1492c09afaeb363f542f0d6780bcac4af3c26034e3b20034666b2d523aa94821df813aafb57a0b150a7d5c2224fe8257452ad1de2237a58 + checksum: cbaa057485c7f52c45d0dfb4f5a8e9273abccb1c52dcb4426a79f9e71d2c1062cf2525bad6d4aca5ec42db3fe723d749843bcade5a323bde7fbe4b5d5b5d5c3b languageName: node linkType: hard @@ -18161,23 +18110,13 @@ __metadata: languageName: node linkType: hard -"@typescript-eslint/visitor-keys@npm:5.58.0": - version: 5.58.0 - resolution: "@typescript-eslint/visitor-keys@npm:5.58.0" +"@typescript-eslint/visitor-keys@npm:5.59.8": + version: 5.59.8 + resolution: "@typescript-eslint/visitor-keys@npm:5.59.8" dependencies: - "@typescript-eslint/types": 5.58.0 + "@typescript-eslint/types": 5.59.8 eslint-visitor-keys: ^3.3.0 - checksum: ab2d1f37660559954c840429ef78bbf71834063557e3e68e435005b4987970b9356fdf217ead53f7a57f66f5488dc478062c5c44bf17053a8bf041733539b98f - languageName: node - linkType: hard - -"@typescript-eslint/visitor-keys@npm:5.9.0": - version: 5.9.0 - resolution: "@typescript-eslint/visitor-keys@npm:5.9.0" - dependencies: - "@typescript-eslint/types": 5.9.0 - eslint-visitor-keys: ^3.0.0 - checksum: 34a595b83b0e7d4f387d6c81b272804b94a1a91478c5f856fdfdd227595bf8562bf3f5d732606d10b4522c3f2617d09d4bacd2193f757a324ea66b3144a68903 + checksum: 6bfa7918dbb0e08d8a7404aeeef7bcd1a85736dc8d01614d267c0c5ec10f94d2746b50a945bf5c82c54fda67926e8deaeba8565c919da17f725fc11209ef8987 languageName: node linkType: hard @@ -24103,16 +24042,16 @@ __metadata: linkType: hard "eslint-plugin-deprecation@npm:^1.3.2": - version: 1.3.3 - resolution: "eslint-plugin-deprecation@npm:1.3.3" + version: 1.4.1 + resolution: "eslint-plugin-deprecation@npm:1.4.1" dependencies: - "@typescript-eslint/experimental-utils": ^5.0.0 + "@typescript-eslint/utils": ^5.57.0 tslib: ^2.3.1 tsutils: ^3.21.0 peerDependencies: eslint: ^6.0.0 || ^7.0.0 || ^8.0.0 - typescript: ^3.7.5 || ^4.0.0 - checksum: 5e14d7bc8245a14784623632d43a6210880a4aad4c029fd44686a5516c248287f32406ff230f6e9d238784854b24cd09da953ec8f73d9d19a7c4b3905884e432 + typescript: ^3.7.5 || ^4.0.0 || ^5.0.0 + checksum: 75c7535d820d1749664705724cc979d706da126a2277f2937467f70156a2c220b10c66670f18226801c9555e4cd02312d353936f14d5752c2d2c648455fe5769 languageName: node linkType: hard @@ -24280,7 +24219,7 @@ __metadata: languageName: node linkType: hard -"eslint-visitor-keys@npm:^3.0.0, eslint-visitor-keys@npm:^3.3.0, eslint-visitor-keys@npm:^3.4.1": +"eslint-visitor-keys@npm:^3.3.0, eslint-visitor-keys@npm:^3.4.1": version: 3.4.1 resolution: "eslint-visitor-keys@npm:3.4.1" checksum: f05121d868202736b97de7d750847a328fcfa8593b031c95ea89425333db59676ac087fa905eba438d0a3c5769632f828187e0c1a0d271832a2153c1d3661c2c From 856495adb036b1c009ee862f9d3e2eb6761df7f1 Mon Sep 17 00:00:00 2001 From: "renovate[bot]" <29139614+renovate[bot]@users.noreply.github.com> Date: Mon, 5 Jun 2023 17:33:17 +0000 Subject: [PATCH 59/65] fix(deps): update dependency @keyv/redis to v2.6.1 Signed-off-by: renovate[bot] <29139614+renovate[bot]@users.noreply.github.com> --- yarn.lock | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/yarn.lock b/yarn.lock index 943bd87958..7f430b63bf 100644 --- a/yarn.lock +++ b/yarn.lock @@ -12680,11 +12680,11 @@ __metadata: linkType: hard "@keyv/redis@npm:^2.5.3": - version: 2.6.0 - resolution: "@keyv/redis@npm:2.6.0" + version: 2.6.1 + resolution: "@keyv/redis@npm:2.6.1" dependencies: ioredis: ^5.3.2 - checksum: f3e5dc086d0406cd2d12b8660eceef76124b56bbefe204bf152ceb4de536d6370fd60667cd4982936590e1084055a8368c406302c39be492fc45d632b3c06dba + checksum: c0c0aa7d0b449ef295ab65bcc38d42a2f6f606f49bf1d9bc95cd0276d60854c4d579d6dfce9e070f350a07987dfde9d452884ee05e8f87215c49c304b27a68ab languageName: node linkType: hard From 73cc0deee48ae0f1b58ade5c0acc4a6e786dd5e4 Mon Sep 17 00:00:00 2001 From: Matthew Clarke Date: Mon, 5 Jun 2023 16:45:48 -0400 Subject: [PATCH 60/65] feat: Proposed fix dialog (#17576) * feat: add errors to Pod Drawer Signed-off-by: Matthew Clarke * fix: lint fix Signed-off-by: Matthew Clarke * test: useMatchingErrorTest Signed-off-by: Matthew Clarke * feat: pod fix dialog for errors Signed-off-by: Matthew Clarke * fix: link Signed-off-by: Matthew Clarke * fix: icon tweak Signed-off-by: Matthew Clarke --------- Signed-off-by: Matthew Clarke --- .changeset/wise-bats-repair.md | 6 + .../dice-roller/dice-roller-manifests.yaml | 36 ++++ plugins/kubernetes/api-report.md | 195 +++++++++++++++++- .../src/api/KubernetesProxyClient.test.ts | 70 +++++++ .../src/api/KubernetesProxyClient.ts | 44 ++++ plugins/kubernetes/src/api/types.ts | 7 + .../Pods/ErrorList/ErrorList.test.tsx | 16 +- .../components/Pods/ErrorList/ErrorList.tsx | 33 ++- .../components/Pods/Events/Events.test.tsx | 96 +++++++++ .../src/components/Pods/Events/Events.tsx | 154 ++++++++++++++ .../src/components/Pods/Events/index.ts | 17 ++ .../components/Pods/Events/useEvents.test.tsx | 68 ++++++ .../src/components/Pods/Events/useEvents.ts | 49 +++++ .../Pods/FixDialog/FixDialog.test.tsx | 159 ++++++++++++++ .../components/Pods/FixDialog/FixDialog.tsx | 187 +++++++++++++++++ .../src/components/Pods/FixDialog/index.ts | 16 ++ .../Pods/PodDrawer/ContainerCard.tsx | 12 +- .../Pods/PodDrawer/PendingPodContent.tsx | 14 +- .../Pods/PodDrawer/PodDrawer.test.tsx | 2 +- .../components/Pods/PodDrawer/PodDrawer.tsx | 11 + .../src/components/Pods/PodDrawer/index.ts | 4 +- .../src/components/Pods/PodLogs/PodLogs.tsx | 43 +++- .../components/Pods/PodLogs/PodLogsDialog.tsx | 22 +- .../src/components/Pods/PodLogs/types.ts | 10 + .../src/components/Pods/PodLogs/usePodLogs.ts | 28 ++- .../kubernetes/src/components/Pods/index.ts | 7 +- .../kubernetes/src/components/Pods/types.ts | 5 + .../src/error-detection/deployments.ts | 1 - .../error-detection/error-detection.test.ts | 63 +++++- .../kubernetes/src/error-detection/hpas.ts | 1 - .../kubernetes/src/error-detection/pods.ts | 131 +++++++++++- .../kubernetes/src/error-detection/types.ts | 7 +- .../src/hooks/useMatchingErrors.test.tsx | 16 +- 33 files changed, 1457 insertions(+), 73 deletions(-) create mode 100644 .changeset/wise-bats-repair.md create mode 100644 plugins/kubernetes/src/components/Pods/Events/Events.test.tsx create mode 100644 plugins/kubernetes/src/components/Pods/Events/Events.tsx create mode 100644 plugins/kubernetes/src/components/Pods/Events/index.ts create mode 100644 plugins/kubernetes/src/components/Pods/Events/useEvents.test.tsx create mode 100644 plugins/kubernetes/src/components/Pods/Events/useEvents.ts create mode 100644 plugins/kubernetes/src/components/Pods/FixDialog/FixDialog.test.tsx create mode 100644 plugins/kubernetes/src/components/Pods/FixDialog/FixDialog.tsx create mode 100644 plugins/kubernetes/src/components/Pods/FixDialog/index.ts diff --git a/.changeset/wise-bats-repair.md b/.changeset/wise-bats-repair.md new file mode 100644 index 0000000000..fc383eb11d --- /dev/null +++ b/.changeset/wise-bats-repair.md @@ -0,0 +1,6 @@ +--- +'@backstage/plugin-kubernetes-backend': patch +'@backstage/plugin-kubernetes': patch +--- + +Add proposed fix dialog for pod errors diff --git a/plugins/kubernetes-backend/examples/dice-roller/dice-roller-manifests.yaml b/plugins/kubernetes-backend/examples/dice-roller/dice-roller-manifests.yaml index a1a2e105b3..8f225e666a 100644 --- a/plugins/kubernetes-backend/examples/dice-roller/dice-roller-manifests.yaml +++ b/plugins/kubernetes-backend/examples/dice-roller/dice-roller-manifests.yaml @@ -32,6 +32,42 @@ spec: ports: - containerPort: 80 +--- +apiVersion: apps/v1 +kind: Deployment +metadata: + name: dice-roller-incorrect-probe + labels: + 'backstage.io/kubernetes-id': dice-roller +spec: + selector: + matchLabels: + app: dice-roller-incorrect-probe + replicas: 2 + template: + metadata: + labels: + app: dice-roller-incorrect-probe + 'backstage.io/kubernetes-id': dice-roller + spec: + containers: + - name: nginx + image: nginx:1.14.2 + resources: + requests: + memory: '64Mi' + cpu: '50m' + limits: + memory: '128Mi' + cpu: '50m' + readinessProbe: + tcpSocket: + port: 8080 + initialDelaySeconds: 5 + periodSeconds: 10 + ports: + - containerPort: 80 + --- apiVersion: apps/v1 kind: Deployment diff --git a/plugins/kubernetes/api-report.md b/plugins/kubernetes/api-report.md index 823b9c89a2..e117e3627d 100644 --- a/plugins/kubernetes/api-report.md +++ b/plugins/kubernetes/api-report.md @@ -6,6 +6,7 @@ /// import { ApiRef } from '@backstage/core-plugin-api'; +import { AsyncState } from 'react-use/lib/useAsyncFn'; import { BackstagePlugin } from '@backstage/core-plugin-api'; import { ClientPodStatus } from '@backstage/plugin-kubernetes-common'; import { ClusterAttributes } from '@backstage/plugin-kubernetes-common'; @@ -14,6 +15,9 @@ import { CustomObjectsByEntityRequest } from '@backstage/plugin-kubernetes-commo import { CustomResourceMatcher } from '@backstage/plugin-kubernetes-common'; import { DiscoveryApi } from '@backstage/core-plugin-api'; import { Entity } from '@backstage/catalog-model'; +import { Event as Event_2 } from 'kubernetes-models/v1'; +import { IContainer } from 'kubernetes-models/v1'; +import { IContainerStatus } from 'kubernetes-models/v1'; import { IdentityApi } from '@backstage/core-plugin-api'; import { IObjectMeta } from '@kubernetes-models/apimachinery/apis/meta/v1/ObjectMeta'; import type { JsonObject } from '@backstage/types'; @@ -21,8 +25,8 @@ import { KubernetesRequestBody } from '@backstage/plugin-kubernetes-common'; import { OAuthApi } from '@backstage/core-plugin-api'; import { ObjectsByEntityResponse } from '@backstage/plugin-kubernetes-common'; import { OpenIdConnectApi } from '@backstage/core-plugin-api'; -import { Pod } from 'kubernetes-models/v1'; -import { Pod as Pod_2 } from 'kubernetes-models/v1/Pod'; +import { Pod } from 'kubernetes-models/v1/Pod'; +import { Pod as Pod_2 } from 'kubernetes-models/v1'; import { default as React_2 } from 'react'; import { RouteRef } from '@backstage/core-plugin-api'; import { V1ConfigMap } from '@kubernetes/client-node'; @@ -78,6 +82,25 @@ export interface ClusterLinksFormatterOptions { // @public (undocumented) export const clusterLinksFormatters: Record; +// @public +export const ContainerCard: React_2.FC; + +// @public +export interface ContainerCardProps { + // (undocumented) + containerSpec?: IContainer; + // (undocumented) + containerStatus: IContainerStatus; + // (undocumented) + podScope: PodScope; +} + +// @public +export interface ContainerScope extends PodScope { + // (undocumented) + containerName: string; +} + // Warning: (ae-forgotten-export) The symbol "CronJobsAccordionsProps" needs to be exported by the entry point index.d.ts // Warning: (ae-missing-release-tag) "CronJobsAccordions" is part of the package's API, but it is missing a release tag (@alpha, @beta, @public, or @internal) // @@ -113,7 +136,7 @@ export interface DetectedError { // Warning: (ae-forgotten-export) The symbol "ProposedFix" needs to be exported by the entry point index.d.ts // // (undocumented) - proposedFix: ProposedFix[]; + proposedFix?: ProposedFix; // (undocumented) severity: ErrorSeverity; // Warning: (ae-forgotten-export) The symbol "ResourceRef" needs to be exported by the entry point index.d.ts @@ -144,6 +167,15 @@ export type EntityKubernetesContentProps = { refreshIntervalMs?: number; }; +// @public +export const ErrorList: ({ podAndErrors }: ErrorListProps) => JSX.Element; + +// @public +export interface ErrorListProps { + // (undocumented) + podAndErrors: PodAndErrors[]; +} + // Warning: (ae-forgotten-export) The symbol "ErrorPanelProps" needs to be exported by the entry point index.d.ts // Warning: (ae-missing-release-tag) "ErrorPanel" is part of the package's API, but it is missing a release tag (@alpha, @beta, @public, or @internal) // @@ -165,6 +197,65 @@ export const ErrorReporting: ({ // @public export type ErrorSeverity = 0 | 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10; +// @public +export const Events: ({ + involvedObjectName, + namespace, + clusterName, + warningEventsOnly, +}: EventsProps) => JSX.Element; + +// @public +export const EventsContent: ({ + events, + warningEventsOnly, +}: EventsContentProps) => JSX.Element; + +// @public +export interface EventsContentProps { + // (undocumented) + events: Event_2[]; + // (undocumented) + warningEventsOnly?: boolean; +} + +// @public +export interface EventsOptions { + // (undocumented) + clusterName: string; + // (undocumented) + involvedObjectName: string; + // (undocumented) + namespace: string; +} + +// @public +export interface EventsProps { + // (undocumented) + clusterName: string; + // (undocumented) + involvedObjectName: string; + // (undocumented) + namespace: string; + // (undocumented) + warningEventsOnly?: boolean; +} + +// @public +export const FixDialog: React_2.FC; + +// @public +export interface FixDialogProps { + // (undocumented) + clusterName: string; + // (undocumented) + error: DetectedError; + // (undocumented) + open?: boolean; + // (undocumented) + pod: Pod; +} + // Warning: (ae-forgotten-export) The symbol "FormatClusterLinkOptions" needs to be exported by the entry point index.d.ts // Warning: (ae-missing-release-tag) "formatClusterLink" is part of the package's API, but it is missing a release tag (@alpha, @beta, @public, or @internal) // @@ -416,12 +507,19 @@ export { kubernetesPlugin as plugin }; // // @public (undocumented) export interface KubernetesProxyApi { + // (undocumented) + getEventsByInvolvedObjectName(request: { + clusterName: string; + involvedObjectName: string; + namespace: string; + }): Promise; // (undocumented) getPodLogs(request: { podName: string; namespace: string; clusterName: string; containerName: string; + previous?: boolean; }): Promise<{ text: string; }>; @@ -436,16 +534,28 @@ export const kubernetesProxyApiRef: ApiRef; export class KubernetesProxyClient { constructor(options: { kubernetesApi: KubernetesApi }); // (undocumented) + getEventsByInvolvedObjectName({ + clusterName, + involvedObjectName, + namespace, + }: { + clusterName: string; + involvedObjectName: string; + namespace: string; + }): Promise; + // (undocumented) getPodLogs({ podName, namespace, clusterName, containerName, + previous, }: { podName: string; namespace: string; clusterName: string; containerName: string; + previous?: boolean; }): Promise<{ text: string; }>; @@ -476,12 +586,62 @@ export const LinkErrorPanel: ({ errorMessage, }: ErrorPanelProps_2) => JSX.Element; +// @public +export const PendingPodContent: ({ + pod, +}: PendingPodContentProps) => JSX.Element; + +// @public +export interface PendingPodContentProps { + // (undocumented) + pod: Pod_2; +} + +// @public +export interface PodAndErrors { + // (undocumented) + clusterName: string; + // (undocumented) + errors: DetectedError[]; + // (undocumented) + pod: Pod_2; +} + // Warning: (ae-forgotten-export) The symbol "PodDrawerProps" needs to be exported by the entry point index.d.ts -// Warning: (ae-missing-release-tag) "PodDrawer" is part of the package's API, but it is missing a release tag (@alpha, @beta, @public, or @internal) // -// @public (undocumented) +// @public export const PodDrawer: ({ podAndErrors, open }: PodDrawerProps) => JSX.Element; +// @public +export const PodLogs: React_2.FC; + +// @public +export const PodLogsDialog: ({ + containerScope, +}: PodLogsDialogProps) => JSX.Element; + +// @public +export interface PodLogsDialogProps { + // (undocumented) + containerScope: ContainerScope; +} + +// @public +export interface PodLogsOptions { + // (undocumented) + containerScope: ContainerScope; + // (undocumented) + previous?: boolean; +} + +// @public +export interface PodLogsProps { + // (undocumented) + containerScope: ContainerScope; + // (undocumented) + previous?: boolean; +} + // Warning: (ae-missing-release-tag) "PodNamesWithErrorsContext" is part of the package's API, but it is missing a release tag (@alpha, @beta, @public, or @internal) // // @public (undocumented) @@ -494,6 +654,16 @@ export const PodNamesWithMetricsContext: React_2.Context< Map >; +// @public +export interface PodScope { + // (undocumented) + clusterName: string; + // (undocumented) + podName: string; + // (undocumented) + podNamespace: string; +} + // Warning: (ae-forgotten-export) The symbol "PodsTablesProps" needs to be exported by the entry point index.d.ts // Warning: (ae-missing-release-tag) "PodsTable" is part of the package's API, but it is missing a release tag (@alpha, @beta, @public, or @internal) // @@ -533,6 +703,13 @@ export const useCustomResources: ( intervalMs?: number, ) => KubernetesObjects; +// @public +export const useEvents: ({ + involvedObjectName, + namespace, + clusterName, +}: EventsOptions) => AsyncState; + // Warning: (ae-missing-release-tag) "useKubernetesObjects" is part of the package's API, but it is missing a release tag (@alpha, @beta, @public, or @internal) // // @public (undocumented) @@ -540,4 +717,12 @@ export const useKubernetesObjects: ( entity: Entity, intervalMs?: number, ) => KubernetesObjects; + +// @public +export const usePodLogs: ({ + containerScope, + previous, +}: PodLogsOptions) => AsyncState<{ + text: string; +}>; ``` diff --git a/plugins/kubernetes/src/api/KubernetesProxyClient.test.ts b/plugins/kubernetes/src/api/KubernetesProxyClient.test.ts index 6db1e459be..6b0be6de6c 100644 --- a/plugins/kubernetes/src/api/KubernetesProxyClient.test.ts +++ b/plugins/kubernetes/src/api/KubernetesProxyClient.test.ts @@ -14,11 +14,13 @@ * limitations under the License. */ +import { DateTime } from 'luxon'; import { KubernetesProxyClient } from './KubernetesProxyClient'; describe('KubernetesProxyClient', () => { let proxy: KubernetesProxyClient; const callProxyMock = jest.fn(); + const oneHourAgo = DateTime.now().minus({ hours: 1 }).toISO(); beforeEach(() => { jest.resetAllMocks(); @@ -51,4 +53,72 @@ describe('KubernetesProxyClient', () => { path: '/api/v1/namespaces/some-namespace/pods/some-pod/log?container=some-container', }); }); + it('/logs returns log text - crash logs', async () => { + const request = { + podName: 'some-pod', + namespace: 'some-namespace', + clusterName: 'some-cluster', + containerName: 'some-container', + previous: true, + }; + + callProxyMock.mockResolvedValue({ + text: jest.fn().mockResolvedValue('Hello World'), + ok: true, + }); + + const response = await proxy.getPodLogs(request); + await expect(response).toStrictEqual({ text: 'Hello World' }); + expect(callProxyMock).toHaveBeenCalledWith({ + clusterName: 'some-cluster', + init: { + method: 'GET', + }, + path: '/api/v1/namespaces/some-namespace/pods/some-pod/log?container=some-container&previous=', + }); + }); + it('/getEventsByInvolvedObjectName returns events', async () => { + const request = { + clusterName: 'some-cluster', + involvedObjectName: 'some-object', + namespace: 'some-namespace', + }; + const events = [ + { + type: 'Warning', + message: 'uh oh', + reason: 'something happened', + count: 23, + metadata: { + creationTimestamp: oneHourAgo, + }, + }, + { + type: 'Info', + message: 'hello there', + reason: 'something happened', + count: 52, + metadata: { + creationTimestamp: oneHourAgo, + }, + }, + ]; + + callProxyMock.mockResolvedValue({ + json: jest.fn().mockResolvedValue({ + items: events, + }), + ok: true, + }); + + const response = await proxy.getEventsByInvolvedObjectName(request); + await expect(response).toStrictEqual(events); + expect(callProxyMock).toHaveBeenCalledWith({ + clusterName: 'some-cluster', + init: { + method: 'GET', + }, + path: '/api/v1/namespaces/some-namespace/events?fieldSelector=involvedObject.name=some-object', + }); + }); }); diff --git a/plugins/kubernetes/src/api/KubernetesProxyClient.ts b/plugins/kubernetes/src/api/KubernetesProxyClient.ts index 8fd4674ddd..3703d8b180 100644 --- a/plugins/kubernetes/src/api/KubernetesProxyClient.ts +++ b/plugins/kubernetes/src/api/KubernetesProxyClient.ts @@ -14,6 +14,7 @@ * limitations under the License. */ import { KubernetesApi } from './types'; +import { Event } from 'kubernetes-models/v1'; /** * A client for common requests through the proxy endpoint of the kubernetes backend plugin. @@ -41,20 +42,63 @@ export class KubernetesProxyClient { return await response.text(); } + private async handleJson(response: Response): Promise { + if (!response.ok) { + const payload = await response.text(); + let message = `Request failed with ${response.status} ${response.statusText}, ${payload}`; + switch (response.status) { + case 404: + message = `Proxy request failed with ${response.status} ${response.statusText}, ${payload}`; + break; + default: + message = `Request failed with ${response.status} ${response.statusText}, ${payload}`; + } + throw new Error(message); + } + + return await response.json(); + } + + async getEventsByInvolvedObjectName({ + clusterName, + involvedObjectName, + namespace, + }: { + clusterName: string; + involvedObjectName: string; + namespace: string; + }): Promise { + return await this.kubernetesApi + .proxy({ + clusterName, + path: `/api/v1/namespaces/${namespace}/events?fieldSelector=involvedObject.name=${involvedObjectName}`, + init: { + method: 'GET', + }, + }) + .then(response => this.handleJson(response)) + .then(eventList => eventList.items); + } + async getPodLogs({ podName, namespace, clusterName, containerName, + previous, }: { podName: string; namespace: string; clusterName: string; containerName: string; + previous?: boolean; }): Promise<{ text: string }> { const params = new URLSearchParams({ container: containerName, }); + if (previous) { + params.append('previous', ''); + } return await this.kubernetesApi .proxy({ clusterName: clusterName, diff --git a/plugins/kubernetes/src/api/types.ts b/plugins/kubernetes/src/api/types.ts index 5dec189982..6065e47169 100644 --- a/plugins/kubernetes/src/api/types.ts +++ b/plugins/kubernetes/src/api/types.ts @@ -21,6 +21,7 @@ import { CustomObjectsByEntityRequest, } from '@backstage/plugin-kubernetes-common'; import { createApiRef } from '@backstage/core-plugin-api'; +import { Event } from 'kubernetes-models/v1'; export const kubernetesApiRef = createApiRef({ id: 'plugin.kubernetes.service', @@ -60,5 +61,11 @@ export interface KubernetesProxyApi { namespace: string; clusterName: string; containerName: string; + previous?: boolean; }): Promise<{ text: string }>; + getEventsByInvolvedObjectName(request: { + clusterName: string; + involvedObjectName: string; + namespace: string; + }): Promise; } diff --git a/plugins/kubernetes/src/components/Pods/ErrorList/ErrorList.test.tsx b/plugins/kubernetes/src/components/Pods/ErrorList/ErrorList.test.tsx index f28580b509..3ee755becb 100644 --- a/plugins/kubernetes/src/components/Pods/ErrorList/ErrorList.test.tsx +++ b/plugins/kubernetes/src/components/Pods/ErrorList/ErrorList.test.tsx @@ -45,15 +45,13 @@ describe('ErrorList', () => { kind: 'Pod', apiGroup: 'v1', }, - proposedFix: [ - { - type: 'logs', - container: 'some-container', - errorType: 'some error type', - rootCauseExplanation: 'some root cause', - possibleFixes: ['fix1', 'fix2'], - }, - ], + proposedFix: { + type: 'logs', + container: 'some-container', + errorType: 'some error type', + rootCauseExplanation: 'some root cause', + actions: ['fix1', 'fix2'], + }, }, ], }, diff --git a/plugins/kubernetes/src/components/Pods/ErrorList/ErrorList.tsx b/plugins/kubernetes/src/components/Pods/ErrorList/ErrorList.tsx index b7b3418889..4d1d7a3033 100644 --- a/plugins/kubernetes/src/components/Pods/ErrorList/ErrorList.tsx +++ b/plugins/kubernetes/src/components/Pods/ErrorList/ErrorList.tsx @@ -24,8 +24,10 @@ import { makeStyles, Theme, Paper, + Grid, } from '@material-ui/core'; import { PodAndErrors } from '../types'; +import { FixDialog } from '../FixDialog/FixDialog'; const useStyles = makeStyles((_theme: Theme) => createStyles({ @@ -38,10 +40,20 @@ const useStyles = makeStyles((_theme: Theme) => }), ); -interface ErrorListProps { +/** + * Props for ErrorList + * + * @public + */ +export interface ErrorListProps { podAndErrors: PodAndErrors[]; } +/** + * Shows a list of errors found on a Pod + * + * @public + */ export const ErrorList = ({ podAndErrors }: ErrorListProps) => { const classes = useStyles(); return ( @@ -59,10 +71,21 @@ export const ErrorList = ({ podAndErrors }: ErrorListProps) => { > {i > 0 && } - + + + + + + + + ); diff --git a/plugins/kubernetes/src/components/Pods/Events/Events.test.tsx b/plugins/kubernetes/src/components/Pods/Events/Events.test.tsx new file mode 100644 index 0000000000..8323666e66 --- /dev/null +++ b/plugins/kubernetes/src/components/Pods/Events/Events.test.tsx @@ -0,0 +1,96 @@ +/* + * Copyright 2023 The Backstage Authors + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ +import React from 'react'; +import { EventsContent } from './Events'; +import { render } from '@testing-library/react'; +import { Event } from 'kubernetes-models/v1'; +import { DateTime } from 'luxon'; + +describe('EventsContent', () => { + const oneHourAgo = DateTime.now().minus({ hours: 1 }).toISO(); + it('should show info events', () => { + const { getByText } = render( + , + ); + expect(getByText('First event 1 hour ago (count: 52)')).toBeInTheDocument(); + expect(getByText('something happened: hello there')).toBeInTheDocument(); + }); + it('should show warning events', () => { + const { getByText } = render( + , + ); + expect(getByText('First event 1 hour ago (count: 23)')).toBeInTheDocument(); + expect(getByText('something happened: uh oh')).toBeInTheDocument(); + }); + + it('should only show warning events when warningEventsOnly set', () => { + const { getByText, queryByText } = render( + , + ); + expect(queryByText('First event 1 hour ago (count: 52)')).toBeNull(); + expect(queryByText('something happened: hello there')).toBeNull(); + expect(getByText('First event 1 hour ago (count: 23)')).toBeInTheDocument(); + expect(getByText('something happened: uh oh')).toBeInTheDocument(); + }); +}); diff --git a/plugins/kubernetes/src/components/Pods/Events/Events.tsx b/plugins/kubernetes/src/components/Pods/Events/Events.tsx new file mode 100644 index 0000000000..9f888d182c --- /dev/null +++ b/plugins/kubernetes/src/components/Pods/Events/Events.tsx @@ -0,0 +1,154 @@ +/* + * Copyright 2023 The Backstage Authors + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ +import React from 'react'; + +import { + Avatar, + Container, + Grid, + List, + ListItem, + ListItemAvatar, + ListItemText, + Tooltip, + Typography, +} from '@material-ui/core'; + +import InfoIcon from '@material-ui/icons/Info'; +import WarningIcon from '@material-ui/icons/Warning'; +import { DateTime } from 'luxon'; + +import { useEvents } from './useEvents'; +import { Skeleton } from '@material-ui/lab'; +import { DismissableBanner } from '@backstage/core-components'; +import { Event } from 'kubernetes-models/v1'; + +/** + * Props for Events + * + * @public + */ +export interface EventsContentProps { + warningEventsOnly?: boolean; + events: Event[]; +} + +const getAvatarByType = (type?: string) => { + return ( + + {type === 'Warning' ? : } + + ); +}; + +/** + * Shows given Kubernetes events + * + * @public + */ +export const EventsContent = ({ + events, + warningEventsOnly, +}: EventsContentProps) => { + if (events.length === 0) { + return No events found; + } + + return ( + + + + {events + .filter(event => { + if (warningEventsOnly) { + return event.type === 'Warning'; + } + return true; + }) + .map(event => { + const timeAgo = event.metadata.creationTimestamp + ? DateTime.fromISO(event.metadata.creationTimestamp).toRelative( + { + locale: 'en', + }, + ) + : 'unknown'; + return ( + + + {getAvatarByType(event.type)} + + + + ); + })} + + + + ); +}; + +/** + * Props for Events + * + * @public + */ +export interface EventsProps { + involvedObjectName: string; + namespace: string; + clusterName: string; + warningEventsOnly?: boolean; +} + +/** + * Retrieves and shows Kubernetes events for the given object + * + * @public + */ +export const Events = ({ + involvedObjectName, + namespace, + clusterName, + warningEventsOnly, +}: EventsProps) => { + const { value, error, loading } = useEvents({ + involvedObjectName, + namespace, + clusterName, + }); + + return ( + <> + {error && ( + + )} + {loading && } + {!loading && value !== undefined && ( + + )} + + ); +}; diff --git a/plugins/kubernetes/src/components/Pods/Events/index.ts b/plugins/kubernetes/src/components/Pods/Events/index.ts new file mode 100644 index 0000000000..da6c4102fa --- /dev/null +++ b/plugins/kubernetes/src/components/Pods/Events/index.ts @@ -0,0 +1,17 @@ +/* + * Copyright 2023 The Backstage Authors + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ +export * from './Events'; +export * from './useEvents'; diff --git a/plugins/kubernetes/src/components/Pods/Events/useEvents.test.tsx b/plugins/kubernetes/src/components/Pods/Events/useEvents.test.tsx new file mode 100644 index 0000000000..15da221f64 --- /dev/null +++ b/plugins/kubernetes/src/components/Pods/Events/useEvents.test.tsx @@ -0,0 +1,68 @@ +/* + * Copyright 2023 The Backstage Authors + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ +import { useApi } from '@backstage/core-plugin-api'; +import { renderHook } from '@testing-library/react-hooks'; +import { useEvents } from './useEvents'; +import { DateTime } from 'luxon'; + +jest.mock('@backstage/core-plugin-api'); + +jest.mock('@backstage/plugin-kubernetes', () => ({ + kubernetesProxyApiRef: () => jest.fn(), +})); + +const oneHourAgo = DateTime.now().minus({ hours: 1 }).toISO(); + +const response = [ + { + type: 'Info', + message: 'hello there', + reason: 'something happened', + count: 52, + metadata: { + creationTimestamp: oneHourAgo, + }, + }, +] as any; + +describe('Events', () => { + const mockGetEventsByInvolvedObjectName = jest.fn(); + afterEach(() => { + jest.resetAllMocks(); + }); + it('should fetch and show events', async () => { + (useApi as any).mockReturnValue({ + getEventsByInvolvedObjectName: + mockGetEventsByInvolvedObjectName.mockResolvedValue(response), + }); + + const { result, waitForNextUpdate } = renderHook(() => + useEvents({ + involvedObjectName: 'some-objecgt', + namespace: 'some-namespace', + clusterName: 'some-cluster', + }), + ); + + expect(result.current.loading).toEqual(true); + + await waitForNextUpdate(); + + expect(result.current.error).toBeUndefined(); + expect(result.current.loading).toEqual(false); + expect(result.current.value).toStrictEqual(response); + }); +}); diff --git a/plugins/kubernetes/src/components/Pods/Events/useEvents.ts b/plugins/kubernetes/src/components/Pods/Events/useEvents.ts new file mode 100644 index 0000000000..441937507d --- /dev/null +++ b/plugins/kubernetes/src/components/Pods/Events/useEvents.ts @@ -0,0 +1,49 @@ +/* + * Copyright 2023 The Backstage Authors + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ +import { useApi } from '@backstage/core-plugin-api'; +import useAsync from 'react-use/lib/useAsync'; +import { kubernetesProxyApiRef } from '../../../api'; + +/** + * Arguments for useEvents + * + * @public + */ +export interface EventsOptions { + involvedObjectName: string; + namespace: string; + clusterName: string; +} + +/** + * Retrieves the events for the given object + * + * @public + */ +export const useEvents = ({ + involvedObjectName, + namespace, + clusterName, +}: EventsOptions) => { + const kubernetesProxyApi = useApi(kubernetesProxyApiRef); + return useAsync(async () => { + return await kubernetesProxyApi.getEventsByInvolvedObjectName({ + involvedObjectName, + namespace, + clusterName, + }); + }, [involvedObjectName, namespace, clusterName]); +}; diff --git a/plugins/kubernetes/src/components/Pods/FixDialog/FixDialog.test.tsx b/plugins/kubernetes/src/components/Pods/FixDialog/FixDialog.test.tsx new file mode 100644 index 0000000000..e779ab5f0d --- /dev/null +++ b/plugins/kubernetes/src/components/Pods/FixDialog/FixDialog.test.tsx @@ -0,0 +1,159 @@ +/* + * Copyright 2023 The Backstage Authors + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ +import React from 'react'; + +import { render } from '@testing-library/react'; + +import { FixDialog } from './FixDialog'; +import { Pod } from 'kubernetes-models/v1/Pod'; + +jest.mock('../Events', () => ({ + Events: () => { + return ; + }, +})); + +jest.mock('../PodLogs', () => ({ + PodLogs: () => { + return ; + }, +})); + +describe('FixDialog', () => { + it('docs link should render', () => { + const { getByText } = render( + , + ); + expect(getByText('Open docs')).toBeInTheDocument(); + expect(getByText('some error message')).toBeInTheDocument(); + expect(getByText('some-pod - some error type')).toBeInTheDocument(); + expect(getByText('some root cause')).toBeInTheDocument(); + expect(getByText('fix1')).toBeInTheDocument(); + expect(getByText('fix2')).toBeInTheDocument(); + }); + it('events button should render', () => { + const { getByText } = render( + , + ); + expect(getByText('Events:')).toBeInTheDocument(); + expect(getByText('some error message')).toBeInTheDocument(); + expect(getByText('some-pod - some error type')).toBeInTheDocument(); + expect(getByText('some root cause')).toBeInTheDocument(); + expect(getByText('fix1')).toBeInTheDocument(); + expect(getByText('fix2')).toBeInTheDocument(); + }); + it('Logs button should render', () => { + const { getByText } = render( + , + ); + expect(getByText('Crash logs:')).toBeInTheDocument(); + expect(getByText('some error message')).toBeInTheDocument(); + expect(getByText('some-pod - some error type')).toBeInTheDocument(); + expect(getByText('some root cause')).toBeInTheDocument(); + expect(getByText('fix1')).toBeInTheDocument(); + expect(getByText('fix2')).toBeInTheDocument(); + }); +}); diff --git a/plugins/kubernetes/src/components/Pods/FixDialog/FixDialog.tsx b/plugins/kubernetes/src/components/Pods/FixDialog/FixDialog.tsx new file mode 100644 index 0000000000..63ce4af03b --- /dev/null +++ b/plugins/kubernetes/src/components/Pods/FixDialog/FixDialog.tsx @@ -0,0 +1,187 @@ +/* + * Copyright 2023 The Backstage Authors + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ +import React, { useState } from 'react'; + +import { Button, Grid } from '@material-ui/core'; +import Dialog from '@material-ui/core/Dialog'; +import DialogActions from '@material-ui/core/DialogActions'; +import DialogContent from '@material-ui/core/DialogContent'; +import DialogTitle from '@material-ui/core/DialogTitle'; +import IconButton from '@material-ui/core/IconButton'; +import { makeStyles, createStyles, Theme } from '@material-ui/core/styles'; +import Typography from '@material-ui/core/Typography'; +import CloseIcon from '@material-ui/icons/Close'; +import HelpIcon from '@material-ui/icons/Help'; +import OpenInNewIcon from '@material-ui/icons/OpenInNew'; + +import { Pod } from 'kubernetes-models/v1/Pod'; +import { DetectedError } from '../../../error-detection'; +import { PodLogs } from '../PodLogs'; +import { Events } from '../Events'; +import { LinkButton } from '@backstage/core-components'; + +const useStyles = makeStyles((theme: Theme) => + createStyles({ + closeButton: { + position: 'absolute', + right: theme.spacing(1), + top: theme.spacing(1), + color: theme.palette.grey[500], + }, + }), +); + +/** + * Props for FixDialog + * + * @public + */ +export interface FixDialogProps { + open?: boolean; + clusterName: string; + pod: Pod; + error: DetectedError; +} + +/** + * A dialog for fixing detected Kubernetes errors + * + * @public + */ +export const FixDialog: React.FC = ({ + open, + pod, + error, + clusterName, +}: FixDialogProps) => { + const [isOpen, setOpen] = useState(!!open); + const classes = useStyles(); + + const openDialog = () => { + setOpen(true); + }; + + const closeDialog = () => { + setOpen(false); + }; + + const pf = error.proposedFix; + + const dialogContent = () => { + return ( + + + Detected error: + {error.message} + + + Cause explanation: + + {error.proposedFix?.rootCauseExplanation ?? 'unknown'} + + + + Fix: + +
    + {(error.proposedFix?.actions ?? []).map((fix, i) => { + return ( +
  • + {fix} +
  • + ); + })} +
+
+
+ + {pf && pf.type === 'logs' && ( + <> + + Crash logs: + + + + + + )} + {pf && pf.type === 'events' && ( + <> + + Events: + + + + + + )} +
+ ); + }; + + return ( + <> + + + + {pod.metadata?.name} - {error.type} + + + + + {dialogContent()} + + {pf && pf.type === 'docs' && ( + } + target="_blank" + rel="noopener" + > + Open docs + + )} + + + + ); +}; diff --git a/plugins/kubernetes/src/components/Pods/FixDialog/index.ts b/plugins/kubernetes/src/components/Pods/FixDialog/index.ts new file mode 100644 index 0000000000..35601f9bd6 --- /dev/null +++ b/plugins/kubernetes/src/components/Pods/FixDialog/index.ts @@ -0,0 +1,16 @@ +/* + * Copyright 2023 The Backstage Authors + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ +export * from './FixDialog'; diff --git a/plugins/kubernetes/src/components/Pods/PodDrawer/ContainerCard.tsx b/plugins/kubernetes/src/components/Pods/PodDrawer/ContainerCard.tsx index eac64ae741..970982d7a3 100644 --- a/plugins/kubernetes/src/components/Pods/PodDrawer/ContainerCard.tsx +++ b/plugins/kubernetes/src/components/Pods/PodDrawer/ContainerCard.tsx @@ -83,12 +83,22 @@ const ContainerDatetime = ({ prefix, dateTime }: ContainerDatetimeProps) => { ); }; +/** + * Props for ContainerCard + * + * @public + */ export interface ContainerCardProps { podScope: PodScope; containerSpec?: IContainer; containerStatus: IContainerStatus; } +/** + * Shows details about a container within a pod + * + * @public + */ export const ContainerCard: React.FC = ({ podScope, containerSpec, @@ -162,7 +172,7 @@ export const ContainerCard: React.FC = ({ { +const PodCondition = ({ condition }: PodConditionProps) => { return ( <> {condition.status === 'False' && ( @@ -64,10 +64,20 @@ export const PodCondition = ({ condition }: PodConditionProps) => { ); }; -interface PendingPodContentProps { +/** + * Props for PendingPodContent + * + * @public + */ +export interface PendingPodContentProps { pod: Pod; } +/** + * Shows details about pod's conditions as it starts + * + * @public + */ export const PendingPodContent = ({ pod }: PendingPodContentProps) => { // TODO add PodHasNetwork when it's out of alpha // https://kubernetes.io/docs/concepts/workloads/pods/pod-lifecycle/#pod-conditions diff --git a/plugins/kubernetes/src/components/Pods/PodDrawer/PodDrawer.test.tsx b/plugins/kubernetes/src/components/Pods/PodDrawer/PodDrawer.test.tsx index 64fd38c8d7..2b71976d8a 100644 --- a/plugins/kubernetes/src/components/Pods/PodDrawer/PodDrawer.test.tsx +++ b/plugins/kubernetes/src/components/Pods/PodDrawer/PodDrawer.test.tsx @@ -69,7 +69,7 @@ describe('PodDrawer', () => { container: 'some-container', errorType: 'some error type', rootCauseExplanation: 'some root cause', - possibleFixes: ['fix1', 'fix2'], + actions: ['fix1', 'fix2'], }, ], }, diff --git a/plugins/kubernetes/src/components/Pods/PodDrawer/PodDrawer.tsx b/plugins/kubernetes/src/components/Pods/PodDrawer/PodDrawer.tsx index 5e49410dd4..8e616df14e 100644 --- a/plugins/kubernetes/src/components/Pods/PodDrawer/PodDrawer.tsx +++ b/plugins/kubernetes/src/components/Pods/PodDrawer/PodDrawer.tsx @@ -58,11 +58,22 @@ const useDrawerContentStyles = makeStyles((_theme: Theme) => function getContainerSpecByName(pod: Pod, containerName: string) { return pod.spec?.containers.find(c => c.name === containerName); } + +/** + * Props for PodDrawer + * + * @public + */ interface PodDrawerProps { open?: boolean; podAndErrors: PodAndErrors; } +/** + * A Drawer for Kubernetes Pods + * + * @public + */ export const PodDrawer = ({ podAndErrors, open }: PodDrawerProps) => { const classes = useDrawerContentStyles(); diff --git a/plugins/kubernetes/src/components/Pods/PodDrawer/index.ts b/plugins/kubernetes/src/components/Pods/PodDrawer/index.ts index 17d50ddfcd..92bb254c48 100644 --- a/plugins/kubernetes/src/components/Pods/PodDrawer/index.ts +++ b/plugins/kubernetes/src/components/Pods/PodDrawer/index.ts @@ -13,4 +13,6 @@ * See the License for the specific language governing permissions and * limitations under the License. */ -export { PodDrawer } from './PodDrawer'; +export * from './PodDrawer'; +export * from './ContainerCard'; +export * from './PendingPodContent'; diff --git a/plugins/kubernetes/src/components/Pods/PodLogs/PodLogs.tsx b/plugins/kubernetes/src/components/Pods/PodLogs/PodLogs.tsx index 5cff023772..de9341508e 100644 --- a/plugins/kubernetes/src/components/Pods/PodLogs/PodLogs.tsx +++ b/plugins/kubernetes/src/components/Pods/PodLogs/PodLogs.tsx @@ -15,20 +15,39 @@ */ import React from 'react'; -import { DismissableBanner, LogViewer } from '@backstage/core-components'; +import { + DismissableBanner, + EmptyState, + LogViewer, +} from '@backstage/core-components'; import { Paper } from '@material-ui/core'; import { Skeleton } from '@material-ui/lab'; import { ContainerScope } from './types'; import { usePodLogs } from './usePodLogs'; -interface PodLogsProps { - podScope: ContainerScope; +/** + * Props for PodLogs + * + * @public + */ +export interface PodLogsProps { + containerScope: ContainerScope; + previous?: boolean; } -export const PodLogs: React.FC = ({ podScope }: PodLogsProps) => { +/** + * Shows the logs for the given pod + * + * @public + */ +export const PodLogs: React.FC = ({ + containerScope, + previous, +}: PodLogsProps) => { const { value, error, loading } = usePodLogs({ - podScope: podScope, + containerScope, + previous, }); return ( @@ -45,10 +64,20 @@ export const PodLogs: React.FC = ({ podScope }: PodLogsProps) => { )} {loading && } - {!loading && value !== undefined && } + {!loading && + value !== undefined && + (value.text === '' ? ( + + ) : ( + + ))} ); diff --git a/plugins/kubernetes/src/components/Pods/PodLogs/PodLogsDialog.tsx b/plugins/kubernetes/src/components/Pods/PodLogs/PodLogsDialog.tsx index 05d980b26a..48fda2de2a 100644 --- a/plugins/kubernetes/src/components/Pods/PodLogs/PodLogsDialog.tsx +++ b/plugins/kubernetes/src/components/Pods/PodLogs/PodLogsDialog.tsx @@ -43,11 +43,21 @@ const useStyles = makeStyles((theme: Theme) => }), ); -interface PodLogsDialogProps { - podScope: ContainerScope; +/** + * Props for PodLogsDialog + * + * @public + */ +export interface PodLogsDialogProps { + containerScope: ContainerScope; } -export const PodLogsDialog = ({ podScope }: PodLogsDialogProps) => { +/** + * Shows the logs for the given pod in a Dialog + * + * @public + */ +export const PodLogsDialog = ({ containerScope }: PodLogsDialogProps) => { const classes = useStyles(); const [open, setOpen] = useState(false); @@ -62,8 +72,8 @@ export const PodLogsDialog = ({ podScope }: PodLogsDialogProps) => { <> - {podScope.podName} - {podScope.containerName} logs on cluster{' '} - {podScope.clusterName} + {containerScope.podName} - {containerScope.containerName} logs on + cluster {containerScope.clusterName} { - +