aidevops 2.56.0 → 2.58.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/README.md CHANGED
@@ -57,7 +57,7 @@ The result: AI agents that work *with* your development process, not around it.
57
57
  [![GitHub commits since latest release](https://img.shields.io/github/commits-since/marcusquinn/aidevops/latest)](https://github.com/marcusquinn/aidevops/commits/main)
58
58
 
59
59
  <!-- Repository Stats -->
60
- [![Version](https://img.shields.io/badge/Version-2.56.0-blue)](https://github.com/marcusquinn/aidevops/releases)
60
+ [![Version](https://img.shields.io/badge/Version-2.58.0-blue)](https://github.com/marcusquinn/aidevops/releases)
61
61
  [![GitHub repo size](https://img.shields.io/github/repo-size/marcusquinn/aidevops?style=flat&color=blue)](https://github.com/marcusquinn/aidevops)
62
62
  [![Lines of code](https://img.shields.io/badge/Lines%20of%20Code-18%2C000%2B-brightgreen)](https://github.com/marcusquinn/aidevops)
63
63
  [![GitHub language count](https://img.shields.io/github/languages/count/marcusquinn/aidevops)](https://github.com/marcusquinn/aidevops)
@@ -870,7 +870,7 @@ Ordered as they appear in OpenCode Tab selector and other AI assistants (14 tota
870
870
 
871
871
  | Name | File | Purpose | MCPs Enabled |
872
872
  |------|------|---------|--------------|
873
- | Plan+ | `plan-plus.md` | Read-only planning with semantic codebase search | context7, augment, repomix |
873
+ | Plan+ | `plan-plus.md` | Planning with semantic search, writes to TODO.md/todo/ | context7, augment, repomix |
874
874
  | Build+ | `build-plus.md` | Enhanced Build with context tools | context7, augment, repomix |
875
875
  | Build-Agent | `build-agent.md` | Design and improve AI agents | context7, augment, repomix |
876
876
  | Build-MCP | `build-mcp.md` | Build MCP servers with TS+Bun+ElysiaJS | context7, augment, repomix |
package/VERSION CHANGED
@@ -1 +1 @@
1
- 2.56.0
1
+ 2.58.0
package/aidevops.sh CHANGED
@@ -3,7 +3,7 @@
3
3
  # AI DevOps Framework CLI
4
4
  # Usage: aidevops <command> [options]
5
5
  #
6
- # Version: 2.56.0
6
+ # Version: 2.58.0
7
7
 
8
8
  set -euo pipefail
9
9
 
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "aidevops",
3
- "version": "2.56.0",
3
+ "version": "2.58.0",
4
4
  "description": "AI DevOps Framework - AI-assisted development workflows, code quality, and deployment automation",
5
5
  "type": "module",
6
6
  "main": "index.js",
package/setup.sh CHANGED
@@ -3,7 +3,7 @@
3
3
  # AI Assistant Server Access Framework Setup Script
4
4
  # Helps developers set up the framework for their infrastructure
5
5
  #
6
- # Version: 2.56.0
6
+ # Version: 2.58.0
7
7
  #
8
8
  # Quick Install (one-liner):
9
9
  # bash <(curl -fsSL https://aidevops.dev/install)
@@ -231,7 +231,7 @@ migrate_loop_state_directories() {
231
231
 
232
232
  # Check for loop state files in old location
233
233
  local has_loop_state=false
234
- if [[ -f "$old_state_dir/ralph-loop.local.md" ]] || \
234
+ if [[ -f "$old_state_dir/ralph-loop.local.state" ]] || \
235
235
  [[ -f "$old_state_dir/loop-state.json" ]] || \
236
236
  [[ -d "$old_state_dir/receipts" ]]; then
237
237
  has_loop_state=true
@@ -245,7 +245,7 @@ migrate_loop_state_directories() {
245
245
  mkdir -p "$new_state_dir"
246
246
 
247
247
  # Move loop-related files
248
- for file in ralph-loop.local.md loop-state.json re-anchor.md guardrails.md; do
248
+ for file in ralph-loop.local.state loop-state.json re-anchor.md guardrails.md; do
249
249
  if [[ -f "$old_state_dir/$file" ]]; then
250
250
  mv "$old_state_dir/$file" "$new_state_dir/"
251
251
  print_info " Moved $file"
@@ -562,6 +562,132 @@ setup_git_clis() {
562
562
  return 0
563
563
  }
564
564
 
565
+ # Setup Worktrunk - Git worktree management for parallel AI agent workflows
566
+ setup_worktrunk() {
567
+ print_info "Setting up Worktrunk (git worktree management)..."
568
+
569
+ # Check if worktrunk (wt) is already installed
570
+ if command -v wt >/dev/null 2>&1; then
571
+ local wt_version
572
+ wt_version=$(wt --version 2>/dev/null | head -1 || echo "unknown")
573
+ print_success "Worktrunk already installed: $wt_version"
574
+
575
+ # Check if shell integration is installed
576
+ local shell_name
577
+ shell_name=$(basename "${SHELL:-/bin/bash}")
578
+ local shell_rc=""
579
+ case "$shell_name" in
580
+ zsh) shell_rc="$HOME/.zshrc" ;;
581
+ bash)
582
+ if [[ "$(uname)" == "Darwin" ]]; then
583
+ shell_rc="$HOME/.bash_profile"
584
+ else
585
+ shell_rc="$HOME/.bashrc"
586
+ fi
587
+ ;;
588
+ esac
589
+
590
+ if [[ -n "$shell_rc" ]] && [[ -f "$shell_rc" ]]; then
591
+ if ! grep -q "worktrunk" "$shell_rc" 2>/dev/null; then
592
+ print_info "Shell integration not detected"
593
+ read -r -p "Install Worktrunk shell integration (enables 'wt switch' to change directories)? (y/n): " install_shell
594
+ if [[ "$install_shell" == "y" ]]; then
595
+ if wt config shell install 2>/dev/null; then
596
+ print_success "Shell integration installed"
597
+ print_info "Restart your terminal or run: source $shell_rc"
598
+ else
599
+ print_warning "Shell integration failed - run manually: wt config shell install"
600
+ fi
601
+ fi
602
+ else
603
+ print_success "Shell integration already configured"
604
+ fi
605
+ fi
606
+ return 0
607
+ fi
608
+
609
+ # Worktrunk not installed - offer to install
610
+ print_info "Worktrunk makes git worktrees as easy as branches"
611
+ echo " • wt switch feat - Switch/create worktree (with cd)"
612
+ echo " • wt list - List worktrees with CI status"
613
+ echo " • wt merge - Squash/rebase/merge + cleanup"
614
+ echo " • Hooks for automated setup (npm install, etc.)"
615
+ echo ""
616
+ echo " Note: aidevops also includes worktree-helper.sh as a fallback"
617
+ echo ""
618
+
619
+ local pkg_manager
620
+ pkg_manager=$(detect_package_manager)
621
+
622
+ if [[ "$pkg_manager" == "brew" ]]; then
623
+ read -r -p "Install Worktrunk via Homebrew? (y/n): " install_wt
624
+
625
+ if [[ "$install_wt" == "y" ]]; then
626
+ print_info "Installing Worktrunk..."
627
+ if brew install max-sixty/worktrunk/wt 2>/dev/null; then
628
+ print_success "Worktrunk installed"
629
+
630
+ # Install shell integration
631
+ print_info "Installing shell integration..."
632
+ if wt config shell install 2>/dev/null; then
633
+ print_success "Shell integration installed"
634
+ print_info "Restart your terminal or source your shell config"
635
+ else
636
+ print_warning "Shell integration failed - run manually: wt config shell install"
637
+ fi
638
+
639
+ echo ""
640
+ print_info "Quick start:"
641
+ echo " wt switch feature/my-feature # Create/switch to worktree"
642
+ echo " wt list # List all worktrees"
643
+ echo " wt merge # Merge and cleanup"
644
+ echo ""
645
+ print_info "Documentation: ~/.aidevops/agents/tools/git/worktrunk.md"
646
+ else
647
+ print_warning "Homebrew installation failed"
648
+ echo " Try: cargo install worktrunk && wt config shell install"
649
+ fi
650
+ else
651
+ print_info "Skipped Worktrunk installation"
652
+ print_info "Install later: brew install max-sixty/worktrunk/wt"
653
+ print_info "Fallback available: ~/.aidevops/agents/scripts/worktree-helper.sh"
654
+ fi
655
+ elif command -v cargo >/dev/null 2>&1; then
656
+ read -r -p "Install Worktrunk via Cargo? (y/n): " install_wt
657
+
658
+ if [[ "$install_wt" == "y" ]]; then
659
+ print_info "Installing Worktrunk via Cargo..."
660
+ if cargo install worktrunk 2>/dev/null; then
661
+ print_success "Worktrunk installed"
662
+
663
+ # Install shell integration
664
+ if wt config shell install 2>/dev/null; then
665
+ print_success "Shell integration installed"
666
+ else
667
+ print_warning "Shell integration failed - run manually: wt config shell install"
668
+ fi
669
+ else
670
+ print_warning "Cargo installation failed"
671
+ fi
672
+ else
673
+ print_info "Skipped Worktrunk installation"
674
+ fi
675
+ else
676
+ print_warning "Worktrunk not installed"
677
+ echo ""
678
+ echo " Install options:"
679
+ echo " macOS/Linux (Homebrew): brew install max-sixty/worktrunk/wt"
680
+ echo " Cargo: cargo install worktrunk"
681
+ echo " Windows: winget install max-sixty.worktrunk"
682
+ echo ""
683
+ echo " After install: wt config shell install"
684
+ echo ""
685
+ print_info "Fallback available: ~/.aidevops/agents/scripts/worktree-helper.sh"
686
+ fi
687
+
688
+ return 0
689
+ }
690
+
565
691
  # Setup recommended tools (Tabby terminal, Zed editor)
566
692
  setup_recommended_tools() {
567
693
  print_info "Checking recommended development tools..."
@@ -1140,9 +1266,16 @@ deploy_aidevops_agents() {
1140
1266
  rm -rf "${target_dir:?}"/*
1141
1267
  fi
1142
1268
 
1143
- # Copy all agent files and folders (excluding scripts which are large)
1144
- # We copy scripts separately to maintain structure
1145
- cp -R "$source_dir"/* "$target_dir/"
1269
+ # Copy all agent files and folders, excluding:
1270
+ # - loop-state/ (local runtime state, not agents)
1271
+ # Use rsync for selective exclusion
1272
+ if command -v rsync &>/dev/null; then
1273
+ rsync -a --exclude='loop-state/' "$source_dir/" "$target_dir/"
1274
+ else
1275
+ # Fallback: copy then remove loop-state
1276
+ cp -R "$source_dir"/* "$target_dir/"
1277
+ rm -rf "$target_dir/loop-state" 2>/dev/null || true
1278
+ fi
1146
1279
 
1147
1280
  if [[ $? -eq 0 ]]; then
1148
1281
  print_success "Deployed agents to $target_dir"
@@ -2306,6 +2439,7 @@ main() {
2306
2439
  confirm_step "Check optional dependencies (bun, node, python)" && check_optional_deps
2307
2440
  confirm_step "Setup recommended tools (Tabby, Zed, etc.)" && setup_recommended_tools
2308
2441
  confirm_step "Setup Git CLIs (gh, glab, tea)" && setup_git_clis
2442
+ confirm_step "Setup Worktrunk (git worktree management)" && setup_worktrunk
2309
2443
  confirm_step "Setup SSH key" && setup_ssh_key
2310
2444
  confirm_step "Setup configuration files" && setup_configs
2311
2445
  confirm_step "Set secure permissions on config files" && set_permissions
@@ -12,6 +12,10 @@ readonly YELLOW='\033[1;33m'
12
12
  readonly BLUE='\033[0;34m'
13
13
  readonly NC='\033[0m' # No Color
14
14
 
15
+ # Backup configuration
16
+ readonly BACKUP_KEEP_COUNT=5
17
+ readonly BACKUP_BASE_DIR="$HOME/.aidevops/template-backups"
18
+
15
19
  # Print functions
16
20
  print_info() { local msg="$1"; echo -e "${BLUE}[INFO]${NC} $msg"; return 0; }
17
21
  print_success() { local msg="$1"; echo -e "${GREEN}[SUCCESS]${NC} $msg"; return 0; }
@@ -28,15 +32,93 @@ if [[ ! -f "$REPO_ROOT/AGENTS.md" ]] || [[ ! -d "$REPO_ROOT/.agent" ]]; then
28
32
  exit 1
29
33
  fi
30
34
 
35
+ # Create a backup with rotation (keeps last N backups in centralized location)
36
+ # Usage: create_backup_with_rotation <source_path> <backup_name>
37
+ create_backup_with_rotation() {
38
+ local source_path="$1"
39
+ local backup_name="$2"
40
+ local backup_dir
41
+ # Use nanoseconds to avoid collisions on rapid successive invocations
42
+ backup_dir="$BACKUP_BASE_DIR/$backup_name/$(date +%Y%m%d_%H%M%S%N)"
43
+
44
+ # Validate source exists before attempting backup
45
+ if [[ -d "$source_path" ]]; then
46
+ mkdir -p "$backup_dir"
47
+ cp -R "$source_path" "$backup_dir/"
48
+ elif [[ -f "$source_path" ]]; then
49
+ mkdir -p "$backup_dir"
50
+ cp "$source_path" "$backup_dir/"
51
+ else
52
+ print_warning "Source path does not exist: $source_path"
53
+ return 1
54
+ fi
55
+
56
+ print_info "Backed up to $backup_dir"
57
+
58
+ # Rotate old backups (keep last N)
59
+ local backup_type_dir="$BACKUP_BASE_DIR/$backup_name"
60
+ local backup_count
61
+ backup_count=$(find "$backup_type_dir" -maxdepth 1 -type d -name "20*" 2>/dev/null | wc -l)
62
+
63
+ if (( backup_count > BACKUP_KEEP_COUNT )); then
64
+ local to_delete=$((backup_count - BACKUP_KEEP_COUNT))
65
+ # Delete oldest backups (sorted by name = sorted by date)
66
+ find "$backup_type_dir" -maxdepth 1 -type d -name "20*" -print0 2>/dev/null | sort -z | head -z -n "$to_delete" | xargs -0 rm -rf
67
+ print_info "Rotated backups: removed $to_delete old backup(s)"
68
+ fi
69
+
70
+ return 0
71
+ }
72
+
73
+ # Clean up old in-place backup files from previous versions
74
+ # Uses find -delete to safely remove only files (not directories)
75
+ cleanup_old_backups() {
76
+ local cleaned=0
77
+ local count
78
+
79
+ # Clean ~/AGENTS.md.backup.* files
80
+ count=$(find "$HOME" -maxdepth 1 -name "AGENTS.md.backup.*" -type f 2>/dev/null | wc -l)
81
+ if (( count > 0 )); then
82
+ find "$HOME" -maxdepth 1 -name "AGENTS.md.backup.*" -type f -delete 2>/dev/null
83
+ (( cleaned += count ))
84
+ fi
85
+
86
+ # Clean ~/git/AGENTS.md.backup.* or ~/Git/AGENTS.md.backup.* files
87
+ for git_dir in "$HOME/git" "$HOME/Git"; do
88
+ if [[ -d "$git_dir" ]]; then
89
+ count=$(find "$git_dir" -maxdepth 1 -name "AGENTS.md.backup.*" -type f 2>/dev/null | wc -l)
90
+ if (( count > 0 )); then
91
+ find "$git_dir" -maxdepth 1 -name "AGENTS.md.backup.*" -type f -delete 2>/dev/null
92
+ (( cleaned += count ))
93
+ fi
94
+ fi
95
+ done
96
+
97
+ # Clean ~/.aidevops/.agent-workspace/README.md.backup.* files
98
+ local workspace="$HOME/.aidevops/.agent-workspace"
99
+ if [[ -d "$workspace" ]]; then
100
+ count=$(find "$workspace" -maxdepth 1 -name "README.md.backup.*" -type f 2>/dev/null | wc -l)
101
+ if (( count > 0 )); then
102
+ find "$workspace" -maxdepth 1 -name "README.md.backup.*" -type f -delete 2>/dev/null
103
+ (( cleaned += count ))
104
+ fi
105
+ fi
106
+
107
+ if (( cleaned > 0 )); then
108
+ print_success "Cleaned up $cleaned old backup file(s)"
109
+ fi
110
+
111
+ return 0
112
+ }
113
+
31
114
  deploy_home_agents() {
32
115
  local target_file="$HOME/AGENTS.md"
33
116
 
34
117
  print_info "Deploying minimal AGENTS.md to home directory..."
35
118
 
36
- # Backup existing file if it exists
119
+ # Backup existing file if it exists (with rotation)
37
120
  if [[ -f "$target_file" ]]; then
38
- print_warning "Existing AGENTS.md found, creating backup..."
39
- cp "$target_file" "$target_file.backup.$(date +%Y%m%d_%H%M%S)"
121
+ create_backup_with_rotation "$target_file" "home-agents"
40
122
  fi
41
123
 
42
124
  # Deploy template
@@ -57,10 +139,9 @@ deploy_git_agents() {
57
139
  print_info "Created git directory: $git_dir"
58
140
  fi
59
141
 
60
- # Backup existing file if it exists
142
+ # Backup existing file if it exists (with rotation)
61
143
  if [[ -f "$target_file" ]]; then
62
- print_warning "Existing git/AGENTS.md found, creating backup..."
63
- cp "$target_file" "$target_file.backup.$(date +%Y%m%d_%H%M%S)"
144
+ create_backup_with_rotation "$target_file" "git-agents"
64
145
  fi
65
146
 
66
147
  # Deploy template
@@ -81,10 +162,9 @@ deploy_agent_directory() {
81
162
  print_info "Created workspace directory: $agent_workspace"
82
163
  fi
83
164
 
84
- # Backup existing README if it exists
165
+ # Backup existing README if it exists (with rotation)
85
166
  if [[ -f "$target_file" ]]; then
86
- print_warning "Existing .agent-workspace/README.md found, creating backup..."
87
- cp "$target_file" "$target_file.backup.$(date +%Y%m%d_%H%M%S)"
167
+ create_backup_with_rotation "$target_file" "workspace-readme"
88
168
  fi
89
169
 
90
170
  # Deploy template
@@ -128,6 +208,9 @@ main() {
128
208
  print_info "Deploying minimal, secure AGENTS.md templates..."
129
209
  print_warning "These templates contain minimal instructions to prevent prompt injection attacks"
130
210
 
211
+ # Clean up old in-place backups from previous versions
212
+ cleanup_old_backups
213
+
131
214
  deploy_home_agents
132
215
  deploy_git_agents
133
216
  deploy_agent_directory