Kotlin HTTP GET/POST 请求
最后修改于 2024 年 1 月 29 日
本文展示了如何在 Kotlin 中发送 GET 和 POST 请求。 我们使用 HttpClient 和 Fuel 库。
HTTP
超文本传输协议 (HTTP) 是一种用于分布式、协作式、超媒体信息系统的应用协议。HTTP 是万维网数据通信的基础。
在示例中,我们使用了 httpbin.org
,这是一个免费提供的 HTTP 请求和响应服务,以及 webcode.me
,这是一个用于测试的微型 HTML 页面。
HTTP GET
HTTP GET 方法请求指定资源的表示。使用 GET 的请求应该只检索数据。
HTTP POST
HTTP POST 方法将数据发送到服务器。它通常用于上传文件或提交完成的 Web 表单。
使用 HttpClient 发送 Kotlin GET 请求
HttpClient
是在 Java 中生成 http 请求的工具。
package com.zetcode import java.net.URI import java.net.http.HttpClient import java.net.http.HttpRequest import java.net.http.HttpResponse fun main() { val client = HttpClient.newBuilder().build(); val request = HttpRequest.newBuilder() .uri(URI.create("http://webcode.me")) .build(); val response = client.send(request, HttpResponse.BodyHandlers.ofString()); println(response.body()) }
我们向 webcode.me
网页发出 GET 请求。
val client = HttpClient.newBuilder().build();
创建一个客户端。
val request = HttpRequest.newBuilder() .uri(URI.create("http://webcode.me")) .build();
我们构建一个到网页的同步请求。 默认方法是 GET。
val response = client.send(request, HttpResponse.BodyHandlers.ofString()); println(response.body())
我们发送请求,检索响应的内容,并将其打印到控制台。
<!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8"> <meta name="viewport" content="width=device-width, initial-scale=1.0"> <title>My html page</title> </head> <body> <p> Today is a beautiful day. We go swimming and fishing. </p> <p> Hello there. How are you? </p> </body> </html>
使用 HttpClient 发送 GET 查询参数
下面的例子将一些查询参数附加到 URL。
package com.zetcode import java.net.URI import java.net.URLEncoder import java.net.http.HttpClient import java.net.http.HttpRequest import java.net.http.HttpResponse fun String.utf8(): String = URLEncoder.encode(this, "UTF-8") fun main() { val params = mapOf("name" to "John Doe", "occupation" to "gardener") val urlParams = params.map {(k, v) -> "${(k.utf8())}=${v.utf8()}"} .joinToString("&") val client = HttpClient.newBuilder().build(); val request = HttpRequest.newBuilder() .uri(URI.create("https://httpbin.org/get?${urlParams}")) .build(); val response = client.send(request, HttpResponse.BodyHandlers.ofString()); println(response.body()) }
我们创建一个 GET 请求到 httpbin.org/get
,并带有一些 URL 参数。
fun String.utf8(): String = URLEncoder.encode(this, "UTF-8")
这是一个用于编码 URL 参数的字符串扩展方法。
val params = mapOf("name" to "John Doe", "occupation" to "gardener") val urlParams = params.map {(k, v) -> "${(k.utf8())}=${v.utf8()}"} .joinToString("&")
我们有一个值映射。我们使用自定义扩展方法对它们进行 URL 路径编码。
val request = HttpRequest.newBuilder() .uri(URI.create("https://httpbin.org/get?${urlParams}")) .build();
我们将参数附加到 URL。
{ "args": { "name": "John Doe", "occupation": "gardener" }, "headers": { "Host": "httpbin.org", "User-Agent": "Java-http-client/14.0.1", "X-Amzn-Trace-Id": "Root=1-6000269f-2389dad80db13d002a8a9003" }, ... "url": "https://httpbin.org/get?name=John+Doe&occupation=gardener" }
使用 HttpClient 发送 Kotlin POST JSON 数据请求
下面的例子使用 HttpClient 发送 POST 请求。数据以 JSON 格式发送。
dependencies { testImplementation(kotlin("test-junit")) implementation("com.fasterxml.jackson.module:jackson-module-kotlin:2.12.1") }
对于这个例子,我们需要 jackson-module-kotlin
依赖项。
package com.zetcode import com.fasterxml.jackson.databind.ObjectMapper import java.net.URI import java.net.http.HttpClient import java.net.http.HttpRequest import java.net.http.HttpResponse fun main() { val values = mapOf("name" to "John Doe", "occupation" to "gardener") val objectMapper = ObjectMapper() val requestBody: String = objectMapper .writeValueAsString(values) val client = HttpClient.newBuilder().build(); val request = HttpRequest.newBuilder() .uri(URI.create("https://httpbin.org/post")) .POST(HttpRequest.BodyPublishers.ofString(requestBody)) .build() val response = client.send(request, HttpResponse.BodyHandlers.ofString()); println(response.body()) }
我们生成一个 POST 请求到 httpbin.org/post
网页。 发布的资料取自一个映射,并使用 Jackson 的 ObjectMapper 转换为字符串。
val request = HttpRequest.newBuilder() .uri(URI.create("https://httpbin.org/post")) .POST(HttpRequest.BodyPublishers.ofString(requestBody)) .build()
POST 请求是通过 POST
方法生成的。
[Success: { "args": {}, "data": "{\"name\":\"John Doe\",\"occupation\":\"gardener\"}", "files": {}, "form": {}, "headers": { "Accept": "text/html, image/gif, image/jpeg, *; q=.2, */*; q=.2", "Content-Length": "43", "Content-Type": "application/json", "Host": "httpbin.org", "User-Agent": "Java/14.0.1", "X-Amzn-Trace-Id": "Root=1-60004591-5248fddb69a2221616147220" }, "json": { "name": "John Doe", "occupation": "gardener" }, "origin": "188.167.250.74", "url": "https://httpbin.org/post" } ]
使用 HttpClient 发送 Kotlin POST FORM 数据请求
使用 application/x-www-form-urlencoded
,数据在请求体中发送; 键和值以键值对的形式编码,用 '&' 分隔,键和值之间用 '=' 分隔。
package com.zetcode import java.net.URI import java.net.URLEncoder import java.net.http.HttpClient import java.net.http.HttpRequest import java.net.http.HttpResponse fun main() { val values = mapOf("name" to "John Doe", "occupation" to "gardener") val client = HttpClient.newBuilder().build(); val request = HttpRequest.newBuilder() .uri(URI.create("https://httpbin.org/post")) .POST(formData(values)) .header("Content-Type", "application/x-www-form-urlencoded") .build() val response = client.send(request, HttpResponse.BodyHandlers.ofString()); println(response.body()) } fun String.utf8(): String = URLEncoder.encode(this, "UTF-8") fun formData(data: Map<String, String>): HttpRequest.BodyPublisher? { val res = data.map {(k, v) -> "${(k.utf8())}=${v.utf8()}"} .joinToString("&") return HttpRequest.BodyPublishers.ofString(res) }
我们生成一个带有 FORM 数据的 POST 请求到 httpbin.org/post
。
.header("Content-Type", "application/x-www-form-urlencoded")
我们将内容类型标头设置为 application/x-www-form-urlencoded
。
fun String.utf8(): String = URLEncoder.encode(this, "UTF-8") fun formData(data: Map<String, String>): HttpRequest.BodyPublisher? { val res = data.map {(k, v) -> "${(k.utf8())}=${v.utf8()}"} .joinToString("&") return HttpRequest.BodyPublishers.ofString(res) }
使用 String.uft8
和 formData
辅助函数,我们创建一个带有 URL 编码值的 body 发布者。
{ "args": {}, "data": "", "files": {}, "form": { "name": "John Doe", "occupation": "gardener" }, "headers": { "Content-Length": "33", "Content-Type": "application/x-www-form-urlencoded", "Host": "httpbin.org", "User-Agent": "Java-http-client/14.0.1", "X-Amzn-Trace-Id": "Root=1-600030bb-7c7f4d026883523b438f2e63" }, "json": null, ... "url": "https://httpbin.org/post" }
使用 Fuel 发送 Kotlin GET 请求
Fuel 是一个易于使用的 Kotlin HTTP 网络库。
dependencies { testImplementation(kotlin("test-junit")) implementation("com.github.kittinunf.fuel:fuel:2.3.1") }
我们需要添加 fuel
依赖项。
package com.zetcode import com.github.kittinunf.fuel.httpGet fun main() { val (_, _, result) = "http://webcode.me".httpGet().responseString() println(result) }
该示例向 webcode.me
发送一个简单的 GET 请求。
使用 Fuel 发送 GET 查询参数
下面的例子使用 GET 请求发送一些查询参数。
package com.zetcode import com.github.kittinunf.fuel.httpGet fun main() { val (_, _, result) = "http://httpbin.org/get" .httpGet(listOf("name" to "John Doe", "occupation" to "gardener")) .responseString() println(result) }
Fuel 库会自动处理 httpGet
中参数的编码。
使用 Fuel 发送 Kotlin POST JSON 数据请求
我们使用 JSON 数据设置 POST 请求。这次我们使用 Gson 库。
dependencies { testImplementation(kotlin("test-junit")) implementation("com.github.kittinunf.fuel:fuel:2.3.1") implementation("com.github.kittinunf.fuel:fuel-gson:2.3.1") implementation("com.google.code.gson:gson:2.8.6") }
我们有 Gson 库的额外依赖项。
package com.zetcode import com.github.kittinunf.fuel.core.extensions.jsonBody import com.github.kittinunf.fuel.httpPost import com.google.gson.Gson data class User(var name: String, var occupation: String) fun main() { val user = User("John Doe", "gardener") val (_, _, result) = "https://httpbin.org/post".httpPost() .jsonBody(Gson().toJson(user).toString()) .responseString() println(result) }
我们使用 toJson
方法将用户对象序列化为 JSON 字符串。 我们使用 jsonBody
方法设置 JSON body。
使用 Fuel 发送 Kotlin POST FORM 数据请求
在下面的例子中,我们发送一个带有 FORM 数据的 POST 请求。
package com.zetcode import com.github.kittinunf.fuel.httpPost fun main() { val (_, _, result) = "https://httpbin.org/post" .httpPost(listOf("name" to "John Doe", "occupation" to "gardener")) .responseString() println(result) }
Fuel 自动将数据转换为 application/x-www-form-urlencoded
内容类型在 httpPost
中。
来源
本文展示了如何在 Kotlin 中发送 GET 和 POST 请求。
作者
列出 所有 Kotlin 教程。