4

我是 Java/Web 新手,我希望这里有人可以帮助我。

我正在使用 Eclipse(Juno Windows 7)中的 Spring 构建一个 GAE 应用程序。该项目是使用 Eclipse 的 Maven 插件(使用 Maven 3.1.0)和 Maven 的 appengine-maven-plugin(使用 GAE SDK 1.8.3)生成的。

我的大部分消息必须通过 HTTPS 发送,我在 Spring 配置中强制执行此操作。但是,我不知道如何配置本地 DevAppServer 以支持 HTTPS。

我从创建证书开始

keytool -keystore myKeystore -genkey -keyalg RSA

我希望提供给服务器。但是,GAE 似乎在它自己的 Jetty 版本中运行,我不清楚我是否可以修改它。

我试图通过命令行参数推送它

<plugin>
    <groupId>com.google.appengine</groupId>
    <artifactId>appengine-maven-plugin</artifactId>
    <version>${appengine.target.version}</version>
    <configuration>
        <useJava7>true</useJava7>
        <address>127.0.0.1</address>
        <port>8080</port>
        <compileEncoding>utf-8</compileEncoding>
        <jvmFlags>
            <jvmFlag>-Xdebug</jvmFlag>
            <jvmFlag>-Xrunjdwp:transport=dt_socket,address=1044,server=y,suspend=y</jvmFlag>
            <jvmFlag>-Djavax.net.ssl.keyStore=C:\STEVEN-DEV\projects\apps\testserver\src\main\webapp\WEB-INF\myKeystore</jvmFlag>
            <jvmFlag>-Djavax.net.ssl.keyStorePassword=testpass</jvmFlag>
        </jvmFlags>
    </configuration>
</plugin>

我知道正在加载密钥库,因为如果路径错误,我会看到异常。但是,我不确定它正在加载什么,以及这是否是我想要做的。

当我从 Eclipse 调试应用程序时,打包应用程序后,这会出现在我的日志中:

Running C:\Program Files\Java\jdk1.7.0_10\jre\bin\java -javaagent:C:\Users\Steven\.m2\repository\com\google\appengine\appengine-java-sdk\1.8.3\appengine-java-sdk\appengine-java-sdk-1.8.3\lib\agent\appengine-agent.jar -Xbootclasspath/p:C:\Users\Steven\.m2\repository\com\google\appengine\appengine-java-sdk\1.8.3\appengine-java-sdk\appengine-java-sdk-1.8.3\lib\override\appengine-dev-jdk-overrides.jar -Dappengine.fullscan.seconds=5 -classpath C:\Users\Steven\.m2\repository\com\google\appengine\appengine-java-sdk\1.8.3\appengine-java-sdk\appengine-java-sdk-1.8.3\lib\appengine-tools-api.jar -Xdebug -Xrunjdwp:transport=dt_socket,address=1044,server=y,suspend=y -Djavax.net.ssl.keyStore=C:\STEVEN-DEV\projects\apps\testserver\src\main\webapp\WEB-INF\myKeystore -Djavax.net.ssl.keyStorePassword=testpass com.google.appengine.tools.development.DevAppServerMain --allow_remote_shutdown -a 127.0.0.1 -p 8080 C:\STEVEN-DEV\projects\apps\testserver\target/testserver-0.0.1-SNAPSHOT

如果我打开 chrome 并尝试访问

https://localhost:8080/test/retval

我看到“SSL 连接错误”和“错误代码:ERR_SSL_PROTOCOL_ERROR”

如果我尝试浏览到

http://localhost:8080/test/retval

我将被转发到

https://localhost:8443/test/retval

并被告知“此网页不可用”。

更新 2:在再次查看文档后,我发现了这个

开发 Web 服务器不支持 HTTPS 连接。它忽略了传输保证,因此可以使用与开发 Web 服务器的常规 HTTP 连接来测试用于 HTTPS 的路径。

所以看来我的问题是我的 Spring 配置强制使用 HTTPS。我可以把它拿出来并允许任何连接类型。但是,我并不热衷于这样做,而是更喜欢一种配置/破解开发服务器以支持 SSL 的方法。

(回到老问题:我一直在尝试什么)

