use reqwest::Client;
use serde::{Serialize, de::DeserializeOwned};
use std::sync::LazyLock;
use std::time::{SystemTime, UNIX_EPOCH};
pub const USER_AGENT: &str = "Mozilla/5.0 (Windows NT 10.0; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/63.0.3239.132 Safari/537.36";
pub const COOKIE: &str = "os=pc;osver=Microsoft-Windows-10-Professional-build-16299.125-64bit;appver=2.0.3.131777;channel=netease;__remember_me=true";
static HTTP_CLIENT: LazyLock<Client> = LazyLock::new(|| {
Client::builder()
.user_agent(USER_AGENT)
.build()
.expect("Failed to create HTTP client")
});
pub fn unix_seconds() -> u64 {
SystemTime::now()
.duration_since(UNIX_EPOCH)
.map(|d| d.as_secs())
.unwrap_or(0)
}
pub fn unix_millis() -> u128 {
SystemTime::now()
.duration_since(UNIX_EPOCH)
.map(|d| d.as_millis())
.unwrap_or(0)
}
pub async fn get_json<T: DeserializeOwned>(url: &str) -> Option<T> {
let response = HTTP_CLIENT.get(url).send().await.ok()?;
response.json::<T>().await.ok()
}
pub async fn get_json_with_headers<T: DeserializeOwned>(
url: &str,
headers: &[(&str, &str)],
) -> Option<T> {
let mut request = HTTP_CLIENT.get(url);
for (key, value) in headers {
request = request.header(*key, *value);
}
let response = request.send().await.ok()?;
response.json::<T>().await.ok()
}
pub async fn post_json<T: DeserializeOwned>(url: &str, body: &impl Serialize) -> Option<T> {
let response = HTTP_CLIENT.post(url).json(body).send().await.ok()?;
response.json::<T>().await.ok()
}
pub async fn post_json_with_headers<T: DeserializeOwned>(
url: &str,
body: &impl Serialize,
headers: &[(&str, &str)],
) -> Option<T> {
let mut request = HTTP_CLIENT.post(url).json(body);
for (key, value) in headers {
request = request.header(*key, *value);
}
let response = request.send().await.ok()?;
response.json::<T>().await.ok()
}
pub async fn post_json_raw_with_headers(
url: &str,
body: &impl Serialize,
headers: &[(&str, &str)],
) -> Option<String> {
let mut request = HTTP_CLIENT.post(url).json(body);
for (key, value) in headers {
request = request.header(*key, *value);
}
let response = request.send().await.ok()?;
response.text().await.ok()
}
pub async fn post_form<T: DeserializeOwned>(
url: &str,
form: &[(&str, &str)],
headers: &[(&str, &str)],
) -> Option<T> {
let mut request = HTTP_CLIENT.post(url).form(form);
for (key, value) in headers {
request = request.header(*key, *value);
}
let response = request.send().await.ok()?;
response.json::<T>().await.ok()
}
pub async fn post_form_raw_with_headers(
url: &str,
form: &[(&str, &str)],
headers: &[(&str, &str)],
) -> Option<String> {
let mut request = HTTP_CLIENT.post(url).form(form);
for (key, value) in headers {
request = request.header(*key, *value);
}
let response = request.send().await.ok()?;
response.text().await.ok()
}