v2: workflows bootstrap in downloader; Dockerfile adds Claude Code, hf tooling, no comfy autostart
Browse files- docker/Dockerfile +37 -13
- docker/README.md +26 -15
- docker/start-comfy.sh +8 -4
- download_missing_models.sh +11 -0
docker/Dockerfile
CHANGED
|
@@ -1,12 +1,16 @@
|
|
| 1 |
# ComfyUI Qwen-Image-Edit base image (H100 / RunPod)
|
| 2 |
#
|
| 3 |
-
# NOTE:
|
| 4 |
-
# assembled
|
| 5 |
-
#
|
| 6 |
-
#
|
| 7 |
#
|
| 8 |
-
#
|
| 9 |
-
# docker
|
|
|
|
|
|
|
|
|
|
|
|
|
| 10 |
|
| 11 |
FROM runpod/pytorch:1.0.2-cu1281-torch280-ubuntu2404
|
| 12 |
|
|
@@ -23,16 +27,36 @@ RUN git clone https://github.com/rgthree/rgthree-comfy.git /ComfyUI/custom_nodes
|
|
| 23 |
cd /ComfyUI/custom_nodes/rgthree-comfy && git checkout ${RGTHREE_COMMIT} && \
|
| 24 |
pip install comfyui-manager==4.2.2
|
| 25 |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 26 |
# Manager config baked in: security_level=weak, network_mode=personal_cloud
|
| 27 |
-
COPY config.ini /ComfyUI/user/__manager/config.ini
|
| 28 |
-
COPY comfy.settings.json /ComfyUI/user/default/comfy.settings.json
|
| 29 |
-
COPY workflows/ /ComfyUI/user/default/workflows/
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 30 |
|
| 31 |
# Startup: `comfy` runs ComfyUI (prefers /workspace/ComfyUI when a volume is
|
| 32 |
-
# attached)
|
| 33 |
-
|
| 34 |
-
COPY
|
| 35 |
-
|
|
|
|
| 36 |
|
| 37 |
EXPOSE 7865
|
| 38 |
CMD ["/start-comfy.sh"]
|
|
|
|
| 1 |
# ComfyUI Qwen-Image-Edit base image (H100 / RunPod)
|
| 2 |
#
|
| 3 |
+
# NOTE: published plx1029/comfyui-qwen tags were NOT built from this file β they
|
| 4 |
+
# were assembled daemonlessly (v1: crane append on the pod; v2: skopeo + umoci).
|
| 5 |
+
# This Dockerfile is the reproducible equivalent: building it on any machine
|
| 6 |
+
# with Docker produces the same setup.
|
| 7 |
#
|
| 8 |
+
# Build from the REPO ROOT (context needs download_missing_models.sh):
|
| 9 |
+
# docker build -t plx1029/comfyui-qwen:v2 -f docker/Dockerfile .
|
| 10 |
+
# docker push plx1029/comfyui-qwen:v2
|
| 11 |
+
#
|
| 12 |
+
# No secrets are baked into this image (it is public). The model-download
|
| 13 |
+
# script prompts for your Hugging Face token at runtime (or reads $HF_TOKEN).
|
| 14 |
|
| 15 |
FROM runpod/pytorch:1.0.2-cu1281-torch280-ubuntu2404
|
| 16 |
|
|
|
|
| 27 |
cd /ComfyUI/custom_nodes/rgthree-comfy && git checkout ${RGTHREE_COMMIT} && \
|
| 28 |
pip install comfyui-manager==4.2.2
|
| 29 |
|
| 30 |
+
# Hugging Face hub tooling for fast model downloads (hf_transfer is best-effort:
|
| 31 |
+
# hub >= 1.x ships fast Xet downloads built in and dropped the extra)
|
| 32 |
+
RUN pip install -U "huggingface_hub[hf_transfer]" || pip install -U huggingface_hub && \
|
| 33 |
+
(pip install hf_transfer || true)
|
| 34 |
+
|
| 35 |
+
# Claude Code CLI, on PATH for all shells, with bypassPermissions as the
|
| 36 |
+
# default permission mode (this is a throwaway pod environment)
|
| 37 |
+
RUN curl -fsSL https://claude.ai/install.sh | bash && \
|
| 38 |
+
ln -sf /root/.local/bin/claude /usr/local/bin/claude && \
|
| 39 |
+
mkdir -p /root/.claude && \
|
| 40 |
+
printf '{\n "permissions": {\n "defaultMode": "bypassPermissions"\n }\n}\n' > /root/.claude/settings.json && \
|
| 41 |
+
printf '{\n "bypassPermissionsModeAccepted": true\n}\n' > /root/.claude.json
|
| 42 |
+
ENV PATH="/root/.local/bin:${PATH}"
|
| 43 |
+
|
| 44 |
# Manager config baked in: security_level=weak, network_mode=personal_cloud
|
| 45 |
+
COPY docker/config.ini /ComfyUI/user/__manager/config.ini
|
| 46 |
+
COPY docker/comfy.settings.json /ComfyUI/user/default/comfy.settings.json
|
| 47 |
+
COPY docker/workflows/ /ComfyUI/user/default/workflows/
|
| 48 |
+
|
| 49 |
+
# Model downloader: picks workflows, finds their models in the HF repo
|
| 50 |
+
# (aleph65/ComfyUI), downloads the missing ones into place. Prompts for the
|
| 51 |
+
# HF token; bootstraps /workspace/workflows from the repo if absent.
|
| 52 |
+
COPY download_missing_models.sh /usr/local/bin/download_missing_models.sh
|
| 53 |
|
| 54 |
# Startup: `comfy` runs ComfyUI (prefers /workspace/ComfyUI when a volume is
|
| 55 |
+
# attached). ComfyUI is NOT auto-started; run `comfy` yourself, or set
|
| 56 |
+
# COMFY_AUTOSTART=true in the pod env to restore the old behaviour.
|
| 57 |
+
COPY docker/comfy /usr/local/bin/comfy
|
| 58 |
+
COPY docker/start-comfy.sh /start-comfy.sh
|
| 59 |
+
RUN chmod +x /usr/local/bin/comfy /start-comfy.sh /usr/local/bin/download_missing_models.sh
|
| 60 |
|
| 61 |
EXPOSE 7865
|
| 62 |
CMD ["/start-comfy.sh"]
|
docker/README.md
CHANGED
|
@@ -8,36 +8,47 @@ Everything from the manual setup is baked in β **no reinstalling on new pods**
|
|
| 8 |
- comfyui-manager 4.2.2 + all pip deps (65 packages) preinstalled system-wide
|
| 9 |
- Manager config baked: `security_level = weak`, `network_mode = personal_cloud`
|
| 10 |
- Workflows baked into the workflow browser: `qwen-loras-very-good-nsfw.json`, `qwen-edit-nsfw.json`
|
| 11 |
-
-
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 12 |
|
| 13 |
Models are NOT in the image (keep them on the network volume, as before).
|
|
|
|
|
|
|
| 14 |
|
| 15 |
## Using it on RunPod
|
| 16 |
|
| 17 |
-
1. Create a template with container image `plx1029/comfyui-qwen:
|
| 18 |
2. Expose HTTP port **7865** (plus 8888/22 as usual).
|
| 19 |
3. Attach your network volume at `/workspace`.
|
|
|
|
| 20 |
|
| 21 |
-
|
| 22 |
- uses `/workspace/ComfyUI` if it exists (your current volume β models already there);
|
| 23 |
-
- otherwise seeds a fresh `/workspace/ComfyUI` from the baked-in copy
|
| 24 |
-
- SSH / Jupyter / nginx from the stock RunPod start script
|
| 25 |
|
| 26 |
-
|
| 27 |
-
terminal to start it by hand. `COMFY_PORT` overrides the port.
|
| 28 |
|
| 29 |
## How the image was built
|
| 30 |
|
| 31 |
-
No Docker daemon exists on RunPod pods, so
|
| 32 |
-
|
| 33 |
-
|
| 34 |
-
|
| 35 |
-
|
| 36 |
|
| 37 |
`Dockerfile` in this directory is the reproducible equivalent for rebuilding on
|
| 38 |
-
any machine with real Docker
|
|
|
|
| 39 |
|
| 40 |
```bash
|
| 41 |
-
docker build -t plx1029/comfyui-qwen:
|
| 42 |
-
docker push plx1029/comfyui-qwen:
|
| 43 |
```
|
|
|
|
| 8 |
- comfyui-manager 4.2.2 + all pip deps (65 packages) preinstalled system-wide
|
| 9 |
- Manager config baked: `security_level = weak`, `network_mode = personal_cloud`
|
| 10 |
- Workflows baked into the workflow browser: `qwen-loras-very-good-nsfw.json`, `qwen-edit-nsfw.json`
|
| 11 |
+
- **v2:** `huggingface_hub` + `hf_transfer` preinstalled for fast model downloads
|
| 12 |
+
- **v2:** [Claude Code](https://claude.com/claude-code) CLI preinstalled (`claude`), on PATH,
|
| 13 |
+
with `bypassPermissions` as the default permission mode
|
| 14 |
+
- **v2:** `download_missing_models.sh` on PATH β pick workflows, it fetches their
|
| 15 |
+
missing models from `hf.co/aleph65/ComfyUI` into place (prompts for HF token;
|
| 16 |
+
bootstraps `/workspace/workflows` from the repo if absent)
|
| 17 |
+
- **v2:** ComfyUI **no longer auto-starts** β run `comfy` yourself, or set
|
| 18 |
+
`COMFY_AUTOSTART=true` in the pod env for the old behaviour (port **7865**,
|
| 19 |
+
log: `/workspace/comfyui.log`)
|
| 20 |
|
| 21 |
Models are NOT in the image (keep them on the network volume, as before).
|
| 22 |
+
No secrets are baked in either (the image is public) β the download script asks
|
| 23 |
+
for your Hugging Face token at runtime, or reads it from `$HF_TOKEN`.
|
| 24 |
|
| 25 |
## Using it on RunPod
|
| 26 |
|
| 27 |
+
1. Create a template with container image `plx1029/comfyui-qwen:v2`.
|
| 28 |
2. Expose HTTP port **7865** (plus 8888/22 as usual).
|
| 29 |
3. Attach your network volume at `/workspace`.
|
| 30 |
+
4. In a terminal: `download_missing_models.sh` to fetch models, then `comfy` to start.
|
| 31 |
|
| 32 |
+
When ComfyUI starts it:
|
| 33 |
- uses `/workspace/ComfyUI` if it exists (your current volume β models already there);
|
| 34 |
+
- otherwise seeds a fresh `/workspace/ComfyUI` from the baked-in copy;
|
| 35 |
+
- SSH / Jupyter / nginx from the stock RunPod start script work normally either way.
|
| 36 |
|
| 37 |
+
`COMFY_PORT` overrides the port. `COMFY_AUTOSTART=true` restores auto-start on boot.
|
|
|
|
| 38 |
|
| 39 |
## How the image was built
|
| 40 |
|
| 41 |
+
No Docker daemon exists on RunPod pods, so images are assembled daemonlessly:
|
| 42 |
+
v1 with [`crane`](https://github.com/google/go-containerregistry) (pip-delta +
|
| 43 |
+
git clones appended as one OCI layer); v2 with `skopeo` + `umoci` (unpack v1,
|
| 44 |
+
apply changes in a chroot, repack the delta as a new layer) β the 20 GB base is
|
| 45 |
+
never re-uploaded.
|
| 46 |
|
| 47 |
`Dockerfile` in this directory is the reproducible equivalent for rebuilding on
|
| 48 |
+
any machine with real Docker (build from the repo root β the context needs
|
| 49 |
+
`download_missing_models.sh`):
|
| 50 |
|
| 51 |
```bash
|
| 52 |
+
docker build -t plx1029/comfyui-qwen:v2 -f docker/Dockerfile .
|
| 53 |
+
docker push plx1029/comfyui-qwen:v2
|
| 54 |
```
|
docker/start-comfy.sh
CHANGED
|
@@ -1,9 +1,10 @@
|
|
| 1 |
#!/bin/bash
|
| 2 |
-
# Image CMD:
|
| 3 |
-
#
|
| 4 |
-
# Set COMFY_AUTOSTART=
|
|
|
|
| 5 |
|
| 6 |
-
if [[ "${COMFY_AUTOSTART:-
|
| 7 |
LOG=/workspace/comfyui.log
|
| 8 |
[[ -d /workspace && -w /workspace ]] || LOG=/var/log/comfyui.log
|
| 9 |
(
|
|
@@ -14,6 +15,9 @@ if [[ "${COMFY_AUTOSTART:-true}" != "false" ]]; then
|
|
| 14 |
done
|
| 15 |
) &
|
| 16 |
echo "ComfyUI starting in background (log: $LOG, port ${COMFY_PORT:-7865})"
|
|
|
|
|
|
|
|
|
|
| 17 |
fi
|
| 18 |
|
| 19 |
exec /start.sh
|
|
|
|
| 1 |
#!/bin/bash
|
| 2 |
+
# Image CMD: hand off to the stock RunPod /start.sh (SSH, Jupyter, nginx).
|
| 3 |
+
# ComfyUI does NOT auto-start β run `comfy` yourself when you're ready.
|
| 4 |
+
# Set COMFY_AUTOSTART=true in the pod env to restore the old auto-start
|
| 5 |
+
# behaviour (background loop with auto-restart).
|
| 6 |
|
| 7 |
+
if [[ "${COMFY_AUTOSTART:-false}" == "true" ]]; then
|
| 8 |
LOG=/workspace/comfyui.log
|
| 9 |
[[ -d /workspace && -w /workspace ]] || LOG=/var/log/comfyui.log
|
| 10 |
(
|
|
|
|
| 15 |
done
|
| 16 |
) &
|
| 17 |
echo "ComfyUI starting in background (log: $LOG, port ${COMFY_PORT:-7865})"
|
| 18 |
+
else
|
| 19 |
+
echo "ComfyUI not auto-started. Run 'comfy' to start it (port ${COMFY_PORT:-7865})."
|
| 20 |
+
echo "Run 'download_missing_models.sh' to fetch models for your workflows."
|
| 21 |
fi
|
| 22 |
|
| 23 |
exec /start.sh
|
download_missing_models.sh
CHANGED
|
@@ -173,6 +173,17 @@ def main():
|
|
| 173 |
dry_run = "--dry-run" in argv
|
| 174 |
|
| 175 |
cleanup_debris()
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 176 |
files = sorted(glob.glob(os.path.join(WORKFLOWS_DIR, "*.json")))
|
| 177 |
if not files:
|
| 178 |
sys.exit(f"No workflow JSONs found in {WORKFLOWS_DIR}")
|
|
|
|
| 173 |
dry_run = "--dry-run" in argv
|
| 174 |
|
| 175 |
cleanup_debris()
|
| 176 |
+
|
| 177 |
+
if not os.path.isdir(WORKFLOWS_DIR):
|
| 178 |
+
print(f"{C_YELLOW}{WORKFLOWS_DIR} not found β downloading workflows from hf.co/{REPO_ID} ...{C_RESET}")
|
| 179 |
+
from huggingface_hub import snapshot_download
|
| 180 |
+
snapshot_download(
|
| 181 |
+
repo_id=REPO_ID,
|
| 182 |
+
allow_patterns=["workflows/*.json"],
|
| 183 |
+
local_dir=WORKSPACE,
|
| 184 |
+
token=os.environ.get("HF_TOKEN"),
|
| 185 |
+
)
|
| 186 |
+
|
| 187 |
files = sorted(glob.glob(os.path.join(WORKFLOWS_DIR, "*.json")))
|
| 188 |
if not files:
|
| 189 |
sys.exit(f"No workflow JSONs found in {WORKFLOWS_DIR}")
|