我不知道我的错误在哪里:GAE、Maven 或 Spring。

以下是我完整的 pom.xml

我已经阅读文档并在网上搜索了几个小时。任何帮助将非常感激。

<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
    xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">

    <modelVersion>4.0.0</modelVersion>
    <packaging>war</packaging>
    <version>0.0.1-SNAPSHOT</version>

    <groupId>com.steven</groupId>
    <artifactId>testserver</artifactId>

    <properties>
        <java.version>1.7</java.version>
        <maven.enforcer.plugin-version>1.3.1</maven.enforcer.plugin-version>
        <maven.version.range>[2.2.1,3.1.0]</maven.version.range>
        <appengine.app.version>1</appengine.app.version>
        <appengine.target.version>1.8.3</appengine.target.version>
        <project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
        <org.springframework-version>3.2.3.RELEASE</org.springframework-version>
        <org.springframework.security-version>3.1.4.RELEASE</org.springframework.security-version>
        <org.slf4j-version>1.7.5</org.slf4j-version>
        <ch.qos.logback-version>1.0.13</ch.qos.logback-version>
        <org.codehaus.jackson-version>1.9.12</org.codehaus.jackson-version>
    </properties>

    <dependencies>
        <!-- Compile/runtime dependencies -->
        <dependency>
            <groupId>com.google.appengine</groupId>
            <artifactId>appengine-api-1.0-sdk</artifactId>
            <version>${appengine.target.version}</version>
        </dependency>
        <dependency>
            <groupId>javax.servlet</groupId>
            <artifactId>servlet-api</artifactId>
            <version>2.5</version>
            <scope>provided</scope>
        </dependency>
        <dependency>
            <groupId>jstl</groupId>
            <artifactId>jstl</artifactId>
            <version>1.2</version>
        </dependency>

        <!-- Test Dependencies -->
        <dependency>
            <groupId>com.google.appengine</groupId>
            <artifactId>appengine-testing</artifactId>
            <version>${appengine.target.version}</version>
            <scope>test</scope>
        </dependency>
        <dependency>
            <groupId>com.google.appengine</groupId>
            <artifactId>appengine-api-stubs</artifactId>
            <version>${appengine.target.version}</version>
            <scope>test</scope>
        </dependency>

        <!-- Spring Core -->
        <dependency>
            <groupId>org.springframework</groupId>
            <artifactId>spring-core</artifactId>
            <version>${org.springframework-version}</version>
            <exclusions>
                <exclusion>
                    <groupId>commons-logging</groupId>
                    <artifactId>commons-logging</artifactId>
                </exclusion>
            </exclusions>
        </dependency>
        <dependency>
            <groupId>org.springframework</groupId>
            <artifactId>spring-web</artifactId>
            <version>${org.springframework-version}</version>
        </dependency>
        <dependency>
            <groupId>org.springframework</groupId>
            <artifactId>spring-webmvc</artifactId>
            <version>${org.springframework-version}</version>
        </dependency>

        <!-- Spring Security -->
        <dependency>
            <groupId>org.springframework.security</groupId>
            <artifactId>spring-security-core</artifactId>
            <version>${org.springframework.security-version}</version>
        </dependency>
        <dependency>
            <groupId>org.springframework.security</groupId>
            <artifactId>spring-security-web</artifactId>
            <version>${org.springframework.security-version}</version>
        </dependency>
        <dependency>
            <groupId>org.springframework.security</groupId>
            <artifactId>spring-security-config</artifactId>
            <version>${org.springframework.security-version}</version>
        </dependency>

        <!-- JSON -->
        <dependency>
            <groupId>org.codehaus.jackson</groupId>
            <artifactId>jackson-mapper-asl</artifactId>
            <version>${org.codehaus.jackson-version}</version>
        </dependency>

        <!-- Logging -->
        <dependency>
            <groupId>org.slf4j</groupId>
            <artifactId>jcl-over-slf4j</artifactId>
            <version>${org.slf4j-version}</version>
            <scope>runtime</scope>
        </dependency>
        <dependency>
            <groupId>org.slf4j</groupId>
            <artifactId>slf4j-api</artifactId>
            <version>${org.slf4j-version}</version>
            <scope>runtime</scope>
        </dependency>
        <dependency>
            <groupId>ch.qos.logback</groupId>
            <artifactId>logback-classic</artifactId>
            <version>${ch.qos.logback-version}</version>
        </dependency>
        <dependency>
            <groupId>ch.qos.logback</groupId>
            <artifactId>logback-core</artifactId>
            <version>${ch.qos.logback-version}</version>
        </dependency>

    </dependencies>

    <repositories>
        <repository>
            <id>springsource-repo</id>
            <name>SpringSource Repository</name>
            <url>http://repo.springsource.org/release</url>
        </repository>
    </repositories>

    <build>
        <pluginManagement>
            <plugins>
                <plugin>
                    <groupId>org.eclipse.m2e</groupId>
                    <artifactId>lifecycle-mapping</artifactId>
                    <version>1.0.0</version>
                    <configuration>
                        <lifecycleMappingMetadata>
                            <pluginExecutions>
                                <pluginExecution>
                                    <pluginExecutionFilter>
                                        <groupId>org.apache.maven.plugins</groupId>
                                        <artifactId>maven-enforcer-plugin</artifactId>
                                        <versionRange>[1.0.0,)</versionRange>
                                        <goals>
                                            <goal>enforce</goal>
                                        </goals>
                                    </pluginExecutionFilter>
                                    <action>
                                        <ignore />
                                    </action>
                                </pluginExecution>
                            </pluginExecutions>
                        </lifecycleMappingMetadata>
                    </configuration>
                </plugin>
            </plugins>
        </pluginManagement>

        <plugins>
            <plugin>
                <groupId>org.apache.maven.plugins</groupId>
                <version>2.5.1</version>
                <artifactId>maven-compiler-plugin</artifactId>
                <configuration>
                    <source>1.7</source>
                    <target>1.7</target>
                </configuration>
            </plugin>

            <plugin>
                <groupId>org.apache.maven.plugins</groupId>
                <artifactId>maven-war-plugin</artifactId>
                <version>2.3</version>
                <configuration>
                    <archiveClasses>true</archiveClasses>
                    <webResources>
                        <!-- in order to interpolate version from pom into appengine-web.xml -->
                        <resource>
                            <directory>${basedir}/src/main/webapp/WEB-INF</directory>
                            <filtering>true</filtering>
                            <targetPath>WEB-INF</targetPath>
                        </resource>
                    </webResources>
                </configuration>
            </plugin>

            <plugin>
                <groupId>org.apache.maven.plugins</groupId>
                <artifactId>maven-enforcer-plugin</artifactId>
                <version>${maven.enforcer.plugin-version}</version>
                <executions>
                    <execution>
                        <id>enforce-banned-dependencies</id>
                        <goals>
                            <goal>enforce</goal>
                        </goals>
                        <configuration>
                            <rules>
                                <bannedDependencies>
                                    <searchTransitive>true</searchTransitive>
                                    <excludes>
                                        <exclude>javassist:javassist</exclude>
                                        <exclude>commons-logging</exclude>
                                        <exclude>aspectj:aspectj*</exclude>
                                        <exclude>hsqldb:hsqldb</exclude>
                                        <exclude>log4j:log4j</exclude>
                                        <exclude>org.slf4j:[1.5, 1.6.5]</exclude>
                                        <exclude>org.springframework:2.*</exclude>
                                        <exclude>org.springframework:3.0.*</exclude>
                                    </excludes>
                                </bannedDependencies>
                                <requireMavenVersion>
                                    <version>${maven.version.range}</version>
                                </requireMavenVersion>
                                <requireJavaVersion>
                                    <version>${java.version}</version>
                                </requireJavaVersion>
                            </rules>
                            <fail>true</fail>
                        </configuration>
                    </execution>
                </executions>
            </plugin>

            <plugin>
                <groupId>com.google.appengine</groupId>
                <artifactId>appengine-maven-plugin</artifactId>
                <version>${appengine.target.version}</version>
                <configuration>
                    <useJava7>true</useJava7>
                    <address>127.0.0.1</address>
                    <port>8080</port>
                    <compileEncoding>utf-8</compileEncoding>
                    <jvmFlags>
                        <jvmFlag>-Xdebug</jvmFlag>
                        <jvmFlag>-Xrunjdwp:transport=dt_socket,address=1044,server=y,suspend=y</jvmFlag>
                        <jvmFlag>-Djavax.net.ssl.keyStore=C:\STEVEN-DEV\projects\apps\testserver\src\main\webapp\WEB-INF\myKeystore</jvmFlag>
                        <jvmFlag>-Djavax.net.ssl.keyStorePassword=testpass</jvmFlag>
                    </jvmFlags>
                </configuration>
            </plugin>
        </plugins>
    </build>

