mirror of
https://git.asonix.dog/asonix/http-signature-normalization.git
synced 2024-11-24 18:31:01 +00:00
Update reqwest to automatically set Date header in masto compat
This commit is contained in:
parent
68e55bee28
commit
82b59317cb
3 changed files with 33 additions and 11 deletions
|
@ -24,6 +24,7 @@ required-features = ["sha-2"]
|
||||||
[dependencies]
|
[dependencies]
|
||||||
base64 = { version = "0.13", optional = true }
|
base64 = { version = "0.13", optional = true }
|
||||||
http-signature-normalization = { version = "0.6.0", path = ".." }
|
http-signature-normalization = { version = "0.6.0", path = ".." }
|
||||||
|
httpdate = "1.0.2"
|
||||||
reqwest = { version = "0.11", default-features = false, features = ["json"] }
|
reqwest = { version = "0.11", default-features = false, features = ["json"] }
|
||||||
reqwest-middleware = { version = "0.2.0", optional = true }
|
reqwest-middleware = { version = "0.2.0", optional = true }
|
||||||
sha2 = { version = "0.10", optional = true }
|
sha2 = { version = "0.10", optional = true }
|
||||||
|
@ -34,7 +35,6 @@ tokio = { version = "1", default-features = false, features = [
|
||||||
], optional = true }
|
], optional = true }
|
||||||
|
|
||||||
[dev-dependencies]
|
[dev-dependencies]
|
||||||
httpdate = "1.0.2"
|
|
||||||
pretty_env_logger = "0.4"
|
pretty_env_logger = "0.4"
|
||||||
tokio = { version = "1", default-features = false, features = [
|
tokio = { version = "1", default-features = false, features = [
|
||||||
"rt-multi-thread",
|
"rt-multi-thread",
|
||||||
|
|
|
@ -1,11 +1,9 @@
|
||||||
use http_signature_normalization_reqwest::prelude::*;
|
use http_signature_normalization_reqwest::prelude::*;
|
||||||
use httpdate::HttpDate;
|
|
||||||
use reqwest::{
|
use reqwest::{
|
||||||
header::{ACCEPT, DATE, USER_AGENT},
|
header::{ACCEPT, USER_AGENT},
|
||||||
Client,
|
Client,
|
||||||
};
|
};
|
||||||
use sha2::{Digest, Sha256};
|
use sha2::{Digest, Sha256};
|
||||||
use std::time::SystemTime;
|
|
||||||
|
|
||||||
async fn request(config: Config) -> Result<(), Box<dyn std::error::Error + Send + Sync>> {
|
async fn request(config: Config) -> Result<(), Box<dyn std::error::Error + Send + Sync>> {
|
||||||
let digest = Sha256::new();
|
let digest = Sha256::new();
|
||||||
|
@ -16,7 +14,6 @@ async fn request(config: Config) -> Result<(), Box<dyn std::error::Error + Send
|
||||||
.post("http://127.0.0.1:8010/")
|
.post("http://127.0.0.1:8010/")
|
||||||
.header(USER_AGENT, "Reqwest")
|
.header(USER_AGENT, "Reqwest")
|
||||||
.header(ACCEPT, "text/plain")
|
.header(ACCEPT, "text/plain")
|
||||||
.header(DATE, HttpDate::from(SystemTime::now()).to_string())
|
|
||||||
.signature_with_digest(config, "my-key-id", digest, "Hewwo-owo", |s| {
|
.signature_with_digest(config, "my-key-id", digest, "Hewwo-owo", |s| {
|
||||||
println!("Signing String\n{}", s);
|
println!("Signing String\n{}", s);
|
||||||
Ok(base64::encode(s)) as Result<_, MyError>
|
Ok(base64::encode(s)) as Result<_, MyError>
|
||||||
|
|
|
@ -1,9 +1,14 @@
|
||||||
use http_signature_normalization::create::Signed;
|
use http_signature_normalization::create::Signed;
|
||||||
|
use httpdate::HttpDate;
|
||||||
use reqwest::{
|
use reqwest::{
|
||||||
header::{InvalidHeaderValue, ToStrError},
|
header::{InvalidHeaderValue, ToStrError},
|
||||||
Request, RequestBuilder,
|
Request, RequestBuilder,
|
||||||
};
|
};
|
||||||
use std::{fmt::Display, time::Duration};
|
use std::{
|
||||||
|
convert::TryInto,
|
||||||
|
fmt::Display,
|
||||||
|
time::{Duration, SystemTime},
|
||||||
|
};
|
||||||
|
|
||||||
pub use http_signature_normalization::RequiredError;
|
pub use http_signature_normalization::RequiredError;
|
||||||
|
|
||||||
|
@ -28,6 +33,9 @@ pub struct Config {
|
||||||
|
|
||||||
/// Whether to set the Host header
|
/// Whether to set the Host header
|
||||||
set_host: bool,
|
set_host: bool,
|
||||||
|
|
||||||
|
/// Whether to set the Date header
|
||||||
|
set_date: bool,
|
||||||
}
|
}
|
||||||
|
|
||||||
/// A trait implemented by the reqwest RequestBuilder type to add an HTTP Signature to the request
|
/// A trait implemented by the reqwest RequestBuilder type to add an HTTP Signature to the request
|
||||||
|
@ -90,6 +98,7 @@ impl Config {
|
||||||
Config {
|
Config {
|
||||||
config: self.config,
|
config: self.config,
|
||||||
set_host: true,
|
set_host: true,
|
||||||
|
set_date: self.set_date,
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -101,6 +110,7 @@ impl Config {
|
||||||
Config {
|
Config {
|
||||||
config: self.config.mastodon_compat(),
|
config: self.config.mastodon_compat(),
|
||||||
set_host: true,
|
set_host: true,
|
||||||
|
set_date: true,
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -111,6 +121,7 @@ impl Config {
|
||||||
Config {
|
Config {
|
||||||
config: self.config.require_digest(),
|
config: self.config.require_digest(),
|
||||||
set_host: self.set_host,
|
set_host: self.set_host,
|
||||||
|
set_date: self.set_date,
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -122,6 +133,7 @@ impl Config {
|
||||||
Config {
|
Config {
|
||||||
config: self.config.dont_use_created_field(),
|
config: self.config.dont_use_created_field(),
|
||||||
set_host: self.set_host,
|
set_host: self.set_host,
|
||||||
|
set_date: self.set_date,
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -130,6 +142,7 @@ impl Config {
|
||||||
Config {
|
Config {
|
||||||
config: self.config.set_expiration(expiries_after),
|
config: self.config.set_expiration(expiries_after),
|
||||||
set_host: self.set_host,
|
set_host: self.set_host,
|
||||||
|
set_date: self.set_date,
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -138,6 +151,7 @@ impl Config {
|
||||||
Config {
|
Config {
|
||||||
config: self.config.require_header(header),
|
config: self.config.require_header(header),
|
||||||
set_host: self.set_host,
|
set_host: self.set_host,
|
||||||
|
set_date: self.set_date,
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -155,7 +169,7 @@ impl Sign for RequestBuilder {
|
||||||
K: Display,
|
K: Display,
|
||||||
{
|
{
|
||||||
let mut request = self.build()?;
|
let mut request = self.build()?;
|
||||||
let signed = prepare(&request, config, key_id, f)?;
|
let signed = prepare(&mut request, config, key_id, f)?;
|
||||||
|
|
||||||
let auth_header = signed.authorization_header();
|
let auth_header = signed.authorization_header();
|
||||||
request.headers_mut().insert(
|
request.headers_mut().insert(
|
||||||
|
@ -173,7 +187,7 @@ impl Sign for RequestBuilder {
|
||||||
K: Display,
|
K: Display,
|
||||||
{
|
{
|
||||||
let mut request = self.build()?;
|
let mut request = self.build()?;
|
||||||
let signed = prepare(&request, config, key_id, f)?;
|
let signed = prepare(&mut request, config, key_id, f)?;
|
||||||
|
|
||||||
let sig_header = signed.signature_header();
|
let sig_header = signed.signature_header();
|
||||||
|
|
||||||
|
@ -186,12 +200,23 @@ impl Sign for RequestBuilder {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
fn prepare<F, E, K>(req: &Request, config: &Config, key_id: K, f: F) -> Result<Signed, E>
|
fn prepare<F, E, K>(req: &mut Request, config: &Config, key_id: K, f: F) -> Result<Signed, E>
|
||||||
where
|
where
|
||||||
F: FnOnce(&str) -> Result<String, E>,
|
F: FnOnce(&str) -> Result<String, E>,
|
||||||
E: From<SignError>,
|
E: From<SignError>,
|
||||||
K: Display,
|
K: Display,
|
||||||
{
|
{
|
||||||
|
if config.set_date {
|
||||||
|
if !req.headers().contains_key("date") {
|
||||||
|
req.headers_mut().insert(
|
||||||
|
"date",
|
||||||
|
HttpDate::from(SystemTime::now())
|
||||||
|
.to_string()
|
||||||
|
.try_into()
|
||||||
|
.map_err(SignError::from)?,
|
||||||
|
);
|
||||||
|
}
|
||||||
|
}
|
||||||
let mut bt = std::collections::BTreeMap::new();
|
let mut bt = std::collections::BTreeMap::new();
|
||||||
for (k, v) in req.headers().iter() {
|
for (k, v) in req.headers().iter() {
|
||||||
bt.insert(
|
bt.insert(
|
||||||
|
@ -247,7 +272,7 @@ mod middleware {
|
||||||
K: Display,
|
K: Display,
|
||||||
{
|
{
|
||||||
let mut request = self.build()?;
|
let mut request = self.build()?;
|
||||||
let signed = prepare(&request, config, key_id, f)?;
|
let signed = prepare(&mut request, config, key_id, f)?;
|
||||||
|
|
||||||
let auth_header = signed.authorization_header();
|
let auth_header = signed.authorization_header();
|
||||||
request.headers_mut().insert(
|
request.headers_mut().insert(
|
||||||
|
@ -265,7 +290,7 @@ mod middleware {
|
||||||
K: Display,
|
K: Display,
|
||||||
{
|
{
|
||||||
let mut request = self.build()?;
|
let mut request = self.build()?;
|
||||||
let signed = prepare(&request, config, key_id, f)?;
|
let signed = prepare(&mut request, config, key_id, f)?;
|
||||||
|
|
||||||
let sig_header = signed.signature_header();
|
let sig_header = signed.signature_header();
|
||||||
|
|
||||||
|
|
Loading…
Reference in a new issue