Add ureq::request_url and Agent::request_url. (#226)
These let a user pass an already-parsed Url.
This commit is contained in:
committed by
GitHub
parent
0321ea043d
commit
e92bf0b4bb
38
src/agent.rs
38
src/agent.rs
@@ -1,5 +1,7 @@
|
|||||||
use std::sync::Arc;
|
use std::sync::Arc;
|
||||||
|
|
||||||
|
use url::Url;
|
||||||
|
|
||||||
use crate::pool::ConnectionPool;
|
use crate::pool::ConnectionPool;
|
||||||
use crate::proxy::Proxy;
|
use crate::proxy::Proxy;
|
||||||
use crate::request::Request;
|
use crate::request::Request;
|
||||||
@@ -94,15 +96,21 @@ impl Agent {
|
|||||||
AgentBuilder::new().build()
|
AgentBuilder::new().build()
|
||||||
}
|
}
|
||||||
|
|
||||||
/// Request by providing the HTTP verb such as `GET`, `POST`...
|
/// Make a request with the HTTP verb as a parameter.
|
||||||
|
///
|
||||||
|
/// This allows making requests with verbs that don't have a dedicated
|
||||||
|
/// method.
|
||||||
|
///
|
||||||
|
/// If you've got an already-parsed [Url], try [request_url][Agent::request_url].
|
||||||
///
|
///
|
||||||
/// ```
|
/// ```
|
||||||
/// # fn main() -> Result<(), ureq::Error> {
|
/// # fn main() -> Result<(), ureq::Error> {
|
||||||
/// # ureq::is_test(true);
|
/// # ureq::is_test(true);
|
||||||
|
/// use ureq::Response;
|
||||||
/// let agent = ureq::agent();
|
/// let agent = ureq::agent();
|
||||||
///
|
///
|
||||||
/// let resp = agent
|
/// let resp: Response = agent
|
||||||
/// .request("GET", "http://httpbin.org/status/200")
|
/// .request("OPTIONS", "http://example.com/")
|
||||||
/// .call()?;
|
/// .call()?;
|
||||||
/// # Ok(())
|
/// # Ok(())
|
||||||
/// # }
|
/// # }
|
||||||
@@ -111,6 +119,30 @@ impl Agent {
|
|||||||
Request::new(self.clone(), method.into(), path.into())
|
Request::new(self.clone(), method.into(), path.into())
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// Make a request using an already-parsed [Url].
|
||||||
|
///
|
||||||
|
/// This is useful if you've got a parsed Url from some other source, or if
|
||||||
|
/// you want to parse the URL and then modify it before making the request.
|
||||||
|
/// If you'd just like to pass a String or a `&str`, try [request][Agent::request].
|
||||||
|
///
|
||||||
|
/// ```
|
||||||
|
/// # fn main() -> Result<(), ureq::Error> {
|
||||||
|
/// # ureq::is_test(true);
|
||||||
|
/// use {url::Url, ureq::Response};
|
||||||
|
/// let agent = ureq::agent();
|
||||||
|
///
|
||||||
|
/// let mut url: Url = "http://example.com/some-page".parse().unwrap();
|
||||||
|
/// url.set_path("/robots.txt");
|
||||||
|
/// let resp: Response = agent
|
||||||
|
/// .request_url("GET", &url)
|
||||||
|
/// .call()?;
|
||||||
|
/// # Ok(())
|
||||||
|
/// # }
|
||||||
|
/// ```
|
||||||
|
pub fn request_url(&self, method: &str, url: &Url) -> Request {
|
||||||
|
Request::with_url(self.clone(), method.into(), url.clone())
|
||||||
|
}
|
||||||
|
|
||||||
/// Make a GET request from this agent.
|
/// Make a GET request from this agent.
|
||||||
pub fn get(&self, path: &str) -> Request {
|
pub fn get(&self, path: &str) -> Request {
|
||||||
self.request("GET", path)
|
self.request("GET", path)
|
||||||
|
|||||||
33
src/lib.rs
33
src/lib.rs
@@ -207,6 +207,7 @@ mod cookies;
|
|||||||
|
|
||||||
#[cfg(feature = "json")]
|
#[cfg(feature = "json")]
|
||||||
pub use serde_json::json;
|
pub use serde_json::json;
|
||||||
|
use url::Url;
|
||||||
|
|
||||||
#[cfg(test)]
|
#[cfg(test)]
|
||||||
mod test;
|
mod test;
|
||||||
@@ -265,18 +266,46 @@ pub fn agent() -> Agent {
|
|||||||
return testserver::test_agent();
|
return testserver::test_agent();
|
||||||
}
|
}
|
||||||
|
|
||||||
/// Make a request setting the HTTP method via a string.
|
/// Make a request with the HTTP verb as a parameter.
|
||||||
|
///
|
||||||
|
/// This allows making requests with verbs that don't have a dedicated
|
||||||
|
/// method.
|
||||||
|
///
|
||||||
|
/// If you've got an already-parsed [Url], try [request_url][request_url].
|
||||||
///
|
///
|
||||||
/// ```
|
/// ```
|
||||||
/// # fn main() -> Result<(), ureq::Error> {
|
/// # fn main() -> Result<(), ureq::Error> {
|
||||||
/// # ureq::is_test(true);
|
/// # ureq::is_test(true);
|
||||||
/// ureq::request("GET", "http://example.com").call()?;
|
/// let resp: ureq::Response = ureq::request("OPTIONS", "http://example.com/")
|
||||||
|
/// .call()?;
|
||||||
/// # Ok(())
|
/// # Ok(())
|
||||||
/// # }
|
/// # }
|
||||||
/// ```
|
/// ```
|
||||||
pub fn request(method: &str, path: &str) -> Request {
|
pub fn request(method: &str, path: &str) -> Request {
|
||||||
agent().request(method, path)
|
agent().request(method, path)
|
||||||
}
|
}
|
||||||
|
/// Make a request using an already-parsed [Url].
|
||||||
|
///
|
||||||
|
/// This is useful if you've got a parsed Url from some other source, or if
|
||||||
|
/// you want to parse the URL and then modify it before making the request.
|
||||||
|
/// If you'd just like to pass a String or a `&str`, try [request][request()].
|
||||||
|
///
|
||||||
|
/// ```
|
||||||
|
/// # fn main() -> Result<(), ureq::Error> {
|
||||||
|
/// # ureq::is_test(true);
|
||||||
|
/// use url::Url;
|
||||||
|
/// let agent = ureq::agent();
|
||||||
|
///
|
||||||
|
/// let mut url: Url = "http://example.com/some-page".parse().unwrap();
|
||||||
|
/// url.set_path("/robots.txt");
|
||||||
|
/// let resp: ureq::Response = ureq::request_url("GET", &url)
|
||||||
|
/// .call()?;
|
||||||
|
/// # Ok(())
|
||||||
|
/// # }
|
||||||
|
/// ```
|
||||||
|
pub fn request_url(method: &str, url: &Url) -> Request {
|
||||||
|
agent().request_url(method, url)
|
||||||
|
}
|
||||||
|
|
||||||
/// Make a GET request.
|
/// Make a GET request.
|
||||||
pub fn get(path: &str) -> Request {
|
pub fn get(path: &str) -> Request {
|
||||||
|
|||||||
@@ -15,6 +15,12 @@ use super::SerdeValue;
|
|||||||
|
|
||||||
pub type Result<T> = std::result::Result<T, Error>;
|
pub type Result<T> = std::result::Result<T, Error>;
|
||||||
|
|
||||||
|
#[derive(Debug, Clone)]
|
||||||
|
enum Urlish {
|
||||||
|
Url(Url),
|
||||||
|
Str(String),
|
||||||
|
}
|
||||||
|
|
||||||
/// Request instances are builders that creates a request.
|
/// Request instances are builders that creates a request.
|
||||||
///
|
///
|
||||||
/// ```
|
/// ```
|
||||||
@@ -30,12 +36,21 @@ pub type Result<T> = std::result::Result<T, Error>;
|
|||||||
pub struct Request {
|
pub struct Request {
|
||||||
agent: Agent,
|
agent: Agent,
|
||||||
method: String,
|
method: String,
|
||||||
url: String,
|
url: Urlish,
|
||||||
error_on_non_2xx: bool,
|
error_on_non_2xx: bool,
|
||||||
headers: Vec<Header>,
|
headers: Vec<Header>,
|
||||||
query_params: Vec<(String, String)>,
|
query_params: Vec<(String, String)>,
|
||||||
}
|
}
|
||||||
|
|
||||||
|
impl fmt::Display for Urlish {
|
||||||
|
fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
|
||||||
|
match self {
|
||||||
|
Urlish::Url(u) => write!(f, "{}", u),
|
||||||
|
Urlish::Str(s) => write!(f, "{}", s),
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
impl fmt::Debug for Request {
|
impl fmt::Debug for Request {
|
||||||
fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
|
fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
|
||||||
write!(
|
write!(
|
||||||
@@ -51,7 +66,18 @@ impl Request {
|
|||||||
Request {
|
Request {
|
||||||
agent,
|
agent,
|
||||||
method,
|
method,
|
||||||
url,
|
url: Urlish::Str(url),
|
||||||
|
headers: vec![],
|
||||||
|
error_on_non_2xx: true,
|
||||||
|
query_params: vec![],
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
pub(crate) fn with_url(agent: Agent, method: String, url: Url) -> Request {
|
||||||
|
Request {
|
||||||
|
agent,
|
||||||
|
method,
|
||||||
|
url: Urlish::Url(url),
|
||||||
headers: vec![],
|
headers: vec![],
|
||||||
error_on_non_2xx: true,
|
error_on_non_2xx: true,
|
||||||
query_params: vec![],
|
query_params: vec![],
|
||||||
@@ -79,11 +105,14 @@ impl Request {
|
|||||||
for h in &self.headers {
|
for h in &self.headers {
|
||||||
h.validate()?;
|
h.validate()?;
|
||||||
}
|
}
|
||||||
let mut url: Url = self.url.parse().map_err(|e: url::ParseError| {
|
let mut url: Url = match self.url.clone() {
|
||||||
ErrorKind::BadUrl
|
Urlish::Url(u) => u,
|
||||||
.msg(&format!("failed to parse URL '{}'", self.url))
|
Urlish::Str(s) => s.parse().map_err(|e: url::ParseError| {
|
||||||
.src(e)
|
ErrorKind::BadUrl
|
||||||
})?;
|
.msg(&format!("failed to parse URL '{}'", self.url))
|
||||||
|
.src(e)
|
||||||
|
})?,
|
||||||
|
};
|
||||||
for (name, value) in self.query_params.clone() {
|
for (name, value) in self.query_params.clone() {
|
||||||
url.query_pairs_mut().append_pair(&name, &value);
|
url.query_pairs_mut().append_pair(&name, &value);
|
||||||
}
|
}
|
||||||
|
|||||||
Reference in New Issue
Block a user