Skip to content

lib.version: init #3344

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

Draft
wants to merge 4 commits into
base: main
Choose a base branch
from
Draft
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
1 change: 1 addition & 0 deletions lib/default.nix
Original file line number Diff line number Diff line change
Expand Up @@ -25,6 +25,7 @@ lib.makeExtensible (
options = call ./options.nix { };
plugins = call ./plugins { };
utils = call ./utils.nix { inherit _nixvimTests; } // call ./utils.internal.nix { };
version = call ./version.nix { inherit flake; };

# Top-level helper aliases:
# TODO: deprecate some aliases
Expand Down
140 changes: 140 additions & 0 deletions lib/version.nix
Original file line number Diff line number Diff line change
@@ -0,0 +1,140 @@
{
lib,
flake,
}:
let
inherit (builtins)
isList
mapAttrs
head
tail
;

lockFile = lib.importJSON ../flake.lock;

/**
Resolve an input spec into a node name.

# Inputs

`inputSpec` ([String] | String)
: Either a node name, or a "follows" path relative to the root node.

# Output

The node name.

# Upstream

This is based on `resolveInput` in nix's [call-flake.nix]

[call-flake.nix]: https://github.com/NixOS/nix/blob/46beb9af/src/libflake/call-flake.nix#L21-L25
*/
resolveInput =
inputSpec: if isList inputSpec then getInputByPath lockFile.root inputSpec else inputSpec;

/**
Follow an input attrpath from the root node, stepping through each node along the path.

# Inputs

`nodeName`
: The name of the _current_ node.

`path`
: The input attrpath to follow.
E.g. `["dwarffs" "nixpkgs"]`

# Outputs

The final node name.

# Upstream

This is based on `getInputByPath` in nix's [call-flake.nix]

[call-flake.nix]: https://github.com/NixOS/nix/blob/46beb9af/src/libflake/call-flake.nix#L27-L37
*/
getInputByPath =
nodeName: path:
if path == [ ] then
nodeName
else
getInputByPath (resolveInput lockFile.nodes.${nodeName}.inputs.${head path}) (tail path);

# Inputs specified in our flake.lock
lockedInputs = lib.pipe lockFile.nodes.${lockFile.root}.inputs [
(mapAttrs (inputName: inputSpec: lockFile.nodes.${resolveInput inputSpec}))
];

# Our actual inputs, potentially modified by end-user's "follows"
realInputs = flake.inputs;
in
{
/**
Check whether a specific input is modified when compared to our `flake.lock` file.

This can happen when a user specifies one of our inputs "follows" one of theirs.
*/
isInputModified =
name:
assert lib.assertMsg (
realInputs ? ${name}
) "isInputModified: `${lib.strings.escapeNixIdentifier name}` is not in `inputs`.";
assert lib.assertMsg (
lockedInputs ? ${name}
) "isInputModified: `${lib.strings.escapeNixIdentifier name}` is not in `flake.lock`.";
let
# If a non-flake input is used, `sourceInfo` will be missing
real = realInputs.${name}.sourceInfo.narHash or null;
locked = lockedInputs.${name}.locked.narHash;
in
real != locked;

/**
Nixvim's current commit, or the specified default when nixvim's repo is dirty.
*/
revisionWithDefault = default: flake.sourceInfo.rev or default;

/**
Nixvim's current commit, defaulting to the canonical branch name for this release.
*/
revision = with lib.nixvim.version; revisionWithDefault releaseBranch;

/**
Nixvim's release.

Derived from the nixpkgs branch targeted in `flake.lock`.
*/
release =
let
inherit (lockedInputs.nixpkgs.original) ref;
parts = lib.splitString "-" ref;
in
lib.last parts;

/**
The canonical branch name associated with this release of nixvim.
*/
releaseBranch =
let
inherit (lib.nixvim.version) release;
in
if release == "unstable" then "main" else "nixos-" + release;

/**
Whether the nixpkgs input is correct for this release of nixvim.

Can be used to identify mismatched nixpkgs inputs, usually caused our input
following a user's input from another channel
*/
correctNixpkgsChannel =
let
nixvimRelease = lib.nixvim.version.release;
nixpkgsRelease = lib.trivial.release;
in
if nixvimRelease == "unstable" then
true # TODO: how do we know what channel a nixpkgs instance is on?
else
nixvimRelease == nixpkgsRelease;
}