Skip to content
Merged
Show file tree
Hide file tree
Changes from 1 commit
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
Prev Previous commit
Next Next commit
add expose-local flag: default off
  • Loading branch information
nick1udwig committed Jun 23, 2025
commit 4cfcfef342060a565d7100072246d825e22105b2
11 changes: 9 additions & 2 deletions hyperdrive/src/http/server.rs
Original file line number Diff line number Diff line change
Expand Up @@ -187,6 +187,7 @@ pub async fn http_server(
mut recv_in_server: MessageReceiver,
send_to_loop: MessageSender,
print_tx: PrintSender,
expose_local: bool,
) -> anyhow::Result<()> {
let http_response_senders: HttpResponseSenders = Arc::new(DashMap::new());
let ws_senders: WebSocketSenders = Arc::new(DashMap::new());
Expand Down Expand Up @@ -222,6 +223,7 @@ pub async fn http_server(
Arc::new(jwt_secret_bytes),
send_to_loop.clone(),
print_tx.clone(),
expose_local,
));

while let Some(km) = recv_in_server.recv().await {
Expand Down Expand Up @@ -254,6 +256,7 @@ async fn serve(
jwt_secret_bytes: Arc<Vec<u8>>,
send_to_loop: MessageSender,
print_tx: PrintSender,
expose_local: bool,
) {
// filter to receive websockets
let cloned_our = our.clone();
Expand All @@ -271,6 +274,7 @@ async fn serve(
.and(warp::any().map(move || ws_path_bindings.clone()))
.and(warp::any().map(move || cloned_msg_tx.clone()))
.and(warp::any().map(move || cloned_print_tx.clone()))
.and(warp::any().map(move || expose_local.clone()))
.and_then(ws_handler);

#[cfg(feature = "simulation-mode")]
Expand Down Expand Up @@ -317,6 +321,7 @@ async fn serve(
.and(warp::any().map(move || send_to_loop.clone()))
.and(warp::any().map(move || print_tx.clone()))
.and(warp::any().map(move || login_html.clone()))
.and(warp::any().map(move || expose_local.clone()))
.and_then(http_handler);

let filter_with_ws = ws_route.or(login).or(filter);
Expand Down Expand Up @@ -465,6 +470,7 @@ async fn ws_handler(
ws_path_bindings: WsPathBindings,
send_to_loop: MessageSender,
print_tx: PrintSender,
expose_local: bool,
) -> Result<impl warp::Reply, warp::Rejection> {
let original_path = utils::normalize_path(path.as_str());
Printout::new(
Expand Down Expand Up @@ -548,7 +554,7 @@ async fn ws_handler(

let is_behind_reverse_proxy = utils::is_behind_reverse_proxy(&headers);

if bound_path.extension && (!is_local || is_behind_reverse_proxy) {
if bound_path.extension && (!is_local || is_behind_reverse_proxy || !expose_local) {
return Err(warp::reject::reject());
}

Expand Down Expand Up @@ -597,6 +603,7 @@ async fn http_handler(
send_to_loop: MessageSender,
print_tx: PrintSender,
login_html: Arc<String>,
expose_local: bool,
) -> Result<impl warp::Reply, warp::Rejection> {
let original_path = utils::normalize_path(path.as_str());
let base_path = original_path.split('/').skip(1).next().unwrap_or("");
Expand Down Expand Up @@ -741,7 +748,7 @@ async fn http_handler(

let is_behind_reverse_proxy = utils::is_behind_reverse_proxy(&headers);

if bound_path.local_only && (!is_local || is_behind_reverse_proxy) {
if bound_path.local_only && (!is_local || is_behind_reverse_proxy || !expose_local) {
return Ok(warp::reply::with_status(vec![], StatusCode::FORBIDDEN).into_response());
}

Expand Down
7 changes: 7 additions & 0 deletions hyperdrive/src/main.rs
Original file line number Diff line number Diff line change
Expand Up @@ -106,6 +106,8 @@ async fn main() {
.expect("failed to parse given --process-verbosity. Must be JSON Object with keys `ProcessId`s and values either `{\"U8\": <verbosity>}` or `\"Muted\"`")
};

let expose_local = *matches.get_one::<bool>("expose-local").unwrap();

#[cfg(feature = "simulation-mode")]
let (fake_node_name, fakechain_port) = (
matches.get_one::<String>("fake-node-name"),
Expand Down Expand Up @@ -458,6 +460,7 @@ async fn main() {
http_server_receiver,
kernel_message_sender.clone(),
print_sender.clone(),
expose_local,
));
tasks.spawn(http::client::http_client(
our.name.clone(),
Expand Down Expand Up @@ -784,6 +787,10 @@ fn build_command() -> Command {
.arg(
arg!(--"process-verbosity" <JSON_STRING> "ProcessId: verbosity JSON object")
.default_value("")
)
.arg(
arg!(--"expose-local" <EXPOSE_LOCAL> "Expose local-only and RPC endpoints. WARNING: If behind a reverse proxy, ensure proxy is set to put `x-forwarded-for` headers or this will allow your node to be controlled remotely without authentication! (caddy adds these headers by default and so is strongly recommended)")
.action(clap::ArgAction::SetTrue),
);

#[cfg(feature = "simulation-mode")]
Expand Down