flk

Crates.ioflk
lib.rsflk
version0.5.2
created_at2025-10-28 12:59:46.346988+00
updated_at2026-01-22 14:46:16.061254+00
descriptionA CLI tool for managing flake.nix devShell environments
homepagehttps://github.com/AEduardo-dev/flk
repositoryhttps://github.com/AEduardo-dev/flk
max_upload_size
id1904741
size302,546
Angel Eduardo Vega Conde (AEduardo-dev)

documentation

https://docs.rs/flk

README

flk ๐Ÿš€

A modern CLI tool for managing Nix flake development environments with the simplicity of Devbox

Crates.io License: MIT Rust

flk makes managing Nix flakes feel like using a package manager. No more manually editing flake.nix filesโ€”just use simple commands to add packages, create custom shell commands, and manage your development environment with ease.

โœจ Features

  • ๐ŸŽฏ Smart Initialization - Auto-detects your project type (Rust, Python, Node.js, Go) and creates the right template
  • ๐Ÿ” Package Search - Search nixpkgs directly from your terminal
  • ๐Ÿ“ฆ Easy Package Management - Add and remove packages with simple commands
  • โšก Custom Shell Commands - Define reusable commands for your development workflow
  • ๐ŸŒ Environment Variables - Manage environment variables through the CLI
  • ๐Ÿ”’ Lock File Management - View, backup, and restore your flake.lock with ease
  • ๐ŸŽจ Language Templates - Pre-configured templates for popular languages and frameworks

๐Ÿ“ฆ Installation

Upgrading to v0.5.0 (switch/refresh changes)

WARNING (pre v0.5.0 users): If you are using flk < v0.5.0 and you run flk update / nix flake update, your devshell switch / refresh behavior may break because the nix-profile-lib input may update to a newer version with different activation semantics.

If you intend to stay on flk < v0.5.0, use one of these options:

  1. Do not update flake inputs. Avoid running flk update or nix flake update. If you already did, restore a previous lockfile backup with:

    flk lock restore <BACKUP>
    
  2. Pin nix-profile-lib to v0.1.0. In your flake.nix:

    inputs = {
      nix-profile-lib.url = "github:AEduardo-dev/nix-profile-lib?ref=v0.1.0";
    };
    

    Then update the lock entry:

    nix flake lock --update-input nix-profile-lib
    

    (or nix flake update --update-input nix-profile-lib)

Once you upgrade to flk v0.5.0+, this restriction is lifted.

Prerequisites

  • Nix with flakes enabled
    • We recommend the Lix package manager for easy Nix installation: Lix since it comes with flakes enabled by default.
    • Or using the Determinate System installer: Determinate, as it provides a user-friendly way to install (and uninstall) Nix.
  • Rust 1.83+ (if building from source)

Hooks

If you would like to use hot reloading and switching features, you will need to add the following shell hook to your shell configuration file (~/.bashrc, ~/.zshrc, etc.):

Example for bash:

# flk shell hook
if command -v flk &> /dev/null; then
  eval "$(flk hook bash)"
fi

Support for other shells (zsh and fish) is also available via flk hook <shell>.

From Source

git clone https://github.com/AEduardo-dev/flk.git
cd flk
cargo build --release
sudo cp target/release/flk /usr/local/bin/

From Cargo (crates.io)

cargo install flk

From Release Binaries

  1. Go to https://github.com/AEduardo-dev/flk/releases
  2. Download the archive for your OS/arch (Linux x86_64, macOS Intel, macOS ARM).
  3. Unpack and place flk in your PATH.

Nix (with Cachix binaries)

This flake is prebuilt and published to Cachix.

  1. Install Cachix (once):
nix profile install nixpkgs#cachix
  1. Trust the cache:
cachix use flk-cache

or add the following substituters and trusted-public-keys to your nix.conf content:

substituters = https://flk-cache.cachix.org  ...
trusted-public-keys = flk-cache.cachix.org-1:6xobbpP9iIK5sIH/75DQrsJYKN/61nTOChcH9MJnBR0=  ...
  1. Use the flake:
  • Run (no install): nix run github:AEduardo-dev/flk#flk
  • Install to your profile: nix profile install github:AEduardo-dev/flk#flk

Nix โ€“ Using as a flake input

You can consume flk from another flake either directly or via the overlay.

Direct (no overlay):

