Skip to content

Conversation

zimbatm
Copy link
Member

@zimbatm zimbatm commented Jul 21, 2025

Motivation

In this POC I'm exploring how we could convert linting rules from documentation to code.

There is prior art such as nixpkgs-vet, nixpkgs-hammer, etc... The difference here is that the rules would live in rule files, sitting in nixpkgs. By having them here, it makes it easy to understand, discuss and evolve them alongside the code.

ast-grep is a tool that allows doing just that for any language that can be parsed with tree-sitter. That means we can also use it to set rules for accompanying Bash and Python scripts. Another nice thing is the support for auto-fixing rules, if the rule author can express the fix automatically.

In this POC I just put down the base structure to demonstrate the capabilities. Something production-ready would also integrate with the CI, linting only the changed files, and post comments for errors it encounters.

Before moving further, I'd like to get some feedback. I am not aware of all the ongoing plans and how this would fit in the big picture. /cc @NixOS/nixpkgs-ci team and also @SuperSandro2000 that cares about linting a lot.

Things done

  • Built on platform:
    • x86_64-linux
    • aarch64-linux
    • x86_64-darwin
    • aarch64-darwin
  • Tested, as applicable:
  • Ran nixpkgs-review on this PR. See nixpkgs-review usage.
  • Tested basic functionality of all binary files, usually in ./result/bin/.
  • Nixpkgs Release Notes
    • Package update: when the change is major or breaking.
  • NixOS Release Notes
    • Module addition: when adding a new NixOS module.
    • Module update: when the change is significant.
  • Fits CONTRIBUTING.md, pkgs/README.md, maintainers/README.md and other READMEs.

Add a 👍 reaction to pull requests you find important.

@nixpkgs-ci nixpkgs-ci bot added 2.status: merge conflict This PR has merge conflicts with the target branch 10.rebuild-linux: 1-10 This PR causes between 1 and 10 packages to rebuild on Linux. 10.rebuild-darwin: 1-10 This PR causes between 1 and 10 packages to rebuild on Darwin. labels Jul 21, 2025
@wolfgangwalther
Copy link
Contributor

wolfgangwalther commented Jul 21, 2025

I did some experiments with ast-grep as well, while refactoring substituteAll to replaceVars, see https://github.com/technowledgy/refactor-tractor. The rules I used there are also auto-fixing.

You already mentioned that ast-grep can parse other code, too. Most importantly, it's possible to set up language injections, for example for bash code. There is a very limited example for some special cases here: technowledgy/refactor-tractor@200fc18. This means, it would be possible to lint the bash code inside nix expressions, too.

There is prior art such as nixpkgs-vet, nixpkgs-hammer, etc... The difference here is that the rules would live in rule files, sitting in nixpkgs. By having them here, it makes it easy to understand, discuss and evolve them alongside the code.

Having linting rules live in files inside the nixpkgs repo is certainly a big plus, I think. On the flip side, I think this would probably not be able to replace any of the existing tools: Certainly not treefmt / nixfmt. But also not nixpkgs-vet, because this implements some rules that are impossible to express in ast-grep: Stuff like where the files are created, where relative paths point (not outside the by-name folder) etc.

Personally, I think ast-grep's biggest value is in the ability to do ad-hoc stuff. To experiment. To codify treewides. To do migrations from one pattern to another.

That being said, I could still imagine something where we add another ast-grep job to CI. This would allow people to experiment and codify certain rules. Imho, the goal should then be to move those rules to nixpkgs-vet once they have been stabilized.

Although I already see one example in this PR of a rule, that I would not like to have in nixpkgs-vet / any other repo: Everything that refers to specific attributes in nixpkgs and keeps a list of those, should stay in-tree forever. Otherwise, we're moving into what cabal2nix currently does, and that's really annoying to deal with. Ofc, we could also do that with config files for nixpkgs-vet.

@zimbatm
Copy link
Member Author

zimbatm commented Jul 21, 2025

Makes sense.

What you say about using ast-grep as a tree-wide rewrite tool also resonates with me. With some more documenataion I can see how this could be used more widely.

@wolfgangwalther
Copy link
Contributor

Yeah, I think a framework for how to use this quickly and efficiently in nixpkgs, and some nixpkgs-specific documentation would help big-time. So many treewides are written with simple sed replacements, where ast-grep would be so much better.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
2.status: merge conflict This PR has merge conflicts with the target branch 10.rebuild-darwin: 1-10 This PR causes between 1 and 10 packages to rebuild on Darwin. 10.rebuild-linux: 1-10 This PR causes between 1 and 10 packages to rebuild on Linux.
Projects
None yet
Development

Successfully merging this pull request may close these issues.

2 participants