@mui/internal-bundle-size-checker 1.0.9-canary.72 → 1.0.9-canary.73

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@mui/internal-bundle-size-checker",
3
- "version": "1.0.9-canary.72",
3
+ "version": "1.0.9-canary.73",
4
4
  "description": "Bundle size checker for MUI packages.",
5
5
  "license": "MIT",
6
6
  "type": "module",
@@ -27,8 +27,6 @@
27
27
  }
28
28
  },
29
29
  "dependencies": {
30
- "@aws-sdk/client-s3": "^3.1008.0",
31
- "@aws-sdk/credential-providers": "^3.1008.0",
32
30
  "@octokit/rest": "^22.0.1",
33
31
  "chalk": "^5.6.2",
34
32
  "env-ci": "^11.2.0",
@@ -46,7 +44,7 @@
46
44
  "@types/micromatch": "4.0.10",
47
45
  "@types/yargs": "17.0.35"
48
46
  },
49
- "gitSha": "98e99bf28bdaf246aee9618320f28e440148e844",
47
+ "gitSha": "f5e61069f527a1e0e95d5fc71428bcbae92ecb5f",
50
48
  "scripts": {
51
49
  "build": "tsgo -p tsconfig.build.json",
52
50
  "test": "pnpm -w test --project @mui/internal-bundle-size-checker",
package/src/ciReport.js CHANGED
@@ -25,7 +25,13 @@ const sizeSnapshotEntrySchema = z.object({
25
25
  gzip: z.number(),
26
26
  });
27
27
 
28
- const sizeSnapshotSchema = z.record(z.string(), sizeSnapshotEntrySchema);
28
+ const snapshotMetadataSchema = z.object({
29
+ trackedBundles: z.array(z.string()).optional(),
30
+ });
31
+
32
+ const sizeSnapshotSchema = z
33
+ .record(z.string(), sizeSnapshotEntrySchema)
34
+ .and(z.object({ _metadata: snapshotMetadataSchema }).partial());
29
35
 
30
36
  export const sizeSnapshotUploadSchema = ciReportUploadSchema(
31
37
  'size-snapshot',
package/src/cli.js CHANGED
@@ -152,10 +152,21 @@ async function run(argv) {
152
152
  console.log(`Starting bundle size snapshot creation with ${concurrency} workers...`);
153
153
 
154
154
  const bundleSizes = await getBundleSizes(argv, config);
155
+ // Get tracked bundles from config
156
+ const trackedBundles = config.entrypoints
157
+ .filter((entry) => entry.track === true)
158
+ .map((entry) => entry.id);
159
+
155
160
  const sortedBundleSizes = Object.fromEntries(
156
161
  bundleSizes.sort((a, b) => a[0].localeCompare(b[0])),
157
162
  );
158
163
 
164
+ // Add metadata with tracked bundles to the snapshot
165
+ if (trackedBundles.length > 0) {
166
+ // eslint-disable-next-line no-underscore-dangle
167
+ sortedBundleSizes._metadata = /** @type {any} */ ({ trackedBundles });
168
+ }
169
+
159
170
  // Ensure output directory exists
160
171
  await fs.mkdir(path.dirname(snapshotDestPath), { recursive: true });
161
172
  await fs.writeFile(snapshotDestPath, JSON.stringify(sortedBundleSizes, null, 2));
@@ -169,11 +180,7 @@ async function run(argv) {
169
180
  if (config && config.upload) {
170
181
  try {
171
182
  // eslint-disable-next-line no-console
172
- console.log(
173
- config.upload.legacyUpload
174
- ? 'Uploading bundle size snapshot directly to S3 (legacy)...'
175
- : 'Uploading bundle size snapshot via dashboard API...',
176
- );
183
+ console.log(`Uploading bundle size snapshot via dashboard API at ${config.upload.apiUrl}...`);
177
184
  const { key } = await uploadSnapshot(snapshotDestPath, config.upload);
178
185
  // eslint-disable-next-line no-console
179
186
  console.log(`Bundle size snapshot uploaded to S3 with key: ${key}`);
@@ -210,11 +217,6 @@ async function run(argv) {
210
217
  // eslint-disable-next-line no-console
211
218
  console.log('Syncing PR comment via dashboard API...');
212
219
 
213
- // Get tracked bundles from config
214
- const trackedBundles = config.entrypoints
215
- .filter((entry) => entry.track === true)
216
- .map((entry) => entry.id);
217
-
218
220
  const result = await syncPrComment(ciInfo.slug, {
219
221
  bundleSize: {
220
222
  status: 'complete',
@@ -80,7 +80,10 @@ export function applyUploadConfigDefaults(uploadConfig, ciInfo) {
80
80
  throw new Error('Missing required field: upload.branch. Please specify a branch name.');
81
81
  }
82
82
 
83
- const legacyUpload = uploadConfig.legacyUpload ?? false;
83
+ const apiUrl =
84
+ uploadConfig.apiUrl ||
85
+ process.env.CI_REPORT_API_URL ||
86
+ 'https://code-infra-dashboard.onrender.com';
84
87
 
85
88
  // Return the normalized config
86
89
  /** @type {NormalizedUploadConfig} */
@@ -91,7 +94,7 @@ export function applyUploadConfigDefaults(uploadConfig, ciInfo) {
91
94
  uploadConfig.isPullRequest !== undefined
92
95
  ? Boolean(uploadConfig.isPullRequest)
93
96
  : Boolean(isPr),
94
- legacyUpload,
97
+ apiUrl,
95
98
  };
96
99
 
97
100
  // Add PR number from CI environment if available
@@ -211,6 +214,11 @@ async function normalizeEntries(entries, configPath) {
211
214
  ).flat();
212
215
 
213
216
  for (const entry of result) {
217
+ if (entry.id.startsWith('_')) {
218
+ throw new Error(
219
+ `Entry id "${entry.id}" must not start with "_". Ids starting with "_" are reserved for internal metadata.`,
220
+ );
221
+ }
214
222
  if (usedIds.has(entry.id)) {
215
223
  throw new Error(`Duplicate entry id found: "${entry.id}". Entry ids must be unique.`);
216
224
  }
package/src/types.d.ts CHANGED
@@ -3,7 +3,7 @@ export interface UploadConfig {
3
3
  repo?: string; // The repository name (e.g., "mui/material-ui")
4
4
  branch?: string; // Optional branch name (defaults to current Git branch)
5
5
  isPullRequest?: boolean; // Whether this is a pull request build (defaults to CI detection)
6
- legacyUpload?: boolean; // Upload directly to S3 instead of using the dashboard API
6
+ apiUrl?: string; // Dashboard API URL (defaults to https://code-infra-dashboard.onrender.com)
7
7
  }
8
8
 
9
9
  // Normalized upload configuration where all properties are defined
@@ -12,7 +12,7 @@ export interface NormalizedUploadConfig {
12
12
  branch: string; // Branch name
13
13
  isPullRequest: boolean; // Whether this is a pull request build
14
14
  prNumber?: string; // PR number (from CI environment)
15
- legacyUpload: boolean; // Whether to use direct S3 upload
15
+ apiUrl: string; // Dashboard API URL
16
16
  }
17
17
 
18
18
  // EntryPoint types
@@ -1,7 +1,5 @@
1
1
  import fs from 'node:fs';
2
- import { S3Client, PutObjectCommand, PutObjectTaggingCommand } from '@aws-sdk/client-s3';
3
2
  import { execa } from 'execa';
4
- import { fromEnv } from '@aws-sdk/credential-providers';
5
3
 
6
4
  /**
7
5
  * @typedef {import('./types.js').NormalizedUploadConfig} NormalizedUploadConfig
@@ -16,29 +14,15 @@ async function getCurrentCommitSHA() {
16
14
  return stdout.trim();
17
15
  }
18
16
 
19
- /**
20
- * Sanitizes a string to be used as an S3 tag value
21
- * See https://docs.aws.amazon.com/AWSEC2/latest/UserGuide/Using_Tags.html#tag-restrictions
22
- * @param {string} str
23
- * @returns {string}
24
- */
25
- function sanitizeS3TagString(str) {
26
- // Replace disallowed characters with underscore
27
- const safe = str.replace(/[^a-zA-Z0-9 +\-=.:/@]+/g, '_');
28
- // Truncate to max lengths (256 for value)
29
- const maxLen = 256;
30
- return safe.length > maxLen ? safe.substring(0, maxLen) : safe;
31
- }
32
-
33
17
  /**
34
18
  * Uploads the snapshot via the dashboard API (server-side proxied to S3).
19
+ * @param {string} apiUrl - Base URL of the CI report API
35
20
  * @param {Buffer} fileContent - The file content to upload
36
21
  * @param {NormalizedUploadConfig} uploadConfig - The normalized upload configuration
37
22
  * @param {string} sha - The commit SHA
38
23
  * @returns {Promise<{key:string}>}
39
24
  */
40
- async function uploadViaApi(fileContent, uploadConfig, sha) {
41
- const apiUrl = process.env.CI_REPORT_API_URL || 'https://code-infra-dashboard.onrender.com';
25
+ async function uploadViaApi(apiUrl, fileContent, uploadConfig, sha) {
42
26
  /** @type {import('./ciReport.js').SizeSnapshotUpload} */
43
27
  const requestBody = {
44
28
  version: 1,
@@ -78,53 +62,6 @@ async function uploadViaApi(fileContent, uploadConfig, sha) {
78
62
  return { key: result.key };
79
63
  }
80
64
 
81
- /**
82
- * Uploads the snapshot directly to S3 using AWS credentials.
83
- * @param {Buffer} fileContent - The file content to upload
84
- * @param {NormalizedUploadConfig} uploadConfig - The normalized upload configuration
85
- * @param {string} sha - The commit SHA
86
- * @returns {Promise<{key:string}>}
87
- */
88
- async function uploadDirectToS3(fileContent, uploadConfig, sha) {
89
- const { branch, isPullRequest } = uploadConfig;
90
-
91
- // Create S3 client (uses AWS credentials from environment)
92
- const client = new S3Client({
93
- region: process.env.AWS_REGION_ARTIFACTS || process.env.AWS_REGION || 'eu-central-1',
94
- credentials: fromEnv(),
95
- });
96
-
97
- // S3 bucket and key
98
- const bucket = 'mui-org-ci';
99
- const key = `artifacts/${uploadConfig.repo}/${sha}/size-snapshot.json`;
100
-
101
- // Upload the file first
102
- await client.send(
103
- new PutObjectCommand({
104
- Bucket: bucket,
105
- Key: key,
106
- Body: fileContent,
107
- ContentType: 'application/json',
108
- }),
109
- );
110
-
111
- // Then add tags to the uploaded object
112
- await client.send(
113
- new PutObjectTaggingCommand({
114
- Bucket: bucket,
115
- Key: key,
116
- Tagging: {
117
- TagSet: [
118
- { Key: 'isPullRequest', Value: isPullRequest ? 'yes' : 'no' },
119
- { Key: 'branch', Value: sanitizeS3TagString(branch) },
120
- ],
121
- },
122
- }),
123
- );
124
-
125
- return { key };
126
- }
127
-
128
65
  /**
129
66
  * Uploads the size snapshot to S3
130
67
  * @param {string} snapshotPath - The path to the size snapshot JSON file
@@ -139,9 +76,5 @@ export async function uploadSnapshot(snapshotPath, uploadConfig, commitSha) {
139
76
  fs.promises.readFile(snapshotPath),
140
77
  ]);
141
78
 
142
- if (uploadConfig.legacyUpload) {
143
- return uploadDirectToS3(fileContent, uploadConfig, sha);
144
- }
145
-
146
- return uploadViaApi(fileContent, uploadConfig, sha);
79
+ return uploadViaApi(uploadConfig.apiUrl, fileContent, uploadConfig, sha);
147
80
  }