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
1 change: 1 addition & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,7 @@
- OIDC now checks both normalized request paths and their resolved SQL files against protected prefixes, closing authentication bypasses through path and clean-URL aliases. Nonce verification also rejects provider-returned Argon2 parameters outside SQLPage's fixed low-cost profile before hashing.
- `cargo install sqlpage`, and any build from the crates.io tarball, no longer needs internet access. The browser libraries now come from npm and ship inside the published crate. Building from a git checkout needs `npm ci` first. Pre-built binaries and the Docker image are unaffected.
- The browser libraries are now part of the browser scripts. SQLPage no longer defines the `window.tabler` and `window.bootstrap` globals; custom scripts that reached for them should load their own copy of Bootstrap.
- The startup message now reports the address the server actually bound instead of the one it was configured with.

## v0.46.3

Expand Down
64 changes: 48 additions & 16 deletions src/webserver/http.rs
Original file line number Diff line number Diff line change
Expand Up @@ -40,6 +40,7 @@ use chrono::{DateTime, Utc};
use futures_util::StreamExt;
use futures_util::stream::Stream;
use std::borrow::Cow;
use std::net::SocketAddr;
use std::path::PathBuf;
use std::pin::Pin;
use std::sync::Arc;
Expand Down Expand Up @@ -680,7 +681,7 @@ pub async fn run_server(config: &AppConfig, state: AppState) -> anyhow::Result<(
}
}

log_welcome_message(config);
log_welcome_message(config, &server.addrs());
server
.run()
.await
Expand All @@ -691,25 +692,33 @@ pub async fn run_server(config: &AppConfig, state: AppState) -> anyhow::Result<(
Ok(())
}

fn log_welcome_message(config: &AppConfig) {
fn website_url(bound_to: SocketAddr) -> String {
let port = bound_to.port();
let ip = bound_to.ip();
if ip.is_unspecified() {
format!(
"http://localhost:{port}\n\
(also accessible from other devices using your IP address)"
)
} else if ip.is_ipv6() {
format!("http://[{ip}]:{port}")
} else {
format!("http://{ip}:{port}")
}
}

fn log_welcome_message(config: &AppConfig, bound_to: &[SocketAddr]) {
let address_message = if let Some(unix_socket) = &config.unix_socket {
format!("unix socket \"{}\"", unix_socket.display())
} else if let Some(domain) = &config.https_domain {
format!("https://{domain}")
} else {
let listen_on = config.listen_on();
let port = listen_on.port();
let ip = listen_on.ip();
if ip.is_unspecified() {
format!(
"http://localhost:{port}\n\
(also accessible from other devices using your IP address)"
)
} else if ip.is_ipv6() {
format!("http://[{ip}]:{port}")
} else {
format!("http://{ip}:{port}")
}
bound_to
.iter()
.copied()
.map(website_url)
.collect::<Vec<String>>()
.join("\n")
};

let (sparkle, link, computer, rocket) = if cfg!(target_os = "windows") {
Expand Down Expand Up @@ -747,10 +756,33 @@ fn bind_unix_socket_err(e: std::io::Error, unix_socket: &std::path::Path) -> any

#[cfg(test)]
mod tests {
use super::{request_span_name, sql_execution_span_name};
use super::{request_span_name, sql_execution_span_name, website_url};
use actix_web::test::TestRequest;
use std::path::Path;

#[test]
fn website_url_reports_the_address_the_server_bound() {
assert_eq!(
website_url("127.0.0.1:34567".parse().unwrap()),
"http://127.0.0.1:34567"
);
}

#[test]
fn website_url_sends_an_unspecified_address_to_localhost() {
assert!(
website_url("0.0.0.0:8080".parse().unwrap()).starts_with("http://localhost:8080\n")
);
}

#[test]
fn website_url_brackets_an_ipv6_address() {
assert_eq!(
website_url("[::1]:8080".parse().unwrap()),
"http://[::1]:8080"
);
}

#[test]
fn request_span_name_uses_request_path_when_no_matched_route_exists() {
let request = TestRequest::with_uri("/todos/42?filter=open").to_srv_request();
Expand Down
Loading