From d43bb33dcb4ae358dd398166a377f00d96e1f03b Mon Sep 17 00:00:00 2001 From: m3tm3re Date: Tue, 17 Feb 2026 18:59:43 +0100 Subject: [PATCH] feat(lib): add opencode-rules helper for per-project rule injection - Create lib/opencode-rules.nix with mkOpencodeRules function - Update lib/default.nix to import opencode-rules module - Pattern follows ports.nix: {lib}: { mkOpencodeRules = ...; } Refs: T2, T3 of rules-system plan --- lib/default.nix | 8 +-- lib/opencode-rules.nix | 110 +++++++++++++++++++++++++++++++++++++++++ 2 files changed, 114 insertions(+), 4 deletions(-) create mode 100644 lib/opencode-rules.nix diff --git a/lib/default.nix b/lib/default.nix index e6deac0..0168beb 100644 --- a/lib/default.nix +++ b/lib/default.nix @@ -3,10 +3,10 @@ # let # m3taLib = inputs.m3ta-nixpkgs.lib.${system}; # in ... -{lib}: { +{ lib }: { # Port management utilities - ports = import ./ports.nix {inherit lib;}; + ports = import ./ports.nix { inherit lib; }; - # Add more helper modules here as needed - # example = import ./example.nix { inherit lib; }; + # OpenCode rules injection utilities + opencode-rules = import ./opencode-rules.nix { inherit lib; }; } diff --git a/lib/opencode-rules.nix b/lib/opencode-rules.nix new file mode 100644 index 0000000..27834fb --- /dev/null +++ b/lib/opencode-rules.nix @@ -0,0 +1,110 @@ +# Opencode rules management utilities +# +# This module provides functions to configure Opencode agent rules across +# multiple projects. Rules are defined in the AGENTS repository and can be +# selectively included based on language, framework, and concerns. +# +# Usage in your configuration: +# +# # In your flake or configuration: +# let +# m3taLib = inputs.m3ta-nixpkgs.lib.${system}; +# +# rules = m3taLib.opencode-rules.mkOpencodeRules { +# agents = inputs.agents; +# languages = [ "python" "typescript" ]; +# concerns = [ "coding-style" "naming" "documentation" ]; +# frameworks = [ "react" "fastapi" ]; +# }; +# in { +# # Use in your devShell: +# devShells.default = pkgs.mkShell { +# shellHook = rules.shellHook; +# inherit (rules) instructions; +# }; +# } +# +# The shellHook creates: +# - A `.opencode-rules/` symlink pointing to the AGENTS repository rules directory +# - An `opencode.json` file with a $schema reference and instructions list +# +# The instructions list contains paths relative to the project root, all prefixed +# with `.opencode-rules/`, making them portable across different project locations. +{ lib }: { + # Create Opencode rules configuration from AGENTS repository + # + # Args: + # agents: Path to the AGENTS repository (non-flake input) + # languages: Optional list of language-specific rules to include + # (e.g., [ "python" "typescript" "rust" ]) + # concerns: Optional list of concern rules to include + # Default: [ "coding-style" "naming" "documentation" "testing" "git-workflow" "project-structure" ] + # frameworks: Optional list of framework-specific rules to include + # (e.g., [ "react" "fastapi" "django" ]) + # extraInstructions: Optional list of additional instruction paths + # (for custom rules outside standard locations) + # + # Returns: + # An attribute set containing: + # - shellHook: Bash code to create symlink and opencode.json + # - instructions: List of rule file paths (relative to project root) + # + # Example: + # mkOpencodeRules { + # agents = inputs.agents; + # languages = [ "python" ]; + # frameworks = [ "fastapi" ]; + # } + # # Returns: + # # { + # # shellHook = "..."; + # # instructions = [ + # # ".opencode-rules/concerns/coding-style.md" + # # ".opencode-rules/concerns/naming.md" + # # ".opencode-rules/concerns/documentation.md" + # # ".opencode-rules/concerns/testing.md" + # # ".opencode-rules/concerns/git-workflow.md" + # # ".opencode-rules/concerns/project-structure.md" + # # ".opencode-rules/languages/python.md" + # # ".opencode-rules/frameworks/fastapi.md" + # # ]; + # # } + mkOpencodeRules = { agents, languages ? [ ], concerns ? [ + "coding-style" + "naming" + "documentation" + "testing" + "git-workflow" + "project-structure" + ], frameworks ? [ ], extraInstructions ? [ ] }: + let + rulesDir = ".opencode-rules"; + + # Build instructions list by mapping concerns, languages, frameworks to their file paths + # All paths are relative to project root via the rulesDir symlink + instructions = (map (c: "${rulesDir}/concerns/${c}.md") concerns) + ++ (map (l: "${rulesDir}/languages/${l}.md") languages) + ++ (map (f: "${rulesDir}/frameworks/${f}.md") frameworks) + ++ extraInstructions; + + # Generate JSON configuration for Opencode + opencodeConfig = { + "$schema" = "https://opencode.ai/config.json"; + inherit instructions; + }; + in { + inherit instructions; + + # Shell hook to set up rules in the project + # Creates a symlink to the AGENTS rules directory and generates opencode.json + shellHook = '' + # Create/update symlink to AGENTS rules directory + ln -sfn ${agents}/rules ${rulesDir} + + # Generate opencode.json configuration file + cat > opencode.json <<'OPENCODE_EOF' + ${builtins.toJSON opencodeConfig} + OPENCODE_EOF + ''; + }; +}