px_perimeterx/infrastructure/
handler.rs1use crate::application::solve_px::SolvePx;
2use async_trait::async_trait;
3use px_detector::{Detected, Detector, RegexDetector};
4use px_errors::AppError;
5use px_harvester::Harvester;
6use px_pipeline::{ChallengeHandler, HandlerMetrics, HandlerOutcome, PageHtml};
7use std::sync::Arc;
8
9pub struct PerimeterxHandler {
10 detector: RegexDetector,
11 solver: SolvePx,
12}
13
14impl PerimeterxHandler {
15 pub fn new(harvester: Arc<dyn Harvester>) -> Self {
16 Self {
17 detector: RegexDetector::new(),
18 solver: SolvePx::new(harvester),
19 }
20 }
21}
22
23#[async_trait]
24impl ChallengeHandler for PerimeterxHandler {
25 fn name(&self) -> &'static str {
26 "perimeterx"
27 }
28
29 async fn detects(&self, page: &PageHtml) -> Result<bool, AppError> {
30 Ok(matches!(self.detector.detect(&page.html), Detected::Yes(_)))
31 }
32
33 async fn solve(&self, page: &PageHtml) -> Result<HandlerOutcome, AppError> {
34 let out = self.solver.execute(&page.url).await?;
35 let metrics = HandlerMetrics {
36 detect_us: 0,
37 solve_ms: out.solve_ms,
38 bytes_read: 0,
39 };
40 Ok(HandlerOutcome::solved_with_ua(
41 self.name(),
42 out.cookies,
43 Vec::new(),
44 metrics,
45 out.user_agent,
46 ))
47 }
48}