diff --git a/packages/nextjs/package.json b/packages/nextjs/package.json index 9bc9926d4634..48e0bbca33e8 100644 --- a/packages/nextjs/package.json +++ b/packages/nextjs/package.json @@ -85,8 +85,10 @@ "@sentry/opentelemetry": "10.4.0", "@sentry/react": "10.4.0", "@sentry/vercel-edge": "10.4.0", - "@sentry/webpack-plugin": "^4.0.2", + "@sentry/webpack-plugin": "^4.1.0", + "@sentry/bundler-plugin-core": "^4.1.0", "chalk": "3.0.0", + "glob": "^11.0.3", "resolve": "1.22.8", "rollup": "^4.35.0", "stacktrace-parser": "^0.1.10" diff --git a/packages/nextjs/src/config/getBuildPluginOptions.ts b/packages/nextjs/src/config/getBuildPluginOptions.ts new file mode 100644 index 000000000000..3dfef3bbad08 --- /dev/null +++ b/packages/nextjs/src/config/getBuildPluginOptions.ts @@ -0,0 +1,97 @@ +import type { Options as SentryBuildPluginOptions } from '@sentry/bundler-plugin-core'; +import * as path from 'path'; +import type { SentryBuildOptions } from './types'; + +/** + * Get Sentry Build Plugin options for the runAfterProductionCompile hook. + */ +export function getBuildPluginOptions({ + sentryBuildOptions, + releaseName, + distDirAbsPath, +}: { + sentryBuildOptions: SentryBuildOptions; + releaseName: string | undefined; + distDirAbsPath: string; +}): SentryBuildPluginOptions { + const sourcemapUploadAssets: string[] = []; + const sourcemapUploadIgnore: string[] = []; + + const filesToDeleteAfterUpload: string[] = []; + + // We need to convert paths to posix because Glob patterns use `\` to escape + // glob characters. This clashes with Windows path separators. + // See: https://www.npmjs.com/package/glob + const normalizedDistDirAbsPath = distDirAbsPath.replace(/\\/g, '/'); + + sourcemapUploadAssets.push( + path.posix.join(normalizedDistDirAbsPath, '**'), // Next.js build output + ); + if (sentryBuildOptions.sourcemaps?.deleteSourcemapsAfterUpload) { + filesToDeleteAfterUpload.push( + path.posix.join(normalizedDistDirAbsPath, '**', '*.js.map'), + path.posix.join(normalizedDistDirAbsPath, '**', '*.mjs.map'), + path.posix.join(normalizedDistDirAbsPath, '**', '*.cjs.map'), + ); + } + + return { + authToken: sentryBuildOptions.authToken, + headers: sentryBuildOptions.headers, + org: sentryBuildOptions.org, + project: sentryBuildOptions.project, + telemetry: sentryBuildOptions.telemetry, + debug: sentryBuildOptions.debug, + errorHandler: sentryBuildOptions.errorHandler, + reactComponentAnnotation: { + ...sentryBuildOptions.reactComponentAnnotation, + ...sentryBuildOptions.unstable_sentryWebpackPluginOptions?.reactComponentAnnotation, + }, + silent: sentryBuildOptions.silent, + url: sentryBuildOptions.sentryUrl, + sourcemaps: { + disable: sentryBuildOptions.sourcemaps?.disable, + rewriteSources(source) { + if (source.startsWith('webpack://_N_E/')) { + return source.replace('webpack://_N_E/', ''); + } else if (source.startsWith('webpack://')) { + return source.replace('webpack://', ''); + } else { + return source; + } + }, + assets: sentryBuildOptions.sourcemaps?.assets ?? sourcemapUploadAssets, + ignore: sentryBuildOptions.sourcemaps?.ignore ?? sourcemapUploadIgnore, + filesToDeleteAfterUpload, + ...sentryBuildOptions.unstable_sentryWebpackPluginOptions?.sourcemaps, + }, + release: + releaseName !== undefined + ? { + inject: false, // The webpack plugin's release injection breaks the `app` directory - we inject the release manually with the value injection loader instead. + name: releaseName, + create: sentryBuildOptions.release?.create, + finalize: sentryBuildOptions.release?.finalize, + dist: sentryBuildOptions.release?.dist, + vcsRemote: sentryBuildOptions.release?.vcsRemote, + setCommits: sentryBuildOptions.release?.setCommits, + deploy: sentryBuildOptions.release?.deploy, + ...sentryBuildOptions.unstable_sentryWebpackPluginOptions?.release, + } + : { + inject: false, + create: false, + finalize: false, + }, + bundleSizeOptimizations: { + ...sentryBuildOptions.bundleSizeOptimizations, + }, + _metaOptions: { + loggerPrefixOverride: '[@sentry/nextjs]', + telemetry: { + metaFramework: 'nextjs', + }, + }, + ...sentryBuildOptions.unstable_sentryWebpackPluginOptions, + }; +} diff --git a/packages/nextjs/src/config/handleRunAfterProductionCompile.ts b/packages/nextjs/src/config/handleRunAfterProductionCompile.ts new file mode 100644 index 000000000000..36203e801354 --- /dev/null +++ b/packages/nextjs/src/config/handleRunAfterProductionCompile.ts @@ -0,0 +1,62 @@ +import type { createSentryBuildPluginManager as createSentryBuildPluginManagerType } from '@sentry/bundler-plugin-core'; +import { loadModule } from '@sentry/core'; +import { glob } from 'glob'; +import { getBuildPluginOptions } from './getBuildPluginOptions'; +import type { SentryBuildOptions } from './types'; + +/** + * This function is called by Next.js after the production build is complete. + * It is used to upload sourcemaps to Sentry. + */ +export async function handleRunAfterProductionCompile( + { releaseName, distDir, buildTool }: { releaseName?: string; distDir: string; buildTool: 'webpack' | 'turbopack' }, + sentryBuildOptions: SentryBuildOptions, +): Promise { + if (sentryBuildOptions.debug) { + // eslint-disable-next-line no-console + console.debug('[@sentry/nextjs] Running runAfterProductionCompile logic.'); + } + + const { createSentryBuildPluginManager } = + loadModule<{ createSentryBuildPluginManager: typeof createSentryBuildPluginManagerType }>( + '@sentry/bundler-plugin-core', + module, + ) ?? {}; + + if (!createSentryBuildPluginManager) { + // eslint-disable-next-line no-console + console.warn( + '[@sentry/nextjs] Could not load build manager package. Will not run runAfterProductionCompile logic.', + ); + return; + } + + const sentryBuildPluginManager = createSentryBuildPluginManager( + getBuildPluginOptions({ + sentryBuildOptions, + releaseName, + distDirAbsPath: distDir, + }), + { + buildTool, + loggerPrefix: '[@sentry/nextjs]', + }, + ); + + const buildArtifacts = await glob( + ['/**/*.js', '/**/*.mjs', '/**/*.cjs', '/**/*.js.map', '/**/*.mjs.map', '/**/*.cjs.map'].map( + q => `${q}?(\\?*)?(#*)`, // We want to allow query and hashes strings at the end of files + ), + { + root: distDir, + absolute: true, + nodir: true, + }, + ); + + await sentryBuildPluginManager.telemetry.emitBundlerPluginExecutionSignal(); + await sentryBuildPluginManager.createRelease(); + await sentryBuildPluginManager.injectDebugIds(buildArtifacts); + await sentryBuildPluginManager.uploadSourcemaps(buildArtifacts); + await sentryBuildPluginManager.deleteArtifacts(); +} diff --git a/packages/nextjs/src/config/types.ts b/packages/nextjs/src/config/types.ts index b29fbb6881af..79cb8d7a1985 100644 --- a/packages/nextjs/src/config/types.ts +++ b/packages/nextjs/src/config/types.ts @@ -52,6 +52,9 @@ export type NextConfigObject = { env?: Record; serverExternalPackages?: string[]; // next >= v15.0.0 turbopack?: TurbopackOptions; + compiler?: { + runAfterProductionCompile?: (context: { distDir: string; projectDir: string }) => Promise | void; + }; }; export type SentryBuildOptions = { @@ -498,6 +501,16 @@ export type SentryBuildOptions = { */ disableSentryWebpackConfig?: boolean; + /** + * When true (and Next.js >= 15), use the runAfterProductionCompile hook to consolidate sourcemap uploads + * into a single operation after all webpack/turbopack builds complete, reducing build time. + * + * When false, use the traditional approach of uploading sourcemaps during each webpack build. + * + * @default false + */ + useRunAfterProductionCompileHook?: boolean; + /** * Contains a set of experimental flags that might change in future releases. These flags enable * features that are still in development and may be modified, renamed, or removed without notice. diff --git a/packages/nextjs/src/config/util.ts b/packages/nextjs/src/config/util.ts index a88e68a57135..a5def59a66fe 100644 --- a/packages/nextjs/src/config/util.ts +++ b/packages/nextjs/src/config/util.ts @@ -1,3 +1,4 @@ +import { parseSemver } from '@sentry/core'; import * as fs from 'fs'; import { sync as resolveSync } from 'resolve'; @@ -27,3 +28,39 @@ function resolveNextjsPackageJson(): string | undefined { return undefined; } } + +/** + * Checks if the current Next.js version supports the runAfterProductionCompile hook. + * This hook was introduced in Next.js 15.4.1. (https://github.com/vercel/next.js/pull/77345) + * + * @returns true if Next.js version is 15.4.1 or higher + */ +export function supportsProductionCompileHook(): boolean { + const version = getNextjsVersion(); + if (!version) { + return false; + } + + const { major, minor, patch } = parseSemver(version); + + if (major === undefined || minor === undefined || patch === undefined) { + return false; + } + + if (major > 15) { + return true; + } + + // For major version 15, check if it's 15.4.1 or higher + if (major === 15) { + if (minor > 4) { + return true; + } + if (minor === 4 && patch >= 1) { + return true; + } + return false; + } + + return false; +} diff --git a/packages/nextjs/src/config/webpackPluginOptions.ts b/packages/nextjs/src/config/webpackPluginOptions.ts index f4ff4363cdb7..a48e59dfaf48 100644 --- a/packages/nextjs/src/config/webpackPluginOptions.ts +++ b/packages/nextjs/src/config/webpackPluginOptions.ts @@ -70,7 +70,10 @@ export function getWebpackPluginOptions( silent: sentryBuildOptions.silent, url: sentryBuildOptions.sentryUrl, sourcemaps: { - disable: sentryBuildOptions.sourcemaps?.disable, + // if the user has enabled the runAfterProductionCompileHook, we handle sourcemap uploads a later step + disable: sentryBuildOptions.useRunAfterProductionCompileHook + ? 'disable-upload' + : sentryBuildOptions.sourcemaps?.disable, rewriteSources(source) { if (source.startsWith('webpack://_N_E/')) { return source.replace('webpack://_N_E/', ''); @@ -95,7 +98,8 @@ export function getWebpackPluginOptions( ...sentryBuildOptions.unstable_sentryWebpackPluginOptions?.sourcemaps, }, release: - releaseName !== undefined + // if the user has enabled the runAfterProductionCompileHook, we handle release creation a later step + releaseName !== undefined && !sentryBuildOptions.useRunAfterProductionCompileHook ? { inject: false, // The webpack plugin's release injection breaks the `app` directory - we inject the release manually with the value injection loader instead. name: releaseName, diff --git a/packages/nextjs/src/config/withSentryConfig.ts b/packages/nextjs/src/config/withSentryConfig.ts index 57fff867f64a..248911d61c71 100644 --- a/packages/nextjs/src/config/withSentryConfig.ts +++ b/packages/nextjs/src/config/withSentryConfig.ts @@ -5,6 +5,7 @@ import { getSentryRelease } from '@sentry/node'; import * as childProcess from 'child_process'; import * as fs from 'fs'; import * as path from 'path'; +import { handleRunAfterProductionCompile } from './handleRunAfterProductionCompile'; import { createRouteManifest } from './manifest/createRouteManifest'; import type { RouteManifest } from './manifest/types'; import { constructTurbopackConfig } from './turbopack'; @@ -14,7 +15,7 @@ import type { NextConfigObject, SentryBuildOptions, } from './types'; -import { getNextjsVersion } from './util'; +import { getNextjsVersion, supportsProductionCompileHook } from './util'; import { constructWebpackConfigFunction } from './webpack'; let showedExportModeTunnelWarning = false; @@ -293,6 +294,37 @@ function getFinalConfigObject( } } + if (userSentryOptions.useRunAfterProductionCompileHook === true && supportsProductionCompileHook()) { + if (incomingUserNextConfigObject?.compiler?.runAfterProductionCompile === undefined) { + incomingUserNextConfigObject.compiler ??= {}; + incomingUserNextConfigObject.compiler.runAfterProductionCompile = async ({ distDir }) => { + await handleRunAfterProductionCompile( + { releaseName, distDir, buildTool: isTurbopack ? 'turbopack' : 'webpack' }, + userSentryOptions, + ); + }; + } else if (typeof incomingUserNextConfigObject.compiler.runAfterProductionCompile === 'function') { + incomingUserNextConfigObject.compiler.runAfterProductionCompile = new Proxy( + incomingUserNextConfigObject.compiler.runAfterProductionCompile, + { + async apply(target, thisArg, argArray) { + const { distDir }: { distDir: string } = argArray[0] ?? { distDir: '.next' }; + await target.apply(thisArg, argArray); + await handleRunAfterProductionCompile( + { releaseName, distDir, buildTool: isTurbopack ? 'turbopack' : 'webpack' }, + userSentryOptions, + ); + }, + }, + ); + } else { + // eslint-disable-next-line no-console + console.warn( + '[@sentry/nextjs] The configured `compiler.runAfterProductionCompile` option is not a function. Will not run source map and release management logic.', + ); + } + } + return { ...incomingUserNextConfigObject, ...(nextMajor && nextMajor >= 15 diff --git a/yarn.lock b/yarn.lock index 7d40f9a3ecff..47cb89f961bd 100644 --- a/yarn.lock +++ b/yarn.lock @@ -4708,6 +4708,18 @@ resolved "https://registry.yarnpkg.com/@ioredis/commands/-/commands-1.2.0.tgz#6d61b3097470af1fdbbe622795b8921d42018e11" integrity sha512-Sx1pU8EM64o2BrqNpEO1CNLtKQwyhuXuqyfH7oGKCk+1a33d2r5saW8zNwm3j6BTExtjrv2BxTgzzkMwts6vGg== +"@isaacs/balanced-match@^4.0.1": + version "4.0.1" + resolved "https://registry.yarnpkg.com/@isaacs/balanced-match/-/balanced-match-4.0.1.tgz#3081dadbc3460661b751e7591d7faea5df39dd29" + integrity sha512-yzMTt9lEb8Gv7zRioUilSglI0c0smZ9k5D65677DLWLtWJaXIS3CqcGyUFByYKlnUj6TkjLVs54fBl6+TiGQDQ== + +"@isaacs/brace-expansion@^5.0.0": + version "5.0.0" + resolved "https://registry.yarnpkg.com/@isaacs/brace-expansion/-/brace-expansion-5.0.0.tgz#4b3dabab7d8e75a429414a96bd67bf4c1d13e0f3" + integrity sha512-ZT55BDLV0yv0RBm2czMiZ+SqCGO7AvmOM3G/w2xhVPH+te0aKgFjmBvGlL1dH+ql2tgGO3MVrbb3jCKyvpgnxA== + dependencies: + "@isaacs/balanced-match" "^4.0.1" + "@isaacs/cliui@^8.0.2": version "8.0.2" resolved "https://registry.yarnpkg.com/@isaacs/cliui/-/cliui-8.0.2.tgz#b37667b7bc181c168782259bab42474fbf52b550" @@ -6938,6 +6950,11 @@ resolved "https://registry.yarnpkg.com/@sentry/babel-plugin-component-annotate/-/babel-plugin-component-annotate-4.0.2.tgz#7c8eb80a38b5e6b4c4cea4c391d07581020c91e4" integrity sha512-Nr/VamvpQs6w642EI5t+qaCUGnVEro0qqk+S8XO1gc8qSdpc8kkZJFnUk7ozAr+ljYWGfVgWXrxI9lLiriLsRA== +"@sentry/babel-plugin-component-annotate@4.1.0": + version "4.1.0" + resolved "https://registry.yarnpkg.com/@sentry/babel-plugin-component-annotate/-/babel-plugin-component-annotate-4.1.0.tgz#6e7168f5fa59f53ac4b68e3f79c5fd54adc13f2e" + integrity sha512-UkcnqC7Bp9ODyoBN7BKcRotd1jz/I2vyruE/qjNfRC7UnP+jIRItUWYaXxQPON1fTw+N+egKdByk0M1y2OPv/Q== + "@sentry/bundler-plugin-core@4.0.0": version "4.0.0" resolved "https://registry.yarnpkg.com/@sentry/bundler-plugin-core/-/bundler-plugin-core-4.0.0.tgz#564463cf53f869496ab5d4986e97f86618a67677" @@ -6966,6 +6983,20 @@ magic-string "0.30.8" unplugin "1.0.1" +"@sentry/bundler-plugin-core@4.1.0", "@sentry/bundler-plugin-core@^4.1.0": + version "4.1.0" + resolved "https://registry.yarnpkg.com/@sentry/bundler-plugin-core/-/bundler-plugin-core-4.1.0.tgz#c1b2f7a890a44e5ac5decc984a133aacf6147dd4" + integrity sha512-/5XBtCF6M+9frEXrrvfSWOdOC2q6I1L7oY7qbUVegNkp3kYVGihNZZnJIXGzo9rmwnA0IV7jI3o0pF/HDRqPeA== + dependencies: + "@babel/core" "^7.18.5" + "@sentry/babel-plugin-component-annotate" "4.1.0" + "@sentry/cli" "^2.51.0" + dotenv "^16.3.1" + find-up "^5.0.0" + glob "^9.3.2" + magic-string "0.30.8" + unplugin "1.0.1" + "@sentry/cli-darwin@2.51.1": version "2.51.1" resolved "https://registry.yarnpkg.com/@sentry/cli-darwin/-/cli-darwin-2.51.1.tgz#3a1db065651893f72dad3a502b2d7c2f5e6a7dd8" @@ -7006,7 +7037,7 @@ resolved "https://registry.yarnpkg.com/@sentry/cli-win32-x64/-/cli-win32-x64-2.51.1.tgz#d361e37146c9269d40c37459271a6c2cfa1fa8a6" integrity sha512-v2hreYUPPTNK1/N7+DeX7XBN/zb7p539k+2Osf0HFyVBaoUC3Y3+KBwSf4ASsnmgTAK7HCGR+X0NH1vP+icw4w== -"@sentry/cli@^2.49.0", "@sentry/cli@^2.51.1": +"@sentry/cli@^2.49.0", "@sentry/cli@^2.51.0", "@sentry/cli@^2.51.1": version "2.51.1" resolved "https://registry.yarnpkg.com/@sentry/cli/-/cli-2.51.1.tgz#c6bdc6025e8f600e44fc76f8274c369aeb5d4df4" integrity sha512-FU+54kNcKJABU0+ekvtnoXHM9zVrDe1zXVFbQT7mS0On0m1P0zFRGdzbnWe2XzpzuEAJXtK6aog/W+esRU9AIA== @@ -7051,6 +7082,15 @@ unplugin "1.0.1" uuid "^9.0.0" +"@sentry/webpack-plugin@^4.1.0": + version "4.1.0" + resolved "https://registry.yarnpkg.com/@sentry/webpack-plugin/-/webpack-plugin-4.1.0.tgz#e95e2dcd10e71dc8c3a16ba5cad9153f5e78c3bc" + integrity sha512-YqfDfyGAuT/9YW1kgAPfD7kGUKQCh1E5co+qMdToxi/Mz4xsWJY02rFS5GrJixYktYJfSMze8NiRr89yJMxYHw== + dependencies: + "@sentry/bundler-plugin-core" "4.1.0" + unplugin "1.0.1" + uuid "^9.0.0" + "@sigstore/protobuf-specs@^0.1.0": version "0.1.0" resolved "https://registry.yarnpkg.com/@sigstore/protobuf-specs/-/protobuf-specs-0.1.0.tgz#957cb64ea2f5ce527cc9cf02a096baeb0d2b99b4" @@ -9402,7 +9442,7 @@ postcss "^8.4.47" source-map-js "^1.2.0" -"@vue/compiler-sfc@^3.4.15", "@vue/compiler-sfc@^3.5.13", "@vue/compiler-sfc@^3.5.4": +"@vue/compiler-sfc@^3.4.15", "@vue/compiler-sfc@^3.5.4": version "3.5.17" resolved "https://registry.yarnpkg.com/@vue/compiler-sfc/-/compiler-sfc-3.5.17.tgz#c518871276e26593612bdab36f3f5bcd053b13bf" integrity sha512-rQQxbRJMgTqwRugtjw0cnyQv9cP4/4BxWfTdRBkqsTfLOHWykLzbOc3C4GGzAmdMDxhzU/1Ija5bTjMVrddqww== @@ -13401,10 +13441,10 @@ cross-spawn@^6.0.0: shebang-command "^1.2.0" which "^1.2.9" -cross-spawn@^7.0.0, cross-spawn@^7.0.2, cross-spawn@^7.0.3: - version "7.0.3" - resolved "https://registry.yarnpkg.com/cross-spawn/-/cross-spawn-7.0.3.tgz#f73a85b9d5d41d045551c177e2882d4ac85728a6" - integrity sha512-iRDPJKUPVEND7dHPO8rkbOnPpyDygcDFtWjpeWNCgy8WP2rXcxXL8TskReQl6OrB2G7+UJrags1q15Fudc7G6w== +cross-spawn@^7.0.0, cross-spawn@^7.0.2, cross-spawn@^7.0.3, cross-spawn@^7.0.6: + version "7.0.6" + resolved "https://registry.yarnpkg.com/cross-spawn/-/cross-spawn-7.0.6.tgz#8a58fe78f00dcd70c370451759dfbfaf03e8ee9f" + integrity sha512-uV2QOWP2nWzsy2aMp8aRibhi9dlzF5Hgh5SHaB9OiTGEyDTiJJyx0uy51QXdyWbtAHNua4XJzUKca3OzKUd3vA== dependencies: path-key "^3.1.0" shebang-command "^2.0.0" @@ -14149,9 +14189,6 @@ detective-scss@^5.0.1: version "5.0.1" resolved "https://registry.yarnpkg.com/detective-scss/-/detective-scss-5.0.1.tgz#6a7f792dc9c0e8cfc0d252a50ba26a6df12596a7" integrity sha512-MAyPYRgS6DCiS6n6AoSBJXLGVOydsr9huwXORUlJ37K3YLyiN0vYHpzs3AdJOgHobBfispokoqrEon9rbmKacg== - dependencies: - gonzales-pe "^4.3.0" - node-source-walk "^7.0.1" detective-stylus@^4.0.0: version "4.0.0" @@ -14186,14 +14223,6 @@ detective-vue2@^2.2.0: version "2.2.0" resolved "https://registry.yarnpkg.com/detective-vue2/-/detective-vue2-2.2.0.tgz#35fd1d39e261b064aca9fcaf20e136c76877482a" integrity sha512-sVg/t6O2z1zna8a/UIV6xL5KUa2cMTQbdTIIvqNM0NIPswp52fe43Nwmbahzj3ww4D844u/vC2PYfiGLvD3zFA== - dependencies: - "@dependents/detective-less" "^5.0.1" - "@vue/compiler-sfc" "^3.5.13" - detective-es6 "^5.0.1" - detective-sass "^6.0.1" - detective-scss "^5.0.1" - detective-stylus "^5.0.1" - detective-typescript "^14.0.0" deterministic-object-hash@^1.3.1: version "1.3.1" @@ -16725,9 +16754,6 @@ fetch-blob@^3.1.2, fetch-blob@^3.1.4: version "3.2.0" resolved "https://registry.yarnpkg.com/fetch-blob/-/fetch-blob-3.2.0.tgz#f09b8d4bbd45adc6f0c20b7e787e793e309dcce9" integrity sha512-7yAQpD2UMJzLi1Dqv7qFYnPbaPx7ZfFK6PiIxQ4PfkGPyNyl2Ugx+a/umUonmKqjhM4DnfbMvdX6otXq83soQQ== - dependencies: - node-domexception "^1.0.0" - web-streams-polyfill "^3.0.3" fflate@0.8.2, fflate@^0.8.2: version "0.8.2" @@ -17086,12 +17112,12 @@ foreach@^2.0.5: resolved "https://registry.yarnpkg.com/foreach/-/foreach-2.0.5.tgz#0bee005018aeb260d0a3af3ae658dd0136ec1b99" integrity sha1-C+4AUBiusmDQo6865ljdATbsG5k= -foreground-child@^3.1.0: - version "3.1.1" - resolved "https://registry.yarnpkg.com/foreground-child/-/foreground-child-3.1.1.tgz#1d173e776d75d2772fed08efe4a0de1ea1b12d0d" - integrity sha512-TMKDUnIte6bfb5nWv7V/caI169OHgvwjb7V4WkeUvbQQdjr5rWKqHFiKWb/fcOwB+CzBT+qbWjvj+DVwRskpIg== +foreground-child@^3.1.0, foreground-child@^3.3.1: + version "3.3.1" + resolved "https://registry.yarnpkg.com/foreground-child/-/foreground-child-3.3.1.tgz#32e8e9ed1b68a3497befb9ac2b6adf92a638576f" + integrity sha512-gIXjKqtFuWEgzFRJA9WCQeSJLZDjgJUOMCMzxtvFq/37KojM1BFGufqsCy0r4qSQmYLsZYMeyRqzIWOMup03sw== dependencies: - cross-spawn "^7.0.0" + cross-spawn "^7.0.6" signal-exit "^4.0.1" form-data@^4.0.0: @@ -17696,6 +17722,18 @@ glob@^10.0.0, glob@^10.2.2, glob@^10.3.10, glob@^10.3.4, glob@^10.3.7, glob@^10. package-json-from-dist "^1.0.0" path-scurry "^1.11.1" +glob@^11.0.3: + version "11.0.3" + resolved "https://registry.yarnpkg.com/glob/-/glob-11.0.3.tgz#9d8087e6d72ddb3c4707b1d2778f80ea3eaefcd6" + integrity sha512-2Nim7dha1KVkaiF4q6Dj+ngPPMdfvLJEOpZk/jKiUAkqKebpGAWQXAq9z1xu9HKu5lWfqw/FASuccEjyznjPaA== + dependencies: + foreground-child "^3.3.1" + jackspeak "^4.1.1" + minimatch "^10.0.3" + minipass "^7.1.2" + package-json-from-dist "^1.0.0" + path-scurry "^2.0.0" + glob@^5.0.10: version "5.0.15" resolved "https://registry.yarnpkg.com/glob/-/glob-5.0.15.tgz#1bc936b9e02f4a603fcc222ecf7633d30b8b93b1" @@ -19768,10 +19806,10 @@ jackspeak@^3.1.2: optionalDependencies: "@pkgjs/parseargs" "^0.11.0" -jackspeak@^4.0.1: - version "4.1.0" - resolved "https://registry.yarnpkg.com/jackspeak/-/jackspeak-4.1.0.tgz#c489c079f2b636dc4cbe9b0312a13ff1282e561b" - integrity sha512-9DDdhb5j6cpeitCbvLO7n7J4IxnbM6hoF6O1g4HQ5TfhvvKN8ywDM7668ZhMHRqVmxqhps/F6syWK2KcPxYlkw== +jackspeak@^4.0.1, jackspeak@^4.1.1: + version "4.1.1" + resolved "https://registry.yarnpkg.com/jackspeak/-/jackspeak-4.1.1.tgz#96876030f450502047fc7e8c7fcf8ce8124e43ae" + integrity sha512-zptv57P3GpL+O0I7VdMJNBZCu+BPHVQUk55Ft8/QCJjTVxrnJHuVuX/0Bl2A6/+2oyR/ZMEuFKwmzqqZ/U5nPQ== dependencies: "@isaacs/cliui" "^8.0.2" @@ -22026,12 +22064,12 @@ minimatch@5.1.0, minimatch@^5.0.1, minimatch@^5.1.0: dependencies: brace-expansion "^2.0.1" -minimatch@^10.0.0: - version "10.0.1" - resolved "https://registry.yarnpkg.com/minimatch/-/minimatch-10.0.1.tgz#ce0521856b453c86e25f2c4c0d03e6ff7ddc440b" - integrity sha512-ethXTt3SGGR+95gudmqJ1eNhRO7eGEGIgYA9vnPatK4/etz2MEVDno5GMCibdMTuBMyElzIlgxMna3K94XDIDQ== +minimatch@^10.0.0, minimatch@^10.0.3: + version "10.0.3" + resolved "https://registry.yarnpkg.com/minimatch/-/minimatch-10.0.3.tgz#cf7a0314a16c4d9ab73a7730a0e8e3c3502d47aa" + integrity sha512-IPZ167aShDZZUMdRk66cyQAW3qr0WzbHkPdMYa8bzZhlHhO3jALbKdxcaak7W9FfT2rZNpQuUu4Od7ILEpXSaw== dependencies: - brace-expansion "^2.0.1" + "@isaacs/brace-expansion" "^5.0.0" minimatch@^7.4.1: version "7.4.6" @@ -22877,11 +22915,6 @@ node-cron@^3.0.3: dependencies: uuid "8.3.2" -node-domexception@^1.0.0: - version "1.0.0" - resolved "https://registry.yarnpkg.com/node-domexception/-/node-domexception-1.0.0.tgz#6888db46a1f71c0b76b3f7555016b63fe64766e5" - integrity sha512-/jKZoMpw0F8GRwl4/eLROPA3cfcXtLApP0QzLmUT/HuPCZWyB7IY9ZrMeKw2O/nFIqPQB3PVM9aYm0F312AXDQ== - node-fetch-native@^1.4.0, node-fetch-native@^1.6.3, node-fetch-native@^1.6.4, node-fetch-native@^1.6.6: version "1.6.6" resolved "https://registry.yarnpkg.com/node-fetch-native/-/node-fetch-native-1.6.6.tgz#ae1d0e537af35c2c0b0de81cbff37eedd410aa37" @@ -28567,7 +28600,6 @@ stylus@0.59.0, stylus@^0.59.0: sucrase@^3.27.0, sucrase@^3.35.0, sucrase@getsentry/sucrase#es2020-polyfills: version "3.36.0" - uid fd682f6129e507c00bb4e6319cc5d6b767e36061 resolved "https://codeload.github.com/getsentry/sucrase/tar.gz/fd682f6129e507c00bb4e6319cc5d6b767e36061" dependencies: "@jridgewell/gen-mapping" "^0.3.2" @@ -30930,7 +30962,7 @@ web-namespaces@^2.0.0: resolved "https://registry.yarnpkg.com/web-namespaces/-/web-namespaces-2.0.1.tgz#1010ff7c650eccb2592cebeeaf9a1b253fd40692" integrity sha512-bKr1DkiNa2krS7qxNtdrtHAmzuYGFQLiQ13TsorsdT6ULTkPLKuu5+GsFpDlg6JFjUTwX2DyhMPG2be8uPrqsQ== -web-streams-polyfill@^3.0.3, web-streams-polyfill@^3.1.1: +web-streams-polyfill@^3.1.1: version "3.3.3" resolved "https://registry.yarnpkg.com/web-streams-polyfill/-/web-streams-polyfill-3.3.3.tgz#2073b91a2fdb1fbfbd401e7de0ac9f8214cecb4b" integrity sha512-d2JWLCivmZYTSIoge9MsgFCZrt571BikcWGYkjC1khllbTeDlGqZ2D8vD8E/lJa8WGWbb7Plm8/XJYV7IJHZZw==