{
  description = "My NixOS config with flk";

  inputs = {
    nixpkgs.url = "github:NixOS/nixpkgs/nixos-unstable";
    flk.url = "github:AEduardo-dev/flk";
  };

  outputs = { self, nixpkgs, flk, ... }:
    let
      system = "x86_64-linux"; # set per host
      pkgs = import nixpkgs { inherit system; };
    in {
      nixosConfigurations.myhost = nixpkgs.lib.nixosSystem {
        inherit system;
        modules = [
          {
            environment.systemPackages = [
              flk.packages.${system}.flk
            ];
          }
        ];
      };
    };
}

With overlay (exposes pkgs.flk):

{
  inputs.nixpkgs.url = "github:NixOS/nixpkgs/nixos-unstable";
  inputs.flk.url = "github:AEduardo-dev/flk";

  outputs = { self, nixpkgs, flk, ... }:
    let
      system = "x86_64-linux"; # set per host

      pkgs = import nixpkgs {
        inherit system;
        overlays = [ flk.overlay ];
      };
    in {
      nixosConfigurations.myhost = nixpkgs.lib.nixosSystem {
        inherit system;
        modules = [
          { environment.systemPackages = [ pkgs.flk ]; }
        ];
      };
    };
}

Home Manager example (per-user install via flake):

{
  inputs.flk.url = "github:AEduardo-dev/flk";

  outputs = { self, flk, ... }: {
    homeConfigurations.myhost = {
      # ...
      home.packages = [ flk.packages.${system}.flk ];
    };
  };
}

Architectures covered by the cache

  • x86_64-linux
  • x86_64-darwin
  • aarch64-darwin
  • aarch64-linux (built via qemu on CI; may be slower/occasional misses)

Other architectures will fall back to building from source.

๐Ÿš€ Quick Start

1. Initialize Your Project

# Auto-detect project type and create flake.nix
flk init

# Or specify a template
flk init --template rust
flk init --template python
flk init --template node
flk init --template go

Supported auto-detection:

  • Cargo.toml โ†’ Rust template
  • package.json โ†’ Node.js template
  • pyproject.toml or requirements.txt โ†’ Python template
  • go.mod โ†’ Go template

2. Add Packages

# Search for packages
flk search ripgrep

# Get detailed package info and versions
flk deep-search ripgrep

# Add packages to your environment
flk add ripgrep
flk add git
flk add neovim

# Or add pinned versions
flk add ripgrep --version '15.1.0'
flk add git --version '2.42.0'

3. Add Custom Commands

# Add inline commands
flk command add test "cargo test --all"
flk command add dev "npm run dev"

4. Manage Environment Variables

# Add environment variables
flk env add DATABASE_URL "postgresql://localhost/mydb"
flk env add API_KEY "your-api-key"

# List all environment variables
flk env list

# Remove an environment variable
flk env remove API_KEY

5. Enter Your Development Environment

flk activate

Your custom commands and environment variables will be automatically available!

6. Generate completions

# Generates the completion file and prints it
flk completions

# Install the generated completions to the detected shell
flk completions --install

Follow the instructions after the command to make the completions available for you.

7. Attach to your direnv (optional)

If you use direnv, you can set it up to automatically load your flk environment when you enter the project directory.

# Generates a .envrc file for direnv with use flake command
flk direnv init

#or

# Add the direnv hook to an existing project
flk direnv attach

if you ever want to detach the direnv hook, you can run:

flk direnv detach

8. Switch / Refresh your environment

switch <profile_name>  # Switch to a different profile_name
refresh                # Refresh the current profile (useful after modifying the environment)

๐Ÿ“– Command Reference

Project Management

flk init [OPTIONS]

Initialize a new flake.nix in the current directory.

Options:

  • -t, --template <TYPE> - Project type: rust, python, node, go, or generic
  • -f, --force - Overwrite existing flake.nix

Examples:

flk init                    # Auto-detect project type
flk init --template rust    # Use Rust template
flk init --force            # Overwrite existing flake.nix

flk activate

Activate the nix shell for the current shell session. This command sets up the necessary environment for your project based on the flake.nix configuration. It also installs some convenience features, such as a shell hook to refresh.

Future implementations will include the option to activate specific profiles.

flk show

Display the contents and configuration of your flake.nix in a human-readable format.

flk show

flk list

List all packages in your development environment.

flk list

Package Management

flk search <QUERY> [OPTIONS]

Search for packages in nixpkgs.

