如何在Java中构建URL?

45

我正在使用 StringBuilder 构建一个字符串

StringBuilder builder = new StringBuilder();
builder.append("my parameters");
builder.append("other parameters");

然后我构建了一个URL

Url url = new Url(builder.toString());

然后我尝试连接。

HttpURLConnection connection = (HttpURLConnection) url.openConnection();

但是从我得到的结果来看,URL似乎不正确。就像某个参数被错误地传递了一样。这就是为什么我认为问题出在StringBuilder的部分。

问题在于我试图传递一个双参数。

double longitude = 23.433114;
String lng = String.ValueOf(longitude);

然后我将它放在URL中。但如果我将其作为字符串传递,结果就是正确的。

String lng = "23.433114"

UrlEncoding必要吗?我会尝试下面建议的内容。


1
@RealSkeptic URLEncoder.encode() 编码的是 application/x-www-form-urlencoded,这与编码查询参数/URI 片段等完全不同。 - fge
1
@fge 不,URL编码是一种标准的编码方案。它既用于GET查询中的参数,也用于POST查询中的参数,这些参数是application/x-www-form-urlencoded的格式。请参阅Wikipedia - RealSkeptic
1
@RealSkeptic @EJP 对不起但是那是错误的。在查询参数中,例如,空格会变成 %20;就像我说的那样,你提到的方法是编码为其中空格变成 + 的表单。这只是一个例子。 - fge
1
@fge - 在查询中尝试使用它们两个。你会感到惊讶的。+在GET查询中可以替代空格。但如果你不相信维基百科,请尝试HTML规范 - RealSkeptic
可能是Java中组合URL或URI的惯用方式是什么?的重复问题。 - Nick Grealy
显示剩余9条评论
3个回答

99
尝试使用Apache的URIBuilder:[文档]。
import org.apache.http.client.utils.URIBuilder;

// ...

URIBuilder b = new URIBuilder("http://example.com");
b.addParameter("t", "search");
b.addParameter("q", "apples");

Url url = b.build().toUrl();

Maven依赖:

<dependency>
    <groupId>org.apache.httpcomponents</groupId>
    <artifactId>httpclient</artifactId>
    <version>4.5.1</version>
</dependency>

7
运行完美。唯一的问题是它抛出了检查异常,这些异常处理起来很无聊。 - Aron Lorincz
1
它们被捕获起来就像其他异常一样无聊...不是吗? :) - Andrea Bori

4

由于您想创建URL并通过GET请求进行消费,最好使用可帮助您完成此过程的库。您可以使用HttpComponents或类似Unirest的另一个基于HttpComponents构建的库来简化所有这些工作。

这是使用Unirest的示例:

HttpResponse<String> stringResponse = Unirest.get("https://www.youtube.com/results")
    .field("search_query", "eñe")
    .asString();
System.out.println(stringResponse.getBody());

这将检索与使用"eñe"在YouTube上搜索的所有结果相对应的HTML响应。 ñ字符将为您编码。
免责声明:我与Unirest无关。 我不是此项目的开发人员或赞助商。 我只是这个框架的一个满意用户。

嘿,现在已经很晚了,但我们能在GET请求中传递值.field("search_query", "eñe")吗? - mukesh patel

0

还有另一个选项,这次使用Spring框架(在进行一些自动化测试时特别有用)

UriComponentsBuilder.newInstance()
                .scheme(URIScheme.HTTP.getId())
                .host("host")
                .port(8000)
                .path("/employee")
                .pathSegment("{employeeName}", "{anotherThing}")
                // this build(xxx) will automatically perform encoding
                .build("John", "YetMoreData")
                .toURL();

这个工具的小问题是,并没有对所有特殊字符进行编码。例如,查询参数中的加号并没有被编码! - Ahmad Shahwan
哦,不知道这个。也许这个方法可以做你说的那个?https://docs.spring.io/spring-framework/docs/current/javadoc-api/org/springframework/web/util/UriComponentsBuilder.html#encode() - Tonsic

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接