# Python 3.10+: pip install comfy-sdk==0.4.0
import os
from comfy_sdk import Comfy
api_key = os.environ.get("COMFY_API_KEY", "").strip()
if not api_key: raise RuntimeError("Set COMFY_API_KEY")
os.environ.setdefault("COMFY_BASE_URL", "https://cloud.comfy.org")
client = Comfy(api_key=api_key)
workflow = client.workflows.from_json({
"76": {
"class_type": "LoadImage",
"inputs": {
"image": "UPLOADED_image_FILENAME"
},
"_meta": {
"title": "Load Image"
}
},
"81": {
"class_type": "LoadImage",
"inputs": {
"image": "UPLOADED_reference_image_FILENAME"
},
"_meta": {
"title": "Load Image"
}
},
"94": {
"class_type": "SaveImage",
"inputs": {
"filename_prefix": "Flux2-Klein",
"images": [
"92:65",
0
]
},
"_meta": {
"title": "Save Image"
}
},
"92:61": {
"class_type": "KSamplerSelect",
"inputs": {
"sampler_name": "euler"
},
"_meta": {
"title": "KSamplerSelect"
}
},
"92:62": {
"class_type": "Flux2Scheduler",
"inputs": {
"height": [
"92:81",
1
],
"steps": 4,
"width": [
"92:81",
0
]
},
"_meta": {
"title": "Flux2Scheduler"
}
},
"92:63": {
"class_type": "CFGGuider",
"inputs": {
"cfg": 1,
"model": [
"92:70",
0
],
"negative": [
"92:84:76",
0
],
"positive": [
"92:84:77",
0
]
},
"_meta": {
"title": "CFG Guider"
}
},
"92:64": {
"class_type": "SamplerCustomAdvanced",
"inputs": {
"guider": [
"92:63",
0
],
"latent_image": [
"92:66",
0
],
"noise": [
"92:73",
0
],
"sampler": [
"92:61",
0
],
"sigmas": [
"92:62",
0
]
},
"_meta": {
"title": "SamplerCustomAdvanced"
}
},
"92:65": {
"class_type": "VAEDecode",
"inputs": {
"samples": [
"92:64",
0
],
"vae": [
"92:72",
0
]
},
"_meta": {
"title": "VAE Decode"
}
},
"92:66": {
"class_type": "EmptyFlux2LatentImage",
"inputs": {
"batch_size": 1,
"height": [
"92:81",
1
],
"width": [
"92:81",
0
]
},
"_meta": {
"title": "Empty Flux 2 Latent"
}
},
"92:70": {
"class_type": "UNETLoader",
"inputs": {
"unet_name": "flux-2-klein-4b-fp8.safetensors",
"weight_dtype": "default"
},
"_meta": {
"title": "Load Diffusion Model"
}
},
"92:71": {
"class_type": "CLIPLoader",
"inputs": {
"clip_name": "qwen_3_4b.safetensors",
"device": "default",
"type": "flux2"
},
"_meta": {
"title": "Load CLIP"
}
},
"92:72": {
"class_type": "VAELoader",
"inputs": {
"vae_name": "flux2-vae.safetensors"
},
"_meta": {
"title": "Load VAE"
}
},
"92:73": {
"class_type": "RandomNoise",
"inputs": {
"noise_seed": 432262096973495
},
"_meta": {
"title": "RandomNoise"
}
},
"92:74": {
"class_type": "CLIPTextEncode",
"inputs": {
"clip": [
"92:71",
0
],
"text": "Restyle the object in image 1 with the woven pattern and colours from the textile in image 2. Cover the whole enclosure and its lid with the stepped medallions and sunburst motifs, in the same vermilion red, cobalt blue, saffron yellow and black, as if the pattern were enamelled onto the surface. Let the motifs wrap naturally around the edges and follow the bevelled corners and the recessed seam, scaled so several full medallions fit across the top. Keep the object's exact shape, size, position and the round stone plinth beneath it unchanged. Keep the warm taupe studio backdrop, the soft overhead light and the gentle contact shadow from image 1. The finish is a smooth glossy glaze with soft reflections, crisp edges and no text."
},
"_meta": {
"title": "CLIP Text Encode (Positive Prompt)"
}
},
"92:79:76": {
"class_type": "ReferenceLatent",
"inputs": {
"conditioning": [
"92:86",
0
],
"latent": [
"92:79:78",
0
]
},
"_meta": {
"title": "Set Reference Latent"
}
},
"92:79:77": {
"class_type": "ReferenceLatent",
"inputs": {
"conditioning": [
"92:74",
0
],
"latent": [
"92:79:78",
0
]
},
"_meta": {
"title": "Set Reference Latent"
}
},
"92:79:78": {
"class_type": "VAEEncode",
"inputs": {
"pixels": [
"92:80",
0
],
"vae": [
"92:72",
0
]
},
"_meta": {
"title": "VAE Encode"
}
},
"92:80": {
"class_type": "ImageScaleToTotalPixels",
"inputs": {
"image": [
"76",
0
],
"megapixels": 1,
"resolution_steps": 1,
"upscale_method": "nearest-exact"
},
"_meta": {
"title": "Scale Image to Total Pixels"
}
},
"92:81": {
"class_type": "GetImageSize",
"inputs": {
"image": [
"92:80",
0
]
},
"_meta": {
"title": "Get Image Size"
}
},
"92:84:76": {
"class_type": "ReferenceLatent",
"inputs": {
"conditioning": [
"92:79:76",
0
],
"latent": [
"92:84:78",
0
]
},
"_meta": {
"title": "Set Reference Latent"
}
},
"92:84:77": {
"class_type": "ReferenceLatent",
"inputs": {
"conditioning": [
"92:79:77",
0
],
"latent": [
"92:84:78",
0
]
},
"_meta": {
"title": "Set Reference Latent"
}
},
"92:84:78": {
"class_type": "VAEEncode",
"inputs": {
"pixels": [
"92:85",
0
],
"vae": [
"92:72",
0
]
},
"_meta": {
"title": "VAE Encode"
}
},
"92:85": {
"class_type": "ImageScaleToTotalPixels",
"inputs": {
"image": [
"81",
0
],
"megapixels": 1,
"resolution_steps": 1,
"upscale_method": "nearest-exact"
},
"_meta": {
"title": "Scale Image to Total Pixels"
}
},
"92:86": {
"class_type": "ConditioningZeroOut",
"inputs": {
"conditioning": [
"92:74",
0
]
},
"_meta": {
"title": "Conditioning Zero Out"
}
}
})
workflow.set_input("76", "image", client.assets.from_url("https://comfy.org/catalog-media/904478c3-f8cb-49d8-ae87-2d2a37c7c277/7da4b4ee-74cd-4e72-b27d-4f79fefa975c"))
workflow.set_input("81", "image", client.assets.from_url("https://comfy.org/catalog-media/8dca4d88-7b50-457a-9563-a094cc1750c2/634b4e77-cc50-4a50-81ac-87180de56035"))
# run() also passes api_key to the partner nodes in this workflow.
job = client.run(workflow, api_key=api_key)
for output in job.get_outputs("94"):
output.to_file(output.name)