trying some new stuff with zig - #71
Merged
Merged
Conversation
Everything that lands in $HOME is a zig build step now. bootstrap.sh is the one link that cannot be zig -- 46 lines of posix sh that fetch a compiler for the host and put it in ~/.local/bin -- and from there `zig build headless` does the rest with no package manager underneath it. build.zig is only a list; each entry in zig/packages/ exports install(env) and owns one thing. Env resolves the install prefix to ~/.local instead of zig-out, so there is nothing to pass on the command line. What zig took over: neovim (upstream's own build.zig), fish (cargo, pinned tarball), the rust toolchain (rustup-init fetched over zig's http client, no curl), lua-language-server, zls and ripgrep (prebuilt releases), the tree-sitter grammars (compiled here, so nvim-treesitter's cli and runtime compiler are not needed), the nvim plugins, the ~/.config symlinks, and the chsh to the fish we just built. The bet underneath all of it is that zig bundles clang, lld, musl and headers for 76 targets, which the distros workflow checks on images with no cc, gcc, make or pkg-config installed. What nix still owns, and only on linux: the bootloader, the filesystems, the users, the services and the desktop. flake.nix is gone with the macbook, which is a Brewfile now, and home-manager went with it -- nvim, fish, git and the symlinks are all packages, so nothing was left for it to configure. common.nix keeps just the floor zig cannot stand on: gcc, because cargo shells out to cc to link; curl and xz for bootstrap; nix-ld, because rustup, cargo and lua-language-server are prebuilt glibc binaries and nixos has no dynamic loader for them; and environment.shells, because /etc/shells is a read-only store symlink there. nvim moved to native lsp and vim.pack, dropped the vendored auto-dark-mode copy for a real light/dark switch, and its themes, plugins, treesitter and ui config are split by concern rather than living in one packages.lua.
Two workflows. ci.yml runs bootstrap.sh and each zig build step on
GitHub's hosted runners -- 6 platforms by 9 packages, plus an
integration job that builds everything and checks that neovim starts,
loads all eight parsers, and reports nothing in :messages.
distros.yml runs the same in bare containers, which is where the
interesting failures are. It is driven with docker run rather than
`container:` because actions/checkout needs a glibc node and alpine
does not have one. One job asserts no cc, gcc, clang, make or
pkg-config exists and then builds the tree-sitter grammars anyway,
which is the load-bearing claim of this repo.
Marked experimental rather than fixed here:
- bootstrap.sh builds a .tar.xz url unconditionally, but zig ships
.zip for windows, so both windows runners fail
- zls and lua-ls publish no musl build, so those alpine cells fail
while ripgrep, which has one, should pass
login-shell is left out of the integration job. chsh wants a PAM
password on linux runners and mutates the machine either way, so the
headless group cannot run unattended as it stands.
GNU tar will not autodetect compression when the archive arrives on stdin -- it stops with "Archive is compressed. Use -J option" -- so every linux runner and every container died before zig was unpacked. bsdtar does autodetect, which is why macOS was the only platform where this worked and why it survived local testing. -J is accepted by GNU tar, bsdtar and busybox tar alike, so naming the decompressor costs nothing and removes the guess. Found by the CI matrix on its first run: 32/32 macOS cells green, every one of the 33 linux cells and all 27 container cells red at the same line.
origin/master carries 9d6d00a "unbreak setup", which touches four files that no longer exist on this branch: nix/common/nvim.nix, nix/flake.nix, nix/flake.lock and nvim/lua/packages.lua. That is a modify/delete conflict on every one of them, which is why the PR showed as CONFLICTING. Nothing in it is lost. The lspconfig.X.setup() to vim.lsp.config() migration it performs is already done here in a different shape -- nvim/lsp/<server>.lua plus vim.lsp.enable() in init.lua -- and the zls and plenary additions are packages in build.zig and nvim_plugins.zig. Only nixd and nil_ls are dropped, deliberately, along with the rest of the nix-owned nvim layer. Recorded with -s ours so the merge states plainly that master was considered and has nothing to contribute, rather than reintroducing files this branch exists to remove.
Parth
marked this pull request as ready for review
August 24, 2026 15:31
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
for more info: https://parth.cafe/gp/shipping-software.html