Skip to main content

agentics_config/
local_urls.rs

1/// Build the local API base URL from an explicit host and port.
2pub fn local_api_base_url(api_host: &str, api_port: u16) -> String {
3    format!("http://{api_host}:{api_port}")
4}
5
6/// Build the local web base URL from an explicit host and port.
7pub fn local_web_base_url(web_host: &str, web_port: u16) -> String {
8    format!("http://{web_host}:{web_port}")
9}
10
11/// Returns whether a configured bind host is loopback-only.
12pub(crate) fn is_loopback_host(host: &str) -> bool {
13    let host = host.trim();
14    if host.eq_ignore_ascii_case("localhost") {
15        return true;
16    }
17
18    host.parse::<std::net::IpAddr>()
19        .map(|addr| addr.is_loopback())
20        .unwrap_or(false)
21}
22
23/// Returns whether a parsed URL's host is loopback-only.
24pub(crate) fn is_loopback_url(url: &url::Url) -> bool {
25    url.host_str().is_some_and(is_loopback_host)
26}
27
28/// Validates cookie name invariants for this contract.
29pub(crate) fn validate_cookie_name(value: &str, field: &str) -> anyhow::Result<()> {
30    let value = value.trim();
31    if value.is_empty() {
32        anyhow::bail!("{field} must not be empty");
33    }
34    if !value
35        .bytes()
36        .all(|byte| matches!(byte, b'!' | b'#'..=b'\'' | b'*' | b'+' | b'-' | b'.' | b'0'..=b'9' | b'A'..=b'Z' | b'^' | b'_' | b'`' | b'a'..=b'z' | b'|' | b'~'))
37    {
38        anyhow::bail!("{field} contains characters that are not valid in a cookie name");
39    }
40    Ok(())
41}