diff options
| author | tv <tv@krebsco.de> | 2026-11-09 15:37:16 +0000 |
|---|---|---|
| committer | tv <tv@krebsco.de> | 2026-11-09 18:20:09 +0100 |
| commit | 822e6a8268e2bc03463b2f0672fd6d6aad160432 (patch) | |
| tree | 42228ecc05d87c19ddaf1f7f66e5cdd00740deb7 /src/document | |
| parent | d16da7283ceca16f223f3fb6b0429c7b2ae1aec0 (diff) | |
signatures: a listed signed path takes `*`, as everything else does
Review 4, appendix: whether a write is signed because `_continuum/access/signed` lists
its path compared the listed paths by prefix (`signatures::related`), so a `*` there
was a literal key, while api.md says the list holds paths as capabilities name them,
which take `*` since 1259, and signed values already read the same list as patterns
(`envelope::reaches_signed`). A listed `metrics/*/alerts` signed nothing.
It compares by `access::agree` now: within or above the pattern, `*` for any one key.
Diffstat (limited to 'src/document')
| -rw-r--r-- | src/document/signatures.rs | 19 |
1 files changed, 16 insertions, 3 deletions
diff --git a/src/document/signatures.rs b/src/document/signatures.rs index da2df03..e5c9e69 100644 --- a/src/document/signatures.rs +++ b/src/document/signatures.rs @@ -60,10 +60,11 @@ impl Sign { } } -/// Whether a write at `path` touches what is at `signed`: within it, or above it -/// (replacing or deleting what holds it). +/// Whether a write at `path` touches what is at `signed`, a pattern as capabilities and +/// signed values take them (`*` for any one key): within it, or above it (replacing or +/// deleting what holds it). fn related(signed: &[String], path: &[String]) -> bool { - path.starts_with(signed) || signed.starts_with(path) + crate::access::agree(signed, path) } /// The paths `doc` lists as signed (`SIGNED_PATHS`); an entry that isn't a list of @@ -587,6 +588,18 @@ mod tests { .unwrap(); } + /// A listed signed path is a pattern: `*` takes any one key, within and above. + #[test] + fn listed_paths_take_a_star() { + let path = |text: &str| -> Vec<String> { text.split('/').map(str::to_owned).collect() }; + let signed = path("metrics/*/alerts"); + assert!(related(&signed, &path("metrics/eu/alerts/x"))); + assert!(related(&signed, &path("metrics/eu"))); + assert!(related(&signed, &path("metrics"))); + assert!(!related(&signed, &path("metrics/eu/rates"))); + assert!(!related(&signed, &path("other"))); + } + /// The latest unsigned change of each of this node's actors is signed, below the /// heads too (an earlier actor's, built on under a later one); another node's, and /// those vouched for, left. |
