Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Add docker files #1418

Merged
merged 48 commits into from
Feb 26, 2024
Merged
Show file tree
Hide file tree
Changes from 43 commits
Commits
Show all changes
48 commits
Select commit Hold shift + click to select a range
97769de
Add docker files
whitehara Dec 15, 2023
ef5da9d
Merge branch 'main' into docker-build
whitehara Dec 15, 2023
5b30983
Add python precompiled cache file in the image
whitehara Dec 16, 2023
5b30804
Merge branch 'main' into docker-build
whitehara Dec 16, 2023
79ba09c
Merge branch 'main' into docker-build
whitehara Dec 17, 2023
992979b
Merge branch 'main' into docker-build
whitehara Dec 17, 2023
14b1acd
Add Notes in docker.md
whitehara Dec 18, 2023
b68807b
Merge branch 'main' into docker-build
whitehara Dec 18, 2023
45b1bdd
Merge branch 'main' into docker-build
whitehara Dec 19, 2023
3af1528
Merge branch 'main' into docker-build
whitehara Dec 22, 2023
ca45144
Create docker-publish.yml
whitehara Dec 22, 2023
3cd3c7e
Merge branch 'main' into docker-build
whitehara Dec 29, 2023
40e716b
Merge branch 'main' into docker
whitehara Dec 29, 2023
8072641
Merge branch 'main' into docker-build
whitehara Dec 31, 2023
c07de3d
Merge branch 'main' into docker
whitehara Dec 31, 2023
854a4fd
Modify docker-compose.yml not to use the bind mount
whitehara Dec 31, 2023
ad9fc1e
Merge branch 'lllyasviel:main' into docker-build
whitehara Jan 1, 2024
81a45ed
Merge branch 'docker' into docker-build
whitehara Jan 1, 2024
ac5af9f
Update torch version
whitehara Jan 1, 2024
c37f540
Merge branch 'main' into docker-build
whitehara Jan 2, 2024
17e9811
Merge branch 'main' into docker-build
whitehara Jan 6, 2024
e5cc831
Change --share to --listen
whitehara Jan 6, 2024
70a8626
Merge branch 'main' into docker
whitehara Jan 6, 2024
19aa714
Update torch version
whitehara Jan 6, 2024
b5ccc63
Change '--share' to '--listen`
whitehara Jan 6, 2024
416448b
adjust code comments
mashb1t Jan 6, 2024
1b094f3
Merge branch 'main' into docker-build
whitehara Jan 8, 2024
d79de68
Merge branch 'main' into docker-build
whitehara Jan 9, 2024
6d9d2b3
Merge branch 'main' into docker-build
whitehara Jan 12, 2024
b05be6f
Merge branch 'main' into docker-build
whitehara Jan 28, 2024
97f27c1
Merge branch 'main' into docker
whitehara Feb 2, 2024
2c42a3e
Merge branch 'docker' of https://github.com/whitehara/Fooocus into do…
whitehara Feb 2, 2024
97ac2e3
Merge branch 'main' into docker-build
whitehara Feb 13, 2024
8b5b1b9
Update requirements-docker.txt
whitehara Feb 13, 2024
7c75e49
chore: code cleanup
mashb1t Feb 19, 2024
509a61b
CHange entry_with_update.py to launch.py in entrypoint.sh
whitehara Feb 19, 2024
66ec479
CHnage CMD in Dockerfile
whitehara Feb 19, 2024
dfa4da0
Change default CMDARGS to --listen in Dockerfile
whitehara Feb 19, 2024
b1ea926
Modify CMD in Dockerfile
whitehara Feb 19, 2024
6da2903
Fix docker-compose.yml
whitehara Feb 20, 2024
b32bcde
Merge branch 'docker-build' into docker
whitehara Feb 20, 2024
34d7617
Import files from models,outputs
whitehara Feb 20, 2024
4da6c44
Merge branch 'docker-build' into docker
whitehara Feb 20, 2024
ab528e1
docs: change wording in docker.md, change git clone URL, add quotes t…
mashb1t Feb 25, 2024
e838927
docs: remove docker publish github action, remove pre-built image fro…
mashb1t Feb 25, 2024
b48ff50
Modify modules versions for linux/arm64
whitehara Feb 25, 2024
6a5b5dc
docs: update docker readme
mashb1t Feb 26, 2024
6fb8f5f
Merge branch 'develop' into docker
mashb1t Feb 26, 2024
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
1 change: 1 addition & 0 deletions .dockerignore
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
.idea
58 changes: 58 additions & 0 deletions .github/workflows/docker-publish.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,58 @@
name: Docker