</project>

更新:我在 web.xml 中尝试过有和没有安全限制的情况

我不禁认为我需要找到一种方法来配置应用引擎插件使用的 Jetty 以使用 SSL

<?xml version="1.0" encoding="utf-8"?>
<web-app version="2.5" xmlns="http://java.sun.com/xml/ns/javaee"
    xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
    xsi:schemaLocation="http://java.sun.com/xml/ns/javaee http://java.sun.com/xml/ns/javaee/web-app_2_5.xsd">

    <display-name>Test Server</display-name>

    <!-- Spring MVC -->
    <servlet>
        <servlet-name>mvc-dispatcher</servlet-name>
        <servlet-class>org.springframework.web.servlet.DispatcherServlet</servlet-class>
        <load-on-startup>1</load-on-startup>
    </servlet>
    <servlet-mapping>
        <servlet-name>mvc-dispatcher</servlet-name>
        <url-pattern>/</url-pattern>
    </servlet-mapping>

    <listener>
        <listener-class>org.springframework.web.context.ContextLoaderListener</listener-class>
    </listener>

    <context-param>
        <param-name>contextConfigLocation</param-name>
        <param-value>/WEB-INF/mvc-dispatcher-servlet.xml, /WEB-INF/spring-security.xml</param-value>
    </context-param>

    <!-- Spring Security -->
    <filter>
        <filter-name>springSecurityFilterChain</filter-name>
        <filter-class>org.springframework.web.filter.DelegatingFilterProxy</filter-class>
    </filter>

    <filter-mapping>
        <filter-name>springSecurityFilterChain</filter-name>
        <url-pattern>/*</url-pattern>
    </filter-mapping>

    <security-constraint>
        <web-resource-collection>
            <web-resource-name>test</web-resource-name>
            <url-pattern>/test/*</url-pattern>
        </web-resource-collection>
        <user-data-constraint>
            <transport-guarantee>CONFIDENTIAL</transport-guarantee>
        </user-data-constraint>
    </security-constraint>
</web-app>
4

2 回答 2

2

如文档中所述,只需在security-contraint您的 src/main/webapp/WEB-INF/web.xml 文件中添加一个,以在您的应用程序的某些 URL 上强制使用 SSL(例如 /rest/*):

<?xml version="1.0" encoding="UTF-8"?>
<web-app xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns="http://java.sun.com/xml/ns/javaee" xmlns:web="http://java.sun.com/xml/ns/javaee/web-app_2_5.xsd" xsi:schemaLocation="http://java.sun.com/xml/ns/javaee http://java.sun.com/xml/ns/javaee/web-app_2_5.xsd" version="2.5">
    ...
    <security-constraint>
        <web-resource-collection>
            <url-pattern>/rest/*</url-pattern>
        </web-resource-collection>
        <user-data-constraint>
            <transport-guarantee>CONFIDENTIAL</transport-guarantee>
        </user-data-constraint>
    </security-constraint>
    ...
</web-app>

您应该能够在本地使用 HTTP 和 HTTPS。我不确定是否在 localhost 上强制执行仅 SSL 约束。一旦您将应用程序部署到 GAE,它将根据您的 web.xml 设置相应地强制执行。

于 2013-08-30T15:56:46.857 回答
2

我在上面的答案中将此作为评论发布,但我也应该将其放在这里:

根据文档

https://developers.google.com/appengine/docs/java/config/webxml#Secure_URLs

“开发 Web 服务器不支持 HTTPS 连接。它忽略了传输保证,因此可以使用与开发 Web 服务器的常规 HTTP 连接来测试用于 HTTPS 的路径。”

于 2014-02-06T19:28:59.553 回答