Options:

  • -l, --limit <NUMBER> - Limit number of results (default: 10)

Examples:

flk search ripgrep
flk search python --limit 20

flk deep-search <PACKAGE> [OPTIONS]

Get detailed information about a specific package.

Examples:

flk deep-search ripgrep
flk deep-search python311
```

#### `flk add <PACKAGE>`

Add a package to your `flake.nix`.

**Examples:**

```bash
flk add ripgrep
flk add git
flk add nodejs

Or add a specific version:

flk add ripgrep --version '15.1.0'
flk add git --version '2.42.0'

flk remove <PACKAGE>

Remove a package from your flake.nix.

Examples:

flk remove ripgrep

Custom Commands

flk command add <NAME> <COMMAND> [OPTIONS]

Add a custom shell command to your development environment.

Examples:

# Inline command
flk command add test "cargo test --all"
flk command add dev "npm run dev -- --watch"

# Multi-line command
flk command add deploy "cargo build --release && scp target/release/app server:/opt/"

Command naming rules:

  • Must contain only letters, numbers, hyphens, and underscores
  • Cannot start with a hyphen
  • Examples: test, dev-server, build_prod

flk command remove <NAME>

Remove a custom command from your dev shell.

Examples:

flk command remove test

Environment Variables

flk env add <NAME> <VALUE>

Add an environment variable to your dev shell.

Examples:

flk env add DATABASE_URL "postgresql://localhost:5432/mydb"
flk env add NODE_ENV "development"
flk env add API_KEY "sk-..."

Variable naming rules:

  • Must start with a letter or underscore
  • Can only contain letters, numbers, and underscores
  • Examples: MY_VAR, _private, API_KEY_2

flk env remove <NAME>

Remove an environment variable from your dev shell.

Examples:

flk env remove DATABASE_URL

flk env list

List all environment variables in your dev shell.

flk env list

Lock File Management

flk lock show

Display detailed information about your flake.lock file.

flk lock show

flk lock history

Show backup history of your lock file.

flk lock history

flk lock restore <BACKUP>

Restore a previous version of your lock file.

Examples:

flk lock restore latest                    # Restore most recent backup
flk lock restore 2025-01-27_14-30-00      # Restore specific backup

Updates

flk update [OPTIONS]

Update all flake inputs to their latest versions.

Options:

  • --show - Preview updates without applying them

Examples:

flk update              # Update all inputs
flk update --show       # Preview available updates

Note: A backup of your flake.lock is automatically created before updating.

Exports

flk export --format <FORMAT> [OPTIONS]

Export the current flake configuration to different formats. Options:

  • --format <FORMAT> - Export format: docker, podman, json

Examples:

flk export --format docker     # Export as Dockerfile
flk export --format podman     # Export as Podmanfile
flk export --format json       # Export as JSON

Direnv Integration

flk direnv init

Generate a .envrc file for direnv with use flake command.

flk direnv init

flk direnv attach

Add the direnv hook to an existing project.

flk direnv attach

flk direnv detach

Remove the direnv hook from the project.

flk direnv detach

๐Ÿ’ก Usage Examples

Python Data Science Environment

flk init --template python
flk add python312Packages.numpy
flk add python312Packages.pandas
flk add python312Packages.matplotlib
flk add jupyter

flk command add notebook "jupyter notebook --port=8888"
flk env add JUPYTER_CONFIG_DIR "./.jupyter"

flk activate
notebook  # Your custom command is ready!

Rust Web Development

flk init --template rust
flk add postgresql
flk add redis

flk command add dev "cargo watch -x run"
flk command add migrate "sqlx migrate run"
flk env add DATABASE_URL "postgresql://localhost/myapp"

flk activate
dev      # Start development server with auto-reload
migrate  # Run database migrations

Node.js Full-Stack Project

flk init --template node
flk add postgresql
flk add docker-compose

flk command add dev "npm run dev"
flk command add db "docker-compose up -d postgres"
flk env add NODE_ENV "development"

flk activate
db   # Start database
dev  # Start development server

Go Microservice

flk init --template go
flk add protobuf
flk add grpcurl

flk command add build "go build -o bin/service ./cmd/service"
flk command add proto "protoc --go_out=. --go-grpc_out=. api/*.proto"
flk env add GO_ENV "development"

flk activate
proto  # Generate protobuf code
build  # Build the service

๐Ÿ› ๏ธ Development

