Adds an invoiceninja-nixos flake input and two things built from it: - nixosConfigurations.invoiceninja-test-nginx/-caddy: manual test VMs, re-exported as-is from that repo rather than redefined here — same principle as this crate being a client of the SDK, not a second implementation of it. - checks.invoiceninja-cli: an automated nixosTest (tests/, adapted from invoiceninja-nixos's own test scaffolding) that boots a real Invoice Ninja instance and runs the actual invoiceninja-cli binary against it - create/list/get/update/invoice/payment/delete across clients, invoices, and payments - rather than raw curl. tests/common.nix's module import had to change from a relative ../nixos-module/invoiceninja.nix (which doesn't exist here) to a parameter threaded from the flake input's nixosModules.invoiceninja. Building the VM pulls from the invoiceninja-nixos cachix cache via a nixConfig block, mirroring that repo's own. Also fixes a wrong assumption the first version of this test's final assertion made, caught by actually running it against a real server: `clients list` with no `--status` does not exclude soft-deleted records - confirmed empirically (Invoice Ninja returns everything regardless of is_deleted unless status=active is passed explicitly). Corrected the test to check is_deleted via `clients get` instead, and fixed the misleadingly-incomplete --status doc comment in cli.rs that had the same wrong assumption baked in. Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com>
147 lines
6.9 KiB
Nix
147 lines
6.9 KiB
Nix
{
|
|
description = "invoiceninja-cli: a command-line client for the Invoice Ninja v5 API";
|
|
|
|
# Mirrors invoiceninja-nixos's own nixConfig: without this, building
|
|
# `nixosConfigurations.invoiceninja-test-*` here rebuilds the whole PHP/UI
|
|
# app (and its chromium-headless-shell closure) from source instead of
|
|
# pulling the cached result.
|
|
nixConfig = {
|
|
extra-substituters = [ "https://invoiceninja-nixos.cachix.org" ];
|
|
extra-trusted-public-keys = [
|
|
"invoiceninja-nixos.cachix.org-1:TmRZaji8FFVjjIw9KZmvLrxMxfP+JDThOyOX04z526A="
|
|
];
|
|
};
|
|
|
|
inputs = {
|
|
nixpkgs.url = "github:NixOS/nixpkgs/nixos-unstable";
|
|
rust-overlay.url = "github:oxalica/rust-overlay";
|
|
rust-overlay.inputs.nixpkgs.follows = "nixpkgs";
|
|
flake-utils.url = "github:numtide/flake-utils";
|
|
# For a real Invoice Ninja instance to test the CLI against — see
|
|
# CLAUDE.md's "Testing against a real server". Not `follows`-ed to this
|
|
# flake's own `nixpkgs`: it pins its own (nixos-26.05, as of writing),
|
|
# and `nixosConfigurations.test-nginx`/`test-caddy` below are consumed
|
|
# as already-built flake outputs, not re-evaluated against our
|
|
# nixos-unstable — the two never need to agree.
|
|
invoiceninja-nixos.url = "git+ssh://gitea@gitea.awkawb.cloud/awkawb/invoiceninja-nixos.git";
|
|
};
|
|
|
|
outputs = { self, nixpkgs, rust-overlay, flake-utils, invoiceninja-nixos, ... }:
|
|
let
|
|
cargoToml = builtins.fromTOML (builtins.readFile ./Cargo.toml);
|
|
|
|
# Shared between `packages.default` (built below with the pinned
|
|
# rust-overlay toolchain, for parity with `nix develop`) and
|
|
# `overlays.default` (built with whatever `rustPlatform` the
|
|
# *consuming* nixpkgs provides, per the usual nixpkgs packaging
|
|
# convention — see the note on `overlays.default` below). Takes its
|
|
# inputs as a plain attrset so both call sites, and `callPackage`,
|
|
# can hand it the pieces however they're sourced.
|
|
mkInvoiceninjaCli = { lib, rustPlatform, pkg-config, openssl }:
|
|
rustPlatform.buildRustPackage {
|
|
pname = "invoiceninja-cli";
|
|
version = cargoToml.package.version;
|
|
src = self;
|
|
cargoLock.lockFile = ./Cargo.lock;
|
|
nativeBuildInputs = [ pkg-config ];
|
|
buildInputs = [ openssl ];
|
|
|
|
meta = {
|
|
description = cargoToml.package.description;
|
|
license = lib.licenses.mit;
|
|
mainProgram = "invoiceninja-cli";
|
|
platforms = lib.platforms.unix;
|
|
};
|
|
};
|
|
in
|
|
flake-utils.lib.eachDefaultSystem (system:
|
|
let
|
|
pkgs = import nixpkgs {
|
|
inherit system;
|
|
overlays = [ rust-overlay.overlays.default ];
|
|
};
|
|
|
|
# Kept in step with invoiceninjars-sdk's own `devVersion`, so the two
|
|
# sibling crates build with the same toolchain during development.
|
|
devVersion = "1.99.1";
|
|
|
|
rustToolchain = pkgs.rust-bin.stable.${devVersion}.default.override {
|
|
extensions = [ "rust-src" "rust-analyzer" "clippy" "rustfmt" ];
|
|
};
|
|
|
|
# Built with the pinned dev toolchain, not nixpkgs' own rustc, so a
|
|
# `nix build` matches what `nix develop` compiles with.
|
|
rustPlatform = pkgs.makeRustPlatform {
|
|
cargo = rustToolchain;
|
|
rustc = rustToolchain;
|
|
};
|
|
in
|
|
{
|
|
devShells.default = pkgs.mkShell {
|
|
# jq is for parsing the /api/v1/login response when testing
|
|
# against a real server — see CLAUDE.md's "Testing against a
|
|
# real server".
|
|
packages = [ rustToolchain pkgs.pkg-config pkgs.openssl pkgs.jq ];
|
|
RUST_SRC_PATH = "${rustToolchain}/lib/rustlib/src/rust/library";
|
|
};
|
|
|
|
# Unlike invoiceninjars-sdk, this crate has a `[[bin]]` target, so
|
|
# `nix build` produces an installable binary, not just a test gate.
|
|
# `invoiceninja-sdk` resolves from crates.io (see Cargo.toml), so
|
|
# unlike before this no longer needs a `../invoiceninjars-sdk`
|
|
# checkout to be present in the sandbox.
|
|
packages.default = mkInvoiceninjaCli {
|
|
inherit (pkgs) lib pkg-config openssl;
|
|
inherit rustPlatform;
|
|
};
|
|
|
|
# Automated: boots a real Invoice Ninja instance (invoiceninja-nixos's
|
|
# module, not a mock) and runs actual `invoiceninja-cli` commands
|
|
# against it — create/list/get/update/delete across clients,
|
|
# invoices, and payments, including that `update` preserves fields
|
|
# it wasn't told about. `tests/` is a vendored, adapted copy of
|
|
# invoiceninja-nixos's own test scaffolding; see its
|
|
# nixos-test.nix for what it does and doesn't check (it
|
|
# deliberately skips things like PDF generation and the language-
|
|
# list regression, which are that repo's own concern, not this
|
|
# CLI's). Uses invoiceninja-nixos's own pinned nixpkgs (26.05), not
|
|
# this flake's nixos-unstable, to build+evaluate the VM/module —
|
|
# matches what that module was actually tested against. The CLI
|
|
# binary itself (`self.packages.${system}.default`, built against
|
|
# our own nixos-unstable) runs fine inside it regardless: Nix
|
|
# binaries carry their own closure, so differing nixpkgs revisions
|
|
# in the same system closure is an explicitly supported case, not a
|
|
# version mismatch to work around.
|
|
checks.invoiceninja-cli = import ./tests/nixos-test.nix {
|
|
nixpkgsPath = invoiceninja-nixos.inputs.nixpkgs;
|
|
inherit system;
|
|
invoiceninjaModule = invoiceninja-nixos.nixosModules.invoiceninja;
|
|
invoiceninjaCliPkg = self.packages.${system}.default;
|
|
};
|
|
}) // {
|
|
# For a flake that wants `invoiceninja-cli` in its own `pkgs`, not for
|
|
# this flake's own `packages.default`/`devShells.default` above (those
|
|
# keep the pinned rust-overlay toolchain). `callPackage` resolves
|
|
# `rustPlatform` from the *consuming* nixpkgs, which means it builds
|
|
# with whatever rustc that channel ships — this crate's `rust-version
|
|
# = "1.88"` in Cargo.toml has to be met there too, same as any other
|
|
# nixpkgs Rust package; this overlay doesn't carry the rust-overlay
|
|
# pin along with it.
|
|
overlays.default = final: _prev: {
|
|
invoiceninja-cli = final.callPackage mkInvoiceninjaCli { };
|
|
};
|
|
|
|
# Real Invoice Ninja instances to test this CLI against, reusing
|
|
# invoiceninja-nixos's own test VMs as-is rather than redefining them
|
|
# here — same principle as this crate being a client of the SDK, not
|
|
# a second implementation of it. Known test credentials baked into
|
|
# that repo's tests/common.nix: admin@email.com / password (from
|
|
# tests/invoice_ninja_test_password). See CLAUDE.md for how to boot
|
|
# one and get an API token from it.
|
|
nixosConfigurations = {
|
|
invoiceninja-test-nginx = invoiceninja-nixos.nixosConfigurations.test-nginx;
|
|
invoiceninja-test-caddy = invoiceninja-nixos.nixosConfigurations.test-caddy;
|
|
};
|
|
};
|
|
}
|