git.delta.rocks / jrsonnet / refs/commits / ddc0d176fb77

difftreelog

perf std.manifestTomlEx builtin

Yaroslav Bolyukin2022-12-03parent: #68bea05.patch.diff
in: master

5 files changed

modifiedcrates/jrsonnet-cli/src/manifest.rsdiffbeforeafterboth
--- a/crates/jrsonnet-cli/src/manifest.rs
+++ b/crates/jrsonnet-cli/src/manifest.rs
@@ -1,4 +1,4 @@
-use std::{path::PathBuf, str::FromStr};
+use std::path::PathBuf;
 
 use clap::{Parser, ValueEnum};
 use jrsonnet_evaluator::{
@@ -6,7 +6,7 @@
 	manifest::{JsonFormat, ManifestFormat, StringFormat, ToStringFormat, YamlStreamFormat},
 	State,
 };
-use jrsonnet_stdlib::YamlFormat;
+use jrsonnet_stdlib::{TomlFormat, YamlFormat};
 
 use crate::ConfigureState;
 
@@ -16,18 +16,7 @@
 	String,
 	Json,
 	Yaml,
-}
-
-impl FromStr for ManifestFormatName {
-	type Err = &'static str;
-	fn from_str(s: &str) -> std::result::Result<Self, Self::Err> {
-		Ok(match s {
-			"string" => ManifestFormatName::String,
-			"json" => ManifestFormatName::Json,
-			"yaml" => ManifestFormatName::Yaml,
-			_ => return Err("no such format"),
-		})
-	}
+	Toml,
 }
 
 #[derive(Parser)]
@@ -44,7 +33,7 @@
 	#[clap(long, short = 'y', conflicts_with = "string")]
 	yaml_stream: bool,
 	/// Number of spaces to pad output manifest with.
-	/// `0` for hard tabs, `-1` for single line output [default: 3 for json, 2 for yaml]
+	/// `0` for hard tabs, `-1` for single line output [default: 3 for json, 2 for yaml/toml]
 	#[clap(long)]
 	line_padding: Option<usize>,
 	/// Preserve order in object manifestification
@@ -72,6 +61,11 @@
 					#[cfg(feature = "exp-preserve-order")]
 					preserve_order,
 				)),
+				ManifestFormatName::Toml => Box::new(TomlFormat::cli(
+					self.line_padding.unwrap_or(2),
+					#[cfg(feature = "exp-preserve-order")]
+					preserve_order,
+				)),
 			}
 		};
 		Ok(if self.yaml_stream {
modifiedcrates/jrsonnet-stdlib/src/lib.rsdiffbeforeafterboth
--- a/crates/jrsonnet-stdlib/src/lib.rs
+++ b/crates/jrsonnet-stdlib/src/lib.rs
@@ -121,6 +121,7 @@
 		("escapeStringJson", builtin_escape_string_json::INST),
 		("manifestJsonEx", builtin_manifest_json_ex::INST),
 		("manifestYamlDoc", builtin_manifest_yaml_doc::INST),
+		("manifestTomlEx", builtin_manifest_toml_ex::INST),
 		// Parsing
 		("parseJson", builtin_parse_json::INST),
 		("parseYaml", builtin_parse_yaml::INST),
modifiedcrates/jrsonnet-stdlib/src/manifest/mod.rsdiffbeforeafterboth
--- a/crates/jrsonnet-stdlib/src/manifest/mod.rs
+++ b/crates/jrsonnet-stdlib/src/manifest/mod.rs
@@ -1,3 +1,4 @@
+mod toml;
 mod yaml;
 
 use jrsonnet_evaluator::{
@@ -5,8 +6,9 @@
 	function::builtin,
 	manifest::{escape_string_json, JsonFormat},
 	typed::Any,
-	IStr,
+	IStr, ObjValue, Val,
 };
+pub use toml::TomlFormat;
 pub use yaml::YamlFormat;
 
 #[builtin]
@@ -47,3 +49,16 @@
 		preserve_order.unwrap_or(false),
 	))
 }