Prerequisites

  • Rust 1.83+
  • Nix with flakes enabled

Building

git clone https://github.com/AEduardo-dev/flk.git
cd flk
cargo build

Running Tests

# Run all tests
cargo test

# Run unit tests only
cargo test --test unit_tests

# Run integration tests only
cargo test --test integration_tests

# Run with output
cargo test -- --nocapture

# Run a specific test
cargo test test_name

The test suite includes comprehensive unit tests for the parser, generator, and interface modules, as well as integration tests covering the complete CLI workflow including the dendritic . flk/profiles/ architecture.

Installing Locally

cargo install --path .

๐Ÿ—๏ธ Project Structure


๎—ฟ .
โ”œโ”€โ”€ ๎š‹ Cargo.lock
โ”œโ”€โ”€ ๎š‹ Cargo.toml
โ”œโ”€โ”€ ๏‡ช CHANGELOG.md
โ”œโ”€โ”€ ๎šฒ cliff.toml
โ”œโ”€โ”€ ๏’ฎ CODE_OF_CONDUCT.md
โ”œโ”€โ”€ ๏’Š CONTRIBUTING.md
โ”œโ”€โ”€ ๎šฒ dist-workspace.toml
โ”œโ”€โ”€ ๏Œ“ flake.lock
โ”œโ”€โ”€ ๏Œ“ flake.nix
โ”œโ”€โ”€ ๏€ญ LICENSE
โ”œโ”€โ”€ ๓ฐ‚บ README.md
โ”œโ”€โ”€ ๎šฒ release-plz.toml
โ”œโ”€โ”€ ๓ฐฃž src
โ”‚   โ”œโ”€โ”€ ๎—ฟ commands
โ”‚   โ”‚   โ”œโ”€โ”€ ๎š‹ activate.rs
โ”‚   โ”‚   โ”œโ”€โ”€ ๎š‹ add.rs
โ”‚   โ”‚   โ”œโ”€โ”€ ๎š‹ command.rs
โ”‚   โ”‚   โ”œโ”€โ”€ ๎š‹ completions.rs
โ”‚   โ”‚   โ”œโ”€โ”€ ๎š‹ direnv.rs
โ”‚   โ”‚   โ”œโ”€โ”€ ๎š‹ env.rs
โ”‚   โ”‚   โ”œโ”€โ”€ ๎š‹ export.rs
โ”‚   โ”‚   โ”œโ”€โ”€ ๎š‹ init.rs
โ”‚   โ”‚   โ”œโ”€โ”€ ๎š‹ list.rs
โ”‚   โ”‚   โ”œโ”€โ”€ ๎š‹ lock.rs
โ”‚   โ”‚   โ”œโ”€โ”€ ๎š‹ mod.rs
โ”‚   โ”‚   โ”œโ”€โ”€ ๎š‹ remove.rs
โ”‚   โ”‚   โ”œโ”€โ”€ ๎š‹ search.rs
โ”‚   โ”‚   โ”œโ”€โ”€ ๎š‹ show.rs
โ”‚   โ”‚   โ””โ”€โ”€ ๎š‹ update.rs
โ”‚   โ”œโ”€โ”€ ๎—ฟ flake
โ”‚   โ”‚   โ”œโ”€โ”€ ๎š‹ generator.rs
โ”‚   โ”‚   โ”œโ”€โ”€ ๎—ฟ interfaces
โ”‚   โ”‚   โ”‚   โ”œโ”€โ”€ ๎š‹ mod.rs
โ”‚   โ”‚   โ”‚   โ”œโ”€โ”€ ๎š‹ overlays.rs
โ”‚   โ”‚   โ”‚   โ”œโ”€โ”€ ๎š‹ profiles.rs
โ”‚   โ”‚   โ”‚   โ”œโ”€โ”€ ๎š‹ shellhooks.rs
โ”‚   โ”‚   โ”‚   โ””โ”€โ”€ ๎š‹ utils.rs
โ”‚   โ”‚   โ”œโ”€โ”€ ๎š‹ mod.rs
โ”‚   โ”‚   โ”œโ”€โ”€ ๎š‹ nix_render.rs
โ”‚   โ”‚   โ””โ”€โ”€ ๎—ฟ parsers
โ”‚   โ”‚       โ”œโ”€โ”€ ๎š‹ commands.rs
โ”‚   โ”‚       โ”œโ”€โ”€ ๎š‹ env.rs
โ”‚   โ”‚       โ”œโ”€โ”€ ๎š‹ flake.rs
โ”‚   โ”‚       โ”œโ”€โ”€ ๎š‹ mod.rs
โ”‚   โ”‚       โ”œโ”€โ”€ ๎š‹ overlays.rs
โ”‚   โ”‚       โ”œโ”€โ”€ ๎š‹ packages.rs
โ”‚   โ”‚       โ””โ”€โ”€ ๎š‹ utils.rs
โ”‚   โ”œโ”€โ”€ ๎š‹ lib.rs
โ”‚   โ”œโ”€โ”€ ๎š‹ main.rs
โ”‚   โ”œโ”€โ”€ ๎—ฟ nix
โ”‚   โ”‚   โ””โ”€โ”€ ๎š‹ mod.rs
โ”‚   โ””โ”€โ”€ ๎—ฟ utils
โ”‚       โ”œโ”€โ”€ ๎š‹ backup.rs
โ”‚       โ”œโ”€โ”€ ๎š‹ mod.rs
โ”‚       โ””โ”€โ”€ ๎š‹ visual.rs
โ”œโ”€โ”€ ๎—ฟ templates
โ”‚   โ”œโ”€โ”€ ๏Œ“ default.nix
โ”‚   โ”œโ”€โ”€ ๏Œ“ flake.nix
โ”‚   โ”œโ”€โ”€ ๏Œ“ overlays.nix
โ”‚   โ”œโ”€โ”€ ๏Œ“ pins.nix
โ”‚   โ””โ”€โ”€ ๎—ฟ profiles
โ”‚       โ”œโ”€โ”€ ๏Œ“ base.nix
โ”‚       โ”œโ”€โ”€ ๏Œ“ default.nix
โ”‚       โ”œโ”€โ”€ ๏Œ“ go.nix
โ”‚       โ”œโ”€โ”€ ๏Œ“ node.nix
โ”‚       โ”œโ”€โ”€ ๏Œ“ python.nix
โ”‚       โ””โ”€โ”€ ๏Œ“ rust.nix
โ”œโ”€โ”€ ๎—ฟ tests
โ”‚   โ”œโ”€โ”€ ๏Œ“ flake_tests.nix
โ”‚   โ”œโ”€โ”€ ๎š‹ integration_tests.rs
โ”‚   โ”œโ”€โ”€ ๏Œ“ pins_tests.nix
โ”‚   โ”œโ”€โ”€ ๏Œ“ profile_tests.nix
โ”‚   โ””โ”€โ”€ ๎š‹ unit_tests.rs
โ””โ”€โ”€ ๎—ฟ wix
    โ””โ”€โ”€ ๏…› main.wxs

