@angular/build 19.1.0-rc.0 → 19.1.1

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.
Files changed (32) hide show
  1. package/package.json +9 -9
  2. package/src/builders/application/build-action.js +27 -14
  3. package/src/builders/application/execute-build.js +4 -1
  4. package/src/builders/application/index.d.ts +4 -3
  5. package/src/builders/application/index.js +2 -1
  6. package/src/builders/application/setup-bundling.d.ts +2 -1
  7. package/src/builders/application/setup-bundling.js +2 -2
  8. package/src/builders/dev-server/index.d.ts +4 -2
  9. package/src/builders/dev-server/index.js +2 -1
  10. package/src/builders/dev-server/vite-server.d.ts +5 -1
  11. package/src/builders/dev-server/vite-server.js +30 -16
  12. package/src/builders/extract-i18n/index.d.ts +4 -2
  13. package/src/builders/extract-i18n/index.js +2 -1
  14. package/src/builders/ng-packagr/index.d.ts +4 -2
  15. package/src/builders/ng-packagr/index.js +2 -1
  16. package/src/private.d.ts +4 -7
  17. package/src/private.js +4 -1
  18. package/src/tools/esbuild/angular/compiler-plugin.d.ts +2 -4
  19. package/src/tools/esbuild/angular/compiler-plugin.js +21 -10
  20. package/src/tools/esbuild/application-code-bundle.d.ts +2 -1
  21. package/src/tools/esbuild/application-code-bundle.js +33 -26
  22. package/src/tools/esbuild/bundler-execution-result.d.ts +3 -2
  23. package/src/tools/esbuild/bundler-execution-result.js +1 -0
  24. package/src/tools/esbuild/compiler-plugin-options.js +0 -1
  25. package/src/tools/vite/middlewares/assets-middleware.d.ts +2 -2
  26. package/src/tools/vite/middlewares/assets-middleware.js +4 -4
  27. package/src/tools/vite/plugins/angular-memory-plugin.js +12 -2
  28. package/src/tools/vite/plugins/setup-middlewares-plugin.d.ts +2 -2
  29. package/src/tools/vite/utils.d.ts +3 -0
  30. package/src/utils/environment-options.js +1 -1
  31. package/src/utils/i18n-options.js +3 -3
  32. package/src/utils/normalize-cache.js +1 -1
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@angular/build",
3
- "version": "19.1.0-rc.0",
3
+ "version": "19.1.1",
4
4
  "description": "Official build system for Angular",
