{"record":{"id":"154b2a849e5ce685","repo":"tw93/Pake","slug":"about-blank-must-be-a-valid-url","errorCode":null,"errorMessage":"about:blank must be a valid URL","messagePattern":"about:blank must be a valid URL","errorType":"panic","errorClass":null,"httpStatus":null,"severity":"info","filePath":"src-tauri/src/app/window.rs","lineNumber":401,"sourceCode":"    // On macOS both HTTP Basic auth and certificate bypass use the same\n    // navigation-delegate proxy. Start on a neutral page so the proxy is in\n    // place before the target can issue its first authentication challenge.\n    #[cfg(target_os = \"macos\")]\n    let auth_target = if label == \"pake\"\n        && window_config.url_type == \"web\"\n        && (config.basic_auth || window_config.ignore_certificate_errors)\n    {\n        Url::parse(&window_config.url).ok()\n    } else {\n        None\n    };\n\n    // The delegate must be installed before the first TLS challenge. Start on\n    // a neutral page, then navigate from the with_webview callback below.\n    #[cfg(target_os = \"macos\")]\n    let url = if auth_target.is_some() {\n        WebviewUrl::CustomProtocol(\n            Url::parse(\"about:blank\").expect(\"about:blank must be a valid URL\"),\n        )\n    } else {\n        url\n    };\n\n    let user_agent = config.user_agent.get();\n\n    let config_script = format!(\n        \"window.pakeConfig = {}\",\n        serde_json::to_string(&window_config).unwrap_or_else(|_| \"{}\".to_string())\n    );\n\n    // Platform-specific title: macOS prefers empty, others fallback to product name\n    let effective_title = window_config.title.as_deref().unwrap_or_else(|| {\n        if cfg!(target_os = \"macos\") {\n            \"\"\n        } else {\n            tauri_config.product_name.as_deref().unwrap_or(\"\")","sourceCodeStart":383,"sourceCodeEnd":419,"githubUrl":"https://github.com/tw93/Pake/blob/777dd552ade5fd49c96cf4cbab73312eba1011db/src-tauri/src/app/window.rs#L383-L419","documentation":"This is a Rust `.expect(...)` panic on `Url::parse(\"about:blank\")` in the macOS auth-popup path of `build_window` (src-tauri/src/app/window.rs:401). The `url` crate's parser rejects strings that are not valid RFC 3986 URLs; the `.expect` converts a failed parse into a hard panic at window creation. In practice `about:blank` is a valid URL and always parses, so this panic is a defensive assertion, not a condition users can normally reach.","triggerScenarios":"Only reachable when compiling on `target_os = \"macos\"` with `auth_target.is_some()` (a macOS Basic Auth / certificate-error flow) AND the literal `\"about:blank\"` string being changed to something the `url` crate cannot parse. A plain `Url::parse(\"about:blank\")` in user code panics only if the string is malformed (bad scheme, invalid percent-encoding, missing scheme, etc.).","commonSituations":"Developers hit this pattern when (1) refactoring the hardcoded `about:blank` literal into a config value or constant and mistyping it, (2) copying the parse-expect idiom with user-supplied URL strings that may lack a scheme, or (3) using an older `url` crate version whose parser is stricter about some scheme forms. End users of the packaged app essentially never see it.","solutions":["Keep the literal as `about:blank` — it always parses; if you hit this panic, diff the string against the original literal in window.rs:401","Replace `.expect(...)` with graceful error handling: `Url::parse(s).map_err(|e| ...)` and fall back to the plain `url` branch instead of starting on the neutral page","If parsing a dynamic string, validate it before calling `Url::parse`, e.g. require a scheme: `if !s.contains(\"://\") && s != \"about:blank\" { prepend \"https://\" }`","Pin/upgrade the `url` crate and re-run `cargo build` to rule out a version-specific parser regression"],"exampleFix":"// before\nWebviewUrl::CustomProtocol(\n    Url::parse(\"about:blank\").expect(\"about:blank must be a valid URL\"),\n)\n// after\nlet neutral = Url::parse(\"about:blank\")\n    .map_err(|e| anyhow::anyhow!(\"neutral page URL invalid: {e}\"))?;\nWebviewUrl::CustomProtocol(neutral)","handlingStrategy":"validation","validationCode":"fn is_parseable_url(s: &str) -> bool {\n    url::Url::parse(s).is_ok()\n}\n// call before using the value as a WebviewUrl\nassert!(is_parseable_url(\"about:blank\"));","typeGuard":"fn valid_url(s: &str) -> Option<url::Url> {\n    url::Url::parse(s).ok()\n}","tryCatchPattern":"let parsed = url::Url::parse(input).map_err(|e| format!(\"invalid URL '{input}': {e}\"))?; // propagate instead of expect","preventionTips":["Never `.expect()`/`.unwrap()` on `Url::parse` for any string that is not a compile-time literal","Keep neutral-page literals like `about:blank` as constants and add a unit test asserting they parse","Centralize URL parsing in one helper that returns `Result` so panics cannot scatter through the codebase"],"tags":["rust","url-parsing","macos","panic","tauri"],"backgroundTag":"invalid-url-parse","analyzedSha":"777dd552ade5fd49c96cf4cbab73312eba1011db","analyzedAt":"2026-09-05T10:03:52.999Z","contentChangedAt":"2026-09-05T10:03:52.999Z","schemaVersion":2},"datasetVersion":"2026-09-14T05:17:10.506Z"}