๐Ÿ—บ๏ธ Roadmap

Roadmap

๐Ÿค Contributing

Contributions are welcome! Please feel free to submit a Pull Request. For major changes, please open an issue first to discuss what you would like to change.

How to Contribute

  1. Fork the repository
  2. Create your feature branch (git checkout -b feature/amazing-feature)
  3. Commit your changes (git commit -m 'Add some amazing feature')
  4. Push to the branch (git push origin feature/amazing-feature)
  5. Open a Pull Request

๐Ÿ› Bug Reports

If you find a bug, please open an issue with:

  • A clear description of the problem
  • Steps to reproduce
  • Expected vs actual behavior
  • Your environment (OS, Nix version, etc.)

๐Ÿ”— Related Projects

  • Devbox - Instant, portable dev environments (inspiration for flk)
  • devenv - Fast, declarative developer environments
  • Flox - Developer environments you can take with you
  • direnv - Shell extension for loading environments

๐Ÿ“„ License

This project is licensed under the MIT License - see the LICENSE file for details.

๐Ÿ™ Acknowledgments

  • The Nix community for creating an amazing ecosystem
  • Jetify for the Devbox inspiration and showing what's possible
  • All contributors and users of flk
  • Special mention to @vic for creating nix-versions

๐Ÿ“ž Support

  • ๐Ÿ“ง Open an issue for bug reports or feature requests
  • ๐Ÿ’ฌ Start a discussion for questions or ideas
  • โญ Star the repository if you find it useful!

Made with โค๏ธ by AEduardo-dev

Note: This project is under active development. While all core features are implemented and working, some advanced features are still in progress and will be subject to change.

Commit count: 235

cargo fmt