我在一个应用程序中有两个单独的REST服务.让我们说一个主要的"人"服务和一个辅助"管理"服务.我想要的是在服务器上的不同路径中公开它们.我正在使用JAX-RS,RESTEasy和Spring.
例:
@Path("/people")
public interface PeopleService {
// Stuff
}
@Path("/management")
public interface ManagementService {
// Stuff
}
Run Code Online (Sandbox Code Playgroud)
在web.xml我目前有如下设置:
<listener>
<listener-class>org.jboss.resteasy.plugins.server.servlet.ResteasyBootstrap</listener-class>
</listener>
<listener>
<listener-class>org.jboss.resteasy.plugins.spring.SpringContextLoaderListener</listener-class>
</listener>
<context-param>
<param-name>resteasy.servlet.mapping.prefix</param-name>
<param-value>/public</param-value>
</context-param>
<servlet>
<servlet-name>Resteasy</servlet-name>
<servlet-class>
org.jboss.resteasy.plugins.server.servlet.HttpServletDispatcher
</servlet-class>
</servlet>
<servlet-mapping>
<servlet-name>Resteasy</servlet-name>
<url-pattern>/public/*</url-pattern>
</servlet-mapping>
Run Code Online (Sandbox Code Playgroud)
在PeopleService和ManagementService实施只是春豆.上面的web.xml配置将它们都暴露在外/public(因此分别具有/public/people和/public/management).
我想要完成的是暴露PeopleServiceon /public,以便完整路径将成为/public/people并暴露ManagementServiceon /internal,以便它的完整路径将成为/internal/management.
不幸的是,我无法更改@Path注释的值.
我该怎么办?
在webservice调用中,我想用这个JSON结构返回我的对象.
{
"date" : "30/06/2014",
"price" : {
"val" : "12.50",
"curr" : "EUR"
}
}
Run Code Online (Sandbox Code Playgroud)
我想将这个JSON代码映射到这个Java结构(使用joda-time和joda-money):
public class MyResponse {
LocalDate date;
Money price;
}
Run Code Online (Sandbox Code Playgroud)
我的网络服务目前看起来像这样:
@javax.ws.rs.POST
@javax.ws.rs.Path("test")
@javax.ws.rs.Produces({MediaType.APPLICATION_JSON})
@javax.ws.rs.Consumes({MediaType.APPLICATION_JSON})
public MyResponse test(MyRequest request) {
MyResponse response = new MyResponse();
response.setDate(LocalDate.now());
response.setMoney(Money.parse("EUR 12.50"));
return response;
}
Run Code Online (Sandbox Code Playgroud)
所以我的问题是:我在哪里注册一个自定义处理程序来格式化我想要的日期以及货币表示?
特别是在JAX-RS中(我不确定是否相关)有一些方法允许您将EntityTags添加到响应中.究竟什么是实体标签以及它们使用的实用方法?
是否可以配置GET方法来读取可变数量的URI参数并将它们解释为变量参数(数组)或集合?我知道查询参数可以作为列表/集读取,但在我的情况下我不能用它们.
例如:
@GET
@Produces("text/xml")
@Path("list/{taskId}")
public String getTaskCheckLists(@PathParam("taskId") int... taskId) {
return Arrays.toString(taskId);
}
Run Code Online (Sandbox Code Playgroud)
提前致谢
在Adam Bien的博客上阅读文章时,我在使用EJB 3.1时发现了java restful中的一个新功能.
问题是Stateless和Singleton bean可以作为root资源公开.但是怎么样?我试着这样做:
@Stateless
@LocalBean
@Path("Hybrid")
public class RESTEJBSample {
@GET
@Path("/demo")
@Produces(MediaType.TEXT_PLAIN)
public String something() {
return "I am a Hybrid!!!";
}
}
Run Code Online (Sandbox Code Playgroud)
当我调用URL http:// localhost:8080/HybridSample/resources/Hybrid/demo时,我收到404错误.
为了确保JAXRS正在我的项目中工作,我创建了一个简单的pojo资源,以测试它是否正常工作.
@Path("/genericresource")
public class GenericResource {
@GET
@Path("/samplemethod")
@Produces(MediaType.TEXT_PLAIN)
public String saySomething() {
return "Something!";
}
}
Run Code Online (Sandbox Code Playgroud)
这里当我调用URL http:// localhost:8080/HybridSample/resources/genericresource/samplemethod它工作正常!
所以我的问题是:
我的EJB中缺少什么,所以它可以作为Web服务资源,如GenericResource类正在做什么?
是否需要一些额外的配置?
使用EJB作为Web服务有什么限制?
我正在尝试向媒体类型设置为的jaxrs服务执行请求multipart/form-data.此请求包含实体列表(xml)和图像(png,二进制).我已经创建了BalusC 在此主题中描述的请求.
在wireshark中检查它之后,请求似乎没问题,除了ip头校验和错误.(说"可能是由IP校验和卸载引起的".)
这里我的大问题是如何在服务端处理多部分请求.我不希望包含来自apache.cxf,resteasy或任何类型的任何库.我想要依赖的是jaxrs api.
这两部分的要求有名字deliveries和signature,其中签名是发送二进制PNG图像文件.应该从xml解析交付列表(实体具有xmlrootelement注释等,因此这部分单独工作).我尝试用这种方式阅读不同的部分,但这真的是一个长期的结果;
@PUT
@Path("signOff")
@Consumes(MediaType.MULTIPART_FORM_DATA)
public void signOffDeliveries(@FormParam("deliveries") List<Delivery> deliveries, @FormParam("signature")File signature) {
//do something with the signature(image) and the list of deliveries.
}
Run Code Online (Sandbox Code Playgroud)
这当然不起作用,如果我在Websphere上运行请求,它会给我一个404 http状态代码,当我向嵌入式openejb(在我们的集成测试框架中)运行请求时,它会给我一个415.如果我删除FormParam注释,请求成功.
如何仅使用jaxrs api读取多部分请求的不同部分?
编辑
好了,所以我把它编织PUT到了POST,并@Encoding为params 添加了一个注释:
@POST
@Path("signOff")
@Consumes(MediaType.MULTIPART_FORM_DATA)
public void signOffDeliveries(
@Encoded @FormParam("deliveries") String deliveries,
@Encoded @FormParam("signature") File signature) {
}
Run Code Online (Sandbox Code Playgroud)
现在我将xml作为文本字符串,但我无法自动将其解组为交付列表,即使Content-Type有效负载的这部分设置为application/xml.另一个问题是我收到的文件长度== 0,我无法从中读取任何字节.
我在这里错过了一个基本点吗?
我有一个使用RESTEasy的简单客户端,如下所示:
public class Test {
public static void main(String[] args) {
ResteasyClient client = new ResteasyClientBuilder().build();
ResteasyWebTarget target = client.target("http://localhost");
client.register(new MyMapper());
MyProxy proxy = target.proxy(MyProxy.class);
String r = proxy.getTest();
}
}
public interface MyProxy {
@GET
@Path("test")
String getTest();
}
@Provider
public class MyMapper implements ClientExceptionMapper<BadRequestException>{
@Override
public RuntimeException toException(BadRequestException arg0) {
// TODO Auto-generated method stub
System.out.println("mapped a bad request exception");
return null;
}
}
Run Code Online (Sandbox Code Playgroud)
服务器配置为返回400 - Bad Request打开http://localhost/test以及有用的消息.A BadRequestException被抛出ClientProxy.除了包装之外try/catch …
我正在向我的应用程序发送POST JSON请求.
POST /CharSetTest/Test HTTP/1.1
Host: localhost:8090
Content-Type: application/json
Cache-Control: no-cache
Postman-Token: 1637b92b-5896-4765-63c5-d04ad73ea9f1
{
"SampleRequest": {
"FullName": "???"
}
}
Run Code Online (Sandbox Code Playgroud)
我的CXF JAXRS消费者定义如下.
@POST
@Produces("application/json; charset=UTF-8")
@Consumes("application/json; charset=UTF-8")
public Response testCharSet(@Encoded String jsonBody);
Run Code Online (Sandbox Code Playgroud)
但是我作为POST请求发送的日文字符(关连当)没有编码,导致一些垃圾字符" é¢é£å½äºè "
使用SoapUI导致"?????" 字符.
这个垃圾字符在客户端与客户端之间不同,我点击了请求.我如何编码我的POST请求?
在检测到我的某个Web服务中存在缺陷后,我将错误跟踪到以下单行:
return this.getTemplate().getDomains().stream().anyMatch(domain -> domain.getName().equals(name));
Run Code Online (Sandbox Code Playgroud)
当我肯定地知道域名列表包含一个名称等于提供的域名时,该行返回false name.所以在我搔了一会儿之后,我最终分开整条线来看看发生了什么.我在调试会话中得到以下内容:
请注意以下行:
List<Domain> domains2 = domains.stream().collect(Collectors.toList());
Run Code Online (Sandbox Code Playgroud)
根据调试器,domains是一个包含两个元素的列表.但申请后,.stream().collect(Collectors.toList())我得到一个完全空的名单.如果我错了,请纠正我,但根据我的理解,那应该是身份操作并返回相同的列表(如果我们是严格的话,还是它的副本).那么这里发生了什么?
在你问之前:不,我根本没有操纵过截图.
为了将其置于上下文中,此代码在有状态请求范围EJB中使用JPA管理实体执行,并在扩展持久性上下文中具有字段访问权限.在这里,您可以获得与手头问题相关的代码的一些部分:
@Stateful
@RequestScoped
@Consumes(MediaType.APPLICATION_JSON)
@Produces(MediaType.APPLICATION_JSON)
public class DomainResources {
@PersistenceContext(type = PersistenceContextType.EXTENDED) @RequestScoped
private EntityManager entityManager;
public boolean templateContainsDomainWithName(String name) { // Extra code included to diagnose the problem
MetadataTemplate template = this.getTemplate();
List<Domain> domains = template.getDomains();
List<Domain> domains2 = domains.stream().collect(Collectors.toList());
List<String> names = domains.stream().map(Domain::getName).collect(Collectors.toList());
boolean exists1 = names.contains(name);
boolean exists2 = this.getTemplate().getDomains().stream().anyMatch(domain -> domain.getName().equals(name));
return this.getTemplate().getDomains().stream().anyMatch(domain -> domain.getName().equals(name));
} …Run Code Online (Sandbox Code Playgroud) 我有以下GETREST方法:
import java.time.OffsetDateTime;
import javax.ws.rs.Consumes;
import javax.ws.rs.DELETE;
import javax.ws.rs.GET;
import javax.ws.rs.HeaderParam;
import javax.ws.rs.POST;
import javax.ws.rs.PUT;
import javax.ws.rs.Path;
import javax.ws.rs.PathParam;
import javax.ws.rs.Produces;
import javax.ws.rs.QueryParam;
import javax.ws.rs.core.Response;
import io.swagger.annotations.Api;
import io.swagger.annotations.ApiOperation;
import io.swagger.annotations.ApiResponse;
import io.swagger.annotations.ApiResponses;
import com.product.rest.api.TransactionsApi;
import com.product.rest.model.Transaction;
@Path("/transactions")
@Api(description = "the transactions API")
@Consumes({ "application/json" })
@Produces({ "application/json" })
public class TransactionsApiImpl extends TransactionsApi {
@GET
@Consumes({ "application/json" })
@Produces({ "application/json" })
@ApiOperation(value = "", notes = "Get all transactions", response = Transaction.class, responseContainer = "List", tags = …Run Code Online (Sandbox Code Playgroud)