on:
push:
branches-ignore: [ "*" ]
# Publish semver tags as releases.
tags: [ '*' ]

jobs:
build:
runs-on: ubuntu-latest
permissions:
contents: read
packages: write
# This is used to complete the identity challenge
# with sigstore/fulcio when running outside of PRs.
id-token: write

steps:
- name: Checkout repository
uses: actions/checkout@v4

- name: Set up Docker Buildx
uses: docker/setup-buildx-action@v3

- name: Fooocus version check
id: vercheck-fooocus
run: |
sed -e "s/version *= *'\([0-9\.]*\)'/version=\1/p" \
-e d \
fooocus_version.py >> $GITHUB_OUTPUT
shell: bash

- name: Docker Fooocus meta
id: meta-fooocus
uses: docker/metadata-action@v5
with:
images: |
${{ github.repository_owner }}/fooocus
tags: |
type=semver,pattern={{version}},value=${{ steps.vercheck-fooocus.outputs.version }}

- name: Login to Docker Hub
uses: docker/login-action@v3
with:
username: ${{ secrets.DOCKERHUB_USERNAME }}
password: ${{ secrets.DOCKERHUB_TOKEN }}

- name: Build and push Docker image
id: build-and-push
uses: docker/build-push-action@v5
with:
context: .
push: ${{ github.event_name != 'pull_request' }}
tags: ${{ steps.meta-fooocus.outputs.tags }}
labels: ${{ steps.meta-fooocus.outputs.labels }}
cache-from: type=gha
cache-to: type=gha,mode=max
28 changes: 28 additions & 0 deletions Dockerfile
Original file line number Diff line number Diff line change
@@ -0,0 +1,28 @@
FROM nvidia/cuda:12.3.1-base-ubuntu22.04
ENV DEBIAN_FRONTEND noninteractive
ENV CMDARGS --listen

