[英]What is the fastest way to stand up a REST service using Java?
我有一些用Java寫的實用程序方法,用於針對服務測試數據的創建。 我的幾個具有相同用例的同事認為,如果可以重用它會很酷,但是他們分別在Perl和Python中編寫測試。 因此,我正在考慮建立一個將公開這些方法的JSON REST服務。
我在編寫網絡應用方面經驗有限。 站起來並部署我的服務的最快方法是什么?
我正在考慮使用eclipse / spring來做,並將ant部署在Jetty容器上。 但我想聽聽您的經驗。 同樣,似乎某些IDE /插件對某些技術的支持要比對其他技術的更好。 因此,我想聽聽什么IDE /插件+ J2EE技術堆棧+服務器(如果很重要)對於我的用例以及原因是一個很好的組合。 我想堅持使用開源軟件。
我相信使用Maven可以使您盡快起步。 這是您的操作方法。
它使用JAX-RS的RESTEasy實現( RESTful Web Services的Java API ,Java EE 6的正式部分)。
這是一個Java War Maven項目,僅具有最小的結構。 這些是文件:
-pom.xml
-src
|
--main
|
--java
|
--rest
|
--HelloResource.java
--JaxRsActivator.java
我將其稱為simpleRest
,如下所示。 所有檔案均完全如圖所示:
<?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/maven-v4_0_0.xsd">
<modelVersion>4.0.0</modelVersion>
<groupId>simpleRest</groupId>
<artifactId>simpleRest</artifactId>
<version>1.0</version>
<packaging>war</packaging>
<dependencies>
<dependency>
<groupId>org.jboss.resteasy</groupId>
<artifactId>resteasy-jaxrs</artifactId>
<version>2.3.1.GA</version>
<scope>provided</scope>
</dependency>
</dependencies>
<build>
<finalName>${project.artifactId}</finalName>
<plugins>
<plugin>
<artifactId>maven-war-plugin</artifactId>
<version>2.1.1</version>
<configuration>
<!-- So maven doesn't require web.xml -->
<failOnMissingWebXml>false</failOnMissingWebXml>
</configuration>
</plugin>
</plugins>
</build>
</project>
package rest;
import java.util.Date;
import javax.ws.rs.GET;
import javax.ws.rs.Path;
import javax.ws.rs.Produces;
@Path("/hello")
public class HelloResource {
@GET
@Produces("text/plain")
public String helloResource() {
return "Hello! It's "+new Date();
}
}
package rest;
import javax.ws.rs.ApplicationPath;
import javax.ws.rs.core.Application;
@ApplicationPath("/rest")
public class JaxRsActivator extends Application {
}
這將生成一個simpleRest.war
(通過mvn clean package
)。 您可以將其部署到新安裝的JBoss AS 7.1.1.Final (只需將war文件扔到deploy文件夾中)或Tomcat中 。
之后,URL可以按預期使用:
http://127.0.0.1:8080/simpleRest/rest/hello
那有多快?
對於僅需要Java, Gradle和文本編輯器的全功能REST API,這是我想到的最短方法。 在干凈的項目目錄中創建兩個文件,如下所示:
build.gradle
buildscript {
repositories { mavenCentral() }
dependencies {
classpath 'org.gradle.api.plugins:gradle-tomcat-plugin:0.9.8'
}
}
apply plugin: 'tomcat'
repositories { mavenCentral() }
dependencies {
compile(
'com.sun.jersey:jersey-core:1.17',
'com.sun.jersey:jersey-server:1.17',
'com.sun.jersey:jersey-servlet:1.17',
'com.sun.jersey:jersey-json:1.17',
)
tomcat(
'org.apache.tomcat:tomcat-catalina:7.0.40',
'org.apache.tomcat:tomcat-coyote:7.0.40',
'org.apache.tomcat:tomcat-jasper:7.0.40',
)
}
src / main / java / org / example / TheApplication.java
package org.example;
import com.sun.jersey.api.core.ClassNamesResourceConfig;
import javax.ws.rs.*;
import javax.ws.rs.core.Response;
import javax.xml.bind.annotation.XmlRootElement;
@Path("/")
@ApplicationPath("/")
public class TheApplication extends ClassNamesResourceConfig {
public TheApplication() { super(TheApplication.class); }
static Foo foo = new Foo();
@GET @Produces("application/json")
public Foo getFoo() {
return foo;
}
@POST @Consumes("application/json")
public Response setFoo(Foo foo) {
TheApplication.foo = foo;
return Response.ok().entity("Stored it!").build();
}
@XmlRootElement
static class Foo {
private String message = "Hello World";
public String getMessage() { return message; }
public void setMessage(String message) { this.message = message; }
}
}
一旦這兩個文件到位, gradle tomcatRunWar
將啟動您的REST API,並且在瀏覽器中導航到http://localhost:8080/fastest-web-service/
將為您提供“ Hello World” JSON消息。 然后,如果您將類似的JSON(例如{"message": "something else"}
到相同的URL,並使用curl或Poster指定了Content-Type為“ application / json”,則該新對象將被存儲並在后續的操作中返回GET請求。 這只是一個非常簡單的示例,但涵蓋了JSON API的許多基礎知識。
IDE :您可以使用任何常見的Java IDE輕松地進一步開發它。 IntelliJ IDEA和Eclipse的社區版都是流行的免費IDE。 <opinion>
IDEA的優勢要大得多,而Ultimate Edition的價格是普通Java開發人員的個人許可證費用的110%。 </opinion>
技術堆棧 : JAX-RS是用Java編寫REST API的領先方法。 選擇任何實現。 本示例使用Jersey ,參考實現。 如果您只需要一個簡單的API來公開已經編寫的邏輯,那么Spring可能會顯得過大。 它帶來的復雜性超出了您的需求。 另一方面,如果您需要一個更靈活,功能更強大的框架,並且對世界上的幾乎所有事物都具有更多的內置支持,那么Spring可能只是問題而已。
好吧,我將把與GlassFish 3.x捆綁在一起的NetBeans IDE扔進去。
下載該軟件包,安裝它,並且提供服務的JAX-RS是一個右鍵單擊向導。 一鍵下載,一安裝,全面。 許多文檔,向導和示例。
這確實是最短的路徑,並且是一個完整的工具箱。
我們公司要使用的是Apache TomEE服務器,它使用JAX-RS將我們的API公開為REST服務。 它易於設置且易於使用。
我在Jersey方面有很好的經驗,它是jax-ws的參考實現。 它支持jax-ws批注,並且易於使用。
作為顧問,我因解決問題而得到報酬。 我發現Espresso Logic是我交付JSON / REST API最快的方法。 它運行在Tomcat基礎上,可以輕松地在本地,Elastic Beanstalk或Microsoft Azure上部署。 它連接到所有主要的SQL數據庫,並為我提供了用於所有表,視圖,存儲過程和關系(用於構建更復雜的文檔樣式資源)的即時REST API。 它同時具有HTML Studio和用於管理的Node.JS命令行。 最好的功能是用於公式,推導和驗證的聲明性邏輯(如電子表格)。 可以使用JavaScript和Java插件庫來擴展邏輯。 我花時間編寫JavaScript解決方案,並讓Espresso進行REST分頁,樂觀鎖定,SQL查詢優化和多表事務邏輯的繁重工作。 全面披露-我已經認識他們25年了,這是我所見過的最好的改變游戲規則的技術。 檢查出來:www.espressologic.com
我想建議以下方法來編寫基於REST的Web服務。 下面的“腳本”將指導您使用Kikaha和Undertow創建一個非常簡單,輕便的Web項目。 這種波紋管方法與Ryan Stewart提供的基於JAXRS的示例非常相似,但是由於Undertow的體系結構,Undertow具有較高的性能和較低的占用空間(Undertow 確實非常快 )。
使用Kikaha的命令行工具創建一個存根項目:
kikaha項目創建2.0 --name = my-app
盡管上面的命令為您帶來了一些現成的REST API類,但是您可以創建代表您的業務規則的自己的實體類,如下所示。
User.java
import lombok.*;
@Getter
@Setter
public class User {
@NonNull Long id;
@NonNull String name;
}
UserResource.java
import lombok.*;
import kikaha.urouting.api.*;
import javax.inject.*;
@Singleton
@Path("user")
@Consumes( Mimes.JSON )
@Produces( Mimes.JSON )
public class UserResource {
User savedUser;
@POST
public Response saveUser( User user ){
if ( user.getName().isEmpty() )
return DefaultResponses.preconditionFailed()
.entity("Name is blank");
savedUser = user;
return DefaultResponses.ok();
}
@GET
public User getUser(){
return savedUser;
}
}
通過命令行運行5Mb項目:
kikaha運行應用
免責聲明 :我參與了Kikaha的開發工作,並且自從發布第一個版本以來就植入了許多Undertow項目。
為了按照https://stackoverflow.com/a/3891380/1497139的方式使用Jersey框架來加快速度
我們(BITPlan-我的公司)創建了以下開源項目:
請參閱下面的代碼示例如何設置:
package com.bitplan.simplerest.example;
import static org.junit.Assert.*;
import org.junit.Before;
import org.junit.Test;
import com.bitplan.rest.RestServer;
import com.bitplan.rest.test.TestRestServer;
/**
* test the example Server
* @author wf
*
*/
public class TestExampleServer extends TestRestServer {
boolean debug=true;
@Before
public void initServer() throws Exception {
startServer();
}
@Override
public RestServer createServer() throws Exception {
RestServer result = new ExampleServer();
return result;
}
@Test
public void testExampleServer() throws Exception {
String userXml=getResponseString("application/xml", "/example/user");
if (debug)
System.out.println(userXml);
String expected="<?xml version=\"1.0\" encoding=\"UTF-8\" standalone=\"yes\"?><user><name>Doe</name><firstname>John</firstname><email>john@doe.org</email></user>";
assertEquals(expected,userXml);
String userJson=getResponseString("application/json", "/example/user");
if (debug)
System.out.println(userJson);
String expectedJson="{\"name\":\"Doe\",\"firstname\":\"John\",\"email\":\"john@doe.org\"}";
assertEquals(expectedJson,userJson);
}
}
package com.bitplan.simplerest.example;
import com.bitplan.rest.RestServerImpl;
/**
* an Example Server
* @author wf
*
*/
public class ExampleServer extends RestServerImpl {
/**
* construct Example Server
* setting defaults
* @throws Exception
*/
public ExampleServer() throws Exception {
// listen to whole network
settings.setHost("0.0.0.0");
// listen on given port
settings.setPort(8111);
// add the default path
settings.setContextPath("/example");
// add a static handler
settings.addClassPathHandler("/", "/static/");
// setup resources from the given packages
String packages="com.bitplan.simplerest.example.resources;";
settings.setPackages(packages);
}
/**
* start Server
*
* @param args
* @throws Exception
*/
public static void main(String[] args) throws Exception {
ExampleServer rs=new ExampleServer();
rs.settings.parseArguments(args);
rs.startWebServer();
} // main
}
package com.bitplan.simplerest.example;
import javax.xml.bind.annotation.XmlAccessType;
import javax.xml.bind.annotation.XmlAccessorType;
import javax.xml.bind.annotation.XmlRootElement;
/**
* example class
*/
@XmlRootElement
@XmlAccessorType(XmlAccessType.FIELD)
public class User {
public String name;
public String firstname;
public String email;
}
package com.bitplan.simplerest.example.resources;
import javax.ws.rs.GET;
import javax.ws.rs.Path;
import com.bitplan.simplerest.example.User;
@Path("/user")
public class UserResource {
@GET
public User getUser() {
User user=new User();
user.name="Doe";
user.firstname="John";
user.email="john@doe.org";
return user;
}
}
所有答案都適用於通過本地容器在本地使用Java。 如果您正在考慮支持Java(和類似Java的擴展)的雲環境,則可能僅需使用一種即可。
Raimme平台提供了方便的@Rest批注。 您所需要做的就是設置URL,您的REST服務將自動公開:
@Rest(url = "customer/list")
@ResponseBody
public String getCustomer()
{
return "[]";
}
此處將詳細描述整個功能: http : //raimme.com/devcenter?questionId=1cg000000000g
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.