use std::net::IpAddr;
use std::net::Ipv4Addr;
use std::time::{Duration, SystemTime};
pub const DEFAULT_PAC_TIMEOUT: Duration = Duration::from_secs(5);
#[derive(Debug, Clone, Copy, PartialEq, Eq)]
pub struct PacPolicy {
resolve_dns: bool,
allow_internal_addresses: bool,
my_ip_address: Option<IpAddr>,
timeout: Option<Duration>,
local_utc_offset: i32,
now: Option<SystemTime>,
}
impl Default for PacPolicy {
fn default() -> Self {
Self {
resolve_dns: false,
allow_internal_addresses: false,
my_ip_address: None,
timeout: Some(DEFAULT_PAC_TIMEOUT),
local_utc_offset: 0,
now: None,
}
}
}
impl PacPolicy {
#[must_use]
pub fn new() -> Self {
Self::default()
}
#[must_use]
pub fn with_dns_resolution(mut self, enabled: bool) -> Self {
self.resolve_dns = enabled;
self
}
#[must_use]
pub fn with_internal_addresses(mut self, allowed: bool) -> Self {
self.allow_internal_addresses = allowed;
self
}
#[must_use]
pub fn with_my_ip_address(mut self, address: IpAddr) -> Self {
self.my_ip_address = Some(address);
self
}
#[must_use]
pub fn with_timeout(mut self, timeout: Option<Duration>) -> Self {
self.timeout = timeout;
self
}
#[must_use]
pub fn with_local_utc_offset(mut self, seconds: i32) -> Self {
self.local_utc_offset = seconds;
self
}
#[must_use]
pub fn with_now(mut self, now: SystemTime) -> Self {
self.now = Some(now);
self
}
#[must_use]
pub fn resolve_dns(&self) -> bool {
self.resolve_dns
}
#[must_use]
pub fn allow_internal_addresses(&self) -> bool {
self.allow_internal_addresses
}
#[must_use]
pub fn my_ip_address(&self) -> IpAddr {
self.my_ip_address
.unwrap_or(IpAddr::V4(Ipv4Addr::LOCALHOST))
}
#[must_use]
pub fn timeout(&self) -> Option<Duration> {
self.timeout
}
#[must_use]
pub fn local_utc_offset(&self) -> i32 {
self.local_utc_offset
}
#[must_use]
pub fn now(&self) -> Option<SystemTime> {
self.now
}
}
#[cfg(test)]
mod tests {
use super::*;
#[test]
fn the_default_budget_is_five_seconds_and_not_the_absence_of_one() {
assert_eq!(PacPolicy::new().timeout(), Some(DEFAULT_PAC_TIMEOUT));
assert_eq!(DEFAULT_PAC_TIMEOUT, Duration::from_secs(5));
}
#[test]
fn the_default_clock_is_the_real_one() {
assert_eq!(PacPolicy::new().now(), None);
}
#[test]
fn removing_the_budget_is_a_request_the_builder_honours() {
assert_eq!(PacPolicy::new().with_timeout(None).timeout(), None);
assert_eq!(
PacPolicy::new()
.with_timeout(Some(Duration::ZERO))
.timeout(),
Some(Duration::ZERO)
);
}
}