Skip to content

Commit 42cc629

Browse files
committed
redirect url error fixed
1 parent 3301320 commit 42cc629

2 files changed

Lines changed: 36 additions & 11 deletions

File tree

src/handlers/http/oidc.rs

Lines changed: 4 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -660,13 +660,10 @@ fn get_canonical_origin() -> Url {
660660
if let Some(origin_url) = &PARSEABLE.options.domain_address {
661661
return origin_url.clone();
662662
}
663-
let addr = &PARSEABLE.options.address;
664-
// detect http vs https based on TLS cert/key
665-
let scheme = PARSEABLE.options.get_scheme();
666-
match Url::parse(&format!("{}://{}", scheme, addr)) {
667-
Ok(url) => url,
668-
Err(_) => Url::parse("http://localhost:8000").unwrap(),
669-
}
663+
crate::oidc::canonical_local_origin(
664+
&PARSEABLE.options.address,
665+
PARSEABLE.options.tls_cert_path.is_some() && PARSEABLE.options.tls_key_path.is_some(),
666+
)
670667
}
671668

672669
fn is_valid_redirect_url_safe(canonical: &Url, redirect: &str) -> Result<String, ()> {

src/oidc.rs

Lines changed: 32 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -54,10 +54,7 @@ impl OpenidConfig {
5454
redirect_to: &str,
5555
) -> Result<DiscoveredClient, openid::error::Error> {
5656
let redirect_uri = match self.origin {
57-
Origin::Local { socket_addr, https } => {
58-
let protocol = if https { "https" } else { "http" };
59-
url::Url::parse(&format!("{protocol}://{socket_addr}")).expect("valid url")
60-
}
57+
Origin::Local { socket_addr, https } => canonical_local_origin(&socket_addr, https),
6158
Origin::Production(url) => url,
6259
};
6360

@@ -67,6 +64,37 @@ impl OpenidConfig {
6764
}
6865
}
6966

67+
pub fn canonical_local_origin(socket_addr: &str, https: bool) -> Url {
68+
let scheme = if https { "https" } else { "http" };
69+
let mut url = Url::parse(&format!("{scheme}://{socket_addr}"))
70+
.unwrap_or_else(|_| Url::parse(&format!("{scheme}://localhost:8000")).unwrap());
71+
if matches!(url.host_str(), Some("0.0.0.0") | Some("::")) {
72+
url.set_host(Some("localhost")).expect("localhost is valid");
73+
}
74+
url
75+
}
76+
77+
#[cfg(test)]
78+
mod tests {
79+
use super::*;
80+
81+
#[test]
82+
fn wildcard_ipv4_origin_uses_localhost_with_configured_port() {
83+
assert_eq!(
84+
canonical_local_origin("0.0.0.0:8000", false).as_str(),
85+
"http://localhost:8000/"
86+
);
87+
}
88+
89+
#[test]
90+
fn loopback_ipv4_origin_is_preserved() {
91+
assert_eq!(
92+
canonical_local_origin("127.0.0.1:9000", false).as_str(),
93+
"http://127.0.0.1:9000/"
94+
);
95+
}
96+
}
97+
7098
#[derive(Debug, serde::Serialize, serde::Deserialize, Clone)]
7199
pub struct Claims {
72100
#[serde(flatten)]

0 commit comments

Comments
 (0)