rickveloper commited on
Commit
7cd5b28
·
verified ·
1 Parent(s): 8e257d6

Update app.py

Browse files
Files changed (1) hide show
  1. app.py +56 -33
app.py CHANGED
@@ -4,18 +4,16 @@ from PIL import Image, ImageDraw, ImageFont
4
  import gradio as gr
5
 
6
  # ==============================
7
- # Secrets / Config
8
  # ==============================
9
- HF_TOKEN = os.getenv("HF_TOKEN") # optional, via Repo Secrets
10
- # Try these Inference API models in order; skip silently on 404/403/5xx
11
  INFERENCE_CANDIDATES = [
12
  "stabilityai/stable-diffusion-2-1",
13
  "runwayml/stable-diffusion-v1-5",
14
- "stabilityai/sd-turbo", # may 404 for some accounts
15
  ]
16
- # Public Space as last resort (no token). If they change UI, we still fail gracefully.
17
  PUBLIC_SPACE_ID = "black-forest-labs/FLUX.1-schnell"
18
- PUBLIC_SPACE_APIS = ["/predict", "/run"]
19
 
20
  # ==============================
21
  # Fonts
@@ -34,10 +32,8 @@ def get_font(size: int):
34
  # Utils
35
  # ==============================
36
  def i(v):
37
- try:
38
- return int(round(float(v)))
39
- except Exception:
40
- return int(v)
41
 
42
  def gradient_from_prompt(prompt: str, w=768, h=768) -> Image.Image:
43
  w, h = i(w), i(h)
@@ -98,8 +94,7 @@ PRESETS = {
98
  }
99
  def smart_split_text(prompt: str):
100
  p = (prompt or "").strip()
101
- if not p:
102
- return "TOP TEXT", "BOTTOM TEXT"
103
  for sep in ["|", " - ", " — ", ":", ";"]:
104
  if sep in p:
105
  a, b = p.split(sep, 1)
@@ -115,52 +110,80 @@ def smart_split_text(prompt: str):
115
  # ==============================
116
  def call_inference_api(model_id: str, prompt: str, width: int, height: int) -> Image.Image:
117
  if not HF_TOKEN:
118
- raise RuntimeError("HF token not set")
119
  url = f"https://api-inference.huggingface.co/models/{model_id}"
120
  headers = {"Authorization": f"Bearer {HF_TOKEN}"}
121
- payload = {
122
- "inputs": prompt,
123
- "options": {"wait_for_model": True},
124
- "parameters": {"width": int(width), "height": int(height)}
125
- }
126
  r = requests.post(url, headers=headers, json=payload, timeout=180)
127
  if r.status_code != 200:
128
- raise RuntimeError(f"{r.status_code}:{r.text[:160]}")
129
  return Image.open(BytesIO(r.content)).convert("RGB")
130
 
131
- def call_public_space(prompt: str, width: int, height: int) -> Image.Image:
132
- # no token required
133
  from gradio_client import Client
134
  client = Client(PUBLIC_SPACE_ID)
135
- # try multiple API names to survive UI tweaks
136
  last_err = None
137
- for api in PUBLIC_SPACE_APIS:
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
138
  try:
139
- res = client.predict(prompt, width, height, api_name=api)
140
  if isinstance(res, list): res = res[0]
141
  return Image.open(res).convert("RGB")
142
  except Exception as e:
143
  last_err = e
144
  continue
145
- raise RuntimeError(f"public-space-fail:{last_err}")
146
 
147
  def generate_image_auto(prompt: str, width: int, height: int):
148
- # 1) try HF Inference API candidates
149
  tried = []
 
150
  if HF_TOKEN:
151
  for mid in INFERENCE_CANDIDATES:
152
  try:
153
  img = call_inference_api(mid, prompt, width, height)
154
  return img, f"✅ Inference API: **{mid}** (token present)"
155
  except Exception as e:
156
- tried.append(f"{mid}→{str(e)[:80]}")
157
- # 2) try public Space (no token)
 
158
  try:
159
- img = call_public_space(prompt, width, height)
160
- return img, f"✅ Public Space: **{PUBLIC_SPACE_ID}**"
161
  except Exception as e:
162
- tried.append(f"{PUBLIC_SPACE_ID}→{str(e)[:80]}")
163
- # 3) fallback gradient
164
  return gradient_from_prompt(prompt, w=width, h=height), f"⚠️ Fallback gradient | tried: {', '.join(tried)}"
165
 
166
  # ==============================
