原文:http://zetcode.com/java/spark/
这是 Spark Java Web 框架的入门教程。 我们介绍了 Spark Java 框架,并提供了三个代码示例。
Spark Java
Spark 是一个 Java 微框架,用于以最小的工作量在 Java8 中创建 Web 应用。 Spark 框架是为快速开发而构建的简单,轻量级的 Java Web 框架。 它的灵感来自流行的 Ruby 微框架 Sinatra 。
Spark 广泛使用 Java8 的 lambda 表达式,这使 Spark 应用不再那么冗长。 与其他 Java Web 框架相比,Spark 不使用大量的 XML 文件或注解。
路由
Spark 应用包含一组路由。 路由将 URL 模式映射到 Java 处理器。
路由包含三个部分:
- 动词,包括获取,发布,放置,删除,开头,跟踪,连接和选项
- 诸如
/first或/hello/:name之类的路径 - 回调
(request, response) -> {}
首个应用
第一个应用返回一条简单消息。 Gradle 用于构建应用。
$ tree.├── build.gradle└── src└── main└── java└── com└── zetcode└── firstspark└── FirstSpark.java
这是项目结构。 Gradle 的 Java 插件期望 Java 生产代码位于src/main/java目录中。
build.gradle
apply plugin: 'java'apply plugin: 'application'archivesBaseName = "first"version = '1.0'mainClassName = "com.zetcode.firstspark.FirstSpark"repositories {mavenCentral()}dependencies {compile 'com.sparkjava:spark-core:2.5'compile 'org.slf4j:slf4j-simple:1.7.6'}
这是 Gradle 构建文件。 它包括 Spark 核心组件和 slf4j 简单记录器的依赖项。
FirstSpark.java
package com.zetcode.firstspark;import static spark.Spark.get;public class FirstSpark {public static void main(String[] args) {get("/first", (req, res) -> "First Spark application");}}
应用将"First Spark application"返回到 GET 请求。 当我们运行应用时,Spark 将启动嵌入式 Jetty Web 服务器。
get("/first", (req, res) -> "First Spark application");
get()方法映射 HTTP GET 请求的路由。 在 Spark 术语中,路由是处理器。路由是映射到处理器的 URL 模式。 处理器可以是物理文件,也可以是
$ gradle build
我们使用gradle build命令构建应用。
$ gradle run
我们使用gradle run命令运行该应用。 嵌入式 Jetty 服务器启动。
$ curl localhost:4567/firstFirst Spark application
我们使用curl工具将 GET 请求发送到服务器。 内置嵌入式 Jetty 服务器默认情况下监听端口 4567。
你好应用
第二个应用将向用户打招呼。 客户端发送带有 URL 的名称,应用向用户打招呼。
build.gradle
apply plugin: 'java'apply plugin: 'application'archivesBaseName = "hello"version = '1.0'mainClassName = "com.zetcode.hellospark.HelloSpark"repositories {mavenCentral()}dependencies {compile 'com.sparkjava:spark-core:2.5'compile 'org.slf4j:slf4j-simple:1.7.6'}
这是应用的 Gradle 构建文件。
$ tree.├── build.gradle└── src└── main└── java└── com└── zetcode└── hellospark└── HelloSpark.java6 directories, 2 files
这是项目结构。
HelloSpark.java
package com.zetcode.hellospark;import static spark.Spark.get;public class HelloSpark {public static void main(String[] args) {get("/hello/:name", (req, res) -> "Hello " + req.params(":name"));}}
Spark 应用检索请求参数,生成一条消息,然后将其返回给调用方。
get("/hello/:name", (req, res) -> "Hello " + req.params(":name"));
params()方法返回提供的路由模式参数的值。
$ gradle build run
我们构建并运行该应用。
$ curl localhost:4567/hello/PeterHello Peter
我们向服务器发送请求; URL 包含一个名称。 该应用发回问候。
在 Tomcat 中运行 Spark 应用
默认情况下,Spark 应用在嵌入式 Jetty 服务器中运行。 在此示例中,我们显示了如何在 Tomcat 中运行 Spark Java 应用。 这次我们使用 Maven 构建工具并在 NetBeans 中创建一个项目。

