Ekenedirichukwu commited on
Commit
9ebf75a
·
verified ·
1 Parent(s): 2b08d2c

Upload app (1).py

Browse files
Files changed (1) hide show
  1. app (1).py +75 -0
app (1).py ADDED
@@ -0,0 +1,75 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ import base64
2
+ import gradio as gr
3
+ from huggingface_hub import InferenceClient
4
+
5
+ # Free serverless models
6
+ TEXT_MODEL = "Qwen/Qwen2.5-Coder-32B-Instruct" # strong at PHP / WordPress code
7
+ VISION_MODEL = "Qwen/Qwen2.5-VL-72B-Instruct" # can read screenshots
8
+
9
+ client = InferenceClient()
10
+
11
+ SYSTEM_PROMPT = (
12
+ "You are a senior WordPress plugin developer and web developer assistant. "
13
+ "You help write, debug, and explain PHP, WordPress plugin code (hooks, filters, "
14
+ "shortcodes, admin settings pages, Media Library integration), HTML, CSS, and "
15
+ "JavaScript. When shown a screenshot of a website, describe the layout/section "
16
+ "the user points to, then rebuild it as real HTML/CSS/PHP as closely as possible. "
17
+ "Give complete, working code. When code is long, deliver it in full, installable "
18
+ "form (ready to save as a .php file)."
19
+ )
20
+
21
+ def image_to_data_url(img_path):
22
+ with open(img_path, "rb") as f:
23
+ b64 = base64.b64encode(f.read()).decode("utf-8")
24
+ ext = img_path.split(".")[-1].lower()
25
+ mime = "jpeg" if ext in ("jpg", "jpeg") else ext
26
+ return f"data:image/{mime};base64,{b64}"
27
+
28
+ def chat(message, history):
29
+ # message can be a dict with "text" and "files" when multimodal input is used
30
+ text = message.get("text", "") if isinstance(message, dict) else message
31
+ files = message.get("files", []) if isinstance(message, dict) else []
32
+
33
+ messages = [{"role": "system", "content": SYSTEM_PROMPT}]
34
+ for turn in history:
35
+ if isinstance(turn, dict):
36
+ role = turn.get("role")
37
+ content = turn.get("content")
38
+ if role and content:
39
+ messages.append({"role": role, "content": content})
40
+
41
+ if files:
42
+ # Vision path: send image + text together to the VL model
43
+ content = [{"type": "text", "text": text or "What is in this screenshot? Rebuild the relevant section as code."}]
44
+ for f in files:
45
+ content.append({"type": "image_url", "image_url": {"url": image_to_data_url(f)}})
46
+ messages.append({"role": "user", "content": content})
47
+ model = VISION_MODEL
48
+ else:
49
+ messages.append({"role": "user", "content": text})
50
+ model = TEXT_MODEL
51
+
52
+ try:
53
+ response = client.chat_completion(
54
+ model=model,
55
+ messages=messages,
56
+ max_tokens=2048,
57
+ temperature=0.3,
58
+ )
59
+ return response.choices[0].message.content
60
+ except Exception as e:
61
+ return f"⚠️ Error calling the model: {e}"
62
+
63
+ demo = gr.ChatInterface(
64
+ fn=chat,
65
+ title="Free WordPress Dev Assistant (with screenshot support)",
66
+ description=(
67
+ "Free coding helper for WordPress plugins, PHP, HTML, and JS. "
68
+ "Attach a screenshot and ask it to rebuild that section as code. "
69
+ "Runs on Qwen2.5-Coder and Qwen2.5-VL via Hugging Face's free Inference API."
70
+ ),
71
+ multimodal=True,
72
+ )
73
+
74
+ if __name__ == "__main__":
75
+ demo.launch()