mirror of
https://github.com/Comfy-Org/ComfyUI-Manager.git
synced 2025-12-16 18:02:58 +08:00
Remove package-level caching in cnr_utils and node_package modules to enable proper dynamic custom node installation and version switching without ComfyUI server restarts. Key Changes: - Remove @lru_cache decorators from version-sensitive functions - Remove cached_property from NodePackage for dynamic state updates - Add comprehensive test suite with parallel execution support - Implement version switching tests (CNR ↔ Nightly) - Add case sensitivity integration tests - Improve error handling and logging API Priority Rules (manager_core.py:1801): - Enabled-Priority: Show only enabled version when both exist - CNR-Priority: Show only CNR when both CNR and Nightly are disabled - Prevents duplicate package entries in /v2/customnode/installed API - Cross-match using cnr_id and aux_id for CNR ↔ Nightly detection Test Infrastructure: - 8 test files with 59 comprehensive test cases - Parallel test execution across 5 isolated environments - Automated test scripts with environment setup - Configurable timeout (60 minutes default) - Support for both master and dr-support-pip-cm branches Bug Fixes: - Fix COMFYUI_CUSTOM_NODES_PATH environment variable export - Resolve test fixture regression with module-level variables - Fix import timing issues in test configuration - Register pytest integration marker to eliminate warnings - Fix POSIX compliance in shell scripts (((var++)) → $((var + 1))) Documentation: - CNR_VERSION_MANAGEMENT_DESIGN.md v1.0 → v1.1 with API priority rules - Add test guides and execution documentation (TESTING_PROMPT.md) - Add security-enhanced installation guide - Create CLI migration guides and references - Document package version management 🤖 Generated with [Claude Code](https://claude.com/claude-code) Co-Authored-By: Claude <noreply@anthropic.com>
10 KiB
10 KiB
CLI Glob Migration - Implementation Todo List
📅 Project Timeline: 3.5 Days
🚀 Phase 1: Initial Setup & Import Changes (0.5 day)
Day 1 Morning
✅ Setup and Preparation (30 min)
- Read implementation context file
- Review glob APIs documentation
- Set up development environment
- Create backup of current CLI
🔄 Import Path Changes (1 hour)
- CRITICAL: Update import statements in
cm_cli/__main__.py:39-41# Change from: from ..legacy import manager_core as core from ..legacy.manager_core import unified_manager # Change to: from ..glob import manager_core as core from ..glob.manager_core import unified_manager - Test CLI loads without crashing
- Identify immediate import-related errors
🧪 Initial Testing (30 min)
- Test basic CLI help:
python -m comfyui_manager.cm_cli help - Test simple commands that should work:
python -m comfyui_manager.cm_cli show snapshot - Document all errors found
- Prioritize fixes needed
⚙️ Phase 2: Core Function Implementation (2 days)
Day 1 Afternoon + Day 2
🛠️ install_node() Function Update (3 hours)
File: cm_cli/__main__.py:187-235
Complexity: Medium
Tasks:
- Replace Git URL handling logic
# OLD (line ~191): if core.is_valid_url(node_spec_str): res = asyncio.run(core.gitclone_install(node_spec_str, no_deps=cmd_ctx.no_deps)) # NEW: if unified_manager.is_url_like(node_spec_str): repo_name = os.path.basename(node_spec_str) if repo_name.endswith('.git'): repo_name = repo_name[:-4] res = asyncio.run(unified_manager.repo_install( node_spec_str, repo_name, instant_execution=True, no_deps=cmd_ctx.no_deps )) - Test Git URL installation
- Test CNR package installation
- Verify error handling works correctly
- Update progress messages if needed
🔍 show_list() Function Rewrite - Installed-Only Approach (3 hours)
File: cm_cli/__main__.py:418-534
Complexity: High - Complete architectural change
New Approach: Show only installed nodepacks with on-demand info retrieval
Key Changes:
- ❌ Remove: Full cache loading (
get_custom_nodes()) - ❌ Remove: Support for
show all,show not-installed,show cnr - ✅ Add: Lightweight caching system for nodepack metadata
- ✅ Add: On-demand CNR API calls for additional info
Tasks:
-
Phase 2A: Lightweight Cache Implementation (1 hour)
class NodePackageCache: def __init__(self, cache_file_path: str): self.cache_file = cache_file_path self.cache_data = self._load_cache() def get_metadata(self, nodepack_id: str) -> dict: # Get cached metadata or fetch on-demand from CNR def update_metadata(self, nodepack_id: str, metadata: dict): # Update cache (called during install) -
Phase 2B: New show_list Implementation (1.5 hours)
def show_list(kind, simple=False): # Validate supported commands if kind not in ['installed', 'enabled', 'disabled']: print(f"Unsupported: 'show {kind}'. Use: installed/enabled/disabled") return # Get installed packages only all_packages = [] for packages in unified_manager.installed_node_packages.values(): all_packages.extend(packages) # Filter by status if kind == 'enabled': packages = [pkg for pkg in all_packages if pkg.is_enabled] elif kind == 'disabled': packages = [pkg for pkg in all_packages if not pkg.is_enabled] else: # 'installed' packages = all_packages -
Phase 2C: On-Demand Display with Cache (0.5 hour)
cache = NodePackageCache(cache_file_path) for package in packages: # Basic info from InstalledNodePackage status = "[ ENABLED ]" if package.is_enabled else "[ DISABLED ]" # Enhanced info from cache or on-demand cached_info = cache.get_metadata(package.id) name = cached_info.get('name', package.id) author = cached_info.get('author', 'Unknown') version = cached_info.get('version', 'Unknown') if simple: print(f"{name}@{version}") else: print(f"{status} {name:50} {package.id:30} (author: {author:20}) [{version}]")
Install-time Cache Update:
- Update install_node() to populate cache
# After successful installation in install_node() if install_success: metadata = cnr_utils.get_nodepackage_info(installed_package.id) cache.update_metadata(installed_package.id, metadata)
Testing:
- Test
show installed(enabled + disabled packages) - Test
show enabled(only enabled packages) - Test
show disabled(only disabled packages) - Test unsupported commands show helpful error
- Test
simple-showvariants work correctly - Test cache functionality (create, read, update)
- Test on-demand CNR info retrieval for cache misses
📝 get_all_installed_node_specs() Update (1 hour)
File: cm_cli/__main__.py:573-605
Complexity: Medium
Tasks:
- Rewrite using InstalledNodePackage
def get_all_installed_node_specs(): res = [] for packages in unified_manager.installed_node_packages.values(): for pack in packages: node_spec_str = f"{pack.id}@{pack.version}" res.append(node_spec_str) return res - Test with
update allcommand - Verify node spec format is correct
⚙️ Context Management Updates (1 hour)
File: cm_cli/__main__.py:117-134
Complexity: Low
Tasks:
- Remove load_nightly() call
def set_channel_mode(self, channel, mode): if mode is not None: self.mode = mode if channel is not None: self.channel = channel # OLD: asyncio.run(unified_manager.reload(...)) # OLD: asyncio.run(unified_manager.load_nightly(...)) # NEW: Just reload unified_manager.reload() - Test channel/mode switching still works
🧹 Phase 3: Feature Removal & Final Testing (1 day)
Day 3
❌ Remove Unavailable Features (2 hours)
Complexity: Low
deps-in-workflow Command Removal:
- Update deps_in_workflow() function (
cm_cli/__main__.py:1000-1050)@app.command("deps-in-workflow") def deps_in_workflow(...): print("[bold red]ERROR: This feature is not available in the current version.[/bold red]") print("The 'deps-in-workflow' feature has been removed.") print("Please use alternative workflow analysis tools.") sys.exit(1) - Test command shows proper error message
- Update help text to reflect removal
install-deps Command Update:
- Update install_deps() function (
cm_cli/__main__.py:1203-1250)# Remove extract_nodes_from_workflow usage (line ~1033) # Replace with error handling or alternative approach - Test with dependency files
🧪 Comprehensive Testing (4 hours)
Core Command Testing (2 hours):
-
Install Commands:
install <cnr-package>install <git-url>install all(if applicable)
-
Uninstall Commands:
uninstall <package>uninstall all
-
Enable/Disable Commands:
enable <package>disable <package>enable all/disable all
-
Update Commands:
update <package>update all
Show Commands Testing (1 hour):
show installedshow enabledshow disabledshow allshow not-installedsimple-showvariants
Advanced Features Testing (1 hour):
save-snapshotrestore-snapshotshow snapshotshow snapshot-listclearcli-only-mode
🐛 Bug Fixes & Polish (2 hours)
- Fix any errors found during testing
- Improve error messages
- Ensure output formatting consistency
- Performance optimization if needed
- Code cleanup and comments
📋 Daily Checklists
End of Day 1 Checklist:
- Imports successfully changed
- Basic CLI loading works
- install_node() handles both CNR and Git URLs
- No critical crashes in core functions
End of Day 2 Checklist:
- show_list() displays all package types correctly
- get_all_installed_node_specs() works with new data structure
- Context management updated
- Core functionality regression-free
End of Day 3 Checklist:
- All CLI commands tested and working
- Removed features show appropriate messages
- Output format acceptable to users
- No glob module modifications made
- Ready for code review
🎯 Success Criteria
Must Pass:
- All core commands functional (install/uninstall/enable/disable/update)
- show commands display accurate information
- No modifications to glob module
- CLI code changes < 200 lines
- No critical regressions
Bonus Points:
- Output format matches legacy closely
- Performance equals or exceeds legacy
- Error messages user-friendly
- Code is clean and maintainable
🚨 Emergency Contacts & Resources
If Stuck:
- Review:
CLI_PURE_GLOB_MIGRATION_PLAN.mdfor detailed technical specs - Reference:
CLI_IMPLEMENTATION_CONTEXT.mdfor current state - Debug: Use
print()statements to understand data structures - Fallback: Implement minimal working version first, polish later
Key Files to Reference:
comfyui_manager/glob/manager_core.py- UnifiedManager APIscomfyui_manager/common/node_package.py- InstalledNodePackage classcomfyui_manager/common/cnr_utils.py- CNR utilities
Remember: Focus on making it work first, then making it perfect. The constraint is NO glob modifications - CLI must adapt to glob's way of doing things.