图:NetBeans 项目结构
该图显示了该项目在 NetBeans 中的外观。
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><groupId>com.zetcode</groupId><artifactId>HelloSpark2</artifactId><version>1.0-SNAPSHOT</version><packaging>war</packaging><name>HelloSpark2</name><properties><endorsed.dir>${project.build.directory}/endorsed</endorsed.dir><project.build.sourceEncoding>UTF-8</project.build.sourceEncoding></properties><dependencies><dependency><groupId>com.sparkjava</groupId><artifactId>spark-core</artifactId><version>2.5</version></dependency><dependency><groupId>org.slf4j</groupId><artifactId>slf4j-simple</artifactId><version>1.7.21</version></dependency></dependencies><build><plugins><plugin><groupId>org.apache.maven.plugins</groupId><artifactId>maven-compiler-plugin</artifactId><version>3.1</version><configuration><source>1.8</source><target>1.8</target><compilerArguments><endorseddirs>${endorsed.dir}</endorseddirs></compilerArguments></configuration></plugin><plugin><groupId>org.apache.maven.plugins</groupId><artifactId>maven-war-plugin</artifactId><version>2.3</version><configuration><failOnMissingWebXml>false</failOnMissingWebXml></configuration></plugin></plugins></build></project>
这是 Maven 构建文件。
context.xml
<?xml version="1.0" encoding="UTF-8"?><Context path="/HelloSpark2"/>
这是context.xml文件。
web.xml
<?xml version="1.0" encoding="UTF-8"?><web-app xmlns="http://xmlns.jcp.org/xml/ns/javaee"xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"xsi:schemaLocation="http://xmlns.jcp.org/xml/ns/javaee http://xmlns.jcp.org/xml/ns/javaee/web-app_3_1.xsd"version="3.1"><welcome-file-list><welcome-file>index.html</welcome-file></welcome-file-list><filter><filter-name>SparkFilter</filter-name><filter-class>spark.servlet.SparkFilter</filter-class><init-param><param-name>applicationClass</param-name><param-value>com.zetcode.hellospark2.HelloSpark</param-value></init-param></filter><filter-mapping><filter-name>SparkFilter</filter-name><url-pattern>/*</url-pattern></filter-mapping></web-app>
在web.xml部署描述符中,我们指定spark.servlet.SparkFilter。
HelloSpark.java
package com.zetcode.hellospark2;import static spark.Spark.get;import spark.servlet.SparkApplication;public class HelloSpark implements SparkApplication {@Overridepublic void init() {get("/hello/:name", (request, response) -> "Hello " + request.params(":name"));}}
我们实现SparkApplication接口,并在init()方法中指定路由。
最后,我们运行 Tomcat Web 服务器。
$ curl localhost:8084/HelloSpark2/hello/PeterHello Peter
NetBeans 的内置 Tomcat 监听端口 8084。
模板引擎
Spark 没有自己的模板系统。 它使用第三方引擎。 在以下两个示例中,我们使用 Thymeleaf 和 FreeMarker。
使用 Thymeleaf
在以下示例中,我们将把 Thymeleaf 模板引擎集成到我们的 Spark 应用中。 Thymeleaf 是适用于 Web 和独立环境的现代服务器端 Java 模板引擎。
$ tree.├── build.gradle└── src└── main├── java│ └── com│ └── zetcode│ └── thymeleaf│ └── SparkThymeleaf.java└── resources└── templates└── hello.html
这是项目的目录结构。 模板文件位于src/main/resources/templates目录中。
build.gradle
apply plugin: 'java'apply plugin: 'application'archivesBaseName = "sparkthymeleaf"version = '1.0'mainClassName = "com.zetcode.thymeleaf.SparkThymeleaf"repositories {mavenCentral()}dependencies {compile 'com.sparkjava:spark-core:2.5'compile 'org.slf4j:slf4j-simple:1.7.6'compile 'com.sparkjava:spark-template-thymeleaf:2.3'}
在这里,我们有 Gradle 构建文件,其中包含spark-template-thymeleaf依赖项。
SparkThymeleaf.java
package com.zetcode.thymeleaf;import java.util.HashMap;import java.util.Map;import spark.ModelAndView;import spark.Request;import spark.Response;import spark.template.thymeleaf.ThymeleafTemplateEngine;import static spark.Spark.get;import static spark.Spark.staticFileLocation;public class SparkThymeleaf {public static void main(String[] args) {get("/hello/:name", SparkThymeleaf::message, new ThymeleafTemplateEngine());}public static ModelAndView message(Request req, Response res) {Map<String, Object> params = new HashMap<>();params.put("name", req.params(":name"));return new ModelAndView(params, "hello");}}
应用读取请求参数并将其放入ModelAndView对象。
get("/hello/:name", SparkThymeleaf::message, new ThymeleafTemplateEngine());
ThymeleafTemplateEngine的实例传递给get()方法。
hello.html
<pre class="code"><!DOCTYPE html><html lang="en" xmlns="http://www.w3.org/1999/xhtml" xmlns:th="http://www.thymeleaf.org"><head><meta charset="UTF-8"></meta><title>Hello user</title></head><body><p th:inline="text">Hello, [[${name}]]!</p></body></html>
这是hello.html模板文件。 它引用随ModelAndView对象传递的名称变量。
$ curl localhost:4567/hello/Peter<!DOCTYPE html><html lang="en" xmlns="http://www.w3.org/1999/xhtml"><head><meta charset="UTF-8" /><title>Hello user</title></head><body><p>Hello, Peter!</p></body></html>
我们得到这个输出。
FreeMarker
在以下示例中,我们将把 FreeMarker 模板引擎集成到我们的 Spark 应用中。 FreeMarker 是一个完善的 Java 模板引擎。
$ tree.├── build.gradle└── src└── main├── java│ └── com│ └── zetcode│ └── SparkFreeMarker.java└── resources└── views└── hello.ftl
这是项目的目录结构。 模板文件位于src/main/resources/views目录中。
build.gradle
apply plugin: 'application'sourceCompatibility = '1.8'version = '1.0'mainClassName = "com.zetcode.SparkFreeMarker"repositories {mavenCentral()}dependencies {compile 'com.sparkjava:spark-core:2.5.5'compile 'org.slf4j:slf4j-simple:1.7.24'compile 'com.sparkjava:spark-template-freemarker:2.5.5'}
在这里,我们有 Gradle 构建文件,其中包含spark-template-freemarker依赖项。
SparkFreeMarker.java
package com.zetcode;import freemarker.template.Configuration;import freemarker.template.Version;import java.io.IOException;import java.util.HashMap;import java.util.Map;import spark.ModelAndView;import spark.Request;import spark.Response;import static spark.Spark.get;import spark.template.freemarker.FreeMarkerEngine;public class SparkFreeMarker {public static void main(String[] args) throws IOException {Configuration conf = new Configuration(new Version(2, 3, 23));conf.setClassForTemplateLoading(SparkFreeMarker.class, "/views");get("/hello/:name", SparkFreeMarker::message, new FreeMarkerEngine(conf));}public static ModelAndView message(Request req, Response res) {Map<String, Object> params = new HashMap<>();params.put("name", req.params(":name"));return new ModelAndView(params, "hello.ftl");}}
我们为 FreeMarker 设置了相同的应用。
Configuration conf = new Configuration(new Version(2, 3, 23));conf.setClassForTemplateLoading(SparkFreeMarker.class, "/views");
我们用Configuration类配置 FreeMarker。 模板文件将放置在views目录中,该目录必须位于类路径上。
get("/hello/:name", SparkFreeMarker::message, new FreeMarkerEngine(conf));
FreeMarkerEngine传递给get()方法。
hello.ftl
<!DOCTYPE html><html><head><title>Home page</title><meta charset="UTF-8"><meta name="viewport" content="width=device-width, initial-scale=1.0"></head><body><p>Hello ${name}</p></body></html>
这是hello.ftl模板文件; 它引用随ModelAndView对象传递的名称变量。
$ curl localhost:4567/hello/Lucy<!DOCTYPE html><html><head><title>Home page</title><meta charset="UTF-8"><meta name="viewport" content="width=device-width, initial-scale=1.0"></head><body><p>Hello Lucy</p></body></html>
这是输出。
在本教程中,我们介绍了 Spark Java 框架。 您可能也对相关教程感兴趣: Java 教程,游戏介绍,Stripes 介绍或 Jtwig 教程。
