Our Roadmap for Nix
tweag.io
tweag.io
I wanted to give guix a shot does anybody know if its any better ignoring their stance on non-free software as I think you can work around it.
Hmm I guess the nix approach would be "convention as shared configuration"
The primary issue for me has been that Nix is a very deep rabbit hole. You can spend enormous amounts of time on making your configuration more functional and declarative. Pretty much like you can spend enormous amounts of time on customizing an Emacs configuration. It's hard to strike a balance. And outside declaratively defined infrastructure (servers), it's probably not really worth it. I could almost fully reproduce my NixOS system (there is always some mutable state left) with a single command. But takes many months of effort to get to that point. On the other hand, I can set up a fresh macOS or Fedora Silverblue systems with all my customizations in 1 or 2 hours and have to do that maybe once of twice a year? So, ¯\_(ツ)_/¯.
I think the balance is different when you manage a lot of servers and most servers can be defined as a function with a small number of varying parameters.
The other part of the rabbit hole is that software breaks frequently in Nix. Upstreams do not really develop things under the assumption of a non-FHS, immutable system. So, you were going to work on something, but before you know it is 30 minutes later because you ended up fixing some package you need and that broke. Similarly, you'll end up packaging a lot of stuff and spending quite some time making it fit the Nix mold (looking at you Python packages that mutate in-place, sigh).
I love Nix as a principle -- it's declarative, immutable, pure, reproducible. But in practice, you can reap many of the same benefits from impure, inferior alternatives, with far less work. Yes, Docker is an ugly duck compared to Nix, but it brings 90% of the reproducibility benefits and probably everyone on your team can be up and running in hours. Rust's cargo doesn't allow you to specify every non-Rust dependency exactly, but with a Cargo.lock file you can make most of your build reproducible. NixOS is a clean, immutable, declarative system, but other systems offer a subset of its features, such as atomic upgrades/rollbacks, immutable root, and isolated applications (e.g. Fedora SilverBlue + Flatpaks, Fedora IoT, macOS). These alternatives are far more familiar and easier to work with. You can get most (but not all) of the benefits of NixOS with far less work.
Worse is better.
I see some younger folks really investing time in it and it worries me. Sometimes smart people fall under this fallacy of "you have to be smart to learn this so it must be good because it's hard" when really it looks more like quicksand than asphalt. Quicksand is hard to get out of, but there's still no reward for falling in.
I don’t think learning nix from its internals is worth it, especially not for beginners.
Nitpick: what you're calling 'Nix internals' are actually Nixpkgs internals.
FWIW, I think that to some extent this is just the way you have to go when you're trying to quickly take up a new (to you) configuration language for practical purposes.
I've somewhat recently started putting together some simple CI/CD pipelines at work with a tool called Dagger, which is a container image builder-and-runner based on BuildKit and the CUE language.
When I first started learning Nix years ago, I had a lot of packaging trouble with some quirky software that wasn't yet packaged for Nix, and I only ended up getting unstuck by asking for help on IRC. One generous person was hitting me with incredibly helpful links to examples from Nixpkgs and the documentation left and right, and I was astonished with their fluency. I asked them how they knew all this, and they basically said:
> Idk, one day I just sat down and started to read through some of the Nixpkgs codebase, and now I `grep -R` through it a lot to look for examples.
At the time it sounded adventurous and crazy to me, as I was pretty intimidated by the prospect. Eventually that became one of my standard tools: I treat the Nixpkgs repo as another source of documentation.
Fast forward to today and my Dagger implementation efforts, and things got immensely easier for me the moment I started treating Dagger like Nix. I cloned the upstream Dagger repository and started searching through the unit tests with `rg`, and all the answers to my questions about what functionality Dagger exposes via CUE modules were right there. Tons of the guesswork disappeared, even though I don't yet have a great grasp of the CUE language.
In some ways, the Dagger case is harder, though. In the name of simplicity and partly for other language design reasons, CUE is emphatically not Turing-complete. This is interesting and attractive in some ways, but one of the consequences is that sometimes you hit bottom in the CUE libraries to find some compiler directive that links in functionality which had to be implemented in a Real™ programming language (in this case, Go). So to really understand, e.g., the custom data types Dagger uses for secrets, you have to go read code in another language.
By contrast, in the Nix case, the language is powerful enough that you can learn everything you need to for even very advanced Nix usage only by reading Nixlang, either in Nixpkgs or in other examples. You never actually have to dive into true 'Nix internals' (the Nix repo, which is C++ code) to figure out how something in a Nix example is achieved. With a more restricted DSL, you sometimes do.
Maybe one valuable 'missing manual' would be something like 'How to read Nixpkgs'! It's such a rich source of examples. I think making earlier reference to it could help a lot of people make faster progress and feel more effective when learning Nix.
I feel like so many of the problem I encounter as a new nix user have been neatly solved already and there are probably tons of great examples in nixpkgs, but I have no clue where to look, or even what to grep for.
It would be super helpful if there were a resource with examples of common problems and how they're solved in the real world. For example, say you're packaging something whose unit tests hit the network. There could be a link to a package definition in nixpkgs that overrides the check phase to disable the problematic test.
- disabling the code that hits the network, whether by patching or by configuration ("--disable-downloads" or anything similar)
- or emulating it; e.g. if the script downloads a file, we can `fetchurl` it and move the downloaded file to its expected place. 9Of course, it works when the script does not override the downloaded file; otherwise, go to the previous option)
Two examples came to my mind:
- Arcan vendoring required patching its cmake scripts, because cmake does not honor the cache and tries to download things anyway:
https://github.com/NixOS/nixpkgs/blob/901978e1fd43753d56299a...
- cardboard didn't require it because meson honors the cache (and Nixpkgs configures Meson to not download anything):
https://github.com/NixOS/nixpkgs/blob/901978e1fd43753d56299a...
Lazy and pure and duck-typed and broken ass stack traces? Fuck that. Fuck that in particular.
Eelco fucked up. Badly. nixpkgs uses Haskell type signatures as comments in the core ‘lib’s, because duck-typed pure lazy functional is fucking insane.
At my work those “O RLY” meme book covers are in vogue this week, and my last one was “Nix Haskell Overlays for Fun and Murder: Homicidal Ideation for the Working Hacker”.
It was my job to get Clash (the VHDL/Verilog synthesis tool on Haskell) building under Bazel via Tweag’s rules_haskell and playing nice with all our other Haskell shit. That’s 14 hours straight I’m never getting back.
But… because it’s Nix I never have to do that again. Even if I upgrade everything else I can keep nixpkgs at that version in my flake.lock and that will always work forever. So I’m cool with it.
good god pls share the link
This is the killer feature for me. My use-case for Nix is vastly different from yours, as I use it for centralized declarative configuration through NixOS, but I have an immense sense of satisfaction knowing that hell can freeze over but I'm still only a single command away from my exact setup running on (almost) any machine on the planet.
This might not matter much for most people, but making my machine work for me is something that took me years, and I can sleep well knowing that it's finally safe under Nix vs. multiple different configuration files for multiple different programs scattered across my filesystem.
Making NVIDIA drivers work with either Xorg on someone’s desk or CuDNN on the GPU boxes with like two friggin lines in the NixOS stuff is like, doing drugs or something in terms of sheer feeling great after years of chasing that shit all around Ubuntu’s broken-ass standard of living.
The bad error messages, the useless stack traces, and the overall un-debuggability of Nix are not just minor issues. These are at the core of the steep learning curve of Nix. These are also the reason why with Nix you are often 'dead in the water' and don't know how to fix a problem, and end up googling for hours or asking somebody else who knows more about Nix.
And these issues cannot be fixed by having "better docs" or a better tutorial.
If somebody were to rewrite the language today then my suggestion would be to make it statically typed, like Haskell. I would probably also make it strict, with optional laziness, although that's less important imo. And providing good error messages and good debuggability should be explicit design goals.
Making it statically typed would necessitate a different overall design, since many of the dynamic tricks would not be possible any more, but I suspect that you would end up with a better overall design in the end.
Nix (the language) stomps like JSON or YAML for writing config files, it’s actually not bad at that, but it’s a disaster in its contemporary role.
https://researchr.org/publication/Dolstra2006
More recently there is an attempt to run Nickel as a successor for Nix: https://www.tweag.io/blog/2020-10-22-nickel-open-sourcing/
> Worse is better.
There are some potential alternatives out there that seem inspired by Nix but which are less strict. I think a system that offers and manages Nix's purity but doesn't require it could end up the final winner some day. Shea Levy had some ideas for eventually achieving this in Nix that he called 'Nomia' (probably riffing on the name of Sander van der Burg's Dysnomia, I'd guess), but his life circumstances changed before the project really materialized. But Nix still could be the place where that is first achieved.
Meanwhile new container image-building DSLs like Dagger¹ and Bass² look a lot like a Nix which is impure by default, and bash builders are replaced with BuildKit directives. And there's Denxi³, which looks more like a Nix that lets you reduce its purity when you want to.
For now, though, the Nix ecosystem is still vastly more capable than these alternatives because of all the incredible work that Nixpkgs represents. Nix we know it today could still end up the concrete basis for what succeeds it, and not just an inspiration.
Incidentally, I treat both my Emacs config and my NixOS and home-manager configurations as Igors. They are never really finished. In this sense, the "many months of effort to get to that point" does not matter. Also, with NixOS I feel I can be bolder than with other distros, knowing with way more accuracy what is breaking my configuration.
> Yes, Docker is an ugly duck compared to Nix, but it brings 90% of the reproducibility benefits and probably everyone on your team can be up and running in hours.
The Docker replit was using before Nix was going hopelessly "uglier": https://blog.replit.com/nix
Also, what Cargo and NPM and `<insert lang here>` lockfile system do for each lang, Nix does in a more general package management level.
The big different is the language and I think Nix wins here by a mile. Doing everything with Scheme just leads to layers of macro spaghetti that I really did not enjoy to dig through. Error messages that tell you absolutely nothing about what went wrong were pretty common. Nix has those too, but less frequently. Also with Nix you just use regular shell scripts snippets for the building the packages, Guix wants you to do it all in Scheme. Package selection on NixOS is much bigger.
Another big thing, Nix has Flakes, which make it trivially to turn all your Git repositories into Nix packages. Your Git repository becomes essentially a first class citizen in the package manager, making it completely trivial to run different versions of the same software. Guix has none of that, they still treat packages as a separate thing from the software itself and trying to add third party packages involves quite a bit of overhead. Easily up or downgrading individual software isn't possible as far as I can tell, you have have to roll back the complete Guix system to do so.
Basically, after switching from Guix to NixOS, I can't say I missed anything. NixOS just felt like a more polished and feature rich version of what Guix was doing, which given that Guix is basically a NIH version of Nix, is understandable.
On the flip side, it’s a real language, well understood, with a real specification, working tooling, and community support outside Guix (or in the case of Nix, outside the package manager).
As someone who gave up NixOS exactly because of the incomprehensibleness of the Nix language, I know what I would choose.
There’s no doubt at all.
For most common uses you barely even have to care about the language, as it's just some JSON-like data with shell scripts in between that do the actual work.
Incidentally, this is one of the things that some of the people involved with the blog post in the OP have set out to fix. A few years ago, Théophane (author of the blog post) started an experiment to add gradual typing to Nix, which eventually became the start of Nickel: https://github.com/tweag/nickel
Today, Nickel development continues at Tweag, but now they have someone else, Yann Hamdaoui, driving the implementation forward. (I assume because he's a domain expert in programming languages.) Producing helpful error messages is one of the major goals of Nickel, as a potential successor language to Nix. All of the language design decisions are documented as GitHub issues on the repo, so if the technical side of this kind of problem is interesting to you, you may enjoy browsing that.
It appears that Nickel is very close to a usable state for early experimentation. You might be interested in cloning the repo and messing around with it!
The nix language is pretty nice on the other hand. The only thing I’m missing is a language server protocol thing so I can go to definition
Ironically, this has been posted on a popular site written in a dialect of scheme:
Don't think the parent was saying that it's impossible to write a good program in scheme/lisp, more that scheme as user interface for a software system is a hard sell... which seems anecdotally true.
I have no doubt that this is true, but I still feel dumb about it. I run a Plex server (among a few other workloads) on a NixOS box, and just figuring out how to update the Plex binaries off of the official master branch was a multi-hour back-and-forth endeavor between StackOverflow suggestions and compiler errors.
I really do love Nix though. And once I got it working I felt a LITTLE bit smarter, AND it's worked flawlessly for months.
Flakes aren’t “experimental”. “Experimental” is what happens to your sanity without them.
Okay, I like flakes, I use flakes, I enable flakes without much worry. But. They literally are an experimental feature, and they are still enabled by setting "experimental-features = nix-command flakes" in nix's config.
Outside of some (hypothetical to me) edge cases, not using them is masochism.
Flakes have a standard library (“flake-utils”) and and a pimped out version (“flake-utils-plus”).
Making it a weird gymnastics trick for a novice user to even access them is the kind of shit GHC devs say, “no, that’s too user-hostile even for us”.
Use flakes.
Sounds like the authentic 90s linux package experience! (except with 's/StackOverflow/mailing list/')
and then I added this blurb to my Nix config:
nixpkgs.config = { allowUnfree = true; packageOverrides = pkgs: { unstable = import <nixos-unstable> { config = config.nixpkgs.config; }; }; };
nix build "git+file://$(pwd)?submodules=1"
But it will work with submodules.Another mild annoyance related to this is that Flake inputs can't be expressions, this can make it a rather difficult to fetch dependencies that aren't packaged in a way understood by the existing fetch methods.
Which reveals another annoying thing about using flakes for development. It copies every time you build something the whole darn project into the Nix store. Fine when you have a small project, but with large projects this becomes a significant overhead.
Isn't copying the repo to a read only location just inherent to the problem of reproducibility?
In Nix you can get that via 'nix develop', which gives you a shell with access to the individual build phases and with a bit of tweaking, allows you to run them from your source directory without copying the source around first (see 'declare -f genericBuild').
nix develop .
All the build phases are available as shell functions or variables (unpackPhase, patchPhase, configurePhase, buildPhase, ...). The phases depend on each other, so if you want to skip a phase some additional tweaking or setting of environment variables will be necessary. The "genericBuild" function is the top level entry point for a normal build, the source can be viewed via: declare -f genericBuild
and should give a bit of an idea what Nix is doing.It's one where the community is pretty clear don't use nix-env etc. but the tutorials only explain nix-env, with the only details of the new commands being the CLI reference manual which doesn't cover workflows.
For reference documentation, there's "experimental commands" in the manual https://nixos.org/manual/nix/stable/command-ref/experimental...
If people aren't supposed to use nix-env, why don't nix put a huge deprecated notice on every invocation and delete the nix-env command itself from nix?
- nix-env -i and nix-env -u will almost certainly eventually do the wrong thing for you if you use them enough (nix-env -iA is ok): https://ianthehenry.com/posts/how-to-learn-nix/ambiguous-pac...
- It's not reproducible as it depends on the state of your nix-channel setup at that time. How much of a problem this is depends on your use case. nix-as-homebrew-replacemnt or nix-as-shared-package-list-across-osx-and-linux users are probably fine with this, as what these users care about is more portability than reproducibility, but nix-as-predictable-dev-environment types will be let down by it.
I think the fact that the latter affects different users differently and that the new flake world doesn't offer a "modify your global environment without the tool taking over" option (expecting you to use nixOS or nix-darwin instead) has meant that there's not enough motivation to agree on a replacement that nix-env could tell you to use instead.
I guess the eventual replacement will be "nix profile", but while you'll find at least some documentation on "nix develop" and "nix flake", I had to look in the CLI tool docs for this one, which makes me suspect it's even less final than the other two
So instead the community will tell you to avoid nix-env, but there's no agreement to have the tool or docs tell you that.
Maybe I'm holding it wrong, but I almost never get useful error messages from Nix (NixOS and NixOps). Almost every error is deep within some module with no trace to the option I set. Just nix barfing its 300-line eval traceback where my own code doesn't even appear.
Fix the fucking “—show-trace” thing folks. Seriously.
IIRC debugger comes with nix 2.9 and nixpkgs for 22.05 still has 2.8.x.
Of course running with the debugger flag resulted in an unintelligible error message and no debugger.
buildInputs = [ nixpkgs.gcc ];
but it complains that nixpkgs.gcc does not exist. There's nothing helpful. I remember fixing this issue a month ago, and I have no recollection on how I did it. buildInputs = [ nixpkgs.legacyPackages."x64_64-linux".gcc ];
In practice, it usually looks something like this: let
system = "x86_64-linux";
pkgs = nixpkgs.legacyPackages.${system};
in stdenv.mkDerivation {
...
buildInputs = [ pkgs.gcc ];
...
}To correct your coffee snippet: nativeBuildInputs = [ pkgs.gcc ];
I strongly encourage the Nix community to embrace a mainstream Q&A platform like StackOverflow or GitHub Issues.
Nix is “weird” enough for beginners already, the kind of janky interface and uneven moderation/quality on discourse is IMHO self-defeating for Nix.
You can do this up top by hand, e.g. P = inputs.nixpkgs { inherit system; }, but more commonly you would use a library like ‘flake-utils’ or ‘flake-utils-plus’ to issue system configuration for all supported packages to all your packages/derivations/devShells.
I have this or that nitpick with FL and FLP but overall it’s very solid stuff. FLP is a little more “magical”, and that’s not always the best starting out, but you really can’t go wrong with either.
It also doesn't require the definition of a package if all you want is an environment to hack on the code in a git repo. People use `manifest.scm` or `guix.scm` for these purposes.
Guix System services are in fact all built together, but upgrading individual software or services does not require "roll[ing] back the complete Guix system ".
(I want to point out that describing Guix as "a NIH version of Nix" is a symptom of the attitudes that made me almost completely retreat from discussions of software online. It's so grating to deal with dismissive attitudes like that again and again. Sucks all the fun out of hacking.)
https://guix.gnu.org/manual/devel/en/html_node/Channels.html
I guess it serves some of the same purposes as Flakes, and it comes with other bells and whistles such as authentication (which I think is kinda important!).
For the rest, your description of Guix is largely incorrect ("has none of that", "you have to roll back the complete Guix system", etc.), but as a Guix hacker I'd be interested in better understanding your experience and perceptions if you'd like to get in touch with us on the mailing lists!
I'm by no means a good schemer, but I'd still take scheme over shell every time. Shell tends to devolve into something completely unreadable with even moderate complexity while scheme can make even the most complex logic nice to work with.
> Guix has none of that, they still treat packages as a separate thing from the software itself
I'm not quite sure what you mean with that, but it's sure possible (and easy) to just define a guix repo that points to all your projects repositories and make them available through the guix package manager. Guix repos are just git repos with a few lines of metadata attached.
> Easily up or downgrading individual software isn't possible as far as I can tell, you have have to roll back the complete Guix system to do so.
It's very easy actually. You declare a package definition as an inferior to a package and can pin that definition to whatever version, commit hash, tag, you want. You basically say "I want the package declared as name X, but I want it while the guix repo is at point Y. That way, the package manager knows what dependencies the package has and provide those with the right versions as well.
> NixOS just felt like a more polished and feature rich version of what Guix was doing, which given that Guix is basically a NIH version of Nix, is understandable.
On the contrary, guix is more like a more polished and dedicated version of nix. Nix's solution to hard-to-package packages is "We take everything that's needed to build this thing and freeze it in the repository" while guix will not accept anything that doesn't build completly from scratch and can thus be distributed as optional source code. The difference is very important because it allows for better packaging and more flexible versioning of the packages. Using guix, you will never run into a situation where the solution has you staring down at a binary blob and questioning your life choices.
Perfect description.
I don't get why it's necessary or unfortunately why it is so complicated... Anything that can be done in nix can be done in a tenth the time by any employee in a more commonly used technology. In industry, this is a very bad thing in my opinion
But Nix or something like it is going to take over the world.
Dynamic linking by default is absurdly stupid and mostly motivated by GNU politics. It’s a terrible problem. Many (most?) of the users of Docker don’t even realize that this is the problem Docker is solving for them. But they know they have a terrible problem and Docker helps a lot.
Nix is Docker on steroids. It’s Docker that got bitten by a radioactive spider.
Linux namespaces and cgroups and BSD jails have been around. Docker made it Just Work.
When someone does that for Nix, which is basically Docker done by computer scientists, it’s game over for anything else.
Nix is a souped up package manager, Docker is a container runtime.
Nix depends on packages existing in /nix Docker chroots into a "folder" and runs a command(+many more things).
Lets not mix technologies up for the readers too much.
People use Docker for a lot of reasons, but mostly? Same Dockerfile, same outcome, mostly every time. No one is moving /usr/lib/x86_64 around under you. It’s a real sea change, on the order of revision control: we hadn’t even realized that we were living with constant low-level anxiety that someone was going to break our computing environment at any moment. “sudo apt upgrade —whatever”, eh, maybe next week, we’ve got a release coming up.
Calling Nix a souped up package manager is like technically correct maybe?
It’s ‘git reset —hard HEAD^’ for your whole computer or fleet of computers. It’s utterly fearless experimentation, it’s low/zero runtime cost isolation and reproducibility.
It’s early days ‘git’ for systems: pain in the ass to learn and use, frequently and credibly accused of being too hard for mortals, but profoundly game changing.
Whether Nix per se remains the plumbing, someone is going to do good porcelain and end DevOps as a specialization, along with Docker and Canonical and mandatory glibc nonsense and a thousand other things that have overstayed their welcome. Disks are big now, we can have a big directory full of hashes. We can afford the good life.
It’s going to be a big deal.
I use it as a stable base system, but when I need to do something that I'm unable to do with Nix I still drop into a $DISTRO container and do my work there where everything is stateful and "disgusting".
Having worked with DevOps for awhile I can happily tell you that we don't run around building Docker containers all days, at least in my team the developers do so. We provide them with a base to build upon, provide CI and stateful services like databases and storage.
I spend an awful lot of time writing Terraform and Helm charts though, since things needs to run somewhere.
But yes, the immutable nature of Nix is great. Nix was VERY helpful for me when I switched GPU's from NVIDIA to AMD on my desktop, no screen? Reboot, reconfigure, retry.
But yes, I agree. Something that resembles Nix will take over the computing world, as someone said somewhere in the comments of this post. The great thing about Nix is that when you fix something it stays fixed. Even if it was a PITA to get there.
I used the exact same words “things stay fixed” elsewhere in the thread. Which is big psychologically. I’ll do some really difficult or even painful things in good humor if I get a lasting benefit. But if someone or something is just going to yank the rug underneath me next month? Fuck it, hack up some doofy shell script and call it a day.
Nix aligns the incentives on getting things right. I’m happy to learn the arcana of some weird corner case of some tool or service if I can apply that in a way that is permanent.
Now we just need someone to unfuck the UX nightmare :P
It is the most sophisticated programming language/system for software packaging on the market today.
We use it for all our reproducible software development environments. All of our project templates. And all of our employees are issued NixOS configurations so everybody on the team has the same NixOS, the same Nix package overlay... Etc. This level of consistency ensures that we get a level of reproducibility from hardware to OS to user profile to development environment to CI/CD that just doesn't exist anywhere else atm.
It's not entirely perfect but that's not really Nix's fault. It's actually the fault of the rest of the software industry that persists with bad tech. All of Nix's complexity stems from having to package everybody else's mess. Anyway one day I hope the CI/CD systems in the world will just provide Nix jobs directly instead of proxying through a docker container image that I have to setup atm.
It seems to me that people who go through the agony and ecstasy of getting it set up do so because the difficulty of the domain is high and the headcount is low: you need leverage in that setting.
Can you share anything about what motivated your group to get it dialed in?
So it was only natural to fully dog food Nix. We also introduced it to clients during our computer vision machine learning consulting work. It was the only way to get reproducible projects involving a complex set of Python dependencies, Tensorflow, CUDNN, CUDA, Nvidia libraries (there is a very strict set of requirements going all the way to hardware). I actually first tried doing it with Ubuntu and apt, it did not work. Setting up your own nixpkgs overlay is a must in these scenarios.
It is definitely something that is easier to fully dial in when you start from scratch. It's a comprehensive system so it will take time for adoption. I always recommend starting with it as a development environment tool first, then consider automating your OS conf or user profile or VMs... etc.
Yes ML workloads is particularly complex, because they have both batch oriented data flows (training), and service oriented data flows (inference). There aren't many systems that can adequately express both.
Uhm, no? Dockerfile has tons of side effects:
- doing `apt-get update -y`? On some machines it will run, on others it won't be due to caching. - Using `FROM` that isn't locked to sha256? Well, sometimes you will get version 1.2.3 sometimes you will get 1.2.5. Sometimes a new one will get tagged with the same tag. - It literally has network access during the build, unless you include a hash of what you're downloading, there is zero guarantee it will be the same download.
I think the majority of leaf containers rarely get the same result with the same Dockerfile. The only thing that is guaranteed with docker is that the same image will be the same image, but ensuring that different machines pull the same version of an image is another story.
Modulus the absurdly high barriers to entry, Nix is trivially better for this purpose.
Learning Nix well from the Internet is a horror film. But… once you do it’s shockingly, actually worth it.
Getting anything complicated working/building under Nix is a PITA, the payoff is that when you fix broken things, they stay fixed.
Nix has been great but I've run up against a few thorny edges. Luckily I've sent out patches for them; long love OSS :)
As with FP, eventually, practicality beats purity I guess.
Until you can take enough advantage of purity that it's practicality is higher.
We’ve got a very nice setup that deeply integrates Nix/NixOS/Bazel (working name “straylight” for the Gibson fans) that builds most major languages well and rounds off the (very) rough corners. I’m dying to open source it but it takes time to detangle that kind of thing from your proprietary stuff. I paid in blood to know Nix inside out and I don’t want any more people to do that than already have. We use Tweag’s shit for some of the Haskell stuff.
Until then: if you’re ready to pay the price of learning this shit: you’ll get a favorable exchange rate by reading the source of nixpkgs. The docs/blogs are just usually wrong. There are exceptions (Xe is a baller), but mostly you’re flipping a coin whether or not an online resource will move you forwards or backwards.
Edit: Flakes aren’t an experimental new feature. They are a desperately needed fix to a badly broken status quo. Do not pass go, go directly to flakes.
https://nixos.wiki/wiki/Flakes tells me to enable Flakes by adding “flakes” to the config option named “experimental-features”...
Exhibit #902353 in “Why Everything About Nix on The Internet is Wrong”.
Haskell used to have a semi-official motto: “Avoid success at all costs”. I think they were joking.
Docs/UX that bad makes one wonder if the Nix people took that to heart. Flakes being some weird shoulder-surgery to even turn on? Why don’t we save time and just kick the ball into our own goal over and over.
Le sigh.
I think we can wait a few more months until they become stable enough.
Perhaps for more casual users it’s still a bad default? Even that doesn’t tie out with my personal experience.
A year ago flakes were already default amongst the serious pros, now if I don’t see a flake.nix I assume I stumbled into the old repo.
So in practice I’m eating the cost of “installing” it the first time I use it, which is subsequently amortized across all the other times I use it?
And if I’m really worried about this, my flake hits a default.nix in a directory that can also have a shell.nix I’m it so I can get around this?
I think Einstein once said: “However great your troubles with mathematics are: be of good cheer. I assure you mine are far greater.”
Nix isn’t relativity and I’m no Einstein, but if you work in Nix world and that issue even rises to your notice? Let’s trade jobs because I fucking wish I had Nix problems like that.
My assumption is that bazel is running in an environment created by nix, so I wonder what you mean by 'deeply integrated'.
When I was at FB there were dozens if not hundreds of serious hackers working on this sort of thing, and they were fucking good at their jobs, but technology usually moves forward with time and this setup smokes where FB was at in 2018. I don’t know what they’re up to now, I bet it’s good.
I want to build my own company, but I want it to have this kind of tooling, that I don’t fully understand yet.
Sounds really interesting, would love to see it used more.
As for getting the big company job, it’s a weird time over like the last two months and the next two months, but this will soon pass.
Everyone hates leetcode interviews. I hated being interviewed in that format, and I hated interviewing in that format. It is what it is. It’s a test like the SAT or LSAT or GMAT or anything, arguably not as hard. It’s basically nothing to do with the job at the lower seniorities. I think people would be less psyched out about it if they viewed it the same as cramming for any other test. A high score on the LSAT doesn’t make you a good lawyer, it’s a loose proxy metric at best, and you game it by studying.
By virtue of a) hanging out on HN and b) hanging out in a thread about Nix you’re clearly curious and paying attention, so go get that marquee job, and take the experience with you when you start your venture! I’ll be rooting for your success!
I take it you have departed quite a bit from https://github.com/tweag/rules_nixpkgs ? Are you generating BUILD.bazel files for nixpkgs, or are you doing that by hand?
But when you widen that scope to incorporate the rest of nix's warts, I'm not sure whether the project carries the requisite momentum to become a ubiquitous tool. I hope it does! The project has lofty goals and it really deserves a layer of porcelain to soften its usability and bring its benefits to more developers, because the actual, pragmatic results it delivers border on magic sometimes, and I wish more people were able to experience it. I don't blame people for avoiding that ramp-up time investement. I tried, gave up for many years, and only in the past six months or so devoted enough time to use it proficiently without training wheels. Not everyone has that luxury, nor should we in the nix community expect people to pay down enormous initial learning debt.
I began freelance consulting at the start of the year, and interesingly, more than one of my engagements turned into "let's solve this with nix", which is both surprising and encouraging. If the nix community can trim down the harsh thorns that encircle the language and tools (and provide rock solid learning materials), there's an actual chance that nix could really bloom in the near future.
IMHO Nix is relatively easy if your usecase doesn't involve unpackaged artifacts that require heavy patching to fit them into Nix.
For example, I think it's one of the best distros to run a common Linux desktop setup because you can upgrade without fear and you can test new things without adding clutter.
The biggest hurdle is documentation. Writing documentation is not as sexy as implementing new features, but that's the biggest area to improve. https://nixos.wiki has recently documented many areas that lacked sufficient coverage, but there's a ton more needed.
You can use Fedora Silverblue, which also offers atomic upgrades and rollbacks, offers support for regular RPMs as an escape hatch. It provides meaningful desktop security (verified secure boot, kernel lockdown mode, SELinux, some application sandboxing in Flatpaks). But you don't have to learn a functional language and ecosystem that is completely foreign to most people.
Oh, and Steam doesn't break all the time :).
I think Nix is great, but I wouldn't recommend most desktop users to use NixOS on the desktop, unless you are willing to invest a lot of time.
The beauty of Nix with Flakes is not just upgrades and rollbacks, but that it can be completely stateless. You can just run software directly from the Git repository:
nix run github:JUser/your_app
And if you want an old or newer version, just go: nix run github:JUser/your_app?rev=01f352202ad
You can even override dependencies if you like: nix run --override-input somlib git+file:///yourlocalfork github:JUser/your_app
There isn't a whole lot of software that has turned their Git repository into a Flake yet (i.e. added a flake.nix), so that benefit is a bit theoretical for the average user, but the potential to completely reshaping the Free Software landscape is certainly there, as Nix finally allows upstream to become a first class citizen in the distributions packaging system.As long as the project developers are not going to use Nix themselves, there are going to be a lot of unmaintained, broken flakes. All dependencies are pinned, but the project itself may move on from what is specified in the flake. A bunch of my own projects were flakes [1], but they would regularly break, because the project would move on (e.g. requiring a newer version of libtorch), but I forgot to update flake.nix/lock.
Of course, you can still run historical versions, but when the main path doesn't work, many users will just move on. So, including Nix flake files becomes more of a liability to a project than an asset.
(Besides that, it probably fills your store with many, potentially vulnerable versions of glibc and whatnot due to use of many different nixpkgs revisions, a problem that the centralized nixpkgs package set doesn't have.)
[1] I even implemented/contributed the cargoLock functionality, so that you can use buildRustPackage (rather than an external solution) without needing to specify the Cargo vendoring hash to make it easier to use buildRustPackage in your own repositories:
https://nixos.org/manual/nixpkgs/stable/#importing-a-cargo.l...
I was able to run 10 years old chrome builds on latest nixos using nix. Windows users might read this and go meh but linux people know how big of a deal that is.
I love Nix and NixOS and have used them for years, but it always feels like I am stuck in beginner level when it comes to understanding the language.
The biggest obstacle is pedagogic. I think big wins can be make by creating an up-to-date, deep-dive learning resource. I get the suspicion that one must learn Nix in a somewhat different way than one learns other languages. But I don't know what this method should be, and I wish somebody showed it to me.
Admittedly, some of the difficulty relates to the Nix language itself. I got excited when I saw a gist [1] by Eelco Dolstra that 'naturalize' aspects of the Nix language by bringing them down a level of abstraction. I am disappointed this isn't discussed so often in the community. Making configurations and packages explicit parts of the language - as Eelco suggests - is certainly going to help us mere-mortals understand what is going on in Nix. But syntactic improvements that makes Nix feel more like YAML are also huge: familiarity is a cornerstone of intuitiveness.
Please twaeg - make this happen!
[1] https://gist.github.com/edolstra/29ce9d8ea399b703a7023073b0d...
Regarding the language and "configurations" specifically, you might like what we do with Nickel: https://github.com/tweag/nickel. Research project showing a potential future for Nix.
No data on this, but I'm pretty sure Nix is used mostly by for-profit companies trying to tame complexity on a limited budget.
It's not nice or pretty, but there's very little alternative unless you're ready to keep a whole team of developers just fixing Dockerfiles all day.
To each his own, it targets an entirely different niche.
It does appear to be an experiment in package management that got out of hand. Basic usability is lacking, as I was unable to even get a listing of available packages on a NixOS virtual machine due to nix-env requiring well over 1GB of RAM. This flagrant waste of resources doesn't inspire confidence in the quality of the tools.
I'd rather see existing packaging data leveraged rather than adding a new language to the mix. Something like a translator or interpreter for RPM .spec files, for example.
Can you elaborate on this? I don’t follow.
But a lot of users want to leverage Nixpkgs while instead (or simply first) adding their custom packages to an overlay or a company repo of Nix packages.
> 3. Add the package to the file pkgs/top-level/all-packages.nix. The Nix expression written in the first step is a function; it requires other packages in order to build it. In this step you put it all together, i.e., you call the function with the right arguments to build the actual package.
[1] https://nixos.org/manual/nix/stable/expressions/simple-expre...
Rust has few things that makes it outstanding against other languages (in this context in particular):
- Tooling: I think nix needs an lsp (if isn’t any yet).
- Static typing: In this particular case might work better the typescript route, where you can gradually add typing (to not break old nix code).
- Docs.rs and documentation: In particular it is very powerful to have a centralized documentation that isn’t ambiguous and also this forces the packages to document themselves, so you could access that documentation directly from the source code and the tooling in your text editor.
This is just something that for me will make it easier to use, I think the days where you write text without help are over, it is much better IMHO work with rust because those points (there are few others, but besides those) for me is so important, and also ease the learning curve of nix language in general.
The other thing is the ecosystem, iirc you need some other packages or helpers to make nix work, there are also cases where you want to setup something and the official docs tell you that you need some package first, then you go a step back and try to figure out what’s that, and the same if you want to install another package, it requires you another package to setup first, I don’t remember exactly but in macos you needed some packager or darwin packager, I really don’t remember, and that was a huge set back, besides other issues with newer macos changes that did nix a PITA to install correctly.
"I need something that does X"
"But it already does X"
"But what about Y?"
On a more serious note, the linked project really does work with Visual Studio Code, do check the README of the linked project and you'll see :)
I use it, but i hate it, but i'll never leave it. I really hope for advancements in either the LSP or a sane type system (Nickel? Perhaps) to replace NixLang.
I think modern Nix (Flakes, modern CLI, etc) would be nearly flawless if i could get good inline information on each field, types, etc. When Nix Lang has as many language features as Rust, ie docstrings, types, etc - i think i'll love it. Until then it's an abusive relationship for me hah.
I love that flakes allow you to decouple a package from nixpkgs and place it in your repo, but in order to fully realize this dream, there needs to be a proper index of these packages, as well as non-experimental support for flakes.
Another (pipe) dream of mine is that Nix gets true cross-platform support, including non-WSL windows. This would allow it to fulfill a role that doesn't currently exist, which is a cross-platform package manager and build system that works across language ecosystems.
Thanks!
A flake.nix file is roughly comparable to a Dockerfile. With a Dockerfile, you're describing how to build an image that can be deployed in Docker runtimes. With nix, you're describing how nix can build the package.
A neat side-effect of this is that if you've got a nix file which can build the package, nix will be able to provide the toolchain used to build the package. (Whereas rustup more specifically provides the rust toolchain).
I have seen how it works great in a team, if all are onboard.
No place I've worked at was interested in the advantages of Nix though.
I wonder if switching to something less recognizable to a functional programming language might help adoption.
The approach Starlark (the DSL for Bazel) has taken, is have mutable datastructures, but freeze them after they are evaluated. This seems a lot more explainable and debuggable for the average programmer.
Infinite recursion errors are not fun to debug in Nixlang.
At my current job, NX is used to be a kind of Nix, but it does not seem to try to solve the entire problem space. Just to solve the additional complexity that introducing a monorepo in regards to tracking build dependencies.
It seems to me that how awesome Nix is from a tech perspective, it doesn't make delivering actual software any easier without team buy-in and effort in integrating in their delivery pipelines.
1. "Reproducible builds and deployments." OK, this is exactly Docket etc. claim. No differentiation here.
2. "Nix is a tool that takes a unique approach to package management and system configuration." Uh, why should I care? What problem is this solving? What's the benefit to me?
And it continues throughout Nix. E.g. advice in this thread that the only sane way to use Nix is with Flakes, which are some semi-documented experimental feature of Nix. It's just terrible user experience right from the start. Just read the thread.
You can indeed achieve some reproducibility with Docker. It's tricky though, as you'd have to pin exact package versions of software. If you'd `FROM ubuntu:$VERION`, and would run an `apt-get update`, you're not guaranteed to get the same software.
Nix is like ZFS, as that it breaks the wall between two previously distinct area's. Those being building software, and installing/configuration software on your OS. It's quite different from the snapshot-everything methodology that Docker uses. Yeah, one can split in multi-stage images etc, but than you'll be keeping track of which dependencies need to be moved between the stages yourself, in a manner that cannot be abstracted away, so you're doomed to repeat the same patterns over and over again.
People also state that LVM + ext3 is more than sufficient compared to the complexity of ZFS. They miss out on the fact on how much more fine grained solutions are possible with ZFS.
I've used niv [0] before flakes arrived, and am actually still using that instead of flakes. The experimental nature of them has scared me away from them, as I'm not daily involved in this ecosystem at the moment.
Docker doesn't give you reproducible, it gives you repeatable 90% of the time.
> 2. "Nix is a tool that takes a unique approach to package management and system configuration."
> Uh, why should I care? What problem is this solving? What's the benefit to me?
Because #2 enables Nix to actually deliver 100% reproducibile builds and deployments.
I guess there are some related efforts that are looking to share components as well: https://riir-nix.github.io/
There also has been some effort on https://github.com/nix-community/go-nix spearheaded by flokli to re-define some of the binary cache protocols. This will allow for more incremental transfers of build artefacts, reduced bandwidth and disk consumption.
That makes a lot of sense for TVL and could be a valuable characteristic to a of other organizations as well. :)
> I don't think that work is public yet.
I'd hoped there was something like that going on!
> There also has been some effort on https://github.com/nix-community/go-nix spearheaded by flokli to re-define some of the binary cache protocols. This will allow for more incremental transfers of build artefacts, reduced bandwidth and disk consumption.
Cool!
Somewhat naively, I assumed that installing it from the official channel would do the job. It didnt't. I then searched the Internet and found a very "creative" workaround for Arch users that didn't work either.
My own problems aside, I would expect from a tool marketed as something that helps you keep your environment clean to not litter my disk with a ton of hidden files and directories spread all over the filesystem.
I hope it doesn't sound too harsh. I'm keeping my fingers crossed for the development of this amazing project!
Did you tried the method shown in Nix's site?
https://nixos.org/download.html
>I assumed that installing it from the official channel would do the job. It didnt't.
"Official channel" you mean from repos? That's a problem of your distro's package then, isn't it?
[1] https://github.com/NixOS/nix/issues/879#issuecomment-4109043...
On non-nixOS, I think the changes Nix makes are:
1. puts the majority of its stuff under /nix 2. in the user directory, puts some files under ~/.nix-channels, ~/.nix-defexpr and ~/.nix-profile 3. modifies the default shell script /etc/bashrc or so, with some stuff under /etc/nix. 4. adds multiple users nixbuild1 ... nixbuildN.
The uninstall command given in the manual is a one-line:
``` sudo rm -rf /etc/profile/nix.sh /etc/nix /nix ~root/.nix-profile ~root/.nix-defexpr ~root/.nix-channels ~/.nix-profile ~/.nix-defexpr ~/.nix-channels ```
Years ago, I submitted a PR that added this exact behavior. But it depended on interpolating a Nix-internal variable into a config file in the Fish package which at the time was undocumented (@NIX_STATE_DIR@) and upon the layout of profiles within it, so there was concern that it might break on future Nix releases. There were a few other issues, too, and at the time I don't think there was a great way to add tests, either. (That's important because if you screw this up, you can break login for Nix users— I know because I did it once, and that was awful.) Anyway, I felt discouraged and didn't know where to go with it next, so I got lazy and dropped the PR.
At any rate, I don't think your expectation there was unreasonable. I think that would be a good and sensible UX, and your intuition was reasonable.
> After yesterday's post about Nix I tried to install it on my Arch+fish machine. I couldn't.
So the problem is this: the official Nix installer leverages an initialization script, to be sourced at shell init time, which is written in POSIX shell. Fish can't just source it because it's not compatible with POSIX shell.
> I then searched the Internet and found a very "creative" workaround for Arch users that didn't work either.
Arch users shouldn't need anything special here.
You can use fenv¹ to source it, you can translate it to bash using babelfish, or you can exec into fish after running bash to log in (make sure to set $SHELL after if you choose that option). Just make sure you do it as early as possible if you want to use things installed by Nix in your other Fish config snippets.
I think Home Manager will also take care of this for you. (The other module systems, Nix-Darwin and NixOS, both do.)
If you wanna do it like NixOS does, you can install Fish via Nix and then create your own preinit environment script in /etc/fish. This has the advantage of setting up your Nix environment variables before any other config is sourced. You can take a look at it here, which also explains some of the Fish initialization process: https://github.com/NixOS/nixpkgs/blob/master/nixos/modules/p...
and here's where the hooks go in the Fish package, where the comments describe the Fish initialization process in detail as well as why things are done this way on NixOS: https://github.com/NixOS/nixpkgs/blob/master/pkgs/shells/fis...
—
Definitely check out the Tweag development update posts on discourse.nixos.org if you're wondering who they are! The update posts are great, and they give you a clear sense of what Tweag's commitments are, how much they regularly contribute to Nix and the wider ecosystem, and the way they conduct software development out in the open.
And there it is. Every time I hear about Nix, the goal is to convince me to adopt it, as if it was some kind of religion. Every time the Nix folks are being too pushy about it.
Just stop pestering random project maintainers with Nix. If a project maintainer likes Nix, they'll add the Nix files. If they don't have Nix files, that doesn't mean they want to sign up for Nix advertising.
I don't know of a religion where you have to go through hell before reaching heaven.
Unfortunately many private FOSS enthusiasts do not know that reliability and documentation is a must for serious engineering environments.
Plus, a coworker pointed out that while its supposed to be pure and functional, many recipes still basically wrap a shell script. So its not that far from the build system we already have...
Not defending Nix here, but using shell script as part of the build doesn't make Nix itself imperative/impure. As long as the evaluation of the Nix expression itself is pure [1], the build inputs are fully specified, and the build is performed in a sandbox, the shell script (and things like configure/cmake/make/ninja) should always be run in the same manner and result in the same output (modulo things like embedded time stamps in files).
[1] This hasn't traditionally been true, since you could e.g. read files or use environment variables from Nix, but this is something flakes address.
Yup.
The key contribution Nix brings is arranging the outputs of builds into the nix store, in such a way that you can trust that building a package with the same set of inputs will result in a package that behaves the same way. (This then allows e.g. different versions of the same package).
There's some friction, since with some software, if you try and build things but disallow writing to arbitrary files (e.g. no writing to $HOME), the tools might have assumed they could, so things might not work. -- That's 'purity' in some sense, in that what inputs the package building uses is totally declared.
I liked the analogy introduced from a tweag post from a couple of weeks ago https://www.tweag.io/blog/2022-07-14-taming-unix-with-nix/ (big discussion yesterday https://news.ycombinator.com/item?id=32355327) that illustrated nix as 'pure', but interacting with the Unix system by way of files. -- You have a pure way of managing an impure system. (Which is loosely comparable to how Haskell can be pure, but still do impure stuff like Input/Output).
This is really unfortunate. Unless you invest time into learning which paths to walk, you're not going to have a great experience with Nix. That just doesn't scale to modern engineering teams, you can't expect everyone to know everything.
> Plus, a coworker pointed out that while its supposed to be pure and functional, many recipes still basically wrap a shell script. So its not that far from the build system we already have...
It's true that a lot of nix expressions boil down to a shell script. But by default they're running in a sandboxed environment that can be exactly replicated and guarantees (mostly) reproducible results. And that's great - after some ceremony to set everything up, Nix lets you work with the tools you already know, but puts them into a reproducible environment.
The shell scripts' effects get frozen in the Nix store, though, and can't be touched after build time. So it's a bit like using a loop in the implementation of an interface that that returns an immutable value in a language like Scala or something.
But I agree, they need to drop or reword that as an official goal. I suspect what they're thinking is that they want it to become so good and more broadly accessible to a wider range of developers that it gets natural usage and traction and becomes ubiquitous organically.
But they make it sound more like they're missionaries proselytizing a religion, ostensibly for the audience's benefit, but really more for the religion's benefit. Or salesmen selling something by telling you how good it is for you, when it's really better for the salesman. People pick up on that and reject it.
Of course, they should keep trying to make Nix ubiquitous by making it really good and broadly accessible and by engaging with the dev community for ideas on how to do that, as they outline in this post. Just don't make ubiquity an official goal. Let that happen organically.
The Nix language itself is half of the problem, difficult to search for because "nix" doesn't refer to something specific as it's overloaded, what hubris there must of been to think that was a good idea, it's also terribly documented with too much of a focus being on "elegant code" instead of being clear. Java and Go obviously being too verbose, but you could use a subset of python like starlark to achieve clarity and readability.
This being one of many but I've lost the will to continue as Nix as a dev experience is abysmal and really something else needs to replace it because I don't the language being fixed anytime soon. Guix will not be the on either due to FSF dogma.
People can go on about having successfully adopted it at their org but simply put, if it was good enough as is the percentage of companies using it would be meaningful. FYI a little script that only a minority of the devs understand does not count.
Most devs don't understand or care about the build process as long as it works and they know how to poke a stick at it in my experience
For example, running pip (python package manager) fails because it tries to change the current installation environment behind Nix's back. Instead, Nix should allow it to run, but monitor any changes it makes in a functional way. This may require running programs inside an emulation environment (catching all the kernel calls that make modifications), or perhaps use a specialized filesystem, which sucks, but you can't have a free lunch here.
The way I go about this these days is to keep a nix derivation that builds a container image, and then I run pip installs freely in containers that I spin up. I use mach-nix.
If a package is deemed important, then I add it in the derivation. So there is a kind of flow from "runtime" to "build".
Yes, this is exactly how it should work, imho.
People aren't going to switch to Nix unless they have a reason to, and frankly what they are proposing won't capture a lot of users. Maybe some Mac people who want more packages available, but that is about it. I like the idea of Nix, but it is going to take a lot more to get people to adopt it. Nix packages are ugly. Rather than build the API around package management like winget or to some extent pacman, they instead added a bunch of scripting so each package ends up looking like a clusterfuck. A lot of the features aren't even documented well.
https://o1-labs.github.io/ocamlbyexample/
https://doc.rust-lang.org/rust-by-example/
Also if it’s not on learnXinYminutes it should be
You got any hard data to back this up? None of the things I've personally picked up, have been because of the existence of such websites, but instead because of practical reasons, being able to do new things other languages couldn't (as easily).
"flake.nix in every repo" seems a bit of a chicken & egg thing relating to "nix should work reliably everywhere". If nix runs into problems with common situations, it's less likely there'll be a flake.nix. But, if it's rare to spot a flake.nix file, it's harder to be interested in nix.
Rather, I think most of the comments I see from people who are less than happy about nix as-is relates to friction from trying to use nix, but things go wrong.
- consistent dev environment with all local dependencies (postgres, rustc, awk, etc.)
- building rust packages themselves
- building tiny docker images that run rust binaries
The official Rust tooling for nix still uses Cargo under the hood, and this makes it way easier to use and more consistently functional than the equivalent tooling for Python, JS, and similar, at least in my experience
Sure I love to program, but that doesn't mean I want to program every aspect of my OS just so I can start writing a web app.
If you increase user friendliness of the app with a GUI or easily understood commands not only will more regular people start using it, but MORE developers will start using it too. Many developers just want to work on their own project with an OS that just works.
Hence why more devs use mac and windows over linux.
Individual functional programming techniques may become interesting to you as you become curious about some implementation details— you might read a bit about 'fixed point recursion' after you chat with some people about how overlays work. But you don't have to think of yourself as a functional programmer to make great use of Nix or even to help solve technical problems in Nixpkgs.
I think some folks hear all the FP talk surrounding Nix and don't realize that there's a lot they can achieve and contribute without being FP wizards. And that sucks. I hope that the ecosystem feels increasingly welcoming to people like that as the documentation and UX continue to improve.
Making a GUI for generating Nix config is a complex task (and maybe not a better approach than providing a highly discoverable, user-frindly IDE experience, like DrRacket or something), so nothing like that is complete yet. But there are efforts along those lines that are still actively being worked on.
NixOS has also recently seen the addition of a graphical installer, for reasons like you describe. It's nice to see that kind of progress.
IDE support (code intelligence etc.) is always good though.
That is because it is an exemplary in accidental complexity at least from a user point of view. I cannot in good faith introduce it to an organization as it is way too complex to use / configure, only thing with worse documentation I've seen was PHP (this in itself a big red flag).
The language itself sucks (and this bleeds into the code), but the idea of it and the documentation are great imho.
Curious from others who used similar in the past and use Nix now think about it.
Ansible is great to deploy stuff with. Not perfect and not like terraform+k8s/docker.
Nix may be more for developers, as you'll end up developing for it.
The tutorials try to teach a soup of functional programming, build systems, configurations, nix language and nix framework, and that’s somewhat difficult to disentangle and tell what’s what.
Anyway I use it as my daily driver now, and overcame almost all the difficulties, but one still remains: the lack of static type checking. It’s hard to build and validate modules without having this built in the language itself.
I’m hoping that you’d accelerate the work on nickel and try to automatically translate the current nixpkgs/nixos.
I find that hard to believe, do you have examples?
I love the responsibility you're taking on, and why you're choosing the problems you do. You're doing dog's work.
Nix ix the best thing in applied computer science since I don't know what (suggestions in the comments below please)
It's evolving so quickly, and so easily, that it's hard to keep up. There's a general need for coherent porcelain, and the documentation to match. There's a lot of hope for what it can do, but it's still very hard to learn how to do a lot of it.
It's going to become ubiquitous
Thank you
e.g. on par with the quality of Java editing in IntelliJ
This would help massively for folks learning how to do things.
Besides that, I just keep wondering — and tweag said it too — if some tool that did nix-shell and nixpkgs would be enough.
At the end of the day, a lot of folks are really just using nix like Python‘s virtualenv — i.e. declare what you need, change $PATH to include it in a sandboxed environment.
It’s hard to use. It solves a problem that Docker already solved and Docker UX is much better.
And it has a DSL that I think is unnecessary for the problem at hand.
But for that to happen I imagine PkgBase needs to be completed first.
It makes more sense to make a strong push for getting the new features fleshed out, made user friendly, and stabilized, and then slamming the brakes and doing a documentation push.
In practice, this will take a long time, and it probably makes sense to concurrently work on documenting things that won't change. But I don't think at this stage dropping all feature work for documentation makes sense.
The other thing is that I don't think Nix's learnability issues come entirely from lack of documentation. A big chunk of the problem is a lot of very strange UX decisions and confusing defaults. Rather than documenting these as is, it seems better to put effort into fixing them, making default behaviour more intuitive and less confusing.
Nickel looks much prettier than Nixlang, but it carries over a feature that still confuses me about Nixlang: variable declaration. Perhaps you can shed light on why it is the way it is.
Why does it need to be of the format "let x = 5 in whatever(x);"? Why not, like Rust/F#/etc, allow the syntax "let x = 5; whatever(x)", i.e., allow the definition to stay in scope for the remainder of current block?
Meaning whenever you see a 'let', look at the surrounding, it will probably look like '{ a = (let x = 5; in x); }' which is just a convoluted way to write '{ a = 5; }'. Or often you'll see 'a = (foo: let ...)' in this case the ':' declares a function taking the argument 'foo'.
You can play around with the language in the 'nix repl'. The language itself is really simple, but not very obvious when just looking at a code snippet it.
And yes, there is an argument to be made that a purely expression based language is not very ergonomic, but it keeps the Nix language simple.
Btw, aptitude includes an ncurses TUI, but it's also an improved CLI frontend for apt that includes a few really nice features. Check it out next time you're on a Debian-based distro and try some of the special search patterns at least.