5
5
  "keywords": [
6
6
  "Angular CLI",
@@ -23,7 +23,7 @@
23
23
  "builders": "builders.json",
24
24
  "dependencies": {
25
25
  "@ampproject/remapping": "2.3.0",
26
- "@angular-devkit/architect": "0.1901.0-rc.0",
26
+ "@angular-devkit/architect": "0.1901.1",
27
27
  "@babel/core": "7.26.0",
28
28
  "@babel/helper-annotate-as-pure": "7.25.9",
29
29
  "@babel/helper-split-export-declaration": "7.24.7",
@@ -52,14 +52,14 @@
52
52
  "lmdb": "3.2.2"
53
53
  },
54
54
  "peerDependencies": {
55
- "@angular/compiler": "^19.0.0 || ^19.1.0-next.0",
56
- "@angular/compiler-cli": "^19.0.0 || ^19.1.0-next.0",
57
- "@angular/localize": "^19.0.0 || ^19.1.0-next.0",
58
- "@angular/platform-server": "^19.0.0 || ^19.1.0-next.0",
59
- "@angular/service-worker": "^19.0.0 || ^19.1.0-next.0",
60
- "@angular/ssr": "^19.1.0-rc.0",
55
+ "@angular/compiler": "^19.0.0",
56
+ "@angular/compiler-cli": "^19.0.0",
57
+ "@angular/localize": "^19.0.0",
58
+ "@angular/platform-server": "^19.0.0",
59
+ "@angular/service-worker": "^19.0.0",
60
+ "@angular/ssr": "^19.1.1",
61
61
  "less": "^4.2.0",
62
- "ng-packagr": "^19.0.0 || ^19.1.0-next.0",
62
+ "ng-packagr": "^19.0.0",
63
63
  "postcss": "^8.4.0",
64
64
  "tailwindcss": "^2.0.0 || ^3.0.0",
65
65
  "typescript": ">=5.5 <5.8"
@@ -164,7 +164,7 @@ async function* runEsBuildBuildAction(action, options) {
164
164
  if (staleWatchFiles?.size) {
165
165
  watcher.remove([...staleWatchFiles]);
166
166
  }
167
- for (const outputResult of emitOutputResults(result, outputOptions, incrementalResults ? rebuildState.previousOutputInfo : undefined)) {
167
+ for (const outputResult of emitOutputResults(result, outputOptions, changes, incrementalResults ? rebuildState : undefined)) {
168
168
  yield outputResult;
169
169
  }
170
170
  }
@@ -175,7 +175,7 @@ async function* runEsBuildBuildAction(action, options) {
175
175
  (0, sass_language_1.shutdownSassWorkerPool)();
176
176
  }
177
177
  }
178
- function* emitOutputResults({ outputFiles, assetFiles, errors, warnings, externalMetadata, htmlIndexPath, htmlBaseHref, templateUpdates, }, outputOptions, previousOutputInfo) {
178
+ function* emitOutputResults({ outputFiles, assetFiles, errors, warnings, externalMetadata, htmlIndexPath, htmlBaseHref, templateUpdates, }, outputOptions, changes, rebuildState) {
179
179
  if (errors.length > 0) {
180
180
  yield {
181
181
  kind: results_1.ResultKind.Failure,
@@ -201,7 +201,8 @@ function* emitOutputResults({ outputFiles, assetFiles, errors, warnings, externa
201
201
  yield updateResult;
202
202
  }
203
203
  // Use an incremental result if previous output information is available
204
- if (previousOutputInfo) {
204
+ if (rebuildState && changes) {
205
+ const { previousAssetsInfo, previousOutputInfo } = rebuildState;
205
206
  const incrementalResult = {
206
207
  kind: results_1.ResultKind.Incremental,
207
208
  warnings: warnings,
@@ -245,21 +246,33 @@ function* emitOutputResults({ outputFiles, assetFiles, errors, warnings, externa
245
246
  };
246
247
  }
247
248
  }
248
- // Include the removed output files
249
- incrementalResult.removed.push(...Array.from(removedOutputFiles, ([file, { type }]) => ({
250
- path: file,
251
- type,
252
- })));
253
- // Always consider asset files as added to ensure new/modified assets are available.
254
- // TODO: Consider more comprehensive asset analysis.
255
- for (const file of assetFiles) {
256
- incrementalResult.added.push(file.destination);
257
- incrementalResult.files[file.destination] = {
249
+ // Initially assume all previous assets files have been removed
250
+ const removedAssetFiles = new Map(previousAssetsInfo);
251
+ for (const { source, destination } of assetFiles) {
252
+ removedAssetFiles.delete(source);
253
+ if (!previousAssetsInfo.has(source)) {
254
+ incrementalResult.added.push(destination);
255
+ }
256
+ else if (changes.modified.has(source)) {
257
+ incrementalResult.modified.push(destination);
258
+ }
259
+ else {
260
+ continue;
261
+ }
262
+ incrementalResult.files[destination] = {
258
263
  type: bundler_context_1.BuildOutputFileType.Browser,
259
- inputPath: file.source,
264
+ inputPath: source,
260
265
  origin: 'disk',
261
266
  };
262
267
  }
268
+ // Include the removed output and asset files
269
+ incrementalResult.removed.push(...Array.from(removedOutputFiles, ([file, { type }]) => ({
270
+ path: file,
271
+ type,
272
+ })), ...Array.from(removedAssetFiles.values(), (file) => ({
273
+ path: file,
274
+ type: bundler_context_1.BuildOutputFileType.Browser,
275
+ })));
263
276
  yield incrementalResult;
264
277
  return;
265
278
  }
@@ -41,6 +41,7 @@ var __importStar = (this && this.__importStar) || (function () {
41
41
  })();
42
42
  Object.defineProperty(exports, "__esModule", { value: true });
43
43
  exports.executeBuild = executeBuild;
44
+ const compilation_1 = require("../../tools/angular/compilation");
44
45
  const source_file_cache_1 = require("../../tools/esbuild/angular/source-file-cache");
45
46
  const budget_stats_1 = require("../../tools/esbuild/budget-stats");
46
47
  const bundler_context_1 = require("../../tools/esbuild/bundler-context");
@@ -102,7 +103,9 @@ async function executeBuild(options, context, rebuildState) {
102
103
  if (options.templateUpdates) {
103
104
  templateUpdates = new Map();
104
105
  }
105
- bundlerContexts = (0, setup_bundling_1.setupBundlerContexts)(options, target, codeBundleCache, componentStyleBundler, templateUpdates);
106
+ bundlerContexts = (0, setup_bundling_1.setupBundlerContexts)(options, target, codeBundleCache, componentStyleBundler,
107
+ // Create new reusable compilation for the appropriate mode based on the `jit` plugin option
108
+ await (0, compilation_1.createAngularCompilation)(!!options.jit, !options.serverEntryPoint), templateUpdates);
106
109
  // Bundle everything on initial build
107
110
  bundlingResult = await bundler_context_1.BundlerContext.bundleAll([
108
111
  ...bundlerContexts.typescriptContexts,
@@ -5,7 +5,8 @@
5
5
  * Use of this source code is governed by an MIT-style license that can be
6
6
  * found in the LICENSE file at https://angular.dev/license
7
7
  */
8
- import { BuilderContext, BuilderOutput } from '@angular-devkit/architect';
8
+ import { Builder, BuilderContext, BuilderOutput } from '@angular-devkit/architect';
9
+ import { json } from '@angular-devkit/core';
9
10
  import { ApplicationBuilderExtensions, ApplicationBuilderInternalOptions } from './options';
10
11
  import { Result } from './results';
11
12
  import { Schema as ApplicationBuilderOptions } from './schema';
@@ -28,5 +29,5 @@ export declare function buildApplicationInternal(options: ApplicationBuilderInte
28
29
  * @returns The build output results of the build.
29
30
  */
30
31
  export declare function buildApplication(options: ApplicationBuilderOptions, context: BuilderContext, extensions?: ApplicationBuilderExtensions): AsyncIterable<BuilderOutput>;
31
- declare const _default: import("../../../../../angular_devkit/architect/src/internal").Builder<ApplicationBuilderOptions & import("../../../../../angular_devkit/core").JsonObject>;
32
- export default _default;
32
+ declare const builder: Builder<ApplicationBuilderOptions & json.JsonObject>;
33
+ export default builder;
@@ -196,4 +196,5 @@ function generateFullPath(filePath, type, outputOptions) {
196
196
  const fullFilePath = node_path_1.default.join(outputOptions.base, typeDirectory, filePath);
197
197
  return fullFilePath;
198
198
  }
199
- exports.default = (0, architect_1.createBuilder)(buildApplication);
199
+ const builder = (0, architect_1.createBuilder)(buildApplication);
200
+ exports.default = builder;
@@ -5,6 +5,7 @@
5
5
  * Use of this source code is governed by an MIT-style license that can be
6
6
  * found in the LICENSE file at https://angular.dev/license
7
7
  */
8
+ import { AngularCompilation } from '../../tools/angular/compilation';
8
9
  import { ComponentStylesheetBundler } from '../../tools/esbuild/angular/component-stylesheets';
9
10
  import { SourceFileCache } from '../../tools/esbuild/angular/source-file-cache';
10
11
  import { BundlerContext } from '../../tools/esbuild/bundler-context';
@@ -17,7 +18,7 @@ import { NormalizedApplicationBuildOptions } from './options';
17
18
  * @param codeBundleCache An instance of the TypeScript source file cache.
18
19
  * @returns An array of BundlerContext objects.
19
20
  */
20
- export declare function setupBundlerContexts(options: NormalizedApplicationBuildOptions, target: string[], codeBundleCache: SourceFileCache, stylesheetBundler: ComponentStylesheetBundler, templateUpdates: Map<string, string> | undefined): {
21
+ export declare function setupBundlerContexts(options: NormalizedApplicationBuildOptions, target: string[], codeBundleCache: SourceFileCache, stylesheetBundler: ComponentStylesheetBundler, angularCompilation: AngularCompilation, templateUpdates: Map<string, string> | undefined): {
21
22
  typescriptContexts: BundlerContext[];
22
23
  otherContexts: BundlerContext[];
23
24
  };
@@ -23,12 +23,12 @@ const utils_1 = require("../../tools/esbuild/utils");
23
23
  * @param codeBundleCache An instance of the TypeScript source file cache.
24
24
  * @returns An array of BundlerContext objects.
25
25
  */
26
- function setupBundlerContexts(options, target, codeBundleCache, stylesheetBundler, templateUpdates) {
26
+ function setupBundlerContexts(options, target, codeBundleCache, stylesheetBundler, angularCompilation, templateUpdates) {
27
27
  const { outputMode, serverEntryPoint, appShellOptions, prerenderOptions, ssrOptions, workspaceRoot, watch = false, } = options;
28
28
  const typescriptContexts = [];
29
29
  const otherContexts = [];
30
30
  // Browser application code
31
- typescriptContexts.push(new bundler_context_1.BundlerContext(workspaceRoot, watch, (0, application_code_bundle_1.createBrowserCodeBundleOptions)(options, target, codeBundleCache, stylesheetBundler, templateUpdates)));
31
+ typescriptContexts.push(new bundler_context_1.BundlerContext(workspaceRoot, watch, (0, application_code_bundle_1.createBrowserCodeBundleOptions)(options, target, codeBundleCache, stylesheetBundler, angularCompilation, templateUpdates)));
32
32
  // Browser polyfills code
33
33
  const browserPolyfillBundleOptions = (0, application_code_bundle_1.createBrowserPolyfillBundleOptions)(options, target, codeBundleCache, stylesheetBundler);
34
34
  if (browserPolyfillBundleOptions) {
@@ -5,10 +5,12 @@
5
5
  * Use of this source code is governed by an MIT-style license that can be
6
6
  * found in the LICENSE file at https://angular.dev/license
7
7
  */
8
+ import { Builder } from '@angular-devkit/architect';
9
+ import { json } from '@angular-devkit/core';
8
10
  import { execute } from './builder';
9
11
  import type { DevServerBuilderOutput } from './output';
10
12
  import type { Schema as DevServerBuilderOptions } from './schema';
11
13
  export { type DevServerBuilderOptions, type DevServerBuilderOutput, execute as executeDevServerBuilder, };
12
- declare const _default: import("../../../../../angular_devkit/architect/src/internal").Builder<DevServerBuilderOptions & import("../../../../../angular_devkit/core").JsonObject>;
13
- export default _default;
14
+ declare const builder: Builder<DevServerBuilderOptions & json.JsonObject>;
15
+ export default builder;
14
16
  export { execute as executeDevServer };
@@ -12,4 +12,5 @@ const architect_1 = require("@angular-devkit/architect");
12
12
  const builder_1 = require("./builder");
13
13
  Object.defineProperty(exports, "executeDevServerBuilder", { enumerable: true, get: function () { return builder_1.execute; } });
14
14
  Object.defineProperty(exports, "executeDevServer", { enumerable: true, get: function () { return builder_1.execute; } });
15
- exports.default = (0, architect_1.createBuilder)(builder_1.execute);
15
+ const builder = (0, architect_1.createBuilder)(builder_1.execute);
16
+ exports.default = builder;
@@ -23,6 +23,10 @@ interface OutputFileRecord {
23
23
  servable: boolean;
24
24
  type: BuildOutputFileType;
25
25
  }
26
+ interface OutputAssetRecord {
27
+ source: string;
28
+ updated: boolean;
29
+ }
26
30
  interface DevServerExternalResultMetadata extends Omit<ExternalResultMetadata, 'explicit'> {
27
31
  explicitBrowser: string[];
28
32
  explicitServer: string[];
@@ -34,5 +38,5 @@ export declare function serveWithVite(serverOptions: NormalizedDevServerOptions,
34
38
  middleware?: Connect.NextHandleFunction[];
35
39
  buildPlugins?: Plugin[];
36
40
  }): AsyncIterableIterator<DevServerBuilderOutput>;
37
- export declare function setupServer(serverOptions: NormalizedDevServerOptions, outputFiles: Map<string, OutputFileRecord>, assets: Map<string, string>, preserveSymlinks: boolean | undefined, externalMetadata: DevServerExternalResultMetadata, ssrMode: ServerSsrMode, prebundleTransformer: JavaScriptTransformer, target: string[], zoneless: boolean, componentStyles: Map<string, ComponentStyleRecord>, templateUpdates: Map<string, string>, prebundleLoaderExtensions: EsbuildLoaderOption | undefined, define: ApplicationBuilderInternalOptions['define'], extensionMiddleware?: Connect.NextHandleFunction[], indexHtmlTransformer?: (content: string) => Promise<string>, thirdPartySourcemaps?: boolean): Promise<InlineConfig>;
41
+ export declare function setupServer(serverOptions: NormalizedDevServerOptions, outputFiles: Map<string, OutputFileRecord>, assets: Map<string, OutputAssetRecord>, preserveSymlinks: boolean | undefined, externalMetadata: DevServerExternalResultMetadata, ssrMode: ServerSsrMode, prebundleTransformer: JavaScriptTransformer, target: string[], zoneless: boolean, componentStyles: Map<string, ComponentStyleRecord>, templateUpdates: Map<string, string>, prebundleLoaderExtensions: EsbuildLoaderOption | undefined, define: ApplicationBuilderInternalOptions['define'], extensionMiddleware?: Connect.NextHandleFunction[], indexHtmlTransformer?: (content: string) => Promise<string>, thirdPartySourcemaps?: boolean): Promise<InlineConfig>;
38
42
  export {};
@@ -103,7 +103,7 @@ async function* serveWithVite(serverOptions, builderName, builderAction, context
103
103
  // https://nodejs.org/api/process.html#processsetsourcemapsenabledval
104
104
  process.setSourceMapsEnabled(true);
105
105
  }
106
- // Enable to support link-based component style hot reloading (`NG_HMR_CSTYLES=0` can be used to disable selectively)
106
+ // Enable to support link-based component style hot reloading (`NG_HMR_CSTYLES=1` can be used to enable)
107
107
  browserOptions.externalRuntimeStyles =
108
108
  serverOptions.liveReload && serverOptions.hmr && environment_options_1.useComponentStyleHmr;
109
109
  // Enable to support component template hot replacement (`NG_HMR_TEMPLATE=0` can be used to disable selectively)
@@ -182,13 +182,8 @@ async function* serveWithVite(serverOptions, builderName, builderAction, context
182
182
  assetFiles.clear();
183
183
  componentStyles.clear();
184
184
  generatedFiles.clear();
185
- for (const entry of Object.entries(result.files)) {
186
- const [outputPath, file] = entry;
187
- if (file.origin === 'disk') {
188
- assetFiles.set('/' + normalizePath(outputPath), normalizePath(file.inputPath));
189
- continue;
190
- }
191
- updateResultRecord(outputPath, file, normalizePath, htmlIndexPath, generatedFiles, componentStyles,
185
+ for (const [outputPath, file] of Object.entries(result.files)) {
186
+ updateResultRecord(outputPath, file, normalizePath, htmlIndexPath, generatedFiles, assetFiles, componentStyles,
192
187
  // The initial build will not yet have a server setup
193
188
  !server);
194
189
  }
@@ -207,10 +202,10 @@ async function* serveWithVite(serverOptions, builderName, builderAction, context
207
202
  assetFiles.delete(filePath);
208
203
  }
209
204
  for (const modified of result.modified) {
210
- updateResultRecord(modified, result.files[modified], normalizePath, htmlIndexPath, generatedFiles, componentStyles);
205
+ updateResultRecord(modified, result.files[modified], normalizePath, htmlIndexPath, generatedFiles, assetFiles, componentStyles);
211
206
  }
212
207
  for (const added of result.added) {
213
- updateResultRecord(added, result.files[added], normalizePath, htmlIndexPath, generatedFiles, componentStyles);
208
+ updateResultRecord(added, result.files[added], normalizePath, htmlIndexPath, generatedFiles, assetFiles, componentStyles);
214
209
  }
215
210
  break;
216
211
  case results_1.ResultKind.ComponentUpdate:
@@ -262,9 +257,12 @@ async function* serveWithVite(serverOptions, builderName, builderAction, context
262
257
  if (server) {
263
258
  // Update fs allow list to include any new assets from the build option.
264
259
  server.config.server.fs.allow = [
265
- ...new Set([...server.config.server.fs.allow, ...assetFiles.values()]),
260
+ ...new Set([
261
+ ...server.config.server.fs.allow,
262
+ ...[...assetFiles.values()].map(({ source }) => source),
263
+ ]),
266
264
  ];
267
- await handleUpdate(normalizePath, generatedFiles, server, serverOptions, context.logger, componentStyles);
265
+ await handleUpdate(normalizePath, generatedFiles, assetFiles, server, serverOptions, context.logger, componentStyles);
268
266
  }
269
267
  else {
270
268
  const projectName = context.target?.project;
@@ -337,10 +335,18 @@ async function* serveWithVite(serverOptions, builderName, builderAction, context
337
335
  }
338
336
  await new Promise((resolve) => (deferred = resolve));
339
337
  }
340
- async function handleUpdate(normalizePath, generatedFiles, server, serverOptions, logger, componentStyles) {
338
+ async function handleUpdate(normalizePath, generatedFiles, assetFiles, server, serverOptions, logger, componentStyles) {
341
339
  const updatedFiles = [];
342
- let destroyAngularServerAppCalled = false;
340
+ // Invalidate any updated asset
341
+ for (const [file, record] of assetFiles) {
342
+ if (!record.updated) {
343
+ continue;
344
+ }
345
+ record.updated = false;
346
+ updatedFiles.push(file);
347
+ }
343
348
  // Invalidate any updated files
349
+ let destroyAngularServerAppCalled = false;
344
350
  for (const [file, record] of generatedFiles) {
345
351
  if (!record.updated) {
346
352
  continue;
@@ -419,8 +425,12 @@ async function handleUpdate(normalizePath, generatedFiles, server, serverOptions
419
425
  logger.info('Page reload sent to client(s).');
420
426
  }
421
427
  }
422
- function updateResultRecord(outputPath, file, normalizePath, htmlIndexPath, generatedFiles, componentStyles, initial = false) {
428
+ function updateResultRecord(outputPath, file, normalizePath, htmlIndexPath, generatedFiles, assetFiles, componentStyles, initial = false) {
423
429
  if (file.origin === 'disk') {
430
+ assetFiles.set('/' + normalizePath(outputPath), {
431
+ source: normalizePath(file.inputPath),
432
+ updated: !initial,
433
+ });
424
434
  return;
425
435
  }
426
436
  let filePath;
@@ -542,7 +552,11 @@ async function setupServer(serverOptions, outputFiles, assets, preserveSymlinks,
542
552
  // The first two are required for Vite to function in prebundling mode (the default) and to load
543
553
  // the Vite client-side code for browser reloading. These would be available by default but when
544
554
  // the `allow` option is explicitly configured, they must be included manually.
545
- allow: [cacheDir, (0, node_path_1.join)(serverOptions.workspaceRoot, 'node_modules'), ...assets.values()],
555
+ allow: [
556
+ cacheDir,
557
+ (0, node_path_1.join)(serverOptions.workspaceRoot, 'node_modules'),
558
+ ...[...assets.values()].map(({ source }) => source),
559
+ ],
546
560
  },
547
561
  // This is needed when `externalDependencies` is used to prevent Vite load errors.
548
562
  // NOTE: If Vite adds direct support for externals, this can be removed.
@@ -5,8 +5,10 @@
5
5
  * Use of this source code is governed by an MIT-style license that can be
6
6
  * found in the LICENSE file at https://angular.dev/license
7
7
  */
8
+ import { Builder } from '@angular-devkit/architect';
9
+ import { json } from '@angular-devkit/core';
8
10
  import { execute } from './builder';
9
11
  import type { Schema as ExtractI18nBuilderOptions } from './schema';
10
12
  export { ExtractI18nBuilderOptions, execute };
11
- declare const _default: import("../../../../../angular_devkit/architect/src/internal").Builder<ExtractI18nBuilderOptions & import("../../../../../angular_devkit/core").JsonObject>;
12
- export default _default;
13
+ declare const builder: Builder<ExtractI18nBuilderOptions & json.JsonObject>;
14
+ export default builder;
@@ -11,4 +11,5 @@ exports.execute = void 0;
11
11
  const architect_1 = require("@angular-devkit/architect");
12
12
  const builder_1 = require("./builder");
13
13
  Object.defineProperty(exports, "execute", { enumerable: true, get: function () { return builder_1.execute; } });
14
- exports.default = (0, architect_1.createBuilder)(builder_1.execute);
14
+ const builder = (0, architect_1.createBuilder)(builder_1.execute);
15
+ exports.default = builder;
@@ -5,8 +5,10 @@
5
5
  * Use of this source code is governed by an MIT-style license that can be
6
6
  * found in the LICENSE file at https://angular.dev/license
7
7
  */
8
+ import { Builder } from '@angular-devkit/architect';
9
+ import { json } from '@angular-devkit/core';
8
10
  import { execute } from './builder';
9
11
  import type { Schema as NgPackagrBuilderOptions } from './schema';
10
12
  export { type NgPackagrBuilderOptions, execute };
11
- declare const _default: import("../../../../../angular_devkit/architect/src/internal").Builder<NgPackagrBuilderOptions & import("../../../../../angular_devkit/core").JsonObject>;
12
- export default _default;
13
+ declare const builder: Builder<NgPackagrBuilderOptions & json.JsonObject>;
14
+ export default builder;
@@ -11,4 +11,5 @@ exports.execute = void 0;
11
11
  const architect_1 = require("@angular-devkit/architect");
12
12
  const builder_1 = require("./builder");
13
13
  Object.defineProperty(exports, "execute", { enumerable: true, get: function () { return builder_1.execute; } });
14
- exports.default = (0, architect_1.createBuilder)(builder_1.execute);
14
+ const builder = (0, architect_1.createBuilder)(builder_1.execute);
15
+ exports.default = builder;
package/src/private.d.ts CHANGED
@@ -5,12 +5,6 @@
5
5
  * Use of this source code is governed by an MIT-style license that can be
6
6
  * found in the LICENSE file at https://angular.dev/license
7
7
  */
8
- /**
9
- * @fileoverview
10
- * Private exports intended only for use with the @angular-devkit/build-angular package.
11
- * All exports are not supported for external use, do not provide SemVer guarantees, and
12
- * their existence may change in any future version.
13
- */
14
8
  import { CompilerPluginOptions } from './tools/esbuild/angular/compiler-plugin';
15
9
  import { BundleStylesheetOptions } from './tools/esbuild/stylesheets/bundle-options';
16
10
  export { buildApplicationInternal } from './builders/application';
@@ -25,7 +19,10 @@ export { SassWorkerImplementation } from './tools/sass/sass-service';
25
19
  export { SourceFileCache } from './tools/esbuild/angular/source-file-cache';
26
20
  export { createJitResourceTransformer } from './tools/angular/transformers/jit-resource-transformer';
27
21
  export { JavaScriptTransformer } from './tools/esbuild/javascript-transformer';
28
- export declare function createCompilerPlugin(pluginOptions: CompilerPluginOptions, styleOptions: BundleStylesheetOptions & {
22
+ export declare function createCompilerPlugin(pluginOptions: CompilerPluginOptions & {
23
+ browserOnlyBuild?: boolean;
24
+ noopTypeScriptCompilation?: boolean;
25
+ }, styleOptions: BundleStylesheetOptions & {
29
26
  inlineStyleLanguage: string;
30
27
  }): import('esbuild').Plugin;
31
28
  export * from './utils/bundle-calculator';
package/src/private.js CHANGED
@@ -29,6 +29,7 @@ exports.createCompilerPlugin = createCompilerPlugin;
29
29
  * All exports are not supported for external use, do not provide SemVer guarantees, and
30
30
  * their existence may change in any future version.
31
31
  */
32
+ const compilation_1 = require("./tools/angular/compilation");
32
33
  const compiler_plugin_1 = require("./tools/esbuild/angular/compiler-plugin");
33
34
  const component_stylesheets_1 = require("./tools/esbuild/angular/component-stylesheets");
34
35
  // Builders
@@ -53,7 +54,9 @@ Object.defineProperty(exports, "createJitResourceTransformer", { enumerable: tru
53
54
  var javascript_transformer_1 = require("./tools/esbuild/javascript-transformer");
54
55
  Object.defineProperty(exports, "JavaScriptTransformer", { enumerable: true, get: function () { return javascript_transformer_1.JavaScriptTransformer; } });
55
56
  function createCompilerPlugin(pluginOptions, styleOptions) {
56
- return (0, compiler_plugin_1.createCompilerPlugin)(pluginOptions, new component_stylesheets_1.ComponentStylesheetBundler(styleOptions, styleOptions.inlineStyleLanguage, pluginOptions.incremental));
57
+ return (0, compiler_plugin_1.createCompilerPlugin)(pluginOptions, pluginOptions.noopTypeScriptCompilation
58
+ ? new compilation_1.NoopCompilation()
59
+ : () => (0, compilation_1.createAngularCompilation)(!!pluginOptions.jit, !!pluginOptions.browserOnlyBuild), new component_stylesheets_1.ComponentStylesheetBundler(styleOptions, styleOptions.inlineStyleLanguage, pluginOptions.incremental));
57
60
  }
58
61
  // Utilities
59
62
  __exportStar(require("./utils/bundle-calculator"), exports);
@@ -6,6 +6,7 @@
6
6
  * found in the LICENSE file at https://angular.dev/license
7
7
  */
8
8
  import type { Plugin } from 'esbuild';
9
+ import { AngularCompilation } from '../../angular/compilation';
9
10
  import { LoadResultCache } from '../load-result-cache';
10
11
  import { ComponentStylesheetBundler } from './component-stylesheets';
11
12
  import { SourceFileCache } from './source-file-cache';
@@ -13,9 +14,6 @@ export interface CompilerPluginOptions {
13
14
  sourcemap: boolean | 'external';
14
15
  tsconfig: string;
15
16
  jit?: boolean;
16
- browserOnlyBuild?: boolean;
17
- /** Skip TypeScript compilation setup. This is useful to re-use the TypeScript compilation from another plugin. */
18
- noopTypeScriptCompilation?: boolean;
19
17
  advancedOptimizations?: boolean;
20
18
  thirdPartySourcemaps?: boolean;
21
19
  fileReplacements?: Record<string, string>;
@@ -26,4 +24,4 @@ export interface CompilerPluginOptions {
26
24
  instrumentForCoverage?: (request: string) => boolean;
27
25
  templateUpdates?: Map<string, string>;
28
26
  }
29
- export declare function createCompilerPlugin(pluginOptions: CompilerPluginOptions, stylesheetBundler: ComponentStylesheetBundler): Plugin;
27
+ export declare function createCompilerPlugin(pluginOptions: CompilerPluginOptions, compilationOrFactory: AngularCompilation | (() => Promise<AngularCompilation>), stylesheetBundler: ComponentStylesheetBundler): Plugin;
@@ -56,7 +56,7 @@ const compilation_state_1 = require("./compilation-state");
56
56
  const file_reference_tracker_1 = require("./file-reference-tracker");
57
57
  const jit_plugin_callbacks_1 = require("./jit-plugin-callbacks");
58
58
  // eslint-disable-next-line max-lines-per-function
59
- function createCompilerPlugin(pluginOptions, stylesheetBundler) {
59
+ function createCompilerPlugin(pluginOptions, compilationOrFactory, stylesheetBundler) {
60
60
  return {
61
61
  name: 'angular-compiler',
62
62
  // eslint-disable-next-line max-lines-per-function
@@ -94,16 +94,17 @@ function createCompilerPlugin(pluginOptions, stylesheetBundler) {
94
94
  // Setup defines based on the values used by the Angular compiler-cli
95
95
  build.initialOptions.define ??= {};
96
96
  build.initialOptions.define['ngI18nClosureMode'] ??= 'false';
97
+ // The factory is only relevant for compatibility purposes with the private API.
98
+ // TODO: Update private API in the next major to allow compilation function factory removal here.
99
+ const compilation = typeof compilationOrFactory === 'function'
100
+ ? await compilationOrFactory()
101
+ : compilationOrFactory;
97
102
  // The in-memory cache of TypeScript file outputs will be used during the build in `onLoad` callbacks for TS files.
98
103
  // A string value indicates direct TS/NG output and a Uint8Array indicates fully transformed code.
99
104
  const typeScriptFileCache = pluginOptions.sourceFileCache?.typeScriptFileCache ??
100
105
  new Map();
101
106
  // The resources from component stylesheets and web workers that will be added to the build results output files
102
107
  const additionalResults = new Map();
103
- // Create new reusable compilation for the appropriate mode based on the `jit` plugin option
104
- const compilation = pluginOptions.noopTypeScriptCompilation
105
- ? new compilation_1.NoopCompilation()
106
- : await (0, compilation_1.createAngularCompilation)(!!pluginOptions.jit, !!pluginOptions.browserOnlyBuild);
107
108
  // Compilation is initially assumed to have errors until emitted
108
109
  let hasCompilationErrors = true;
109
110
  // Determines if TypeScript should process JavaScript files based on tsconfig `allowJs` option
@@ -128,8 +129,8 @@ function createCompilerPlugin(pluginOptions, stylesheetBundler) {
128
129
  // Angular compiler which does not have direct knowledge of transitive resource
129
130
  // dependencies or web worker processing.
130
131
  let modifiedFiles;
131
- if (pluginOptions.sourceFileCache?.modifiedFiles.size &&
132
- !pluginOptions.noopTypeScriptCompilation) {
132
+ if (!(compilation instanceof compilation_1.NoopCompilation) &&
133
+ pluginOptions.sourceFileCache?.modifiedFiles.size) {
133
134
  // TODO: Differentiate between changed input files and stale output files
134
135
  modifiedFiles = referencedFileTracker.update(pluginOptions.sourceFileCache.modifiedFiles);
135
136
  pluginOptions.sourceFileCache.invalidate(modifiedFiles);
@@ -141,9 +142,7 @@ function createCompilerPlugin(pluginOptions, stylesheetBundler) {
141
142
  // Remove any stale additional results based on modified files
142
143
  modifiedFiles.forEach((file) => additionalResults.delete(file));
143
144
  }
144
- if (!pluginOptions.noopTypeScriptCompilation &&
145
- compilation.update &&
146
- pluginOptions.sourceFileCache?.modifiedFiles.size) {
145
+ if (compilation.update && pluginOptions.sourceFileCache?.modifiedFiles.size) {
147
146
  await compilation.update(modifiedFiles ?? pluginOptions.sourceFileCache.modifiedFiles);
148
147
  }
149
148
  // Create Angular compiler host options
@@ -523,6 +522,18 @@ function createCompilerOptionsTransformer(setupWarnings, pluginOptions, preserve
523
522
  notes: [{ text: `The 'module' option will be set to 'ES2022' instead.` }],
524
523
  });
525
524
  }
525
+ if (compilerOptions.isolatedModules && compilerOptions.emitDecoratorMetadata) {
526
+ setupWarnings?.push({
527
+ text: `TypeScript compiler option 'isolatedModules' may prevent the 'emitDecoratorMetadata' option from emitting all metadata.`,
528
+ location: null,
529
+ notes: [
530
+ {
531
+ text: `The 'emitDecoratorMetadata' option is not required by Angular` +
532
+ 'and can be removed if not explictly required by the project.',
533
+ },
534
+ ],
535
+ });
536
+ }
526
537
  // Synchronize custom resolve conditions.
527
538
  // Set if using the supported bundler resolution mode (bundler is the default in new projects)
528
539
  if (compilerOptions.moduleResolution === 100 /* ModuleResolutionKind.Bundler */) {
@@ -7,11 +7,12 @@
7
7
  */
8
8
  import type { BuildOptions } from 'esbuild';
9
9
  import type { NormalizedApplicationBuildOptions } from '../../builders/application/options';
10
+ import { AngularCompilation } from '../angular/compilation';
10
11
  import { ComponentStylesheetBundler } from './angular/component-stylesheets';
11
12
  import { SourceFileCache } from './angular/source-file-cache';
12
13
  import { BundlerOptionsFactory } from './bundler-context';
13
14
  import type { LoadResultCache } from './load-result-cache';
14
- export declare function createBrowserCodeBundleOptions(options: NormalizedApplicationBuildOptions, target: string[], sourceFileCache: SourceFileCache, stylesheetBundler: ComponentStylesheetBundler, templateUpdates: Map<string, string> | undefined): BundlerOptionsFactory;
15
+ export declare function createBrowserCodeBundleOptions(options: NormalizedApplicationBuildOptions, target: string[], sourceFileCache: SourceFileCache, stylesheetBundler: ComponentStylesheetBundler, angularCompilation: AngularCompilation, templateUpdates: Map<string, string> | undefined): BundlerOptionsFactory;
15
16
  export declare function createBrowserPolyfillBundleOptions(options: NormalizedApplicationBuildOptions, target: string[], sourceFileCache: SourceFileCache, stylesheetBundler: ComponentStylesheetBundler): BuildOptions | BundlerOptionsFactory | undefined;
16
17
  export declare function createServerPolyfillBundleOptions(options: NormalizedApplicationBuildOptions, target: string[], loadResultCache: LoadResultCache | undefined): BundlerOptionsFactory | undefined;
17
18
  export declare function createServerMainCodeBundleOptions(options: NormalizedApplicationBuildOptions, target: string[], sourceFileCache: SourceFileCache, stylesheetBundler: ComponentStylesheetBundler): BundlerOptionsFactory;
@@ -21,6 +21,7 @@ const node_path_1 = require("node:path");
21
21
  const schema_1 = require("../../builders/application/schema");
22
22
  const environment_options_1 = require("../../utils/environment-options");
23
23
  const manifest_1 = require("../../utils/server-rendering/manifest");
24
+ const compilation_1 = require("../angular/compilation");
24
25
  const compiler_plugin_1 = require("./angular/compiler-plugin");
25
26
  const angular_localize_init_warning_plugin_1 = require("./angular-localize-init-warning-plugin");
26
27
  const compiler_plugin_options_1 = require("./compiler-plugin-options");
@@ -33,7 +34,7 @@ const sourcemap_ignorelist_plugin_1 = require("./sourcemap-ignorelist-plugin");
33
34
  const utils_1 = require("./utils");
34
35
  const virtual_module_plugin_1 = require("./virtual-module-plugin");
35
36
  const wasm_plugin_1 = require("./wasm-plugin");
36
- function createBrowserCodeBundleOptions(options, target, sourceFileCache, stylesheetBundler, templateUpdates) {
37
+ function createBrowserCodeBundleOptions(options, target, sourceFileCache, stylesheetBundler, angularCompilation, templateUpdates) {
37
38
  return (loadCache) => {
38
39
  const { entryPoints, outputNames, polyfills } = options;
39
40
  const pluginOptions = (0, compiler_plugin_options_1.createCompilerPluginOptions)(options, sourceFileCache, loadCache, templateUpdates);
@@ -57,7 +58,7 @@ function createBrowserCodeBundleOptions(options, target, sourceFileCache, styles
57
58
  (0, angular_localize_init_warning_plugin_1.createAngularLocalizeInitWarningPlugin)(),
58
59
  (0, compiler_plugin_1.createCompilerPlugin)(
59
60
  // JS/TS options
60
- pluginOptions,
61
+ pluginOptions, angularCompilation,
61
62
  // Component stylesheet bundler
62
63
  stylesheetBundler),
63
64
  ],
@@ -65,19 +66,7 @@ function createBrowserCodeBundleOptions(options, target, sourceFileCache, styles
65
66
  if (options.plugins) {
66
67
  buildOptions.plugins?.push(...options.plugins);
67
68
  }
68
- if (options.externalPackages) {
69
- // Package files affected by a customized loader should not be implicitly marked as external
70
- if (options.loaderExtensions ||
71
- options.plugins ||
72
- typeof options.externalPackages === 'object') {
73
- // Plugin must be added after custom plugins to ensure any added loader options are considered
74
- buildOptions.plugins?.push((0, external_packages_plugin_1.createExternalPackagesPlugin)(options.externalPackages !== true ? options.externalPackages : undefined));
75
- }
76
- else {
77
- // Safe to use the packages external option directly
78
- buildOptions.packages = 'external';
79
- }
80
- }
69
+ appendOptionsForExternalPackages(options, buildOptions);
81
70
  return buildOptions;
82
71
  };
83
72
  }
@@ -109,7 +98,9 @@ function createBrowserPolyfillBundleOptions(options, target, sourceFileCache, st
109
98
  const pluginOptions = (0, compiler_plugin_options_1.createCompilerPluginOptions)(options, sourceFileCache);
110
99
  buildOptions.plugins.push((0, compiler_plugin_1.createCompilerPlugin)(
111
100
  // JS/TS options
112
- { ...pluginOptions, noopTypeScriptCompilation: true },
101
+ pluginOptions,
102
+ // Browser compilation handles the actual Angular code compilation
103
+ new compilation_1.NoopCompilation(),
113
104
  // Component stylesheet options are unused for polyfills but required by the plugin
114
105
  stylesheetBundler));
115
106
  }
@@ -201,16 +192,15 @@ function createServerMainCodeBundleOptions(options, target, sourceFileCache, sty
201
192
  (0, angular_localize_init_warning_plugin_1.createAngularLocalizeInitWarningPlugin)(),
202
193
  (0, compiler_plugin_1.createCompilerPlugin)(
203
194
  // JS/TS options
204
- { ...pluginOptions, noopTypeScriptCompilation: true },
195
+ pluginOptions,
196
+ // Browser compilation handles the actual Angular code compilation
197
+ new compilation_1.NoopCompilation(),
205
198
  // Component stylesheet bundler
206
199
  stylesheetBundler),
207
200
  ],
208
201
  };
209
202
  buildOptions.plugins ??= [];
210
- if (externalPackages) {
211
- buildOptions.packages = 'external';
212
- }
213
- else {
203
+ if (!externalPackages) {
214
204
  buildOptions.plugins.push((0, rxjs_esm_resolution_plugin_1.createRxjsEsmResolutionPlugin)());
215
205
  }
216
206
  // Mark manifest and polyfills file as external as these are generated by a different bundle step.
@@ -269,6 +259,7 @@ function createServerMainCodeBundleOptions(options, target, sourceFileCache, sty
269
259
  if (options.plugins) {
270
260
  buildOptions.plugins.push(...options.plugins);
271
261
  }
262
+ appendOptionsForExternalPackages(options, buildOptions);
272
263
  return buildOptions;
273
264
  };
274
265
  }
@@ -305,16 +296,15 @@ function createSsrEntryCodeBundleOptions(options, target, sourceFileCache, style
305
296
  (0, angular_localize_init_warning_plugin_1.createAngularLocalizeInitWarningPlugin)(),
306
297
  (0, compiler_plugin_1.createCompilerPlugin)(
307
298
  // JS/TS options
308
- { ...pluginOptions, noopTypeScriptCompilation: true },
299
+ pluginOptions,
300
+ // Browser compilation handles the actual Angular code compilation
301
+ new compilation_1.NoopCompilation(),
309
302
  // Component stylesheet bundler
310
303
  stylesheetBundler),
311
304
  ],
312
305
  };
313
306
  buildOptions.plugins ??= [];
314
- if (externalPackages) {
315
- buildOptions.packages = 'external';
316
- }
317
- else {
307
+ if (!externalPackages) {
318
308
  buildOptions.plugins.push((0, rxjs_esm_resolution_plugin_1.createRxjsEsmResolutionPlugin)());
319
309
  }
320
310
  // Mark manifest file as external. As this will be generated later on.
@@ -370,6 +360,7 @@ function createSsrEntryCodeBundleOptions(options, target, sourceFileCache, style
370
360
  if (options.plugins) {
371
361
  buildOptions.plugins.push(...options.plugins);
372
362
  }
363
+ appendOptionsForExternalPackages(options, buildOptions);
373
364
  return buildOptions;
374
365
  };
375
366
  }
@@ -528,3 +519,19 @@ function entryFileToWorkspaceRelative(workspaceRoot, entryFile) {
528
519
  .replace(/.[mc]?ts$/, '')
529
520
  .replace(/\\/g, '/'));
530
521
  }
522
+ function appendOptionsForExternalPackages(options, buildOptions) {
523
+ if (!options.externalPackages) {
524
+ return;
525
+ }
526
+ buildOptions.plugins ??= [];
527
+ // Package files affected by a customized loader should not be implicitly marked as external
528
+ if (options.loaderExtensions || options.plugins || typeof options.externalPackages === 'object') {
529
+ // Plugin must be added after custom plugins to ensure any added loader options are considered
530
+ buildOptions.plugins.push((0, external_packages_plugin_1.createExternalPackagesPlugin)(options.externalPackages !== true ? options.externalPackages : undefined));
531
+ buildOptions.packages = undefined;
532
+ }
533
+ else {
534
+ // Safe to use the packages external option directly
535
+ buildOptions.packages = 'external';
536
+ }
537
+ }
@@ -22,10 +22,11 @@ export interface RebuildState {
22
22
  componentStyleBundler: ComponentStylesheetBundler;
23
23
  codeBundleCache?: SourceFileCache;
24
24
  fileChanges: ChangedFiles;
25
- previousOutputInfo: Map<string, {
25
+ previousOutputInfo: ReadonlyMap<string, {
26
26
  hash: string;
27
27
  type: BuildOutputFileType;
28
28
  }>;
29
+ previousAssetsInfo: ReadonlyMap<string, string>;
29
30
  templateUpdates?: Map<string, string>;
30
31
  }
31
32
  export interface ExternalResultMetadata {
@@ -86,7 +87,7 @@ export declare class ExecutionResult {
86
87
  };
87
88
  get watchFiles(): Readonly<string[]>;
88
89
  createRebuildState(fileChanges: ChangedFiles): RebuildState;
89
- findChangedFiles(previousOutputHashes: Map<string, {
90
+ findChangedFiles(previousOutputHashes: ReadonlyMap<string, {
90
91
  hash: string;
91
92
  type: BuildOutputFileType;
92
93
  }>): Set<string>;
@@ -123,6 +123,7 @@ class ExecutionResult {
123
123
  componentStyleBundler: this.componentStyleBundler,
124
124
  fileChanges,
125
125
  previousOutputInfo: new Map(this.outputFiles.map(({ path, hash, type }) => [path, { hash, type }])),
126
+ previousAssetsInfo: new Map(this.assetFiles.map(({ source, destination }) => [source, destination])),
126
127
  templateUpdates: this.templateUpdates,
127
128
  };
128
129
  }
@@ -12,7 +12,6 @@ function createCompilerPluginOptions(options, sourceFileCache, loadResultCache,
12
12
  const { sourcemapOptions, tsconfig, fileReplacements, advancedOptimizations, jit, externalRuntimeStyles, instrumentForCoverage, } = options;
13
13
  const incremental = !!options.watch;
14
14
  return {
15
- browserOnlyBuild: !options.serverEntryPoint,
16
15
  sourcemap: !!sourcemapOptions.scripts && (sourcemapOptions.hidden ? 'external' : true),
17
16
  thirdPartySourcemaps: sourcemapOptions.vendor,
18
17
  tsconfig,
@@ -6,10 +6,10 @@
6
6
  * found in the LICENSE file at https://angular.dev/license
7
7
  */
8
8
  import type { Connect, ViteDevServer } from 'vite';
9
- import { AngularMemoryOutputFiles } from '../utils';
9
+ import { AngularMemoryOutputFiles, AngularOutputAssets } from '../utils';
10
10
  export interface ComponentStyleRecord {
11
11
  rawContent: Uint8Array;
12
12
  used?: Set<string>;
13
13
  reload?: boolean;
14
14
  }
15
- export declare function createAngularAssetsMiddleware(server: ViteDevServer, assets: Map<string, string>, outputFiles: AngularMemoryOutputFiles, componentStyles: Map<string, ComponentStyleRecord>, encapsulateStyle: (style: Uint8Array, componentId: string) => string): Connect.NextHandleFunction;
15
+ export declare function createAngularAssetsMiddleware(server: ViteDevServer, assets: AngularOutputAssets, outputFiles: AngularMemoryOutputFiles, componentStyles: Map<string, ComponentStyleRecord>, encapsulateStyle: (style: Uint8Array, componentId: string) => string): Connect.NextHandleFunction;
@@ -22,15 +22,15 @@ function createAngularAssetsMiddleware(server, assets, outputFiles, componentSty
22
22
  const extension = (0, node_path_1.extname)(pathname);
23
23
  const pathnameHasTrailingSlash = pathname[pathname.length - 1] === '/';
24
24
  // Rewrite all build assets to a vite raw fs URL
25
- const assetSourcePath = assets.get(pathname);
26
- if (assetSourcePath !== undefined) {
25
+ const asset = assets.get(pathname);
26
+ if (asset) {
27
27
  // Workaround to disable Vite transformer middleware.
28
28
  // See: https://github.com/vitejs/vite/blob/746a1daab0395f98f0afbdee8f364cb6cf2f3b3f/packages/vite/src/node/server/middlewares/transform.ts#L201 and
29
29
  // https://github.com/vitejs/vite/blob/746a1daab0395f98f0afbdee8f364cb6cf2f3b3f/packages/vite/src/node/server/transformRequest.ts#L204-L206
30
30
  req.headers.accept = 'text/html';
31
31
  // The encoding needs to match what happens in the vite static middleware.
32
32
  // ref: https://github.com/vitejs/vite/blob/d4f13bd81468961c8c926438e815ab6b1c82735e/packages/vite/src/node/server/middlewares/static.ts#L163
33
- req.url = `${server.config.base}@fs/${encodeURI(assetSourcePath)}`;
33
+ req.url = `${server.config.base}@fs/${encodeURI(asset.source)}`;
34
34
  next();
35
35
  return;
36
36
  }
@@ -43,7 +43,7 @@ function createAngularAssetsMiddleware(server, assets, outputFiles, componentSty
43
43
  : // Non-trailing slash check for fallback `.html`
44
44
  assets.get(pathname + '.html');
45
45
  if (htmlAssetSourcePath) {
46
- req.url = `${server.config.base}@fs/${encodeURI(htmlAssetSourcePath)}`;
46
+ req.url = `${server.config.base}@fs/${encodeURI(htmlAssetSourcePath.source)}`;
47
47
  next();
48
48
  return;
49
49
  }
@@ -14,9 +14,11 @@ exports.createAngularMemoryPlugin = createAngularMemoryPlugin;
14
14
  const node_assert_1 = __importDefault(require("node:assert"));
15
15
  const promises_1 = require("node:fs/promises");
16
16
  const node_path_1 = require("node:path");
17
+ const node_url_1 = require("node:url");
17
18
  const load_esm_1 = require("../../../utils/load-esm");
18
19
  const ANGULAR_PREFIX = '/@ng/';
19
20
  const VITE_FS_PREFIX = '/@fs/';
21
+ const FILE_PROTOCOL = 'file:';
20
22
  async function createAngularMemoryPlugin(options) {
21
23
  const { virtualProjectRoot, outputFiles, external } = options;
22
24
  const { normalizePath } = await (0, load_esm_1.loadEsmModule)('vite');
@@ -29,8 +31,16 @@ async function createAngularMemoryPlugin(options) {
29
31
  return;
30
32
  }
31
33
  // For SSR with component HMR, pass through as a virtual module
32
- if (ssr && source.startsWith(ANGULAR_PREFIX)) {
33
- return '\0' + source;
34
+ if (ssr && source.startsWith(FILE_PROTOCOL) && source.includes(ANGULAR_PREFIX)) {
35
+ // Vite will resolve these these files example:
36
+ // `file:///@ng/component?c=src%2Fapp%2Fapp.component.ts%40AppComponent&t=1737017253850`
37
+ const sourcePath = (0, node_url_1.fileURLToPath)(source);
38
+ const { root } = (0, node_path_1.parse)(sourcePath);
39
+ const sourceWithoutRoot = normalizePath('/' + sourcePath.slice(root.length));
40
+ if (sourceWithoutRoot.startsWith(ANGULAR_PREFIX)) {
41
+ const [, query] = source.split('?', 2);
42
+ return `\0${sourceWithoutRoot}?${query}`;
43
+ }
34
44
  }
35
45
  // Prevent vite from resolving an explicit external dependency (`externalDependencies` option)
36
46
  if (external?.includes(source)) {
@@ -7,7 +7,7 @@
7
7
  */
8
8
  import type { Connect, Plugin } from 'vite';
9
9
  import { ComponentStyleRecord } from '../middlewares';
10
- import { AngularMemoryOutputFiles } from '../utils';
10
+ import { AngularMemoryOutputFiles, AngularOutputAssets } from '../utils';
11
11
  export declare enum ServerSsrMode {
12
12
  /**
13
13
  * No SSR
@@ -32,7 +32,7 @@ export declare enum ServerSsrMode {
32
32
  }
33
33
  interface AngularSetupMiddlewaresPluginOptions {
34
34
  outputFiles: AngularMemoryOutputFiles;
35
- assets: Map<string, string>;
35
+ assets: AngularOutputAssets;
36
36
  extensionMiddleware?: Connect.NextHandleFunction[];
37
37
  indexHtmlTransformer?: (content: string) => Promise<string>;
38
38
  componentStyles: Map<string, ComponentStyleRecord>;
@@ -12,6 +12,9 @@ export type AngularMemoryOutputFiles = Map<string, {
12
12
  hash: string;
13
13
  servable: boolean;
14
14
  }>;
15
+ export type AngularOutputAssets = Map<string, {
16
+ source: string;
17
+ }>;
15
18
  export declare function pathnameWithoutBasePath(url: string, basePath: string): string;
16
19
  export declare function lookupMimeTypeFromRequest(url: string): string | undefined;
17
20
  export type EsbuildLoaderOption = Exclude<DepOptimizationConfig['esbuildOptions'], undefined>['loader'];
@@ -83,7 +83,7 @@ exports.useJSONBuildLogs = isPresent(buildLogsJsonVariable) && isEnabled(buildLo
83
83
  const optimizeChunksVariable = process.env['NG_BUILD_OPTIMIZE_CHUNKS'];
84
84
  exports.shouldOptimizeChunks = isPresent(optimizeChunksVariable) && isEnabled(optimizeChunksVariable);
85
85
  const hmrComponentStylesVariable = process.env['NG_HMR_CSTYLES'];
86
- exports.useComponentStyleHmr = !isPresent(hmrComponentStylesVariable) || !isDisabled(hmrComponentStylesVariable);
86
+ exports.useComponentStyleHmr = isPresent(hmrComponentStylesVariable) && isEnabled(hmrComponentStylesVariable);
87
87
  const hmrComponentTemplateVariable = process.env['NG_HMR_TEMPLATES'];
88
88
  exports.useComponentTemplateHmr = !isPresent(hmrComponentTemplateVariable) || !isDisabled(hmrComponentTemplateVariable);
89
89
  const partialSsrBuildVariable = process.env['NG_BUILD_PARTIAL_SSR'];
@@ -39,7 +39,7 @@ function ensureString(value, name) {
39
39
  throw new Error(`Project field '${name}' is malformed. Expected a string.`);
40
40
  }
41
41
  }
42
- function ensureValidsubPath(value, name) {
42
+ function ensureValidSubPath(value, name) {
43
43
  ensureString(value, name);
44
44
  if (!/^[\w-]*$/.test(value)) {
45
45
  throw new Error(`Project field '${name}' is invalid. It can only contain letters, numbers, hyphens, and underscores.`);
@@ -78,7 +78,7 @@ function createI18nOptions(projectMetadata, inline, logger) {
78
78
  rawSourceLocaleBaseHref = metadata.sourceLocale.baseHref;
79
79
  }
80
80
  if (metadata.sourceLocale.subPath !== undefined) {
81
- ensureValidsubPath(metadata.sourceLocale.subPath, 'i18n.sourceLocale.subPath');
81
+ ensureValidSubPath(metadata.sourceLocale.subPath, 'i18n.sourceLocale.subPath');
82
82
  rawsubPath = metadata.sourceLocale.subPath;
83
83
  }
84
84
  if (rawsubPath !== undefined && rawSourceLocaleBaseHref !== undefined) {
@@ -111,7 +111,7 @@ function createI18nOptions(projectMetadata, inline, logger) {
111
111
  baseHref = options.baseHref;
112
112
  }
113
113
  if ('subPath' in options) {
114
- ensureString(options.subPath, `i18n.locales.${locale}.subPath`);
114
+ ensureValidSubPath(options.subPath, `i18n.locales.${locale}.subPath`);
115
115
  subPath = options.subPath;
116
116
  }
117
117
  if (subPath !== undefined && baseHref !== undefined) {
@@ -10,7 +10,7 @@ Object.defineProperty(exports, "__esModule", { value: true });
10
10
  exports.normalizeCacheOptions = normalizeCacheOptions;
11
11
  const node_path_1 = require("node:path");
12
12
  /** Version placeholder is replaced during the build process with actual package version */
13
- const VERSION = '19.1.0-rc.0';
13
+ const VERSION = '19.1.1';
14
14
  function hasCacheMetadata(value) {
15
15
  return (!!value &&
16
16
  typeof value === 'object' &&