|
|
"""
|
|
|
Jade Web Dev - Vibe Coder
|
|
|
AI-powered web code generator
|
|
|
"""
|
|
|
|
|
|
import os
|
|
|
import logging
|
|
|
from groq import Groq
|
|
|
|
|
|
logger = logging.getLogger("JadeWebDev")
|
|
|
|
|
|
class WebDevAgent:
|
|
|
def __init__(self):
|
|
|
self.groq_api_key = os.getenv("GROQ_API_KEY")
|
|
|
if not self.groq_api_key:
|
|
|
logger.warning("GROQ_API_KEY not set. WebDev agent may fail.")
|
|
|
|
|
|
self.client = Groq(api_key=self.groq_api_key)
|
|
|
self.model = "moonshotai/kimi-k2-instruct-0905"
|
|
|
|
|
|
self.system_prompt = """You are an elite web developer AI creating stunning, FULLY FUNCTIONAL websites.
|
|
|
|
|
|
TECHNICAL REQUIREMENTS:
|
|
|
1. Use Tailwind CSS via CDN: <script src="https://cdn.tailwindcss.com"></script>
|
|
|
2. Output ONLY valid HTML - no markdown, no explanations, no code blocks
|
|
|
3. MUST include functional JavaScript in <script> tags
|
|
|
4. ALL styling must use Tailwind classes - no inline CSS
|
|
|
5. Must be a complete, standalone HTML file starting with <!DOCTYPE html>
|
|
|
|
|
|
JAVASCRIPT INTERACTIVITY (CRITICAL):
|
|
|
1. ALL buttons MUST have onclick handlers that DO something
|
|
|
2. Modals must open/close when clicked
|
|
|
3. Navigation tabs/links must show/hide content sections
|
|
|
4. Forms must have validation and show feedback
|
|
|
5. Counters, toggles, accordions must work
|
|
|
6. Use event listeners for all interactive elements
|
|
|
7. Mobile menu toggle must work
|
|
|
8. Add loading states, animations on interaction
|
|
|
|
|
|
DESIGN REQUIREMENTS:
|
|
|
1. Use modern, premium aesthetics (gradients, shadows, rounded corners)
|
|
|
2. Dark mode by default with rich colors (slate, zinc, purple, blue accents)
|
|
|
3. Smooth hover animations (hover:scale-105, hover:shadow-lg)
|
|
|
4. Professional typography (font-sans, proper spacing)
|
|
|
5. Responsive design (flex, grid, md:, lg: breakpoints)
|
|
|
6. Use placeholder images from picsum.photos
|
|
|
7. Include relevant icons using SVG
|
|
|
8. Add micro-interactions (transitions, transforms)
|
|
|
|
|
|
EXAMPLE OF WORKING BUTTON:
|
|
|
<button onclick="alert('Clicked!')" class="bg-purple-600 hover:bg-purple-700 px-4 py-2 rounded">
|
|
|
Click Me
|
|
|
</button>
|
|
|
|
|
|
EXAMPLE OF WORKING MODAL:
|
|
|
<div id="modal" class="hidden fixed inset-0 bg-black/50 flex items-center justify-center">
|
|
|
<div class="bg-slate-800 p-6 rounded-xl">
|
|
|
<button onclick="document.getElementById('modal').classList.add('hidden')">Close</button>
|
|
|
</div>
|
|
|
</div>
|
|
|
<button onclick="document.getElementById('modal').classList.remove('hidden')">Open Modal</button>
|
|
|
|
|
|
OUTPUT: Raw HTML only, starting with <!DOCTYPE html>"""
|
|
|
|
|
|
def generate(self, prompt: str, refine_code: str = None) -> dict:
|
|
|
"""
|
|
|
Generate or refine code based on prompt
|
|
|
|
|
|
Args:
|
|
|
prompt: User's description of the website
|
|
|
refine_code: Optional existing code to refine
|
|
|
|
|
|
Returns:
|
|
|
dict with 'code' and 'success' keys
|
|
|
"""
|
|
|
try:
|
|
|
if refine_code:
|
|
|
user_message = f"""Current code:
|
|
|
```html
|
|
|
{refine_code}
|
|
|
```
|
|
|
|
|
|
User feedback: {prompt}
|
|
|
|
|
|
Update the code based on the feedback. Output the complete updated HTML file."""
|
|
|
else:
|
|
|
user_message = f"Create a website: {prompt}"
|
|
|
|
|
|
response = self.client.chat.completions.create(
|
|
|
model=self.model,
|
|
|
messages=[
|
|
|
{"role": "system", "content": self.system_prompt},
|
|
|
{"role": "user", "content": user_message}
|
|
|
],
|
|
|
temperature=0.7,
|
|
|
max_tokens=8000
|
|
|
)
|
|
|
|
|
|
code = response.choices[0].message.content
|
|
|
|
|
|
|
|
|
code = code.strip()
|
|
|
if code.startswith("```html"):
|
|
|
code = code[7:]
|
|
|
if code.startswith("```"):
|
|
|
code = code[3:]
|
|
|
if code.endswith("```"):
|
|
|
code = code[:-3]
|
|
|
code = code.strip()
|
|
|
|
|
|
|
|
|
if not code.lower().startswith("<!doctype"):
|
|
|
code = "<!DOCTYPE html>\n" + code
|
|
|
|
|
|
return {"success": True, "code": code}
|
|
|
|
|
|
except Exception as e:
|
|
|
logger.error(f"WebDev generation error: {e}")
|
|
|
return {"success": False, "error": str(e)}
|
|
|
|