5 ms·
Oh great! More indirection. Now when I want to deploy my web app I can check my private nixery.dev deployment is properly configured in Nix to build my Docker i
by exdsq 4y ago
Oh great! More indirection. Now when I want to deploy my web app I can check my private nixery.dev deployment is properly configured in Nix to build my Docker images so I can deploy my containers to the cloud so someone can access me Rest API. And the cost of guaranteeing builds will probably work? Running your own nixery service, learning Nix, and learning Docker. I would love someone to do a cost-benefit analysis of these sorts of tools against the time of using (and sometimes debugging) Make and/or Bash. I’m so cynical of Nix lol - no disrespect to the OP/Author, I just want to work on problems but most of my time is spent on building and deploying stuff.
- hamandcheese 4y agoDo you actually use nix and have an experience to share?
- WJW 4y agoNot OP, but the evangelism about "never having build problems anymore" does perplex me a bit. In the languages I have been programming in (Haskell, Ruby, some Python and elm and JS and Rust), I can't recall having any significant build problems in the last ~8 years or so anyway. What does everyone do that their build keeps breaking?
- steeleduncan 4y agoThose languages all have sensible package managers built in, nix adds more value with languages like C/C++, or when you have multiple binaries interacting. For example, I had a C++ project break catastrophically when upgrading from Ubuntu 19.10 to 20.04. It built fine, but wouldn't boot. Undoubtedly the root cause was my fault, but I couldn't trace it and the timing was terrible, so I had a hack to build inside a 19.10 container. Nix would have saved me a lot of pain in that case by pinning the compiler or whatever dependency broke it. Nix is also useful in that it pins the entire ecosystem in the case that your project isn't fully contained in one language. To take your Haskell example, if you use Stack it will pin every piece of Haskell code you might import, but I've had problems where an external tool changes its output, requiring changes to my tool. In that case nix is like Stack, but for your entire OS, building that tool in a reproducible manner.
- ananthakumaran 4y agoProbably you are lucky to not run into the nokogiri compilation issue. For production codebases, usually, this is not an issue because the build breakages are fixed one at a time by upgrading gem, etc. This is a big issue for personal projects, I am no longer able to run many old projects (last commit made before 5 years), because they depend on older library version (like libglew), which is not supported by any recent distros.
- drewm1980 4y agoPull in a lot of transitive dependencies, without a system in place that automatically and strictly vendors or pins the versions of everything, and the probably of your build succeeding will converge to zero over time. Humans screw up semver all the time even when they're aware of hyrum's law and are doing their very best not to break user code. I would say this starts becoming an issue when you're around 20-30 devs maintaining software that's a few years old. All that's just for rebuilding when their are no changes to your code... pulling in security updates is a whole additional mess if your software is exposed to adversaries.
- chriswarbo 4y agoOne reason you might have avoided problems in Haskell is that it (specifically: Cabal) added "Nix-style builds" in 2016 ;) https://cabal.readthedocs.io/en/latest/nix-local-build-overview.html https://cabal.readthedocs.io/en/latest/nix-local-build-overv...
- exdsq 4y agoYeah I was in a company using Nix for around 18 months where some of the DevOps team were contributors so everything was Nix’d. CI, dev environments, deployments, cluster management. Want to add a library to your Python app? Don’t use pip or poetry, update Nix. But because DRY this nix isn’t even in your project, it’s in another repo somewhere. Want to update Haskell? Well you can’t use Cabal or Stack, you need to use Nix2Cabal or whatever. It slowed down so much stuff that anyone could usually do to a ticket for a Nix-versed engineer to fix and was a choke point on everything. I’ve since vetoed it very hard at two startups I’ve worked at. I want to like Nix, I made my primary computer NixOS, but it’s just so much complexity. For small dev environments I kind of get it - I might still use it to spin up a Haskell env - but when the total Nix lines of code > 10k for a project then have fun!
- soraminazuki 4y ago> when the total Nix lines of code > 10k for a project then have fun! I have the suspicion that you’re talking about auto-generated Nix code. For comparison, lock files for language-specific package managers can easily exceed 10k lines. But I have yet to see any hand-written Nix build description for a single software project reach nearly as much LOC.
- exdsq 4y agoI just checked and without giving too much info I’ll round, but there’s 20 repos with 10K commits of pure Nix repos, 3k issues across them, and 30k references to the word nix lol. Random check and none of the files are generated in these repos - it’s all reasoned code judging from commits. These are then used across all projects which includes additional nix stuff. Going for the entire org and these numbers increase drastically but could include auto generated nix code.
- soraminazuki 4y agoAssuming your team consolidates Nix code in a few repos, that sounds fairly normal. In contrast, my team maintains a bunch of RPM builds and it's messier business than Nix. More boilerplate, breakage, and manual work.
- d4mi3n 4y agoThis really isn't too different than what is already done, but it does as you say add more layers of indirection. Consider: Prior to Docker, you'd typically go to AWS or a virtual host provider, spin up your OS of choice, install any relevant system dependencies, language runtimes, set up a CI/CD pipeline, and finally deploy. The only real difference between what I just described and Docker / Nix / additional layers is that we (as an industry/profession) have not yet built sufficiently ergonomic tooling to make this trivial. AWS and similar cloud providers did away with much of the server and network setup. Docker has done away with some of the application environment setup. All that said, Nix does seem to be trying to replace something we already have a workable answer to (host/app config). Whether or not the additional overhead is worthwhile even after ergonomics have caught up will probably depend on your own use-cases. I can see it being useful for high-trust environments (finance, medicine, anything else regulated). It could also do a lot to improve the general security of the OSS ecosystem by giving projects a path forward to truly reproducible binaries. Outside of those contexts, you probably don't care until tooling gets to the point where you can opt-in and get those guarantees "for free".
- unicornmama 4y agoNix makes a lot of sense if you really understand build system. But makes less sense if you understand operations, or management. Real world engineering is about trade-offs, and Nix has no wiggle room for compromise. It’s optimizes on one dimension: Reproducible builds. But an organisation won’t succeed when it places the needs of build system engineers on a pedestal.
- zimbatm 4y agoYou can always set `__noChroot = true;` on your derivations and forgo the sandbox. Then it's not more difficult than a Dockerfile really.
- pjkundert 4y agoIt adds some effort and complexity to the "build" dimension of your multi-dimension optimization, yes. But it also removes a whole bunch of complexity from every other dimension, by removing variability from the equation. If you cannot rely on /what/ you are running, then what, exactly, are you testing? Do you really know? I've found that most "managers" (in fact, most programmers) don't seem to appreciate this. The "well, I don't know what happened -- maybe reboot the system, and it'll work?" approach is insane.
- JamesSwift 4y agoId disagree its uni-dimensional. It optimizes for reproducibility and hermeticity without using virtualization (i.e. better performance).
- drewm1980 4y agoIs the extra layer of indirection you don't like Docker or this nix -> Docker integration? Compared to just installing all your nix packages in one Docker layer, this does introduce build complexity. But it's analogous to the complexity of a compiler for a static language... the thing that comes out is not more complex than what went in, so at least the complexity doesn't propagate. The images produced by this should be interchangeable with their single-layer counterparts; the caching will just be better when the code is rebuilt and re-distributed. If you're all-in on nix, does the container ecosystem even add value? The author of this software thought so, at least when he posted in 2018: "Tying in to the schedulers, orchestration, and monitoring is very valuable" Note, I have not used this; I'm just also frustrated by software development getting eaten by incidental complexity.
- chriswarbo 4y ago> I would love someone to do a cost-benefit analysis of these sorts of tools against the time of using (and sometimes debugging) Make and/or Bash. Nix does essentially the same job as Make. The differences are: - Make embeds a shell code interpreter, whilst Nix just execs a binary; given its path, a list of args and a set of env vars. (Note that almost all Nix definitions use bash as their binary!) - Make does meta-programming with a mixture of "automatic variables" ('$<', '$^', etc.), 'eval', macros, etc. whilst Nix uses a programming language. - Make relies on timestamps to figure out whether to re-use existing outputs; Nix relies on the hash of the definition (this works recursively, since hashes are included in filenames; hence changing a reference will alter all the hashes up the dependency tree). - Make runs commands in the directory where 'make' was invoked, Nix runs commands in a temp folder (and optionally restricts network and filesystem access) - Make runs commands with the same environment it was invoked with, Nix specifies the environment of commands in the build definition Nix also has a killer feature that Make can't do, called "import from derivation". This lets us define a build process, like 'fetch this git repo', then import and use Nix definitions from its result. In comparison, Makefiles can't (reliably) fetch and import each other; e.g. my C project's Makefile can't fetch the GCC source tarball, and depend on its Makefile's "install" rule to provide a compiler. My hypothesis is that this deficiency of Make is the reason for a whole bunch of unneeded complexity in the software world (e.g. "package managers", "OS distributions", "configuration managers", etc.) From a practical point of view, Nix is almost always used as a wrapper on top of something else (Make/Ant/Maven/Cabal/etc.); but that's just because most projects benefit from those "ecosystems". Note that we could just as well wrap such Ant/Maven/Cabal/etc. projects in a layer of Make instead of Nix, but nobody does since it wouldn't give us any benefit ;) If you're happy to ignore those "ecosystems" and just have a simple "bash + Make" project, you could instead have a simple "bash + Nix" project and avoid all the layers of Make/Ant/Maven/Cabal/etc. (as well as any Docker, Ansible, Apt/RPM, etc. that others might also decide to layer on top!)
- dboreham 4y agoThank you for this post. This is the kind of authoritative, insightful, contextually relevant information that makes HN so valuable.
- goodpoint 4y ago> I would love someone to do a cost-benefit analysis of these sorts of tools against the time of using (and sometimes debugging) Make and/or Bash Spot on! But HN is so biased towards new or flashy stuff...