Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
37 changes: 37 additions & 0 deletions cli/src/commands.rs
Original file line number Diff line number Diff line change
Expand Up @@ -101,6 +101,10 @@ pub fn parse_command(args: &[String], flags: &Flags) -> Result<Value, ParseError
format!("https://{}", url)
};
let mut nav_cmd = json!({ "id": id, "action": "navigate", "url": url });
// If --wait-until flag is set, include waitUntil strategy
if let Some(ref wait_until) = flags.wait_until {
nav_cmd["waitUntil"] = json!(wait_until);
}
// If --headers flag is set, include headers (scoped to this origin)
if let Some(ref headers_json) = flags.headers {
if let Ok(headers) = serde_json::from_str::<serde_json::Value>(headers_json) {
Expand Down Expand Up @@ -1535,6 +1539,7 @@ mod tests {
device: None,
auto_connect: false,
session_name: None,
wait_until: None,
cli_executable_path: false,
cli_extensions: false,
cli_profile: false,
Expand Down Expand Up @@ -1836,6 +1841,38 @@ mod tests {
assert!(cmd.get("headers").is_none());
}

#[test]
fn test_navigate_with_wait_until() {
let mut flags = default_flags();
flags.wait_until = Some("domcontentloaded".to_string());
let cmd = parse_command(&args("open example.com"), &flags).unwrap();
assert_eq!(cmd["action"], "navigate");
assert_eq!(cmd["waitUntil"], "domcontentloaded");
}

#[test]
fn test_navigate_with_wait_until_load() {
let mut flags = default_flags();
flags.wait_until = Some("load".to_string());
let cmd = parse_command(&args("open example.com"), &flags).unwrap();
assert_eq!(cmd["waitUntil"], "load");
}

#[test]
fn test_navigate_with_wait_until_networkidle() {
let mut flags = default_flags();
flags.wait_until = Some("networkidle".to_string());
let cmd = parse_command(&args("open example.com"), &flags).unwrap();
assert_eq!(cmd["waitUntil"], "networkidle");
}

#[test]
fn test_navigate_without_wait_until() {
let cmd = parse_command(&args("open example.com"), &default_flags()).unwrap();
// waitUntil should not be present when flag is not set (daemon uses its own default)
assert!(cmd.get("waitUntil").is_none());
}

// === Set Headers Tests ===

#[test]
Expand Down
27 changes: 27 additions & 0 deletions cli/src/flags.rs
Original file line number Diff line number Diff line change
Expand Up @@ -22,6 +22,7 @@ pub struct Flags {
pub device: Option<String>,
pub auto_connect: bool,
pub session_name: Option<String>,
pub wait_until: Option<String>,

// Track which launch-time options were explicitly passed via CLI
// (as opposed to being set only via environment variables)
Expand Down Expand Up @@ -69,6 +70,7 @@ pub fn parse_flags(args: &[String]) -> Flags {
device: env::var("AGENT_BROWSER_IOS_DEVICE").ok(),
auto_connect: env::var("AGENT_BROWSER_AUTO_CONNECT").is_ok(),
session_name: env::var("AGENT_BROWSER_SESSION_NAME").ok(),
wait_until: env::var("AGENT_BROWSER_WAIT_UNTIL").ok(),
// Track CLI-passed flags (default false, set to true when flag is passed)
cli_executable_path: false,
cli_extensions: false,
Expand Down Expand Up @@ -186,6 +188,12 @@ pub fn parse_flags(args: &[String]) -> Flags {
i += 1;
}
}
"--wait-until" => {
if let Some(s) = args.get(i + 1) {
flags.wait_until = Some(s.clone());
i += 1;
}
}
_ => {}
}
i += 1;
Expand Down Expand Up @@ -224,6 +232,7 @@ pub fn clean_args(args: &[String]) -> Vec<String> {
"--provider",
"--device",
"--session-name",
"--wait-until",
];

for arg in args.iter() {
Expand Down Expand Up @@ -401,4 +410,22 @@ mod tests {
assert!(!flags.cli_extensions);
assert!(!flags.cli_state);
}

#[test]
fn test_parse_wait_until_flag() {
let flags = parse_flags(&args("open example.com --wait-until domcontentloaded"));
assert_eq!(flags.wait_until, Some("domcontentloaded".to_string()));
}

#[test]
fn test_parse_no_wait_until_flag() {
let flags = parse_flags(&args("open example.com"));
assert!(flags.wait_until.is_none());
}

#[test]
fn test_clean_args_removes_wait_until() {
let cleaned = clean_args(&args("open example.com --wait-until domcontentloaded"));
assert_eq!(cleaned, vec!["open", "example.com"]);
}
}
8 changes: 8 additions & 0 deletions cli/src/output.rs
Original file line number Diff line number Diff line change
Expand Up @@ -491,6 +491,10 @@ https:// is automatically prepended.

Aliases: goto, navigate

Options:
--wait-until <strategy> When to consider navigation done (default: domcontentloaded)
Values: load, domcontentloaded, networkidle

Global Options:
--json Output as JSON
--session <name> Use specific session
Expand All @@ -501,6 +505,7 @@ Examples:
agent-browser open example.com
agent-browser open https://github.com
agent-browser open localhost:3000
agent-browser open example.com --wait-until networkidle
agent-browser open api.example.com --headers '{"Authorization": "Bearer token"}'
# ^ Headers only sent to api.example.com, not other domains
"##
Expand Down Expand Up @@ -1872,6 +1877,8 @@ Options:
--headed Show browser window (not headless)
--cdp <port> Connect via CDP (Chrome DevTools Protocol)
--auto-connect Auto-discover and connect to running Chrome
--wait-until <strategy> Navigation wait strategy: load, domcontentloaded, networkidle
(or AGENT_BROWSER_WAIT_UNTIL, default: domcontentloaded)
--session-name <name> Auto-save/restore session state (cookies, localStorage)
--debug Debug output
--version, -V Show version
Expand All @@ -1885,6 +1892,7 @@ Environment:
AGENT_BROWSER_PROVIDER Browser provider (ios, browserbase, kernel, browseruse)
AGENT_BROWSER_AUTO_CONNECT Auto-discover and connect to running Chrome
AGENT_BROWSER_STREAM_PORT Enable WebSocket streaming on port (e.g., 9223)
AGENT_BROWSER_WAIT_UNTIL Navigation wait strategy (default: domcontentloaded)
AGENT_BROWSER_IOS_DEVICE Default iOS device name
AGENT_BROWSER_IOS_UDID Default iOS device UDID

Expand Down
2 changes: 1 addition & 1 deletion src/actions.ts
Original file line number Diff line number Diff line change
Expand Up @@ -511,7 +511,7 @@ async function handleNavigate(
}

await page.goto(command.url, {
waitUntil: command.waitUntil ?? 'load',
waitUntil: command.waitUntil ?? 'domcontentloaded',
});

return successResponse(command.id, {
Expand Down