Skip to content

Commit

Permalink
feat(@schematics/angular): Update universal schematic to support stan…
Browse files Browse the repository at this point in the history
…dalone applications
  • Loading branch information
Brocco authored and angular-robot[bot] committed Mar 28, 2023
1 parent 66a33c6 commit dc5cc89
Show file tree
Hide file tree
Showing 5 changed files with 103 additions and 1 deletion.
Original file line number Diff line number Diff line change
@@ -0,0 +1,19 @@
/**
* @license
* Copyright Google LLC All Rights Reserved.
*
* Use of this source code is governed by an MIT-style license that can be
* found in the LICENSE file at https://angular.io/license
*/

import { mergeApplicationConfig, ApplicationConfig } from '@angular/core';
import { provideServerSupport } from '@angular/platform-server';
import { appConfig } from './app.config';

const serverConfig: ApplicationConfig = {
providers: [
provideServerSupport()
]
};

export const config = mergeApplicationConfig(appConfig, serverConfig);
Original file line number Diff line number Diff line change
@@ -0,0 +1,15 @@
/**
* @license
* Copyright Google LLC All Rights Reserved.
*
* Use of this source code is governed by an MIT-style license that can be
* found in the LICENSE file at https://angular.io/license
*/

import { bootstrapApplication } from '@angular/platform-browser';
import { AppComponent } from './app/app.component';
import { config } from './app/app.config.server';

const bootstrap = () => bootstrapApplication(AppComponent, config);

export default bootstrap;
6 changes: 5 additions & 1 deletion packages/schematics/angular/universal/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,7 @@ import {
chain,
mergeWith,
move,
noop,
strings,
url,
} from '@angular-devkit/schematics';
Expand All @@ -27,6 +28,7 @@ import {
getPackageJsonDependency,
} from '../utility/dependencies';
import { latestVersions } from '../utility/latest-versions';
import { isStandaloneApp } from '../utility/ng-ast-utils';
import { relativePathToWorkspaceRoot } from '../utility/paths';
import { targetBuildNotFoundError } from '../utility/project-targets';
import { getWorkspace, updateWorkspace } from '../utility/workspace';
Expand Down Expand Up @@ -133,7 +135,9 @@ export default function (options: UniversalOptions): Rule {
context.addTask(new NodePackageInstallTask());
}

const templateSource = apply(url('./files/src'), [
const isStandalone = isStandaloneApp(host, clientBuildOptions.main);

const templateSource = apply(url(isStandalone ? './files/standalone-src' : './files/src'), [
applyTemplates({
...strings,
...options,
Expand Down
51 changes: 51 additions & 0 deletions packages/schematics/angular/universal/index_spec.ts
Original file line number Diff line number Diff line change
Expand Up @@ -188,4 +188,55 @@ describe('Universal Schematic', () => {
};
expect(compilerOptions.types).toContain('@angular/localize');
});

describe('standalone application', () => {
let standaloneAppOptions;
let defaultStandaloneOptions: UniversalOptions;
beforeEach(async () => {
const standaloneAppName = 'baz';
standaloneAppOptions = {
...appOptions,
name: standaloneAppName,
standalone: true,
};
defaultStandaloneOptions = {
project: standaloneAppName,
};
appTree = await schematicRunner.runSchematic('application', standaloneAppOptions, appTree);
});

it('should create not root module file', async () => {
const tree = await schematicRunner.runSchematic(
'universal',
defaultStandaloneOptions,
appTree,
);
const filePath = '/projects/baz/src/app/app.server.module.ts';
expect(tree.exists(filePath)).toEqual(false);
});

it('should create a main file', async () => {
const tree = await schematicRunner.runSchematic(
'universal',
defaultStandaloneOptions,
appTree,
);
const filePath = '/projects/baz/src/main.server.ts';
expect(tree.exists(filePath)).toEqual(true);
const contents = tree.readContent(filePath);
expect(contents).toContain(`bootstrapApplication(AppComponent, config)`);
});

it('should create server app config file', async () => {
const tree = await schematicRunner.runSchematic(
'universal',
defaultStandaloneOptions,
appTree,
);
const filePath = '/projects/baz/src/app/app.config.server.ts';
expect(tree.exists(filePath)).toEqual(true);
const contents = tree.readContent(filePath);
expect(contents).toContain(`const serverConfig: ApplicationConfig = {`);
});
});
});
13 changes: 13 additions & 0 deletions packages/schematics/angular/utility/ng-ast-utils.ts
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,7 @@
import { normalize } from '@angular-devkit/core';
import { SchematicsException, Tree } from '@angular-devkit/schematics';
import { dirname } from 'path';
import { findBootstrapApplicationCall } from '../private/standalone';
import * as ts from '../third_party/github.com/Microsoft/TypeScript/lib/typescript';
import { findNode, getSourceNodes } from '../utility/ast-utils';

Expand Down Expand Up @@ -78,3 +79,15 @@ export function getAppModulePath(host: Tree, mainPath: string): string {

return modulePath;
}

export function isStandaloneApp(host: Tree, mainPath: string): boolean {
const source = ts.createSourceFile(
mainPath,
host.readText(mainPath),
ts.ScriptTarget.Latest,
true,
);
const bootstrapCall = findBootstrapApplicationCall(source);

return bootstrapCall !== null;
}

0 comments on commit dc5cc89

Please sign in to comment.