codetether_agent/browser/
error.rs1use thiserror::Error;
2
3#[path = "error_cdp.rs"]
4mod cdp;
5
6#[allow(dead_code)]
7#[derive(Debug, Error)]
8pub enum BrowserError {
9 #[error("browser command is not implemented")]
10 NotImplemented,
11 #[error("navigation timed out")]
12 NavigationTimeout,
13 #[error("element not found: {0}")]
14 ElementNotFound(String),
15 #[error("javascript exception: {message}{stack_suffix}", stack_suffix = stack_suffix(.stack.as_deref()))]
16 JsException {
17 message: String,
18 stack: Option<String>,
19 },
20 #[error("browser session not started")]
21 SessionNotStarted,
22 #[error("tab is closed")]
23 TabClosed,
24 #[error("browser crashed or connection was lost")]
25 BrowserCrashed,
26 #[error("evaluation timed out")]
27 EvaluationTimeout,
28 #[error("evaluation promise rejected: {message}")]
29 EvalRejection { message: String },
30 #[error(
31 "evaluation returned non-serializable value: {description} (type={type_}, subtype={subtype:?})"
32 )]
33 EvalNonSerializable {
34 type_: String,
35 subtype: Option<String>,
36 description: String,
37 },
38 #[error("evaluation wrapper error: {0}")]
39 EvalWrapperError(String),
40 #[error("browser operation failed: {0}")]
41 OperationFailed(String),
42}
43
44impl From<anyhow::Error> for BrowserError {
45 fn from(error: anyhow::Error) -> Self {
46 Self::OperationFailed(error.to_string())
47 }
48}
49
50impl From<serde_json::Error> for BrowserError {
51 fn from(error: serde_json::Error) -> Self {
52 Self::OperationFailed(error.to_string())
53 }
54}
55
56fn stack_suffix(stack: Option<&str>) -> String {
57 stack.map(|value| format!("\n{value}")).unwrap_or_default()
58}