Metadata-Version: 2.4
Name: comfy-env
Version: 0.2.14
Summary: Environment management for ComfyUI custom nodes - CUDA wheel resolution and process isolation
Project-URL: Homepage, https://github.com/PozzettiAndrea/comfy-env
Project-URL: Repository, https://github.com/PozzettiAndrea/comfy-env
Project-URL: Issues, https://github.com/PozzettiAndrea/comfy-env/issues
Author: Andrea Pozzetti
License: MIT
License-File: LICENSE
Keywords: comfyui,cuda,environment,isolation,process,venv,wheels
Classifier: Development Status :: 3 - Alpha
Classifier: Intended Audience :: Developers
Classifier: License :: OSI Approved :: MIT License
Classifier: Programming Language :: Python :: 3.10
Classifier: Programming Language :: Python :: 3.11
Classifier: Programming Language :: Python :: 3.12
Classifier: Programming Language :: Python :: 3.13
Requires-Python: >=3.10
Requires-Dist: numpy
Requires-Dist: pip>=21.0
Requires-Dist: pre-commit
Requires-Dist: tomli-w>=1.0.0
Requires-Dist: tomli>=2.0.0
Requires-Dist: uv>=0.4.0
Description-Content-Type: text/markdown

# comfy-env

Environment management for ComfyUI custom nodes.

## Quick Start

```bash
pip install comfy-env
```

**1. Create `comfy-env-root.toml` in your node directory:**

```toml
[cuda]
packages = ["nvdiffrast", "pytorch3d"]

[apt]
packages = ["libgl1-mesa-glx"]

[node_reqs]
ComfyUI_essentials = "cubiq/ComfyUI_essentials"
```

PyPI deps go in `requirements.txt` (standard ComfyUI pattern).

**2. In `install.py`:**

```python
from comfy_env import install
install()
```

**3. In `prestartup_script.py`:**

```python
from comfy_env import setup_env
setup_env()
```

---

## Two Config Files

| File | Purpose |
|------|---------|
| `comfy-env-root.toml` | Main node config (root level) |
| `comfy-env.toml` | Isolated subfolder config |

### comfy-env-root.toml (main node)

```toml
[cuda]
packages = ["nvdiffrast", "pytorch3d"]

[apt]
packages = ["libgl1-mesa-glx"]

[dependencies]
cgal = "*"

[env_vars]
KMP_DUPLICATE_LIB_OK = "TRUE"

[node_reqs]
ComfyUI_essentials = "cubiq/ComfyUI_essentials"
```

PyPI deps -> `requirements.txt`

### comfy-env.toml (isolated folder)

```toml
python = "3.11"

[dependencies]
cgal = "*"

[pypi-dependencies]
trimesh = { version = "*", extras = ["easy"] }

[env_vars]
SOME_VAR = "value"
```

### What goes where?

| Section | Root | Isolated |
|---------|------|----------|
| `[cuda]` | [x] | [x] |
| `[apt]` | [x] | [x] |
| `[dependencies]` | [x] | [x] |
| `[env_vars]` | [x] | [x] |
| `[node_reqs]` | [x] | [ ] |
| `python = "X.Y"` | [ ] | [x] |
| `[pypi-dependencies]` | [ ] | [x] |

---

## Process Isolation

For nodes with conflicting dependencies:

```python
# In nodes/__init__.py
from pathlib import Path
from comfy_env import wrap_isolated_nodes

from .cgal import NODE_CLASS_MAPPINGS as cgal_mappings

NODE_CLASS_MAPPINGS = wrap_isolated_nodes(
    cgal_mappings,
    Path(__file__).parent / "cgal"  # Has comfy-env.toml
)
```

Each wrapped node runs in a subprocess with its own Python environment.

---

## CLI

```bash
comfy-env init              # Create comfy-env-root.toml
comfy-env init --isolated   # Create comfy-env.toml (for subfolders)
comfy-env install           # Install dependencies
comfy-env install --dry-run # Preview
comfy-env info              # Show runtime info
comfy-env doctor            # Verify packages
comfy-env apt-install       # Install system packages
```

---

## API

### install()

```python
from comfy_env import install
install()
```

### setup_env()

```python
from comfy_env import setup_env
setup_env()  # Call in prestartup_script.py
```

### wrap_isolated_nodes()

```python
from comfy_env import wrap_isolated_nodes
wrapped = wrap_isolated_nodes(NODE_CLASS_MAPPINGS, node_dir)
```

### Detection

```python
from comfy_env import RuntimeEnv, detect_cuda_version, detect_gpu

env = RuntimeEnv.detect()
print(env)  # Python 3.11, CUDA 12.8, PyTorch 2.8.0, GPU: RTX 4090
```

---

## Example

See [ComfyUI-GeometryPack](https://github.com/PozzettiAndrea/ComfyUI-GeometryPack):

- Multiple isolated environments (CGAL, Blender, GPU)
- Per-subdirectory `comfy-env.toml`
- Different Python versions

---

## Why?

**Why isolation?** ComfyUI nodes share one Python. Conflicts happen when:
- Node A needs torch 2.4, Node B needs torch 2.8
- Two packages bundle incompatible libomp
- Blender API requires Python 3.11

**Why CUDA wheels?** Installing nvdiffrast normally needs CUDA toolkit + C++ compiler + 30 min compilation. [cuda-wheels](https://pozzettiandrea.github.io/cuda-wheels/) provides pre-built wheels.

**How envs work:**
- Central cache: `~/.comfy-env/envs/`
- Marker files link nodes -> cached envs
- Config hash in name -> changes create new envs

---

## License

MIT
