आपके पास कुछ सौ प्रोडक्ट फोटो, हेडशॉट या लिस्टिंग इमेज का फ़ोल्डर है, और हर एक का बैकग्राउंड हटाना है। एडिटर में हाथ से करना पूरे दिन क्लिक करने का काम है। Python में यह एक लूप है, और असली फ़ैसला यह है कि लूप के अंदर क्या चलेगा: आपकी अपनी मशीन पर ओपन-सोर्स मॉडल, या HTTP API।
यह गाइड दोनों बनाती है, पूरी स्क्रिप्ट के साथ जिन्हें आप आज ही किसी फ़ोल्डर पर चला सकते हैं, और उन हिस्सों को कवर करती है जो बैच जॉब को भरोसेमंद बनाते हैं: मॉडल चुनना, CPU बनाम GPU, रीट्राई, रेट लिमिट, idempotency और क्रैश के बाद फिर से शुरू करना।
विकल्प A या विकल्प B?
| लोकल मॉडल (rembg) | HTTP API | |
|---|---|---|
| लागत | मुफ़्त सॉफ़्टवेयर; आप हार्डवेयर और समय में चुकाते हैं | हर इमेज के हिसाब से |
| सेटअप | Python 3.11 से 3.13, मॉडल डाउनलोड, वैकल्पिक CUDA | एक API की और requests |
| स्पीड | आपके CPU या GPU और मॉडल पर निर्भर | सेवा और पैरेलल रिक्वेस्ट पर निर्भर |
| क्वालिटी | आपके चुने मॉडल पर निर्भर | सेवा पर निर्भर |
| प्राइवेसी | इमेज कभी आपकी मशीन से बाहर नहीं जातीं | इमेज किसी तीसरे पक्ष पर अपलोड होती हैं |
| रखरखाव | मॉडल, ड्राइवर और लाइसेंस आप संभालते हैं | प्रोवाइडर संभालता है |
| किसके लिए अच्छा | ऑफ़लाइन काम, संवेदनशील इमेज, प्रयोग | प्रोडक्शन पाइपलाइन, बिना GPU वाले सर्वर |
कई टीमें दोनों इस्तेमाल करती हैं: प्रयोगों और अंदरूनी टूल के लिए लोकल मॉडल, और प्रोडक्शन के लिए API जहां अनुमान लायक क्वालिटी और GPU सर्वर न होना ज़्यादा मायने रखता है।
विकल्प A: rembg, ओपन-सोर्स रास्ता
rembg एक MIT-लाइसेंस वाली Python लाइब्रेरी और CLI है जो कई बैकग्राउंड रिमूवल मॉडल को लपेटती है और उन्हें ONNX Runtime से चलाती है। इसे लिखते समय मौजूदा रिलीज़ 2.0.86 है, और इसके लिए Python 3.11 या बाद का और 3.14 से पहले का चाहिए।
इंस्टॉल करें
अपने हार्डवेयर से मेल खाता बैकएंड चुनें। CPU बिल्ड हर जगह चलता है:
python -m venv .venv && source .venv/bin/activate
pip install "rembg[cpu]" # library only
pip install "rembg[cpu,cli]" # library plus the rembg commandNVIDIA GPU के लिए इसके बजाय rembg[gpu] इंस्टॉल करें। प्रोजेक्ट बताता है कि इसके लिए onnxruntime-gpu और मेल खाते CUDA और cuDNN चाहिए, और सुझाव देता है कि अगर आप इन्हें इंस्टॉल न कर सकें तो CPU बिल्ड पर लौट जाएं। Linux पर AMD GPU onnxruntime-rocm के साथ rembg[rocm] इस्तेमाल करते हैं।
जब ONNX Runtime CUDA (या ROCm) execution provider को उपलब्ध बताता है तो rembg उसे अपने आप चुन लेता है, और CPU पर लौटने पर चेतावनी देता है। ONNX Runtime क्या देख सकता है, यह जांचने के लिए:
import onnxruntime
print(onnxruntime.get_available_providers()) # look for CUDAExecutionProviderमॉडल चुनें
मॉडल पहली बार इस्तेमाल पर ~/.rembg/models/ में डाउनलोड होते हैं (बदलने के लिए REMBG_HOME सेट करें)। प्रोजेक्ट की सूची से कुछ काम के मॉडल:
| मॉडल | नोट्स |
|---|---|
bria-rmbg | डिफ़ॉल्ट। BRIA का RMBG-2.0, लगभग 1.02 GB, 1024 x 1024 पर चलता है। इसका लाइसेंस कमर्शियल इस्तेमाल के लिए पेड एग्रीमेंट मांगता है। |
birefnet-general | आम इस्तेमाल वाला BiRefNet मॉडल; अच्छे नरम किनारे |
birefnet-general-lite | आम इस्तेमाल के लिए हल्का BiRefNet |
birefnet-portrait | लोगों के लिए ट्यून किया गया |
isnet-general-use | आम इस्तेमाल वाला IS-Net मॉडल |
u2net | क्लासिक आम मॉडल; तेज़, ज़्यादा चौकोर किनारे |
u2netp | हल्का u2net; धीमी मशीनों पर जल्दी के टेस्ट |
silueta | u2net जैसा ही, 43 MB तक छोटा |
दो बातें दिखने से ज़्यादा अहम हैं। पहली, डिफ़ॉल्ट मॉडल कमर्शियल इस्तेमाल के लिए मुफ़्त नहीं है: मॉडल वेट के अपने लाइसेंस होते हैं, rembg के MIT लाइसेंस से अलग, इसलिए जो भी मॉडल आप इस्तेमाल करें उसका सोर्स जांचें। दूसरी, नए मॉडल (bria-rmbg, birefnet-*, isnet-general-use) नरम, अच्छे आकार वाले किनारे देते हैं, जबकि पुराना u2net परिवार ज़्यादा सख़्त, चौकोर किनारे देता है।
किनारे की क्वालिटी के विकल्प
rembg बालों और फ़र जैसे नरम किनारे वाले पिक्सल को संभालने के तीन तरीक़े देता है:
- डिफ़ॉल्ट: प्रोडक्ट, कार और लोगो जैसे सख़्त किनारे वाले विषयों के लिए ठीक।
decontaminate=True(CLI पर-dc): पुराना बैकग्राउंड किनारे के पिक्सल में जो रंगीन हेलो छोड़ता है उसे हटाता है। यह सिर्फ़ रंग बदलता है, मास्क का आकार कभी नहीं, बहुत कम लागत लेता है, और पूरे बैच के लिए चालू छोड़ना सुरक्षित है।alpha_matting=True(-a): जब मास्क का आकार ग़लत हो, जैसे लटें कट गई हों, तो किनारे का फिर से अनुमान लगाता है। यह बहुत धीमा है और converge होने में फ़ेल हो सकता है, जिस स्थिति में rembg डीकंटैमिनेटेड कटआउट पर लौट जाता है।
बिना निगरानी वाले बैच के लिए प्रोजेक्ट -a के बजाय -dc की सलाह देता है क्योंकि यह तेज़ है और फ़ेल नहीं हो सकता। अल्फ़ा चैनल गाइड बताती है कि हेलो क्यों आते हैं।
तेज़ तरीक़ा: CLI
rembg p -m birefnet-general -dc photos/ cutouts/rembg p पूरा फ़ोल्डर प्रोसेस करता है; फ़ोल्डर पर नज़र रखने और नई फ़ाइलें आते ही प्रोसेस करने के लिए -w जोड़ें।
Python स्क्रिप्ट
यह वर्ज़न मॉडल एक बार लोड करता है, पहले से तैयार फ़ाइलें छोड़ देता है ताकि आप रोककर फिर शुरू कर सकें, और एक फ़ाइल फ़ेल होने पर भी चलता रहता है:
import sys
from pathlib import Path
from rembg import new_session, remove
EXTS = {".jpg", ".jpeg", ".png", ".webp"}
def main(in_dir: str, out_dir: str, model: str = "birefnet-general") -> None:
src_dir, dst_dir = Path(in_dir), Path(out_dir)
dst_dir.mkdir(parents=True, exist_ok=True)
session = new_session(model) # load the model once, reuse it for every image
files = sorted(p for p in src_dir.iterdir() if p.suffix.lower() in EXTS)
for i, src in enumerate(files, 1):
dst = dst_dir / f"{src.stem}.png"
if dst.exists():
continue # resume where a previous run stopped
try:
out = remove(src.read_bytes(), session=session, decontaminate=True)
dst.write_bytes(out)
print(f"[{i}/{len(files)}] ok {src.name}")
except Exception as e: # one bad file shouldn't stop the batch
print(f"[{i}/{len(files)}] failed {src.name}: {e}")
if __name__ == "__main__":
main(*sys.argv[1:])इसे python batch_rembg.py photos cutouts birefnet-general से चलाएं। सेशन एक बार बनाना मायने रखता है: मॉडल लोड करने में उसे चलाने से कहीं ज़्यादा समय लगता है, और rembg README बैच परफ़ॉर्मेंस के लिए सेशन दोबारा इस्तेमाल करने की सलाह देता है। आउटपुट हमेशा PNG होते हैं क्योंकि नतीजे में अल्फ़ा चैनल होता है।
rembg कहां कम पड़ता है
- मॉडल डाउनलोड होते समय पहला रन धीमा होता है, और बड़े मॉडल को बहुत RAM या VRAM चाहिए।
- ऊंची क्वालिटी वाले मॉडल के साथ CPU थ्रूपुट मामूली है। हज़ार पर लगने से पहले 20 प्रतिनिधि इमेज से टेस्ट करें।
- लाइसेंस और ड्राइवर आपकी ज़िम्मेदारी हैं। अपने rembg और मॉडल वर्ज़न पिन करें ताकि बाद का अपग्रेड चुपचाप नतीजे न बदल दे।
विकल्प B: HTTP API
API के साथ भारी काम किसी और के GPU पर होता है, और आपकी स्क्रिप्ट ज़्यादातर नेटवर्क को ठीक से संभालने के बारे में है। उदाहरण removebackground.dev API इस्तेमाल करता है क्योंकि इसका कॉन्ट्रैक्ट /openapi.json पर OpenAPI 3.1 के रूप में प्रकाशित है; यही पैटर्न किसी भी मिलती-जुलती सेवा पर लागू होते हैं।
कॉन्ट्रैक्ट
x-api-keyहेडर में अपनी की के साथPOST https://removebackground.dev/v1/remove।- इमेज को multipart फ़ील्ड
image_fileके रूप में भेजें (JPG, PNG या WebP, 25 MB तक), याimage_urlके साथ JSON के रूप में। - वैकल्पिक फ़ील्ड में
format(png,jpgयाwebp),bg_color,size(preview,medium,hd,full) औरcropशामिल हैं। - 200 का मतलब है कि बॉडी तैयार इमेज है। 202 का मतलब है कि लगभग 55 सेकंड बाद भी प्रोसेसिंग चल रही है: बॉडी जॉब
idवाला JSON है, और आपGET /v1/jobs/{id}/resultको पोल करते हैं, जो इमेज तैयार होने तकRetry-Afterके साथ 409not_readyजवाब देता है। 202 बॉडी को कभी इमेज के रूप में सेव न करें। - हर अकाउंट के लिए एक मिनट में 60 प्रोसेसिंग रिक्वेस्ट तक; इससे ज़्यादा पर आपको
Retry-Afterके साथ 429rate_limitedमिलता है। - एक
Idempotency-Keyहेडर रीट्राई को सुरक्षित बनाता है: उसी रिक्वेस्ट के साथ वही की दोबारा चार्ज करने के बजाय असली जॉब लौटाती है। अलग रिक्वेस्ट के साथ वही की 409idempotency_key_reusedजवाब देती है। - नतीजे 48 घंटे बाद डिलीट हो जाते हैं, इसलिए मिलते ही सेव करें।
रीट्राई के नियम जो आपको दोबारा भुगतान से बचाते हैं
| रिस्पॉन्स | क्या करें |
|---|---|
| 200 | इमेज सेव करें |
| 202 | जॉब रिज़ल्ट पोल करें; दोबारा अपलोड न करें |
| 400, 401, 402, 413, 422 | रिक्वेस्ट, की, क्रेडिट या इमेज ठीक करें; लूप न करें |
| 429 | Retry-After सेकंड रुकें, उसी की के साथ दोबारा भेजें |
| 500, 503, टाइमआउट, टूटा कनेक्शन | रुककर उसी की के साथ दोबारा भेजें |
| 502 | वह इमेज फ़ेल हुई और चार्ज नहीं हुई; लॉग करें |
तरकीब यह है कि idempotency की को निश्चित (deterministic) बनाएं: इमेज बाइट और विकल्पों का हैश। अगर स्क्रिप्ट क्रैश हो और आप उसे दोबारा चलाएं, तो हर दोबारा भेजी गई रिक्वेस्ट में वही की होती है, इसलिए कुछ भी दो बार प्रोसेस या चार्ज नहीं होता।
Python स्क्रिप्ट
import hashlib
import mimetypes
import os
import sys
import time
from concurrent.futures import ThreadPoolExecutor, as_completed
from pathlib import Path
import requests
API = os.environ.get("REMOVEBG_API", "https://removebackground.dev")
KEY = os.environ["REMOVEBG_API_KEY"] # keep the key out of your code
OPTIONS = {"format": "png", "size": "full"} # or {"format": "jpg", "bg_color": "ffffff"}
WORKERS = 4 # the API allows 60 processing requests a minute
EXTS = {".jpg", ".jpeg", ".png", ".webp"}
RETRYABLE = {429, 500, 503}
def idempotency_key(data: bytes) -> str:
# Same image + same options = same key, so a rerun never pays twice.
h = hashlib.sha256(data)
h.update(repr(sorted(OPTIONS.items())).encode())
return h.hexdigest()
def wait(res, default=2.0):
try:
return float(res.headers.get("Retry-After", default))
except ValueError:
return default
def save(res, dst: Path) -> Path:
if res.status_code != 200 or not res.headers.get("Content-Type", "").startswith("image/"):
raise RuntimeError(f"HTTP {res.status_code}: {res.text[:300]}")
dst.write_bytes(res.content)
return dst
def process(src: Path, dst: Path) -> Path:
data = src.read_bytes()
mime = mimetypes.guess_type(src.name)[0] or "application/octet-stream"
headers = {"x-api-key": KEY, "Idempotency-Key": idempotency_key(data)}
for attempt in range(6):
try:
res = requests.post(
f"{API}/v1/remove",
files={"image_file": (src.name, data, mime)},
data=OPTIONS,
headers=headers,
timeout=(10, 120),
)
except (requests.ConnectionError, requests.Timeout):
time.sleep(2 ** attempt) # same key: safe to resend
continue
if res.status_code in RETRYABLE:
time.sleep(wait(res, 2 ** attempt))
continue
break
else:
raise RuntimeError("gave up after retries")
if res.status_code != 202:
return save(res, dst) # 200 is the image; 4xx and 502 raise
# 202: still processing. Poll the same job; never upload the image again.
job_id = res.json()["id"]
deadline = time.monotonic() + 600
while time.monotonic() < deadline:
time.sleep(wait(res))
try:
res = requests.get(f"{API}/v1/jobs/{job_id}/result", headers=headers, timeout=30)
except (requests.ConnectionError, requests.Timeout):
continue # reading a job is free and safe to repeat
if res.status_code == 409 and res.json()["error"]["code"] == "not_ready":
continue
if res.status_code >= 500:
continue
return save(res, dst)
raise TimeoutError(f"job {job_id} still running; fetch it later")
def main(in_dir: str, out_dir: str) -> None:
src_dir, dst_dir = Path(in_dir), Path(out_dir)
dst_dir.mkdir(parents=True, exist_ok=True)
ext = ".jpg" if OPTIONS.get("format") == "jpg" else "." + OPTIONS.get("format", "png")
todo = [
(p, dst_dir / (p.stem + ext))
for p in sorted(src_dir.iterdir())
if p.suffix.lower() in EXTS and not (dst_dir / (p.stem + ext)).exists()
]
print(f"{len(todo)} images to process")
failed = []
with ThreadPoolExecutor(max_workers=WORKERS) as pool:
jobs = {pool.submit(process, s, d): s for s, d in todo}
for fut in as_completed(jobs):
src = jobs[fut]
try:
print("ok ", src.name, "->", fut.result().name)
except Exception as e:
failed.append(src.name)
print("failed", src.name, e)
print(f"done: {len(todo) - len(failed)} ok, {len(failed)} failed")
if __name__ == "__main__":
main(sys.argv[1], sys.argv[2])इसे REMOVEBG_API_KEY=... python batch_api.py photos cutouts से चलाएं। चार वर्कर एक मामूली शुरुआत है; अगर तेज़ रिस्पॉन्स आपको प्रति मिनट की सीमा से आगे ले जाएं, तो 429 हैंडलिंग रुककर उसी की के साथ दोबारा भेजती है। फ़ाइलों के बजाय URL भेजने के लिए JSON पोस्ट करें:
res = requests.post(
f"{API}/v1/remove",
json={"image_url": "https://example.com/shoe.jpg", "format": "png"},
headers={"x-api-key": KEY, "Idempotency-Key": "shoe-front-v1"},
timeout=(10, 120),
)URL की लंबी सूचियों के लिए उसी API में POST /v1/batch है, जो 100 इमेज URL तक को एक जॉब के रूप में क़तार में रखता है जिसे आप पोल करते हैं।
किसी भी बैच जॉब को मज़बूत बनाना
- तैयार आउटपुट छोड़ दें ताकि दोबारा चलाने पर नए सिरे से शुरू करने के बजाय वहीं से आगे बढ़े। दोनों स्क्रिप्ट यह करती हैं।
- नामों के टकराव पर नज़र रखें। एक ही फ़ोल्डर में
shoe.jpgऔरshoe.pngदोनोंshoe.pngबन जाते हैं; इनपुट का नाम बदलें या आउटपुट नाम में असली एक्सटेंशन शामिल करें। - फ़ेल हुई फ़ाइलों को एक फ़ाइल में लॉग करें और सिर्फ़ उन्हें दोबारा चलाएं।
- सब कुछ प्रोसेस करने से पहले एक सैंपल को गहरे और हल्के बैकग्राउंड पर 100% ज़ूम पर जांचें।
- असली फ़ाइलों को न छुएं। अलग आउटपुट फ़ोल्डर में लिखें।
- मंज़िल के हिसाब से आउटपुट फ़ॉर्मैट चुनें। ट्रांसपेरेंसी के लिए PNG या WebP, मार्केटप्लेस के लिए सफ़ेद पर JPG। देखें PNG बनाम JPEG बनाम WebP।
सवाल
क्या rembg कमर्शियल इस्तेमाल के लिए मुफ़्त है?
rembg खुद MIT लाइसेंस वाला है, लेकिन हर मॉडल का अपना लाइसेंस है। डिफ़ॉल्ट मॉडल, BRIA का RMBG-2.0 (bria-rmbg), कमर्शियल इस्तेमाल के लिए पेड एग्रीमेंट मांगता है, इसलिए जो मॉडल इस्तेमाल करें उसका लाइसेंस जांचें या कोई दूसरा चुनें।
क्या rembg अपने आप मेरा GPU इस्तेमाल करता है?
हां, अगर आप rembg[gpu] इंस्टॉल करें और ONNX Runtime CUDA provider लोड कर सके (जिसके लिए मेल खाते CUDA और cuDNN चाहिए)। rembg उपलब्ध होने पर CUDA या ROCm इस्तेमाल करता है और CPU पर लौटने पर चेतावनी देता है। onnxruntime.get_available_providers() जांचें।
कौन सा rembg मॉडल सबसे अच्छी क्वालिटी देता है?
नए मॉडल, bria-rmbg (डिफ़ॉल्ट), birefnet परिवार और isnet-general-use, पुराने u2net परिवार से ज़्यादा नरम और बेहतर आकार वाले किनारे देते हैं। लोगों के लिए birefnet-portrait अच्छी शुरुआत है। अपनी इमेज के एक सैंपल पर टेस्ट करें, क्योंकि नतीजे विषय के हिसाब से बदलते हैं।
API कॉल रीट्राई करते समय दोबारा चार्ज होने से कैसे बचें?
एक Idempotency-Key हेडर भेजें और उसी इमेज के हर रीट्राई पर उसे दोबारा इस्तेमाल करें। इसे इमेज बाइट और विकल्पों के हैश से बनाने का मतलब है कि पूरी स्क्रिप्ट दोबारा चलाने पर भी वही की इस्तेमाल होती हैं।
202 रिस्पॉन्स पर मेरी स्क्रिप्ट को क्या करना चाहिए?
इसे अब भी प्रोसेस हो रहा मानें, इमेज नहीं। JSON बॉडी से जॉब id पढ़ें और GET /v1/jobs/{id}/result को पोल करें, और जब भी वह 409 not_ready जवाब दे तो Retry-After तक रुकें। इमेज दोबारा अपलोड न करें।
removebackground.dev API पर मैं कितनी तेज़ी से रिक्वेस्ट भेज सकता हूं?
हर अकाउंट के लिए एक मिनट में 60 प्रोसेसिंग रिक्वेस्ट तक। इससे ज़्यादा पर API Retry-After हेडर के साथ 429 rate_limited जवाब देता है। कई URL के लिए POST /v1/batch हर रिक्वेस्ट में 100 तक लेता है।
अपनी इमेज पर आज़माएं
नए अकाउंट को 50 मुफ़्त क्रेडिट मिलते हैं। हर इमेज के लिए 1 क्रेडिट, कोई सब्सक्रिप्शन नहीं, और क्रेडिट कभी खत्म नहीं होते।
बैकग्राउंड हटाएंस्रोत
- rembg on GitHub (README: installation, models, edge modes)
- rembg on PyPI (version and Python requirement)
- BRIA RMBG-2.0 model card and license
- ONNX Runtime: Get started and installation matrix
- removebackground.dev API reference and guides
- removebackground.dev OpenAPI 3.1 schema
- Requests: Quickstart (multipart file uploads, timeouts)