ADD 添加Comfy-FFmpeg模块

FIX S3目录挂载点替换
This commit is contained in:
康宇佳 2025-02-28 18:49:34 +08:00
parent 24b3b021ee
commit 05ff0a42d5
8 changed files with 88 additions and 16 deletions

8
.idea/.gitignore vendored Normal file
View File

@ -0,0 +1,8 @@
# 默认忽略的文件
/shelf/
/workspace.xml
# 基于编辑器的 HTTP 客户端请求
/httpRequests/
# Datasource local storage ignored files
/dataSources/
/dataSources.local.xml

View File

@ -0,0 +1,13 @@
<component name="InspectionProjectProfileManager">
<profile version="1.0">
<option name="myName" value="Project Default" />
<inspection_tool class="Eslint" enabled="true" level="WARNING" enabled_by_default="true" />
<inspection_tool class="PyPep8NamingInspection" enabled="true" level="WEAK WARNING" enabled_by_default="true">
<option name="ignoredErrors">
<list>
<option value="N802" />
</list>
</option>
</inspection_tool>
</profile>
</component>

View File

@ -0,0 +1,6 @@
<component name="InspectionProjectProfileManager">
<settings>
<option name="USE_PROJECT_PROFILE" value="false" />
<version value="1.0" />
</settings>
</component>

7
.idea/misc.xml Normal file
View File

@ -0,0 +1,7 @@
<?xml version="1.0" encoding="UTF-8"?>
<project version="4">
<component name="Black">
<option name="sdkName" value="Python 3.9 (pythonProject)" />
</component>
<component name="ProjectRootManager" version="2" project-jdk-name="Python 3.9 (modalDeploy)" project-jdk-type="Python SDK" />
</project>

10
.idea/modalDeploy.iml Normal file
View File

@ -0,0 +1,10 @@
<?xml version="1.0" encoding="UTF-8"?>
<module type="PYTHON_MODULE" version="4">
<component name="NewModuleRootManager">
<content url="file://$MODULE_DIR$">
<excludeFolder url="file://$MODULE_DIR$/.venv" />
</content>
<orderEntry type="jdk" jdkName="Python 3.9 (modalDeploy)" jdkType="Python SDK" />
<orderEntry type="sourceFolder" forTests="false" />
</component>
</module>

8
.idea/modules.xml Normal file
View File

@ -0,0 +1,8 @@
<?xml version="1.0" encoding="UTF-8"?>
<project version="4">
<component name="ProjectModuleManager">
<modules>
<module fileurl="file://$PROJECT_DIR$/.idea/modalDeploy.iml" filepath="$PROJECT_DIR$/.idea/modalDeploy.iml" />
</modules>
</component>
</project>

6
.idea/vcs.xml Normal file
View File

@ -0,0 +1,6 @@
<?xml version="1.0" encoding="UTF-8"?>
<project version="4">
<component name="VcsDirectoryMappings">
<mapping directory="$PROJECT_DIR$" vcs="Git" />
</component>
</project>

View File

