为什么Jersey的UriBuilder.build方法编码#'和%',但不是/?

Mat*_*rog 12 rest jax-rs urlencode jersey

我有一个相当典型的REST API,除了资源的id不是整数,而是字符串,通常包含/字符.因此,如果客户的ID是string/with/slashes该客户的URI应该是http://localhost/customers/string%2Fwith%2Fslashes.返回客户列表时,我想用UriBuilder构造URI,这样我就可以把它放在ATOM风格的链接元素的href中.但它不太有效; 这是一个小测试类,显示我的意思:

@Path("/customers")
public class JerseyTest {

  @Path("{id}")
  public Customer getCustomer(@PathParam("{id}") String id) {
    return null;
  }

  public static void main(String[] args) {
    buildURI("string#with#hashes"); // => http://localhost/customers/string%23with%23hashes
    buildURI("string/with/slashes"); // => http://localhost/customers/string/with/slashes
  }

  public static void buildURI(String id) {
    UriBuilder builder = UriBuilder.fromUri("http://localhost");
    builder.path(JerseyTest.class).path(JerseyTest.class, "getCustomer");
    URI uri = builder.build(id);
    System.out.println(uri);
  }
}
Run Code Online (Sandbox Code Playgroud)

#太棒了,我们编码为我所期望的,但/我们做不.我尝试使用builder.build(URLEncoder.encode(id)),但随后UriBuilder编码了%,所以你得到了.../string%252Fwith%252Fslashes!

在我看来,不一致的,它编码#%而不是/,但我怀疑是有很好的理由对此我没有看到.所以我的问题是:

  1. 我怎样才能得到UriBuilder给我.../string%2Fwith%2Fslashes,这是导致泽西调用URI getCustomerid相等string/with/slashes编辑:我发现了解决这个问题的方法:builder.buildFromEncoded(URLEncoder.encode(id)).尽管如此,希望能得到第二部分的答案......
  2. 更一般地说,为什么要UriBuilder.build编码一些特殊字符,而不是其他字符?

我发现如何编码URI参数值?,接受的答案是"使用UriBuilder".好吧,我正在使用它,但显然我使用它不正确.

Dou*_*rop 4

这似乎是一个已确认的问题:

http://java.net/jira/browse/JAX_RS_SPEC-70

你的解决方法听起来不错。