-
Notifications
You must be signed in to change notification settings - Fork 1
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
- Loading branch information
1 parent
44bb0ed
commit a9d85e1
Showing
10 changed files
with
659 additions
and
2 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -1 +1,10 @@ | ||
mod test; | ||
|
||
use hickory_resolver::{ | ||
config::{ResolverConfig, ResolverOpts}, | ||
Resolver, | ||
}; | ||
|
||
pub fn prepare_dns_resolver() -> std::io::Result<Resolver> { | ||
Resolver::new(ResolverConfig::cloudflare_tls(), ResolverOpts::default()) | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,24 @@ | ||
use async_trait::async_trait; | ||
use mockall::automock; | ||
use reqwest::{Client, Error, Request, Response}; | ||
|
||
#[automock] | ||
#[async_trait] | ||
pub trait HttpClient: Send + Sync { | ||
async fn execute(&self, req: Request) -> Result<Response, Error>; | ||
} | ||
|
||
pub struct ReqwestClient(Client); | ||
|
||
impl ReqwestClient { | ||
pub const fn new(c: Client) -> Self { | ||
Self(c) | ||
} | ||
} | ||
|
||
#[async_trait] | ||
impl HttpClient for ReqwestClient { | ||
async fn execute(&self, req: Request) -> Result<Response, Error> { | ||
self.0.execute(req).await | ||
} | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -12,6 +12,7 @@ mod cache; | |
mod cli; | ||
mod core; | ||
mod dns; | ||
mod http; | ||
mod policy; | ||
mod tls; | ||
|
||
|
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,64 @@ | ||
mod syncer; | ||
mod test; | ||
|
||
use std::sync::Arc; | ||
|
||
use anyhow::{anyhow, Error}; | ||
use async_trait::async_trait; | ||
use futures::future::join_all; | ||
use rustls::{crypto::aws_lc_rs, sign::CertifiedKey}; | ||
|
||
// Converts raw PEM certificate chain & private key to a CertifiedKey ready to be consumed by Rustls | ||
pub fn pem_convert_to_rustls(key: &[u8], certs: &[u8]) -> Result<Arc<CertifiedKey>, Error> { | ||
let (key, certs) = (key.to_vec(), certs.to_vec()); | ||
|
||
let key = rustls_pemfile::private_key(&mut key.as_ref())? | ||
.ok_or_else(|| anyhow!("No private key found"))?; | ||
|
||
let certs = rustls_pemfile::certs(&mut certs.as_ref()).collect::<Result<Vec<_>, _>>()?; | ||
if certs.is_empty() { | ||
return Err(anyhow!("No certificates found")); | ||
} | ||
|
||
let key = aws_lc_rs::sign::any_supported_type(&key)?; | ||
Ok(Arc::new(CertifiedKey::new(certs, key))) | ||
} | ||
|
||
// Trait that the certificate sources should implement | ||
// It should return a vector of Rustls-compatible CertifiedKeys | ||
#[async_trait] | ||
pub trait ProvidesCertificates: Sync + Send { | ||
async fn get_certificates(&self) -> Result<Vec<Arc<CertifiedKey>>, Error>; | ||
} | ||
|
||
// Provider that aggregates other providers' output | ||
pub struct AggregatingProvider { | ||
providers: Vec<Arc<dyn ProvidesCertificates>>, | ||
} | ||
|
||
impl AggregatingProvider { | ||
pub fn new(providers: Vec<Arc<dyn ProvidesCertificates>>) -> Self { | ||
Self { providers } | ||
} | ||
} | ||
|
||
#[async_trait] | ||
impl ProvidesCertificates for AggregatingProvider { | ||
async fn get_certificates(&self) -> Result<Vec<Arc<CertifiedKey>>, Error> { | ||
let certs = join_all( | ||
self.providers | ||
.iter() | ||
.map(|x| async { x.get_certificates().await }), | ||
) | ||
.await; | ||
|
||
let certs = certs | ||
.into_iter() | ||
.collect::<Result<Vec<_>, _>>()? | ||
.into_iter() | ||
.flatten() | ||
.collect::<Vec<_>>(); | ||
|
||
Ok(certs) | ||
} | ||
} |
Oops, something went wrong.