1. 程式人生 > >Jetty實戰之 maven+嵌入式Jetty執行web app

Jetty實戰之 maven+嵌入式Jetty執行web app

ApacheMaven是一個軟體專案管理和理解工具。基於專案物件模型(POM)內容,Maven能夠通過資訊中心管理一個專案構建、報告和文件。它是一個理想的工具用來構建Web應用專案。這專案可以使用Jetty Maven外掛在部署模式下執行Web應用。

       你能使用Maven來構建嵌入式Jetty應用程式和標準的基於Web應用。

為了理解使用Jetty構建和執行的基本操作,首先閱讀:

1) Jetty HelloWorld教程

http://wiki.eclipse.org/Jetty/Tutorial/Jetty_HelloWorld

2) 嵌入Jetty教程

http://wiki.eclipse.org/Jetty/Tutorial/Embedding_Jetty

使用Maven配置嵌入式Jetty

       Maven使用約定優先於配置,因此最好使用Maven的專案結構,正如Maven推薦的。你能使用Archetypes快速設定Maven專案,但是對於本教程,我們將手動的設定結構:

mkdir JettyMavenHelloWorld

cd JettyMavenHelloWorld

mkdir -p src/main/java/org/example

建立HelloWorld類

       使用編輯器建立一個檔案src/main/java/org/example/HelloWorld.java,內容如下:

package org.example;

importjavax.servlet.http.HttpServletRequest;

importjavax.servlet.http.HttpServletResponse;

import javax.servlet.ServletException;

import java.io.IOException;

import org.eclipse.jetty.server.Server;

import org.eclipse.jetty.server.Request;

importorg.eclipse.jetty.server.handler.AbstractHandler;

public class HelloWorld extendsAbstractHandler

{

   public void handle(String target,

                       Request baseRequest,

                       HttpServletRequestrequest,

                       HttpServletResponseresponse)

       throws IOException, ServletException

    {

       response.setContentType("text/html;charset=utf-8");

       response.setStatus(HttpServletResponse.SC_OK);

       baseRequest.setHandled(true);

       response.getWriter().println("<h1>HelloWorld</h1>");

    }

   public static void main(String[] args) throws Exception

    {

       Server server = new Server(8080);

       server.setHandler(new HelloWorld());

       server.start();

       server.join();

    }

}

建立POM描述

       pom.xml宣告專案名稱及其依賴。使用編輯器建立一個pom.xml檔案,內容如下:<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.0http://maven.apache.org/maven-v4_0_0.xsd">

 <modelVersion>4.0.0</modelVersion>

 <groupId>org.example</groupId>

 <artifactId>hello-world</artifactId>

 <version>0.1-SNAPSHOT</version>

 <packaging>jar</packaging>

 <name>Jetty HelloWorld</name>

 <properties>

   <jettyVersion>9.0.2.v20130417</jettyVersion>

 </properties>

 <dependencies>

   <dependency>

     <groupId>org.eclipse.jetty</groupId>

     <artifactId>jetty-server</artifactId>

     <version>${jettyVersion}</version>

   </dependency>

 </dependencies>

 <build>

   <plugins>

     <plugin>

       <!-- This plugin is needed for the servlet example -->

       <groupId>org.mortbay.jetty</groupId>

       <artifactId>jetty-maven-plugin</artifactId>

       <version>${jettyVersion}</version>

     </plugin>

     <plugin>

       <groupId>org.codehaus.mojo</groupId>

       <artifactId>exec-maven-plugin</artifactId>

       <version>1.1</version>

       <executions>

         <execution><goals><goal>java</goal></goals></execution>

       </executions>

       <configuration>

         <mainClass>org.example.HelloWorld</mainClass>

       </configuration>

     </plugin>

   </plugins>

 </build>

</project>

       注:使用9.0.2.v20130417版本可以找到下面的類:

importorg.eclipse.jetty.server.handler.AbstractHandler;

    但是使用Jetty的最新版本9.2.3.v20140905無法匯入該類。

構建和執行嵌入式HelloWorld

       你現在能夠使用下面的命令編譯和執行HelloWorld類。

mvn clean compile exec:java

       你能使用瀏覽器開啟http://localhost:8080看到Hello world頁面。你能使用mvndependency:tree命令檢視Maven幕後為你做了什麼。它揭露解析和下載的依賴關係,如下:

> mvn dependency:tree

[INFO] Scanning for projects...

[INFO] Searching repository for plugin withprefix: 'dependency'.

[INFO] ------------------------------------------------------------------------

[INFO] Building Jetty HelloWorld

[INFO]   task-segment: [dependency:tree]

[INFO]------------------------------------------------------------------------

[INFO] [dependency:tree {execution:default-cli}]

[INFO]org.example:hello-world:jar:0.1-SNAPSHOT

[INFO] \-org.eclipse.jetty:jetty-server:jar:7.0.1.v20091125:compile

[INFO]   +- javax.servlet:servlet-api:jar:2.5:compile

[INFO]   +- org.eclipse.jetty:jetty-continuation:jar:7.0.1.v20091125:compile

[INFO]   \- org.eclipse.jetty:jetty-http:jar:7.0.1.v20091125:compile

