refactor: comprehensive scripts directory reorganization by functionality
Scripts Directory Reorganization - Complete: ✅ FUNCTIONAL ORGANIZATION: Scripts sorted into 8 logical categories - github/: GitHub and Git operations (6 files) - sync/: Synchronization and data replication (4 files) - security/: Security and audit operations (2 files) - monitoring/: System and service monitoring (6 files) - maintenance/: System maintenance and cleanup (4 files) - deployment/: Deployment and provisioning (11 files) - testing/: Testing and quality assurance (13 files) - utils/: Utility scripts and helpers (47 files) ✅ ROOT DIRECTORY CLEANED: Only README.md remains in scripts root - scripts/README.md: Main documentation - scripts/SCRIPTS_ORGANIZATION.md: Complete organization guide - All functional scripts moved to appropriate subdirectories ✅ SCRIPTS CATEGORIZATION: 📁 GitHub Operations: PR resolution, repository management, Git workflows 📁 Synchronization: Bulk sync, fast sync, sync detection, SystemD sync 📁 Security: Security audits, monitoring, vulnerability scanning 📁 Monitoring: Health checks, log monitoring, network monitoring, production monitoring 📁 Maintenance: Cleanup operations, performance tuning, weekly maintenance 📁 Deployment: Release building, node provisioning, DAO deployment, production deployment 📁 Testing: E2E testing, workflow testing, QA cycles, service testing 📁 Utilities: System management, setup scripts, helpers, tools ✅ ORGANIZATION BENEFITS: - Better Navigation: Scripts grouped by functionality - Easier Maintenance: Related scripts grouped together - Scalable Structure: Easy to add new scripts to appropriate categories - Clear Documentation: Comprehensive organization guide with descriptions - Improved Workflow: Quick access to relevant scripts by category ✅ DOCUMENTATION ENHANCED: - SCRIPTS_ORGANIZATION.md: Complete directory structure and usage guide - Quick Reference: Common script usage examples - Script Descriptions: Purpose and functionality for each script - Maintenance Guidelines: How to keep organization current DIRECTORY STRUCTURE: 📁 scripts/ ├── README.md (Main documentation) ├── SCRIPTS_ORGANIZATION.md (Organization guide) ├── github/ (6 files - GitHub operations) ├── sync/ (4 files - Synchronization) ├── security/ (2 files - Security) ├── monitoring/ (6 files - Monitoring) ├── maintenance/ (4 files - Maintenance) ├── deployment/ (11 files - Deployment) ├── testing/ (13 files - Testing) ├── utils/ (47 files - Utilities) ├── ci/ (existing - CI/CD) ├── deployment/ (existing - legacy deployment) ├── development/ (existing - Development tools) ├── monitoring/ (existing - Legacy monitoring) ├── services/ (existing - Service management) ├── testing/ (existing - Legacy testing) ├── utils/ (existing - Legacy utilities) ├── workflow/ (existing - Workflow automation) └── workflow-openclaw/ (existing - OpenClaw workflows) RESULT: Successfully reorganized 27 unorganized scripts into 8 functional categories, creating a clean, maintainable, and well-documented scripts directory structure with comprehensive organization guide.
This commit is contained in:
144
scripts/utils/link-systemd.sh
Executable file
144
scripts/utils/link-systemd.sh
Executable file
@@ -0,0 +1,144 @@
|
||||
#!/bin/bash
|
||||
|
||||
# AITBC Systemd Link Script
|
||||
# Creates symbolic links from active systemd to repository systemd files
|
||||
# Keeps active systemd always in sync with repository
|
||||
|
||||
# set -e # Disabled to allow script to continue even if some operations fail
|
||||
|
||||
REPO_SYSTEMD_DIR="/opt/aitbc/systemd"
|
||||
ACTIVE_SYSTEMD_DIR="/etc/systemd/system"
|
||||
|
||||
echo "=== AITBC SYSTEMD LINKING ==="
|
||||
echo "Repository: $REPO_SYSTEMD_DIR"
|
||||
echo "Active: $ACTIVE_SYSTEMD_DIR"
|
||||
echo
|
||||
|
||||
# Check if running as root
|
||||
if [[ $EUID -ne 0 ]]; then
|
||||
echo "❌ This script must be run as root (use sudo)"
|
||||
echo " sudo $0"
|
||||
exit 1
|
||||
fi
|
||||
|
||||
# Check if repository systemd directory exists
|
||||
if [[ ! -d "$REPO_SYSTEMD_DIR" ]]; then
|
||||
echo "❌ Repository systemd directory not found: $REPO_SYSTEMD_DIR"
|
||||
exit 1
|
||||
fi
|
||||
|
||||
echo "🔍 Creating symbolic links for AITBC systemd files..."
|
||||
|
||||
# Create backup of current active systemd files
|
||||
BACKUP_DIR="/opt/aitbc/systemd-backup-$(date +%Y%m%d-%H%M%S)"
|
||||
echo "📦 Creating backup: $BACKUP_DIR"
|
||||
mkdir -p "$BACKUP_DIR"
|
||||
find "$ACTIVE_SYSTEMD_DIR" -name "aitbc-*" -type f -exec cp {} "$BACKUP_DIR/" \; 2>/dev/null || true
|
||||
|
||||
# Remove existing aitbc-* files (but not directories)
|
||||
echo "🧹 Removing existing systemd files..."
|
||||
find "$ACTIVE_SYSTEMD_DIR" -name "aitbc-*" -type f -delete 2>/dev/null || true
|
||||
|
||||
# Create symbolic links
|
||||
echo "🔗 Creating symbolic links..."
|
||||
linked_files=0
|
||||
error_count=0
|
||||
|
||||
for file in "$REPO_SYSTEMD_DIR"/aitbc-*; do
|
||||
if [[ -f "$file" ]]; then
|
||||
filename=$(basename "$file")
|
||||
target="$ACTIVE_SYSTEMD_DIR/$filename"
|
||||
source="$REPO_SYSTEMD_DIR/$filename"
|
||||
|
||||
echo " 🔗 Linking: $filename -> $source"
|
||||
|
||||
# Create symbolic link
|
||||
if ln -sf "$source" "$target" 2>/dev/null; then
|
||||
echo " ✅ Successfully linked: $filename"
|
||||
else
|
||||
echo " ❌ Failed to link: $filename"
|
||||
((error_count++))
|
||||
fi
|
||||
|
||||
# Handle .d directories
|
||||
if [[ -d "${file}.d" ]]; then
|
||||
target_dir="${target}.d"
|
||||
source_dir="${file}.d"
|
||||
|
||||
echo " 📁 Linking directory: ${filename}.d -> ${source_dir}"
|
||||
|
||||
# Remove existing directory
|
||||
rm -rf "$target_dir" 2>/dev/null || true
|
||||
|
||||
# Create symbolic link for directory
|
||||
if ln -sf "$source_dir" "$target_dir" 2>/dev/null; then
|
||||
echo " ✅ Successfully linked directory: ${filename}.d"
|
||||
else
|
||||
echo " ❌ Failed to link directory: ${filename}.d"
|
||||
((error_count++))
|
||||
fi
|
||||
fi
|
||||
|
||||
((linked_files++))
|
||||
fi
|
||||
done
|
||||
|
||||
echo
|
||||
echo "📊 Linking Summary:"
|
||||
echo " Files processed: $linked_files"
|
||||
echo " Errors encountered: $error_count"
|
||||
|
||||
if [[ $error_count -gt 0 ]]; then
|
||||
echo "⚠️ Some links failed, but continuing..."
|
||||
else
|
||||
echo "✅ All links created successfully"
|
||||
fi
|
||||
|
||||
echo
|
||||
echo "🔄 Reloading systemd daemon..."
|
||||
if systemctl daemon-reload 2>/dev/null; then
|
||||
echo " ✅ Systemd daemon reloaded successfully"
|
||||
else
|
||||
echo " ⚠️ Systemd daemon reload failed, but continuing..."
|
||||
fi
|
||||
|
||||
echo
|
||||
echo "✅ Systemd linking completed!"
|
||||
echo
|
||||
echo "📊 Link Summary:"
|
||||
echo " Linked files: $linked_files"
|
||||
echo " Repository: $REPO_SYSTEMD_DIR"
|
||||
echo " Active: $ACTIVE_SYSTEMD_DIR"
|
||||
echo " Backup location: $BACKUP_DIR"
|
||||
echo
|
||||
echo "🎯 Benefits:"
|
||||
echo " ✅ Active systemd files always match repository"
|
||||
echo " ✅ No gap between repo and running services"
|
||||
echo " ✅ Changes in repo immediately reflected"
|
||||
echo " ✅ Automatic sync on every repository update"
|
||||
echo
|
||||
echo "🔧 To restart services:"
|
||||
echo " sudo systemctl restart aitbc-blockchain-node"
|
||||
echo " sudo systemctl restart aitbc-coordinator-api"
|
||||
echo " # ... or restart all AITBC services:"
|
||||
echo " sudo systemctl restart aitbc-*"
|
||||
echo
|
||||
echo "🔍 To check status:"
|
||||
echo " sudo systemctl status aitbc-*"
|
||||
echo
|
||||
echo "🔍 To verify links:"
|
||||
echo " ls -la /etc/systemd/system/aitbc-*"
|
||||
echo " readlink /etc/systemd/system/aitbc-blockchain-node.service"
|
||||
echo
|
||||
echo "⚠️ If you need to restore backup:"
|
||||
echo " sudo cp $BACKUP_DIR/* /etc/systemd/system/"
|
||||
echo " sudo systemctl daemon-reload"
|
||||
|
||||
# Ensure script exits successfully
|
||||
if [[ $linked_files -gt 0 ]]; then
|
||||
echo "✅ Script completed successfully with $linked_files files linked"
|
||||
exit 0
|
||||
else
|
||||
echo "⚠️ No files were linked, but script completed"
|
||||
exit 0
|
||||
fi
|
||||
49
scripts/utils/manage-services.sh
Executable file
49
scripts/utils/manage-services.sh
Executable file
@@ -0,0 +1,49 @@
|
||||
#!/bin/bash
|
||||
# AITBC Service Management Script - No sudo required
|
||||
|
||||
case "${1:-help}" in
|
||||
"start")
|
||||
echo "Starting AITBC services..."
|
||||
systemctl start aitbc-coordinator-api.service
|
||||
systemctl start aitbc-blockchain-node.service
|
||||
systemctl start aitbc-blockchain-rpc.service
|
||||
echo "Services started"
|
||||
;;
|
||||
"stop")
|
||||
echo "Stopping AITBC services..."
|
||||
systemctl stop aitbc-coordinator-api.service
|
||||
systemctl stop aitbc-blockchain-node.service
|
||||
systemctl stop aitbc-blockchain-rpc.service
|
||||
echo "Services stopped"
|
||||
;;
|
||||
"restart")
|
||||
echo "Restarting AITBC services..."
|
||||
systemctl restart aitbc-coordinator-api.service
|
||||
systemctl restart aitbc-blockchain-node.service
|
||||
systemctl restart aitbc-blockchain-rpc.service
|
||||
echo "Services restarted"
|
||||
;;
|
||||
"status")
|
||||
echo "=== AITBC Services Status ==="
|
||||
systemctl status aitbc-coordinator-api.service --no-pager
|
||||
systemctl status aitbc-blockchain-node.service --no-pager
|
||||
systemctl status aitbc-blockchain-rpc.service --no-pager
|
||||
;;
|
||||
"logs")
|
||||
echo "=== AITBC Service Logs ==="
|
||||
sudo journalctl -u aitbc-coordinator-api.service -f
|
||||
;;
|
||||
"help"|*)
|
||||
echo "AITBC Service Management"
|
||||
echo ""
|
||||
echo "Usage: $0 {start|stop|restart|status|logs|help}"
|
||||
echo ""
|
||||
echo "Commands:"
|
||||
echo " start - Start all AITBC services"
|
||||
echo " stop - Stop all AITBC services"
|
||||
echo " restart - Restart all AITBC services"
|
||||
echo " status - Show service status"
|
||||
echo " logs - Follow service logs"
|
||||
echo " help - Show this help message"
|
||||
;;
|
||||
esac
|
||||
364
scripts/utils/requirements_migrator.py
Executable file
364
scripts/utils/requirements_migrator.py
Executable file
@@ -0,0 +1,364 @@
|
||||
#!/usr/bin/env python3
|
||||
"""
|
||||
AITBC Requirements Migration Tool
|
||||
Core function to migrate service requirements to central and identify 3rd party modules
|
||||
"""
|
||||
|
||||
import os
|
||||
import sys
|
||||
import re
|
||||
from pathlib import Path
|
||||
from typing import Dict, List, Set, Tuple
|
||||
import argparse
|
||||
|
||||
class RequirementsMigrator:
|
||||
"""Core requirements migration and analysis tool"""
|
||||
|
||||
def __init__(self, base_path: str = "/opt/aitbc"):
|
||||
self.base_path = Path(base_path)
|
||||
self.central_req = self.base_path / "requirements.txt"
|
||||
self.central_packages = set()
|
||||
self.migration_log = []
|
||||
|
||||
def load_central_requirements(self) -> Set[str]:
|
||||
"""Load central requirements packages"""
|
||||
if not self.central_req.exists():
|
||||
print(f"❌ Central requirements not found: {self.central_req}")
|
||||
return set()
|
||||
|
||||
packages = set()
|
||||
with open(self.central_req, 'r') as f:
|
||||
for line in f:
|
||||
line = line.strip()
|
||||
if line and not line.startswith('#'):
|
||||
# Extract package name (before version specifier)
|
||||
match = re.match(r'^([a-zA-Z0-9_-]+)', line)
|
||||
if match:
|
||||
packages.add(match.group(1))
|
||||
|
||||
self.central_packages = packages
|
||||
print(f"✅ Loaded {len(packages)} packages from central requirements")
|
||||
return packages
|
||||
|
||||
def find_requirements_files(self) -> List[Path]:
|
||||
"""Find all requirements.txt files"""
|
||||
files = []
|
||||
for req_file in self.base_path.rglob("requirements.txt"):
|
||||
if req_file != self.central_req:
|
||||
files.append(req_file)
|
||||
return files
|
||||
|
||||
def parse_requirements_file(self, file_path: Path) -> List[str]:
|
||||
"""Parse individual requirements file"""
|
||||
requirements = []
|
||||
try:
|
||||
with open(file_path, 'r') as f:
|
||||
for line in f:
|
||||
line = line.strip()
|
||||
if line and not line.startswith('#'):
|
||||
requirements.append(line)
|
||||
except Exception as e:
|
||||
print(f"❌ Error reading {file_path}: {e}")
|
||||
return requirements
|
||||
|
||||
def analyze_coverage(self, file_path: Path, requirements: List[str]) -> Dict:
|
||||
"""Analyze coverage of requirements by central packages"""
|
||||
covered = []
|
||||
not_covered = []
|
||||
version_upgrades = []
|
||||
|
||||
if not requirements:
|
||||
return {
|
||||
'file': file_path,
|
||||
'total': 0,
|
||||
'covered': 0,
|
||||
'not_covered': [],
|
||||
'coverage_percent': 100.0,
|
||||
'version_upgrades': []
|
||||
}
|
||||
|
||||
for req in requirements:
|
||||
# Extract package name
|
||||
match = re.match(r'^([a-zA-Z0-9_-]+)([><=!]+.*)?', req)
|
||||
if not match:
|
||||
continue
|
||||
|
||||
package_name = match.group(1)
|
||||
version_spec = match.group(2) or ""
|
||||
|
||||
if package_name in self.central_packages:
|
||||
covered.append(req)
|
||||
# Check for version upgrades
|
||||
central_req = self._find_central_requirement(package_name)
|
||||
if central_req and version_spec and central_req != version_spec:
|
||||
version_upgrades.append({
|
||||
'package': package_name,
|
||||
'old_version': version_spec,
|
||||
'new_version': central_req
|
||||
})
|
||||
else:
|
||||
not_covered.append(req)
|
||||
|
||||
return {
|
||||
'file': file_path,
|
||||
'total': len(requirements),
|
||||
'covered': len(covered),
|
||||
'not_covered': not_covered,
|
||||
'coverage_percent': (len(covered) / len(requirements) * 100) if requirements else 100.0,
|
||||
'version_upgrades': version_upgrades
|
||||
}
|
||||
|
||||
def _find_central_requirement(self, package_name: str) -> str:
|
||||
"""Find requirement specification in central file"""
|
||||
try:
|
||||
with open(self.central_req, 'r') as f:
|
||||
for line in f:
|
||||
line = line.strip()
|
||||
if line and not line.startswith('#'):
|
||||
match = re.match(rf'^{re.escape(package_name)}([><=!]+.+)', line)
|
||||
if match:
|
||||
return match.group(1)
|
||||
except:
|
||||
pass
|
||||
return ""
|
||||
|
||||
def categorize_uncovered(self, not_covered: List[str]) -> Dict[str, List[str]]:
|
||||
"""Categorize uncovered requirements"""
|
||||
categories = {
|
||||
'core_infrastructure': [],
|
||||
'ai_ml': [],
|
||||
'blockchain': [],
|
||||
'translation_nlp': [],
|
||||
'monitoring': [],
|
||||
'testing': [],
|
||||
'security': [],
|
||||
'utilities': [],
|
||||
'other': []
|
||||
}
|
||||
|
||||
# Package categorization mapping
|
||||
category_map = {
|
||||
# Core Infrastructure
|
||||
'fastapi': 'core_infrastructure', 'uvicorn': 'core_infrastructure',
|
||||
'sqlalchemy': 'core_infrastructure', 'pydantic': 'core_infrastructure',
|
||||
'sqlmodel': 'core_infrastructure', 'alembic': 'core_infrastructure',
|
||||
|
||||
# AI/ML
|
||||
'torch': 'ai_ml', 'tensorflow': 'ai_ml', 'numpy': 'ai_ml',
|
||||
'pandas': 'ai_ml', 'scikit-learn': 'ai_ml', 'transformers': 'ai_ml',
|
||||
'opencv-python': 'ai_ml', 'pillow': 'ai_ml', 'tenseal': 'ai_ml',
|
||||
|
||||
# Blockchain
|
||||
'web3': 'blockchain', 'eth-utils': 'blockchain', 'eth-account': 'blockchain',
|
||||
'cryptography': 'blockchain', 'ecdsa': 'blockchain', 'base58': 'blockchain',
|
||||
|
||||
# Translation/NLP
|
||||
'openai': 'translation_nlp', 'google-cloud-translate': 'translation_nlp',
|
||||
'deepl': 'translation_nlp', 'langdetect': 'translation_nlp',
|
||||
'polyglot': 'translation_nlp', 'fasttext': 'translation_nlp',
|
||||
'nltk': 'translation_nlp', 'spacy': 'translation_nlp',
|
||||
|
||||
# Monitoring
|
||||
'prometheus-client': 'monitoring', 'structlog': 'monitoring',
|
||||
'sentry-sdk': 'monitoring',
|
||||
|
||||
# Testing
|
||||
'pytest': 'testing', 'pytest-asyncio': 'testing', 'pytest-mock': 'testing',
|
||||
|
||||
# Security
|
||||
'python-jose': 'security', 'passlib': 'security', 'keyring': 'security',
|
||||
|
||||
# Utilities
|
||||
'click': 'utilities', 'rich': 'utilities', 'typer': 'utilities',
|
||||
'httpx': 'utilities', 'requests': 'utilities', 'aiohttp': 'utilities',
|
||||
}
|
||||
|
||||
for req in not_covered:
|
||||
package_name = re.match(r'^([a-zA-Z0-9_-]+)', req).group(1)
|
||||
category = category_map.get(package_name, 'other')
|
||||
categories[category].append(req)
|
||||
|
||||
return categories
|
||||
|
||||
def migrate_requirements(self, dry_run: bool = True) -> Dict:
|
||||
"""Migrate requirements to central if fully covered"""
|
||||
results = {
|
||||
'migrated': [],
|
||||
'kept': [],
|
||||
'errors': []
|
||||
}
|
||||
|
||||
self.load_central_requirements()
|
||||
req_files = self.find_requirements_files()
|
||||
|
||||
for file_path in req_files:
|
||||
try:
|
||||
requirements = self.parse_requirements_file(file_path)
|
||||
analysis = self.analyze_coverage(file_path, requirements)
|
||||
|
||||
if analysis['coverage_percent'] == 100:
|
||||
if not dry_run:
|
||||
file_path.unlink()
|
||||
results['migrated'].append({
|
||||
'file': str(file_path),
|
||||
'packages': analysis['covered']
|
||||
})
|
||||
print(f"✅ Migrated: {file_path} ({len(analysis['covered'])} packages)")
|
||||
else:
|
||||
results['migrated'].append({
|
||||
'file': str(file_path),
|
||||
'packages': analysis['covered']
|
||||
})
|
||||
print(f"🔄 Would migrate: {file_path} ({len(analysis['covered'])} packages)")
|
||||
else:
|
||||
categories = self.categorize_uncovered(analysis['not_covered'])
|
||||
results['kept'].append({
|
||||
'file': str(file_path),
|
||||
'coverage': analysis['coverage_percent'],
|
||||
'not_covered': analysis['not_covered'],
|
||||
'categories': categories
|
||||
})
|
||||
print(f"⚠️ Keep: {file_path} ({analysis['coverage_percent']:.1f}% covered)")
|
||||
|
||||
except Exception as e:
|
||||
results['errors'].append({
|
||||
'file': str(file_path),
|
||||
'error': str(e)
|
||||
})
|
||||
print(f"❌ Error processing {file_path}: {e}")
|
||||
|
||||
return results
|
||||
|
||||
def generate_report(self, results: Dict) -> str:
|
||||
"""Generate migration report"""
|
||||
report = []
|
||||
report.append("# AITBC Requirements Migration Report\n")
|
||||
|
||||
# Summary
|
||||
report.append("## Summary")
|
||||
report.append(f"- Files analyzed: {len(results['migrated']) + len(results['kept']) + len(results['errors'])}")
|
||||
report.append(f"- Files migrated: {len(results['migrated'])}")
|
||||
report.append(f"- Files kept: {len(results['kept'])}")
|
||||
report.append(f"- Errors: {len(results['errors'])}\n")
|
||||
|
||||
# Migrated files
|
||||
if results['migrated']:
|
||||
report.append("## ✅ Migrated Files")
|
||||
for item in results['migrated']:
|
||||
packages = item['packages'] if isinstance(item['packages'], list) else []
|
||||
report.append(f"- `{item['file']}` ({len(packages)} packages)")
|
||||
report.append("")
|
||||
|
||||
# Kept files with analysis
|
||||
if results['kept']:
|
||||
report.append("## ⚠️ Files Kept (Specialized Dependencies)")
|
||||
for item in results['kept']:
|
||||
report.append(f"### `{item['file']}`")
|
||||
report.append(f"- Coverage: {item['coverage']:.1f}%")
|
||||
report.append(f"- Uncovered packages: {len(item['not_covered'])}")
|
||||
|
||||
for category, packages in item['categories'].items():
|
||||
if packages:
|
||||
report.append(f" - **{category.replace('_', ' ').title()}**: {len(packages)} packages")
|
||||
for pkg in packages[:3]: # Show first 3
|
||||
report.append(f" - `{pkg}`")
|
||||
if len(packages) > 3:
|
||||
report.append(f" - ... and {len(packages) - 3} more")
|
||||
report.append("")
|
||||
|
||||
# Errors
|
||||
if results['errors']:
|
||||
report.append("## ❌ Errors")
|
||||
for item in results['errors']:
|
||||
report.append(f"- `{item['file']}`: {item['error']}")
|
||||
report.append("")
|
||||
|
||||
return "\n".join(report)
|
||||
|
||||
def suggest_3rd_party_modules(self, results: Dict) -> Dict[str, List[str]]:
|
||||
"""Suggest 3rd party module groupings"""
|
||||
modules = {
|
||||
'ai_ml_translation': [],
|
||||
'blockchain_web3': [],
|
||||
'monitoring_observability': [],
|
||||
'testing_quality': [],
|
||||
'security_compliance': []
|
||||
}
|
||||
|
||||
for item in results['kept']:
|
||||
categories = item['categories']
|
||||
|
||||
# AI/ML + Translation
|
||||
ai_ml_packages = categories.get('ai_ml', []) + categories.get('translation_nlp', [])
|
||||
if ai_ml_packages:
|
||||
modules['ai_ml_translation'].extend([pkg.split('>=')[0] for pkg in ai_ml_packages])
|
||||
|
||||
# Blockchain
|
||||
blockchain_packages = categories.get('blockchain', [])
|
||||
if blockchain_packages:
|
||||
modules['blockchain_web3'].extend([pkg.split('>=')[0] for pkg in blockchain_packages])
|
||||
|
||||
# Monitoring
|
||||
monitoring_packages = categories.get('monitoring', [])
|
||||
if monitoring_packages:
|
||||
modules['monitoring_observability'].extend([pkg.split('>=')[0] for pkg in monitoring_packages])
|
||||
|
||||
# Testing
|
||||
testing_packages = categories.get('testing', [])
|
||||
if testing_packages:
|
||||
modules['testing_quality'].extend([pkg.split('>=')[0] for pkg in testing_packages])
|
||||
|
||||
# Security
|
||||
security_packages = categories.get('security', [])
|
||||
if security_packages:
|
||||
modules['security_compliance'].extend([pkg.split('>=')[0] for pkg in security_packages])
|
||||
|
||||
# Remove duplicates and sort
|
||||
for key in modules:
|
||||
modules[key] = sorted(list(set(modules[key])))
|
||||
|
||||
return modules
|
||||
|
||||
|
||||
def main():
|
||||
"""Main entry point"""
|
||||
parser = argparse.ArgumentParser(description="AITBC Requirements Migration Tool")
|
||||
parser.add_argument("--dry-run", action="store_true", help="Show what would be migrated without actually doing it")
|
||||
parser.add_argument("--execute", action="store_true", help="Actually migrate files")
|
||||
parser.add_argument("--base-path", default="/opt/aitbc", help="Base path for AITBC repository")
|
||||
|
||||
args = parser.parse_args()
|
||||
|
||||
if not args.dry_run and not args.execute:
|
||||
print("Use --dry-run to preview or --execute to actually migrate")
|
||||
return
|
||||
|
||||
migrator = RequirementsMigrator(args.base_path)
|
||||
|
||||
print("🔍 Analyzing AITBC requirements files...")
|
||||
results = migrator.migrate_requirements(dry_run=not args.execute)
|
||||
|
||||
print("\n📊 Generating report...")
|
||||
report = migrator.generate_report(results)
|
||||
|
||||
# Save report
|
||||
report_file = Path(args.base_path) / "docs" / "REQUIREMENTS_MIGRATION_REPORT.md"
|
||||
report_file.parent.mkdir(exist_ok=True)
|
||||
with open(report_file, 'w') as f:
|
||||
f.write(report)
|
||||
|
||||
print(f"📄 Report saved to: {report_file}")
|
||||
|
||||
# Suggest 3rd party modules
|
||||
modules = migrator.suggest_3rd_party_modules(results)
|
||||
print("\n🎯 Suggested 3rd Party Modules:")
|
||||
|
||||
for module_name, packages in modules.items():
|
||||
if packages:
|
||||
print(f"\n📦 {module_name.replace('_', ' ').title()}:")
|
||||
for pkg in packages:
|
||||
print(f" - {pkg}")
|
||||
|
||||
|
||||
if __name__ == "__main__":
|
||||
main()
|
||||
342
scripts/utils/setup.sh
Executable file
342
scripts/utils/setup.sh
Executable file
@@ -0,0 +1,342 @@
|
||||
#!/bin/bash
|
||||
# OpenClaw AITBC Integration Setup & Health Check
|
||||
# Field-tested setup and management for OpenClaw + AITBC integration
|
||||
# Version: 5.0 — Updated 2026-03-30 with AI operations and advanced coordination
|
||||
|
||||
set -e
|
||||
|
||||
AITBC_DIR="/opt/aitbc"
|
||||
AITBC_CLI="$AITBC_DIR/aitbc-cli"
|
||||
DATA_DIR="/var/lib/aitbc/data"
|
||||
ENV_FILE="/etc/aitbc/.env"
|
||||
GENESIS_RPC="http://localhost:8006"
|
||||
FOLLOWER_RPC="http://10.1.223.40:8006"
|
||||
WALLET_PASSWORD="123"
|
||||
|
||||
RED='\033[0;31m'
|
||||
GREEN='\033[0;32m'
|
||||
YELLOW='\033[1;33m'
|
||||
BLUE='\033[0;34m'
|
||||
NC='\033[0m'
|
||||
|
||||
log_info() { echo -e "${BLUE}[INFO]${NC} $1"; }
|
||||
log_success() { echo -e "${GREEN}[OK]${NC} $1"; }
|
||||
log_warning() { echo -e "${YELLOW}[WARN]${NC} $1"; }
|
||||
log_error() { echo -e "${RED}[ERROR]${NC} $1"; }
|
||||
|
||||
# ── Prerequisites ──────────────────────────────────────────────
|
||||
check_prerequisites() {
|
||||
log_info "Checking prerequisites..."
|
||||
local fail=0
|
||||
|
||||
command -v openclaw &>/dev/null && log_success "OpenClaw CLI found" || { log_error "OpenClaw not found"; fail=1; }
|
||||
[ -x "$AITBC_CLI" ] && log_success "AITBC CLI found" || { log_error "AITBC CLI not found at $AITBC_CLI"; fail=1; }
|
||||
|
||||
if curl -sf http://localhost:8006/health &>/dev/null; then
|
||||
log_success "Genesis RPC (localhost:8006) healthy"
|
||||
else
|
||||
log_warning "Genesis RPC not responding — try: sudo systemctl start aitbc-blockchain-rpc.service"
|
||||
fi
|
||||
|
||||
if ssh aitbc1 'curl -sf http://localhost:8006/health' &>/dev/null; then
|
||||
log_success "Follower RPC (aitbc1:8006) healthy"
|
||||
else
|
||||
log_warning "Follower RPC not responding — check aitbc1 services"
|
||||
fi
|
||||
|
||||
[ -d "$DATA_DIR/ait-mainnet" ] && log_success "Data dir $DATA_DIR/ait-mainnet exists" || log_warning "Data dir missing"
|
||||
[ -f "$ENV_FILE" ] && log_success "Env file $ENV_FILE exists" || log_warning "Env file missing"
|
||||
|
||||
[ $fail -eq 0 ] && log_success "Prerequisites satisfied" || { log_error "Prerequisites check failed"; exit 1; }
|
||||
}
|
||||
|
||||
# ── OpenClaw Agent Test ────────────────────────────────────────
|
||||
test_agent_communication() {
|
||||
log_info "Testing OpenClaw agent communication..."
|
||||
# IMPORTANT: use --message (long form), not -m
|
||||
local SESSION_ID="health-$(date +%s)"
|
||||
local GENESIS_HEIGHT
|
||||
GENESIS_HEIGHT=$(curl -sf http://localhost:8006/rpc/head | jq -r '.height // "unknown"')
|
||||
|
||||
openclaw agent --agent main --session-id "$SESSION_ID" \
|
||||
--message "AITBC integration health check. Genesis height: $GENESIS_HEIGHT. Report status." \
|
||||
--thinking low \
|
||||
&& log_success "Agent communication working" \
|
||||
|| log_warning "Agent communication failed (non-fatal)"
|
||||
}
|
||||
|
||||
# ── Blockchain Status ──────────────────────────────────────────
|
||||
show_status() {
|
||||
log_info "=== OpenClaw AITBC Integration Status ==="
|
||||
|
||||
echo ""
|
||||
echo "OpenClaw:"
|
||||
openclaw --version 2>/dev/null || echo " (not available)"
|
||||
|
||||
echo ""
|
||||
echo "Genesis Node (aitbc):"
|
||||
curl -sf http://localhost:8006/rpc/head | jq '{height, hash: .hash[0:18], timestamp}' 2>/dev/null \
|
||||
|| echo " RPC not responding"
|
||||
|
||||
echo ""
|
||||
echo "Follower Node (aitbc1):"
|
||||
ssh aitbc1 'curl -sf http://localhost:8006/rpc/head' 2>/dev/null | jq '{height, hash: .hash[0:18], timestamp}' \
|
||||
|| echo " RPC not responding"
|
||||
|
||||
echo ""
|
||||
echo "Wallets (aitbc):"
|
||||
cd "$AITBC_DIR" && source venv/bin/activate && ./aitbc-cli list 2>/dev/null || echo " CLI error"
|
||||
|
||||
echo ""
|
||||
echo "Wallets (aitbc1):"
|
||||
ssh aitbc1 "cd $AITBC_DIR && source venv/bin/activate && ./aitbc-cli list" 2>/dev/null || echo " CLI error"
|
||||
|
||||
echo ""
|
||||
echo "Services (aitbc):"
|
||||
systemctl is-active aitbc-blockchain-node.service 2>/dev/null | sed 's/^/ node: /'
|
||||
systemctl is-active aitbc-blockchain-rpc.service 2>/dev/null | sed 's/^/ rpc: /'
|
||||
|
||||
echo ""
|
||||
echo "Services (aitbc1):"
|
||||
ssh aitbc1 'systemctl is-active aitbc-blockchain-node.service' 2>/dev/null | sed 's/^/ node: /'
|
||||
ssh aitbc1 'systemctl is-active aitbc-blockchain-rpc.service' 2>/dev/null | sed 's/^/ rpc: /'
|
||||
|
||||
echo ""
|
||||
echo "Data Directory:"
|
||||
ls -lh "$DATA_DIR/ait-mainnet/" 2>/dev/null | head -5 || echo " not found"
|
||||
}
|
||||
|
||||
# ── Run Integration Test ───────────────────────────────────────
|
||||
run_integration_test() {
|
||||
log_info "Running integration test..."
|
||||
|
||||
local pass=0 total=0
|
||||
|
||||
# Test 1: RPC health
|
||||
total=$((total+1))
|
||||
curl -sf http://localhost:8006/health &>/dev/null && { log_success "RPC health OK"; pass=$((pass+1)); } || log_error "RPC health FAIL"
|
||||
|
||||
# Test 2: CLI works
|
||||
total=$((total+1))
|
||||
cd "$AITBC_DIR" && source venv/bin/activate && ./aitbc-cli list &>/dev/null && { log_success "CLI OK"; pass=$((pass+1)); } || log_error "CLI FAIL"
|
||||
|
||||
# Test 3: Cross-node SSH
|
||||
total=$((total+1))
|
||||
ssh aitbc1 'echo ok' &>/dev/null && { log_success "SSH to aitbc1 OK"; pass=$((pass+1)); } || log_error "SSH FAIL"
|
||||
|
||||
# Test 4: Agent communication
|
||||
total=$((total+1))
|
||||
openclaw agent --agent main --message "ping" --thinking minimal &>/dev/null && { log_success "Agent OK"; pass=$((pass+1)); } || log_warning "Agent FAIL (non-fatal)"
|
||||
|
||||
echo ""
|
||||
log_info "Results: $pass/$total passed"
|
||||
}
|
||||
|
||||
# ── Main ───────────────────────────────────────────────────────
|
||||
main() {
|
||||
case "${1:-status}" in
|
||||
setup)
|
||||
check_prerequisites
|
||||
test_agent_communication
|
||||
show_status
|
||||
log_success "Setup verification complete"
|
||||
;;
|
||||
test)
|
||||
run_integration_test
|
||||
;;
|
||||
status)
|
||||
show_status
|
||||
;;
|
||||
ai-setup)
|
||||
setup_ai_operations
|
||||
;;
|
||||
ai-test)
|
||||
test_ai_operations
|
||||
;;
|
||||
comprehensive)
|
||||
show_comprehensive_status
|
||||
;;
|
||||
help)
|
||||
echo "Usage: $0 {setup|test|status|ai-setup|ai-test|comprehensive|help}"
|
||||
echo " setup — Verify prerequisites and test agent communication"
|
||||
echo " test — Run integration tests"
|
||||
echo " status — Show current multi-node status"
|
||||
echo " ai-setup — Setup AI operations and agents"
|
||||
echo " ai-test — Test AI operations functionality"
|
||||
echo " comprehensive — Show comprehensive status including AI operations"
|
||||
echo " help — Show this help"
|
||||
;;
|
||||
*)
|
||||
log_error "Unknown command: $1"
|
||||
main help
|
||||
exit 1
|
||||
;;
|
||||
esac
|
||||
}
|
||||
|
||||
# ── AI Operations Setup ───────────────────────────────────────────
|
||||
setup_ai_operations() {
|
||||
log_info "Setting up AI operations..."
|
||||
|
||||
cd "$AITBC_DIR"
|
||||
source venv/bin/activate
|
||||
|
||||
# Create AI inference agent
|
||||
log_info "Creating AI inference agent..."
|
||||
if ./aitbc-cli agent create --name "ai-inference-worker" \
|
||||
--description "Specialized agent for AI inference tasks" \
|
||||
--verification full; then
|
||||
log_success "AI inference agent created"
|
||||
else
|
||||
log_warning "AI inference agent creation failed"
|
||||
fi
|
||||
|
||||
# Allocate GPU resources
|
||||
log_info "Allocating GPU resources..."
|
||||
if ./aitbc-cli resource allocate --agent-id "ai-inference-worker" \
|
||||
--gpu 1 --memory 8192 --duration 3600; then
|
||||
log_success "GPU resources allocated"
|
||||
else
|
||||
log_warning "GPU resource allocation failed"
|
||||
fi
|
||||
|
||||
# Create AI service marketplace listing
|
||||
log_info "Creating AI marketplace listing..."
|
||||
if ./aitbc-cli marketplace --action create \
|
||||
--name "AI Image Generation" \
|
||||
--type ai-inference \
|
||||
--price 50 \
|
||||
--wallet genesis-ops \
|
||||
--description "Generate high-quality images from text prompts"; then
|
||||
log_success "AI marketplace listing created"
|
||||
else
|
||||
log_warning "AI marketplace listing creation failed"
|
||||
fi
|
||||
|
||||
# Setup follower AI operations
|
||||
log_info "Setting up follower AI operations..."
|
||||
if ssh aitbc1 "cd $AITBC_DIR && source venv/bin/activate && \
|
||||
./aitbc-cli agent create --name 'ai-training-agent' \
|
||||
--description 'Specialized agent for AI model training' \
|
||||
--verification full && \
|
||||
./aitbc-cli resource allocate --agent-id 'ai-training-agent' \
|
||||
--cpu 4 --memory 16384 --duration 7200"; then
|
||||
log_success "Follower AI operations setup completed"
|
||||
else
|
||||
log_warning "Follower AI operations setup failed"
|
||||
fi
|
||||
|
||||
log_success "AI operations setup completed"
|
||||
}
|
||||
|
||||
# ── AI Operations Test ──────────────────────────────────────────────
|
||||
test_ai_operations() {
|
||||
log_info "Testing AI operations..."
|
||||
|
||||
cd "$AITBC_DIR"
|
||||
source venv/bin/activate
|
||||
|
||||
# Test AI job submission
|
||||
log_info "Testing AI job submission..."
|
||||
if ./aitbc-cli ai-submit --wallet genesis-ops \
|
||||
--type inference \
|
||||
--prompt "Test image generation" \
|
||||
--payment 10; then
|
||||
log_success "AI job submission test passed"
|
||||
else
|
||||
log_warning "AI job submission test failed"
|
||||
fi
|
||||
|
||||
# Test smart contract messaging
|
||||
log_info "Testing smart contract messaging..."
|
||||
TOPIC_ID=$(curl -s -X POST "$GENESIS_RPC/rpc/messaging/topics/create" \
|
||||
-H "Content-Type: application/json" \
|
||||
-d '{"agent_id": "test-agent", "agent_address": "ait158ec7a0713f30ccfb1aac6bfbab71f36271c5871", "title": "Test Topic", "description": "Test coordination"}' | \
|
||||
jq -r '.topic_id // "error"')
|
||||
|
||||
if [ "$TOPIC_ID" != "error" ] && [ -n "$TOPIC_ID" ]; then
|
||||
log_success "Smart contract messaging test passed - Topic: $TOPIC_ID"
|
||||
else
|
||||
log_warning "Smart contract messaging test failed"
|
||||
fi
|
||||
|
||||
log_success "AI operations testing completed"
|
||||
}
|
||||
|
||||
# ── Comprehensive Status ───────────────────────────────────────────
|
||||
show_comprehensive_status() {
|
||||
log_info "Comprehensive AITBC + OpenClaw + AI Operations Status"
|
||||
echo ""
|
||||
|
||||
# Basic status
|
||||
show_multi_node_status
|
||||
echo ""
|
||||
|
||||
# AI operations status
|
||||
log_info "AI Operations Status:"
|
||||
cd "$AITBC_DIR"
|
||||
source venv/bin/activate
|
||||
|
||||
# Check AI agents
|
||||
AI_AGENTS=$(./aitbc-cli agent list 2>/dev/null | grep -c "agent_" || echo "0")
|
||||
echo " AI Agents Created: $AI_AGENTS"
|
||||
|
||||
# Check resource allocation
|
||||
if ./aitbc-cli resource status &>/dev/null; then
|
||||
echo " Resource Management: Operational"
|
||||
else
|
||||
echo " Resource Management: Not operational"
|
||||
fi
|
||||
|
||||
# Check marketplace
|
||||
if ./aitbc-cli marketplace --action list &>/dev/null; then
|
||||
echo " AI Marketplace: Operational"
|
||||
else
|
||||
echo " AI Marketplace: Not operational"
|
||||
fi
|
||||
|
||||
# Check smart contract messaging
|
||||
if curl -s "$GENESIS_RPC/rpc/messaging/topics" &>/dev/null; then
|
||||
TOPICS_COUNT=$(curl -s "$GENESIS_RPC/rpc/messaging/topics" | jq '.total_topics // 0' 2>/dev/null || echo "0")
|
||||
echo " Smart Contract Messaging: Operational ($TOPICS_COUNT topics)"
|
||||
else
|
||||
echo " Smart Contract Messaging: Not operational"
|
||||
fi
|
||||
|
||||
echo ""
|
||||
log_info "Health Check:"
|
||||
if [ -f /tmp/aitbc1_heartbeat.py ]; then
|
||||
python3 /tmp/aitbc1_heartbeat.py
|
||||
else
|
||||
log_warning "Heartbeat script not found"
|
||||
fi
|
||||
}
|
||||
|
||||
ai-setup)
|
||||
setup_ai_operations
|
||||
;;
|
||||
ai-test)
|
||||
test_ai_operations
|
||||
;;
|
||||
comprehensive)
|
||||
show_comprehensive_status
|
||||
;;
|
||||
help)
|
||||
echo "Usage: $0 {setup|test|status|ai-setup|ai-test|comprehensive|help}"
|
||||
echo " setup — Verify prerequisites and test agent communication"
|
||||
echo " test — Run integration tests"
|
||||
echo " status — Show current multi-node status"
|
||||
echo " ai-setup — Setup AI operations and agents"
|
||||
echo " ai-test — Test AI operations functionality"
|
||||
echo " comprehensive — Show comprehensive status including AI operations"
|
||||
echo " help — Show this help"
|
||||
;;
|
||||
*)
|
||||
log_error "Unknown command: $1"
|
||||
main help
|
||||
exit 1
|
||||
;;
|
||||
esac
|
||||
}
|
||||
|
||||
main "$@"
|
||||
205
scripts/utils/workspace-manager.sh
Executable file
205
scripts/utils/workspace-manager.sh
Executable file
@@ -0,0 +1,205 @@
|
||||
#!/bin/bash
|
||||
# AITBC Workspace Management Script
|
||||
# Handles setup, cleanup, and management of external workspaces
|
||||
|
||||
set -euo pipefail
|
||||
|
||||
# Configuration
|
||||
WORKSPACE_BASE="/var/lib/aitbc-workspaces"
|
||||
REPO_URL="http://10.0.3.107:3000/oib/aitbc.git"
|
||||
GITEA_TOKEN="${GITEA_TOKEN:-b8fbb3e7e6cecf3a01f8a242fc652631c6dfd010}"
|
||||
|
||||
# Colors for output
|
||||
RED='\033[0;31m'
|
||||
GREEN='\033[0;32m'
|
||||
YELLOW='\033[1;33m'
|
||||
BLUE='\033[0;34m'
|
||||
NC='\033[0m' # No Color
|
||||
|
||||
# Logging functions
|
||||
log_info() {
|
||||
echo -e "${BLUE}[INFO]${NC} $1"
|
||||
}
|
||||
|
||||
log_success() {
|
||||
echo -e "${GREEN}[SUCCESS]${NC} $1"
|
||||
}
|
||||
|
||||
log_warning() {
|
||||
echo -e "${YELLOW}[WARNING]${NC} $1"
|
||||
}
|
||||
|
||||
log_error() {
|
||||
echo -e "${RED}[ERROR]${NC} $1"
|
||||
}
|
||||
|
||||
# Create workspace base directory
|
||||
ensure_workspace_base() {
|
||||
if [[ ! -d "$WORKSPACE_BASE" ]]; then
|
||||
log_info "Creating workspace base directory: $WORKSPACE_BASE"
|
||||
sudo mkdir -p "$WORKSPACE_BASE"
|
||||
sudo chmod 755 "$WORKSPACE_BASE"
|
||||
log_success "Workspace base directory created"
|
||||
fi
|
||||
}
|
||||
|
||||
# Setup a specific workspace
|
||||
setup_workspace() {
|
||||
local workspace_type="$1"
|
||||
local workspace_dir="$WORKSPACE_BASE/$workspace_type"
|
||||
|
||||
log_info "=== Setting up $workspace_type workspace ==="
|
||||
|
||||
# Cleanup existing workspace
|
||||
if [[ -d "$workspace_dir" ]]; then
|
||||
log_warning "Removing existing workspace: $workspace_dir"
|
||||
rm -rf "$workspace_dir"
|
||||
fi
|
||||
|
||||
# Create new workspace
|
||||
mkdir -p "$workspace_dir"
|
||||
cd "$workspace_dir"
|
||||
|
||||
# Clone repository
|
||||
log_info "Cloning repository to: $workspace_dir/repo"
|
||||
if ! git clone "$REPO_URL" repo; then
|
||||
log_error "Failed to clone repository"
|
||||
return 1
|
||||
fi
|
||||
|
||||
cd repo
|
||||
log_success "✅ $workspace_type workspace ready at $workspace_dir/repo"
|
||||
log_info "Current directory: $(pwd)"
|
||||
log_info "Repository contents:"
|
||||
ls -la | head -10
|
||||
|
||||
# Set git config for CI
|
||||
git config --global http.sslVerify false
|
||||
git config --global http.postBuffer 1048576000
|
||||
|
||||
return 0
|
||||
}
|
||||
|
||||
# Cleanup all workspaces
|
||||
cleanup_all_workspaces() {
|
||||
log_info "=== Cleaning up all workspaces ==="
|
||||
|
||||
if [[ -d "$WORKSPACE_BASE" ]]; then
|
||||
log_warning "Removing workspace base directory: $WORKSPACE_BASE"
|
||||
rm -rf "$WORKSPACE_BASE"
|
||||
log_success "All workspaces cleaned up"
|
||||
else
|
||||
log_info "No workspaces to clean up"
|
||||
fi
|
||||
}
|
||||
|
||||
# List all workspaces
|
||||
list_workspaces() {
|
||||
log_info "=== AITBC Workspaces ==="
|
||||
|
||||
if [[ ! -d "$WORKSPACE_BASE" ]]; then
|
||||
log_info "No workspace base directory found"
|
||||
return 0
|
||||
fi
|
||||
|
||||
log_info "Workspace base: $WORKSPACE_BASE"
|
||||
echo
|
||||
|
||||
for workspace in "$WORKSPACE_BASE"/*; do
|
||||
if [[ -d "$workspace" ]]; then
|
||||
local workspace_name=$(basename "$workspace")
|
||||
local size=$(du -sh "$workspace" 2>/dev/null | cut -f1)
|
||||
local files=$(find "$workspace" -type f 2>/dev/null | wc -l)
|
||||
|
||||
echo "📁 $workspace_name"
|
||||
echo " Size: $size"
|
||||
echo " Files: $files"
|
||||
echo " Path: $workspace"
|
||||
echo
|
||||
fi
|
||||
done
|
||||
}
|
||||
|
||||
# Check workspace status
|
||||
check_workspace() {
|
||||
local workspace_type="$1"
|
||||
local workspace_dir="$WORKSPACE_BASE/$workspace_type"
|
||||
|
||||
log_info "=== Checking $workspace_type workspace ==="
|
||||
|
||||
if [[ ! -d "$workspace_dir" ]]; then
|
||||
log_warning "Workspace does not exist: $workspace_dir"
|
||||
return 1
|
||||
fi
|
||||
|
||||
if [[ ! -d "$workspace_dir/repo" ]]; then
|
||||
log_warning "Repository not found in workspace: $workspace_dir/repo"
|
||||
return 1
|
||||
fi
|
||||
|
||||
cd "$workspace_dir/repo"
|
||||
|
||||
local git_status=$(git status --porcelain 2>/dev/null | wc -l)
|
||||
local current_branch=$(git rev-parse --abbrev-ref HEAD 2>/dev/null || echo "unknown")
|
||||
local last_commit=$(git log -1 --format="%h %s" 2>/dev/null || echo "unknown")
|
||||
local workspace_size=$(du -sh "$workspace_dir" 2>/dev/null | cut -f1)
|
||||
|
||||
echo "📊 Workspace Status:"
|
||||
echo " Path: $workspace_dir/repo"
|
||||
echo " Size: $workspace_size"
|
||||
echo " Branch: $current_branch"
|
||||
echo " Modified files: $git_status"
|
||||
echo " Last commit: $last_commit"
|
||||
|
||||
return 0
|
||||
}
|
||||
|
||||
# Main function
|
||||
main() {
|
||||
local command="${1:-help}"
|
||||
|
||||
case "$command" in
|
||||
"setup")
|
||||
ensure_workspace_base
|
||||
setup_workspace "${2:-python-packages}"
|
||||
;;
|
||||
"cleanup")
|
||||
cleanup_all_workspaces
|
||||
;;
|
||||
"list")
|
||||
list_workspaces
|
||||
;;
|
||||
"check")
|
||||
check_workspace "${2:-python-packages}"
|
||||
;;
|
||||
"help"|*)
|
||||
echo "AITBC Workspace Management Script"
|
||||
echo
|
||||
echo "Usage: $0 <command> [args]"
|
||||
echo
|
||||
echo "Commands:"
|
||||
echo " setup [workspace] Setup a workspace (default: python-packages)"
|
||||
echo " cleanup Clean up all workspaces"
|
||||
echo " list List all workspaces"
|
||||
echo " check [workspace] Check workspace status"
|
||||
echo " help Show this help"
|
||||
echo
|
||||
echo "Available workspaces:"
|
||||
echo " python-packages"
|
||||
echo " javascript-packages"
|
||||
echo " security-tests"
|
||||
echo " integration-tests"
|
||||
echo " compatibility-tests"
|
||||
echo
|
||||
echo "Examples:"
|
||||
echo " $0 setup python-packages"
|
||||
echo " $0 setup javascript-packages"
|
||||
echo " $0 check python-packages"
|
||||
echo " $0 list"
|
||||
echo " $0 cleanup"
|
||||
;;
|
||||
esac
|
||||
}
|
||||
|
||||
# Run main function
|
||||
main "$@"
|
||||
Reference in New Issue
Block a user