Skip to content

Commit

Permalink
feat: Introduce Signer along with Load/Build/Context (#482)
Browse files Browse the repository at this point in the history
Signed-off-by: Xuanwo <github@xuanwo.io>
  • Loading branch information
Xuanwo authored Sep 1, 2024
1 parent 80eabe7 commit b866d45
Show file tree
Hide file tree
Showing 13 changed files with 175 additions and 86 deletions.
18 changes: 9 additions & 9 deletions crates/reqsign-aliyun-oss/src/signer.rs
Original file line number Diff line number Diff line change
Expand Up @@ -14,12 +14,12 @@ use once_cell::sync::Lazy;
use percent_encoding::utf8_percent_encode;

use super::credential::Credential;
use reqsign::ctx::SigningContext;
use reqsign::ctx::SigningMethod;
use reqsign::hash::base64_hmac_sha1;
use reqsign::time;
use reqsign::time::format_http_date;
use reqsign::time::DateTime;
use reqsign::SigningMethod;
use reqsign::SigningRequest;

const CONTENT_MD5: &str = "content-md5";

Expand All @@ -42,9 +42,9 @@ impl Signer {
req: &mut http::request::Parts,
method: SigningMethod,
cred: &Credential,
) -> Result<SigningContext> {
) -> Result<SigningRequest> {
let now = time::now();
let mut ctx = SigningContext::build(req)?;
let mut ctx = SigningRequest::build(req)?;

let string_to_sign = string_to_sign(&mut ctx, cred, now, method, &self.bucket)?;
let signature =
Expand Down Expand Up @@ -111,7 +111,7 @@ impl Signer {
/// + CanonicalizedResource
/// ```
fn string_to_sign(
ctx: &mut SigningContext,
ctx: &mut SigningRequest,
cred: &Credential,
now: DateTime,
method: SigningMethod,
Expand Down Expand Up @@ -159,7 +159,7 @@ fn string_to_sign(
///
/// [Building CanonicalizedOSSHeaders](https://help.aliyun.com/document_detail/31951.html#section-w2k-sw2-xdb)
fn canonicalize_header(
ctx: &mut SigningContext,
ctx: &mut SigningRequest,
method: SigningMethod,
cred: &Credential,
) -> Result<String> {
Expand All @@ -170,7 +170,7 @@ fn canonicalize_header(
}
}

Ok(SigningContext::header_to_string(
Ok(SigningRequest::header_to_string(
ctx.header_to_vec_with_prefix("x-oss-"),
":",
"\n",
Expand All @@ -183,7 +183,7 @@ fn canonicalize_header(
///
/// [Building CanonicalizedResource](https://help.aliyun.com/document_detail/31951.html#section-w2k-sw2-xdb)
fn canonicalize_resource(
ctx: &mut SigningContext,
ctx: &mut SigningRequest,
bucket: &str,
method: SigningMethod,
cred: &Credential,
Expand All @@ -201,7 +201,7 @@ fn canonicalize_resource(
let params = ctx.query_to_vec_with_filter(is_sub_resource);

// OSS requires that the query string be percent-decoded.
let params_str = SigningContext::query_to_percent_decoded_string(params, "=", "&");
let params_str = SigningRequest::query_to_percent_decoded_string(params, "=", "&");

if params_str.is_empty() {
format!("/{bucket}{}", ctx.path_percent_decoded())
Expand Down
16 changes: 8 additions & 8 deletions crates/reqsign-aws-v4/src/signer.rs
Original file line number Diff line number Diff line change
Expand Up @@ -16,15 +16,15 @@ use super::constants::X_AMZ_CONTENT_SHA_256;
use super::constants::X_AMZ_DATE;
use super::constants::X_AMZ_SECURITY_TOKEN;
use super::credential::Credential;
use reqsign::ctx::SigningContext;
use reqsign::ctx::SigningMethod;
use reqsign::hash::hex_hmac_sha256;
use reqsign::hash::hex_sha256;
use reqsign::hash::hmac_sha256;
use reqsign::time::format_date;
use reqsign::time::format_iso8601;
use reqsign::time::now;
use reqsign::time::DateTime;
use reqsign::SigningMethod;
use reqsign::SigningRequest;

/// Signer that implement AWS SigV4.
///
Expand Down Expand Up @@ -64,9 +64,9 @@ impl Signer {
req: &mut http::request::Parts,
method: SigningMethod,
cred: &Credential,
) -> Result<SigningContext> {
) -> Result<SigningRequest> {
let now = self.time.unwrap_or_else(now);
let mut ctx = SigningContext::build(req)?;
let mut ctx = SigningRequest::build(req)?;

// canonicalize context
canonicalize_header(&mut ctx, method, cred, now)?;
Expand Down Expand Up @@ -213,7 +213,7 @@ impl Signer {
}
}

fn canonical_request_string(ctx: &mut SigningContext) -> Result<String> {
fn canonical_request_string(ctx: &mut SigningRequest) -> Result<String> {
// 256 is specially chosen to avoid reallocation for most requests.
let mut f = String::with_capacity(256);

Expand Down Expand Up @@ -260,14 +260,14 @@ fn canonical_request_string(ctx: &mut SigningContext) -> Result<String> {
}

fn canonicalize_header(
ctx: &mut SigningContext,
ctx: &mut SigningRequest,
method: SigningMethod,
cred: &Credential,
now: DateTime,
) -> Result<()> {
// Header names and values need to be normalized according to Step 4 of https://docs.aws.amazon.com/general/latest/gr/sigv4-create-canonical-request.html
for (_, value) in ctx.headers.iter_mut() {
SigningContext::header_value_normalize(value)
SigningRequest::header_value_normalize(value)
}

// Insert HOST header if not present.
Expand Down Expand Up @@ -305,7 +305,7 @@ fn canonicalize_header(
}

fn canonicalize_query(
ctx: &mut SigningContext,
ctx: &mut SigningRequest,
method: SigningMethod,
cred: &Credential,
now: DateTime,
Expand Down
18 changes: 9 additions & 9 deletions crates/reqsign-azure-storage/src/signer.rs
Original file line number Diff line number Diff line change
Expand Up @@ -13,13 +13,13 @@ use percent_encoding::percent_encode;
use super::credential::Credential;
use crate::account_sas;
use crate::constants::*;
use reqsign::ctx::SigningContext;
use reqsign::ctx::SigningMethod;
use reqsign::hash::base64_decode;
use reqsign::hash::base64_hmac_sha256;
use reqsign::time;
use reqsign::time::format_http_date;
use reqsign::time::DateTime;
use reqsign::SigningMethod;
use reqsign::SigningRequest;

/// Signer that implement Azure Storage Shared Key Authorization.
///
Expand Down Expand Up @@ -52,8 +52,8 @@ impl Signer {
parts: &mut http::request::Parts,
method: SigningMethod,
cred: &Credential,
) -> Result<SigningContext> {
let mut ctx = SigningContext::build(parts)?;
) -> Result<SigningRequest> {
let mut ctx = SigningRequest::build(parts)?;

match cred {
Credential::SharedAccessSignature(token) => {
Expand Down Expand Up @@ -192,7 +192,7 @@ impl Signer {
/// ## Reference
///
/// - [Blob, Queue, and File Services (Shared Key authorization)](https://docs.microsoft.com/en-us/rest/api/storageservices/authorize-with-shared-key)
fn string_to_sign(ctx: &mut SigningContext, ak: &str, now: DateTime) -> Result<String> {
fn string_to_sign(ctx: &mut SigningRequest, ak: &str, now: DateTime) -> Result<String> {
let mut s = String::with_capacity(128);

writeln!(&mut s, "{}", ctx.method.as_str())?;
Expand Down Expand Up @@ -231,11 +231,11 @@ fn string_to_sign(ctx: &mut SigningContext, ak: &str, now: DateTime) -> Result<S
/// ## Reference
///
/// - [Constructing the canonicalized headers string](https://docs.microsoft.com/en-us/rest/api/storageservices/authorize-with-shared-key#constructing-the-canonicalized-headers-string)
fn canonicalize_header(ctx: &mut SigningContext, now: DateTime) -> Result<String> {
fn canonicalize_header(ctx: &mut SigningRequest, now: DateTime) -> Result<String> {
ctx.headers
.insert(X_MS_DATE, format_http_date(now).parse()?);

Ok(SigningContext::header_to_string(
Ok(SigningRequest::header_to_string(
ctx.header_to_vec_with_prefix("x-ms-"),
":",
"\n",
Expand All @@ -245,7 +245,7 @@ fn canonicalize_header(ctx: &mut SigningContext, now: DateTime) -> Result<String
/// ## Reference
///
/// - [Constructing the canonicalized resource string](https://docs.microsoft.com/en-us/rest/api/storageservices/authorize-with-shared-key#constructing-the-canonicalized-resource-string)
fn canonicalize_resource(ctx: &mut SigningContext, ak: &str) -> String {
fn canonicalize_resource(ctx: &mut SigningRequest, ak: &str) -> String {
if ctx.query.is_empty() {
return format!("/{}{}", ak, ctx.path);
}
Expand All @@ -260,7 +260,7 @@ fn canonicalize_resource(ctx: &mut SigningContext, ak: &str) -> String {
"/{}{}\n{}",
ak,
ctx.path,
SigningContext::query_to_percent_decoded_string(query, ":", "\n")
SigningRequest::query_to_percent_decoded_string(query, ":", "\n")
)
}

Expand Down
22 changes: 11 additions & 11 deletions crates/reqsign-google/src/signer.rs
Original file line number Diff line number Diff line change
Expand Up @@ -14,13 +14,13 @@ use super::constants::GOOG_QUERY_ENCODE_SET;
use super::credential::Credential;
use super::credential::ServiceAccount;
use super::token::Token;
use reqsign::ctx::SigningContext;
use reqsign::ctx::SigningMethod;
use reqsign::hash::hex_sha256;
use reqsign::time;
use reqsign::time::format_date;
use reqsign::time::format_iso8601;
use reqsign::time::DateTime;
use reqsign::SigningMethod;
use reqsign::SigningRequest;

/// Signer that implement Google OAuth2 Authentication.
///
Expand Down Expand Up @@ -67,8 +67,8 @@ impl Signer {
&self,
parts: &mut http::request::Parts,
token: &Token,
) -> Result<SigningContext> {
let mut ctx = SigningContext::build(parts)?;
) -> Result<SigningRequest> {
let mut ctx = SigningRequest::build(parts)?;

ctx.headers.insert(header::AUTHORIZATION, {
let mut value: http::HeaderValue =
Expand All @@ -86,8 +86,8 @@ impl Signer {
parts: &mut http::request::Parts,
expire: Duration,
cred: &ServiceAccount,
) -> Result<SigningContext> {
let mut ctx = SigningContext::build(parts)?;
) -> Result<SigningRequest> {
let mut ctx = SigningRequest::build(parts)?;

let now = self.time.unwrap_or_else(time::now);

Expand Down Expand Up @@ -241,7 +241,7 @@ impl Signer {
}
}

fn canonical_request_string(ctx: &mut SigningContext) -> Result<String> {
fn canonical_request_string(ctx: &mut SigningRequest) -> Result<String> {
// 256 is specially chosen to avoid reallocation for most requests.
let mut f = String::with_capacity(256);

Expand All @@ -258,7 +258,7 @@ fn canonical_request_string(ctx: &mut SigningContext) -> Result<String> {
f.push('\n');

// Insert query
f.push_str(&SigningContext::query_to_string(
f.push_str(&SigningRequest::query_to_string(
ctx.query.clone(),
"=",
"&",
Expand All @@ -283,9 +283,9 @@ fn canonical_request_string(ctx: &mut SigningContext) -> Result<String> {
Ok(f)
}

fn canonicalize_header(ctx: &mut SigningContext) -> Result<()> {
fn canonicalize_header(ctx: &mut SigningRequest) -> Result<()> {
for (_, value) in ctx.headers.iter_mut() {
SigningContext::header_value_normalize(value)
SigningRequest::header_value_normalize(value)
}

// Insert HOST header if not present.
Expand All @@ -298,7 +298,7 @@ fn canonicalize_header(ctx: &mut SigningContext) -> Result<()> {
}

fn canonicalize_query(
ctx: &mut SigningContext,
ctx: &mut SigningRequest,
method: SigningMethod,
cred: &ServiceAccount,
now: DateTime,
Expand Down
18 changes: 9 additions & 9 deletions crates/reqsign-huaweicloud-obs/src/signer.rs
Original file line number Diff line number Diff line change
Expand Up @@ -15,12 +15,12 @@ use percent_encoding::utf8_percent_encode;

use super::constants::*;
use super::credential::Credential;
use reqsign::ctx::SigningContext;
use reqsign::ctx::SigningMethod;
use reqsign::hash::base64_hmac_sha1;
use reqsign::time::format_http_date;
use reqsign::time::now;
use reqsign::time::DateTime;
use reqsign::SigningMethod;
use reqsign::SigningRequest;

/// Signer that implement Huawei Cloud Object Storage Service Authorization.
///
Expand Down Expand Up @@ -58,9 +58,9 @@ impl Signer {
parts: &mut http::request::Parts,
method: SigningMethod,
cred: &Credential,
) -> Result<SigningContext> {
) -> Result<SigningRequest> {
let now = self.time.unwrap_or_else(now);
let mut ctx = SigningContext::build(parts)?;
let mut ctx = SigningRequest::build(parts)?;

let string_to_sign = string_to_sign(&mut ctx, cred, now, method, &self.bucket)?;
let signature =
Expand Down Expand Up @@ -164,7 +164,7 @@ impl Signer {
///
/// - [User Signature Authentication (OBS)](https://support.huaweicloud.com/intl/en-us/api-obs/obs_04_0009.html)
fn string_to_sign(
ctx: &mut SigningContext,
ctx: &mut SigningRequest,
cred: &Credential,
now: DateTime,
method: SigningMethod,
Expand Down Expand Up @@ -210,7 +210,7 @@ fn string_to_sign(
///
/// - [Authentication of Signature in a Header](https://support.huaweicloud.com/intl/en-us/api-obs/obs_04_0010.html)
fn canonicalize_header(
ctx: &mut SigningContext,
ctx: &mut SigningRequest,
method: SigningMethod,
cred: &Credential,
) -> Result<String> {
Expand All @@ -221,7 +221,7 @@ fn canonicalize_header(
}
}

Ok(SigningContext::header_to_string(
Ok(SigningRequest::header_to_string(
ctx.header_to_vec_with_prefix("x-obs-"),
":",
"\n",
Expand All @@ -232,7 +232,7 @@ fn canonicalize_header(
///
/// - [Authentication of Signature in a Header](https://support.huaweicloud.com/intl/en-us/api-obs/obs_04_0010.html)
fn canonicalize_resource(
ctx: &mut SigningContext,
ctx: &mut SigningRequest,
bucket: &str,
method: SigningMethod,
cred: &Credential,
Expand All @@ -247,7 +247,7 @@ fn canonicalize_resource(

let params = ctx.query_to_vec_with_filter(is_sub_resource);

let params_str = SigningContext::query_to_string(params, "=", "&");
let params_str = SigningRequest::query_to_string(params, "=", "&");

if params_str.is_empty() {
format!("/{bucket}{}", ctx.path)
Expand Down
8 changes: 4 additions & 4 deletions crates/reqsign-oracle/src/signer.rs
Original file line number Diff line number Diff line change
Expand Up @@ -14,19 +14,19 @@ use rsa::{pkcs8::DecodePrivateKey, RsaPrivateKey};
use std::fmt::Write;

use super::credential::Credential;
use reqsign::ctx::SigningContext;
use reqsign::time;
use reqsign::time::DateTime;
use reqsign::SigningRequest;

/// Signer for Oracle Cloud Infrastructure using API Key.
#[derive(Default)]
pub struct APIKeySigner {}

impl APIKeySigner {
/// Building a signing context.
fn build(&self, parts: &mut http::request::Parts, cred: &Credential) -> Result<SigningContext> {
fn build(&self, parts: &mut http::request::Parts, cred: &Credential) -> Result<SigningRequest> {
let now = time::now();
let mut ctx = SigningContext::build(parts)?;
let mut ctx = SigningRequest::build(parts)?;

let string_to_sign = string_to_sign(&mut ctx, now)?;
let private_key = if let Some(path) = &cred.key_file {
Expand Down Expand Up @@ -76,7 +76,7 @@ impl APIKeySigner {
/// + "(request-target): {verb} {uri}" + "\n"
/// + "host: {Host}"
/// ```
fn string_to_sign(ctx: &mut SigningContext, now: DateTime) -> Result<String> {
fn string_to_sign(ctx: &mut SigningRequest, now: DateTime) -> Result<String> {
let string_to_sign = {
let mut f = String::new();
writeln!(f, "date: {}", time::format_http_date(now))?;
Expand Down
Loading

0 comments on commit b866d45

Please sign in to comment.