Files
devin/main.py
T
2025-09-12 11:12:23 +01:00

110 lines
3.3 KiB
Python

from rich import print
from rich.console import Console
from rich.table import Table
from rich.panel import Panel
from rich.progress import Progress, SpinnerColumn, BarColumn, track
from rich.markdown import Markdown
from rich.syntax import Syntax
from rich.live import Live
from rich.prompt import Prompt
import requests
import sys
from tools import ToolExecutor
import random
import time
LM_STUDIO_URL = "http://127.0.0.1:1234/v1/chat/completions" # default LM Studio endpoint
EXIT_STRINGS = ['exit','goodbye','go away','fuck off']
console = Console()
PRE_PROMPT = '''You have the following tools available, only use the tools if you need to.
please reply with only the tool call if you need to
{
"name": "get_weather",
"description": "Get current weather for a location",
"examples": [
{
"input": {"tool": "get_weather", "parameters":{"city":"New York"}},
"output": {"temperature": 22, "condition": "partly cloudy", "humidity": 65}
},
{
"input": {"tool": "get_weather", "parameters":{"city":"London"}},
"output": {"temperature": 18, "condition": "rainy", "humidity": 80}
}
]
}'''
# "parameters": {
# "type": "object",
# "properties": {
# "city": {"type": "string", "description": "City name"},
# },
# "required": ["city"]
# },
def ask_model(prompt: str, url=LM_STUDIO_URL) -> str:
payload = {
"model": 'qwen/qwen3-coder-30b',
"messages": [{"role": "user", "content": PRE_PROMPT+prompt}],
"temperature": 0.7,
"max_tokens": 2048,
}
resp = requests.post(url, json=payload)
resp.raise_for_status()
return resp.json()["choices"][0]["message"]["content"].strip()
def ask_model_no_pre(prompt: str, url=LM_STUDIO_URL) -> str:
payload = {
#"model": 'qwen/qwen3-coder-30b',
"model": 'openai/gpt-oss-20b',
"messages": [{"role": "user", "content": prompt}],
"temperature": 0.7,
"max_tokens": 2048,
}
resp = requests.post(url, json=payload)
resp.raise_for_status()
return resp.json()["choices"][0]["message"]["content"].strip()
def get_llm_prompt():
while True:
llm_prompt = Prompt.ask("[bold cyan]Ask your local llm[/]")
if llm_prompt.strip():
return llm_prompt.strip()
console.print("[red]Cannot be empty![/]", style="bold")
return llm_prompt
def handle_llm_reply(llm_reply:str):
architect = ToolExecutor()
return architect.process_llm_response(llm_output=llm_reply)
def main():
while True:
llm_prompt = get_llm_prompt()
if llm_prompt.lower() in EXIT_STRINGS:
sys.exit()
start = time.time()
llm_reply = ask_model(llm_prompt)
print(llm_reply)
handled_response = handle_llm_reply(llm_reply)
print(handled_response)
print(handled_response == llm_reply)
if handled_response != llm_reply:
output = ask_model_no_pre(prompt=f'Make this lovely markdown, use fun emojis {handled_response}')
elif handled_response == llm_reply:
output = handled_response
elapsed = time.time() - start
panel_narrow = Panel(Markdown(output),
title="LLM Reply",
subtitle=f"Response time: {elapsed:.2f}s",
expand=False,
)
console.print(panel_narrow)
if __name__ == "__main__":
main()