Face-similarity
One number for “does this still look like the same person?”
- main_image
- compare_image
- STRING
Character consistency is the eternal ComfyUI complaint: generate fifty images of a character and it feels like fifty different people came out. The model has no memory - each image is sampled fresh and the face drifts. The classic fix is to generate, eyeball everything, and toss the ones that drifted. This node automates the eyeball part. Give it two images and it returns a confidence score, 0–100, for "these are the same face."
Where it slots into a workflow: your reference image on one side, a batch of renders on the other, and a quick score for how close each render stayed to the reference. That's a job the community has wanted automated for years - the old threads asking "how do I compare a generated face against my reference without doing it by hand?" are exactly this use case.
What it actually does
Read faceSimilarity.py and there's no machine learning in this pack at all. The node takes both IMAGE tensors, converts them back to PNGs, and POSTs them to Face++'s compare endpoint:
url = "https://api-cn.faceplusplus.com/facepp/v3/compare"
files = {"image_file1": <png bytes>, "image_file2": <png bytes>}
Face++ detects a face in each image, embeds both, and compares them server-side, returning a confidence value. The node rounds it to two decimals, prints a verdict to the console - it logs "same person" when the score is over 80 - and hands the score back as a string. That's the whole mechanism: one HTTP call, no local model, no VRAM, no weights.
The inputs and the output that matter
Two images in, one string out. That's the entire surface area:
main_image(IMAGE) - your reference.compare_image(IMAGE) - the render you're checking.- Output -
STRING, a confidence score like"92.35".
Two things to remember. First, the output is a string, not a number - you can't wire it into an if or a math node without converting it to FLOAT first. Second, the 80-point threshold is baked into the source's print statement, not exposed as a widget, so if you want to treat 70 as "close enough" you're editing code, not flipping a dropdown. As a rule of thumb, treat 80+ as a solid match and low scores as "that's someone else."
Installing it
Same story as the pack's other node - no models, no heavy dependencies:
- ComfyUI Manager: search "FaceSimilarity", install, restart.
- Or manually:
cd ComfyUI/custom_nodes
git clone https://github.com/ultimatech-cn/FaceSimilarity
pip install -r requirements.txt # opencv-python
Then restart ComfyUI. The only entry in requirements.txt is opencv-python, which the module imports at load even though the comparison never actually uses it - skip the pip install and the node silently won't exist. There's also no key widget: the API key is hardcoded in the file and shared by everyone using the pack. The README suggests editing in your own Face++ key, and the author offers a free key good for about 200 uses if you ping the WeChat公众号 with "Face++". Budget accordingly.
The catches
- A failed call reads as "not the same person." This is the trap that'll bite you. If anything goes wrong - no face detected in one of the images, the API throttles, the network is blocked - the node's exception handler returns
"0". A score of 0 reads as "completely different people," and you'd silently discard renders that were actually fine. Treat a flat"0"or missing result as a red flag, not a verdict. - Privacy. Both images go to a Chinese cloud -
api-cnis hardwired. Generated faces, fine. Real people, think hard before you upload. - Shared key, rate-limited. One key, every user of the pack hammering it. When it dies, calls fail and you're back in the "0" trap above.
- One image per call. Scoring fifty renders means fifty round-trips with a PNG upload each. Not instant, and it burns the rate limit fast.
If you want this locally and privately, the ecosystem-standard backbone is InsightFace - the engine under FaceID, InstantID, PuLID and Roop. It's a heavier install, but nothing leaves your machine and you can score as many images as you like for free. This node is the quick-and-cloud version: minutes to set up, works anywhere, but it costs you trust in a shared key and a one-way trip for your faces. Fine as a character-consistency sanity check; read the docs before you point it at real people.
Inputs (2)
| Name | Type | Default | Description |
|---|---|---|---|
| main_image | IMAGE | — | |
| compare_image | IMAGE | — |
Outputs (1)
| Name | Type | Description |
|---|---|---|
| STRING | STRING | — |