[INFO]      \- org.eclipse.jetty:jetty-io:jar:7.0.1.v20091125:compile

[INFO]          \-org.eclipse.jetty:jetty-util:jar:7.0.1.v20091125:compile

[INFO] ------------------------------------------------------------------------

[INFO] BUILD SUCCESSFUL

[INFO]------------------------------------------------------------------------

[INFO] Total time: 4 seconds

[INFO] Finished at: Tue Feb 16 16:19:08 EST2010

[INFO] Final Memory: 11M/68M

[INFO]------------------------------------------------------------------------

使用Jetty和Maven開發標準WebApp

       上面的例子顯示如何使用嵌入式Jetty處理器執行Hello world示例。下面的示例顯示如何使用Maven和Jetty開發一個標準的WebApp。首先建立Maven結構。

mkdir JettyMavenHelloWarApp

cd JettyMavenHelloWarApp

mkdir -p src/main/java/org/example

mkdir -p src/main/webapp/WEB-INF

       建立靜態內容:

       一個Web應用可以包含靜態內容,因此建立檔案src/main/webapp/index.html,內容如下:

<h1>Hello World Webapp</h1>

<a href="/hello">HelloServlet</a>

       建立一個Servlet

       使用編輯器建立src/main/java/org/example/HelloServlet.java,內容如下:

package org.example;

import java.io.IOException;

import javax.servlet.ServletException;

import javax.servlet.http.HttpServlet;

importjavax.servlet.http.HttpServletRequest;

import javax.servlet.http.HttpServletResponse;

public class HelloServlet extendsHttpServlet

{

   protected void doGet(HttpServletRequest request, HttpServletResponseresponse) throws ServletException, IOException

    {

       response.setContentType("text/html");

       response.setStatus(HttpServletResponse.SC_OK);

       response.getWriter().println("<h1>HelloServlet</h1>");

       response.getWriter().println("session=" +request.getSession(true).getId());

    }

}

該Servlet需要在部署描述中宣告,因此編譯src/main/webapp/WEB-INF/web.xml,新增如下內容。

<?xml version="1.0"encoding="ISO-8859-1"?>

<web-app

  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/javaeehttp://java.sun.com/xml/ns/javaee/web-app_2_5.xsd"

  version="2.5">

 <servlet>

   <servlet-name>Hello</servlet-name>

   <servlet-class>org.example.HelloServlet</servlet-class>

 </servlet>

 <servlet-mapping>

   <servlet-name>Hello</servlet-name>

   <url-pattern>/hello/*</url-pattern>

 </servlet-mapping>

</web-app>

       構建和執行Web應用:

       拷貝pom.xml,使用下面命令構建和執行Web應用。

mvn jetty:run

       你能在http://localhost:8080/hello-world/hello看到靜態和動態的內容。內容的路徑是url(hello-world)的一部分,來自於pom.xml檔案中的人工ID。

構建WAR檔案:

你能為專案建立一個WebApplication Archive(WAR)檔案,使用命令:

mvn package

生成的war檔案位於target目錄中,你可以把它部署到標準servlet服務上或者部署到Jetty上。

啟用SSL

       在嵌入式Jetty 9中啟用SSL的過程如下:

       1)首先使用解釋安全方案和埠的HTTP配置建立一個HttpConfiguration。

HttpConfiguration http_config = newHttpConfiguration();

http_config.setSecureScheme("https");

http_config.setSecurePort(8443);

       然後,我們為從上面的配置中擴充套件的https建立另外一個HttpConfiguration,但是新增一個SecureRequestCustomizer。

HttpConfiguration https_config = newHttpConfiguration(http_config);

https_config.addCustomizer(newSecureRequestCustomizer());

       3)接下來建立一個SslContexFactory指向你的JavaKeystore檔案。

SslContextFactory sslContextFactory = newSslContextFactory("/its_dir/cert.keystore");

sslContextFactory.setKeyStorePassword("password");

       注意:你能使用OBF字首密碼,如果你打算使用Jetty模糊的密碼。

     4)接下來我們建立一個ServerConnector,傳遞給它Server類,SslConnectorFactory和HttpConnectionFactory。如下:

ServerConnector httpsConnector = newServerConnector(server,

      new SslConnectionFactory(sslContextFactory, "http/1.1"),

      new HttpConnectionFactory(https_config));

httpsConnector.setPort(8443);

httpsConnector.setIdleTimeout(50000);      

       最後使用這個連線給服務,與正常的HTPP ServerConnector一樣。

server.setConnectors(new Connector[]{httpsConnector });

與Jersey一起使用

下載網址:

       你能在程式碼中混合使用Jersey的2個版本,來自Jersey2.x(org.glassfish.jersey*包)中的ServletContainer和來自Jersey 1.x(包字首com.sum.jersey.*)的屬性。

       為了使用Jersey2.x開發你的應用,修改下面兩行:

h.setInitParameter("com.sun.jersey.config.property.resourceConfigClass","com.sun.jersey.api.core.PackagesResourceConfig");

h.setInitParameter("com.sun.jersey.config.property.packages","resources");

       從main方法到下面函式中:

       h.setInitParameter(ServerProperties.PROVIDER_PACKAGES,"resources");

       並且檢查其他ServerProperties,你可能找到有用的。