flake-info: Adapt RFC-166 style (#749)

* flake-info: Adapt RFC-166 style

* flake-info: Properly escape attrset keys

* flake-info: Stop owning values for pretty-printing
This commit is contained in:
Janne Heß 2024-04-08 18:29:16 +02:00 committed by GitHub
parent 7081483b91
commit 0f14890c79
Failed to generate hash of commit
2 changed files with 99 additions and 14 deletions

View file

@ -145,7 +145,7 @@ impl Serialize for DocValue {
md.to_owned() md.to_owned()
})) }))
} }
DocValue::Value(v) => serializer.serialize_str(&print_value(v.to_owned())), DocValue::Value(v) => serializer.serialize_str(&print_value(v)),
} }
} }
} }

View file

@ -15,11 +15,24 @@ impl Display for Indent {
} }
} }
pub fn print_value(value: Value) -> String { pub fn print_value(value: &Value) -> String {
print_value_indent(value, Indent(0)) print_value_indent(value, Indent(0))
} }
fn print_value_indent(value: Value, indent: Indent) -> String { /// Formats an attrset key by adding quotes when necessary
fn format_attrset_key(key: &str) -> String {
if key.contains("/")
|| key.contains(" ")
|| key.is_empty()
|| (b'0'..=b'9').contains(&key.as_bytes()[0])
{
format!("{:?}", key)
} else {
key.to_string()
}
}
fn print_value_indent(value: &Value, indent: Indent) -> String {
match value { match value {
Value::Null => "null".to_owned(), Value::Null => "null".to_owned(),
Value::Bool(b) => format!("{}", b), Value::Bool(b) => format!("{}", b),
@ -44,6 +57,14 @@ fn print_value_indent(value: Value, indent: Indent) -> String {
if a.is_empty() { if a.is_empty() {
return "[ ]".to_owned(); return "[ ]".to_owned();
} }
if a.len() == 1 {
// Return early if the wrapped value fits on one line
let val = print_value(a.first().unwrap());
if !val.contains("\n") {
return format!("[ {} ]", val);
}
}
let items = a let items = a
.into_iter() .into_iter()
.map(|v| print_value_indent(v, indent.next())) .map(|v| print_value_indent(v, indent.next()))
@ -63,9 +84,26 @@ fn print_value_indent(value: Value, indent: Indent) -> String {
if o.is_empty() { if o.is_empty() {
return "{ }".to_owned(); return "{ }".to_owned();
} }
if o.len() == 1 {
// Return early if the wrapped value fits on one line
let val = print_value(o.values().next().unwrap());
if !val.contains("\n") {
return format!(
"{{ {} = {}; }}",
format_attrset_key(o.keys().next().unwrap()),
val
);
}
}
let items = o let items = o
.into_iter() .into_iter()
.map(|(k, v)| format!("{} = {}", k, print_value_indent(v, indent.next()))) .map(|(k, v)| {
format!(
"{} = {}",
format_attrset_key(&k),
print_value_indent(v, indent.next())
)
})
.collect::<Vec<_>>() .collect::<Vec<_>>()
.join(&format!(";\n{}", indent.next())); .join(&format!(";\n{}", indent.next()));
@ -90,7 +128,7 @@ mod tests {
#[test] #[test]
fn test_string() { fn test_string() {
let json = json!("Hello World"); let json = json!("Hello World");
assert_eq!(print_value(json), "\"Hello World\""); assert_eq!(print_value(&json), "\"Hello World\"");
} }
#[test] #[test]
@ -101,7 +139,7 @@ World
!!!"# !!!"#
); );
assert_eq!( assert_eq!(
print_value(json), print_value(&json),
r#"'' r#"''
Hello Hello
World World
@ -113,26 +151,46 @@ World
#[test] #[test]
fn test_num() { fn test_num() {
let json = json!(1); let json = json!(1);
assert_eq!(print_value(json), "1"); assert_eq!(print_value(&json), "1");
} }
#[test] #[test]
fn test_bool() { fn test_bool() {
let json = json!(true); let json = json!(true);
assert_eq!(print_value(json), "true"); assert_eq!(print_value(&json), "true");
} }
#[test] #[test]
fn test_empty_list() { fn test_empty_list() {
let json = json!([]); let json = json!([]);
assert_eq!(print_value(json), "[ ]"); assert_eq!(print_value(&json), "[ ]");
}
#[test]
fn test_list_one_item() {
let json = json!([1]);
assert_eq!(print_value(&json), "[ 1 ]");
}
#[test]
fn test_list_one_multiline_item() {
let json = json!(["first line\nsecond line"]);
assert_eq!(
print_value(&json),
r#"[
''
first line
second line
''
]"#
);
} }
#[test] #[test]
fn test_filled_list() { fn test_filled_list() {
let json = json!([1, "hello", true, null]); let json = json!([1, "hello", true, null]);
assert_eq!( assert_eq!(
print_value(json), print_value(&json),
r#"[ r#"[
1 1
"hello" "hello"
@ -145,15 +203,42 @@ World
#[test] #[test]
fn test_empty_set() { fn test_empty_set() {
let json = json!({}); let json = json!({});
assert_eq!(print_value(json), "{ }"); assert_eq!(print_value(&json), "{ }");
}
#[test]
fn test_set_one_item() {
let json = json!({ "hello": "world" });
assert_eq!(print_value(&json), "{ hello = \"world\"; }");
}
#[test]
fn test_set_number_key() {
let json = json!({ "1hello": "world" });
assert_eq!(print_value(&json), "{ \"1hello\" = \"world\"; }");
}
#[test]
fn test_set_one_multiline_item() {
let json = json!({ "hello": "pretty\nworld" });
assert_eq!(
print_value(&json),
"{
hello = ''
pretty
world
'';
}"
);
} }
#[test] #[test]
fn test_filled_set() { fn test_filled_set() {
let json = json!({"hello": "world"}); let json = json!({"hello": "world", "another": "test"});
assert_eq!( assert_eq!(
print_value(json), print_value(&json),
"{ "{
another = \"test\";
hello = \"world\"; hello = \"world\";
}" }"
); );
@ -176,7 +261,7 @@ World
]); ]);
assert_eq!( assert_eq!(
print_value(json), print_value(&json),
r#"[ r#"[
"HDMI-0" "HDMI-0"
{ {