about summary refs log tree commit diff
path: root/lib/generators.nix
diff options
context:
space:
mode:
Diffstat (limited to 'lib/generators.nix')
-rw-r--r--lib/generators.nix72
1 files changed, 72 insertions, 0 deletions
diff --git a/lib/generators.nix b/lib/generators.nix
new file mode 100644
index 000000000000..27d4142e8d9a
--- /dev/null
+++ b/lib/generators.nix
@@ -0,0 +1,72 @@
+/* Functions that generate widespread file
+ * formats from nix data structures.
+ *
+ * They all follow a similar interface:
+ * generator { config-attrs } data
+ *
+ * Tests can be found in ./tests.nix
+ * Documentation in the manual, #sec-generators
+ */
+with import ./trivial.nix;
+let
+  libStr = import ./strings.nix;
+  libAttr = import ./attrsets.nix;
+
+  flipMapAttrs = flip libAttr.mapAttrs;
+in
+
+rec {
+
+  /* Generates an INI-style config file from an
+   * attrset of sections to an attrset of key-value pairs.
+   *
+   * generators.toINI {} {
+   *   foo = { hi = "${pkgs.hello}"; ciao = "bar"; };
+   *   baz = { "also, integers" = 42; };
+   * }
+   *
+   *> [baz]
+   *> also, integers=42
+   *>
+   *> [foo]
+   *> ciao=bar
+   *> hi=/nix/store/y93qql1p5ggfnaqjjqhxcw0vqw95rlz0-hello-2.10
+   *
+   * The mk* configuration attributes can generically change
+   * the way sections and key-value strings are generated.
+   *
+   * For more examples see the test cases in ./tests.nix.
+   */
+  toINI = {
+    # apply transformations (e.g. escapes) to section names
+    mkSectionName ? (name: libStr.escape [ "[" "]" ] name),
+    # format a setting line from key and value
+    mkKeyValue    ? (k: v: "${libStr.escape ["="] k}=${toString v}")
+  }: attrsOfAttrs:
+    let
+        # map function to string for each key val
+        mapAttrsToStringsSep = sep: mapFn: attrs:
+          libStr.concatStringsSep sep
+            (libAttr.mapAttrsToList mapFn attrs);
+        mkLine = k: v: mkKeyValue k v + "\n";
+        mkSection = sectName: sectValues: ''
+          [${mkSectionName sectName}]
+        '' + libStr.concatStrings (libAttr.mapAttrsToList mkLine sectValues);
+    in
+      # map input to ini sections
+      mapAttrsToStringsSep "\n" mkSection attrsOfAttrs;
+
+
+  /* Generates JSON from an arbitrary (non-function) value.
+    * For more information see the documentation of the builtin.
+    */
+  toJSON = {}: builtins.toJSON;
+
+
+  /* YAML has been a strict superset of JSON since 1.2, so we
+    * use toJSON. Before it only had a few differences referring
+    * to implicit typing rules, so it should work with older
+    * parsers as well.
+    */
+  toYAML = {}@args: toJSON args;
+}