Repository: nftblackmagic/sdwebui-api-manager Branch: main Commit: 71f03c950a18 Files: 17 Total size: 36.8 KB Directory structure: gitextract_2av0vv_n/ ├── .circleci/ │ └── config.yml ├── .gitignore ├── .vscode/ │ └── settings.json ├── Dockerfile ├── README.md ├── app/ │ ├── __init__.py │ ├── api/ │ │ └── api.py │ ├── db/ │ │ └── models.py │ ├── main.py │ └── manager/ │ └── reqq.py ├── docker-compose.yml ├── install.sh ├── launch.sh ├── launch_sd.sh ├── requirements.txt └── test/ ├── __init__.py └── test.py ================================================ FILE CONTENTS ================================================ ================================================ FILE: .circleci/config.yml ================================================ version: 2 jobs: unit_test: docker: - image: circleci/python:3.6.1 working_directory: ~/repo steps: - checkout # Download and cache dependencies - restore_cache: keys: - v1-dependencies-{{ checksum "requirements.txt" }} # fallback to using the latest cache if no exact match is found - v1-dependencies- - run: name: install dependencies command: | python3 -m venv venv . venv/bin/activate pip install -r requirements.txt - save_cache: paths: - ./venv key: v1-dependencies-{{ checksum "requirements.txt" }} # run tests! - run: name: run tests command: | . venv/bin/activate pytest test/test.py workflows: version: 2 build: jobs: - unit_test ================================================ FILE: .gitignore ================================================ # Created by https://www.gitignore.io/api/linux,macos,python,pycharm,windows,visualstudiocode # Edit at https://www.gitignore.io/?templates=linux,macos,python,pycharm,windows,visualstudiocode ### Linux ### *~ # temporary files which can be created if a process still has a handle open of a deleted file .fuse_hidden* # KDE directory preferences .directory # Linux trash folder which might appear on any partition or disk .Trash-* # .nfs files are created when an open file is removed but is still being accessed .nfs* ### macOS ### # General .DS_Store .AppleDouble .LSOverride # Icon must end with two \r Icon # Thumbnails ._* # Files that might appear in the root of a volume .DocumentRevisions-V100 .fseventsd .Spotlight-V100 .TemporaryItems .Trashes .VolumeIcon.icns .com.apple.timemachine.donotpresent # Directories potentially created on remote AFP share .AppleDB .AppleDesktop Network Trash Folder Temporary Items .apdisk ### PyCharm ### # Covers JetBrains IDEs: IntelliJ, RubyMine, PhpStorm, AppCode, PyCharm, CLion, Android Studio and WebStorm # Reference: https://intellij-support.jetbrains.com/hc/en-us/articles/206544839 # User-specific stuff .idea/**/workspace.xml .idea/**/tasks.xml .idea/**/usage.statistics.xml .idea/**/dictionaries .idea/**/shelf # Generated files .idea/**/contentModel.xml # Sensitive or high-churn files .idea/**/dataSources/ .idea/**/dataSources.ids .idea/**/dataSources.local.xml .idea/**/sqlDataSources.xml .idea/**/dynamic.xml .idea/**/uiDesigner.xml .idea/**/dbnavigator.xml # Gradle .idea/**/gradle.xml .idea/**/libraries # Gradle and Maven with auto-import # When using Gradle or Maven with auto-import, you should exclude module files, # since they will be recreated, and may cause churn. Uncomment if using # auto-import. # .idea/modules.xml # .idea/*.iml # .idea/modules # *.iml # *.ipr # CMake cmake-build-*/ # Mongo Explorer plugin .idea/**/mongoSettings.xml # File-based project format *.iws # IntelliJ out/ # mpeltonen/sbt-idea plugin .idea_modules/ # JIRA plugin atlassian-ide-plugin.xml # Cursive Clojure plugin .idea/replstate.xml # Crashlytics plugin (for Android Studio and IntelliJ) com_crashlytics_export_strings.xml crashlytics.properties crashlytics-build.properties fabric.properties # Editor-based Rest Client .idea/httpRequests # Android studio 3.1+ serialized cache file .idea/caches/build_file_checksums.ser ### PyCharm Patch ### # Comment Reason: https://github.com/joeblau/gitignore.io/issues/186#issuecomment-215987721 # *.iml # modules.xml # .idea/misc.xml # *.ipr # Sonarlint plugin .idea/**/sonarlint/ # SonarQube Plugin .idea/**/sonarIssues.xml # Markdown Navigator plugin .idea/**/markdown-navigator.xml .idea/**/markdown-navigator/ ### Python ### # Byte-compiled / optimized / DLL files __pycache__/ *.py[cod] *$py.class # C extensions *.so # Distribution / packaging .Python build/ develop-eggs/ dist/ downloads/ eggs/ .eggs/ lib/ lib64/ parts/ sdist/ var/ wheels/ pip-wheel-metadata/ share/python-wheels/ *.egg-info/ .installed.cfg *.egg MANIFEST # PyInstaller # Usually these files are written by a python script from a template # before PyInstaller builds the exe, so as to inject date/other infos into it. *.manifest *.spec # Installer logs pip-log.txt pip-delete-this-directory.txt # Unit test / coverage reports htmlcov/ .tox/ .nox/ .coverage .coverage.* .cache nosetests.xml coverage.xml *.cover .hypothesis/ .pytest_cache/ # Translations *.mo *.pot # Scrapy stuff: .scrapy # Sphinx documentation docs/_build/ # PyBuilder target/ # pyenv .python-version # pipenv # According to pypa/pipenv#598, it is recommended to include Pipfile.lock in version control. # However, in case of collaboration, if having platform-specific dependencies or dependencies # having no cross-platform support, pipenv may install dependencies that don't work, or not # install all needed dependencies. #Pipfile.lock # celery beat schedule file celerybeat-schedule # SageMath parsed files *.sage.py # Spyder project settings .spyderproject .spyproject # Rope project settings .ropeproject # Mr Developer .mr.developer.cfg .project .pydevproject # mkdocs documentation /site # mypy .mypy_cache/ .dmypy.json dmypy.json # Pyre type checker .pyre/ ### VisualStudioCode ### .vscode/* !.vscode/settings.json !.vscode/tasks.json !.vscode/launch.json !.vscode/extensions.json ### VisualStudioCode Patch ### # Ignore all local history of files .history ### Windows ### # Windows thumbnail cache files Thumbs.db Thumbs.db:encryptable ehthumbs.db ehthumbs_vista.db # Dump file *.stackdump # Folder config file [Dd]esktop.ini # Recycle Bin used on file shares $RECYCLE.BIN/ # Windows Installer files *.cab *.msi *.msix *.msm *.msp # Windows shortcuts *.lnk # End of https://www.gitignore.io/api/linux,macos,python,pycharm,windows,visualstudiocode ================================================ FILE: .vscode/settings.json ================================================ { "[python]": { "editor.defaultFormatter": "ms-python.autopep8" }, "python.formatting.provider": "none" } ================================================ FILE: Dockerfile ================================================ # pull official base image FROM python:3.8.1-alpine # set work directory WORKDIR /src # set environment variables ENV PYTHONDONTWRITEBYTECODE 1 ENV PYTHONUNBUFFERED 1 # copy requirements file COPY ./requirements.txt /src/requirements.txt # install dependencies RUN set -eux \ && apk add --no-cache --virtual .build-deps build-base \ libressl-dev libffi-dev gcc musl-dev python3-dev \ postgresql-dev \ && pip install --upgrade pip setuptools wheel \ && pip install -r /src/requirements.txt \ && rm -rf /root/.cache/pip # copy project COPY . /src/ EXPOSE 5001 CMD ["uvicorn", "app.main:app", "--reload", "--host", "0.0.0.0", "--port", "5001"] ================================================ FILE: README.md ================================================ ## Problem of stable diffusion webui Stable diffusion webui provides a powerful tool for AI image generation. However, the webui api has some limitations: 1. a blocking REST api call, which might take more than 30s to return the final value. Most gateways don't allow such long blocking time on api call. 2. webui api is a single thread process. Once the thread is occupied, other webui api will fail. (Even though there is a multi thread mode in stable diffusion webui) This repo is aiming to solve the above problems. ## Preconditions: - Python 3 - Stable diffusion Webui ## Inspired by the project https://github.com/marciovrl/fastapi-example.git ## Run local ### Before run this project, please make sure you launched the stable diffusion webui api. ### Install dependencies ``` pip install -r requirements.txt ``` ### Run server ``` uvicorn app.main:app --reload --port 5001 ``` ## API documentation (provided by Swagger UI) ``` http://127.0.0.1:8000/docs ``` ## Model swtich There is an extra filed in txt2img/img2img api: options: Optional[dict] You can swtich stable diffusion by using this options. ``` "options": { "sd_model_checkpoint": } ``` ================================================ FILE: app/__init__.py ================================================ ================================================ FILE: app/api/api.py ================================================ import json import requests def img2img(payload): url = 'http://0.0.0.0:7860/sdapi/v1/img2img' headers = { 'Content-Type': 'application/json', } filter_data = {} for k, v in payload.items(): if payload[k] != None: filter_data[k] = v print("img2img settings", filter_data) response = requests.post(url, headers=headers, data=json.dumps(filter_data)) res = response.json() return res def txt2img(payload): url = 'http://0.0.0.0:7860/sdapi/v1/txt2img' headers = { 'Content-Type': 'application/json', } filter_data = {} for k, v in payload.items(): if payload[k] != None: filter_data[k] = v print("txt2img settings", filter_data) response = requests.post(url, headers=headers, data=json.dumps(filter_data)) res = response.json() return res def progress(): url = 'http://0.0.0.0:7860/sdapi/v1/progress?skip_current_image=false' headers = { 'Content-Type': 'application/json', } response = requests.get(url, headers=headers) res = response.json() return res def get_options(): url = 'http://0.0.0.0:7860/sdapi/v1/options' headers = { 'Content-Type': 'application/json', } response = requests.get(url, headers=headers, timeout=5) res = response.json() return res def set_options(payload): url = 'http://0.0.0.0:7860/sdapi/v1/options' headers = { 'Content-Type': 'application/json', } filter_data = {} for k, v in payload.items(): if payload[k] != None: filter_data[k] = v print("set_options settings", filter_data) response = requests.post(url, headers=headers, data=json.dumps(filter_data)) res = response.json() return res def extra_single_image(payload): url = 'http://0.0.0.0:7860/sdapi/v1/extra-single-image' headers = { 'Content-Type': 'application/json', } filter_data = {} for k, v in payload.items(): if payload[k] != None: filter_data[k] = v print("set_options settings", filter_data) response = requests.post(url, headers=headers, data=json.dumps(filter_data)) res = response.json() return res def controlnet_model_list(): url = 'http://0.0.0.0:7860/controlnet/model_list' headers = { 'Content-Type': 'application/json', } response = requests.get(url, headers=headers) res = response.json() return res def controlnet_module_list(): url = 'http://0.0.0.0:7860/controlnet/module_list' headers = { 'Content-Type': 'application/json', } response = requests.get(url, headers=headers) res = response.json() return res def sd_models(): url = 'http://0.0.0.0:7860/sdapi/v1/sd-models' headers = { 'Content-Type': 'application/json', } response = requests.get(url, headers=headers) res = response.json() return res ================================================ FILE: app/db/models.py ================================================ from pydantic import BaseModel from typing import List, Optional class Img2imgArgs(BaseModel): init_images: Optional[List[str]] resize_mode: Optional[int] denoising_strength: Optional[float] image_cfg_scale: Optional[int] mask: Optional[str] mask_blur: Optional[int] inpainting_fill: Optional[int] inpaint_full_res: Optional[bool] inpaint_full_res_padding: Optional[int] inpainting_mask_invert: Optional[bool] initial_noise_multiplier: Optional[int] prompt: Optional[str] styles: Optional[List[str]] seed: Optional[int] subseed: Optional[int] subseed_strength: Optional[int] seed_resize_from_h: Optional[int] seed_resize_from_w: Optional[int] sampler_name: Optional[str] batch_size: Optional[int] n_iter: Optional[int] steps: Optional[int] cfg_scale: Optional[int] width: Optional[int] height: Optional[int] restore_faces: Optional[bool] tiling: Optional[bool] do_not_save_samples: Optional[bool] do_not_save_grid: Optional[bool] negative_prompt: Optional[str] eta: Optional[int] s_min_uncond: Optional[int] s_churn: Optional[int] s_tmax: Optional[int] s_tmin: Optional[int] s_noise: Optional[int] override_settings: Optional[dict] override_settings_restore_afterwards: Optional[bool] script_args: Optional[List[dict]] sampler_index: Optional[str] include_init_images: Optional[bool] script_name: Optional[str] send_images: Optional[bool] save_images: Optional[bool] alwayson_scripts: Optional[dict] options: Optional[dict] class Txt2imgArgs(BaseModel): enable_hr: Optional[bool] denoising_strength: Optional[float] firstphase_width: Optional[int] firstphase_height: Optional[int] hr_scale: Optional[int] hr_upscaler: Optional[str] hr_second_pass_steps: Optional[int] hr_resize_x: Optional[int] hr_resize_y: Optional[int] prompt: Optional[str] styles: Optional[List[str]] seed: Optional[int] subseed: Optional[int] subseed_strength: Optional[int] seed_resize_from_h: Optional[int] seed_resize_from_w: Optional[int] sampler_name: Optional[str] batch_size: Optional[int] n_iter: Optional[int] steps: Optional[int] cfg_scale: Optional[int] width: Optional[int] height: Optional[int] restore_faces: Optional[bool] tiling: Optional[bool] do_not_save_samples: Optional[bool] do_not_save_grid: Optional[bool] negative_prompt: Optional[str] eta: Optional[int] s_min_uncond: Optional[int] s_churn: Optional[int] s_tmax: Optional[int] s_tmin: Optional[int] s_noise: Optional[int] override_settings: Optional[dict] override_settings_restore_afterwards: Optional[bool] script_args: Optional[List[dict]] sampler_index: Optional[str] script_name: Optional[str] send_images: Optional[bool] save_image: Optional[bool] alwayson_scripts: Optional[dict] options: Optional[dict] class ExtraSingleImage(BaseModel): resize_mode: Optional[int] show_extras_results: Optional[bool] gfpgan_visibility: Optional[int] codeformer_visibility: Optional[int] codeformer_weight: Optional[float] upscaling_resize: Optional[int] upscaling_resize_w: Optional[int] upscaling_resize_h: Optional[int] upscaling_crop: Optional[bool] upscaler_1: Optional[str] upscaler_2: Optional[str] extras_upscaler_2_visibility: Optional[int] upscale_first: Optional[bool] image: Optional[str] ================================================ FILE: app/main.py ================================================ from fastapi import FastAPI, HTTPException from starlette.responses import Response from app.db.models import Img2imgArgs, Txt2imgArgs, ExtraSingleImage from app.api import api from app.manager import reqq app = FastAPI() @app.get("/") def root(): return {"message": "Fast API in Python"} @app.post("/rawimg2img", status_code=201) def rawimg2img(payload: Img2imgArgs): payload = payload.dict() return api.img2img(payload) @app.post("/rawtxt2img", status_code=201) def rawtxt2img(payload: Txt2imgArgs): payload = payload.dict() return api.txt2img(payload) @app.post("/img2img", status_code=201) def img2img(payload: Img2imgArgs): payload = payload.dict() return reqq.add_req_queue(payload, "img2img") @app.post("/txt2img", status_code=201) def txt2img(payload: Txt2imgArgs): payload = payload.dict() return reqq.add_req_queue(payload, "txt2img") @app.get("/progress/{req_id}") def progress(req_id: str): return reqq.get_result(req_id) @app.get("/controlnet/model_list") def controlnet_model_list(): return api.controlnet_model_list() @app.get("/controlnet/module_list") def controlnet_module_list(): return api.controlnet_module_list() @app.post("/sdapi/v1/extra-single-image", status_code=201) def extra_single_image(payload: ExtraSingleImage): payload = payload.dict() return api.extra_single_image(payload) @app.get("/sdapi/v1/sd-models") def sd_models(): return api.sd_models() ================================================ FILE: app/manager/reqq.py ================================================ import uuid import queue import threading import time import copy from app.api import api from fastapi import HTTPException current_request = {} final_results = {} current_options = {} class QueueMonitor: def __init__(self, q): self.q = q self.monitor_thread = threading.Thread( target=self.monitor_queue, daemon=True) self.monitor_thread.start() def get_queue_size(self): return self.q.qsize() def monitor_queue(self): while True: current_size = self.get_queue_size() if current_size > 0: self.queue_has_items() time.sleep(1) # check the queue every second def queue_has_items(self): print(f"Queue has items. Current size: {self.get_queue_size()}") self.callback_function() def callback_function(self): start_process_queue() requests_queue = queue.Queue(20) # Create a QueueMonitor object with the Queue monitor = QueueMonitor(requests_queue) def start_process_queue(): global current_request global final_results if ((current_request.get("status") != "pending") and (current_request.get("status") != "processing")): if not requests_queue.empty(): current_request = requests_queue.get() current_request["status"] = "processing" print("current_request is processing", current_request.get( "request_id"), current_request.get("status")) request_options = current_request.get("options") compare_options(request_options) if (current_request.get("type") == "txt2img"): res = api.txt2img(current_request.get("payload")) final_request = copy.deepcopy(current_request) final_request["status"] = "done" final_request["result"] = res final_results[final_request.get("request_id")] = final_request print("request is complete", final_request.get( "request_id"), final_request.get("status")) current_request["status"] = "finishing" if (current_request.get("type") == "img2img"): res = api.img2img(current_request.get("payload")) final_request = copy.deepcopy(current_request) final_request["status"] = "done" final_request["result"] = res final_results[final_request.get("request_id")] = final_request print("request is complete", final_request.get( "request_id"), final_request.get("status")) current_request["status"] = "finishing" def add_req_queue(payload, type): # try: # api.get_options() # except: # raise HTTPException( # status_code=500, detail="No options found, please check backend is running correctly.") filter_data = {} options = {} for k, v in payload.items(): if (k == "options"): options = v if payload[k] != None: filter_data[k] = v request_id = str(uuid.uuid4()) temp_request = { "type": type, "payload": filter_data, "request_id": request_id, "status": "pending", "options": options } requests_queue.put(temp_request) print("add request into queue, pending", request_id) return temp_request def check_variable_in_queue(q, var): queue_as_list = list(q.queue) pending_requests = [] for i in queue_as_list: pending_requests.append(i.get("request_id")) if var in pending_requests: print(f"{var} is in the queue.") return pending_requests.index(var) else: print(f"{var} is not in the queue.") return -1 def get_result(request_id): global final_results print("final_results", final_results.keys(), request_id) if (request_id in final_results): print("Found final result", request_id) return final_results[request_id] elif (request_id == current_request.get("request_id")): res = api.progress() temp_res = current_request temp_res["result"] = res return temp_res else: index = check_variable_in_queue(requests_queue, request_id) if (index > -1): return {"status": "pending", "request_id": request_id, "pending_count": index+1} else: return {"status": "not_found"} def compare_options(options): global current_options is_change = False print("compare_options", options) for k, v in options.items(): if (current_options.get(k) != v): is_change = True break if (is_change): current_options = copy.deepcopy(options) print("start to set options to api", current_options) api.set_options(options) ================================================ FILE: docker-compose.yml ================================================ version: "3.7" services: app: build: . container_name: app command: uvicorn app.main:app --reload --workers 1 --host 0.0.0.0 --port 8000 volumes: - ./:/src/ ports: - 8002:8000 environment: - DATABASE_URL=postgresql://fastapi:fastapi@db/fastapi db: image: postgres:12.1-alpine container_name: db volumes: - postgres_data:/var/lib/postgresql/data/ environment: - POSTGRES_USER=fastapi - POSTGRES_PASSWORD=fastapi - POSTGRES_DB=fastapi volumes: postgres_data: ================================================ FILE: install.sh ================================================ apt update apt install -y aria2 apt-get install python3-pip apt install vim apt-get install tmux pip3 install -r requirements.txt git clone https://github.com/AUTOMATIC1111/stable-diffusion-webui.git git reset --hard 394ffa7 aria2c --console-log-level=error -c -x 16 -s 16 -k 1M https://huggingface.co/embed/upscale/resolve/main/4x-UltraSharp.pth -d ./stable-diffusion-webui/models/ESRGAN -o 4x-UltraSharp.pth wget https://raw.githubusercontent.com/camenduru/stable-diffusion-webui-scripts/main/run_n_times.py -O ./stable-diffusion-webui/scripts/run_n_times.py git clone https://github.com/camenduru/stable-diffusion-webui-images-browser ./stable-diffusion-webui/extensions/stable-diffusion-webui-images-browser git clone https://github.com/camenduru/sd-civitai-browser ./stable-diffusion-webui/extensions/sd-civitai-browser git clone https://github.com/kohya-ss/sd-webui-additional-networks ./stable-diffusion-webui/extensions/sd-webui-additional-networks git clone https://github.com/Mikubill/sd-webui-controlnet ./stable-diffusion-webui/extensions/sd-webui-controlnet git clone https://github.com/camenduru/sd-webui-tunnels ./stable-diffusion-webui/extensions/sd-webui-tunnels git clone https://github.com/etherealxx/batchlinks-webui ./stable-diffusion-webui/extensions/batchlinks-webui git clone https://github.com/camenduru/stable-diffusion-webui-catppuccin ./stable-diffusion-webui/extensions/stable-diffusion-webui-catppuccin git clone https://github.com/AUTOMATIC1111/stable-diffusion-webui-rembg ./stable-diffusion-webui/extensions/stable-diffusion-webui-rembg git clone https://github.com/ashen-sensored/stable-diffusion-webui-two-shot ./stable-diffusion-webui/extensions/stable-diffusion-webui-two-shot git clone https://github.com/thomasasfk/sd-webui-aspect-ratio-helper ./stable-diffusion-webui/extensions/sd-webui-aspect-ratio-helper git clone https://github.com/nonnonstop/sd-webui-3d-open-pose-editor ./stable-diffusion-webui/extensions/sd-webui-3d-open-pose-editor git clone https://github.com/continue-revolution/sd-webui-segment-anything.git ./stable-diffusion-webui/extensions/sd-webui-segment-anything aria2c --console-log-level=error -c -x 16 -s 16 -k 1M https://huggingface.co/ckpt/ControlNet-v1-1/resolve/main/control_v11e_sd15_ip2p_fp16.safetensors -d ./stable-diffusion-webui/extensions/sd-webui-controlnet/models -o control_v11e_sd15_ip2p_fp16.safetensors aria2c --console-log-level=error -c -x 16 -s 16 -k 1M https://huggingface.co/ckpt/ControlNet-v1-1/resolve/main/control_v11e_sd15_shuffle_fp16.safetensors -d ./stable-diffusion-webui/extensions/sd-webui-controlnet/models -o control_v11e_sd15_shuffle_fp16.safetensors aria2c --console-log-level=error -c -x 16 -s 16 -k 1M https://huggingface.co/ckpt/ControlNet-v1-1/resolve/main/control_v11p_sd15_canny_fp16.safetensors -d ./stable-diffusion-webui/extensions/sd-webui-controlnet/models -o control_v11p_sd15_canny_fp16.safetensors aria2c --console-log-level=error -c -x 16 -s 16 -k 1M https://huggingface.co/ckpt/ControlNet-v1-1/resolve/main/control_v11f1p_sd15_depth_fp16.safetensors -d ./stable-diffusion-webui/extensions/sd-webui-controlnet/models -o control_v11f1p_sd15_depth_fp16.safetensors aria2c --console-log-level=error -c -x 16 -s 16 -k 1M https://huggingface.co/ckpt/ControlNet-v1-1/resolve/main/control_v11p_sd15_inpaint_fp16.safetensors -d ./stable-diffusion-webui/extensions/sd-webui-controlnet/models -o control_v11p_sd15_inpaint_fp16.safetensors aria2c --console-log-level=error -c -x 16 -s 16 -k 1M https://huggingface.co/ckpt/ControlNet-v1-1/resolve/main/control_v11p_sd15_lineart_fp16.safetensors -d ./stable-diffusion-webui/extensions/sd-webui-controlnet/models -o control_v11p_sd15_lineart_fp16.safetensors aria2c --console-log-level=error -c -x 16 -s 16 -k 1M https://huggingface.co/ckpt/ControlNet-v1-1/resolve/main/control_v11p_sd15_mlsd_fp16.safetensors -d ./stable-diffusion-webui/extensions/sd-webui-controlnet/models -o control_v11p_sd15_mlsd_fp16.safetensors aria2c --console-log-level=error -c -x 16 -s 16 -k 1M https://huggingface.co/ckpt/ControlNet-v1-1/resolve/main/control_v11p_sd15_normalbae_fp16.safetensors -d ./stable-diffusion-webui/extensions/sd-webui-controlnet/models -o control_v11p_sd15_normalbae_fp16.safetensors aria2c --console-log-level=error -c -x 16 -s 16 -k 1M https://huggingface.co/ckpt/ControlNet-v1-1/resolve/main/control_v11p_sd15_openpose_fp16.safetensors -d ./stable-diffusion-webui/extensions/sd-webui-controlnet/models -o control_v11p_sd15_openpose_fp16.safetensors aria2c --console-log-level=error -c -x 16 -s 16 -k 1M https://huggingface.co/ckpt/ControlNet-v1-1/resolve/main/control_v11p_sd15_scribble_fp16.safetensors -d ./stable-diffusion-webui/extensions/sd-webui-controlnet/models -o control_v11p_sd15_scribble_fp16.safetensors aria2c --console-log-level=error -c -x 16 -s 16 -k 1M https://huggingface.co/ckpt/ControlNet-v1-1/resolve/main/control_v11p_sd15_seg_fp16.safetensors -d ./stable-diffusion-webui/extensions/sd-webui-controlnet/models -o control_v11p_sd15_seg_fp16.safetensors aria2c --console-log-level=error -c -x 16 -s 16 -k 1M https://huggingface.co/ckpt/ControlNet-v1-1/resolve/main/control_v11p_sd15_softedge_fp16.safetensors -d ./stable-diffusion-webui/extensions/sd-webui-controlnet/models -o control_v11p_sd15_softedge_fp16.safetensors aria2c --console-log-level=error -c -x 16 -s 16 -k 1M https://huggingface.co/ckpt/ControlNet-v1-1/resolve/main/control_v11p_sd15s2_lineart_anime_fp16.safetensors -d ./stable-diffusion-webui/extensions/sd-webui-controlnet/models -o control_v11p_sd15s2_lineart_anime_fp16.safetensors aria2c --console-log-level=error -c -x 16 -s 16 -k 1M https://huggingface.co/ckpt/ControlNet-v1-1/resolve/main/control_v11f1e_sd15_tile_fp16.safetensors -d ./stable-diffusion-webui/extensions/sd-webui-controlnet/models -o control_v11f1e_sd15_tile_fp16.safetensors aria2c --console-log-level=error -c -x 16 -s 16 -k 1M https://huggingface.co/ckpt/ControlNet-v1-1/raw/main/control_v11e_sd15_ip2p_fp16.yaml -d ./stable-diffusion-webui/extensions/sd-webui-controlnet/models -o control_v11e_sd15_ip2p_fp16.yaml aria2c --console-log-level=error -c -x 16 -s 16 -k 1M https://huggingface.co/ckpt/ControlNet-v1-1/raw/main/control_v11e_sd15_shuffle_fp16.yaml -d ./stable-diffusion-webui/extensions/sd-webui-controlnet/models -o control_v11e_sd15_shuffle_fp16.yaml aria2c --console-log-level=error -c -x 16 -s 16 -k 1M https://huggingface.co/ckpt/ControlNet-v1-1/raw/main/control_v11p_sd15_canny_fp16.yaml -d ./stable-diffusion-webui/extensions/sd-webui-controlnet/models -o control_v11p_sd15_canny_fp16.yaml aria2c --console-log-level=error -c -x 16 -s 16 -k 1M https://huggingface.co/ckpt/ControlNet-v1-1/raw/main/control_v11f1p_sd15_depth_fp16.yaml -d ./stable-diffusion-webui/extensions/sd-webui-controlnet/models -o control_v11f1p_sd15_depth_fp16.yaml aria2c --console-log-level=error -c -x 16 -s 16 -k 1M https://huggingface.co/ckpt/ControlNet-v1-1/raw/main/control_v11p_sd15_inpaint_fp16.yaml -d ./stable-diffusion-webui/extensions/sd-webui-controlnet/models -o control_v11p_sd15_inpaint_fp16.yaml aria2c --console-log-level=error -c -x 16 -s 16 -k 1M https://huggingface.co/ckpt/ControlNet-v1-1/raw/main/control_v11p_sd15_lineart_fp16.yaml -d ./stable-diffusion-webui/extensions/sd-webui-controlnet/models -o control_v11p_sd15_lineart_fp16.yaml aria2c --console-log-level=error -c -x 16 -s 16 -k 1M https://huggingface.co/ckpt/ControlNet-v1-1/raw/main/control_v11p_sd15_mlsd_fp16.yaml -d ./stable-diffusion-webui/extensions/sd-webui-controlnet/models -o control_v11p_sd15_mlsd_fp16.yaml aria2c --console-log-level=error -c -x 16 -s 16 -k 1M https://huggingface.co/ckpt/ControlNet-v1-1/raw/main/control_v11p_sd15_normalbae_fp16.yaml -d ./stable-diffusion-webui/extensions/sd-webui-controlnet/models -o control_v11p_sd15_normalbae_fp16.yaml aria2c --console-log-level=error -c -x 16 -s 16 -k 1M https://huggingface.co/ckpt/ControlNet-v1-1/raw/main/control_v11p_sd15_openpose_fp16.yaml -d ./stable-diffusion-webui/extensions/sd-webui-controlnet/models -o control_v11p_sd15_openpose_fp16.yaml aria2c --console-log-level=error -c -x 16 -s 16 -k 1M https://huggingface.co/ckpt/ControlNet-v1-1/raw/main/control_v11p_sd15_scribble_fp16.yaml -d ./stable-diffusion-webui/extensions/sd-webui-controlnet/models -o control_v11p_sd15_scribble_fp16.yaml aria2c --console-log-level=error -c -x 16 -s 16 -k 1M https://huggingface.co/ckpt/ControlNet-v1-1/raw/main/control_v11p_sd15_seg_fp16.yaml -d ./stable-diffusion-webui/extensions/sd-webui-controlnet/models -o control_v11p_sd15_seg_fp16.yaml aria2c --console-log-level=error -c -x 16 -s 16 -k 1M https://huggingface.co/ckpt/ControlNet-v1-1/raw/main/control_v11p_sd15_softedge_fp16.yaml -d ./stable-diffusion-webui/extensions/sd-webui-controlnet/models -o control_v11p_sd15_softedge_fp16.yaml aria2c --console-log-level=error -c -x 16 -s 16 -k 1M https://huggingface.co/ckpt/ControlNet-v1-1/raw/main/control_v11p_sd15s2_lineart_anime_fp16.yaml -d ./stable-diffusion-webui/extensions/sd-webui-controlnet/models -o control_v11p_sd15s2_lineart_anime_fp16.yaml aria2c --console-log-level=error -c -x 16 -s 16 -k 1M https://huggingface.co/ckpt/ControlNet-v1-1/raw/main/control_v11f1e_sd15_tile_fp16.yaml -d ./stable-diffusion-webui/extensions/sd-webui-controlnet/models -o control_v11f1e_sd15_tile_fp16.yaml aria2c --console-log-level=error -c -x 16 -s 16 -k 1M https://huggingface.co/ckpt/ControlNet-v1-1/resolve/main/t2iadapter_style_sd14v1.pth -d ./stable-diffusion-webui/extensions/sd-webui-controlnet/models -o t2iadapter_style_sd14v1.pth aria2c --console-log-level=error -c -x 16 -s 16 -k 1M https://huggingface.co/ckpt/ControlNet-v1-1/resolve/main/t2iadapter_sketch_sd14v1.pth -d ./stable-diffusion-webui/extensions/sd-webui-controlnet/models -o t2iadapter_sketch_sd14v1.pth aria2c --console-log-level=error -c -x 16 -s 16 -k 1M https://huggingface.co/ckpt/ControlNet-v1-1/resolve/main/t2iadapter_seg_sd14v1.pth -d ./stable-diffusion-webui/extensions/sd-webui-controlnet/models -o t2iadapter_seg_sd14v1.pth aria2c --console-log-level=error -c -x 16 -s 16 -k 1M https://huggingface.co/ckpt/ControlNet-v1-1/resolve/main/t2iadapter_openpose_sd14v1.pth -d ./stable-diffusion-webui/extensions/sd-webui-controlnet/models -o t2iadapter_openpose_sd14v1.pth aria2c --console-log-level=error -c -x 16 -s 16 -k 1M https://huggingface.co/ckpt/ControlNet-v1-1/resolve/main/t2iadapter_keypose_sd14v1.pth -d ./stable-diffusion-webui/extensions/sd-webui-controlnet/models -o t2iadapter_keypose_sd14v1.pth aria2c --console-log-level=error -c -x 16 -s 16 -k 1M https://huggingface.co/ckpt/ControlNet-v1-1/resolve/main/t2iadapter_depth_sd14v1.pth -d ./stable-diffusion-webui/extensions/sd-webui-controlnet/models -o t2iadapter_depth_sd14v1.pth aria2c --console-log-level=error -c -x 16 -s 16 -k 1M https://huggingface.co/ckpt/ControlNet-v1-1/resolve/main/t2iadapter_color_sd14v1.pth -d ./stable-diffusion-webui/extensions/sd-webui-controlnet/models -o t2iadapter_color_sd14v1.pth aria2c --console-log-level=error -c -x 16 -s 16 -k 1M https://huggingface.co/ckpt/ControlNet-v1-1/resolve/main/t2iadapter_canny_sd14v1.pth -d ./stable-diffusion-webui/extensions/sd-webui-controlnet/models -o t2iadapter_canny_sd14v1.pth aria2c --console-log-level=error -c -x 16 -s 16 -k 1M https://huggingface.co/ckpt/ControlNet-v1-1/resolve/main/t2iadapter_canny_sd15v2.pth -d ./stable-diffusion-webui/extensions/sd-webui-controlnet/models -o t2iadapter_canny_sd15v2.pth aria2c --console-log-level=error -c -x 16 -s 16 -k 1M https://huggingface.co/ckpt/ControlNet-v1-1/resolve/main/t2iadapter_depth_sd15v2.pth -d ./stable-diffusion-webui/extensions/sd-webui-controlnet/models -o t2iadapter_depth_sd15v2.pth aria2c --console-log-level=error -c -x 16 -s 16 -k 1M https://huggingface.co/ckpt/ControlNet-v1-1/resolve/main/t2iadapter_sketch_sd15v2.pth -d ./stable-diffusion-webui/extensions/sd-webui-controlnet/models -o t2iadapter_sketch_sd15v2.pth aria2c --console-log-level=error -c -x 16 -s 16 -k 1M https://huggingface.co/ckpt/ControlNet-v1-1/resolve/main/t2iadapter_zoedepth_sd15v1.pth -d ./stable-diffusion-webui/extensions/sd-webui-controlnet/models -o t2iadapter_zoedepth_sd15v1.pth aria2c --console-log-level=error -c -x 16 -s 16 -k 1M https://huggingface.co/ckpt/anything-v3.0/resolve/main/Anything-V3.0-pruned.ckpt -d ./stable-diffusion-webui/models/Stable-diffusion -o Anything-V3.0-pruned.ckpt aria2c --console-log-level=error -c -x 16 -s 16 -k 1M https://huggingface.co/ckpt/sd-vae-ft-mse-original/resolve/main/vae-ft-mse-840000-ema-pruned.ckpt -d ./stable-diffusion-webui/models/Stable-diffusion -o Anything-V3.0-pruned.vae.pt aria2c --console-log-level=error -c -x 16 -s 16 -k 1M https://huggingface.co/xiaozaa/animaTest/resolve/main/animeoutlineV4_16.safetensors -d ./stable-diffusion-webui/models/Lora -o animeoutlineV4_16.safetensors aria2c --console-log-level=error -c -x 16 -s 16 -k 1M https://huggingface.co/SG161222/Realistic_Vision_V4.0/resolve/main/Realistic_Vision_V4.0.safetensors -d ./stable-diffusion-webui/models/Stable-diffusion -o Realistic_Vision_V4.0.safetensors aria2c --console-log-level=error -c -x 16 -s 16 -k 1M https://huggingface.co/Sasulee/animeLineartMangaLike_v30MangaLike/resolve/main/animeLineartMangaLike_v30MangaLike.safetensors -d ./stable-diffusion-webui/models/Lora -o animeLineartMangaLike_v30MangaLike.safetensors aria2c --console-log-level=error -c -x 16 -s 16 -k 1M https://huggingface.co/datasets/Nerfgun3/bad_prompt/resolve/main/bad_prompt_version2.pt -d ./stable-diffusion-webui/embeddings -o bad_prompt_version2.pt aria2c --console-log-level=error -c -x 16 -s 16 -k 1M https://huggingface.co/datasets/gsdf/EasyNegative/resolve/main/EasyNegative.pt -d ./stable-diffusion-webui/embeddings -o EasyNegative.pt aria2c --console-log-level=error -c -x 16 -s 16 -k 1M https://huggingface.co/nick-x-hacker/bad-artist/resolve/main/bad-artist.pt -d ./stable-diffusion-webui/embeddings -o bad-artist.pt aria2c --console-log-level=error -c -x 16 -s 16 -k 1M https://huggingface.co/embed/negative/resolve/main/bad-hands-5.pt -d ./stable-diffusion-webui/embeddings -o bad-hands-5.pt aria2c --console-log-level=error -c -x 16 -s 16 -k 1M https://huggingface.co/embed/negative/resolve/main/ng_deepnegative_v1_75t.pt -d ./stable-diffusion-webui/embeddings -o ng_deepnegative_v1_75t.pt aria2c --console-log-level=error -c -x 16 -s 16 -k 1M https://huggingface.co/embed/negative/resolve/main/EasyNegativeV2.safetensors -d ./stable-diffusion-webui/embeddings -o EasyNegativeV2.safetensors aria2c --console-log-level=error -c -x 16 -s 16 -k 1M https://huggingface.co/embed/negative/resolve/main/verybadimagenegative_v1.3.pt -d ./stable-diffusion-webui/embeddings -o verybadimagenegative_v1.3.pt aria2c --console-log-level=error -c -x 16 -s 16 -k 1M https://huggingface.co/embed/negative/resolve/main/bad-image-v2-39000.pt -d ./stable-diffusion-webui/embeddings -o bad-image-v2-39000.pt aria2c --console-log-level=error -c -x 16 -s 16 -k 1M https://civitai.com/api/download/models/90072?type=Model&format=SafeTensor&size=pruned&fp=fp16 -d ./stable-diffusion-webui/models/Stable-diffusion -o photon_v1.safetensors aria2c --console-log-level=error -c -x 16 -s 16 -k 1M https://dl.fbaipublicfiles.com/segment_anything/sam_vit_h_4b8939.pth -d ./stable-diffusion-webui/models/sam -o sam_vit_h_4b8939.pth sed -i -e '/ api = create_api/a\' -e ' modules.script_callbacks.before_ui_callback()' ./stable-diffusion-webui/webui.py sed -i -e 's/\"sd_model_checkpoint\"\,/\"sd_model_checkpoint\,sd_vae\,CLIP_stop_at_last_layers\"\,/g' ./stable-diffusion-webui/modules/shared.py cd ./stable-diffusion-webui apt install python3.10-venv python3.10 -m venv venv ================================================ FILE: launch.sh ================================================ python3 -m uvicorn app.main:app --reload --host 0.0.0.0 --port 5001 ================================================ FILE: launch_sd.sh ================================================ cd ./stable-diffusion-webui bash <(wget -qO- https://raw.githubusercontent.com/AUTOMATIC1111/stable-diffusion-webui/master/webui.sh) -f --listen --xformers --enable-insecure-extension-access --theme dark --api ================================================ FILE: requirements.txt ================================================ fastapi==0.98.0 pytest==7.4.0 requests==2.31.0 uvicorn==0.22.0 ================================================ FILE: test/__init__.py ================================================ ================================================ FILE: test/test.py ================================================ from starlette.testclient import TestClient from app.main import app import json client = TestClient(app)