use crate::config::{Config, HeaderMapExt};
use crate::parse::parse_remaps;
use anyhow::{Context, Result};
use http::{HeaderMap, StatusCode};
use lychee_lib::{Client, ClientBuilder, ratelimit::RateLimitConfig};
use regex::RegexSet;
use reqwest_cookie_store::CookieStoreMutex;
use std::sync::Arc;
use std::{collections::HashSet, str::FromStr};
pub(crate) fn create(cfg: &Config, cookie_jar: Option<&Arc<CookieStoreMutex>>) -> Result<Client> {
let timeout = cfg.timeout();
let retry_wait_time = cfg.retry_wait_time();
let method: reqwest::Method = reqwest::Method::from_str(&cfg.method().to_uppercase())?;
let remaps = parse_remaps(&cfg.remap)?;
let includes = RegexSet::new(&cfg.include)?;
let excludes = RegexSet::new(&cfg.exclude)?;
let accepted: HashSet<StatusCode> = cfg.accept().into();
let schemes = if cfg.offline() {
vec!["file".to_string()]
} else {
cfg.scheme.clone()
};
let headers = HeaderMap::from_header_pairs(&cfg.headers())?;
ClientBuilder::builder()
.remaps(remaps)
.base(cfg.base_url.clone().unwrap_or_default())
.includes(includes)
.excludes(excludes)
.exclude_all_private(cfg.exclude_all_private())
.exclude_private_ips(cfg.exclude_private())
.exclude_link_local_ips(cfg.exclude_link_local())
.exclude_loopback_ips(cfg.exclude_loopback())
.include_mail(cfg.include_mail())
.max_redirects(cfg.max_redirects())
.user_agent(cfg.user_agent())
.allow_insecure(cfg.insecure())
.custom_headers(headers)
.method(method)
.timeout(timeout)
.retry_wait_time(retry_wait_time)
.max_retries(cfg.max_retries())
.github_token(cfg.github_token.clone())
.schemes(HashSet::from_iter(schemes))
.accepted(accepted)
.require_https(cfg.require_https())
.cookie_jar(cookie_jar.cloned())
.min_tls_version(cfg.min_tls.clone().map(Into::into))
.fragment_checker_options(cfg.fragment_checker_options())
.fallback_extensions(cfg.fallback_extensions.clone())
.index_files(cfg.index_files.clone())
.include_wikilinks(cfg.include_wikilinks())
.rate_limit_config(RateLimitConfig::from_options(
cfg.host_concurrency,
cfg.host_request_interval,
))
.hosts(cfg.hosts.clone())
.build()
.client()
.context("Failed to create request client")
}