pub mod parsing;
pub mod site;
pub mod types;
use tail_fin_common::page::{browser_origin_fetch, ensure_on_domain};
use tail_fin_common::BrowserSession;
use tail_fin_common::TailFinError;
pub use site::PccSite;
pub use types::*;
const PCC_DOMAINS: &[&str] = &["pcc.g0v.ronny.tw", "pcc-api.openfun.app"];
pub struct PccClient {
session: BrowserSession,
}
impl PccClient {
pub fn new(session: BrowserSession) -> Self {
Self { session }
}
async fn api_get(&self, path: &str) -> Result<serde_json::Value, TailFinError> {
ensure_on_domain(&self.session, PCC_DOMAINS).await?;
browser_origin_fetch(&self.session, path, None).await
}
pub async fn info(&self) -> Result<PccInfo, TailFinError> {
let data = self.api_get("/api/getinfo").await?;
parsing::parse_info(&data)
}
pub async fn search(&self, query: &str, page: u32) -> Result<SearchResult, TailFinError> {
let q = urlencoding::encode(query);
let data = self
.api_get(&format!("/api/searchbytitle?query={}&page={}", q, page))
.await?;
parsing::parse_search_result(&data)
}
pub async fn search_company(
&self,
query: &str,
page: u32,
) -> Result<SearchResult, TailFinError> {
let q = urlencoding::encode(query);
let data = self
.api_get(&format!(
"/api/searchbycompanyname?query={}&page={}",
q, page
))
.await?;
parsing::parse_search_result(&data)
}
pub async fn search_id(&self, query: &str, page: u32) -> Result<SearchResult, TailFinError> {
let q = urlencoding::encode(query);
let data = self
.api_get(&format!("/api/searchbycompanyid?query={}&page={}", q, page))
.await?;
parsing::parse_search_result(&data)
}
pub async fn search_budget(
&self,
query: &str,
page: u32,
) -> Result<SearchResult, TailFinError> {
let q = urlencoding::encode(query);
let data = self
.api_get(&format!(
"/api/searchbyspecialbudget?query={}&page={}",
q, page
))
.await?;
parsing::parse_search_result(&data)
}
pub async fn budgets(&self) -> Result<Vec<SpecialBudget>, TailFinError> {
let data = self.api_get("/api/searchallspecialbudget").await?;
Ok(parsing::parse_budgets(&data))
}
pub async fn date(&self, date: &str) -> Result<SearchResult, TailFinError> {
let data = self
.api_get(&format!("/api/listbydate?date={}", date))
.await?;
parsing::parse_search_result(&data)
}
pub async fn units(&self) -> Result<Vec<Unit>, TailFinError> {
let data = self.api_get("/api/unit").await?;
Ok(parsing::parse_units(&data))
}
pub async fn unit(&self, unit_id: &str, page: u32) -> Result<SearchResult, TailFinError> {
let data = self
.api_get(&format!(
"/api/listbyunit?unit_id={}&page={}",
unit_id, page
))
.await?;
parsing::parse_search_result(&data)
}
pub async fn tender(
&self,
unit_id: &str,
job_number: &str,
) -> Result<serde_json::Value, TailFinError> {
self.api_get(&format!(
"/api/tender?unit_id={}&job_number={}",
unit_id, job_number
))
.await
}
}