-
-
Notifications
You must be signed in to change notification settings - Fork 1.6k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Improve path value documentation #10560
Conversation
doc/manual/src/language/values.md
Outdated
|
||
Paths are the preferred type for referring to local files. | ||
This is thanks to the following properties: | ||
- Path values are always in a canonical form, so that you are relieved from trailing slashes, `.` and `..`. |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Unfortunately this isn't true, paths can have a trailing slash.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
But why is this then:
nix-repl> a = /home/
error: path has a trailing slash
at «string»:1:2:
1| /home/
| ^
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
nix-repl> let x = "x"; in /home${x}
/homex
nix-repl> let x = "x"; in /home/${x}
/home/x
I.e. /home/
is represented internally with a trailing slash, since canonicalizing it to /home
would cause /home${x}
to evaluate to /homex
.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This is internal to the /p/${e}
expression and not observable as the result of a properly composable expression, right?
If it is, then I would expect that to be a bug.
At least these are fine:
nix-repl> /home${""}
/home
nix-repl> /home/${""}
/home
nix-repl> /home/${"/"}
/home
nix-repl> /home/${"////"}
/home
I should clarify that trailing slashes do matter in the literals.
- Path values are always in a canonical form, so that you are relieved from trailing slashes, `.` and `..`. | ||
- Path literals are automatically resolved [relative to the file](@docroot@/glossary.md#gloss-base-directory). | ||
- Path values are automatically copied into the Nix store when used in a string interpolation or concatenation. | ||
- Tooling can recognize path literals and provide additional features, such as autocompletion, refactoring automation and jump-to-file. |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
- Tooling can recognize path literals and provide additional features, such as autocompletion, refactoring automation and jump-to-file. |
This is hypothetical from the perspective of the Nix language
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Users really do get to enjoy autocompletion in the repl already.
I don't know, should I be writing a guide "How to pick a Nix value representation for local files"?
That'd be quite absurd.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Okay, this one's low impact, feel free to ignore then.
doc/manual/src/language/values.md
Outdated
A path literal must contain at least one slash to be recognised as such. | ||
For instance, `builder.sh` is not a path: | ||
it's parsed as an expression that selects the attribute `sh` from the variable `builder`. | ||
|
||
Path literals may also refer to absolute paths by starting with a slash. | ||
This is generally not recommended, because it makes the expression less portable. | ||
In the case where a path literal is translated into an absolute path string for a configuration file, it is recommended to just use strings. | ||
This avoids some confusion about whether files at that location will be used during evaluation, | ||
and it avoids unintentional situations where some function might try to copy everything at the location into the store. | ||
|
||
If the first component of a path is a `~`, it is interpreted such that the rest of the path were relative to the user's home directory. | ||
For example, `~/foo` would be equivalent to `/home/edolstra/foo` for a user whose home directory is `/home/edolstra`. | ||
Path literals that start with `~` are not allowed in [pure](@docroot@/command-ref/conf-file.md#conf-pure-eval) evaluation or flakes. |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I was recently thinking about moving the Nix language tutorial section on paths here, but I'd approach it a bit differently, and never find time for it. I really dislike the idea of perpetuating dense prose in the reference manual. But as we discussed on the other thread, doing things properly takes time no one has, and having something at all is probably better than nothing.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I thought we didn't write tutorials in the manual.
I wouldn't oppose it, because the tutorial would be scoped to the project nicely, and I suppose you have a good reason to change course?
- Tooling can recognize path literals and provide additional features, such as autocompletion, refactoring automation and jump-to-file. | ||
|
||
A path literal must contain at least one slash to be recognised as such. | ||
For instance, `builder.sh` is not a path: |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Generally, please highlight examples as such: https://hydra.nixos.org/build/256586709/download/1/manual/contributing/documentation.html#markdown-conventions
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
That would disrupt the flow for something that isn't even an example of a path.
Worse, when scanning the text, "Example: builder.sh
" under Paths, that would suggest that it is a path.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Right. I'm generally skeptical of this conversational tone that meanders between facts and counterfactuals. It would take me way too much time to unravel this with concrete suggestions for that text, so I don't know. See the other comment on using parts from nix.dev.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Ok, let's postpone that then.
Paths can be used in [string interpolation] and string concatenation. | ||
For instance, evaluating `"${./foo.txt}"` will cause `foo.txt` from the same directory to be copied into the Nix store and result in the string `"/nix/store/<hash>-foo.txt"`. | ||
|
||
Note that the Nix language assumes that all input files will remain _unchanged_ while evaluating a Nix expression. |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Make a proper highlight
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
What makes a highlight proper?
Note that this was in the original text.
Paths can be used in [string interpolation] and string concatenation. | ||
For instance, evaluating `"${./foo.txt}"` will cause `foo.txt` from the same directory to be copied into the Nix store and result in the string `"/nix/store/<hash>-foo.txt"`. | ||
|
||
Note that the Nix language assumes that all input files will remain _unchanged_ while evaluating a Nix expression. | ||
For example, assume you used a file path in an interpolated string during a `nix repl` session. |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Make a proper example
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I am not rewriting everything, sorry.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Rewriting everything blows up the scope of the PR.
Our priority should be to get improvements merged.
The base directory part can stand on its own, we could merge that quickly instead of blocking on the lengthy prose. |
See NixOS#8738 for a more pointed criticism of absolute paths.
Co-authored-by: Valentin Gagarin <[email protected]>
Motivation
Reduce my anxiety levels when people discuss path value related code on the internet.
They're an important feature that deserves to be understood well.
This improves the description of path literals and path values to
Also this defines "base directory", which is a useful term when discussing path values, which are usually relative. I'll remove that commit if it's not easy to get into a good state.
Context
no-absolute-path-literals
experimental feature #8738Priorities and Process
Add 👍 to pull requests you find important.
The Nix maintainer team uses a GitHub project board to schedule and track reviews.