3 ms·
Some community members have looked into this quite a bit, and personally I have come to the conclusion that types don't really give that much benefit to Nix (an
by tazjin 4y ago
Some community members have looked into this quite a bit, and personally I have come to the conclusion that types don't really give that much benefit to Nix (and I say this as a Rust & Haskell developer).
Nix expressions are almost always[2] short-lived snippets that evaluate to a data structure, not long-running programs where the distinction between "static analysis time" and runtime is extremely relevant.
In fact, deriving the full set of potentially relevant type constraints is only possible at runtime due to how the import system works and the shape of most expressions. If you pick a single file from nixpkgs without context, you can't get much information from it at all (other than a lot of unknown types being passed to things that accept an unknown type) - it's only in the context of an evaluation of a graph node that uses that file that you can infer anything meaningful about it (and even then that information is only relevant in that context).
I think what people actually want is a way to derive more sensible documentation information from the code so that the various builders etc. could have checked documentation pages, as well as tooling for auto-completing members of attribute sets, names of (formals) function arguments and so on.
fwiw, there's an alternative implementation of the Nix language[0] that we (TVL[1]) are slowly open-sourcing at the moment, and we're aiming to design it in such a way that things like an LSP can be implemented on top of it, and to be able to dump out static information from a context that can help with documentation etc.
[0]: https://cs.tvl.fyi/depot/-/tree/tvix/eval https://cs.tvl.fyi/depot/-/tree/tvix/eval
[1]: https://tvl.fyi/ https://tvl.fyi/
[2]: Yes, I'm aware that Nix is turing-complete, but surely nobody would write a web framework[3] and HTML templater[4] in it.
[3]: https://cs.tvl.fyi/depot/-/blob/web/bubblegum/README.md https://cs.tvl.fyi/depot/-/blob/web/bubblegum/README.md
[4]: https://cl.tvl.fyi/c/depot/+/3410 https://cl.tvl.fyi/c/depot/+/3410
- hamandcheese 4y ago> If you pick a single file from nixpkgs without context, you can't get much information from it at all (other than a lot of unknown types being passed to things that accept an unknown type) - it's only in the context of an evaluation of a graph node that uses that file that you can infer anything meaningful about it (and even then that information is only relevant in that context). This is exactly where types would be the most beneficial, and what makes nix so hard to read. If a nix function could specify the types of its arguments, then I might have a chance of better understanding it. Just because most nix functions currently don’t have many constraints on their inputs doesn’t mean that they couldn’t in the future. > it's only in the context of an evaluation of a graph node that uses that file that you can infer anything meaningful about it (and even then that information is only relevant in that context) That’s how nixpkgs works now. But we can make functions that work only in more limited contexts.
- tadfisher 4y ago> tooling for auto-completing members of attribute sets That's a great start, but it would be nice to know what the expected type of the member is! Often it's another attribute set, a list, or even a function, and it's impossible to tell what type is expected without looking at where the member is used.
- kaba0 4y agoI am originally opposed to blaming the Nix language, but now that I read your comment and thought a bit more about it, Clojure’s spec might be a much better tool than types. It would solve the readable error messages problem quite well and is flexible enough to accommodate any usage like parameter passing.
- tazjin 4y agoSomething like Clojure's spec would IMO be a better fit, yeah. I've written an experiment with a runtime type-spec and checker for Nix: https://code.tvl.fyi/about/nix/yants/README.md https://code.tvl.fyi/about/nix/yants/README.md However, this has massive runtime cost (especially in hot code paths), so some sort of spec-like annotation system would be cool. We'll see how it shakes out over time ... As for error messages, we might already be able to do big improvements in Tvix. Our bytecode has pretty exact tracking of the source spans that things come from all the way throughout, so we could trace things like a type error being raised somewhere to the last time that value was passed through as a function argument from user code etc. This error message business will be a whole area of development of its own however, for now we're just making sure that as much of the relevant information is available as cheaply as possible.