Merge pull request #9548 from tonygparsehub/put-delete
fix #8777 add missing http methods in httpClient
This commit is contained in:
commit
47d0582ebf
1 changed files with 79 additions and 43 deletions
|
|
@ -1208,7 +1208,9 @@ proc request*(client: HttpClient | AsyncHttpClient, url: string,
|
||||||
for i in 1..client.maxRedirects:
|
for i in 1..client.maxRedirects:
|
||||||
if result.status.redirection():
|
if result.status.redirection():
|
||||||
let redirectTo = getNewLocation(lastURL, result.headers)
|
let redirectTo = getNewLocation(lastURL, result.headers)
|
||||||
result = await client.requestAux(redirectTo, httpMethod, body, headers)
|
# Guarantee method for HTTP 307: see https://developer.mozilla.org/en-US/docs/Web/HTTP/Status/307
|
||||||
|
var meth = if result.status == "307": httpMethod else: "GET"
|
||||||
|
result = await client.requestAux(redirectTo, meth, body, headers)
|
||||||
lastURL = redirectTo
|
lastURL = redirectTo
|
||||||
|
|
||||||
|
|
||||||
|
|
@ -1227,36 +1229,49 @@ proc request*(client: HttpClient | AsyncHttpClient, url: string,
|
||||||
## be closed.
|
## be closed.
|
||||||
result = await request(client, url, $httpMethod, body, headers)
|
result = await request(client, url, $httpMethod, body, headers)
|
||||||
|
|
||||||
proc get*(client: HttpClient | AsyncHttpClient,
|
proc responseContent(resp: Response | AsyncResponse): Future[string] {.multisync.} =
|
||||||
url: string): Future[Response | AsyncResponse] {.multisync.} =
|
## Returns the content of a response as a string.
|
||||||
## Connects to the hostname specified by the URL and performs a GET request.
|
|
||||||
##
|
|
||||||
## This procedure will follow redirects up to a maximum number of redirects
|
|
||||||
## specified in ``client.maxRedirects``.
|
|
||||||
result = await client.request(url, HttpGET)
|
|
||||||
|
|
||||||
proc getContent*(client: HttpClient | AsyncHttpClient,
|
|
||||||
url: string): Future[string] {.multisync.} =
|
|
||||||
## Connects to the hostname specified by the URL and performs a GET request.
|
|
||||||
##
|
|
||||||
## This procedure will follow redirects up to a maximum number of redirects
|
|
||||||
## specified in ``client.maxRedirects``.
|
|
||||||
##
|
##
|
||||||
## A ``HttpRequestError`` will be raised if the server responds with a
|
## A ``HttpRequestError`` will be raised if the server responds with a
|
||||||
## client error (status code 4xx) or a server error (status code 5xx).
|
## client error (status code 4xx) or a server error (status code 5xx).
|
||||||
let resp = await get(client, url)
|
|
||||||
if resp.code.is4xx or resp.code.is5xx:
|
if resp.code.is4xx or resp.code.is5xx:
|
||||||
raise newException(HttpRequestError, resp.status)
|
raise newException(HttpRequestError, resp.status)
|
||||||
else:
|
else:
|
||||||
return await resp.bodyStream.readAll()
|
return await resp.bodyStream.readAll()
|
||||||
|
|
||||||
proc post*(client: HttpClient | AsyncHttpClient, url: string, body = "",
|
proc head*(client: HttpClient | AsyncHttpClient,
|
||||||
multipart: MultipartData = nil): Future[Response | AsyncResponse]
|
url: string): Future[Response | AsyncResponse] {.multisync.} =
|
||||||
{.multisync.} =
|
## Connects to the hostname specified by the URL and performs a HEAD request.
|
||||||
## Connects to the hostname specified by the URL and performs a POST request.
|
|
||||||
##
|
##
|
||||||
## This procedure will follow redirects up to a maximum number of redirects
|
## This procedure uses httpClient values such as ``client.maxRedirects``.
|
||||||
## specified in ``client.maxRedirects``.
|
result = await client.request(url, HttpHEAD)
|
||||||
|
|
||||||
|
proc get*(client: HttpClient | AsyncHttpClient,
|
||||||
|
url: string): Future[Response | AsyncResponse] {.multisync.} =
|
||||||
|
## Connects to the hostname specified by the URL and performs a GET request.
|
||||||
|
##
|
||||||
|
## This procedure uses httpClient values such as ``client.maxRedirects``.
|
||||||
|
result = await client.request(url, HttpGET)
|
||||||
|
|
||||||
|
proc getContent*(client: HttpClient | AsyncHttpClient,
|
||||||
|
url: string): Future[string] {.multisync.} =
|
||||||
|
## Connects to the hostname specified by the URL and returns the content of a GET request.
|
||||||
|
let resp = await get(client, url)
|
||||||
|
return await responseContent(resp)
|
||||||
|
|
||||||
|
proc delete*(client: HttpClient | AsyncHttpClient,
|
||||||
|
url: string): Future[Response | AsyncResponse] {.multisync.} =
|
||||||
|
## Connects to the hostname specified by the URL and performs a DELETE request.
|
||||||
|
## This procedure uses httpClient values such as ``client.maxRedirects``.
|
||||||
|
result = await client.request(url, HttpDELETE)
|
||||||
|
|
||||||
|
proc deleteContent*(client: HttpClient | AsyncHttpClient,
|
||||||
|
url: string): Future[string] {.multisync.} =
|
||||||
|
## Connects to the hostname specified by the URL and returns the content of a DELETE request.
|
||||||
|
let resp = await delete(client, url)
|
||||||
|
return await responseContent(resp)
|
||||||
|
|
||||||
|
proc makeRequestContent(body = "", multipart: MultipartData = nil): (string, HttpHeaders) =
|
||||||
let (mpContentType, mpBody) = format(multipart)
|
let (mpContentType, mpBody) = format(multipart)
|
||||||
# TODO: Support FutureStream for `body` parameter.
|
# TODO: Support FutureStream for `body` parameter.
|
||||||
template withNewLine(x): untyped =
|
template withNewLine(x): untyped =
|
||||||
|
|
@ -1265,38 +1280,59 @@ proc post*(client: HttpClient | AsyncHttpClient, url: string, body = "",
|
||||||
else:
|
else:
|
||||||
x
|
x
|
||||||
var xb = mpBody.withNewLine() & body
|
var xb = mpBody.withNewLine() & body
|
||||||
|
|
||||||
var headers = newHttpHeaders()
|
var headers = newHttpHeaders()
|
||||||
if multipart != nil:
|
if multipart != nil:
|
||||||
headers["Content-Type"] = mpContentType
|
headers["Content-Type"] = mpContentType
|
||||||
headers["Content-Length"] = $len(xb)
|
headers["Content-Length"] = $len(xb)
|
||||||
|
return (xb, headers)
|
||||||
|
|
||||||
result = await client.requestAux(url, $HttpPOST, xb, headers)
|
proc post*(client: HttpClient | AsyncHttpClient, url: string, body = "",
|
||||||
# Handle redirects.
|
multipart: MultipartData = nil): Future[Response | AsyncResponse]
|
||||||
var lastURL = url
|
{.multisync.} =
|
||||||
for i in 1..client.maxRedirects:
|
## Connects to the hostname specified by the URL and performs a POST request.
|
||||||
if result.status.redirection():
|
## This procedure uses httpClient values such as ``client.maxRedirects``.
|
||||||
let redirectTo = getNewLocation(lastURL, result.headers)
|
var (xb, headers) = makeRequestContent(body, multipart)
|
||||||
var meth = if result.status != "307": HttpGet else: HttpPost
|
result = await client.request(url, $HttpPOST, xb, headers)
|
||||||
result = await client.requestAux(redirectTo, $meth, xb, headers)
|
|
||||||
lastURL = redirectTo
|
|
||||||
|
|
||||||
proc postContent*(client: HttpClient | AsyncHttpClient, url: string,
|
proc postContent*(client: HttpClient | AsyncHttpClient, url: string,
|
||||||
body = "",
|
body = "",
|
||||||
multipart: MultipartData = nil): Future[string]
|
multipart: MultipartData = nil): Future[string]
|
||||||
{.multisync.} =
|
{.multisync.} =
|
||||||
## Connects to the hostname specified by the URL and performs a POST request.
|
## Connects to the hostname specified by the URL and returns the content of a POST request.
|
||||||
##
|
|
||||||
## This procedure will follow redirects up to a maximum number of redirects
|
|
||||||
## specified in ``client.maxRedirects``.
|
|
||||||
##
|
|
||||||
## A ``HttpRequestError`` will be raised if the server responds with a
|
|
||||||
## client error (status code 4xx) or a server error (status code 5xx).
|
|
||||||
let resp = await post(client, url, body, multipart)
|
let resp = await post(client, url, body, multipart)
|
||||||
if resp.code.is4xx or resp.code.is5xx:
|
return await responseContent(resp)
|
||||||
raise newException(HttpRequestError, resp.status)
|
|
||||||
else:
|
proc put*(client: HttpClient | AsyncHttpClient, url: string, body = "",
|
||||||
return await resp.bodyStream.readAll()
|
multipart: MultipartData = nil): Future[Response | AsyncResponse]
|
||||||
|
{.multisync.} =
|
||||||
|
## Connects to the hostname specified by the URL and performs a PUT request.
|
||||||
|
## This procedure uses httpClient values such as ``client.maxRedirects``.
|
||||||
|
var (xb, headers) = makeRequestContent(body, multipart)
|
||||||
|
result = await client.request(url, $HttpPUT, xb, headers)
|
||||||
|
|
||||||
|
proc putContent*(client: HttpClient | AsyncHttpClient, url: string,
|
||||||
|
body = "",
|
||||||
|
multipart: MultipartData = nil): Future[string]
|
||||||
|
{.multisync.} =
|
||||||
|
## Connects to the hostname specified by the URL andreturns the content of a PUT request.
|
||||||
|
let resp = await put(client, url, body, multipart)
|
||||||
|
return await responseContent(resp)
|
||||||
|
|
||||||
|
proc patch*(client: HttpClient | AsyncHttpClient, url: string, body = "",
|
||||||
|
multipart: MultipartData = nil): Future[Response | AsyncResponse]
|
||||||
|
{.multisync.} =
|
||||||
|
## Connects to the hostname specified by the URL and performs a PATCH request.
|
||||||
|
## This procedure uses httpClient values such as ``client.maxRedirects``.
|
||||||
|
var (xb, headers) = makeRequestContent(body, multipart)
|
||||||
|
result = await client.request(url, $HttpPATCH, xb, headers)
|
||||||
|
|
||||||
|
proc patchContent*(client: HttpClient | AsyncHttpClient, url: string,
|
||||||
|
body = "",
|
||||||
|
multipart: MultipartData = nil): Future[string]
|
||||||
|
{.multisync.} =
|
||||||
|
## Connects to the hostname specified by the URL and returns the content of a PATCH request.
|
||||||
|
let resp = await patch(client, url, body, multipart)
|
||||||
|
return await responseContent(resp)
|
||||||
|
|
||||||
proc downloadFile*(client: HttpClient, url: string, filename: string) =
|
proc downloadFile*(client: HttpClient, url: string, filename: string) =
|
||||||
## Downloads ``url`` and saves it to ``filename``.
|
## Downloads ``url`` and saves it to ``filename``.
|
||||||
|
|
|
||||||
Loading…
Add table
Add a link
Reference in a new issue