+
+#[builtin]
+pub fn builtin_manifest_toml_ex(
+	value: ObjValue,
+	indent: IStr,
+	#[cfg(feature = "exp-preserve-order")] preserve_order: Option<bool>,
+) -> Result<String> {
+	Val::Obj(value).manifest(TomlFormat::std_to_toml(
+		indent.to_string(),
+		#[cfg(feature = "exp-preserve-order")]
+		preserve_order.unwrap_or(false),
+	))
+}
addedcrates/jrsonnet-stdlib/src/manifest/toml.rsdiffbeforeafterboth

no changes

modifiedcrates/jrsonnet-stdlib/src/std.jsonnetdiffbeforeafterboth
--- a/crates/jrsonnet-stdlib/src/std.jsonnet
+++ b/crates/jrsonnet-stdlib/src/std.jsonnet
@@ -100,86 +100,6 @@
 
   manifestToml(value):: std.manifestTomlEx(value, '  '),
 
-  manifestTomlEx(value, indent)::
-    local
-      escapeStringToml = std.escapeStringJson,
-      escapeKeyToml(key) =
-        local bare_allowed = std.set(std.stringChars('ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789_-'));
-        if std.setUnion(std.set(std.stringChars(key)), bare_allowed) == bare_allowed then key else escapeStringToml(key),
-      isTableArray(v) = std.isArray(v) && std.length(v) > 0 && std.foldl(function(a, b) a && std.isObject(b), v, true),
-      isSection(v) = std.isObject(v) || isTableArray(v),
-      renderValue(v, indexedPath, inline, cindent) =
-        if v == true then
-          'true'
-        else if v == false then
-          'false'
-        else if v == null then
-          error 'Tried to manifest "null" at ' + indexedPath
-        else if std.isNumber(v) then
-          '' + v
-        else if std.isString(v) then
-          escapeStringToml(v)
-        else if std.isFunction(v) then
-          error 'Tried to manifest function at ' + indexedPath
-        else if std.isArray(v) then
-          if std.length(v) == 0 then
-            '[]'
-          else
-            local range = std.range(0, std.length(v) - 1);
-            local new_indent = if inline then '' else cindent + indent;
-            local separator = if inline then ' ' else '\n';
-            local lines = ['[' + separator]
-                          + std.join([',' + separator],
-                                     [
-                                       [new_indent + renderValue(v[i], indexedPath + [i], true, '')]
-                                       for i in range
-                                     ])
-                          + [separator + (if inline then '' else cindent) + ']'];
-            std.join('', lines)
-        else if std.isObject(v) then
-          local lines = ['{ ']
-                        + std.join([', '],
-                                   [
-                                     [escapeKeyToml(k) + ' = ' + renderValue(v[k], indexedPath + [k], true, '')]
-                                     for k in std.objectFields(v)
-                                   ])
-                        + [' }'];
-          std.join('', lines),
-      renderTableInternal(v, path, indexedPath, cindent) =
-        local kvp = std.flattenArrays([
-          [cindent + escapeKeyToml(k) + ' = ' + renderValue(v[k], indexedPath + [k], false, cindent)]
-          for k in std.objectFields(v)
-          if !isSection(v[k])
-        ]);
-        local sections = [std.join('\n', kvp)] + [
-          (
-            if std.isObject(v[k]) then
-              renderTable(v[k], path + [k], indexedPath + [k], cindent)
-            else
-              renderTableArray(v[k], path + [k], indexedPath + [k], cindent)
-          )
-          for k in std.objectFields(v)
-          if isSection(v[k])
-        ];
-        std.join('\n\n', sections),
-      renderTable(v, path, indexedPath, cindent) =
-        cindent + '[' + std.join('.', std.map(escapeKeyToml, path)) + ']'
-        + (if v == {} then '' else '\n')
-        + renderTableInternal(v, path, indexedPath, cindent + indent),
-      renderTableArray(v, path, indexedPath, cindent) =
-        local range = std.range(0, std.length(v) - 1);
-        local sections = [
-          (cindent + '[[' + std.join('.', std.map(escapeKeyToml, path)) + ']]'
-           + (if v[i] == {} then '' else '\n')
-           + renderTableInternal(v[i], path, indexedPath + [i], cindent + indent))
-          for i in range
-        ];
-        std.join('\n\n', sections);
-    if std.isObject(value) then
-      renderTableInternal(value, [], [], '')
-    else
-      error 'TOML body must be an object. Got ' + std.type(value),
-
   escapeStringPython(str)::
     std.escapeStringJson(str),