如何集成 Angular 2 + Java Maven Web 应用程序

Posted

技术标签:

【中文标题】如何集成 Angular 2 + Java Maven Web 应用程序【英文标题】:how to integrate Angular 2 + Java Maven Web Application 【发布时间】:2016-11-26 16:44:39 【问题描述】:

我创建了一个 Angular 2 前端应用程序。我创建了一个连接到数据库的 Java Rest WS 后端应用程序。

Angular 2 App 的文件夹结构如下-

Angular2App
  confg
  dist
  e2e
  node_modules
  public
  src
     app
     favicon.ico
     index.html
     main.ts
     system-config.ts
     tsconfig.json
     typings.d.ts
  tmp
  typings
  .editorconfig
  .gitignore
  angular-cli.json
  angular-cli-build.js
  package.json
  README.md
  tslint.json
  typings.json

我的 Java Maven Web 应用程序结构如下-

JerseyWebApp
  src
   main
     java
       Custom Package
       java classes
     resources
     webapp
       WEB-INF
         web.xml
       index.html
  pom.xml

我想知道如何将这两个应用程序集成到一个只生成一个war文件的应用程序中。

【问题讨论】:

我使用 spring boot 构建我的应用程序,我们为 angular2 制作 jars。样品请参考github.com/Kiran-N/springboot-and-angular2 有类似的任务,这是我的方法***.com/questions/37512154/… 【参考方案1】:

我建议让两个应用程序分开,这样你就有了模块化。 这样您就可以在不影响您的服务的情况下更改 Angular 应用程序,反之亦然。其次,您的 apache/nginx 可以更快地从 Angular 而不是 Tomcat 交付您的 js 和 html(例如)。但是如果你仍然想把 Angular 应用程序放在 war 中,模式是所有的 web 资源都在 src/main/webapp 中。

【讨论】:

这样我尝试将所有的网络资源放在 src/main/webapp 下,但在这里我面临一个问题,比如 angular2 是建立在 typescript 上的,所以 tomcat 服务器无法编译这些文件。而且应用程序卡住了。 是的。也许这对你有帮助:***.com/a/37398298/2285259【参考方案2】:

有趣的是,我上周就这样做了!

使用 Netbeans 8.1 和 Tomcat servlet 版本 8.0.27

Angular 和 Java 项目文件结构。

Java 项目名为 Foo。 Angular 项目是酒吧

Foo (Java Maven Project)
|__ src
|    |__ main
|    |    |__ webapp (This folder contains the entire Angular Project)
|    |    |    |__ META-INF
|    |    |    |    \__ context.xml 
|    |    |    |__ WEB-INF
|    |    |    |    \__ web.xml
|    |    |    |__ includes
|    |    |    |    |__ css
|    |    |    |    |__ images
|    |    |    |    \__ js
|    |    |    |
|    |    |    | ## Bar project files are located here ##
|    |    |    |
|    |    |    |__ app
|    |    |    |    \__ All .ts and compiled .js files are located here
|    |    |    |__ node_modules
|    |    |    |    \__ any dependencies used for Bar are located here
|    |    |    |__ typings
|    |    |    |    \__ typings for Typescript located here
|    |    |    |
|    |    |    |__ README.txt
|    |    |    |__ index.jsp
|    |    |    |__ package.json
|    |    |    |__ systemjs.config.js
|    |    |    |__ tsconfig.json
|    |    |    |__ typings.json
|    |    |    \ ## Bar project files end here
|    |    | 
|    |    |__ resources
|    |    |    |__META-INF
|    |    |    |    \__ persistence.xml
|    |    |__ java
|    |    |    |__ hibernate.cfg.xml
|    |    |    |__ com
|    |    |    |    |__ orgName
|    |    |    |    |    |__ packageName
|    |    |    |    |    |    \__ .java files are here
|__ pom.xml
\__ nb-configuration.xml

【讨论】:

【参考方案3】:

这是我所做的:-

安装 Nodejs v6.9+ 为 Angular CLI 运行 npm install @angular/cli –g 安装 Apache Maven 或使用任何 Maven 友好的 IDE 使用您所需的 Maven 配置,我使用了简单的 webapp (WAR)。

目录结构(除了 ngapp 文件夹其余部分是标准 Maven 结构。)

ngfirst
├── pom.xml
├── src
│   └── main
│       ├── java
│       ├── resources
│       ├── webapp
│       └── ngapp

角部分