@ -1,5 +1,6 @@
import json
import os
import shutil
import subprocess
import uuid
from pathlib import Path
@ -7,7 +8,6 @@ from typing import Dict
import modal
image = ( # build up a Modal Image to run ComfyUI, step by step
modal.Image.debian_slim( # start from basic Linux with Python
python_version="3.10"
@ -25,7 +25,7 @@ image = ( # build up a Modal Image to run ComfyUI, step by step
.pip_install("opencv-python")
.run_commands( # use comfy-cli to install ComfyUI and its dependencies
"comfy --skip-prompt install --nvidia --version 0.3.10"
).add_local_file("snapshot.json","/root/snapshot.json", copy=True)
)
)
image = (
@ -60,14 +60,14 @@ image = (
"rm -rf /root/comfy/ComfyUI/models"
).run_commands(
"apt update && apt install -y ffmpeg && ffmpeg -version"
).pip_install("av")
).pip_install(
"av"
).run_commands(
"comfy node install https://e.coding.net/g-ldyi2063/dev/ComfyUI-FFmpeg.git"
)
# Add .run_commands(...) calls for any other custom nodes you want to download
)
image = image.add_local_file(
"highlight_v0.113_api.json", "/root/workflow_api.json"
)
app = modal.App(name="highlight-comfyui-s3", image=image)
vol = modal.Volume.from_name("comfyui-model", create_if_missing=True)
bucket_dict = modal.Dict.from_name("aws_s3_bucket", create_if_missing=True)
@ -77,26 +77,28 @@ secret = modal.Secret.from_name("aws-s3-secret")
# completed workflows write output images to this directory
output_dir = "/root/comfy/ComfyUI/output"
@app.cls(
allow_concurrent_inputs=1, # allow 10 concurrent API calls
concurrency_limit=50,
container_idle_timeout=120, # 5 minute container keep alive after it processes an input; increasing this value is a great way to reduce ComfyUI cold start times
container_idle_timeout=120,
# 5 minute container keep alive after it processes an input; increasing this value is a great way to reduce ComfyUI cold start times
timeout=800,
gpu="T4",
secrets=[secret],
volumes={
"/root/comfy/ComfyUI/models": vol,
"/root/comfy/ComfyUI/input": modal.CloudBucketMount(
"/root/comfy/ComfyUI/input_s3": modal.CloudBucketMount(
bucket_name=bucket_input,
# bucket_endpoint_url="https://s3.%s.amazonaws.com" % os.environ["AWS_REGION"],
secret=secret,
key_prefix="comfyui/"
key_prefix="/"
),
"/root/comfy/ComfyUI/output": modal.CloudBucketMount(
"/root/comfy/ComfyUI/output_s3": modal.CloudBucketMount(
bucket_name=bucket_output,
# bucket_endpoint_url="https://s3.%s.amazonaws.com" % os.environ["AWS_REGION"],
secret=secret,
key_prefix="comfyui/"
key_prefix="/"
),
},
)
@ -111,14 +113,23 @@ class ComfyUI:
def infer(self, workflow_json: str = ""):
# runs the comfy run --workflow command as a subprocess
session_id = str(uuid.uuid4())
workflow = json.loads(workflow_json)
file_to_move = None
for node in workflow.values():
if node.get("class_type") == "ComfyUIDeployExternalText":
if node.get("inputs").get("input_id") == "file_path":
file_to_move = node.get("inputs").get("default_value")
if file_to_move:
os.makedirs(os.path.dirname(file_to_move.replace("input_s3", "input")), exist_ok=True)
shutil.copy(file_to_move, file_to_move.replace("input_s3", "input"))
node["inputs"]["default_value"] = node["inputs"]["default_value"].replace("input_s3", "input")
with open(f"/root/{session_id}.json", "w", encoding="utf-8") as f:
f.write(workflow_json)
f.write(json.dumps(workflow, ensure_ascii=False))
cmd = f"comfy run --workflow /root/{session_id}.json --wait --timeout 1200"
# TODO 接收返回值
subprocess.run(cmd, shell=True, check=True)
# looks up the name of the output image file based on the workflow
workflow = json.loads(workflow_json)
file_prefix = [
node.get("inputs")
for node in workflow.values()
@ -128,10 +139,13 @@ class ComfyUI:
# returns the image as bytes
file_list = os.listdir(output_dir)
# 获取按照文件时间创建排序的列表,默认是按时间升序
new_file_list = sorted(file_list, key=lambda file: os.path.getctime(os.path.join(output_dir, file)), reverse=True)
new_file_list = sorted(file_list, key=lambda file: os.path.getctime(os.path.join(output_dir, file)),
reverse=True)
# print("file_list", new_file_list)
for f in new_file_list:
if f.startswith(file_prefix):
os.makedirs(os.path.dirname(os.path.join(output_dir.replace("output","output_s3"), f)), exist_ok=True)
shutil.copy(os.path.join(output_dir, f), os.path.join(output_dir.replace("output","output_s3"), f))
return f
@modal.web_endpoint(method="POST")
@ -144,7 +158,7 @@ class ComfyUI:
# run inference on the currently running container
fname = self.infer.local(new_workflow_file)
j = {
"file_name": os.path.join("comfyui",fname)
"file_name": fname
}
print("json", j)