Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
31 changes: 31 additions & 0 deletions .dockerignore
Original file line number Diff line number Diff line change
@@ -0,0 +1,31 @@
# This file should remain in sync with .gitignore. If you need to make changes,
# please add a comment explaining why. For items that must be removed, comment
# them out instead of deleting them.
__pycache__/
*.py[cod]
/output/
/input/
# This file prevents the image from building and would be overwritten by the
# /data volume in any case.
#!/input/example.png
/models/
/temp/
/custom_nodes/
!custom_nodes/example_node.py.example
extra_model_paths.yaml
/.vs
.vscode/
.idea/
venv/
.venv/
/web/extensions/*
!/web/extensions/logging.js.example
!/web/extensions/core/
/tests-ui/data/object_info.json
/user/
*.log
web_custom_versions/
.DS_Store
openapi.yaml
filtered-openapi.yaml
uv.lock
3 changes: 3 additions & 0 deletions .gitattributes
Original file line number Diff line number Diff line change
@@ -1,3 +1,6 @@
/web/assets/** linguist-generated
/web/** linguist-vendored
comfy_api_nodes/apis/__init__.py linguist-generated
# Force LF eol for Docker entrypoint (fix "exec: no such file or directory"
# error with CRLF checkouts)
entrypoint.sh text eol=lf
1 change: 1 addition & 0 deletions .gitignore
Original file line number Diff line number Diff line change
@@ -1,3 +1,4 @@
# If you modify this file, remember to update .dockerignore as well.
__pycache__/
*.py[cod]
/output/
Expand Down
82 changes: 82 additions & 0 deletions Dockerfile
Original file line number Diff line number Diff line change
@@ -0,0 +1,82 @@
# Docker buildfile for the ComfyUI image, with support for hardware
# acceleration, file ownership synchronization, custom nodes, and custom node
# managers.

# Use the recommended Python version 3.12, as specified in the README.
FROM python:3.12.11-bookworm

# Install cmake, which is an indirect installation dependencies
RUN apt-get update && apt-get install -y --no-install-recommends cmake

# Create a mount point for user-generated data.
RUN mkdir -p \
/data/input \
/data/output \
/data/temp \
/data/user

# Create a regular user whose UID and GID will match the host user's at runtime.
# Also create a home directory for this user (-m), as some common Python tools
# (such as uv) interact with the user’s home directory.
RUN useradd -m comfyui

# Install ComfyUI under /comfyui and set folder ownership to the comfyui user.
# With the legacy Docker builder (DOCKER_BUILDKIT=0), WORKDIR always creates missing
# directories as root (even if a different USER is active). To ensure the comfyui user
# can write inside, ownership must be fixed manually.
WORKDIR /comfyui
RUN chown comfyui:comfyui .

# Install ComfyUI as ComfyUI
USER comfyui

# Set up a Python virtual environment and configure it as the default Python.
#
# Reasons for using a virtual environment:
# - Some custom nodes use third-party tools like uv, which do not support
# user-level installations.
# - Custom node managers may install or update dependencies as the regular user,
# so a global installation is not an option.
# This leaves virtual environments as the only viable choice.
RUN python -m venv .venv
ENV PATH="/comfyui/.venv/bin:$PATH"

# Install Python dependencies. This step is also performed automatically by the
# entrypoint script, but doing it at build time reduces startup time on the
# first run.
COPY requirements.txt ./
RUN pip install --no-cache-dir -r requirements.txt

# Install ComfyUI and link the data mount points.
COPY . .
RUN ln -sf /data/* .

# Purely declarative: inform Docker and image users that this image is designed
# to listen on port 8188 for the web GUI.
EXPOSE 8188

# Declare persistent volumes:
# - /data: stores user-generated data from ComfyUI,
# - /comfyui/.venv: stores Python data generated by the entrypoint and custom
# node managers,
# - /comfyui/custom_nodes: stores custom nodes installed at runtime by custom
# node managers,
# - /comfyui/models: Stores models installed by model managers,
# - /home/comfyui: stores data from Python packages that may write outside the
# virtual environment and into the user’s home directory.
VOLUME [ "/data", "/comfyui/.venv", "/comfyui/custom_nodes", "/comfyui/models", "/home/comfyui" ]

# Switch back to root to run the entrypoint and to install additional system
# dependencies
USER root

# Configure entrypoint
RUN chmod +x entrypoint.sh
ENTRYPOINT [ "./entrypoint.sh" ]
CMD [ "python", "./main.py" ]

# Install additional system dependencies
ARG APT_EXTRA_PACKAGES
RUN apt-get install -y --no-install-recommends $APT_EXTRA_PACKAGES \
&& apt-get clean \
&& rm -rf /var/lib/apt/lists/*
29 changes: 29 additions & 0 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -46,6 +46,12 @@ ComfyUI lets you design and execute advanced stable diffusion pipelines using a
- Get the latest commits and completely portable.
- Available on Windows.

#### [Docker Install](#running-with-docker)
- Run ComfyUI inside an isolated Docker container
- Most secure way to run ComfyUI and custom node packs
- Requires Docker and Docker Compose
- Supports NVIDIA GPUs (Not tested on other hardware.)

#### [Manual Install](#manual-install-windows-linux)
Supports all operating systems and GPU types (NVIDIA, AMD, Intel, Apple Silicon, Ascend).

Expand Down Expand Up @@ -319,6 +325,29 @@ For models compatible with Iluvatar Extension for PyTorch. Here's a step-by-step
1. Install the Iluvatar Corex Toolkit by adhering to the platform-specific instructions on the [Installation](https://support.iluvatar.com/#/DocumentCentre?id=1&nameCenter=2&productId=520117912052801536)
2. Launch ComfyUI by running `python main.py`

## Running with Docker

Start by installing Docker, Docker Compose, and the NVIDIA Container Toolkit on
your host. Next, edit `compose.yaml` and update the `UID` and `GID` variables to
match your user. Additional fields are documented in the file for further
customization.

Once ready, build and run the image locally:

```shell
# (Re)build the Docker image. Run this before the first start, after updating
# ComfyUI, or after changing any build arguments in `compose.yaml`.
docker compose build
# Start ComfyUI. This reuses the most recently built image.
docker compose up
```

To stop and remove the container along with its volumes, run:

```shell
docker compose down -v
```

# Running

```python main.py```
Expand Down
42 changes: 42 additions & 0 deletions compose.yaml
Original file line number Diff line number Diff line change
@@ -0,0 +1,42 @@
# Docker Compose file to run ComfyUI locally using Docker.

services:
comfyui:
container_name: comfyui
build:
context: .
args:
# Declare additional system dependencies for custom nodes
APT_EXTRA_PACKAGES:

ports:
- 8188:8188

# Optional: enable GPU access for hardware acceleration.
deploy:
resources:
reservations:
devices:
- capabilities: [gpu]
volumes:
# Share custom nodes and models with the container.
- ./custom_nodes:/comfyui/custom_nodes
- ./models:/comfyui/models
# Optional: mount the user data directory.
#- data:/data/

environment:
# Overwrite the container user's UID and GID to match the host's. This
# allows files created by ComfyUI to be mounted on the host without
# permission issues.
UID: 1000
GID: 1000
# Declare additional Python packages to install. Useful when a custom node
# pack does not properly specify all its dependencies or relies on
# optional dependencies.
PIP_EXTRA_PACKAGES:

# Optional: Override the default command. In this case, configure ComfyUI to
# listen on all network interfaces (which is required when not using
# `network_mode=host`.)
command: python ./main.py --listen 0.0.0.0
75 changes: 75 additions & 0 deletions entrypoint.sh
Original file line number Diff line number Diff line change
@@ -0,0 +1,75 @@
#!/bin/sh

# Entrypoint script for the ComfyUI Docker image.

set -e

user="comfyui"
user_group="$user"

# Allow users to specify a UID and GID matching their own, so files created
# inside the container retain the same numeric ownership when mounted on the
# host.
if [ -n "$UID" ] && [ -n "$GID" ]; then
echo "[entrypoint] Setting user UID and GID..."
usermod -u "$UID" "$user" > /dev/null
groupmod -g "$GID" "$user_group"
else
echo "[entrypoint] Missing UID or GID environment variables; keeping default values."
fi


echo "[entrypoint] Changing directory ownership..."
chown -R "$user:$user_group" \
/data \
/comfyui \
/home/comfyui

# Add the user to the groups owning /dev/nvidia* devices to ensure CUDA access.
# Typically, these devices belong to a single "video" group, but to be safe, we
# add the user to each device's group individually.
echo "[entrypoint] Adding user to GPU device groups..."
for dev in /dev/nvidia*; do
# Known issue: There is no universal standard for group IDs across Linux
# systems, so this may add the user to unexpected groups. For example, the
# 'video' group on some systems uses GID 27, which corresponds to 'sudo' in
# the python:3.12 image. This should not cause serious problems.
group=$(ls -ld "$dev" | awk '{print $4}')
usermod -aG "$group" "$user"
done


# Install packages listed in ./requirements.txt, requirement files under
# ./custom_nodes, and any specified in PIP_EXTRA_PACKAGES. Also store a hash of
# all dependencies to detect when new or updated packages need to be installed.
packages_hash_file="/home/comfyui/pkghash"

packages_comfyui=$(cat requirements.txt)
packages_custom=$(find custom_nodes -name requirements.txt -exec cat {} \;)
packages_extras=$(echo "$PIP_EXTRA_PACKAGES" | tr ' ' '\n')

current_hash=$(
{
echo "$packages_comfyui"
echo "$packages_custom"
echo "$packages_extras"
} | sort | sha256sum | awk '{print $1}'
)

if [ ! -f "$packages_hash_file" ] || [ "$current_hash" != "$(cat $packages_hash_file)" ]; then
echo "[entrypoint] Installing new python dependencies, this might take a while..."
reqs="-r requirements.txt"
for req in custom_nodes/*/requirements.txt; do
[ -f "$req" ] && reqs="$reqs -r $req"
done

su -c "pip install -q --disable-pip-version-check --no-cache-dir $reqs $PIP_EXTRA_PACKAGES" comfyui
echo "$current_hash" > "$packages_hash_file"
else
echo "[entrypoint] Requirements unchanged, skipping install"
fi


# Run command as comfyui
echo "[entrypoint] Running command"
exec su -c "$*" comfyui