在终端打开 ngapp 文件夹并输入 ng init 命令来初始化节点和 npm 配置,结果将是一个简单的 Angular2 示例应用程序,在 ngapp 内的目录结构如下文件夹:-

             ├── angular-cli.json
             ├── e2e
             ├── karma.conf.js
             ├── node_modules
             ├── package.json
             ├── protractor.conf.js
             ├── README.md
             ├── tslint.json
             ├── src
                 ├── app
                 ├── assets
                 ├── environments
                 ├── favicon.ico
                 ├── index.html
                 ├── main.ts
                 ├── polyfills.ts
                 ├── styles.css
                 ├── test.ts
                 └── tsconfig.json

这个结构是 Angular 等效的 Maven 项目结构,src 目录是 Angular 应用程序的源,就像 ma​​ven build 命令在 target 中生成它的输出> 文件夹,ng build 命令在 dist 文件夹中生成其输出。

为了将生成的 Angular 应用程序打包到 Maven 生成的 WAR 中,修改构建配置以将输出文件夹从 dist 更改为 webapp,打开 angular-cli .json 文件并修改其 outDir 如下:-

"outDir": "../webapp/ng"

此时 ng build 命令将在 ngfirst/src/main/webapp 文件夹的 ng 目录中生成已构建的 Angular 应用程序。 p>

Maven 部分

打开pom.xml,配置以下三个maven插件:-

    compiler-plugin:在 /src/main/ngapp 文件夹中没有要编译的 Java 内容,排除它。 war-plugin:/src/main/ngapp 是 Angular 项目文件夹,不应该打包在 WAR 中,排除它。 exec-plugin:执行 NPM Install 和 Angular-CLI Build 命令,在 webapp 文件夹中生成 Angular Application 以进行最终打包。注意 --base-href 参数,需要从 webapp 的上下文路径加载 Angular 资源。

它应该是这样的:-

