use super::*;
use newt_core::markup::plain;
use newt_core::{DenialKind, PermissionRequest};
fn net_low() -> PermissionRequest {
PermissionRequest {
tool: "http".into(),
kind: DenialKind::Net,
target: "https://example.com/api".into(),
reason: String::new(),
harness_bound: false,
}
}
fn exec_high() -> PermissionRequest {
PermissionRequest {
tool: "run_command".into(),
kind: DenialKind::Exec,
target: "bash".into(),
reason: "exec of \"bash\" is not within the granted authority".into(),
harness_bound: false,
}
}
fn goldens() -> Vec<(PermissionRequest, Audience, &'static str)> {
vec![
(
net_low(),
Audience::Terminal,
"\u{2298} http wants to reach `https://example.com/api` \u{2014} outside the granted net allowlist.\n\
Esc=back \u{b7} Ctrl-C/Ctrl-D=exit\n\
[a]llow once\n\
[s]ession allow\n\
[A]llow permanently (signs a durable grant)\n\
[d]eny (default)\n\
[D]eny always\n\
[P]ermanently deny",
),
(
net_low(),
Audience::Web,
"\u{2298} http wants to reach `https://example.com/api` \u{2014} outside the granted net allowlist.\n\
Esc=back \u{b7} Ctrl-C/Ctrl-D=exit\n\
[a]llow once\n\
[s]ession allow\n\
[d]eny (default)",
),
(
exec_high(),
Audience::Terminal,
"\u{2298} run_command wants to run `bash` \u{2014} outside the granted exec allowlist.\n\
\u{26a0} `bash` is an interpreter: this grants arbitrary command execution\n \
(exec of \"bash\" is not within the granted authority)\n\
high-danger: session allow refused; key allow / step-up is the future path, P3\n\
Esc=back \u{b7} Ctrl-C/Ctrl-D=exit\n\
[a]llow once\n\
[d]eny (default)\n\
[D]eny always\n\
[P]ermanently deny",
),
(
exec_high(),
Audience::Web,
"\u{2298} run_command wants to run `bash` \u{2014} outside the granted exec allowlist.\n\
\u{26a0} `bash` is an interpreter: this grants arbitrary command execution\n \
(exec of \"bash\" is not within the granted authority)\n\
High danger: session authorization is unavailable.\n\
Esc=back \u{b7} Ctrl-C/Ctrl-D=exit\n\
[a]llow once\n\
[d]eny (default)",
),
]
}
#[test]
fn render_reproduces_every_a0_golden_byte_for_byte() {
let table = danger::DangerTable::builtin();
for (req, audience, golden) in goldens() {
let definition = permission_definition(&req, &table, audience.clone());
assert_eq!(
plain::render(&definition),
golden,
"the plain renderer moved frozen bytes for {:?}/{audience:?}",
req.tool
);
let composed = format!("{}\n{MODAL_INPUT_GLYPH}", plain::render(&definition));
assert_eq!(composed, format!("{golden}\n{MODAL_INPUT_GLYPH}"));
assert!(
composed.ends_with(&format!("\n{MODAL_INPUT_GLYPH}")),
"the input glyph is not alone on the final line: {composed:?}"
);
}
}
#[test]
fn the_free_text_form_renders_with_a_clear_modal_identity() {
let form = free_text_form("which file should I edit?");
assert_eq!(
plain::render(&form),
"Prompt — which file should I edit?\nEsc=back \u{b7} Ctrl-C/Ctrl-D=exit"
);
assert!(!plain::render(&form).contains('['));
assert!(!form.markdown.starts_with("? "));
}
#[test]
fn the_web_matrix_is_unaffected() {
let table = danger::DangerTable::builtin();
let low = permission_definition(&net_low(), &table, Audience::Web);
let ControlKind::Choice { options } = &low.controls[0].kind else {
panic!("the decision control is not a choice");
};
assert_eq!(
options.iter().map(|o| o.id.as_str()).collect::<Vec<_>>(),
["allow_once", "allow_session", "deny"],
"the web action matrix changed"
);
let high = permission_definition(&exec_high(), &table, Audience::Web);
let ControlKind::Choice { options } = &high.controls[0].kind else {
panic!("the decision control is not a choice");
};
assert_eq!(
options.iter().map(|o| o.id.as_str()).collect::<Vec<_>>(),
["allow_once", "deny"],
"the web action matrix changed for a high-danger target"
);
for definition in [&low, &high] {
let ControlKind::Choice { options } = &definition.controls[0].kind else {
panic!("not a choice");
};
assert!(!options.is_empty(), "a web offer must offer something");
for option in options {
assert!(
action_for_option(option.id.as_str()).is_some(),
"every offered option names an action this build knows: {}",
option.id.as_str()
);
}
}
}