Browse Source

Make non-UTF8 stdout/stderr from nodes non-fatal

Log a warning instead and do a lossy conversion to String. This ensures that `stdout`/`stderr` stay open, which avoids a `SIGPIPE` exit of the node on the next println.
tags/v0.3.5-fix4
Philipp Oppermann 1 year ago
parent
commit
a832b53a1a
Failed to extract signature
1 changed files with 31 additions and 5 deletions
  1. +31
    -5
      binaries/daemon/src/spawn.rs

+ 31
- 5
binaries/daemon/src/spawn.rs View File

@@ -272,16 +272,29 @@ pub async fn spawn_node(
let mut buffer = String::new();
let mut finished = false;
while !finished {
let mut raw = Vec::new();
finished = match child_stdout
.read_line(&mut buffer)
.read_until(b'\n', &mut raw)
.await
.wrap_err("failed to read stdout line from spawned node")
.wrap_err_with(|| format!("failed to read stdout line from spawned node {node_id}"))
{
Ok(0) => true,
Ok(_) => false,
Err(err) => {
tracing::warn!("{err:?}");
true
false
}
};

match String::from_utf8(raw) {
Ok(s) => buffer.push_str(&s),
Err(err) => {
let lossy = String::from_utf8_lossy(err.as_bytes());
tracing::warn!(
"stdout not valid UTF-8 string (node {node_id}): {}: {lossy}",
err.utf8_error()
);
buffer.push_str(&lossy)
}
};

@@ -319,10 +332,11 @@ pub async fn spawn_node(
let mut buffer = String::new();
let mut finished = false;
while !finished {
let mut raw = Vec::new();
finished = match child_stderr
.read_line(&mut buffer)
.read_until(b'\n', &mut raw)
.await
.wrap_err("failed to read stderr line from spawned node")
.wrap_err_with(|| format!("failed to read stderr line from spawned node {node_id}"))
{
Ok(0) => true,
Ok(_) => false,
@@ -332,6 +346,18 @@ pub async fn spawn_node(
}
};

match String::from_utf8(raw) {
Ok(s) => buffer.push_str(&s),
Err(err) => {
let lossy = String::from_utf8_lossy(err.as_bytes());
tracing::warn!(
"stderr not valid UTF-8 string (node {node_id}): {}: {lossy}",
err.utf8_error()
);
buffer.push_str(&lossy)
}
};

if buffer.starts_with("Traceback (most recent call last):") {
if !finished {
continue;


Loading…
Cancel
Save