neondatabase/neon · error

cannot find 'rel='

Error message

cannot find 'rel='

What it means

SpanAttributesFromLogs::from_str extracts a key from a pasted log line such as "whatever{rel=1663/16389/24615 blkno=1052204 req_lsn=FFFFFFFF/FFFFFFFF}". It requires the literal marker rel=; without it the parse fails. This error also surfaces nested inside error 210's combined message when the single-argument path tries the log-line parser.

Source

Thrown at pageserver/ctl/src/key.rs:254

                Ok(KeyMaterial::Split(reltag, blocknum))
            }
        }
    }
}

#[derive(Debug)]
pub(super) struct SpanAttributesFromLogs(RelTag, BlockNumber);

impl std::str::FromStr for SpanAttributesFromLogs {
    type Err = anyhow::Error;

    fn from_str(s: &str) -> Result<Self, Self::Err> {
        // accept the span separator but do not require or fail if either is missing
        // "whatever{rel=1663/16389/24615 blkno=1052204 req_lsn=FFFFFFFF/FFFFFFFF}"
        let (_, reltag) = s
            .split_once("rel=")
            .ok_or_else(|| anyhow::anyhow!("cannot find 'rel='"))?;
        let reltag = reltag.split_whitespace().next().unwrap();

        let (_, blocknum) = s
            .split_once("blkno=")
            .ok_or_else(|| anyhow::anyhow!("cannot find 'blkno='"))?;
        let blocknum = blocknum.split_whitespace().next().unwrap();

        let reltag = reltag
            .parse()
            .with_context(|| format!("parse reltag from {reltag:?}"))?;
        let blocknum = blocknum
            .parse()
            .with_context(|| format!("parse blocknum from {blocknum:?}"))?;

        Ok(Self(reltag, blocknum))
    }
}

View on GitHub (pinned to 8f60b04da4)

Solutions

  1. Paste a line that includes rel=<tablespace>/<dbnode>/<relnode>, for example rel=1663/16389/24615.
  2. If you only have the raw values, use the multi-argument form instead: pageserver_ctl key 1663/16389/24615 1052204.

Example fix

# before
pageserver_ctl key "get_page_at_lsn req_lsn=FFFFFFFF/FFFFFFFF"
# -> "cannot find 'rel='"

# after
pageserver_ctl key "whatever{rel=1663/16389/24615 blkno=1052204 req_lsn=FFFFFFFF/FFFFFFFF}"
Defensive patterns

Strategy: validation

Validate before calling

// before passing a log line, require the markers it needs
anyhow::ensure!(line.contains("rel="), "log line must contain rel=<spc>/<db>/<relnode>");

Type guard

fn log_line_has_rel(line: &str) -> bool {
    line.contains("rel=")
}

Prevention

When it happens

Trigger: Passing a single argument intended as a log line that lacks the rel= marker.

Common situations: Pasting a log line from a context that does not log relation attributes; trimming the line so the rel= token is cut off.

Related errors


AI-assisted analysis of neondatabase/neon@8f60b04da4 (2026-08-16). Data as JSON: /api/errors/bee5d06c1ea9b6cb. Report an issue: GitHub.