@@ -184,7 +207,7 @@ def generate_and_meme(
184
  else:
185
  img, status = gradient_from_prompt(gen_prompt, w=width, h=height), "ℹ️ AI generator is OFF"
186
 
187
- # text
188
  if use_prompt_for_text:
189
  top_text, bottom_text = smart_split_text(base)
190
  else:
 
4
  import gradio as gr
5
 
6
  # ==============================
7
+ # Config / Secrets
8
  # ==============================
9
+ HF_TOKEN = os.getenv("HF_TOKEN") # optional
10
+ # Try these Inference API model IDs first (will skip on 404/403/5xx)
11
  INFERENCE_CANDIDATES = [
12
  "stabilityai/stable-diffusion-2-1",
13
  "runwayml/stable-diffusion-v1-5",
 
14
  ]
15
+ # Public Space fallback (no token). We'll DISCOVER a valid api_name at runtime.
16
  PUBLIC_SPACE_ID = "black-forest-labs/FLUX.1-schnell"
 
17
 
18
  # ==============================
19
  # Fonts
 
32
  # Utils
33
  # ==============================
34
  def i(v):
35
+ try: return int(round(float(v)))
36
+ except Exception: return int(v)
 
 
37
 
38
  def gradient_from_prompt(prompt: str, w=768, h=768) -> Image.Image:
39
  w, h = i(w), i(h)
 
94
  }
95
  def smart_split_text(prompt: str):
96
  p = (prompt or "").strip()
97
+ if not p: return "TOP TEXT", "BOTTOM TEXT"
 
98
  for sep in ["|", " - ", " — ", ":", ";"]:
99
  if sep in p:
100
  a, b = p.split(sep, 1)
 
110
  # ==============================
111
  def call_inference_api(model_id: str, prompt: str, width: int, height: int) -> Image.Image:
112
  if not HF_TOKEN:
113
+ raise RuntimeError("no-token")
114
  url = f"https://api-inference.huggingface.co/models/{model_id}"
115
  headers = {"Authorization": f"Bearer {HF_TOKEN}"}
116
+ payload = {"inputs": prompt, "options": {"wait_for_model": True},
117
+ "parameters": {"width": int(width), "height": int(height)}}
 
 
 
118
  r = requests.post(url, headers=headers, json=payload, timeout=180)
119
  if r.status_code != 200:
120
+ raise RuntimeError(f"{model_id}:{r.status_code}")
121
  return Image.open(BytesIO(r.content)).convert("RGB")
122
 
123
+ def call_public_space_dynamic(prompt: str, width: int, height: int) -> Image.Image:
124
+ # Discover an api_name and feed only fields we can infer.
125
  from gradio_client import Client
126
  client = Client(PUBLIC_SPACE_ID)
127
+ info = client.view_api(all_endpoints=True)
128
  last_err = None
129
+ for ep in info:
130
+ api = ep.get("api_name")
131
+ params = ep.get("parameters", [])
132
+ # Build arg list by index
133
+ args = [None] * len(params)
134
+ bad = False
135
+ for idx, p in enumerate(params):
136
+ label = (p.get("label") or "").lower()
137
+ # Skip endpoints that clearly require an image upload
138
+ if "image" in label and "prompt" not in label:
139
+ bad = True
140
+ break
141
+ if "prompt" in label or label in ("prompt", "text", "caption"):
142
+ args[idx] = prompt
143
+ elif "width" in label:
144
+ args[idx] = int(width)
145
+ elif "height" in label:
146
+ args[idx] = int(height)
147
+ elif "negative" in label:
148
+ args[idx] = ""
149
+ elif "steps" in label or "num_inference_steps" in label:
150
+ args[idx] = 4
151
+ elif "guidance" in label or "cfg" in label:
152
+ args[idx] = 3.5
153
+ elif "seed" in label:
154
+ args[idx] = 42
155
+ else:
156
+ # leave None; gradio_client will fill defaults
157
+ pass
158
+ if bad: # requires an image input etc.
159
+ continue
160
  try:
161
+ res = client.predict(*args, api_name=api)
162
  if isinstance(res, list): res = res[0]
163
  return Image.open(res).convert("RGB")
164
  except Exception as e:
165
  last_err = e
166
  continue
167
+ raise RuntimeError(f"space-no-endpoint:{last_err}")
168
 
169
  def generate_image_auto(prompt: str, width: int, height: int):
 
170
  tried = []
171
+ # 1) Inference API candidates (if token present)
172
  if HF_TOKEN:
173
  for mid in INFERENCE_CANDIDATES:
174
  try:
175
  img = call_inference_api(mid, prompt, width, height)
176
  return img, f"✅ Inference API: **{mid}** (token present)"
177
  except Exception as e:
178
+ tried.append(f"{mid}→{str(e)}")
179
+ continue
180
+ # 2) Public Space dynamic
181
  try:
182
+ img = call_public_space_dynamic(prompt, width, height)
183
+ return img, f"✅ Public Space: **{PUBLIC_SPACE_ID}** (discovered endpoint)"
184
  except Exception as e:
185
+ tried.append(f"{PUBLIC_SPACE_ID}→{str(e)}")
186
+ # 3) Gradient
187
  return gradient_from_prompt(prompt, w=width, h=height), f"⚠️ Fallback gradient | tried: {', '.join(tried)}"
188
 
189
  # ==============================
 
207
  else:
208
  img, status = gradient_from_prompt(gen_prompt, w=width, h=height), "ℹ️ AI generator is OFF"
209
 
210
+ # Text
211
  if use_prompt_for_text:
212
  top_text, bottom_text = smart_split_text(base)
213
  else: