From 583c7ad5f2df4d3cafd9d1a0a7d816268c3652e6 Mon Sep 17 00:00:00 2001 From: Oliver Date: Sat, 9 May 2026 12:44:05 +1000 Subject: [PATCH] [UI] Optimize bundle (#11896) * lazy load global window modules - Required for plugins - Can be separated from the "main.tsx" code Co-authored-by: Copilot * Defer modal loading Co-authored-by: Copilot * Rollup visualiser tool * Remove debug msg * Rearrange to reduce deltas * Refactor CodeEditor and PdfPreview * Split NotesPanel Co-authored-by: Copilot --------- Co-authored-by: Copilot --- src/frontend/.gitignore | 3 + src/frontend/package.json | 1 + .../TemplateEditor/CodeEditor/index.tsx | 8 +- .../TemplateEditor/PdfPreview/index.tsx | 8 +- .../src/components/panels/NotesPanel.tsx | 4 +- src/frontend/src/contexts/ThemeContext.tsx | 28 ++- src/frontend/src/main.tsx | 35 ++-- .../AdminCenter/ReportTemplatePanel.tsx | 8 +- src/frontend/src/window.tsx | 38 ++++ src/frontend/vite.config.ts | 2 + src/frontend/yarn.lock | 171 +++++++++++++++++- 11 files changed, 275 insertions(+), 31 deletions(-) create mode 100644 src/frontend/src/window.tsx diff --git a/src/frontend/.gitignore b/src/frontend/.gitignore index a58463aed3..5d9699d78c 100644 --- a/src/frontend/.gitignore +++ b/src/frontend/.gitignore @@ -29,3 +29,6 @@ dist-ssr /playwright/.cache/ /.nyc_output/ /coverage/ + +# Report generation +stats.html diff --git a/src/frontend/package.json b/src/frontend/package.json index 132cd11437..f8d778469c 100644 --- a/src/frontend/package.json +++ b/src/frontend/package.json @@ -131,6 +131,7 @@ "path": "^0.12.7", "rollup": "^4.59.0", "rollup-plugin-license": "^3.7.0", + "rollup-plugin-visualizer": "^7.0.1", "typescript": "^5.9.3", "vite": "^6.4.2", "vite-plugin-babel-macros": "^1.0.6", diff --git a/src/frontend/src/components/editors/TemplateEditor/CodeEditor/index.tsx b/src/frontend/src/components/editors/TemplateEditor/CodeEditor/index.tsx index 6827fb3685..5cdaba454e 100644 --- a/src/frontend/src/components/editors/TemplateEditor/CodeEditor/index.tsx +++ b/src/frontend/src/components/editors/TemplateEditor/CodeEditor/index.tsx @@ -1,8 +1,14 @@ import { t } from '@lingui/core/macro'; import { IconCode } from '@tabler/icons-react'; +import { lazy } from 'react'; import type { Editor } from '../TemplateEditor'; -import { CodeEditorComponent } from './CodeEditor'; + +const CodeEditorComponent = lazy(() => + import('./CodeEditor').then((module) => ({ + default: module.CodeEditorComponent + })) +); export const CodeEditor: Editor = { key: 'code', diff --git a/src/frontend/src/components/editors/TemplateEditor/PdfPreview/index.tsx b/src/frontend/src/components/editors/TemplateEditor/PdfPreview/index.tsx index 991f507ad4..3dbaab5a88 100644 --- a/src/frontend/src/components/editors/TemplateEditor/PdfPreview/index.tsx +++ b/src/frontend/src/components/editors/TemplateEditor/PdfPreview/index.tsx @@ -1,8 +1,14 @@ import { t } from '@lingui/core/macro'; import { IconFileTypePdf } from '@tabler/icons-react'; +import { lazy } from 'react'; import type { PreviewArea } from '../TemplateEditor'; -import { PdfPreviewComponent } from './PdfPreview'; + +const PdfPreviewComponent = lazy(() => + import('./PdfPreview').then((module) => ({ + default: module.PdfPreviewComponent + })) +); export const PdfPreview: PreviewArea = { key: 'pdf-preview', diff --git a/src/frontend/src/components/panels/NotesPanel.tsx b/src/frontend/src/components/panels/NotesPanel.tsx index 3de9d6f011..6bee76d2b4 100644 --- a/src/frontend/src/components/panels/NotesPanel.tsx +++ b/src/frontend/src/components/panels/NotesPanel.tsx @@ -3,10 +3,12 @@ import { Skeleton } from '@mantine/core'; import { IconNotes } from '@tabler/icons-react'; import type { ModelType } from '@lib/enums/ModelType'; +import { lazy } from 'react'; import { useUserState } from '../../states/UserState'; -import NotesEditor from '../editors/NotesEditor'; import type { PanelType } from './Panel'; +const NotesEditor = lazy(() => import('../editors/NotesEditor')); + export default function NotesPanel({ model_type, model_id, diff --git a/src/frontend/src/contexts/ThemeContext.tsx b/src/frontend/src/contexts/ThemeContext.tsx index 0bd1e0a589..a74cf752f0 100644 --- a/src/frontend/src/contexts/ThemeContext.tsx +++ b/src/frontend/src/contexts/ThemeContext.tsx @@ -9,15 +9,33 @@ import { ModalsProvider } from '@mantine/modals'; import { Notifications } from '@mantine/notifications'; import { ContextMenuProvider } from 'mantine-contextmenu'; import { useShallow } from 'zustand/react/shallow'; -import { AboutInvenTreeModal } from '../components/modals/AboutInvenTreeModal'; -import { LicenseModal } from '../components/modals/LicenseModal'; -import { QrModal } from '../components/modals/QrModal'; -import { ServerInfoModal } from '../components/modals/ServerInfoModal'; import { useLocalState } from '../states/LocalState'; import { LanguageContext } from './LanguageContext'; import { colorSchema } from './colorSchema'; -import type { JSX } from 'react'; +// Lazy load the various modal dialogs - they are not needed immediately, and this can help to reduce the initial bundle size +const AboutInvenTreeModal = lazy(() => + import('../components/modals/AboutInvenTreeModal').then((module) => ({ + default: module.AboutInvenTreeModal + })) +); +const LicenseModal = lazy(() => + import('../components/modals/LicenseModal').then((module) => ({ + default: module.LicenseModal + })) +); +const QrModal = lazy(() => + import('../components/modals/QrModal').then((module) => ({ + default: module.QrModal + })) +); +const ServerInfoModal = lazy(() => + import('../components/modals/ServerInfoModal').then((module) => ({ + default: module.ServerInfoModal + })) +); + +import { type JSX, lazy } from 'react'; export function ThemeContext({ children diff --git a/src/frontend/src/main.tsx b/src/frontend/src/main.tsx index d5fc90bd52..14ade14584 100644 --- a/src/frontend/src/main.tsx +++ b/src/frontend/src/main.tsx @@ -9,20 +9,22 @@ import 'mantine-contextmenu/styles.css'; import 'mantine-datatable/styles.css'; import 'react-grid-layout/css/styles.css'; import 'react-resizable/css/styles.css'; -import * as MantineCore from '@mantine/core'; -import * as MantineNotifications from '@mantine/notifications'; -import * as React from 'react'; -import * as ReactDOM from 'react-dom'; -import * as ReactDOMClient from 'react-dom/client'; -import './styles/overrides.css'; -// Lingui imports (required for plugin translation) -import * as LinguiCore from '@lingui/core'; -import * as LinguiReact from '@lingui/react'; +import type * as LinguiCore from '@lingui/core'; +import type * as LinguiReact from '@lingui/react'; +// Global types to be exported for use in plugins +import type * as MantineCore from '@mantine/core'; +import type * as MantineNotifications from '@mantine/notifications'; +import * as React from 'react'; +import type * as ReactDOM from 'react-dom'; +import * as ReactDOMClient from 'react-dom/client'; + +import './styles/overrides.css'; import { getBaseUrl } from '@lib/functions/Navigation'; import type { HostList } from '@lib/types/Server'; import MainView from './views/MainView'; +import { loadWindowGlobals } from './window'; // define settings declare global { @@ -43,6 +45,8 @@ declare global { ReactDOMClient: typeof ReactDOMClient; MantineCore: typeof MantineCore; MantineNotifications: typeof MantineNotifications; + LinguiCore: typeof LinguiCore; + LinguiReact: typeof LinguiReact; } } @@ -106,16 +110,6 @@ if (window.INVENTREE_SETTINGS.sentry_dsn) { environment: window.INVENTREE_SETTINGS.environment || 'default' }); } - -// Expose global objects for the plugin system -(window as any).React = React; -(window as any).ReactDOM = ReactDOM; -(window as any).ReactDOMClient = ReactDOMClient; -(window as any).MantineCore = MantineCore; -(window as any).MantineNotifications = MantineNotifications; -(window as any).LinguiCore = LinguiCore; -(window as any).LinguiReact = LinguiReact; - // Redirect to base url if on / if (window.location.pathname === '/') { window.location.replace(`/${getBaseUrl()}`); @@ -128,3 +122,6 @@ ReactDOMClient.createRoot( ); + +// Load globals onto the window object, so that they can be accessed by plugins without requiring direct imports +loadWindowGlobals(); diff --git a/src/frontend/src/pages/Index/Settings/AdminCenter/ReportTemplatePanel.tsx b/src/frontend/src/pages/Index/Settings/AdminCenter/ReportTemplatePanel.tsx index fb6a7222c6..8113064f70 100644 --- a/src/frontend/src/pages/Index/Settings/AdminCenter/ReportTemplatePanel.tsx +++ b/src/frontend/src/pages/Index/Settings/AdminCenter/ReportTemplatePanel.tsx @@ -2,7 +2,13 @@ import { YesNoButton } from '@lib/components/YesNoButton'; import { ApiEndpoints } from '@lib/enums/ApiEndpoints'; import { ModelType } from '@lib/enums/ModelType'; import { t } from '@lingui/core/macro'; -import { TemplateTable } from '../../../../tables/settings/TemplateTable'; +import { lazy } from 'react'; + +const TemplateTable = lazy(() => + import('../../../../tables/settings/TemplateTable').then((module) => ({ + default: module.TemplateTable + })) +); function ReportTemplateTable() { return ( diff --git a/src/frontend/src/window.tsx b/src/frontend/src/window.tsx new file mode 100644 index 0000000000..a6f3d19f3f --- /dev/null +++ b/src/frontend/src/window.tsx @@ -0,0 +1,38 @@ +/** + * Expose certain globals to the window object, so that they can be accessed by plugins, + * without requiring plugins to import these dependencies directly. + */ +export function loadWindowGlobals() { + // (window as any).React = React; + import('react').then((module) => { + window.React = module; + }); + + // (window as any).ReactDOM = ReactDOM; + import('react-dom').then((module) => { + window.ReactDOM = module; + }); + + // (window as any).ReactDOMClient = ReactDOMClient; + import('react-dom/client').then((module) => { + window.ReactDOMClient = module; + }); + + // (window as any).MantineCore = MantineCore; + import('@mantine/core').then((module) => { + window.MantineCore = module; + }); + + // (window as any).MantineNotifications = MantineNotifications; + import('@mantine/notifications').then((module) => { + window.MantineNotifications = module; + }); + + import('@lingui/core').then((module) => { + window.LinguiCore = module; + }); + + import('@lingui/react').then((module) => { + window.LinguiReact = module; + }); +} diff --git a/src/frontend/vite.config.ts b/src/frontend/vite.config.ts index 627a1ade6e..3f239c92fd 100644 --- a/src/frontend/vite.config.ts +++ b/src/frontend/vite.config.ts @@ -3,6 +3,7 @@ import { codecovVitePlugin } from '@codecov/vite-plugin'; import { vanillaExtractPlugin } from '@vanilla-extract/vite-plugin'; import react from '@vitejs/plugin-react'; import license from 'rollup-plugin-license'; +import { visualizer } from 'rollup-plugin-visualizer'; import { defineConfig } from 'vite'; import istanbul from 'vite-plugin-istanbul'; @@ -26,6 +27,7 @@ export default defineConfig(({ command, mode }) => { return { plugins: [ + visualizer(), react({ babel: { plugins: ['macros'] diff --git a/src/frontend/yarn.lock b/src/frontend/yarn.lock index 4596ca15f4..b91348b77b 100644 --- a/src/frontend/yarn.lock +++ b/src/frontend/yarn.lock @@ -2305,6 +2305,11 @@ ansi-regex@^5.0.1: resolved "https://registry.yarnpkg.com/ansi-regex/-/ansi-regex-5.0.1.tgz#082cb2c89c9fe8659a311a53bd6a4dc5301db304" integrity sha512-quJQXlTSUGL2LH9SUXo8VwsY4soanhgo6LNSm84E1LBcE8s3O0wpdiRzyR9z/ZZJMlMWv37qOOb9pdJlMUEKFQ== +ansi-regex@^6.2.2: + version "6.2.2" + resolved "https://registry.yarnpkg.com/ansi-regex/-/ansi-regex-6.2.2.tgz#60216eea464d864597ce2832000738a0589650c1" + integrity sha512-Bq3SmSpyFHaWjPk8If9yc6svM8c56dB5BAtW4Qbw5jHTwwXXcTLoRMkpDJp6VL0XzlWaCHTXrkFURMYmD0sLqg== + ansi-styles@^4.0.0, ansi-styles@^4.1.0: version "4.3.0" resolved "https://registry.yarnpkg.com/ansi-styles/-/ansi-styles-4.3.0.tgz#edd803628ae71c04c85ae7a0906edad34b648937" @@ -2317,6 +2322,11 @@ ansi-styles@^5.0.0: resolved "https://registry.yarnpkg.com/ansi-styles/-/ansi-styles-5.2.0.tgz#07449690ad45777d1924ac2abb2fc8895dba836b" integrity sha512-Cxwpt2SfTzTtXcfOlzGEee8O+c+MmUgGrNiBcXnuWxuFJHe6a5Hz7qwhwe5OgaSYI0IJvkLqWX1ASG+cJOkEiA== +ansi-styles@^6.2.1: + version "6.2.3" + resolved "https://registry.yarnpkg.com/ansi-styles/-/ansi-styles-6.2.3.tgz#c044d5dcc521a076413472597a1acb1f103c4041" + integrity sha512-4Dj6M28JB+oAH8kFkTLUo+a2jwOFkuqb3yucU0CANcRRUbxS0cP0nZYCGjcc3BNXwRIsUVmDGgzawme7zvJHvg== + anymatch@~3.1.1: version "3.1.3" resolved "https://registry.yarnpkg.com/anymatch/-/anymatch-3.1.3.tgz#790c58b19ba1720a84205b57c618d5ad8524973e" @@ -2461,6 +2471,13 @@ buffer@^5.5.0: base64-js "^1.3.1" ieee754 "^1.1.13" +bundle-name@^4.1.0: + version "4.1.0" + resolved "https://registry.yarnpkg.com/bundle-name/-/bundle-name-4.1.0.tgz#f3b96b34160d6431a19d7688135af7cfb8797889" + integrity sha512-tjwM5exMg6BGRI+kNmTntNsvdZS1X8BFYS6tnJ2hdH0kVxM6/eVZ2xy+FqStSWvYmtfFMDLIxurorHwDKfDz5Q== + dependencies: + run-applescript "^7.0.0" + cac@^7.0.0: version "7.0.0" resolved "https://registry.yarnpkg.com/cac/-/cac-7.0.0.tgz#7dda83da2268f75f840ab89ac3bcc36c120a78da" @@ -2565,6 +2582,15 @@ cliui@^6.0.0: strip-ansi "^6.0.0" wrap-ansi "^6.2.0" +cliui@^9.0.1: + version "9.0.1" + resolved "https://registry.yarnpkg.com/cliui/-/cliui-9.0.1.tgz#6f7890f386f6f1f79953adc1f78dec46fcc2d291" + integrity sha512-k7ndgKhwoQveBL+/1tqGJYNz097I7WOvwbmmU2AR5+magtbjPWQTS1C5vzGkBC8Ym8UWRzfKUzUUqFLypY4Q+w== + dependencies: + string-width "^7.2.0" + strip-ansi "^7.1.0" + wrap-ansi "^9.0.0" + clone@^1.0.2: version "1.0.4" resolved "https://registry.yarnpkg.com/clone/-/clone-1.0.4.tgz#da309cc263df15994c688ca902179ca3c7cd7c7e" @@ -2846,6 +2872,19 @@ deepmerge@^4.2.2: resolved "https://registry.yarnpkg.com/deepmerge/-/deepmerge-4.3.1.tgz#44b5f2147cd3b00d4b56137685966f26fd25dd4a" integrity sha512-3sUqbMEc77XqpdNO7FRyRog+eW3ph+GYCbj+rK+uYyRMuwsVy0rMiVtPn+QJlKFvWP/1PYpapqYn0Me2knFn+A== +default-browser-id@^5.0.0: + version "5.0.1" + resolved "https://registry.yarnpkg.com/default-browser-id/-/default-browser-id-5.0.1.tgz#f7a7ccb8f5104bf8e0f71ba3b1ccfa5eafdb21e8" + integrity sha512-x1VCxdX4t+8wVfd1so/9w+vQ4vx7lKd2Qp5tDRutErwmR85OgmfX7RlLRMWafRMY7hbEiXIbudNrjOAPa/hL8Q== + +default-browser@^5.4.0: + version "5.5.0" + resolved "https://registry.yarnpkg.com/default-browser/-/default-browser-5.5.0.tgz#2792e886f2422894545947cc80e1a444496c5976" + integrity sha512-H9LMLr5zwIbSxrmvikGuI/5KGhZ8E2zH3stkMgM5LpOWDutGM2JZaj460Udnf1a+946zc7YBgrqEWwbk7zHvGw== + dependencies: + bundle-name "^4.1.0" + default-browser-id "^5.0.0" + default-require-extensions@^3.0.0: version "3.0.1" resolved "https://registry.yarnpkg.com/default-require-extensions/-/default-require-extensions-3.0.1.tgz#bfae00feeaeada68c2ae256c62540f60b80625bd" @@ -2860,6 +2899,11 @@ defaults@^1.0.3: dependencies: clone "^1.0.2" +define-lazy-prop@^3.0.0: + version "3.0.0" + resolved "https://registry.yarnpkg.com/define-lazy-prop/-/define-lazy-prop-3.0.0.tgz#dbb19adfb746d7fc6d734a06b72f4a00d021255f" + integrity sha512-N+MeXYoqr3pOgn8xfyRPREN7gHakLYjhsHhWGT3fWAiL4IkAt0iDw14QiiEm2bE30c5XX5q0FtAA3CK5f9/BUg== + delayed-stream@~1.0.0: version "1.0.0" resolved "https://registry.yarnpkg.com/delayed-stream/-/delayed-stream-1.0.0.tgz#df3ae199acadfb7d440aaae0b29e2272b24ec619" @@ -2943,6 +2987,11 @@ embla-carousel@8.6.0, embla-carousel@^8.5.2: resolved "https://registry.yarnpkg.com/embla-carousel/-/embla-carousel-8.6.0.tgz#abcedff2bff36992ea8ac27cd30080ca5b6a3f58" integrity sha512-SjWyZBHJPbqxHOzckOfo8lHisEaJWmwd23XppYFYVh10bU66/Pn5tkVkbkCMZVdbUE5eTCI2nD8OyIP4Z+uwkA== +emoji-regex@^10.3.0: + version "10.6.0" + resolved "https://registry.yarnpkg.com/emoji-regex/-/emoji-regex-10.6.0.tgz#bf3d6e8f7f8fd22a65d9703475bc0147357a6b0d" + integrity sha512-toUI84YS5YmxW219erniWD0CIVOo46xGKColeNQRgOzDorgBi1v4D71/OFzgD9GO2UGKIv1C3Sp8DAn0+j5w7A== + emoji-regex@^8.0.0: version "8.0.0" resolved "https://registry.yarnpkg.com/emoji-regex/-/emoji-regex-8.0.0.tgz#e818fd69ce5ccfcb404594f842963bf53164cc37" @@ -3071,7 +3120,7 @@ esbuild@^0.25.0, esbuild@^0.25.1: "@esbuild/win32-ia32" "0.27.4" "@esbuild/win32-x64" "0.27.4" -escalade@^3.2.0: +escalade@^3.1.1, escalade@^3.2.0: version "3.2.0" resolved "https://registry.yarnpkg.com/escalade/-/escalade-3.2.0.tgz#011a3f69856ba189dffa7dc8fcce99d2a87903e5" integrity sha512-WUj2qlxaQtO4g6Pq5c29GTcWGDyd8itL8zTlipgECz3JesAiiOKotd8JU6otB3PACgG6xkJUyVhboMS+bje/jA== @@ -3272,11 +3321,16 @@ gensync@^1.0.0-beta.2: resolved "https://registry.yarnpkg.com/gensync/-/gensync-1.0.0-beta.2.tgz#32a6ee76c3d7f52d46b2b1ae5d93fea8580a25e0" integrity sha512-3hN7NaskYvMDLQY55gnW3NQ+mesEAepTqlg+VEbj7zzqEMBVNhzcGYYeqFo/TlYz6eQiFcp1HcsCZO+nGgS8zg== -get-caller-file@^2.0.1: +get-caller-file@^2.0.1, get-caller-file@^2.0.5: version "2.0.5" resolved "https://registry.yarnpkg.com/get-caller-file/-/get-caller-file-2.0.5.tgz#4f94412a82db32f36e3b0b9741f8a97feb031f7e" integrity sha512-DyFP3BM/3YHTQOCUL/w0OZHR0lpKeGrxotcHWcqNEdnltqFwXVfhEBQ94eIo34AfQpo0rGki4cyIiftY06h2Fg== +get-east-asian-width@^1.0.0: + version "1.5.0" + resolved "https://registry.yarnpkg.com/get-east-asian-width/-/get-east-asian-width-1.5.0.tgz#ce7008fe345edcf5497a6f557cfa54bc318a9ce7" + integrity sha512-CQ+bEO+Tva/qlmw24dCejulK5pMzVnUOFOijVogd3KQs07HnRIgp8TGipvCCRT06xeYEbpbgwaCxglFyiuIcmA== + get-intrinsic@^1.2.6: version "1.3.0" resolved "https://registry.yarnpkg.com/get-intrinsic/-/get-intrinsic-1.3.0.tgz#743f0e3b6964a93a5491ed1bffaae054d7f98d01" @@ -3475,6 +3529,11 @@ is-core-module@^2.16.1: dependencies: hasown "^2.0.2" +is-docker@^3.0.0: + version "3.0.0" + resolved "https://registry.yarnpkg.com/is-docker/-/is-docker-3.0.0.tgz#90093aa3106277d8a77a5910dbae71747e15a200" + integrity sha512-eljcgEDlEns/7AXFosB5K/2nCM4P7FQPkGc/DWLy5rmFEWvZayGrik1d9/QIY5nJ4f9YsVvBkA6kJpHn9rISdQ== + is-extglob@^2.1.1: version "2.1.1" resolved "https://registry.yarnpkg.com/is-extglob/-/is-extglob-2.1.1.tgz#a88c02535791f02ed37c76a1b9ea9773c833f8c2" @@ -3492,6 +3551,18 @@ is-glob@^4.0.1, is-glob@~4.0.1: dependencies: is-extglob "^2.1.1" +is-in-ssh@^1.0.0: + version "1.0.0" + resolved "https://registry.yarnpkg.com/is-in-ssh/-/is-in-ssh-1.0.0.tgz#8eb73c1cabba77748d389588eeea132a63057622" + integrity sha512-jYa6Q9rH90kR1vKB6NM7qqd1mge3Fx4Dhw5TVlK1MUBqhEOuCagrEHMevNuCcbECmXZ0ThXkRm+Ymr51HwEPAw== + +is-inside-container@^1.0.0: + version "1.0.0" + resolved "https://registry.yarnpkg.com/is-inside-container/-/is-inside-container-1.0.0.tgz#e81fba699662eb31dbdaf26766a61d4814717ea4" + integrity sha512-KIYLCCJghfHZxqjYBE7rEy0OBuTd5xCHS7tHVgvCLkx7StIoaxwNW3hCALgEUjFfeRk+MG/Qxmp/vtETEF3tRA== + dependencies: + is-docker "^3.0.0" + is-interactive@^1.0.0: version "1.0.0" resolved "https://registry.yarnpkg.com/is-interactive/-/is-interactive-1.0.0.tgz#cea6e6ae5c870a7b0a0004070b7b587e0252912e" @@ -3527,6 +3598,13 @@ is-windows@^1.0.2: resolved "https://registry.yarnpkg.com/is-windows/-/is-windows-1.0.2.tgz#d1850eb9791ecd18e6182ce12a30f396634bb19d" integrity sha512-eXK1UInq2bPmjyX6e3VHIzMLobc4J94i4AWn+Hpq3OU5KkrRC96OAcR3PRJ/pGu6m8TRnBHP9dkXQVsT/COVIA== +is-wsl@^3.1.0: + version "3.1.1" + resolved "https://registry.yarnpkg.com/is-wsl/-/is-wsl-3.1.1.tgz#327897b26832a3eb117da6c27492d04ca132594f" + integrity sha512-e6rvdUCiQCAuumZslxRJWR/Doq4VpPR82kqclvcS0efgt430SlGIk05vdCN58+VrzgtIcfNODjozVielycD4Sw== + dependencies: + is-inside-container "^1.0.0" + isexe@^2.0.0: version "2.0.0" resolved "https://registry.yarnpkg.com/isexe/-/isexe-2.0.0.tgz#e8fbf374dc556ff8947a10dcb0572d633f2cfa10" @@ -4018,6 +4096,18 @@ onetime@^5.1.0: dependencies: mimic-fn "^2.1.0" +open@^11.0.0: + version "11.0.0" + resolved "https://registry.yarnpkg.com/open/-/open-11.0.0.tgz#897e6132f994d3554cbcf72e0df98f176a7e5f62" + integrity sha512-smsWv2LzFjP03xmvFoJ331ss6h+jixfA4UUV/Bsiyuu4YJPfN+FIQGOIiv4w9/+MoHkfkJ22UIaQWRVFRfH6Vw== + dependencies: + default-browser "^5.4.0" + define-lazy-prop "^3.0.0" + is-in-ssh "^1.0.0" + is-inside-container "^1.0.0" + powershell-utils "^0.1.0" + wsl-utils "^0.3.0" + ora@^5.1.0: version "5.4.1" resolved "https://registry.yarnpkg.com/ora/-/ora-5.4.1.tgz#1b2678426af4ac4a509008e5e4ac9e9959db9e18" @@ -4250,6 +4340,11 @@ postcss@^8.5.3: picocolors "^1.1.1" source-map-js "^1.2.1" +powershell-utils@^0.1.0: + version "0.1.0" + resolved "https://registry.yarnpkg.com/powershell-utils/-/powershell-utils-0.1.0.tgz#5a42c9a824fb4f2f251ccb41aaae73314f5d6ac2" + integrity sha512-dM0jVuXJPsDN6DvRpea484tCUaMiXWjuCn++HGTqUWzGDjv5tZkEZldAJ/UMlqRYGFrD/etByo4/xOuC/snX2A== + preact@~10.12.1: version "10.12.1" resolved "https://registry.yarnpkg.com/preact/-/preact-10.12.1.tgz#8f9cb5442f560e532729b7d23d42fd1161354a21" @@ -4618,6 +4713,16 @@ rollup-plugin-license@^3.7.0: spdx-expression-validate "^2.0.0" spdx-satisfies "^5.0.1" +rollup-plugin-visualizer@^7.0.1: + version "7.0.1" + resolved "https://registry.yarnpkg.com/rollup-plugin-visualizer/-/rollup-plugin-visualizer-7.0.1.tgz#291c10ff4a956d9b2483f8b4147b2bf0aacd3a6e" + integrity sha512-UJUT4+1Ho4OcWmPYU3sYXgUqI8B8Ayfe06MX7y0qCJ1K8aGoKtR/NDd/2nZqM7ADkrzny+I99Ul7GgyoiVNAgg== + dependencies: + open "^11.0.0" + picomatch "^4.0.2" + source-map "^0.7.4" + yargs "^18.0.0" + rollup@^4.34.9: version "4.60.2" resolved "https://registry.yarnpkg.com/rollup/-/rollup-4.60.2.tgz#ac23fe4bd530304cef9fa61e639d7098b6762cf4" @@ -4686,6 +4791,11 @@ rollup@^4.59.0: "@rollup/rollup-win32-x64-msvc" "4.60.0" fsevents "~2.3.2" +run-applescript@^7.0.0: + version "7.1.0" + resolved "https://registry.yarnpkg.com/run-applescript/-/run-applescript-7.1.0.tgz#2e9e54c4664ec3106c5b5630e249d3d6595c4911" + integrity sha512-DPe5pVFaAsinSaV6QjQ6gdiedWDcRCbUuiQfQa2wmWV7+xC9bGulGI8+TdRmoFkAPaBXk8CrAbnlY2ISniJ47Q== + safe-buffer@~5.2.0: version "5.2.1" resolved "https://registry.yarnpkg.com/safe-buffer/-/safe-buffer-5.2.1.tgz#1eaf9fa9bdb1fdd4ec75f58f9cdb4e6b7827eec6" @@ -4760,7 +4870,7 @@ source-map@^0.6.1, source-map@~0.6.1: resolved "https://registry.yarnpkg.com/source-map/-/source-map-0.6.1.tgz#74722af32e9614e9c287a8d0bbde48b5e2f1a263" integrity sha512-UjgapumWlbMhkBgzT7Ykc5YXUT46F0iKu8SGXq0bcwP5dz/h0Plj6enJqjz1Zbq2l5WaqYnrVbwWOWMyF3F47g== -source-map@^0.7.6: +source-map@^0.7.4, source-map@^0.7.6: version "0.7.6" resolved "https://registry.yarnpkg.com/source-map/-/source-map-0.7.6.tgz#a3658ab87e5b6429c8a1f3ba0083d4c61ca3ef02" integrity sha512-i5uvt8C3ikiWeNZSVZNWcfZPItFQOsYTUAOkcUPGd8DqDy1uOUikjt5dG+uRlwyvR108Fb9DOd4GvXfT0N2/uQ== @@ -4850,6 +4960,15 @@ string-width@^4.1.0, string-width@^4.2.0: is-fullwidth-code-point "^3.0.0" strip-ansi "^6.0.1" +string-width@^7.0.0, string-width@^7.2.0: + version "7.2.0" + resolved "https://registry.yarnpkg.com/string-width/-/string-width-7.2.0.tgz#b5bb8e2165ce275d4d43476dd2700ad9091db6dc" + integrity sha512-tsaTIkKW9b4N+AEj+SVA+WhJzV7/zMhcSu78mLKWSk7cXMOSHsBKFWUs0fWwq8QyK3MgJBQRX6Gbi4kYbdvGkQ== + dependencies: + emoji-regex "^10.3.0" + get-east-asian-width "^1.0.0" + strip-ansi "^7.1.0" + string_decoder@^1.1.1: version "1.3.0" resolved "https://registry.yarnpkg.com/string_decoder/-/string_decoder-1.3.0.tgz#42f114594a46cf1a8e30b0a84f56c78c3edac21e" @@ -4864,6 +4983,13 @@ strip-ansi@^6.0.0, strip-ansi@^6.0.1: dependencies: ansi-regex "^5.0.1" +strip-ansi@^7.1.0: + version "7.2.0" + resolved "https://registry.yarnpkg.com/strip-ansi/-/strip-ansi-7.2.0.tgz#d22a269522836a627af8d04b5c3fd2c7fa3e32e3" + integrity sha512-yDPMNjp4WyfYBkHnjIRLfca1i6KMyGCtsVgoKe/z1+6vukgaENdgGBZt+ZmKPc4gavvEZ5OgHfHdrazhgNyG7w== + dependencies: + ansi-regex "^6.2.2" + strip-bom@^4.0.0: version "4.0.0" resolved "https://registry.yarnpkg.com/strip-bom/-/strip-bom-4.0.0.tgz#9c3505c1db45bcedca3d9cf7a16f5c5aa3901878" @@ -5251,6 +5377,15 @@ wrap-ansi@^6.2.0: string-width "^4.1.0" strip-ansi "^6.0.0" +wrap-ansi@^9.0.0: + version "9.0.2" + resolved "https://registry.yarnpkg.com/wrap-ansi/-/wrap-ansi-9.0.2.tgz#956832dea9494306e6d209eb871643bb873d7c98" + integrity sha512-42AtmgqjV+X1VpdOfyTGOYRi0/zsoLqtXQckTmqTeybT+BDIbM/Guxo7x3pE2vtpr1ok6xRqM9OpBe+Jyoqyww== + dependencies: + ansi-styles "^6.2.1" + string-width "^7.0.0" + strip-ansi "^7.1.0" + wrappy@1: version "1.0.2" resolved "https://registry.yarnpkg.com/wrappy/-/wrappy-1.0.2.tgz#b5243d8f3ec1aa35f1364605bc0d1036e30ab69f" @@ -5266,11 +5401,24 @@ write-file-atomic@^3.0.0: signal-exit "^3.0.2" typedarray-to-buffer "^3.1.5" +wsl-utils@^0.3.0: + version "0.3.1" + resolved "https://registry.yarnpkg.com/wsl-utils/-/wsl-utils-0.3.1.tgz#9479836ddf03be267aad3abfc3cb1f6e0c9f1ed1" + integrity sha512-g/eziiSUNBSsdDJtCLB8bdYEUMj4jR7AGeUo96p/3dTafgjHhpF4RiCFPiRILwjQoDXx5MqkBr4fwWtR3Ky4Wg== + dependencies: + is-wsl "^3.1.0" + powershell-utils "^0.1.0" + y18n@^4.0.0: version "4.0.3" resolved "https://registry.yarnpkg.com/y18n/-/y18n-4.0.3.tgz#b5f259c82cd6e336921efd7bfd8bf560de9eeedf" integrity sha512-JKhqTOwSrqNA1NY5lSztJ1GrBiUodLMmIZuLiDaMRJ+itFd+ABVE8XBjOvIWL+rSqNDC74LCSFmlb/U4UZ4hJQ== +y18n@^5.0.5: + version "5.0.8" + resolved "https://registry.yarnpkg.com/y18n/-/y18n-5.0.8.tgz#7f4934d0f7ca8c56f95314939ddcd2dd91ce1d55" + integrity sha512-0pfFzegeDWJHJIAmTLRP2DwHjdF5s7jo9tuztdQxAhINCdvS+3nGINqPd00AphqJR/0LhANUS6/+7SCb98YOfA== + yallist@^3.0.2: version "3.1.1" resolved "https://registry.yarnpkg.com/yallist/-/yallist-3.1.1.tgz#dbb7daf9bfd8bac9ab45ebf602b8cbad0d5d08fd" @@ -5294,6 +5442,11 @@ yargs-parser@^18.1.2: camelcase "^5.0.0" decamelize "^1.2.0" +yargs-parser@^22.0.0: + version "22.0.0" + resolved "https://registry.yarnpkg.com/yargs-parser/-/yargs-parser-22.0.0.tgz#87b82094051b0567717346ecd00fd14804b357c8" + integrity sha512-rwu/ClNdSMpkSrUb+d6BRsSkLUq1fmfsY6TOpYzTwvwkg1/NRG85KBy3kq++A8LKQwX6lsu+aWad+2khvuXrqw== + yargs@^15.0.2, yargs@^15.3.1: version "15.4.1" resolved "https://registry.yarnpkg.com/yargs/-/yargs-15.4.1.tgz#0d87a16de01aee9d8bec2bfbf74f67851730f4f8" @@ -5311,6 +5464,18 @@ yargs@^15.0.2, yargs@^15.3.1: y18n "^4.0.0" yargs-parser "^18.1.2" +yargs@^18.0.0: + version "18.0.0" + resolved "https://registry.yarnpkg.com/yargs/-/yargs-18.0.0.tgz#6c84259806273a746b09f579087b68a3c2d25bd1" + integrity sha512-4UEqdc2RYGHZc7Doyqkrqiln3p9X2DZVxaGbwhn2pi7MrRagKaOcIKe8L3OxYcbhXLgLFUS3zAYuQjKBQgmuNg== + dependencies: + cliui "^9.0.1" + escalade "^3.1.1" + get-caller-file "^2.0.5" + string-width "^7.2.0" + y18n "^5.0.5" + yargs-parser "^22.0.0" + yocto-queue@^0.1.0: version "0.1.0" resolved "https://registry.yarnpkg.com/yocto-queue/-/yocto-queue-0.1.0.tgz#0294eb3dee05028d31ee1a5fa2c556a6aaf10a1b"