NixOS / nix

Nix, the purely functional package manager
https://nixos.org/
GNU Lesser General Public License v2.1
12.87k stars 1.52k forks source link

Literate Nix #4620

Open enderger opened 3 years ago

enderger commented 3 years ago

Is your feature request related to a problem? Please describe. Currently, I am working on creating a dotfiles repo and find it a little annoying that there is no way to make a literate Nix expression without external tools.

Describe the solution you'd like I would like to see a literate variant of Nix in the same vein as Literate Haskell. Preferably, it would incorporate a way to mark syntax blocks as other languages (to allow for proper syntax highlighting in config strings), the ability to use these documents without tangling, and official weaving and tangling tooling.

Describe alternatives you've considered I am currently considering using the Literate tool with build automation like Makefiles, however it proves cumbersome to have to write build automation for each config file.

Additional context Literate Haskell - https://wiki.haskell.org/Literate_programming Vim Example - https://wiki.haskell.org/Literate_programming/Vim

7c6f434c commented 3 years ago

Describe alternatives you've considered I am currently considering using the Literate tool with build automation like Makefiles, however it proves cumbersome to have to write build automation for each config file.

I wonder if it makes more sense to make some wrappers instead, that take the same flags as corresponding Nix commands, but tangle/weave the entire subtree then run the corresponding Nix program with the same flags.

enderger commented 3 years ago

I wonder if it makes more sense to make some wrappers instead, that take the same flags as corresponding Nix commands, but tangle/weave the entire subtree then run the corresponding Nix program with the same flags.

Unfortunately, it falls apart whenever you need to just import an expression into another.

matthewbauer commented 3 years ago

I've been able to write literate Nix with org-mode. With org-mode, you can tangle multiple files from one source file so I think the overhead is a lot less.

import-from-derivation provides a lot of usefulness for this too. For instance, you can use this Nix file as a default.nix to tangle your .org file automatically:

{ pkgs ? import (builtins.fetchTarball "channel:nixos-unstable") {} }:

import (pkgs.runCommand "README" {
  buildInputs = [ pkgs.emacs ];
} ''
  mkdir $out
  cp ${./README.org} $out/README.org
  cd $out
  emacs --batch --quick -l ob-tangle --eval "(org-babel-tangle-file \"README.org\")" > /dev/null
  # tangling README.org needs to produce a default.nix
'') { inherit pkgs; }
enderger commented 3 years ago

I've been able to write literate Nix with org-mode. With org-mode, you can tangle multiple files from one source file so I think the overhead is a lot less.

import-from-derivation provides a lot of usefulness for this too. For instance, you can use this Nix file as a default.nix to tangle your .org file automatically:

{ pkgs ? import (builtins.fetchTarball "channel:nixos-unstable") {} }:

import (pkgs.runCommand "README" {
  buildInputs = [ pkgs.emacs ];
} ''
  mkdir $out
  cp ${./README.org} $out/README.org
  cd $out
  emacs --batch --quick -l ob-tangle --eval "(org-babel-tangle-file \"README.org\")" > /dev/null
  # tangling README.org needs to produce a default.nix
'') { inherit pkgs; }

That should also work! Thanks.

stale[bot] commented 3 years ago

I marked this as stale due to inactivity. → More info