Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

refactor(windows): use http scheme by default for custom protocols and add option to change it #994

Merged
merged 8 commits into from
Aug 14, 2023
Merged
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
5 changes: 5 additions & 0 deletions .changes/windows-http.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
---
"wry": "minor"
---

**Breaking change** Wry now defaults to `http://<scheme>.localhost/` for custom protocols on Windows.
5 changes: 5 additions & 0 deletions .changes/windows-with-https-scheme.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
---
"wry": "minor"
---

Add `WebViewBuilderExtWindows::with_https_scheme` to be able to choose between `http` and `https` for custom protocols on Windows.
15 changes: 15 additions & 0 deletions src/webview/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -277,6 +277,7 @@ pub(crate) struct PlatformSpecificWebViewAttributes {
additional_browser_args: Option<String>,
browser_accelerator_keys: bool,
theme: Option<Theme>,
https_scheme: bool,
}
#[cfg(windows)]
impl Default for PlatformSpecificWebViewAttributes {
Expand All @@ -285,6 +286,7 @@ impl Default for PlatformSpecificWebViewAttributes {
additional_browser_args: None,
browser_accelerator_keys: true, // This is WebView2's default behavior
theme: None,
https_scheme: false, // To match macOS & Linux behavior in the context of mixed content.
}
}
}
Expand Down Expand Up @@ -695,6 +697,14 @@ pub trait WebViewBuilderExtWindows {
///
/// Defaults to [`Theme::Auto`] which will follow the OS defaults.
fn with_theme(self, theme: Theme) -> Self;

/// Determines whether the custom protocols should use `https://<scheme>.localhost` instead of the default `http://<scheme>.localhost`.
///
/// Using a `http` scheme will allow mixed content when trying to fetch `http` endpoints
/// and is therefore less secure but will match the behavior of the `<scheme>://localhost` protocols used on macOS and Linux.
///
/// The default value is `false`.
fn with_https_scheme(self, enabled: bool) -> Self;
}

#[cfg(windows)]
Expand All @@ -713,6 +723,11 @@ impl WebViewBuilderExtWindows for WebViewBuilder<'_> {
self.platform_specific.theme = Some(theme);
self
}

fn with_https_scheme(mut self, enabled: bool) -> Self {
self.platform_specific.https_scheme = enabled;
self
}
}

#[cfg(target_os = "android")]
Expand Down
17 changes: 11 additions & 6 deletions src/webview/webview2/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -537,15 +537,20 @@ window.addEventListener('mousemove', (e) => window.chrome.webview.postMessage('_
}
}

let scheme = if pl_attrs.https_scheme {
"https"
} else {
"http"
};
let mut custom_protocol_names = HashSet::new();
if !attributes.custom_protocols.is_empty() {
for (name, _) in &attributes.custom_protocols {
// WebView2 doesn't support non-standard protocols yet, so we have to use this workaround
// WebView2 supports non-standard protocols only on Windows 10+, so we have to use this workaround
// See https://github.com/MicrosoftEdge/WebView2Feedback/issues/73
custom_protocol_names.insert(name.clone());
unsafe {
webview.AddWebResourceRequestedFilter(
PCWSTR::from_raw(encode_wide(format!("https://{}.*", name)).as_ptr()),
PCWSTR::from_raw(encode_wide(format!("{scheme}://{name}.*")).as_ptr()),
COREWEBVIEW2_WEB_RESOURCE_CONTEXT_ALL,
)
}
Expand Down Expand Up @@ -616,11 +621,11 @@ window.addEventListener('mousemove', (e) => window.chrome.webview.postMessage('_

if let Some(custom_protocol) = custom_protocols
.iter()
.find(|(name, _)| uri.starts_with(&format!("https://{}.", name)))
.find(|(name, _)| uri.starts_with(&format!("{scheme}://{name}.")))
{
// Undo the protocol workaround when giving path to resolver
let path = uri.replace(
&format!("https://{}.", custom_protocol.0),
&format!("{scheme}://{}.", custom_protocol.0),
&format!("{}://", custom_protocol.0),
);

Expand Down Expand Up @@ -741,11 +746,11 @@ window.addEventListener('mousemove', (e) => window.chrome.webview.postMessage('_
let mut url_string = String::from(url.as_str());
let name = url.scheme();
if custom_protocol_names.contains(name) {
// WebView2 doesn't support non-standard protocols yet, so we have to use this workaround
// WebView2 supports non-standard protocols only on Windows 10+, so we have to use this workaround
// See https://github.com/MicrosoftEdge/WebView2Feedback/issues/73
url_string = url
.as_str()
.replace(&format!("{}://", name), &format!("https://{}.", name))
.replace(&format!("{}://", name), &format!("{scheme}://{name}."))
}

if let Some(headers) = attributes.headers {
Expand Down
Loading