pkgs-lib/formats: reimplement toml.generate with Rust (#513796)

This commit is contained in:
Matt Sturgeon
2026-05-30 02:39:17 +00:00
committed by GitHub
8 changed files with 316 additions and 3 deletions

View File

@@ -73,6 +73,7 @@
## Format generators/serializers
/pkgs/pkgs-lib @Stunkymonkey @h7x4
/pkgs/pkgs-lib/formats/json2x @Stunkymonkey @h7x4 @figsoda
# Nixpkgs build-support
/pkgs/build-support/writers @lassulus

View File

@@ -81,6 +81,8 @@ let
str
;
};
json2x = pkgs.callPackage ./formats/json2x/package.nix { };
in
optionalAttrs allowAliases aliases
// rec {
@@ -469,7 +471,7 @@ optionalAttrs allowAliases aliases
{ runCommand, remarshal }:
runCommand name
{
nativeBuildInputs = [ remarshal ];
nativeBuildInputs = [ json2x ];
value = builtins.toJSON value;
preferLocalBuild = true;
__structuredAttrs = true;
@@ -477,7 +479,7 @@ optionalAttrs allowAliases aliases
''
valuePath="$TMPDIR/value"
printf "%s" "$value" > "$valuePath"
json2toml "$valuePath" "$out"
json2x toml "$valuePath" "$out"
''
) { };

View File

@@ -0,0 +1 @@
/target

221
pkgs/pkgs-lib/formats/json2x/Cargo.lock generated Normal file
View File

@@ -0,0 +1,221 @@
# This file is automatically @generated by Cargo.
# It is not intended for manual editing.
version = 4
[[package]]
name = "anyhow"
version = "1.0.102"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "7f202df86484c868dbad7eaa557ef785d5c66295e41b460ef922eca0723b842c"
[[package]]
name = "argh"
version = "0.1.19"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "211818e820cda9ca6f167a64a5c808837366a6dfd807157c64c1304c486cd033"
dependencies = [
"argh_derive",
"argh_shared",
]
[[package]]
name = "argh_derive"
version = "0.1.19"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "c442a9d18cef5dde467405d27d461d080d68972d6d0dfd0408265b6749ec427d"
dependencies = [
"argh_shared",
"proc-macro2",
"quote",
"syn",
]
[[package]]
name = "argh_shared"
version = "0.1.19"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "e5ade012bac4db278517a0132c8c10c6427025868dca16c801087c28d5a411f1"
dependencies = [
"serde",
]
[[package]]
name = "equivalent"
version = "1.0.2"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "877a4ace8713b0bcf2a4e7eec82529c029f1d0619886d18145fea96c3ffe5c0f"
[[package]]
name = "hashbrown"
version = "0.17.1"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "ed5909b6e89a2db4456e54cd5f673791d7eca6732202bbf2a9cc504fe2f9b84a"
[[package]]
name = "indexmap"
version = "2.14.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "d466e9454f08e4a911e14806c24e16fba1b4c121d1ea474396f396069cf949d9"
dependencies = [
"equivalent",
"hashbrown",
]
[[package]]
name = "itoa"
version = "1.0.18"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "8f42a60cbdf9a97f5d2305f08a87dc4e09308d1276d28c869c684d7777685682"
[[package]]
name = "json2x"
version = "0.1.0"
dependencies = [
"anyhow",
"argh",
"serde_json",
"toml",
]
[[package]]
name = "memchr"
version = "2.8.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "f8ca58f447f06ed17d5fc4043ce1b10dd205e060fb3ce5b979b8ed8e59ff3f79"
[[package]]
name = "proc-macro2"
version = "1.0.106"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "8fd00f0bb2e90d81d1044c2b32617f68fcb9fa3bb7640c23e9c748e53fb30934"
dependencies = [
"unicode-ident",
]
[[package]]
name = "quote"
version = "1.0.45"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "41f2619966050689382d2b44f664f4bc593e129785a36d6ee376ddf37259b924"
dependencies = [
"proc-macro2",
]
[[package]]
name = "serde"
version = "1.0.228"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "9a8e94ea7f378bd32cbbd37198a4a91436180c5bb472411e48b5ec2e2124ae9e"
dependencies = [
"serde_core",
"serde_derive",
]
[[package]]
name = "serde_core"
version = "1.0.228"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "41d385c7d4ca58e59fc732af25c3983b67ac852c1a25000afe1175de458b67ad"
dependencies = [
"serde_derive",
]
[[package]]
name = "serde_derive"
version = "1.0.228"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "d540f220d3187173da220f885ab66608367b6574e925011a9353e4badda91d79"
dependencies = [
"proc-macro2",
"quote",
"syn",
]
[[package]]
name = "serde_json"
version = "1.0.149"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "83fc039473c5595ace860d8c4fafa220ff474b3fc6bfdb4293327f1a37e94d86"
dependencies = [
"itoa",
"memchr",
"serde",
"serde_core",
"zmij",
]
[[package]]
name = "serde_spanned"
version = "1.1.1"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "6662b5879511e06e8999a8a235d848113e942c9124f211511b16466ee2995f26"
dependencies = [
"serde_core",
]
[[package]]
name = "syn"
version = "2.0.117"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "e665b8803e7b1d2a727f4023456bbbbe74da67099c585258af0ad9c5013b9b99"
dependencies = [
"proc-macro2",
"quote",
"unicode-ident",
]
[[package]]
name = "toml"
version = "1.1.2+spec-1.1.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "81f3d15e84cbcd896376e6730314d59fb5a87f31e4b038454184435cd57defee"
dependencies = [
"indexmap",
"serde_core",
"serde_spanned",
"toml_datetime",
"toml_parser",
"toml_writer",
]
[[package]]
name = "toml_datetime"
version = "1.1.1+spec-1.1.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "3165f65f62e28e0115a00b2ebdd37eb6f3b641855f9d636d3cd4103767159ad7"
dependencies = [
"serde_core",
]
[[package]]
name = "toml_parser"
version = "1.1.2+spec-1.1.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "a2abe9b86193656635d2411dc43050282ca48aa31c2451210f4202550afb7526"
dependencies = [
"winnow",
]
[[package]]
name = "toml_writer"
version = "1.1.1+spec-1.1.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "756daf9b1013ebe47a8776667b466417e2d4c5679d441c26230efd9ef78692db"
[[package]]
name = "unicode-ident"
version = "1.0.24"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "e6e4313cd5fcd3dad5cafa179702e2b244f760991f45397d14d4ebf38247da75"
[[package]]
name = "winnow"
version = "1.0.3"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "0592e1c9d151f854e6fd382574c3a0855250e1d9b2f99d9281c6e6391af352f1"
[[package]]
name = "zmij"
version = "1.0.21"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "b8848ee67ecc8aedbaf3e4122217aff892639231befc6a1b58d29fff4c2cabaa"