<plugins>
    <plugin>
        <groupId>org.apache.maven.plugins</groupId>
        <artifactId>maven-compiler-plugin</artifactId>
        <version>3.3</version>
        <configuration>
            <excludes>
                <exclude>ngapp/**</exclude>
            </excludes>
        </configuration>
    </plugin>
    <plugin>
        <groupId>org.apache.maven.plugins</groupId>
        <artifactId>maven-war-plugin</artifactId>
        <version>3.0.0</version>
        <configuration>
            <excludes>
                <exclude>ngapp/**</exclude>
            </excludes>
        </configuration>
    </plugin>
    <plugin>
        <groupId>org.codehaus.mojo</groupId>
        <artifactId>exec-maven-plugin</artifactId>
        <version>1.5.0</version>
        <executions>
            <execution>
                <id>exec-npm-install</id>
                <phase>generate-sources</phase>
                <configuration>
                    <workingDirectory>$project.basedir/src/main/ngapp</workingDirectory>
                    <executable>npm</executable>
                    <arguments>
                        <argument>install</argument>
                    </arguments>
                </configuration>
                <goals>
                    <goal>exec</goal>
                </goals>
            </execution>
            <execution>
                <id>exec-npm-ng-build</id>
                <phase>generate-sources</phase>
                <configuration>
                    <workingDirectory>$project.basedir/src/main/ngapp</workingDirectory>
                    <executable>ng</executable>
                    <arguments>
                        <argument>build</argument>
                        <argument>--base-href=/ngfirst/ng/</argument>
                    </arguments>
                </configuration>
                <goals>
                    <goal>exec</goal>
                </goals>
            </execution>
        </executions>
    </plugin>
</plugins>  

构建 Maven 项目(以及 Angular 应用程序)

在项目根目录ngfirst打开终端并运行mvn package命令,这将在target中生成一个WAR文件(ngfirst.war)文件夹。

在容器中部署ngfirst.war,在浏览器中打开http://localhost:8080/ngfirst/ng/index.html。 (如果需要,调整您的主机名和端口)

如果一切正常,您应该会在浏览器中看到 应用正常工作!,这就是 Angular 应用程序在工作!

JSP 预处理

我们可以利用 Angular 应用程序的 JSP 技术的动态配置和页面渲染功能,Angular SPA 由 Java 容器作为常规 HTML 页面提供服务,在这种情况下 index.html,如果我们配置 JSP引擎也可以预处理 html 文件,然后所有的 JSP 魔法都可以包含在 Angular SPA 页面中,只需在 web.xml

中包含以下内容
<servlet-mapping>
    <servlet-name>jsp</servlet-name>
    <url-pattern>*.html</url-pattern>
</servlet-mapping>

保存,重建 maven 项目,部署 WAR,瞧!!

【讨论】:

我建议使用&lt;warSourceExcludes&gt;ngapp/**&lt;/warSourceExcludes&gt;排除ngapp文件夹或packagingExcludes&gt; @J_Dev 这工作正常。问题是 jar 还包含节点模块。我怎么能只包含 ng serve --prodng build 输出? @J_Dev - 您能解释一下为什么将 ngapp 排除在战争之外。我认为这个问题是关于在同一场战争中集成/捆绑 angular 2 应用程序和 java 代码。如果您将其排除在外,那么角度代码如何部署? 角路由器不需要url重写吗? @user911 目录ngapp(Angular 应用程序的源代码)被排除在战争之外,但目录webapp/ng(Angular 应用程序的可执行文件)包含在战争中。【参考方案4】:

我有一个用于角度源的 maven 模块,称为 prj-angular,还有一个用于战争应用程序的模块,称为 prj-war

首先构建prj angular

它使用 maven-exec-plugin 调用 npm installng build(感谢 @J_Dev!) 将资源默认目录更改为dist/ 跳过 jar 清单生成 maven 模块结果:仅包含生成的角度 dist/ 内容的 jar!

然后,第二个 prj_war 正在构建:

prj angular 作为依赖项 使用解压阶段将之前的 jar 解压到 Web 应用目标中 此模块使用全新的 angular dist 构建您的应用大战。

按照我使用的对应插件配置下:

prj 角度(pom.xml 提取)

<build>
    <resources>
        <resource>
            <directory>dist</directory>
        </resource>
    </resources>
    <plugins>
        <!-- skip compile -->
        <plugin>
            <groupId>org.apache.maven.plugins</groupId>
            <artifactId>maven-compiler-plugin</artifactId>
            <executions>
                <execution>
                    <id>default-compile</id>
                    <phase />
                </execution>
            </executions>
        </plugin>
        <plugin>
            <groupId>org.codehaus.mojo</groupId>
            <artifactId>exec-maven-plugin</artifactId>
            <executions>
                <execution>
                    <id>exec-npm-install</id>
                    <phase>generate-sources</phase>
                    <configuration>
                        <workingDirectory>$project.basedir</workingDirectory>
                        <executable>npm.cmd</executable>
                        <arguments>
                            <argument>install</argument>
                        </arguments>
                    </configuration>
                    <goals>
                        <goal>exec</goal>
                    </goals>
                </execution>
                <execution>
                    <id>exec-npm-ng-build</id>
                    <phase>generate-sources</phase>
                    <configuration>
                        <workingDirectory>$project.basedir/src</workingDirectory>
                        <executable>ng.cmd</executable>
                        <arguments>
                            <argument>build</argument>
                            <argument>--no-progress</argument>
                            <argument>--base-href=/app/ng/</argument> <== to update
                        </arguments>
                    </configuration>
                    <goals>
                        <goal>exec</goal>
                    </goals>
                </execution>
            </executions>
        </plugin>
        <plugin>
            <groupId>org.apache.maven.plugins</groupId>
            <artifactId>maven-jar-plugin</artifactId>
            <configuration>
                <archive>
                    <addMavenDescriptor>false</addMavenDescriptor>
                    <manifest>
                        <addClasspath>false</addClasspath>
                    </manifest>
                </archive>
            </configuration>
        </plugin>
        <plugin>
            <groupId>org.apache.maven.plugins</groupId>
            <artifactId>maven-shade-plugin</artifactId>
            <executions>
                <execution>
                    <phase>package</phase>
                    <goals>
                        <goal>shade</goal>
                    </goals>
                    <configuration>
                        <filters>
                            <filter>
                                <artifact>*:*</artifact>
                                <excludes>
                                    <exclude>META-INF/</exclude>
                                </excludes>
                            </filter>
                        </filters>
                    </configuration>
                </execution>
            </executions>
        </plugin>
    </plugins>
</build>

prj 战争(pom.xml 提取)

        <plugin>
            <groupId>org.apache.maven.plugins</groupId>
            <artifactId>maven-dependency-plugin</artifactId>
            <executions>
                <execution>
                    <id>unpack angular distribution</id>
                    <phase>generate-resources</phase>
                    <goals>
                        <goal>unpack</goal>
                    </goals>
                    <configuration>
                        <artifactItems>
                            <artifactItem>
                                <groupId>com.myapp</groupId> <== to update
                                <artifactId>prj-angular</artifactId> <== to update
                                <overWrite>true</overWrite>
                                <includes>**/*</includes>
                            </artifactItem>
                        </artifactItems>
                        <outputDirectory>$project.build.directory/prjwar/ng</outputDirectory> <== to update
                        <overWriteReleases>true</overWriteReleases>
                        <overWriteSnapshots>true</overWriteSnapshots>
                    </configuration>
                </execution>
            </executions>
        </plugin>

