Skip to main content

vix_format_tool/
lib.rs

1//! Reformat the selection (or buffer) within one data format: pretty-print or
2//! minify JSON, and canonicalize YAML and TOML.
3//!
4//! Each function parses the text into a generic value and re-serializes it, so
5//! the document is normalized (consistent indentation, key handling, quoting)
6//! without changing its meaning. Used by the Tools → Format menu via
7//! `App::transform_selection_or_buffer_try`.
8
9#![warn(clippy::pedantic)]
10
11/// Pretty-print JSON with two-space indentation.
12///
13/// # Errors
14/// Returns an error when the input is not valid JSON.
15pub fn json_pretty(input: &str) -> Result<String, String> {
16    let v: serde_json::Value = serde_json::from_str(input).map_err(|e| e.to_string())?;
17    serde_json::to_string_pretty(&v).map_err(|e| e.to_string())
18}
19
20/// Minify JSON to its most compact single-line form.
21///
22/// # Errors
23/// Returns an error when the input is not valid JSON.
24pub fn json_minify(input: &str) -> Result<String, String> {
25    let v: serde_json::Value = serde_json::from_str(input).map_err(|e| e.to_string())?;
26    serde_json::to_string(&v).map_err(|e| e.to_string())
27}
28
29/// Canonicalize YAML (re-emit with consistent formatting).
30///
31/// # Errors
32/// Returns an error when the input is not valid YAML.
33pub fn yaml_format(input: &str) -> Result<String, String> {
34    let v: serde_yaml::Value = serde_yaml::from_str(input).map_err(|e| e.to_string())?;
35    serde_yaml::to_string(&v).map_err(|e| e.to_string())
36}
37
38/// Canonicalize TOML (re-emit pretty-printed).
39///
40/// # Errors
41/// Returns an error when the input is not valid TOML, or is not a table.
42pub fn toml_format(input: &str) -> Result<String, String> {
43    let v: toml::Value = toml::from_str(input).map_err(|e| e.to_string())?;
44    toml::to_string_pretty(&v).map_err(|e| e.to_string())
45}
46
47#[cfg(test)]
48mod tests {
49    use super::*;
50
51    #[test]
52    fn json_pretty_indents() {
53        assert_eq!(json_pretty(r#"{"a":1}"#).unwrap(), "{\n  \"a\": 1\n}");
54    }
55
56    #[test]
57    fn json_minify_compacts() {
58        assert_eq!(json_minify("{\n  \"a\": 1\n}").unwrap(), r#"{"a":1}"#);
59    }
60
61    #[test]
62    fn json_rejects_bad_input() {
63        assert!(json_pretty("{nope}").is_err());
64        assert!(json_minify("{nope}").is_err());
65    }
66
67    #[test]
68    fn yaml_roundtrips() {
69        let out = yaml_format("a:    1\nb: 2\n").unwrap();
70        assert!(out.contains("a: 1"), "got: {out}");
71        assert!(yaml_format("a: [unclosed").is_err());
72    }
73
74    #[test]
75    fn toml_roundtrips() {
76        let out = toml_format("a=1\nb=2\n").unwrap();
77        assert!(out.contains("a = 1"), "got: {out}");
78        assert!(toml_format("= bad").is_err());
79    }
80}