RUN apt-get update -y && \
apt-get install -y curl libgl1 libglib2.0-0 python3-pip python-is-python3 git && \
apt-get clean && \
rm -rf /var/lib/apt/lists/*

COPY requirements_docker.txt requirements_versions.txt /tmp/
RUN pip install --no-cache-dir -r /tmp/requirements_docker.txt -r /tmp/requirements_versions.txt && \
rm -f /tmp/requirements_docker.txt /tmp/requirements_versions.txt
RUN curl -fsL -o /usr/local/lib/python3.10/dist-packages/gradio/frpc_linux_amd64_v0.2 https://cdn-media.huggingface.co/frpc-gradio-0.2/frpc_linux_amd64 && \
chmod +x /usr/local/lib/python3.10/dist-packages/gradio/frpc_linux_amd64_v0.2

RUN adduser --disabled-password --gecos '' user && \
mkdir -p /content/app /content/data

COPY entrypoint.sh /content/
RUN chown -R user:user /content

WORKDIR /content
USER user

RUN git clone https://github.com/whitehara/Fooocus /content/app
RUN mv /content/app/models /content/app/models.org

CMD [ "sh", "-c", "/content/entrypoint.sh ${CMDARGS}" ]
38 changes: 38 additions & 0 deletions docker-compose.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,38 @@
version: '3.9'

volumes:
fooocus-data:

services:
app:
build: .
image: whitehara/fooocus
Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I would suggest changing the image name to something more generic. Maybe plainly fooocus?

ports:
- 7865:7865
environment:
- CMDARGS=--listen # Arguments for launch.py.
- DATADIR=/content/data # Directory which stores models, outputs dir
- config_path=/content/data/config.txt
- config_example_path=/content/data/config_modification_tutorial.txt
- path_checkpoints=/content/data/models/checkpoints/
- path_loras=/content/data/models/loras/
- path_embeddings=/content/data/models/embeddings/
- path_vae_approx=/content/data/models/vae_approx/
- path_upscale_models=/content/data/models/upscale_models/
- path_inpaint=/content/data/models/inpaint/
- path_controlnet=/content/data/models/controlnet/
- path_clip_vision=/content/data/models/clip_vision/
- path_fooocus_expansion=/content/data/models/prompt_expansion/fooocus_expansion/
- path_outputs=/content/app/outputs/ # Warning: If it is not located under '/content/app', you can't see history log!
volumes:
- fooocus-data:/content/data
#- ./models:/import/models # Once you import files, you don't need to mount again.
#- ./outputs:/import/outputs # Once you import files, you don't need to mount again.
tty: true
deploy:
resources:
reservations:
devices:
- driver: nvidia
device_ids: ['0']
capabilities: [compute, utility]
72 changes: 72 additions & 0 deletions docker.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,72 @@
# Fooocus on Docker

It's based on NVIDIA CUDA 12.3. See [Dockerfile](Dockerfile) for details.

PyTorch version is 2.1. See [requirements_docker.txt](requirements_docker.txt) for details.

## Quick start

**This is just an easy way for testing. Please also see [Notes](#notes) for using.**

Clone git, Then run the docker container `docker compose up --build`
It takes a time to build the container image.
When you see a messeage `Use the app with http://localhost:7865/` in the console message, you can access the URL on your browser.

Your models, outputs are stored into 'fooocus-data' volume which may be stored in '/var/lib/docker/volumes'.

## Use pre-built image

The pre-built image is provided at `whitehara/fooocus`
Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Same comment as above.

Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

we could even automate the pipeline for each main branch update (or directly optimise thr process and use Gitlab releases for that...) and tag it with the corresponding version

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Same comment as above.

If someone creates an official dockerhub account, I can modify the document for that. Then, I will stop providing my images in my dockerhub account.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

we could even automate the pipeline for each main branch update (or directly optimise thr process and use Gitlab releases for that...) and tag it with the corresponding version

I'm doing it in my repo. Please refer my Github Actions.

Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Sorry for the drive-by comment. I hadn't noticed you were already publishing the images to dockerhub. That makes sense. It wasn't my intention to suggest adding publishing images for this repo in this PR. Although that would be great!

I was just getting impatient 🤭. Thanks for your work!

Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@lllyasviel would you be willing to create a Dockerhub repository for Fooocus or shall i set it up + add the according actions to Github pushes (main) and/or releases?


You can modify 'docker-compose.yml', then `docker compose up`

Note: when you use the pre-built image, you need to make the 'fooocus-data' volume which permission is '777' ( all users can read/write.) before you run the container.
Otherwise, you will see the permission error.

## Details

### Update the container manually

When you are using `docker compose up --build` continuously, the container is not updated to the newest version of Fooocus automatically.
If you want to use the newest one, you need to run `git pull` before you run `docker compose up --build`

### Import models, outputs
If you want to import files from models, outputs folder, you can uncomment following settings in docker-compose.yml
```
#- ./models:/import/models # Once you import files, you don't need to mount again.
#- ./outputs:/import/outputs # Once you import files, you don't need to mount again.
```
Then run `docker compose up --build`, your files will be copied into /content/data/models, /content/data/outputs
Since /content/data is a persistent volume folder, your files will be there when you re-run 'docker compose up --build` without above volume settings.


### Paths inside the container

|Path|Details|
|-|-|
|/content/app|The application stored folder|
|/content/app/models.org|Original 'models' folder.<br> Files are copied to the '/content/app/models' which is symlinked to '/content/data/models' every time the container boots. (Existing files will not be overwritten.) |
|/content/data|Persistent volume mount point|
|/content/data/models|The folder is symlinked to '/content/app/models'|
|/content/data/outputs|The folder is symlinked to '/content/app/outputs'|

### Environments

You can change 'config.txt' parameters by using environments.
**The priority of using the environments is higher than the values defined in 'config.txt'. And they will be saved to the 'config_modification_tuorial.txt'**

Docker specified environments are there. They are used by 'entrypoint.sh'
|Environment|Details|
|-|-|
|DATADIR|'/content/data' location.|
|CMDARGS|Arguments for [entry_with_update.py](entry_with_update.py) which is called by [entrypoint.sh](entrypoint.sh)|
|config_path|'config.txt' location|
|config_example_path|'config_modification_tutorial.txt' location|

You can also use the same json key names and values explained in the 'config_modification_tutorial.txt' as the environments.
See samples in the [docker-compose.yml](docker-compose.yml)

## Notes

- Please keep 'path_outputs' under '/content/app'. Otherwise, you will see an error when you open the history log.
- Docker on Mac/Windows has a slow volume access problem when you use "bind mount" volume. When you see this problem, don't use "bind mount". Please refer to [this article](https://docs.docker.com/storage/volumes/#use-a-volume-with-docker-compose) for not using "bind mount".
33 changes: 33 additions & 0 deletions entrypoint.sh
Original file line number Diff line number Diff line change
@@ -0,0 +1,33 @@
#!/bin/bash

ORIGINALDIR=/content/app
# Use predefined DATADIR if it is defined
[[ x"${DATADIR}" == "x" ]] && DATADIR=/content/data

# Make persistent dir from original dir
function mklink () {
mkdir -p $DATADIR/$1
ln -s $DATADIR/$1 $ORIGINALDIR
}

# Copy old files from import dir
function import () {
(test -d /import/$1 && cd /import/$1 && cp -Rpn . $DATADIR/$1/)
}

cd $ORIGINALDIR

# models
mklink models
# Copy original files
(cd $ORIGINALDIR/models.org && cp -Rpn . $ORIGINALDIR/models/)
# Import old files
import models

# outputs
mklink outputs
# Import old files
import outputs

# Start application
python launch.py $*
26 changes: 22 additions & 4 deletions modules/config.py
Original file line number Diff line number Diff line change
Expand Up @@ -10,8 +10,16 @@
from modules.util import get_files_from_folder


config_path = os.path.abspath("./config.txt")
config_example_path = os.path.abspath("config_modification_tutorial.txt")
def get_config_path(key, default_value):
env = os.getenv(key)
if env is not None and isinstance(env, str):
print(f"Environment: {key} = {env}")
return env
else:
return os.path.abspath(default_value)

config_path = get_config_path('config_path', "./config.txt")
config_example_path = get_config_path('config_example_path', "config_modification_tutorial.txt")
config_dict = {}
always_save_keys = []
visited_keys = []
Expand Down Expand Up @@ -123,7 +131,13 @@ def get_dir_or_set_default(key, default_value):
if key not in always_save_keys:
always_save_keys.append(key)

v = config_dict.get(key, None)
v = os.getenv(key)
if v is not None:
print(f"Environment: {key} = {v}")
config_dict[key] = v
else:
v = config_dict.get(key, None)

if isinstance(v, str) and os.path.exists(v) and os.path.isdir(v):
return v
else:
Expand All @@ -146,13 +160,17 @@ def get_dir_or_set_default(key, default_value):
path_fooocus_expansion = get_dir_or_set_default('path_fooocus_expansion', '../models/prompt_expansion/fooocus_expansion')
path_outputs = get_path_output()


def get_config_item_or_set_default(key, default_value, validator, disable_empty_as_none=False):
global config_dict, visited_keys

if key not in visited_keys:
visited_keys.append(key)

v = os.getenv(key)
if v is not None:
print(f"Environment: {key} = {v}")
config_dict[key] = v

if key not in config_dict:
config_dict[key] = default_value
return default_value
Expand Down
2 changes: 1 addition & 1 deletion modules/util.py
Original file line number Diff line number Diff line change
Expand Up @@ -155,7 +155,7 @@ def generate_temp_filename(folder='./outputs/', extension='png'):
random_number = random.randint(1000, 9999)
filename = f"{time_string}_{random_number}.{extension}"
result = os.path.join(folder, date_string, filename)
return date_string, os.path.abspath(os.path.realpath(result)), filename
return date_string, os.path.abspath(result), filename


def get_files_from_folder(folder_path, exensions=None, name_filter=None):
Expand Down
4 changes: 4 additions & 0 deletions readme.md
Original file line number Diff line number Diff line change
Expand Up @@ -237,6 +237,10 @@ You can install Fooocus on Apple Mac silicon (M1 or M2) with macOS 'Catalina' or

Use `python entry_with_update.py --preset anime` or `python entry_with_update.py --preset realistic` for Fooocus Anime/Realistic Edition.

### Docker

See [docker.md](docker.md)

### Download Previous Version

See the guidelines [here](https://github.com/lllyasviel/Fooocus/discussions/1405).
Expand Down
7 changes: 7 additions & 0 deletions requirements_docker.txt
Original file line number Diff line number Diff line change
@@ -0,0 +1,7 @@
torch==2.2.0
torchvision==0.17.0
torchaudio==2.2.0
torchtext==0.17.0
torchdata==0.7.1
xformers==0.0.24
triton==2.2.0