#!/bin/bash # Cursor Rules Generator CLI # Based on PageAI tutorial: https://pageai.pro/blog/cursor-rules-tutorial set -e PROJECT_ROOT="$(cd "$(dirname "${BASH_SOURCE[0]}")/.." && pwd)" SCRIPT_DIR="$PROJECT_ROOT/scripts" GENERATOR_SCRIPT="$SCRIPT_DIR/generate_cursor_rules.py" # Colors for output RED='\033[0;31m' GREEN='\033[0;32m' YELLOW='\033[1;33m' BLUE='\033[0;34m' NC='\033[0m' # No Color # Function to print colored output print_info() { echo -e "${BLUE}ℹ️ $1${NC}" } print_success() { echo -e "${GREEN}✅ $1${NC}" } print_warning() { echo -e "${YELLOW}⚠️ $1${NC}" } print_error() { echo -e "${RED}❌ $1${NC}" } # Function to show usage show_usage() { cat << EOF Cursor Rules Generator Usage: $0 [OPTIONS] [DIRECTORIES...] OPTIONS: -h, --help Show this help message -a, --analyze Analyze existing rules and suggest improvements -g, --generate Generate rules for specified directories -t, --type TYPE Rule type (python, javascript, testing, generic) -f, --force Overwrite existing rules -v, --verbose Verbose output DIRECTORIES: List of directories to analyze (e.g., src tests scripts) EXAMPLES: $0 --generate src tests # Generate rules for src and tests $0 --generate --type python src # Generate Python-specific rules $0 --analyze # Analyze existing rules $0 --generate --force src # Force overwrite existing rules EOF } # Function to check dependencies check_dependencies() { if ! command -v python3 &> /dev/null; then print_error "Python 3 is required but not installed" exit 1 fi if [[ ! -f "$GENERATOR_SCRIPT" ]]; then print_error "Generator script not found: $GENERATOR_SCRIPT" exit 1 fi } # Function to analyze existing rules analyze_rules() { print_info "Analyzing existing Cursor rules..." RULES_DIR="$PROJECT_ROOT/.cursor/rules" if [[ ! -d "$RULES_DIR" ]]; then print_warning "No .cursor/rules directory found" return fi echo echo "📊 Current Rules Analysis" echo "========================" # Count rules by type total_rules=$(find "$RULES_DIR" -name "*.mdc" | wc -l) always_apply=$(grep -r "alwaysApply: true" "$RULES_DIR" | wc -l) domain_specific=$(find "$RULES_DIR" -name "*.mdc" -exec grep -l "globs:" {} \; | wc -l) echo "Total rules: $total_rules" echo "Always apply: $always_apply" echo "Domain-specific: $domain_specific" echo echo "📁 Rule Categories:" echo "-------------------" # Categorize rules if [[ -f "$RULES_DIR/project-structure.mdc" ]]; then echo "✅ Project Structure (comprehensive)" else echo "❌ Project Structure (missing)" fi if [[ -f "$RULES_DIR/self_improve.mdc" ]]; then echo "✅ Self-Improvement (enabled)" else echo "❌ Self-Improvement (missing)" fi if [[ -f "$RULES_DIR/cursor_rules.mdc" ]]; then echo "✅ Cursor Rules (meta-rule)" else echo "❌ Cursor Rules (missing)" fi # Check for domain-specific rules domain_rules=( "audio-processing.mdc" "database-registry.mdc" "real-file-testing.mdc" "protocol-services.mdc" ) echo echo "🎯 Domain-Specific Rules:" for rule in "${domain_rules[@]}"; do if [[ -f "$RULES_DIR/$rule" ]]; then echo "✅ $rule" else echo "❌ $rule" fi done # Check rule quality echo echo "🔍 Rule Quality Check:" echo "---------------------" for rule_file in "$RULES_DIR"/*.mdc; do if [[ -f "$rule_file" ]]; then rule_name=$(basename "$rule_file") lines=$(wc -l < "$rule_file") # Check for required sections has_frontmatter=$(grep -c "^---" "$rule_file" || echo "0") has_description=$(grep -c "description:" "$rule_file" || echo "0") has_examples=$(grep -c "```" "$rule_file" || echo "0") if [[ $has_frontmatter -ge 2 && $has_description -gt 0 ]]; then echo "✅ $rule_name ($lines lines)" else echo "⚠️ $rule_name ($lines lines) - missing frontmatter" fi fi done } # Function to generate rules generate_rules() { local directories=("$@") local rule_type="${RULE_TYPE:-generic}" local force_flag="" if [[ "$FORCE" == "true" ]]; then force_flag="--force" fi print_info "Generating Cursor rules..." print_info "Rule type: $rule_type" print_info "Directories: ${directories[*]}" # Change to project root cd "$PROJECT_ROOT" # Run the Python generator if [[ "$VERBOSE" == "true" ]]; then python3 "$GENERATOR_SCRIPT" --verbose else python3 "$GENERATOR_SCRIPT" fi print_success "Rule generation completed!" } # Function to validate directories validate_directories() { local directories=("$@") for dir in "${directories[@]}"; do if [[ ! -d "$PROJECT_ROOT/$dir" ]]; then print_error "Directory not found: $dir" exit 1 fi done } # Main script logic main() { # Parse command line arguments GENERATE=false ANALYZE=false RULE_TYPE="generic" FORCE=false VERBOSE=false DIRECTORIES=() while [[ $# -gt 0 ]]; do case $1 in -h|--help) show_usage exit 0 ;; -a|--analyze) ANALYZE=true shift ;; -g|--generate) GENERATE=true shift ;; -t|--type) RULE_TYPE="$2" shift 2 ;; -f|--force) FORCE=true shift ;; -v|--verbose) VERBOSE=true shift ;; -*) print_error "Unknown option: $1" show_usage exit 1 ;; *) DIRECTORIES+=("$1") shift ;; esac done # Check dependencies check_dependencies # Default behavior if no action specified if [[ "$GENERATE" == "false" && "$ANALYZE" == "false" ]]; then if [[ ${#DIRECTORIES[@]} -gt 0 ]]; then GENERATE=true else ANALYZE=true fi fi # Validate rule type case "$RULE_TYPE" in python|javascript|testing|generic) ;; *) print_error "Invalid rule type: $RULE_TYPE" print_info "Valid types: python, javascript, testing, generic" exit 1 ;; esac # Execute requested actions if [[ "$ANALYZE" == "true" ]]; then analyze_rules fi if [[ "$GENERATE" == "true" ]]; then if [[ ${#DIRECTORIES[@]} -eq 0 ]]; then print_warning "No directories specified, using defaults: src tests scripts" DIRECTORIES=("src" "tests" "scripts") fi validate_directories "${DIRECTORIES[@]}" generate_rules "${DIRECTORIES[@]}" fi print_success "Done!" } # Run main function with all arguments main "$@"