View File

@@ -0,0 +1,20 @@
[package]
name = "json2x"
version = "0.1.0"
edition = "2024"
publish = false
[dependencies]
anyhow = "1.0.102"
argh = "0.1.19"
serde_json = "1.0.149"
[dependencies.toml]
version = "1.1.2"
default-features = false
features = ["display", "serde", "std"]
[profile.release]
lto = true
panic = "abort"
codegen-units = 1

View File

@@ -0,0 +1,19 @@
{
lib,
rustPlatform,
}:
rustPlatform.buildRustPackage {
pname = "json2x";
version = "0.1.0";
__structuredAttrs = true;
src = lib.sourceByRegex ./. [
"^src(/.*)?$"
''^Cargo\.(lock|toml)$''
];
cargoLock = {
lockFile = ./Cargo.lock;
};
}

View File

@@ -0,0 +1,49 @@
use std::{
fs::{File, read_to_string},
io::Write,
path::PathBuf,
};
use anyhow::Context;
use argh::{FromArgValue, FromArgs};
/// Convert a JSON file to another format
#[derive(FromArgs)]
struct Args {
/// format of the output file, possible values: toml
#[argh(positional)]
format: Format,
/// path to the input file
#[argh(positional)]
input: PathBuf,
/// path to the output file
#[argh(positional)]
output: PathBuf,
}
#[derive(FromArgValue)]
enum Format {
Toml,
}
fn main() -> anyhow::Result<()> {
let args: Args = argh::from_env();
let input = read_to_string(&args.input)
.with_context(|| format!("failed to read {}", args.input.display()))?;
let input: serde_json::Value = serde_json::from_str(&input)
.with_context(|| format!("failed to parse {}", args.input.display()))?;
let mut output = File::create(&args.output)
.with_context(|| format!("failed to create {}", args.output.display()))?;
match args.format {
Format::Toml => {
let content = toml::to_string(&input).context("failed to serialize value to toml")?;
output
.write_all(content.as_bytes())
.with_context(|| format!("failed to write to {}", args.output.display()))?;
}
}
Ok(())
}

View File

@@ -723,7 +723,7 @@ runBuildTests {
];
};
expected = ''
language-server = ["bash-language-server", {except-features = ["diagnostics"], name = "typescript-language-server"}]
language-server = ["bash-language-server", { except-features = ["diagnostics"], name = "typescript-language-server" }]
'';
};