Update app.py
Browse files
app.py
CHANGED
|
@@ -15,10 +15,23 @@ from PIL import Image, ImageOps
|
|
| 15 |
|
| 16 |
DEFAULT_MODEL = os.getenv("VISION_MODEL", "qwen/qwen3.6-27b")
|
| 17 |
DEFAULT_PROMPT = (
|
| 18 |
-
|
| 19 |
-
|
| 20 |
-
|
| 21 |
-
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 22 |
)
|
| 23 |
|
| 24 |
TFLIVE_RE = re.compile(
|
|
@@ -174,66 +187,27 @@ Requirements:
|
|
| 174 |
- Keep the response under 250 characters when practical.
|
| 175 |
"""
|
| 176 |
|
| 177 |
-
def generate_alt_text(client,
|
| 178 |
-
|
| 179 |
-
|
| 180 |
-
|
| 181 |
-
Return exactly one plain-text alt description and nothing else.
|
| 182 |
-
|
| 183 |
-
Rules:
|
| 184 |
-
1. Do not expose reasoning or analysis.
|
| 185 |
-
2. Do not use <think> tags.
|
| 186 |
-
3. Do not add a heading or label.
|
| 187 |
-
4. Do not begin with "Image of", "Picture of", or "This image shows".
|
| 188 |
-
5. Describe the image's essential information and function.
|
| 189 |
-
6. For diagrams, explain the main process or relationship rather than listing
|
| 190 |
-
every label.
|
| 191 |
-
7. Include visible text only when it is necessary to understand the image.
|
| 192 |
-
8. Do not speculate about unclear content.
|
| 193 |
-
9. Aim for one sentence and fewer than 250 characters.
|
| 194 |
-
"""
|
| 195 |
-
|
| 196 |
-
user_prompt = prompt or (
|
| 197 |
-
"Write accessible alt text for this image. "
|
| 198 |
-
"Return only the finished alt text."
|
| 199 |
-
)
|
| 200 |
-
|
| 201 |
-
response = client.chat.completions.create(
|
| 202 |
-
model="qwen/qwen3.6-27b",
|
| 203 |
reasoning_effort="none",
|
| 204 |
messages=[
|
| 205 |
-
{
|
| 206 |
-
"role": "system",
|
| 207 |
-
"content": system_prompt
|
| 208 |
-
},
|
| 209 |
{
|
| 210 |
"role": "user",
|
| 211 |
"content": [
|
| 212 |
-
{
|
| 213 |
-
"type": "text",
|
| 214 |
-
"text": user_prompt
|
| 215 |
-
},
|
| 216 |
{
|
| 217 |
"type": "image_url",
|
| 218 |
-
"image_url": {
|
| 219 |
-
|
| 220 |
-
|
| 221 |
-
}
|
| 222 |
-
]
|
| 223 |
}
|
| 224 |
],
|
|
|
|
| 225 |
temperature=0,
|
| 226 |
-
max_tokens=100
|
| 227 |
)
|
|
|
|
| 228 |
|
| 229 |
-
raw_text = response.choices[0].message.content or ""
|
| 230 |
-
cleaned_text = clean_alt_text(raw_text)
|
| 231 |
-
|
| 232 |
-
return {
|
| 233 |
-
"alt_text": cleaned_text,
|
| 234 |
-
"model_used": "qwen/qwen3.6-27b",
|
| 235 |
-
"error": ""
|
| 236 |
-
}
|
| 237 |
|
| 238 |
|
| 239 |
def process_table(
|
|
@@ -380,4 +354,4 @@ Upload a CSV, TSV, or Excel table containing one image value per row. The app re
|
|
| 380 |
)
|
| 381 |
|
| 382 |
if __name__ == "__main__":
|
| 383 |
-
demo.queue(default_concurrency_limit=2).launch()
|
|
|
|
| 15 |
|
| 16 |
DEFAULT_MODEL = os.getenv("VISION_MODEL", "qwen/qwen3.6-27b")
|
| 17 |
DEFAULT_PROMPT = (
|
| 18 |
+
"""
|
| 19 |
+
You create accessibility alt text for images.
|
| 20 |
+
|
| 21 |
+
Return only the finished alt text.
|
| 22 |
+
|
| 23 |
+
Requirements:
|
| 24 |
+
- Write one concise sentence.
|
| 25 |
+
- Describe the image's essential meaning and purpose.
|
| 26 |
+
- Do not describe every minor visual detail.
|
| 27 |
+
- Do not begin with "Image of", "Picture of", or "This image shows".
|
| 28 |
+
- Do not include analysis, reasoning, headings, XML tags, or bullet points.
|
| 29 |
+
- Do not include <think> tags.
|
| 30 |
+
- Do not identify people unless their identity is explicitly provided.
|
| 31 |
+
- For diagrams, summarize the main process or relationship.
|
| 32 |
+
- For charts, state the chart type and principal trend or conclusion.
|
| 33 |
+
- Keep the response under 250 characters when practical.
|
| 34 |
+
"""
|
| 35 |
)
|
| 36 |
|
| 37 |
TFLIVE_RE = re.compile(
|
|
|
|
| 187 |
- Keep the response under 250 characters when practical.
|
| 188 |
"""
|
| 189 |
|
| 190 |
+
def generate_alt_text(client, model, prompt, png_bytes, max_tokens):
|
| 191 |
+
completion = client.chat.completions.create(
|
| 192 |
+
model=model,
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 193 |
reasoning_effort="none",
|
| 194 |
messages=[
|
|
|
|
|
|
|
|
|
|
|
|
|
| 195 |
{
|
| 196 |
"role": "user",
|
| 197 |
"content": [
|
| 198 |
+
{"type": "text", "text": prompt},
|
|
|
|
|
|
|
|
|
|
| 199 |
{
|
| 200 |
"type": "image_url",
|
| 201 |
+
"image_url": {"url": _data_uri(png_bytes)},
|
| 202 |
+
},
|
| 203 |
+
],
|
|
|
|
|
|
|
| 204 |
}
|
| 205 |
],
|
| 206 |
+
max_tokens=int(max_tokens),
|
| 207 |
temperature=0,
|
|
|
|
| 208 |
)
|
| 209 |
+
return (completion.choices[0].message.content or "").strip()
|
| 210 |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 211 |
|
| 212 |
|
| 213 |
def process_table(
|
|
|
|
| 354 |
)
|
| 355 |
|
| 356 |
if __name__ == "__main__":
|
| 357 |
+
demo.queue(default_concurrency_limit=2).launch()
|