While working on nixpkgs-update, I found that there are a lot of formats being used for the pkgs attrpaths:
attrpath format
example
version represented
name(MAJORDIGIT)(MINORDIGIT)
qt56
5.6.x
name(major)
icu58
58.x
name(majordigit)(minor)
autoconf213
2.13
name(majordigit)(minor)x
automake111x
1.11.x
name(digit_not_in_version)_(major)_(minor)
libgit2_0_25
0.25.x
name-(major)-(minor)-(patch)
libsigrok-0-3-0
0.3.0
name_(major)_(minor)
apacheKafka_0_10
0.10.x
name-(major)_(minor)
dbus-sharp-glib-2_0
2.0.x
name(major)_(minor)
antlr3_5
3.5.x
name(major)
bison3
3.x.x
name(digit_not_in_version)
automoc4
x.x.x
name_(date)
fplll_20160331
20160331
name
owncloud-client
x.x.x
name(unrelatednumbers)
libavc1394
x.x.x
I believe a standardized attrpath naming convention would be helpful for automated tools, nixpkgs maintainers, contributors, and users:
Automated tools could better understand what derivations correspond to what versions. nixpkgs-update could avoid updating a derivation that is pinned to a specific version, and it could smartly update point releases on multiple major versions of the same package.
Maintainers would be able to refer to and point to the naming conventions when reviewing contributions.
Contributors would have clear rules to follow when naming attrpaths.
Users who learned the policy would have an easier time installing and manipulating derivations.
If a naming policy is adopted, we should add it to the nixpkgs manual in Chapter 13, use aliases and deprecation warnings to transition nixpkgs, and add a linter to enforce the policy.
My proposal for the policy is:
Let pname equal (builtins.parseDrvName attrpath.name).name
Let version equal builtins.concatStringsSep "_" (builtins.splitVersion (builtins.parseDrvName attrpath.name).version)
Let partialVersion be version with any number of parts removed from the end
automake or automake_1 or automake_1_11 or automake_1_11_6
libgit2_0_25
libgit2 or libgit2_0 or libgit2_0_25 or libgit2_0_25_1
apacheKafka_0_10*
apache-kafka or apache-kafka_2 or apache-kafka_2_12 or apache-kafka_2_12_0 or apache-kafka_2_12_0_10 or apache-kafka_2_12_0_10_2 or apache-kafka_2_12_0_10_2_1
dbus-sharp-glib-2_0**
dbus-sharp-glib or dbus-sharp-glib_0 or dbus-sharp-glib_0_6
antlr3_5
antlr or antlr_3 or antlr_3_5 or antlr_3_5_2
bison3
bison or bison_3 or bison_3_0 or bison_3_0_4
automoc4
automoc4 or automoc4_0 or automoc4_0_9 or automoc4_0_9_88
fplll_20160331
fplll or fplll_20160331
owncloud-client
owncloud-client or owncloud-client_2 or owncloud-client_2_4 or owncloud-client_2_4_1
libavc1394
libavc1394 or libavc1394_0 or libavc1394_0_5 or libavc1394_0_5_4
icu58
icu4c or icu4c_58 or icu4c_58_2
* the apacheKafka looks crazy because it has a weird version that is the concatenation of two versions, this shows the shortened paths would not always make sense
** the dbus-sharp-glib attrpath doesn’t contain its own version; it looks like it uses the version of dbus-sharp that it is compatible with
Please comments on this policy or suggest a different policy. I have not specifically thought about what to do about nested package sets (like the language-specific ones). Any comments on how this policy would impact those would be appreciated.
Yes, we should fix any man pages that talk about attrpaths. It looks like the one you linked to is talking about derivations names and versions, which I am not proposing changing.
The good news is 75% of the top-level attrpaths already conform to this policy!
This nix program generates a list of all the attrpaths that don’t currently conform to this policy along with what would be a valid attrpath according to this policy.
This reveals some problems with the policy that should be addressed:
One obvious thing to fix is to allow the attrpaths to start with “_” in the case where name is numeric. It’s impractical to use string attrpaths for these ones, right?
There are attrpaths like “zfsStable” and “zfsUnstable” which do not fit into this policy model. What should we do with those?
Parameterized derivations that use attrpaths, like grub2_efi vs grub2_full.
attrpaths that proxy to a nested package set, like Fabric, which has derivation name of python2.7-Fabric.
I would not be in favour of this, it has a tendency to break stuff that’s meant to somehow automate end-user-exposed applications. This kind of deviating-from-upstream naming has caused lots of trouble with Node.js on Debian, for example, and we’re still picking up the pieces from that decision in the support channel 5 years later.
Ah, yes, symlinking them would probably be fine, so long as the symlinked name doesn’t interfere with the original binary name of some other package. I’m not sure how difficult it is to implement “only expose a symlink if there’s not already a file with the same name”, or whether Nix might even already do this by default.
(Even then, though, you’ll want to consider the possibility of an application relying on its binary name being a particular thing. I’ve seen this issue particularly with proprietary Mono-based games, where it will fail to load some bundled shared libraries if the binary name is changed in any way. So a symlink wouldn’t work there, you’d need a wrapper script.)