【讨论】:

最近发现github.com/eirslett/frontend-maven-plugin【参考方案5】:

我想分享我是如何设置我的 Angular/Java 项目的。一些重要的事情:

    只有一个 Maven 项目,它允许我构建整个项目。这样,我可以构建整个项目,也可以分别构建客户端和后端。

    我的项目基于 Spring Boot 框架。但是,您可以轻松地根据您的情况调整我的解决方案。我生成的 Angular 项目的 output 代码放在 `META-INF' 文件夹下。如果你不使用 Spring Boot,你显然可以改变它。

    在我的项目中,我想在public文件夹中发布angular项目。

    当我开发时,我分别运行 Angular 项目和后端项目:Angular with ng serve 和 IDE (Eclipse) 中的后端项目(Java 部分)。

好的,让我们开始吧。整个项目结构如下图所示。

如您所见,我将 Angular 项目放在 'src\main\ngapp' 文件夹中。对于 Java 项目(后端),我使用 Eclipse IDE,对于 Angular 项目,我使用 Webstorm。您可以选择您喜欢的 IDE 来管理项目。重要的是:您将需要两个 IDE 来管理整个项目。

为了使用 Maven 构建 Angular 项目,我使用了以下 maven 配置文件定义。

<profile>
    <id>build-client</id>

    <build>
        <plugins>
            <plugin>
                <groupId>com.github.eirslett</groupId>
                <artifactId>frontend-maven-plugin</artifactId>
                <version>1.3</version>
                <configuration>
                    <nodeVersion>v10.13.0</nodeVersion>
                    <npmVersion>6.4.1</npmVersion>
                    <workingDirectory>src/main/ngapp/</workingDirectory>
                </configuration>
                <executions>
                    <execution>
                        <id>install node and npm</id>
                        <goals>
                            <goal>install-node-and-npm</goal>
                        </goals>
                    </execution>
                    <execution>
                        <id>npm install</id>
                        <goals>
                            <goal>npm</goal>
                        </goals>
                    </execution>
                    <execution>
                        <id>npm run build-prod</id>
                        <goals>
                            <goal>npm</goal>
                        </goals>
                        <configuration>
                            <arguments>run build</arguments>
                        </configuration>
                    </execution>
                    <execution>
                        <id>prod</id>
                        <goals>
                            <goal>npm</goal>
                        </goals>
                        <configuration>
                            <arguments>run-script build</arguments>
                        </configuration>
                        <phase>generate-resources</phase>
                    </execution>
                </executions>
            </plugin>
        </plugins>
    </build>
</profile>

如您所见,我使用com.github.eirslett:frontend-maven-plugin 插件安装node 并运行npm 来构建Angular 项目。这样,当我运行maven配置文件build-client插件的时候:

检查并安装Angular项目文件夹src/main/ngapp/中的节点版本v10.13.0

运行命令npm run build。在 Angular 项目中定义了构建别名在 package.json

"scripts": 
    "ng": "ng",
    "start": "ng serve --proxy-config proxy.conf.json",
    "build": "ng build --configuration=production",
    "test": "ng test",
    "lint": "ng lint",
    "e2e": "ng e2e"

Angular 客户端必须放在 Web 应用程序的 public 文件夹中。为此,Angular 项目配置为具有baseHref=/public。此外,构建的项目必须放在src/main/resources/META-INF/resources/public。在angular.json 你会发现:

"build": 
  "builder": "@angular-devkit/build-angular:browser",
  "options": 
    "baseHref":"/public/",
    "outputPath": "../resources/META-INF/resources/public",
    ...    

在非 Spring Boot 项目中,您可能需要将构建的 Angular 项目直接放在 src/main/webapp/public 文件夹中。为此,只需根据需要修改angular.json 文件即可。

您可以在my github project 中找到所有项目的代码。插件项目是here。

【讨论】:

我对您的部署有疑问。您是否遇到路由问题/ Maven?如果您在 url 中输入了不指向 /public 的内容(即 /public/user),您会得到一个 while 列表错误页面吗?看起来我们的项目设置与您的类似。这两个应用程序分别部署在 Maven 下,一个用于 java,一个用于 Angular。然后将其配置为将 Angular 应用程序作为静态页面提供服务。【参考方案6】:
<plugin>
                        <groupId>com.github.eirslett</groupId>
                        <artifactId>frontend-maven-plugin</artifactId>
                        <version>1.3</version>
                        <configuration>
                            <nodeVersion>v10.13.0</nodeVersion>
                            <npmVersion>6.4.1</npmVersion>
                            <workingDirectory>src/main/ngapp/</workingDirectory>
                        </configuration>
                        <executions>
                            <execution>
                                <id>install node and npm</id>
                                <goals>
                                    <goal>install-node-and-npm</goal>
                                </goals>
                            </execution>
                            <execution>
                                <id>npm install</id>
                                <goals>
                                    <goal>npm</goal>
                                </goals>
                            </execution>
                            <execution>
                                <id>npm run build-prod</id>
                                <goals>
                                    <goal>npm</goal>
                                </goals>
                                <configuration>
                                    <arguments>run build</arguments>
                                </configuration>
                            </execution>
                            <execution>
                                <id>prod</id>
                                <goals>
                                    <goal>npm</goal>
                                </goals>
                                <configuration>
                                    <arguments>run-script build</arguments>
                                </configuration>
                                <phase>generate-resources</phase>
                            </execution>
                        </executions>
                    </plugin>

【讨论】:

欢迎来到 S/O。请在回答时简要说明您正在做什么。【参考方案7】:

基于命令行构建angular项目的解决方案

npm install --verbose
npm run ng build

给定

src/main/frontend
src/main/webapp

ma​​ven-war-plugin + exec-maven-plugin

<plugins>
    <plugin>
        <groupId>org.apache.maven.plugins</groupId>
        <artifactId>maven-war-plugin</artifactId>
        <version>3.2.3</version>
        <configuration>
            <failOnMissingWebXml>false</failOnMissingWebXml>
            <webResources>
                <resource>
                    <directory>src/main/frontend/dist</directory>
                </resource>
            </webResources>
        </configuration>
    </plugin>
    <plugin>
        <groupId>org.codehaus.mojo</groupId>
        <artifactId>exec-maven-plugin</artifactId>
        <version>3.0.0</version>
        <executions>
            <execution>
                <id>npm-install</id>
                <phase>generate-sources</phase>
                <configuration>
                    <workingDirectory>src/main/frontend</workingDirectory>
                    <executable>npm</executable>
                    <arguments>
                        <argument>install</argument>
                    </arguments>
                </configuration>
                <goals>
                    <goal>exec</goal>
                </goals>
            </execution>
            <execution>
                <id>npm-ng-build</id>
                <phase>generate-sources</phase>
                <configuration>
                    <workingDirectory>src/main/frontend</workingDirectory>
                    <executable>npm</executable>
                    <arguments>
                        <argument>run</argument>
                        <argument>ng</argument>
                        <argument>build</argument>
                    </arguments>
                </configuration>
                <goals>
                    <goal>exec</goal>
                </goals>
            </execution>
        </executions>
    </plugin>
</plugins>

ma​​ven-war-plugin + maven-antrun-plugin(无法直接在我的机器上运行 npm,因此依赖于操作系统构建)

<plugins>
    <plugin>
        <groupId>org.apache.maven.plugins</groupId>
        <artifactId>maven-war-plugin</artifactId>
        <version>3.2.3</version>
        <configuration>
            <failOnMissingWebXml>false</failOnMissingWebXml>
            <webResources>
                <resource>
                    <directory>src/main/frontend/dist</directory>
                </resource>
            </webResources>
        </configuration>
    </plugin>
    <plugin>
        <groupId>org.apache.maven.plugins</groupId>
        <artifactId>maven-antrun-plugin</artifactId>
        <version>3.0.0</version>
        <executions>
            <execution>
                <id>exec-gen-sources</id>
                <phase>generate-sources</phase>
                <configuration>
                    <target name="Build Frontend">
                        <exec executable="cmd" dir="src/main/frontend" failonerror="true">
                            <arg line="/c npm install --verbose" />
                        </exec>
                        <exec executable="cmd" dir="src/main/frontend" failonerror="true">
                            <arg line="/c npm run ng build" />
                        </exec>
                    </target>
                </configuration>
                <goals>
                    <goal>run</goal>
                </goals>
            </execution>
        </executions>
    </plugin>
</plugins>

【讨论】:

以上是关于如何集成 Angular 2 + Java Maven Web 应用程序的主要内容,如果未能解决你的问题,请参考以下文章

集成 Angular + Nodejs + Spring Boot Java REST API 使 Angular Universal 工作

我如何将paytm集成到angular4中

如何将 D3.js 与 Renderer API 与 Angular 2 集成

如何将 Angular js 集成到 grails 2.3.4 中?

将 Sails Js 与 Angular 2 集成

Angular(SPA) 前端和 Spring Boot 后端的 SAML 2.0 集成